// FormatCommand implements the debugger command: format // // format // // Formats AST and produces source text for function. // FIXME: allow one to specify a function or package func FormatCommand(args []string) { var syntax ast.Node var err error fr := gub.CurFrame() fn := fr.Fn() if len(args) > 1 { name := args[1] if name != "." { fn, err = gub.FuncLookup(name) if err != nil { gub.Errmsg(err.Error()) return } else if fn == nil { gub.Errmsg("function '%s' not found", name) return } } syntax = fn.Syntax() } else { syntax = fn.Syntax() switch s := (*gub.Instr).(type) { case *ssa2.Trace: syntax = s.Syntax() } } // FIXME: Put this as a routine in parent gub and // use when showing locations if syntax != nil { gub.PrintSyntax(syntax, fn.Prog.Fset) } else { gub.Msg("Sorry, we don't have an AST for this") } }
// AstCommand implements the debugger command: ast // // ast // // Prints AST for current function. func AstCommand(args []string) { var syntax ast.Node var err error fr := gub.CurFrame() fn := fr.Fn() if len(args) > 1 { name := args[1] fn, err = gub.FuncLookup(name) if err != nil { gub.Errmsg(err.Error()) return } else if fn == nil { gub.Errmsg("function '%s' not found", name) return } else { syntax = fn.Syntax() } } else { syntax = fn.Syntax() switch s := (*gub.Instr).(type) { case *ssa2.Trace: syntax = s.Syntax() } } if syntax != nil { ast.Print(fn.Prog.Fset, syntax) fmt.Println("") } else { gub.Msg("Sorry, we don't have an AST for this") } }
func DisassembleCommand(args []string) { fr := gub.CurFrame() myfn := fr.Fn() if len(args) > 1 { what := args[1] if what == "." { if block := gub.CurBlock(); block != nil { gub.DisasmBlock(myfn, block.Index, fr.PC()) } else { gub.Errmsg("Can't get block info here") } return } else if what != "+" { if fn, err := gub.FuncLookup(what); err == nil && fn != nil { myfn = fn } else { bnum, err := gub.GetInt(args[1], "block number of function name", 0, len(myfn.Blocks)-1) if err == nil { lastBlock := len(myfn.Blocks) - 1 if bnum <= lastBlock { b := myfn.Blocks[bnum] if len(args) == 3 { ic, err := gub.GetUInt(args[2], "instruction number", 0, uint64(len(b.Instrs)-1)) if err == nil { gub.DisasmInst(myfn, bnum, ic) } } else { gub.DisasmBlock(myfn, bnum, -1) } } else { gub.Errmsg("Block number should be between 0 and %d; got %d", lastBlock, bnum) } } return } } } else { gub.DisasmCurrentInst() return } myfn.WriteTo(os.Stderr) }