Commit 9f2dfb85 authored by Russ Cox's avatar Russ Cox

cmd/objdump: add arm disassembler

Fixes #7452.

LGTM=minux, iant
R=minux, iant
CC=golang-codereviews
https://golang.org/cl/104770046
parent 300f3c49
all: x86.go armasm.go
x86.go: bundle
./bundle -p main -x x86_ rsc.io/x86/x86asm | gofmt >x86.go
armasm.go: bundle
./bundle -p main -x arm_ rsc.io/arm/armasm | gofmt >armasm.go
bundle:
go build -o bundle code.google.com/p/rsc/cmd/bundle
This diff is collapsed.
......@@ -42,6 +42,7 @@ import (
"debug/macho"
"debug/pe"
"debug/plan9obj"
"encoding/binary"
"flag"
"fmt"
"io"
......@@ -135,7 +136,7 @@ func main() {
if flag.NArg() == 1 {
// disassembly of entire object - our format
dump(tab, lookup, disasm, syms, textData, textStart)
dump(tab, lookup, disasm, goarch, syms, textData, textStart)
os.Exit(exitCode)
}
......@@ -152,7 +153,7 @@ func base(path string) string {
return path
}
func dump(tab *gosym.Table, lookup lookupFunc, disasm disasmFunc, syms []Sym, textData []byte, textStart uint64) {
func dump(tab *gosym.Table, lookup lookupFunc, disasm disasmFunc, goarch string, syms []Sym, textData []byte, textStart uint64) {
stdout := bufio.NewWriter(os.Stdout)
defer stdout.Flush()
......@@ -178,7 +179,14 @@ func dump(tab *gosym.Table, lookup lookupFunc, disasm disasmFunc, syms []Sym, te
i := pc - textStart
text, size := disasm(textData[i:end-textStart], pc, lookup)
file, line, _ := tab.PCToLine(pc)
fmt.Fprintf(tw, "\t%s:%d\t%#x\t%x\t%s\n", base(file), line, pc, textData[i:i+uint64(size)], text)
// ARM is word-based, so show actual word hex, not byte hex.
// Since ARM is little endian, they're different.
if goarch == "arm" && size == 4 {
fmt.Fprintf(tw, "\t%s:%d\t%#x\t%08x\t%s\n", base(file), line, pc, binary.LittleEndian.Uint32(textData[i:i+uint64(size)]), text)
} else {
fmt.Fprintf(tw, "\t%s:%d\t%#x\t%x\t%s\n", base(file), line, pc, textData[i:i+uint64(size)], text)
}
pc += uint64(size)
}
tw.Flush()
......@@ -206,19 +214,37 @@ func disasm_x86(code []byte, pc uint64, lookup lookupFunc, arch int) (string, in
return text, size
}
type textReader struct {
code []byte
pc uint64
}
func (r textReader) ReadAt(data []byte, off int64) (n int, err error) {
if off < 0 || uint64(off) < r.pc {
return 0, io.EOF
}
d := uint64(off) - r.pc
if d >= uint64(len(r.code)) {
return 0, io.EOF
}
n = copy(data, r.code[d:])
if n < len(data) {
err = io.ErrUnexpectedEOF
}
return
}
func disasm_arm(code []byte, pc uint64, lookup lookupFunc) (string, int) {
/*
inst, size, err := arm_Decode(code, 64)
var text string
if err != nil || size == 0 || inst.Op == 0 {
size = 1
text = "?"
} else {
text = arm_plan9Syntax(inst, pc, lookup)
}
return text, size
*/
return "?", 4
inst, err := arm_Decode(code, arm_ModeARM)
var text string
size := inst.Len
if err != nil || size == 0 || inst.Op == 0 {
size = 4
text = "?"
} else {
text = arm_plan9Syntax(inst, pc, lookup, textReader{code, pc})
}
return text, size
}
var disasms = map[string]disasmFunc{
......
......@@ -140,7 +140,7 @@ var x86Need = []string{
var armNeed = []string{
"fmthello.go:6",
"TEXT main.main(SB)",
"B main.main(SB)",
"B.LS main.main(SB)",
"BL fmt.Println(SB)",
"RET",
}
......@@ -172,7 +172,6 @@ func TestDisasm(t *testing.T) {
need = append(need, x86Need...)
case "arm":
need = append(need, armNeed...)
t.Skip("disassembler not ready on arm yet")
}
out, err = exec.Command(exe, "-s", "main.main", hello).CombinedOutput()
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment