From 8c45eb7524ead71d71842d118beaf3c1ef9a73f5 Mon Sep 17 00:00:00 2001 From: xushiwei Date: Sun, 30 Jun 2024 11:53:12 +0800 Subject: [PATCH] abitype: support Patch --- cl/compile.go | 16 +++++++--------- internal/typepatch/patch.go | 2 ++ ssa/abitype.go | 3 +++ ssa/package.go | 6 ++++++ 4 files changed, 18 insertions(+), 9 deletions(-) diff --git a/cl/compile.go b/cl/compile.go index b2407bd8..b5a299c6 100644 --- a/cl/compile.go +++ b/cl/compile.go @@ -542,7 +542,7 @@ func (p *context) compileInstrOrValue(b llssa.Builder, iv instrOrValue, asValue prog := p.prog t := prog.Type(v.Type(), llssa.InGo) x := p.compileValue(b, v.X) - ret = b.MakeInterface(t, patchValue(p, x)) + ret = b.MakeInterface(t, x) case *ssa.MakeSlice: var nCap llssa.Expr t := p.prog.Type(v.Type(), llssa.InGo) @@ -790,6 +790,7 @@ func NewPackageEx(prog llssa.Program, patches Patches, pkg *ssa.Package, files [ if hasPatch { skips := ctx.skips typepatch.Merge(pkgTypes, oldTypes, skips, ctx.skipall) + ret.SetPatch(ctx.patchType) ctx.skips = nil ctx.state = pkgInPatch if _, ok := skips["init"]; ok || ctx.skipall { @@ -864,21 +865,18 @@ func globalType(gbl *ssa.Global) types.Type { return t } -func patchValue(ctx *context, v llssa.Expr) llssa.Expr { - /* TODO(xsw): - t := v.RawType() - if t, ok := t.(*types.Named); ok { +func (p *context) patchType(typ types.Type) types.Type { + if t, ok := typ.(*types.Named); ok { o := t.Obj() if pkg := o.Pkg(); typepatch.IsPatched(pkg) { - if patch, ok := ctx.patches[pkg.Path()]; ok { + if patch, ok := p.patches[pkg.Path()]; ok { if obj := patch.Types.Scope().Lookup(o.Name()); obj != nil { - v.Type = ctx.prog.Type(obj.Type(), llssa.InGo) + return p.prog.Type(obj.Type(), llssa.InGo).RawType() } } } } - */ - return v + return typ } // ----------------------------------------------------------------------------- diff --git a/internal/typepatch/patch.go b/internal/typepatch/patch.go index 9a94f8f3..8dcd5ccd 100644 --- a/internal/typepatch/patch.go +++ b/internal/typepatch/patch.go @@ -89,9 +89,11 @@ func Merge(alt, pkg *types.Package, skips map[string]struct{}, skipall bool) { scope := *alt.Scope() old := getElems(&scope) elems := make(map[string]types.Object, len(old)) + for name, o := range old { elems[name] = o } + setElems(&scope, elems) setScope(alt, &scope) diff --git a/ssa/abitype.go b/ssa/abitype.go index 4e4009e3..c1110bc1 100644 --- a/ssa/abitype.go +++ b/ssa/abitype.go @@ -315,6 +315,9 @@ func lastParamType(prog Program, fn Expr) Type { func (p Package) abiTypeInit(g Global, t types.Type, pub bool) { b := p.afterBuilder() + if p.patch != nil { + t = p.patch(t) + } tabi := b.abiTypeOf(t) expr := g.Expr var eq Expr diff --git a/ssa/package.go b/ssa/package.go index 09d2d50a..fc5a404a 100644 --- a/ssa/package.go +++ b/ssa/package.go @@ -568,6 +568,7 @@ type aPackage struct { strs map[string]llvm.Value named map[types.Type]Expr afterb unsafe.Pointer + patch func(types.Type) types.Type iRoutine int } @@ -635,6 +636,11 @@ func (p Package) String() string { return p.mod.String() } +// SetPatch sets a patch function. +func (p Package) SetPatch(fn func(types.Type) types.Type) { + p.patch = fn +} + // ----------------------------------------------------------------------------- func (p Package) afterBuilder() Builder {