mirror of
https://github.com/golang/go
synced 2024-11-23 18:40:03 -07:00
cmd/internal/obj/arm: add DMB instruction
Change-Id: Ib67a61d5b37af210ff15d60d72bd5238b9c2d0ca Reviewed-on: https://go-review.googlesource.com/94815 Run-TryBot: Cherry Zhang <cherryyz@google.com> TryBot-Result: Gobot Gobot <gobot@golang.org> Reviewed-by: Cherry Zhang <cherryyz@google.com>
This commit is contained in:
parent
fc7a72596b
commit
0a5be12f5c
@ -205,6 +205,16 @@ func archArm() *Arch {
|
|||||||
"R": true,
|
"R": true,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// special operands for DMB/DSB instructions
|
||||||
|
register["MB_SY"] = arm.REG_MB_SY
|
||||||
|
register["MB_ST"] = arm.REG_MB_ST
|
||||||
|
register["MB_ISH"] = arm.REG_MB_ISH
|
||||||
|
register["MB_ISHST"] = arm.REG_MB_ISHST
|
||||||
|
register["MB_NSH"] = arm.REG_MB_NSH
|
||||||
|
register["MB_NSHST"] = arm.REG_MB_NSHST
|
||||||
|
register["MB_OSH"] = arm.REG_MB_OSH
|
||||||
|
register["MB_OSHST"] = arm.REG_MB_OSHST
|
||||||
|
|
||||||
instructions := make(map[string]obj.As)
|
instructions := make(map[string]obj.As)
|
||||||
for i, s := range obj.Anames {
|
for i, s := range obj.Anames {
|
||||||
instructions[s] = obj.As(i)
|
instructions[s] = obj.As(i)
|
||||||
|
@ -86,7 +86,6 @@ const (
|
|||||||
REG_CPSR // must be 2-aligned
|
REG_CPSR // must be 2-aligned
|
||||||
REG_SPSR
|
REG_SPSR
|
||||||
|
|
||||||
MAXREG
|
|
||||||
REGRET = REG_R0
|
REGRET = REG_R0
|
||||||
/* compiler allocates R1 up as temps */
|
/* compiler allocates R1 up as temps */
|
||||||
/* compiler allocates register variables R3 up */
|
/* compiler allocates register variables R3 up */
|
||||||
@ -124,6 +123,22 @@ func init() {
|
|||||||
f(REG_F0, REG_F15, 64, 2) // Use d0 through D15, aka S0, S2, ..., S30
|
f(REG_F0, REG_F15, 64, 2) // Use d0 through D15, aka S0, S2, ..., S30
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Special registers, after subtracting obj.RBaseARM, bit 9 indicates
|
||||||
|
// a special register and the low bits select the register.
|
||||||
|
const (
|
||||||
|
REG_SPECIAL = obj.RBaseARM + 1<<9 + iota
|
||||||
|
REG_MB_SY
|
||||||
|
REG_MB_ST
|
||||||
|
REG_MB_ISH
|
||||||
|
REG_MB_ISHST
|
||||||
|
REG_MB_NSH
|
||||||
|
REG_MB_NSHST
|
||||||
|
REG_MB_OSH
|
||||||
|
REG_MB_OSHST
|
||||||
|
|
||||||
|
MAXREG
|
||||||
|
)
|
||||||
|
|
||||||
const (
|
const (
|
||||||
C_NONE = iota
|
C_NONE = iota
|
||||||
C_REG
|
C_REG
|
||||||
@ -135,6 +150,7 @@ const (
|
|||||||
C_FREG
|
C_FREG
|
||||||
C_PSR
|
C_PSR
|
||||||
C_FCR
|
C_FCR
|
||||||
|
C_SPR /* REG_MB_SY */
|
||||||
|
|
||||||
C_RCON /* 0xff rotated */
|
C_RCON /* 0xff rotated */
|
||||||
C_NCON /* ~RCON */
|
C_NCON /* ~RCON */
|
||||||
@ -319,6 +335,8 @@ const (
|
|||||||
ALDREXD
|
ALDREXD
|
||||||
ASTREXD
|
ASTREXD
|
||||||
|
|
||||||
|
ADMB
|
||||||
|
|
||||||
APLD
|
APLD
|
||||||
|
|
||||||
ACLZ
|
ACLZ
|
||||||
|
@ -119,6 +119,7 @@ var Anames = []string{
|
|||||||
"STREX",
|
"STREX",
|
||||||
"LDREXD",
|
"LDREXD",
|
||||||
"STREXD",
|
"STREXD",
|
||||||
|
"DMB",
|
||||||
"PLD",
|
"PLD",
|
||||||
"CLZ",
|
"CLZ",
|
||||||
"REV",
|
"REV",
|
||||||
|
@ -15,6 +15,7 @@ var cnames5 = []string{
|
|||||||
"FREG",
|
"FREG",
|
||||||
"PSR",
|
"PSR",
|
||||||
"FCR",
|
"FCR",
|
||||||
|
"SPR",
|
||||||
"RCON",
|
"RCON",
|
||||||
"NCON",
|
"NCON",
|
||||||
"RCON2A",
|
"RCON2A",
|
||||||
|
@ -303,6 +303,9 @@ var optab = []Optab{
|
|||||||
{AMOVHU, C_ADDR, C_NONE, C_REG, 93, 8, 0, LFROM | LPCREL, 4, C_PBIT | C_WBIT | C_UBIT},
|
{AMOVHU, C_ADDR, C_NONE, C_REG, 93, 8, 0, LFROM | LPCREL, 4, C_PBIT | C_WBIT | C_UBIT},
|
||||||
{ALDREX, C_SOREG, C_NONE, C_REG, 77, 4, 0, 0, 0, 0},
|
{ALDREX, C_SOREG, C_NONE, C_REG, 77, 4, 0, 0, 0, 0},
|
||||||
{ASTREX, C_SOREG, C_REG, C_REG, 78, 4, 0, 0, 0, 0},
|
{ASTREX, C_SOREG, C_REG, C_REG, 78, 4, 0, 0, 0, 0},
|
||||||
|
{ADMB, C_NONE, C_NONE, C_NONE, 110, 4, 0, 0, 0, 0},
|
||||||
|
{ADMB, C_LCON, C_NONE, C_NONE, 110, 4, 0, 0, 0, 0},
|
||||||
|
{ADMB, C_SPR, C_NONE, C_NONE, 110, 4, 0, 0, 0, 0},
|
||||||
{AMOVF, C_ZFCON, C_NONE, C_FREG, 80, 8, 0, 0, 0, 0},
|
{AMOVF, C_ZFCON, C_NONE, C_FREG, 80, 8, 0, 0, 0, 0},
|
||||||
{AMOVF, C_SFCON, C_NONE, C_FREG, 81, 4, 0, 0, 0, 0},
|
{AMOVF, C_SFCON, C_NONE, C_FREG, 81, 4, 0, 0, 0, 0},
|
||||||
{ACMPF, C_FREG, C_FREG, C_NONE, 82, 8, 0, 0, 0, 0},
|
{ACMPF, C_FREG, C_FREG, C_NONE, 82, 8, 0, 0, 0, 0},
|
||||||
@ -331,6 +334,20 @@ var optab = []Optab{
|
|||||||
{obj.AXXX, C_NONE, C_NONE, C_NONE, 0, 4, 0, 0, 0, 0},
|
{obj.AXXX, C_NONE, C_NONE, C_NONE, 0, 4, 0, 0, 0, 0},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var mbOp = []struct {
|
||||||
|
reg int16
|
||||||
|
enc uint32
|
||||||
|
}{
|
||||||
|
{REG_MB_SY, 15},
|
||||||
|
{REG_MB_ST, 14},
|
||||||
|
{REG_MB_ISH, 11},
|
||||||
|
{REG_MB_ISHST, 10},
|
||||||
|
{REG_MB_NSH, 7},
|
||||||
|
{REG_MB_NSHST, 6},
|
||||||
|
{REG_MB_OSH, 3},
|
||||||
|
{REG_MB_OSHST, 2},
|
||||||
|
}
|
||||||
|
|
||||||
var oprange [ALAST & obj.AMask][]Optab
|
var oprange [ALAST & obj.AMask][]Optab
|
||||||
|
|
||||||
var xcmp [C_GOK + 1][C_GOK + 1]bool
|
var xcmp [C_GOK + 1][C_GOK + 1]bool
|
||||||
@ -1103,6 +1120,9 @@ func (c *ctxt5) aclass(a *obj.Addr) int {
|
|||||||
if a.Reg == REG_CPSR || a.Reg == REG_SPSR {
|
if a.Reg == REG_CPSR || a.Reg == REG_SPSR {
|
||||||
return C_PSR
|
return C_PSR
|
||||||
}
|
}
|
||||||
|
if a.Reg >= REG_SPECIAL {
|
||||||
|
return C_SPR
|
||||||
|
}
|
||||||
return C_GOK
|
return C_GOK
|
||||||
|
|
||||||
case obj.TYPE_REGREG:
|
case obj.TYPE_REGREG:
|
||||||
@ -1697,6 +1717,7 @@ func buildop(ctxt *obj.Link) {
|
|||||||
ASTREX,
|
ASTREX,
|
||||||
ALDREXD,
|
ALDREXD,
|
||||||
ASTREXD,
|
ASTREXD,
|
||||||
|
ADMB,
|
||||||
APLD,
|
APLD,
|
||||||
AAND,
|
AAND,
|
||||||
AMULA,
|
AMULA,
|
||||||
@ -2786,6 +2807,35 @@ func (c *ctxt5) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
|||||||
r = rt
|
r = rt
|
||||||
}
|
}
|
||||||
o1 |= (uint32(rf)&15)<<8 | (uint32(r)&15)<<0 | (uint32(rt)&15)<<16
|
o1 |= (uint32(rf)&15)<<8 | (uint32(r)&15)<<0 | (uint32(rt)&15)<<16
|
||||||
|
|
||||||
|
case 110: /* dmb [mbop | $con] */
|
||||||
|
o1 = 0xf57ff050
|
||||||
|
mbop := uint32(0)
|
||||||
|
|
||||||
|
switch c.aclass(&p.From) {
|
||||||
|
case C_SPR:
|
||||||
|
for _, f := range mbOp {
|
||||||
|
if f.reg == p.From.Reg {
|
||||||
|
mbop = f.enc
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
case C_RCON:
|
||||||
|
for _, f := range mbOp {
|
||||||
|
enc := uint32(c.instoffset)
|
||||||
|
if f.enc == enc {
|
||||||
|
mbop = enc
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
case C_NONE:
|
||||||
|
mbop = 0xf
|
||||||
|
}
|
||||||
|
|
||||||
|
if mbop == 0 {
|
||||||
|
c.ctxt.Diag("illegal mb option:\n%v", p)
|
||||||
|
}
|
||||||
|
o1 |= mbop
|
||||||
}
|
}
|
||||||
|
|
||||||
out[0] = o1
|
out[0] = o1
|
||||||
|
@ -68,6 +68,23 @@ func rconv(r int) string {
|
|||||||
|
|
||||||
case REG_SPSR:
|
case REG_SPSR:
|
||||||
return "SPSR"
|
return "SPSR"
|
||||||
|
|
||||||
|
case REG_MB_SY:
|
||||||
|
return "MB_SY"
|
||||||
|
case REG_MB_ST:
|
||||||
|
return "MB_ST"
|
||||||
|
case REG_MB_ISH:
|
||||||
|
return "MB_ISH"
|
||||||
|
case REG_MB_ISHST:
|
||||||
|
return "MB_ISHST"
|
||||||
|
case REG_MB_NSH:
|
||||||
|
return "MB_NSH"
|
||||||
|
case REG_MB_NSHST:
|
||||||
|
return "MB_NSHST"
|
||||||
|
case REG_MB_OSH:
|
||||||
|
return "MB_OSH"
|
||||||
|
case REG_MB_OSHST:
|
||||||
|
return "MB_OSHST"
|
||||||
}
|
}
|
||||||
|
|
||||||
return fmt.Sprintf("Rgok(%d)", r-obj.RBaseARM)
|
return fmt.Sprintf("Rgok(%d)", r-obj.RBaseARM)
|
||||||
|
@ -785,7 +785,7 @@ TEXT runtime·armPublicationBarrier(SB),NOSPLIT|NOFRAME,$0-0
|
|||||||
MOVB runtime·goarm(SB), R11
|
MOVB runtime·goarm(SB), R11
|
||||||
CMP $7, R11
|
CMP $7, R11
|
||||||
BLT 2(PC)
|
BLT 2(PC)
|
||||||
WORD $0xf57ff05e // DMB ST
|
DMB MB_ST
|
||||||
RET
|
RET
|
||||||
|
|
||||||
// AES hashing not implemented for ARM
|
// AES hashing not implemented for ARM
|
||||||
|
@ -30,7 +30,7 @@ casl:
|
|||||||
MOVB runtime·goarm(SB), R11
|
MOVB runtime·goarm(SB), R11
|
||||||
CMP $7, R11
|
CMP $7, R11
|
||||||
BLT 2(PC)
|
BLT 2(PC)
|
||||||
WORD $0xf57ff05a // dmb ishst
|
DMB MB_ISHST
|
||||||
|
|
||||||
STREX R3, (R1), R0
|
STREX R3, (R1), R0
|
||||||
CMP $0, R0
|
CMP $0, R0
|
||||||
@ -40,7 +40,7 @@ casl:
|
|||||||
MOVB runtime·goarm(SB), R11
|
MOVB runtime·goarm(SB), R11
|
||||||
CMP $7, R11
|
CMP $7, R11
|
||||||
BLT 2(PC)
|
BLT 2(PC)
|
||||||
WORD $0xf57ff05b // dmb ish
|
DMB MB_ISH
|
||||||
|
|
||||||
MOVB R0, ret+12(FP)
|
MOVB R0, ret+12(FP)
|
||||||
RET
|
RET
|
||||||
|
@ -12,13 +12,13 @@
|
|||||||
MOVB runtime·goarm(SB), R11; \
|
MOVB runtime·goarm(SB), R11; \
|
||||||
CMP $7, R11; \
|
CMP $7, R11; \
|
||||||
BLT 2(PC); \
|
BLT 2(PC); \
|
||||||
WORD $0xf57ff05a // dmb ishst
|
DMB MB_ISHST
|
||||||
|
|
||||||
#define DMB_ISH_7 \
|
#define DMB_ISH_7 \
|
||||||
MOVB runtime·goarm(SB), R11; \
|
MOVB runtime·goarm(SB), R11; \
|
||||||
CMP $7, R11; \
|
CMP $7, R11; \
|
||||||
BLT 2(PC); \
|
BLT 2(PC); \
|
||||||
WORD $0xf57ff05b // dmb ish
|
DMB MB_ISH
|
||||||
|
|
||||||
TEXT ·armCompareAndSwapUint32(SB),NOSPLIT,$0-13
|
TEXT ·armCompareAndSwapUint32(SB),NOSPLIT,$0-13
|
||||||
MOVW addr+0(FP), R1
|
MOVW addr+0(FP), R1
|
||||||
|
@ -6,12 +6,6 @@
|
|||||||
|
|
||||||
// Darwin/ARM atomic operations.
|
// Darwin/ARM atomic operations.
|
||||||
|
|
||||||
#define DMB_ISHST_7 \
|
|
||||||
WORD $0xf57ff05a // dmb ishst
|
|
||||||
|
|
||||||
#define DMB_ISH_7 \
|
|
||||||
WORD $0xf57ff05b // dmb ish
|
|
||||||
|
|
||||||
TEXT ·CompareAndSwapInt32(SB),NOSPLIT,$0
|
TEXT ·CompareAndSwapInt32(SB),NOSPLIT,$0
|
||||||
B ·CompareAndSwapUint32(SB)
|
B ·CompareAndSwapUint32(SB)
|
||||||
|
|
||||||
@ -64,11 +58,11 @@ TEXT ·LoadUint32(SB),NOSPLIT,$0-8
|
|||||||
MOVW addr+0(FP), R1
|
MOVW addr+0(FP), R1
|
||||||
load32loop:
|
load32loop:
|
||||||
LDREX (R1), R2 // loads R2
|
LDREX (R1), R2 // loads R2
|
||||||
DMB_ISHST_7
|
DMB MB_ISHST
|
||||||
STREX R2, (R1), R0 // stores R2
|
STREX R2, (R1), R0 // stores R2
|
||||||
CMP $0, R0
|
CMP $0, R0
|
||||||
BNE load32loop
|
BNE load32loop
|
||||||
DMB_ISH_7
|
DMB MB_ISH
|
||||||
MOVW R2, val+4(FP)
|
MOVW R2, val+4(FP)
|
||||||
RET
|
RET
|
||||||
|
|
||||||
@ -92,11 +86,11 @@ TEXT ·StoreUint32(SB),NOSPLIT,$0-8
|
|||||||
MOVW val+4(FP), R2
|
MOVW val+4(FP), R2
|
||||||
storeloop:
|
storeloop:
|
||||||
LDREX (R1), R4 // loads R4
|
LDREX (R1), R4 // loads R4
|
||||||
DMB_ISHST_7
|
DMB MB_ISHST
|
||||||
STREX R2, (R1), R0 // stores R2
|
STREX R2, (R1), R0 // stores R2
|
||||||
CMP $0, R0
|
CMP $0, R0
|
||||||
BNE storeloop
|
BNE storeloop
|
||||||
DMB_ISH_7
|
DMB MB_ISH
|
||||||
RET
|
RET
|
||||||
|
|
||||||
TEXT ·StoreInt64(SB),NOSPLIT,$0
|
TEXT ·StoreInt64(SB),NOSPLIT,$0
|
||||||
|
@ -8,7 +8,7 @@
|
|||||||
MOVB runtime·goarm(SB), R11; \
|
MOVB runtime·goarm(SB), R11; \
|
||||||
CMP $7, R11; \
|
CMP $7, R11; \
|
||||||
BLT 2(PC); \
|
BLT 2(PC); \
|
||||||
WORD $0xf57ff05b // dmb ish
|
DMB MB_ISH
|
||||||
|
|
||||||
// Plan9/ARM atomic operations.
|
// Plan9/ARM atomic operations.
|
||||||
// TODO(minux): this only supports ARMv6K or higher.
|
// TODO(minux): this only supports ARMv6K or higher.
|
||||||
|
Loading…
Reference in New Issue
Block a user