cl: _testdata/printf: almost done
This commit is contained in:
@@ -38,9 +38,8 @@ type context struct {
|
||||
prog llssa.Program
|
||||
pkg llssa.Package
|
||||
fn llssa.Function
|
||||
fns map[*ssa.Function]llssa.Function
|
||||
glbs map[*ssa.Global]llssa.Global
|
||||
bvals map[ssa.Value]llssa.Expr // block values
|
||||
inits []func()
|
||||
}
|
||||
|
||||
func (p *context) compileType(pkg llssa.Package, member *ssa.Type) {
|
||||
@@ -48,41 +47,28 @@ func (p *context) compileType(pkg llssa.Package, member *ssa.Type) {
|
||||
}
|
||||
|
||||
// Global variable.
|
||||
func (p *context) compileGlobal(pkg llssa.Package, gbl *ssa.Global) llssa.Global {
|
||||
if g, ok := p.glbs[gbl]; ok {
|
||||
return g
|
||||
}
|
||||
func (p *context) compileGlobal(pkg llssa.Package, gbl *ssa.Global) {
|
||||
g := pkg.NewVar(gbl.Name(), gbl.Type())
|
||||
g.Init(p.prog.Null(g.Type))
|
||||
p.glbs[gbl] = g
|
||||
return g
|
||||
}
|
||||
|
||||
func (p *context) compileFunc(pkg llssa.Package, f *ssa.Function) llssa.Function {
|
||||
if fn, ok := p.fns[f]; ok {
|
||||
return fn
|
||||
}
|
||||
fn := p.doCompileFunc(pkg, f)
|
||||
p.fns[f] = fn
|
||||
return fn
|
||||
}
|
||||
|
||||
func (p *context) doCompileFunc(pkg llssa.Package, f *ssa.Function) (fn llssa.Function) {
|
||||
fn = pkg.NewFunc(f.Name(), f.Signature)
|
||||
p.fn = fn
|
||||
defer func() {
|
||||
p.fn = nil
|
||||
}()
|
||||
nblk := len(f.Blocks)
|
||||
if nblk == 0 { // external function
|
||||
return
|
||||
}
|
||||
fn.MakeBlocks(nblk)
|
||||
b := fn.NewBuilder()
|
||||
for _, block := range f.Blocks {
|
||||
p.compileBlock(b, block)
|
||||
}
|
||||
return
|
||||
func (p *context) compileFunc(pkg llssa.Package, f *ssa.Function) {
|
||||
fn := pkg.NewFunc(f.Name(), f.Signature)
|
||||
p.inits = append(p.inits, func() {
|
||||
p.fn = fn
|
||||
defer func() {
|
||||
p.fn = nil
|
||||
}()
|
||||
nblk := len(f.Blocks)
|
||||
if nblk == 0 { // external function
|
||||
return
|
||||
}
|
||||
fn.MakeBlocks(nblk)
|
||||
b := fn.NewBuilder()
|
||||
for _, block := range f.Blocks {
|
||||
p.compileBlock(b, block)
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
func (p *context) compileBlock(b llssa.Builder, block *ssa.BasicBlock) llssa.BasicBlock {
|
||||
@@ -101,10 +87,12 @@ func (p *context) compileInstrAndValue(b llssa.Builder, iv instrAndValue) (ret l
|
||||
}
|
||||
switch v := iv.(type) {
|
||||
case *ssa.Call:
|
||||
call := v.Call
|
||||
fn := p.compileValue(b, call.Value)
|
||||
args := p.compileValues(b, call.Args)
|
||||
ret = b.Call(fn, args...)
|
||||
if false {
|
||||
call := v.Call
|
||||
fn := p.compileValue(b, call.Value)
|
||||
args := p.compileValues(b, call.Args)
|
||||
ret = b.Call(fn, args...)
|
||||
}
|
||||
case *ssa.BinOp:
|
||||
x := p.compileValue(b, v.X)
|
||||
y := p.compileValue(b, v.Y)
|
||||
@@ -112,6 +100,13 @@ func (p *context) compileInstrAndValue(b llssa.Builder, iv instrAndValue) (ret l
|
||||
case *ssa.UnOp:
|
||||
x := p.compileValue(b, v.X)
|
||||
ret = b.UnOp(v.Op, x)
|
||||
case *ssa.IndexAddr:
|
||||
x := p.compileValue(b, v.X)
|
||||
idx := p.compileValue(b, v.Index)
|
||||
ret = b.IndexAddr(x, idx)
|
||||
case *ssa.Alloc:
|
||||
t := v.Type()
|
||||
ret = b.Alloc(p.prog.Type(t), v.Heap)
|
||||
default:
|
||||
panic(fmt.Sprintf("compileInstrAndValue: unknown instr - %T\n", iv))
|
||||
}
|
||||
@@ -168,13 +163,14 @@ func (p *context) compileValue(b llssa.Builder, v ssa.Value) llssa.Expr {
|
||||
}
|
||||
}
|
||||
case *ssa.Function:
|
||||
fn := p.compileFunc(p.pkg, v)
|
||||
fn := p.pkg.FuncOf(v.Name())
|
||||
return fn.Expr
|
||||
case *ssa.Global:
|
||||
g := p.compileGlobal(p.pkg, v)
|
||||
g := p.pkg.VarOf(v.Name())
|
||||
return g.Expr
|
||||
case *ssa.Const:
|
||||
return b.Const(v.Value, v.Type())
|
||||
t := v.Type()
|
||||
return b.Const(v.Value, p.prog.Type(t))
|
||||
}
|
||||
panic(fmt.Sprintf("compileValue: unknown value - %T\n", v))
|
||||
}
|
||||
@@ -215,8 +211,6 @@ func NewPackage(prog llssa.Program, pkg *ssa.Package, conf *Config) (ret llssa.P
|
||||
ctx := &context{
|
||||
prog: prog,
|
||||
pkg: ret,
|
||||
fns: make(map[*ssa.Function]llssa.Function),
|
||||
glbs: make(map[*ssa.Global]llssa.Global),
|
||||
}
|
||||
for _, m := range members {
|
||||
member := m.val
|
||||
@@ -233,6 +227,9 @@ func NewPackage(prog llssa.Program, pkg *ssa.Package, conf *Config) (ret llssa.P
|
||||
ctx.compileGlobal(ret, member)
|
||||
}
|
||||
}
|
||||
for _, ini := range ctx.inits {
|
||||
ini()
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user