1
0
mirror of https://github.com/golang/go synced 2024-11-17 01:04:50 -07:00

cmd/internal/obj/riscv: handle FEQ/FNEG/SEQZ/SNEZ

Based on riscv-go port.

Updates #27532

Change-Id: I5e7f45955e1dfdb9d09cc6a4e6f3ce81216d411d
Reviewed-on: https://go-review.googlesource.com/c/go/+/204628
Reviewed-by: Cherry Zhang <cherryyz@google.com>
This commit is contained in:
Joel Sing 2019-11-04 04:08:26 +11:00
parent 7cab55dfd3
commit 24f08103d2
2 changed files with 74 additions and 0 deletions

View File

@ -282,3 +282,25 @@ start:
// real address and updates the immediates for both instructions.
CALL asmtest(SB) // 970f0000
JMP asmtest(SB) // 970f0000
SEQZ X15, X15 // 93b71700
SNEZ X15, X15 // b337f000
// F extension
FNEGS F0, F1 // d3100020
// TODO(jsing): FNES gets encoded as FEQS+XORI - this should
// be handled as a single *obj.Prog so that the full two
// instruction encoding is tested here.
FNES F0, F1, X7 // d3a300a0
// D extension
FNEGD F0, F1 // d3100022
FEQD F0, F1, X5 // d3a200a2
FLTD F0, F1, X5 // d39200a2
FLED F0, F1, X5 // d38200a2
// TODO(jsing): FNED gets encoded as FEQD+XORI - this should
// be handled as a single *obj.Prog so that the full two
// instruction encoding is tested here.
FNED F0, F1, X5 // d3a200a2

View File

@ -221,6 +221,27 @@ func progedit(ctxt *obj.Link, p *obj.Prog, newprog obj.ProgAlloc) {
case AFCVTWS, AFCVTLS, AFCVTWUS, AFCVTLUS, AFCVTWD, AFCVTLD, AFCVTWUD, AFCVTLUD:
// Set the rounding mode in funct3 to round to zero.
p.Scond = 1
case ASEQZ:
// SEQZ rs, rd -> SLTIU $1, rs, rd
p.As = ASLTIU
p.Reg = p.From.Reg
p.From = obj.Addr{Type: obj.TYPE_CONST, Offset: 1}
case ASNEZ:
// SNEZ rs, rd -> SLTU rs, x0, rd
p.As = ASLTU
p.Reg = REG_ZERO
case AFNEGS:
// FNEGS rs, rd -> FSGNJNS rs, rs, rd
p.As = AFSGNJNS
p.Reg = p.From.Reg
case AFNEGD:
// FNEGD rs, rd -> FSGNJND rs, rs, rd
p.As = AFSGNJND
p.Reg = p.From.Reg
}
}
@ -595,6 +616,37 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
jalrToSym(ctxt, p, newprog, REG_ZERO)
}
}
// Replace FNE[SD] with FEQ[SD] and NOT.
case AFNES:
if p.To.Type != obj.TYPE_REG {
ctxt.Diag("progedit: FNES needs an integer register output")
}
dst := p.To.Reg
p.As = AFEQS
p = obj.Appendp(p, newprog)
p.As = AXORI // [bit] xor 1 = not [bit]
p.From.Type = obj.TYPE_CONST
p.From.Offset = 1
p.Reg = dst
p.To.Type = obj.TYPE_REG
p.To.Reg = dst
case AFNED:
if p.To.Type != obj.TYPE_REG {
ctxt.Diag("progedit: FNED needs an integer register output")
}
dst := p.To.Reg
p.As = AFEQD
p = obj.Appendp(p, newprog)
p.As = AXORI // [bit] xor 1 = not [bit]
p.From.Type = obj.TYPE_CONST
p.From.Offset = 1
p.Reg = dst
p.To.Type = obj.TYPE_REG
p.To.Reg = dst
}
}