blob: 3c13567cb043576f40ae0d5f85f08201744dcc40 [file] [log] [blame] [edit]
// Copyright 2024 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package riscv64asm
import (
"fmt"
"strings"
)
// An Op is a RISC-V opcode.
type Op uint16
// NOTE: The actual Op values are defined in tables.go.
func (op Op) String() string {
if op >= Op(len(opstr)) || opstr[op] == "" {
return fmt.Sprintf("Op(%d)", op)
}
return opstr[op]
}
// An Arg is a single instruction argument.
type Arg interface {
String() string
}
// An Args holds the instruction arguments.
// If an instruction has fewer than 6 arguments,
// the final elements in the array are nil.
type Args [6]Arg
// An Inst is a single instruction.
type Inst struct {
Op Op // Opcode mnemonic.
Enc uint32 // Raw encoding bits.
Args Args // Instruction arguments, in RISC-V mamual order.
Len int // Length of encoded instruction in bytes
}
func (i Inst) String() string {
var args []string
for _, arg := range i.Args {
if arg == nil {
break
}
args = append(args, arg.String())
}
if len(args) == 0 {
return i.Op.String()
}
return i.Op.String() + " " + strings.Join(args, ",")
}
// A Reg is a single register.
// The zero value denotes X0, not the absence of a register.
type Reg uint16
const (
// General-purpose register
X0 Reg = iota
X1
X2
X3
X4
X5
X6
X7
X8
X9
X10
X11
X12
X13
X14
X15
X16
X17
X18
X19
X20
X21
X22
X23
X24
X25
X26
X27
X28
X29
X30
X31
//Float point register
F0
F1
F2
F3
F4
F5
F6
F7
F8
F9
F10
F11
F12
F13
F14
F15
F16
F17
F18
F19
F20
F21
F22
F23
F24
F25
F26
F27
F28
F29
F30
F31
)
func (r Reg) String() string {
switch {
case r >= X0 && r <= X31:
return fmt.Sprintf("x%d", r)
case r >= F0 && r <= F31:
return fmt.Sprintf("f%d", r-F0)
default:
return fmt.Sprintf("Unknown(%d)", r)
}
}
// A CSR is a single control and status register.
// Use stringer to generate CSR match table.
//
//go:generate stringer -type=CSR
type CSR uint16
const (
// Control status register
USTATUS CSR = 0x0000
FFLAGS CSR = 0x0001
FRM CSR = 0x0002
FCSR CSR = 0x0003
UIE CSR = 0x0004
UTVEC CSR = 0x0005
UTVT CSR = 0x0007
VSTART CSR = 0x0008
VXSAT CSR = 0x0009
VXRM CSR = 0x000a
VCSR CSR = 0x000f
USCRATCH CSR = 0x0040
UEPC CSR = 0x0041
UCAUSE CSR = 0x0042
UTVAL CSR = 0x0043
UIP CSR = 0x0044
UNXTI CSR = 0x0045
UINTSTATUS CSR = 0x0046
USCRATCHCSW CSR = 0x0048
USCRATCHCSWL CSR = 0x0049
SSTATUS CSR = 0x0100
SEDELEG CSR = 0x0102
SIDELEG CSR = 0x0103
SIE CSR = 0x0104
STVEC CSR = 0x0105
SCOUNTEREN CSR = 0x0106
STVT CSR = 0x0107
SSCRATCH CSR = 0x0140
SEPC CSR = 0x0141
SCAUSE CSR = 0x0142
STVAL CSR = 0x0143
SIP CSR = 0x0144
SNXTI CSR = 0x0145
SINTSTATUS CSR = 0x0146
SSCRATCHCSW CSR = 0x0148
SSCRATCHCSWL CSR = 0x0149
SATP CSR = 0x0180
VSSTATUS CSR = 0x0200
VSIE CSR = 0x0204
VSTVEC CSR = 0x0205
VSSCRATCH CSR = 0x0240
VSEPC CSR = 0x0241
VSCAUSE CSR = 0x0242
VSTVAL CSR = 0x0243
VSIP CSR = 0x0244
VSATP CSR = 0x0280
MSTATUS CSR = 0x0300
MISA CSR = 0x0301
MEDELEG CSR = 0x0302
MIDELEG CSR = 0x0303
MIE CSR = 0x0304
MTVEC CSR = 0x0305
MCOUNTEREN CSR = 0x0306
MTVT CSR = 0x0307
MSTATUSH CSR = 0x0310
MCOUNTINHIBIT CSR = 0x0320
MHPMEVENT3 CSR = 0x0323
MHPMEVENT4 CSR = 0x0324
MHPMEVENT5 CSR = 0x0325
MHPMEVENT6 CSR = 0x0326
MHPMEVENT7 CSR = 0x0327
MHPMEVENT8 CSR = 0x0328
MHPMEVENT9 CSR = 0x0329
MHPMEVENT10 CSR = 0x032a
MHPMEVENT11 CSR = 0x032b
MHPMEVENT12 CSR = 0x032c
MHPMEVENT13 CSR = 0x032d
MHPMEVENT14 CSR = 0x032e
MHPMEVENT15 CSR = 0x032f
MHPMEVENT16 CSR = 0x0330
MHPMEVENT17 CSR = 0x0331
MHPMEVENT18 CSR = 0x0332
MHPMEVENT19 CSR = 0x0333
MHPMEVENT20 CSR = 0x0334
MHPMEVENT21 CSR = 0x0335
MHPMEVENT22 CSR = 0x0336
MHPMEVENT23 CSR = 0x0337
MHPMEVENT24 CSR = 0x0338
MHPMEVENT25 CSR = 0x0339
MHPMEVENT26 CSR = 0x033a
MHPMEVENT27 CSR = 0x033b
MHPMEVENT28 CSR = 0x033c
MHPMEVENT29 CSR = 0x033d
MHPMEVENT30 CSR = 0x033e
MHPMEVENT31 CSR = 0x033f
MSCRATCH CSR = 0x0340
MEPC CSR = 0x0341
MCAUSE CSR = 0x0342
MTVAL CSR = 0x0343
MIP CSR = 0x0344
MNXTI CSR = 0x0345
MINTSTATUS CSR = 0x0346
MSCRATCHCSW CSR = 0x0348
MSCRATCHCSWL CSR = 0x0349
MTINST CSR = 0x034a
MTVAL2 CSR = 0x034b
PMPCFG0 CSR = 0x03a0
PMPCFG1 CSR = 0x03a1
PMPCFG2 CSR = 0x03a2
PMPCFG3 CSR = 0x03a3
PMPADDR0 CSR = 0x03b0
PMPADDR1 CSR = 0x03b1
PMPADDR2 CSR = 0x03b2
PMPADDR3 CSR = 0x03b3
PMPADDR4 CSR = 0x03b4
PMPADDR5 CSR = 0x03b5
PMPADDR6 CSR = 0x03b6
PMPADDR7 CSR = 0x03b7
PMPADDR8 CSR = 0x03b8
PMPADDR9 CSR = 0x03b9
PMPADDR10 CSR = 0x03ba
PMPADDR11 CSR = 0x03bb
PMPADDR12 CSR = 0x03bc
PMPADDR13 CSR = 0x03bd
PMPADDR14 CSR = 0x03be
PMPADDR15 CSR = 0x03bf
HSTATUS CSR = 0x0600
HEDELEG CSR = 0x0602
HIDELEG CSR = 0x0603
HIE CSR = 0x0604
HTIMEDELTA CSR = 0x0605
HCOUNTEREN CSR = 0x0606
HGEIE CSR = 0x0607
HTIMEDELTAH CSR = 0x0615
HTVAL CSR = 0x0643
HIP CSR = 0x0644
HVIP CSR = 0x0645
HTINST CSR = 0x064a
HGATP CSR = 0x0680
TSELECT CSR = 0x07a0
TDATA1 CSR = 0x07a1
TDATA2 CSR = 0x07a2
TDATA3 CSR = 0x07a3
TINFO CSR = 0x07a4
TCONTROL CSR = 0x07a5
MCONTEXT CSR = 0x07a8
MNOISE CSR = 0x07a9
SCONTEXT CSR = 0x07aa
DCSR CSR = 0x07b0
DPC CSR = 0x07b1
DSCRATCH0 CSR = 0x07b2
DSCRATCH1 CSR = 0x07b3
MCYCLE CSR = 0x0b00
MINSTRET CSR = 0x0b02
MHPMCOUNTER3 CSR = 0x0b03
MHPMCOUNTER4 CSR = 0x0b04
MHPMCOUNTER5 CSR = 0x0b05
MHPMCOUNTER6 CSR = 0x0b06
MHPMCOUNTER7 CSR = 0x0b07
MHPMCOUNTER8 CSR = 0x0b08
MHPMCOUNTER9 CSR = 0x0b09
MHPMCOUNTER10 CSR = 0x0b0a
MHPMCOUNTER11 CSR = 0x0b0b
MHPMCOUNTER12 CSR = 0x0b0c
MHPMCOUNTER13 CSR = 0x0b0d
MHPMCOUNTER14 CSR = 0x0b0e
MHPMCOUNTER15 CSR = 0x0b0f
MHPMCOUNTER16 CSR = 0x0b10
MHPMCOUNTER17 CSR = 0x0b11
MHPMCOUNTER18 CSR = 0x0b12
MHPMCOUNTER19 CSR = 0x0b13
MHPMCOUNTER20 CSR = 0x0b14
MHPMCOUNTER21 CSR = 0x0b15
MHPMCOUNTER22 CSR = 0x0b16
MHPMCOUNTER23 CSR = 0x0b17
MHPMCOUNTER24 CSR = 0x0b18
MHPMCOUNTER25 CSR = 0x0b19
MHPMCOUNTER26 CSR = 0x0b1a
MHPMCOUNTER27 CSR = 0x0b1b
MHPMCOUNTER28 CSR = 0x0b1c
MHPMCOUNTER29 CSR = 0x0b1d
MHPMCOUNTER30 CSR = 0x0b1e
MHPMCOUNTER31 CSR = 0x0b1f
MCYCLEH CSR = 0x0b80
MINSTRETH CSR = 0x0b82
MHPMCOUNTER3H CSR = 0x0b83
MHPMCOUNTER4H CSR = 0x0b84
MHPMCOUNTER5H CSR = 0x0b85
MHPMCOUNTER6H CSR = 0x0b86
MHPMCOUNTER7H CSR = 0x0b87
MHPMCOUNTER8H CSR = 0x0b88
MHPMCOUNTER9H CSR = 0x0b89
MHPMCOUNTER10H CSR = 0x0b8a
MHPMCOUNTER11H CSR = 0x0b8b
MHPMCOUNTER12H CSR = 0x0b8c
MHPMCOUNTER13H CSR = 0x0b8d
MHPMCOUNTER14H CSR = 0x0b8e
MHPMCOUNTER15H CSR = 0x0b8f
MHPMCOUNTER16H CSR = 0x0b90
MHPMCOUNTER17H CSR = 0x0b91
MHPMCOUNTER18H CSR = 0x0b92
MHPMCOUNTER19H CSR = 0x0b93
MHPMCOUNTER20H CSR = 0x0b94
MHPMCOUNTER21H CSR = 0x0b95
MHPMCOUNTER22H CSR = 0x0b96
MHPMCOUNTER23H CSR = 0x0b97
MHPMCOUNTER24H CSR = 0x0b98
MHPMCOUNTER25H CSR = 0x0b99
MHPMCOUNTER26H CSR = 0x0b9a
MHPMCOUNTER27H CSR = 0x0b9b
MHPMCOUNTER28H CSR = 0x0b9c
MHPMCOUNTER29H CSR = 0x0b9d
MHPMCOUNTER30H CSR = 0x0b9e
MHPMCOUNTER31H CSR = 0x0b9f
CYCLE CSR = 0x0c00
TIME CSR = 0x0c01
INSTRET CSR = 0x0c02
HPMCOUNTER3 CSR = 0x0c03
HPMCOUNTER4 CSR = 0x0c04
HPMCOUNTER5 CSR = 0x0c05
HPMCOUNTER6 CSR = 0x0c06
HPMCOUNTER7 CSR = 0x0c07
HPMCOUNTER8 CSR = 0x0c08
HPMCOUNTER9 CSR = 0x0c09
HPMCOUNTER10 CSR = 0x0c0a
HPMCOUNTER11 CSR = 0x0c0b
HPMCOUNTER12 CSR = 0x0c0c
HPMCOUNTER13 CSR = 0x0c0d
HPMCOUNTER14 CSR = 0x0c0e
HPMCOUNTER15 CSR = 0x0c0f
HPMCOUNTER16 CSR = 0x0c10
HPMCOUNTER17 CSR = 0x0c11
HPMCOUNTER18 CSR = 0x0c12
HPMCOUNTER19 CSR = 0x0c13
HPMCOUNTER20 CSR = 0x0c14
HPMCOUNTER21 CSR = 0x0c15
HPMCOUNTER22 CSR = 0x0c16
HPMCOUNTER23 CSR = 0x0c17
HPMCOUNTER24 CSR = 0x0c18
HPMCOUNTER25 CSR = 0x0c19
HPMCOUNTER26 CSR = 0x0c1a
HPMCOUNTER27 CSR = 0x0c1b
HPMCOUNTER28 CSR = 0x0c1c
HPMCOUNTER29 CSR = 0x0c1d
HPMCOUNTER30 CSR = 0x0c1e
HPMCOUNTER31 CSR = 0x0c1f
VL CSR = 0x0c20
VTYPE CSR = 0x0c21
VLENB CSR = 0x0c22
CYCLEH CSR = 0x0c80
TIMEH CSR = 0x0c81
INSTRETH CSR = 0x0c82
HPMCOUNTER3H CSR = 0x0c83
HPMCOUNTER4H CSR = 0x0c84
HPMCOUNTER5H CSR = 0x0c85
HPMCOUNTER6H CSR = 0x0c86
HPMCOUNTER7H CSR = 0x0c87
HPMCOUNTER8H CSR = 0x0c88
HPMCOUNTER9H CSR = 0x0c89
HPMCOUNTER10H CSR = 0x0c8a
HPMCOUNTER11H CSR = 0x0c8b
HPMCOUNTER12H CSR = 0x0c8c
HPMCOUNTER13H CSR = 0x0c8d
HPMCOUNTER14H CSR = 0x0c8e
HPMCOUNTER15H CSR = 0x0c8f
HPMCOUNTER16H CSR = 0x0c90
HPMCOUNTER17H CSR = 0x0c91
HPMCOUNTER18H CSR = 0x0c92
HPMCOUNTER19H CSR = 0x0c93
HPMCOUNTER20H CSR = 0x0c94
HPMCOUNTER21H CSR = 0x0c95
HPMCOUNTER22H CSR = 0x0c96
HPMCOUNTER23H CSR = 0x0c97
HPMCOUNTER24H CSR = 0x0c98
HPMCOUNTER25H CSR = 0x0c99
HPMCOUNTER26H CSR = 0x0c9a
HPMCOUNTER27H CSR = 0x0c9b
HPMCOUNTER28H CSR = 0x0c9c
HPMCOUNTER29H CSR = 0x0c9d
HPMCOUNTER30H CSR = 0x0c9e
HPMCOUNTER31H CSR = 0x0c9f
HGEIP CSR = 0x0e12
MVENDORID CSR = 0x0f11
MARCHID CSR = 0x0f12
MIMPID CSR = 0x0f13
MHARTID CSR = 0x0f14
MENTROPY CSR = 0x0f15
)
// An Uimm is an unsigned immediate number
type Uimm struct {
Imm uint32 // 32-bit unsigned integer
Decimal bool // Print format of the immediate, either decimal or hexadecimal
}
func (ui Uimm) String() string {
if ui.Decimal {
return fmt.Sprintf("%d", ui.Imm)
}
return fmt.Sprintf("%#x", ui.Imm)
}
// A Simm is a signed immediate number
type Simm struct {
Imm int32 // 32-bit signed integer
Decimal bool // Print format of the immediate, either decimal or hexadecimal
Width uint8 // Actual width of the Simm
}
func (si Simm) String() string {
if si.Decimal {
return fmt.Sprintf("%d", si.Imm)
}
return fmt.Sprintf("%#x", si.Imm)
}
// An AmoReg is an atomic address register used in AMO instructions
type AmoReg struct {
reg Reg // Avoid promoted String method
}
func (amoReg AmoReg) String() string {
return fmt.Sprintf("(%s)", amoReg.reg)
}
// A RegOffset is a register with offset value
type RegOffset struct {
OfsReg Reg
Ofs Simm
}
func (regofs RegOffset) String() string {
return fmt.Sprintf("%s(%s)", regofs.Ofs, regofs.OfsReg)
}
// A MemOrder is a memory order hint in fence instruction
type MemOrder uint8
func (memOrder MemOrder) String() string {
var str string
if memOrder<<7>>7 == 1 {
str += "i"
}
if memOrder>>1<<7>>7 == 1 {
str += "o"
}
if memOrder>>2<<7>>7 == 1 {
str += "r"
}
if memOrder>>3<<7>>7 == 1 {
str += "w"
}
return str
}