Commit 24a43e6a authored by Rob Pike's avatar Rob Pike

cmd/internal/obj: delete all Pconv, replace with Prog.String

Remove the per-achitecture formatter for Prog and replace it with
a global String method. Clean up and regularize the output. Update
tests affected by the format; some tests are made correct now when
they were broken before (and known to be).

Also, related: Change the encoding of the (R1+R2) syntax on ppc64
to be equivalent to (R1)(R2*1), which means it needs no special
handling.

Delete the now unused STRINGSZ constant.

Change-Id: I7f6654d11f80065f3914a3f19353f2f12edfe310
Reviewed-on: https://go-review.googlesource.com/6931Reviewed-by: default avatarRuss Cox <rsc@golang.org>
parent d5b5d670
......@@ -81,7 +81,6 @@ func jumpX86(word string) bool {
func archX86(linkArch *obj.LinkArch) *Arch {
register := make(map[string]int16)
// Create maps for easy lookup of instruction names etc.
// TODO: Should this be done in obj for us?
for i, s := range x86.Register {
register[s] = int16(i + x86.REG_AL)
}
......@@ -154,9 +153,7 @@ func archX86(linkArch *obj.LinkArch) *Arch {
func archArm() *Arch {
register := make(map[string]int16)
// Create maps for easy lookup of instruction names etc.
// TODO: Should this be done in obj for us?
// Note that there is no list of names as there is for x86.
// TODO: Are there aliases we need to add?
for i := arm.REG_R0; i < arm.REG_SPSR; i++ {
register[obj.Rconv(i)] = int16(i)
}
......@@ -203,7 +200,6 @@ func archArm() *Arch {
func archPPC64() *Arch {
register := make(map[string]int16)
// Create maps for easy lookup of instruction names etc.
// TODO: Should this be done in obj for us?
// Note that there is no list of names as there is for x86.
for i := ppc64.REG_R0; i <= ppc64.REG_R31; i++ {
register[obj.Rconv(i)] = int16(i)
......
......@@ -460,21 +460,6 @@ func (p *Parser) asmInstruction(op int, cond string, a []obj.Addr) {
}
prog.From = a[0]
prog.To = a[1]
switch p.arch.Thechar {
case '9':
var reg0, reg1 int16
// Handle (R1+R2)
if a[0].Scale != 0 {
reg0 = int16(a[0].Scale)
prog.Reg = reg0
} else if a[1].Scale != 0 {
reg1 = int16(a[1].Scale)
prog.Reg = reg1
}
if reg0 != 0 && reg1 != 0 {
p.errorf("register pair cannot be both left and right operands")
}
}
case 3:
switch p.arch.Thechar {
case '5':
......
......@@ -59,18 +59,6 @@ func TestARMOperandParser(t *testing.T) {
func TestPPC64OperandParser(t *testing.T) {
parser := newParser("ppc64")
testOperandParser(t, parser, ppc64OperandTests)
// Special encoding for (R1+R2).
parser.start(lex.Tokenize("(R1+R2)"))
addr := obj.Addr{}
parser.operand(&addr)
want := obj.Addr{
Type: obj.TYPE_MEM,
Reg: parser.arch.Register["R1"],
Scale: parser.arch.Register["R2"], // TODO: clean up how this is encoded in parse.go
}
if want != addr {
t.Errorf("(R1+R2): expected %+v got %+v", want, addr)
}
}
type operandTest struct {
......@@ -321,6 +309,8 @@ var ppc64OperandTests = []operandTest{
{"(R3)", "(R3)"},
{"(R4)", "(R4)"},
{"(R5)", "(R5)"},
{"(R5)(R6*1)", "(R5)(R6*1)"},
{"(R5+R6)", "(R5)(R6*1)"}, // Old syntax.
{"-1(R4)", "-1(R4)"},
{"-1(R5)", "-1(R5)"},
{"6(PC)", "6(PC)"},
......
......@@ -646,9 +646,9 @@ func (p *Parser) registerIndirect(a *obj.Addr, prefix rune) {
p.errorf("illegal address mode for register pair")
return
}
// TODO: This is rewritten in asm. Clumsy.
a.Type = obj.TYPE_MEM
a.Scale = r2
a.Scale = 1
a.Index = r2
// Nothing may follow.
return
}
......
5 00001 (testdata/arm.s:5) TEXT foo(SB),0,$0
14 00002 (testdata/arm.s:14) ADD $1,R2,R3
15 00003 (testdata/arm.s:15) ADD R1<<R2,R3,R4
16 00004 (testdata/arm.s:16) ADD R1>>R2,R3,R4
17 00005 (testdata/arm.s:17) ADD R1@>R2,R3,R4
18 00006 (testdata/arm.s:18) ADD R1->R2,R3,R4
19 00007 (testdata/arm.s:19) ADD R1,R2,R3
20 00008 (testdata/arm.s:20) ADD R1<<R2,R3,R4
30 00009 (testdata/arm.s:30) ADD $1,R2
31 00010 (testdata/arm.s:31) ADD R1<<R2,R3
32 00011 (testdata/arm.s:32) ADD R1>>R2,R3
33 00012 (testdata/arm.s:33) ADD R1@>R2,R3
34 00013 (testdata/arm.s:34) ADD R1->R2,R3
35 00014 (testdata/arm.s:35) ADD R1,R2
44 00015 (testdata/arm.s:44) CLZ.S R1,R2
53 00016 (testdata/arm.s:53) MOVW.S R1,R2
54 00017 (testdata/arm.s:54) MOVW.S $1,R2
55 00018 (testdata/arm.s:55) MOVW.S R1<<R2,R3
64 00019 (testdata/arm.s:64) JMP.S ,20(PC)
70 00020 (testdata/arm.s:70) JMP.S ,(R2)
71 00021 (testdata/arm.s:71) JMP.S ,foo(SB)
72 00022 (testdata/arm.s:72) JMP.S ,bar<>(SB)
81 00023 (testdata/arm.s:81) BX (R2),
90 00024 (testdata/arm.s:90) BEQ ,25(PC)
99 00025 (testdata/arm.s:99) SWI.S ,R1
100 00026 (testdata/arm.s:100) SWI.S ,(R1)
101 00027 (testdata/arm.s:101) SWI.S ,foo(SB)
110 00028 (testdata/arm.s:110) CMP.S $1,R2,
111 00029 (testdata/arm.s:111) CMP.S R1<<R2,R3,
112 00030 (testdata/arm.s:112) CMP.S R1,R2,
126 00031 (testdata/arm.s:126) MOVM (R1),[R2,R5,R8,g]
127 00032 (testdata/arm.s:127) MOVM (R1),[R2,R3,R4,R5]
128 00033 (testdata/arm.s:128) MOVM.S (R1),[R2]
139 00034 (testdata/arm.s:139) MOVM [R2,R5,R8,g],(R1)
140 00035 (testdata/arm.s:140) MOVM [R2,R3,R4,R5],(R1)
141 00036 (testdata/arm.s:141) MOVM.S [R2],(R1)
150 00037 (testdata/arm.s:150) STREX.S (R2),R1,R3
156 00038 (testdata/arm.s:156) STREX.S (R2),R1,R1
162 00039 (testdata/arm.s:162) STREX.S (R2),R3,R3
170 00040 (testdata/arm.s:170) CASE.S R1,
179 00041 (testdata/arm.s:179) WORD ,$1234
188 00042 (testdata/arm.s:188) ABSF.S F1,F2
194 00043 (testdata/arm.s:194) ADDD.S F1,F2
195 00044 (testdata/arm.s:195) ADDD.S $(0.5),F2
201 00045 (testdata/arm.s:201) ADDD.S F1,F2,F3
202 00046 (testdata/arm.s:202) ADDD.S $(0.5),F2,F3
208 00047 (testdata/arm.s:208) CMPD.S F1,F2
242 00048 (testdata/arm.s:242) MULL R1,R2,(R3, R4)
254 00049 (testdata/arm.s:254) MULAWT R1,R2,R3, R4
262 00050 (testdata/arm.s:262) PLD (R1),
263 00051 (testdata/arm.s:263) PLD 4(R1),
272 00052 (testdata/arm.s:272) RET ,
281 00053 (testdata/arm.s:281) END ,
5 00001 (testdata/arm.s:5) TEXT foo(SB), 0, $0
14 00002 (testdata/arm.s:14) ADD $1, R2, R3
15 00003 (testdata/arm.s:15) ADD R1<<R2, R3, R4
16 00004 (testdata/arm.s:16) ADD R1>>R2, R3, R4
17 00005 (testdata/arm.s:17) ADD R1@>R2, R3, R4
18 00006 (testdata/arm.s:18) ADD R1->R2, R3, R4
19 00007 (testdata/arm.s:19) ADD R1, R2, R3
20 00008 (testdata/arm.s:20) ADD R1<<R2, R3, R4
30 00009 (testdata/arm.s:30) ADD $1, R2
31 00010 (testdata/arm.s:31) ADD R1<<R2, R3
32 00011 (testdata/arm.s:32) ADD R1>>R2, R3
33 00012 (testdata/arm.s:33) ADD R1@>R2, R3
34 00013 (testdata/arm.s:34) ADD R1->R2, R3
35 00014 (testdata/arm.s:35) ADD R1, R2
44 00015 (testdata/arm.s:44) CLZ.S R1, R2
53 00016 (testdata/arm.s:53) MOVW.S R1, R2
54 00017 (testdata/arm.s:54) MOVW.S $1, R2
55 00018 (testdata/arm.s:55) MOVW.S R1<<R2, R3
64 00019 (testdata/arm.s:64) JMP.S 20(PC)
70 00020 (testdata/arm.s:70) JMP.S (R2)
71 00021 (testdata/arm.s:71) JMP.S foo(SB)
72 00022 (testdata/arm.s:72) JMP.S bar<>(SB)
81 00023 (testdata/arm.s:81) BX (R2)
90 00024 (testdata/arm.s:90) BEQ 25(PC)
99 00025 (testdata/arm.s:99) SWI.S R1
100 00026 (testdata/arm.s:100) SWI.S (R1)
101 00027 (testdata/arm.s:101) SWI.S foo(SB)
110 00028 (testdata/arm.s:110) CMP.S $1, R2
111 00029 (testdata/arm.s:111) CMP.S R1<<R2, R3
112 00030 (testdata/arm.s:112) CMP.S R1, R2
126 00031 (testdata/arm.s:126) MOVM (R1), [R2,R5,R8,g]
127 00032 (testdata/arm.s:127) MOVM (R1), [R2,R3,R4,R5]
128 00033 (testdata/arm.s:128) MOVM.S (R1), [R2]
139 00034 (testdata/arm.s:139) MOVM [R2,R5,R8,g], (R1)
140 00035 (testdata/arm.s:140) MOVM [R2,R3,R4,R5], (R1)
141 00036 (testdata/arm.s:141) MOVM.S [R2], (R1)
150 00037 (testdata/arm.s:150) STREX.S (R2), R1, R3
156 00038 (testdata/arm.s:156) STREX.S (R2), R1, R1
162 00039 (testdata/arm.s:162) STREX.S (R2), R3, R3
170 00040 (testdata/arm.s:170) CASE.S R1
179 00041 (testdata/arm.s:179) WORD $1234
188 00042 (testdata/arm.s:188) ABSF.S F1, F2
194 00043 (testdata/arm.s:194) ADDD.S F1, F2
195 00044 (testdata/arm.s:195) ADDD.S $(0.5), F2
201 00045 (testdata/arm.s:201) ADDD.S F1, F2, F3
202 00046 (testdata/arm.s:202) ADDD.S $(0.5), F2, F3
208 00047 (testdata/arm.s:208) CMPD.S F1, F2
242 00048 (testdata/arm.s:242) MULL R1, R2, (R3, R4)
254 00049 (testdata/arm.s:254) MULAWT R1, R2, R3, R4
262 00050 (testdata/arm.s:262) PLD (R1)
263 00051 (testdata/arm.s:263) PLD 4(R1)
272 00052 (testdata/arm.s:272) RET
281 00053 (testdata/arm.s:281) END
This diff is collapsed.
......@@ -81,7 +81,6 @@ const (
EOF = -1
IGN = -2
NHASH = 503
STRINGSZ = 200
NMACRO = 10
)
......
......@@ -24,12 +24,15 @@ const (
BUFSIZ = 8192
NSYMB = 500
NHASH = 1024
STRINGSZ = 200
MAXALIGN = 7
UINF = 100
PRIME1 = 3
AUNK = 100
AMEM = 0 + iota - 9
BADWIDTH = -1000000000
MaxStackVarSize = 10 * 1024 * 1024
)
const (
AMEM = iota
AMEM0
AMEM8
AMEM16
......@@ -51,8 +54,7 @@ const (
AFLOAT64
ACPLX64
ACPLX128
BADWIDTH = -1000000000
MaxStackVarSize = 10 * 1024 * 1024
AUNK = 100
)
const (
......
......@@ -32,9 +32,6 @@ package arm
import "cmd/internal/obj"
// TODO(ality): remove this workaround.
// It's here because Pconv in liblink/list?.c references %L.
const (
NSNAME = 8
NSYM = 50
......
......@@ -35,67 +35,6 @@ import (
"fmt"
)
const (
STRINGSZ = 1000
)
var extra = []string{
".EQ",
".NE",
".CS",
".CC",
".MI",
".PL",
".VS",
".VC",
".HI",
".LS",
".GE",
".LT",
".GT",
".LE",
"",
".NV",
}
var bigP *obj.Prog
func Pconv(p *obj.Prog) string {
a := int(p.As)
s := int(p.Scond)
sc := extra[(s&C_SCOND)^C_SCOND_XOR]
if s&C_SBIT != 0 {
sc += ".S"
}
if s&C_PBIT != 0 {
sc += ".P"
}
if s&C_WBIT != 0 {
sc += ".W"
}
if s&C_UBIT != 0 { /* ambiguous with FBIT */
sc += ".U"
}
var str string
if a == obj.ADATA {
str = fmt.Sprintf("%.5d (%v)\t%v\t%v/%d,%v",
p.Pc, p.Line(), obj.Aconv(a), obj.Dconv(p, &p.From), p.From3.Offset, obj.Dconv(p, &p.To))
} else if p.As == obj.ATEXT {
str = fmt.Sprintf("%.5d (%v)\t%v\t%v,%d,%v",
p.Pc, p.Line(), obj.Aconv(a), obj.Dconv(p, &p.From), p.From3.Offset, obj.Dconv(p, &p.To))
} else if p.Reg == 0 {
str = fmt.Sprintf("%.5d (%v)\t%v%s\t%v,%v",
p.Pc, p.Line(), obj.Aconv(a), sc, obj.Dconv(p, &p.From), obj.Dconv(p, &p.To))
} else {
str = fmt.Sprintf("%.5d (%v)\t%v%s\t%v,%v,%v",
p.Pc, p.Line(), obj.Aconv(a), sc, obj.Dconv(p, &p.From), Rconv(int(p.Reg)), obj.Dconv(p, &p.To))
}
var fp string
fp += str
return fp
}
func init() {
obj.RegisterRegister(obj.RBaseARM, MAXREG, Rconv)
obj.RegisterOpcode(obj.ABaseARM, Anames)
......
......@@ -1045,7 +1045,6 @@ var unaryDst = map[int]bool{
var Linkarm = obj.LinkArch{
ByteOrder: binary.LittleEndian,
Pconv: Pconv,
Name: "arm",
Thechar: '5',
Preprocess: preprocess,
......
......@@ -234,7 +234,6 @@ type Plist struct {
}
type LinkArch struct {
Pconv func(*Prog) string
ByteOrder binary.ByteOrder
Name string
Thechar int
......@@ -382,7 +381,16 @@ type Pciter struct {
// offset = bit mask of registers in list; R0 is low bit.
//
// reg, reg
// TYPE_REGREG2, to be removed.
// Register pair for ARM.
// TYPE_REGREG2
//
// (reg+reg)
// Register pair for PPC64.
// Encoding:
// type = TYPE_MEM
// reg = first register
// index = second register
// scale = 1
//
const (
......
......@@ -604,7 +604,7 @@ func aclass(ctxt *obj.Link, a *obj.Addr) int {
}
return C_LAUTO
case obj.TYPE_NONE:
case obj.NAME_NONE:
ctxt.Instoffset = a.Offset
if ctxt.Instoffset == 0 {
return C_ZOREG
......@@ -1579,11 +1579,11 @@ func asmout(ctxt *obj.Link, p *obj.Prog, o *Optab, out []uint32) {
r = int(o.param)
}
v := regoff(ctxt, &p.To)
if p.To.Type == obj.TYPE_MEM && p.Reg != 0 {
if p.To.Type == obj.TYPE_MEM && p.To.Index != 0 {
if v != 0 {
ctxt.Diag("illegal indexed instruction\n%v", p)
}
o1 = AOP_RRR(uint32(opstorex(ctxt, int(p.As))), uint32(p.From.Reg), uint32(p.Reg), uint32(r))
o1 = AOP_RRR(uint32(opstorex(ctxt, int(p.As))), uint32(p.From.Reg), uint32(p.To.Index), uint32(r))
} else {
if int32(int16(v)) != v {
log.Fatalf("mishandled instruction %v", p)
......@@ -1598,11 +1598,11 @@ func asmout(ctxt *obj.Link, p *obj.Prog, o *Optab, out []uint32) {
r = int(o.param)
}
v := regoff(ctxt, &p.From)
if p.From.Type == obj.TYPE_MEM && p.Reg != 0 {
if p.From.Type == obj.TYPE_MEM && p.From.Index != 0 {
if v != 0 {
ctxt.Diag("illegal indexed instruction\n%v", p)
}
o1 = AOP_RRR(uint32(oploadx(ctxt, int(p.As))), uint32(p.To.Reg), uint32(p.Reg), uint32(r))
o1 = AOP_RRR(uint32(oploadx(ctxt, int(p.As))), uint32(p.To.Reg), uint32(p.From.Index), uint32(r))
} else {
if int32(int16(v)) != v {
log.Fatalf("mishandled instruction %v", p)
......@@ -1617,11 +1617,11 @@ func asmout(ctxt *obj.Link, p *obj.Prog, o *Optab, out []uint32) {
r = int(o.param)
}
v := regoff(ctxt, &p.From)
if p.From.Type == obj.TYPE_MEM && p.Reg != 0 {
if p.From.Type == obj.TYPE_MEM && p.From.Index != 0 {
if v != 0 {
ctxt.Diag("illegal indexed instruction\n%v", p)
}
o1 = AOP_RRR(uint32(oploadx(ctxt, int(p.As))), uint32(p.To.Reg), uint32(p.Reg), uint32(r))
o1 = AOP_RRR(uint32(oploadx(ctxt, int(p.As))), uint32(p.To.Reg), uint32(p.From.Index), uint32(r))
} else {
o1 = AOP_IRR(uint32(opload(ctxt, int(p.As))), uint32(p.To.Reg), uint32(r), uint32(v))
}
......@@ -1764,16 +1764,12 @@ func asmout(ctxt *obj.Link, p *obj.Prog, o *Optab, out []uint32) {
} else {
v = 20 /* unconditional */
}
r := int(p.Reg)
if r == 0 {
r = 0
}
o1 = AOP_RRR(OP_MTSPR, uint32(p.To.Reg), 0, 0) | (REG_LR&0x1f)<<16 | ((REG_LR>>5)&0x1f)<<11
o2 = OPVCC(19, 16, 0, 0)
if p.As == ABL || p.As == ABCL {
o2 |= 1
}
o2 = OP_BCR(o2, uint32(v), uint32(r))
o2 = OP_BCR(o2, uint32(v), uint32(p.To.Index))
case 18: /* br/bl (lr/ctr); bc/bcl bo,bi,(lr/ctr) */
var v int32
......@@ -2085,28 +2081,13 @@ func asmout(ctxt *obj.Link, p *obj.Prog, o *Optab, out []uint32) {
o1 = AOP_RRR(uint32(opirr(ctxt, int(p.As))), uint32(p.To.Reg), uint32(p.From.Reg), 0) | (uint32(regoff(ctxt, &p.From3))&0x7F)<<11
case 43: /* unary indexed source: dcbf (b); dcbf (a+b) */
r := int(p.Reg)
if r == 0 {
r = 0
}
o1 = AOP_RRR(uint32(oprrr(ctxt, int(p.As))), 0, uint32(r), uint32(p.From.Reg))
o1 = AOP_RRR(uint32(oprrr(ctxt, int(p.As))), 0, uint32(p.From.Index), uint32(p.From.Reg))
case 44: /* indexed store */
r := int(p.Reg)
if r == 0 {
r = 0
}
o1 = AOP_RRR(uint32(opstorex(ctxt, int(p.As))), uint32(p.From.Reg), uint32(r), uint32(p.To.Reg))
o1 = AOP_RRR(uint32(opstorex(ctxt, int(p.As))), uint32(p.From.Reg), uint32(p.To.Index), uint32(p.To.Reg))
case 45: /* indexed load */
r := int(p.Reg)
if r == 0 {
r = 0
}
o1 = AOP_RRR(uint32(oploadx(ctxt, int(p.As))), uint32(p.To.Reg), uint32(r), uint32(p.From.Reg))
o1 = AOP_RRR(uint32(oploadx(ctxt, int(p.As))), uint32(p.To.Reg), uint32(p.From.Index), uint32(p.From.Reg))
case 46: /* plain op */
o1 = uint32(oprrr(ctxt, int(p.As)))
......
......@@ -34,85 +34,6 @@ import (
"fmt"
)
const (
STRINGSZ = 1000
)
//
// Format conversions
// %A int Opcodes (instruction mnemonics)
//
// %D Addr* Addresses (instruction operands)
//
// %P Prog* Instructions
//
// %R int Registers
//
// %$ char* String constant addresses (for internal use only)
// %^ int C_* classes (for liblink internal use)
var bigP *obj.Prog
func Pconv(p *obj.Prog) string {
a := int(p.As)
str := ""
if a == obj.ADATA {
str = fmt.Sprintf("%.5d (%v)\t%v\t%v/%d,%v",
p.Pc, p.Line(), obj.Aconv(a), obj.Dconv(p, &p.From), p.From3.Offset, obj.Dconv(p, &p.To))
} else if a == obj.ATEXT || a == obj.AGLOBL {
if p.From3.Offset != 0 {
str = fmt.Sprintf("%.5d (%v)\t%v\t%v,%d,%v",
p.Pc, p.Line(), obj.Aconv(a), obj.Dconv(p, &p.From), p.From3.Offset, obj.Dconv(p, &p.To))
} else {
str = fmt.Sprintf("%.5d (%v)\t%v\t%v,%v",
p.Pc, p.Line(), obj.Aconv(a), obj.Dconv(p, &p.From), obj.Dconv(p, &p.To))
}
} else {
if p.Mark&NOSCHED != 0 {
str += fmt.Sprintf("*")
}
if p.Reg == 0 && p.From3.Type == obj.TYPE_NONE {
str += fmt.Sprintf("%.5d (%v)\t%v\t%v,%v",
p.Pc, p.Line(), obj.Aconv(a), obj.Dconv(p, &p.From), obj.Dconv(p, &p.To))
} else if a != obj.ATEXT && p.From.Type == obj.TYPE_MEM {
off := ""
if p.From.Offset != 0 {
off = fmt.Sprintf("%d", p.From.Offset)
}
str += fmt.Sprintf("%.5d (%v)\t%v\t%s(%v+%v),%v",
p.Pc, p.Line(), obj.Aconv(a), off, Rconv(int(p.From.Reg)), Rconv(int(p.Reg)), obj.Dconv(p, &p.To))
} else if p.To.Type == obj.TYPE_MEM {
off := ""
if p.From.Offset != 0 {
off = fmt.Sprintf("%d", p.From.Offset)
}
str += fmt.Sprintf("%.5d (%v)\t%v\t%v,%s(%v+%v)",
p.Pc, p.Line(), obj.Aconv(a), obj.Dconv(p, &p.From), off, Rconv(int(p.To.Reg)), Rconv(int(p.Reg)))
} else {
str += fmt.Sprintf("%.5d (%v)\t%v\t%v",
p.Pc, p.Line(), obj.Aconv(a), obj.Dconv(p, &p.From))
if p.Reg != 0 {
str += fmt.Sprintf(",%v", Rconv(int(p.Reg)))
}
if p.From3.Type != obj.TYPE_NONE {
str += fmt.Sprintf(",%v", obj.Dconv(p, &p.From3))
}
str += fmt.Sprintf(",%v", obj.Dconv(p, &p.To))
}
if p.Spadj != 0 {
var fp string
fp += fmt.Sprintf("%s # spadj=%d", str, p.Spadj)
return fp
}
}
var fp string
fp += str
return fp
}
func init() {
obj.RegisterRegister(obj.RBasePPC64, REG_DCR0+1024, Rconv)
obj.RegisterOpcode(obj.ABasePPC64, Anames)
......
......@@ -949,7 +949,6 @@ loop:
var Linkppc64 = obj.LinkArch{
ByteOrder: binary.BigEndian,
Pconv: Pconv,
Name: "ppc64",
Thechar: '9',
Preprocess: preprocess,
......@@ -963,7 +962,6 @@ var Linkppc64 = obj.LinkArch{
var Linkppc64le = obj.LinkArch{
ByteOrder: binary.LittleEndian,
Pconv: Pconv,
Name: "ppc64le",
Thechar: '9',
Preprocess: preprocess,
......
......@@ -6,6 +6,7 @@ package obj
import (
"bufio"
"bytes"
"fmt"
"io"
"log"
......@@ -248,11 +249,90 @@ func (p *Prog) Line() string {
return Linklinefmt(p.Ctxt, int(p.Lineno), false, false)
}
var armCondCode = []string{
".EQ",
".NE",
".CS",
".CC",
".MI",
".PL",
".VS",
".VC",
".HI",
".LS",
".GE",
".LT",
".GT",
".LE",
"",
".NV",
}
/* ARM scond byte */
const (
C_SCOND = (1 << 4) - 1
C_SBIT = 1 << 4
C_PBIT = 1 << 5
C_WBIT = 1 << 6
C_FBIT = 1 << 7
C_UBIT = 1 << 7
C_SCOND_XOR = 14
)
// CConv formats ARM condition codes.
func CConv(s uint8) string {
if s == 0 {
return ""
}
sc := armCondCode[(s&C_SCOND)^C_SCOND_XOR]
if s&C_SBIT != 0 {
sc += ".S"
}
if s&C_PBIT != 0 {
sc += ".P"
}
if s&C_WBIT != 0 {
sc += ".W"
}
if s&C_UBIT != 0 { /* ambiguous with FBIT */
sc += ".U"
}
return sc
}
func (p *Prog) String() string {
if p.Ctxt == nil {
return "<Prog without ctxt>"
}
return p.Ctxt.Arch.Pconv(p)
sc := CConv(p.Scond)
var buf bytes.Buffer
fmt.Fprintf(&buf, "%.5d (%v)\t%v%s", p.Pc, p.Line(), Aconv(int(p.As)), sc)
sep := "\t"
if p.From.Type != TYPE_NONE {
fmt.Fprintf(&buf, "%s%v", sep, Dconv(p, &p.From))
sep = ", "
}
if p.Reg != REG_NONE {
// Should not happen but might as well show it if it does.
fmt.Fprintf(&buf, "%s%v", sep, Rconv(int(p.Reg)))
sep = ", "
}
if p.From3.Type != TYPE_NONE {
if p.From3.Type == TYPE_CONST && (p.As == ADATA || p.As == ATEXT || p.As == AGLOBL) {
// Special case - omit $.
fmt.Fprintf(&buf, "%s%d", sep, p.From3.Offset)
} else {
fmt.Fprintf(&buf, "%s%v", sep, Dconv(p, &p.From3))
}
sep = ", "
}
if p.To.Type != TYPE_NONE {
fmt.Fprintf(&buf, "%s%v", sep, Dconv(p, &p.To))
}
return buf.String()
}
func (ctxt *Link) NewProg() *Prog {
......
......@@ -31,58 +31,10 @@
package x86
import (
"bytes"
"cmd/internal/obj"
"fmt"
)
//
// Format conversions
// %A int Opcodes (instruction mnemonics)
//
// %D Addr* Addresses (instruction operands)
//
// %P Prog* Instructions
//
// %R int Registers
//
// %$ char* String constant addresses (for internal use only)
const (
STRINGSZ = 1000
)
var bigP *obj.Prog
func Pconv(p *obj.Prog) string {
var buf bytes.Buffer
fmt.Fprintf(&buf, "%.5d (%v)\t%v", p.Pc, p.Line(), obj.Aconv(int(p.As)))
sep := "\t"
if p.From.Type != obj.TYPE_NONE {
fmt.Fprintf(&buf, "%s%v", sep, obj.Dconv(p, &p.From))
sep = ", "
}
if p.Reg != obj.REG_NONE {
// Should not happen but might as well show it if it does.
fmt.Fprintf(&buf, "%s%v", sep, obj.Rconv(int(p.Reg)))
sep = ", "
}
if p.From3.Type != obj.TYPE_NONE {
if p.From3.Type == obj.TYPE_CONST && (p.As == obj.ADATA || p.As == obj.ATEXT || p.As == obj.AGLOBL) {
// Special case - omit $.
fmt.Fprintf(&buf, "%s%d", sep, p.From3.Offset)
} else {
fmt.Fprintf(&buf, "%s%v", sep, obj.Dconv(p, &p.From3))
}
sep = ", "
}
if p.To.Type != obj.TYPE_NONE {
fmt.Fprintf(&buf, "%s%v", sep, obj.Dconv(p, &p.To))
}
return buf.String()
}
var Register = []string{
"AL", /* [D_AL] */
"CL",
......
......@@ -1187,7 +1187,6 @@ var unaryDst = map[int]bool{
var Linkamd64 = obj.LinkArch{
ByteOrder: binary.LittleEndian,
Pconv: Pconv,
Name: "amd64",
Thechar: '6',
Preprocess: preprocess,
......@@ -1202,7 +1201,6 @@ var Linkamd64 = obj.LinkArch{
var Linkamd64p32 = obj.LinkArch{
ByteOrder: binary.LittleEndian,
Pconv: Pconv,
Name: "amd64p32",
Thechar: '6',
Preprocess: preprocess,
......@@ -1217,7 +1215,6 @@ var Linkamd64p32 = obj.LinkArch{
var Link386 = obj.LinkArch{
ByteOrder: binary.LittleEndian,
Pconv: Pconv,
Name: "386",
Thechar: '8',
Preprocess: preprocess,
......
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