Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
OpenXiangShan
XiangShan
提交
e6cbcb18
X
XiangShan
项目概览
OpenXiangShan
/
XiangShan
10 个月 前同步成功
通知
1183
Star
3914
Fork
526
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
X
XiangShan
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
前往新版Gitcode,体验更适合开发者的 AI 搜索 >>
未验证
提交
e6cbcb18
编写于
7月 14, 2020
作者:
Y
Yinan Xu
提交者:
GitHub
7月 14, 2020
浏览文件
操作
浏览文件
下载
差异文件
Merge pull request #125 from RISCVERS/csr
Add csr read and write instructions
上级
d901279a
db1d07e1
变更
20
展开全部
隐藏空白更改
内联
并排
Showing
20 changed file
with
1014 addition
and
178 deletion
+1014
-178
src/main/scala/device/AXI4Timer.scala
src/main/scala/device/AXI4Timer.scala
+1
-2
src/main/scala/noop/Cache.scala
src/main/scala/noop/Cache.scala
+2
-1
src/main/scala/xiangshan/Bundle.scala
src/main/scala/xiangshan/Bundle.scala
+1
-0
src/main/scala/xiangshan/XSCore.scala
src/main/scala/xiangshan/XSCore.scala
+1
-1
src/main/scala/xiangshan/backend/Backend.scala
src/main/scala/xiangshan/backend/Backend.scala
+12
-1
src/main/scala/xiangshan/backend/decode/DecodeBuffer.scala
src/main/scala/xiangshan/backend/decode/DecodeBuffer.scala
+14
-5
src/main/scala/xiangshan/backend/decode/DecodeHelper.scala
src/main/scala/xiangshan/backend/decode/DecodeHelper.scala
+6
-2
src/main/scala/xiangshan/backend/decode/DecodeStage.scala
src/main/scala/xiangshan/backend/decode/DecodeStage.scala
+4
-5
src/main/scala/xiangshan/backend/decode/Decoder.scala
src/main/scala/xiangshan/backend/decode/Decoder.scala
+3
-14
src/main/scala/xiangshan/backend/decode/isa/Privileged.scala
src/main/scala/xiangshan/backend/decode/isa/Privileged.scala
+11
-1
src/main/scala/xiangshan/backend/decode/isa/RVI.scala
src/main/scala/xiangshan/backend/decode/isa/RVI.scala
+4
-4
src/main/scala/xiangshan/backend/decode/isa/RVZicsr.scala
src/main/scala/xiangshan/backend/decode/isa/RVZicsr.scala
+9
-2
src/main/scala/xiangshan/backend/exu/Exu.scala
src/main/scala/xiangshan/backend/exu/Exu.scala
+1
-18
src/main/scala/xiangshan/backend/exu/JmpExeUnit.scala
src/main/scala/xiangshan/backend/exu/JmpExeUnit.scala
+40
-60
src/main/scala/xiangshan/backend/fu/CSR.scala
src/main/scala/xiangshan/backend/fu/CSR.scala
+855
-0
src/main/scala/xiangshan/backend/fu/FunctionUnit.scala
src/main/scala/xiangshan/backend/fu/FunctionUnit.scala
+14
-0
src/main/scala/xiangshan/backend/fu/Jump.scala
src/main/scala/xiangshan/backend/fu/Jump.scala
+15
-23
src/main/scala/xiangshan/backend/package.scala
src/main/scala/xiangshan/backend/package.scala
+12
-28
src/main/scala/xiangshan/backend/roq/Roq.scala
src/main/scala/xiangshan/backend/roq/Roq.scala
+8
-11
src/main/scala/xiangshan/frontend/Ibuffer.scala
src/main/scala/xiangshan/frontend/Ibuffer.scala
+1
-0
未找到文件。
src/main/scala/device/AXI4Timer.scala
浏览文件 @
e6cbcb18
...
...
@@ -3,7 +3,6 @@ package device
import
chisel3._
import
chisel3.util._
import
chisel3.util.experimental.BoringUtils
import
bus.axi4._
import
utils._
...
...
@@ -17,7 +16,7 @@ class AXI4Timer(sim: Boolean = false) extends AXI4SlaveModule(new AXI4Lite, new
val
clk
=
(
if
(!
sim
)
40
/* 40MHz / 1000000 */
else
10000
)
val
freq
=
RegInit
(
clk
.
U
(
16.
W
))
val
inc
=
RegInit
(
1.
U
(
16.
W
))
val
inc
=
RegInit
(
1
000
.
U
(
16.
W
))
val
cnt
=
RegInit
(
0.
U
(
16.
W
))
val
nextCnt
=
cnt
+
1.
U
...
...
src/main/scala/noop/Cache.scala
浏览文件 @
e6cbcb18
...
...
@@ -181,7 +181,7 @@ sealed class CacheStage2(implicit val cacheConfig: CacheConfig) extends CacheMod
io
.
out
.
bits
.
hit
:=
io
.
in
.
valid
&&
hitVec
.
orR
io
.
out
.
bits
.
waymask
:=
waymask
io
.
out
.
bits
.
datas
:=
io
.
dataReadResp
io
.
out
.
bits
.
mmio
:=
AddressSpace
.
isMMIO
(
req
.
addr
)
io
.
out
.
bits
.
mmio
:=
xiangshan
.
AddressSpace
.
isMMIO
(
req
.
addr
)
val
isForwardData
=
io
.
in
.
valid
&&
(
io
.
dataWriteBus
.
req
match
{
case
r
=>
r
.
valid
&&
r
.
bits
.
setIdx
===
getDataIdx
(
req
.
addr
)
...
...
@@ -542,6 +542,7 @@ object Cache {
empty
:=
cache
.
io
.
empty
cache
.
io
.
out
}
else
{
assert
(
false
,
"XiangShan should not reach here!"
)
val
addrspace
=
List
(
AddressSpace
.
dram
)
++
AddressSpace
.
mmio
val
xbar
=
Module
(
new
SimpleBusCrossbar1toN
(
addrspace
))
val
busC
=
WireInit
(
0.
U
.
asTypeOf
(
new
SimpleBusC
))
...
...
src/main/scala/xiangshan/Bundle.scala
浏览文件 @
e6cbcb18
...
...
@@ -21,6 +21,7 @@ class CtrlFlow extends XSBundle {
val
intrVec
=
Vec
(
12
,
Bool
())
val
isRVC
=
Bool
()
val
isBr
=
Bool
()
val
crossPageIPFFix
=
Bool
()
}
// Decode DecodeWidth insts at Decode Stage
...
...
src/main/scala/xiangshan/XSCore.scala
浏览文件 @
e6cbcb18
...
...
@@ -104,7 +104,7 @@ object AddressSpace extends HasXSParameter {
}
class
XSCore
(
implicit
val
p
:
XSConfig
)
extends
XSModule
{
class
XSCore
(
implicit
p
:
XSConfig
)
extends
XSModule
{
val
io
=
IO
(
new
Bundle
{
val
imem
=
new
SimpleBusC
val
dmem
=
new
SimpleBusC
...
...
src/main/scala/xiangshan/backend/Backend.scala
浏览文件 @
e6cbcb18
...
...
@@ -21,7 +21,6 @@ import xiangshan.backend.roq.Roq
* Decode -> Rename -> Dispatch-1 -> Dispatch-2 -> Issue -> Exe
*/
class
Backend
(
implicit
val
p
:
XSConfig
)
extends
XSModule
with
HasExeUnits
with
NeedImpl
{
val
io
=
IO
(
new
Bundle
{
val
dmem
=
new
SimpleBusUC
(
addrBits
=
VAddrBits
)
...
...
@@ -30,6 +29,18 @@ class Backend(implicit val p: XSConfig) extends XSModule
})
val
aluExeUnits
=
Array
.
tabulate
(
exuParameters
.
AluCnt
)(
_
=>
Module
(
new
AluExeUnit
))
val
jmpExeUnit
=
Module
(
new
JmpExeUnit
)
val
mulExeUnits
=
Array
.
tabulate
(
exuParameters
.
MulCnt
)(
_
=>
Module
(
new
MulExeUnit
))
val
mduExeUnits
=
Array
.
tabulate
(
exuParameters
.
MduCnt
)(
_
=>
Module
(
new
MulDivExeUnit
))
// val fmacExeUnits = Array.tabulate(exuParameters.FmacCnt)(_ => Module(new Fmac))
// val fmiscExeUnits = Array.tabulate(exuParameters.FmiscCnt)(_ => Module(new Fmisc))
// val fmiscDivSqrtExeUnits = Array.tabulate(exuParameters.FmiscDivSqrtCnt)(_ => Module(new FmiscDivSqrt))
val
lsuExeUnits
=
Array
.
tabulate
(
exuParameters
.
StuCnt
)(
_
=>
Module
(
new
LsExeUnit
))
val
exeUnits
=
jmpExeUnit
+:
(
aluExeUnits
++
mulExeUnits
++
mduExeUnits
++
lsuExeUnits
)
exeUnits
.
foreach
(
_
.
io
.
dmem
:=
DontCare
)
exeUnits
.
foreach
(
_
.
io
.
scommit
:=
DontCare
)
val
decode
=
Module
(
new
DecodeStage
)
val
brq
=
Module
(
new
Brq
)
val
decBuf
=
Module
(
new
DecodeBuffer
)
...
...
src/main/scala/xiangshan/backend/decode/DecodeBuffer.scala
浏览文件 @
e6cbcb18
...
...
@@ -24,7 +24,6 @@ class DecodeBuffer extends XSModule {
).
asBool
()
val
rightRdyVec
=
io
.
out
.
map
(
_
.
ready
&&
leftCanIn
)
for
(
i
<-
0
until
RenameWidth
){
when
(
io
.
out
(
i
).
fire
()){
validVec
(
i
)
:=
false
.
B
...
...
@@ -36,17 +35,27 @@ class DecodeBuffer extends XSModule {
validVec
(
i
)
:=
false
.
B
}
val
r
=
RegEnable
(
io
.
in
(
i
).
bits
,
io
.
in
(
i
).
fire
())
io
.
in
(
i
).
ready
:=
rightRdyVec
(
i
)
io
.
out
(
i
).
bits
<>
RegEnable
(
io
.
in
(
i
).
bits
,
io
.
in
(
i
).
fire
())
io
.
out
(
i
).
valid
:=
validVec
(
i
)
&&
!
io
.
redirect
.
valid
io
.
out
(
i
).
bits
<>
r
if
(
i
>
0
){
io
.
out
(
i
).
valid
:=
validVec
(
i
)
&&
!
io
.
redirect
.
valid
&&
Mux
(
r
.
ctrl
.
noSpecExec
,
!
ParallelOR
(
validVec
.
take
(
i
)).
asBool
(),
!
ParallelOR
(
io
.
out
.
zip
(
validVec
).
take
(
i
).
map
(
x
=>
x
.
_2
&&
x
.
_1
.
bits
.
ctrl
.
noSpecExec
)).
asBool
()
)
}
else
{
require
(
i
==
0
)
io
.
out
(
i
).
valid
:=
validVec
(
i
)
&&
!
io
.
redirect
.
valid
}
}
for
(
in
<-
io
.
in
){
for
(
in
<-
io
.
in
){
XSInfo
(
p
"in v:${in.valid} r:${in.ready} pc=${Hexadecimal(in.bits.cf.pc)}\n"
)
}
for
(
out
<-
io
.
out
){
XSInfo
(
p
"out v:${out.valid} r:${out.ready} pc=${Hexadecimal(out.bits.cf.pc)}\n"
)
}
XSDebug
(
p
"validVec: ${Binary(validVec.asUInt())}\n"
)
}
src/main/scala/xiangshan/backend/decode/DecodeHelper.scala
浏览文件 @
e6cbcb18
...
...
@@ -36,8 +36,12 @@ object FuOpType {
object
Instructions
extends
HasInstrType
with
HasXSParameter
{
def
NOP
=
0x00000013
.
U
val
DecodeDefault
=
List
(
InstrN
,
FuType
.
alu
,
ALUOpType
.
sll
)
def
DecodeTable
=
RVIInstr
.
table
++
XSTrap
.
table
++
(
if
(
HasMExtension
)
RVMInstr
.
table
else
Nil
)
// ++
def
DecodeTable
=
RVIInstr
.
table
++
XSTrap
.
table
++
RVZicsrInstr
.
table
++
Privileged
.
table
++
(
if
(
HasMExtension
)
RVMInstr
.
table
else
Nil
)
// ++
// (if (HasCExtension) RVCInstr.table else Nil) ++
// (if (HasFPU) RVFInstr.table ++ RVDInstr.table else Nil) ++
// Privileged.table ++
...
...
src/main/scala/xiangshan/backend/decode/DecodeStage.scala
浏览文件 @
e6cbcb18
...
...
@@ -36,18 +36,17 @@ class DecodeStage extends XSModule {
decoderToBrq
(
i
)
:=
decoders
(
i
).
io
.
out
// CfCtrl without bfTag and brMask
// send CfCtrl without brTags and brMasks to brq
io
.
toBrq
(
i
).
valid
:=
io
.
in
(
i
).
valid
&&
io
.
out
(
i
).
ready
&&
decoders
(
i
).
io
.
out
.
cf
.
isBr
XSDebug
(
io
.
toBrq
(
i
).
valid
&&
io
.
toBrq
(
i
).
ready
,
p
"Branch instr detected. Sending it to BRQ.\n"
)
XSDebug
(
io
.
toBrq
(
i
).
valid
&&
!
io
.
toBrq
(
i
).
ready
,
p
"Branch instr detected. BRQ full...waiting\n"
)
XSDebug
(
io
.
in
(
i
).
valid
&&
!
io
.
out
(
i
).
ready
,
p
"DecBuf full...waiting\n"
)
decoderToBrq
(
i
).
brTag
:=
DontCare
io
.
toBrq
(
i
).
bits
:=
decoderToBrq
(
i
)
// if brq returns ready, then assert valid and send CfCtrl with bfTag and brMask to DecBuffer
io
.
out
(
i
).
valid
:=
io
.
toBrq
(
i
).
ready
&&
io
.
in
(
i
).
valid
XSDebug
(
io
.
out
(
i
).
valid
&&
decoders
(
i
).
io
.
out
.
cf
.
isBr
&&
io
.
out
(
i
).
ready
,
p
"Sending branch instr to DecBuf\n"
)
XSDebug
(
io
.
out
(
i
).
valid
&&
!
decoders
(
i
).
io
.
out
.
cf
.
isBr
&&
io
.
out
(
i
).
ready
,
p
"Sending non-branch instr to DecBuf\n"
)
decoderToDecBuffer
(
i
)
:=
decoders
(
i
).
io
.
out
decoderToDecBuffer
(
i
).
brTag
:=
io
.
brTags
(
i
)
io
.
out
(
i
).
bits
:=
decoderToDecBuffer
(
i
)
XSDebug
(
io
.
out
(
i
).
valid
&&
io
.
out
(
i
).
bits
.
ctrl
.
noSpecExec
,
p
"noSpecExec inst: pc=${Hexadecimal(io.out(i).bits.cf.pc)}\n"
)
// If an instruction i is received by DecBuffer,
// then assert in(i).ready, waiting for new instructions
...
...
src/main/scala/xiangshan/backend/decode/Decoder.scala
浏览文件 @
e6cbcb18
...
...
@@ -27,9 +27,8 @@ class Decoder extends XSModule with HasInstrType {
// todo: remove this when fetch stage can decide if an instr is br/jmp
io
.
out
.
cf
.
isBr
:=
(
instrType
===
InstrB
||
(
fuOpType
===
BRUOpType
.
jal
&&
instrType
===
InstrJ
&&
fuType
===
FuType
.
jmp
)
||
(
fuOpType
===
BRUOpType
.
jalr
&&
instrType
===
InstrI
&&
fuType
===
FuType
.
jmp
))
(
fuOpType
===
JumpOpType
.
jal
&&
instrType
===
InstrJ
&&
fuType
===
FuType
.
jmp
)
||
(
fuOpType
===
JumpOpType
.
jalr
&&
instrType
===
InstrI
&&
fuType
===
FuType
.
jmp
))
// val isRVC = instr(1, 0) =/= "b11".U
// val rvcImmType :: rvcSrc1Type :: rvcSrc2Type :: rvcDestType :: Nil =
// ListLookup(instr, CInstructions.DecodeDefault, CInstructions.CExtraDecodeTable)
...
...
@@ -131,17 +130,6 @@ class Decoder extends XSModule with HasInstrType {
// fix LUI
io
.
out
.
ctrl
.
src1Type
:=
Mux
(
instr
(
6
,
0
)
===
"b0110111"
.
U
,
SrcType
.
reg
,
src1Type
)
io
.
out
.
ctrl
.
src2Type
:=
src2Type
val
NoSpecList
=
Seq
(
// FuType.csr,
// FuType.mou
)
val
BlockList
=
Seq
(
)
io
.
out
.
ctrl
.
noSpecExec
:=
NoSpecList
.
map
(
j
=>
io
.
out
.
ctrl
.
fuType
===
j
).
foldRight
(
false
.
B
)((
sum
,
i
)
=>
sum
|
i
)
io
.
out
.
ctrl
.
isBlocked
:=
DontCare
// (
// io.out.ctrl.fuType === (FuType.ldu | FuType.stu) && LSUOpType.isAtom(io.out.ctrl.fuOpType) ||
// BlockList.map(j => io.out.ctrl.fuType === j).foldRight(false.B)((sum, i) => sum | i)
...
...
@@ -171,6 +159,7 @@ class Decoder extends XSModule with HasInstrType {
when
(
io
.
out
.
ctrl
.
isXSTrap
){
io
.
out
.
ctrl
.
lsrc1
:=
10.
U
// a0
}
io
.
out
.
ctrl
.
noSpecExec
:=
io
.
out
.
ctrl
.
isXSTrap
||
io
.
out
.
ctrl
.
fuType
===
FuType
.
csr
// io.isWFI := (instr === Priviledged.WFI) && io.in.valid
}
src/main/scala/xiangshan/backend/decode/isa/Privileged.scala
浏览文件 @
e6cbcb18
...
...
@@ -3,6 +3,7 @@ package xiangshan.backend.decode.isa
import
chisel3._
import
chisel3.util._
import
xiangshan.FuType
import
xiangshan.backend._
import
xiangshan.backend.decode.HasInstrType
...
...
@@ -15,5 +16,14 @@ object Privileged extends HasInstrType {
def
WFI
=
BitPat
(
"b0001000_00101_00000_000_00000_1110011"
)
// fixme: add privilege inst
val
table
=
Array
()
val
table
=
Array
(
ECALL
->
List
(
InstrI
,
FuType
.
csr
,
CSROpType
.
jmp
),
MRET
->
List
(
InstrI
,
FuType
.
csr
,
CSROpType
.
jmp
),
SRET
->
List
(
InstrI
,
FuType
.
csr
,
CSROpType
.
jmp
)
// SFANCE_VMA -> List(InstrR, FuType.mou, MOUOpType.sfence_vma),
// FENCE -> List(InstrS, FuType.alu, ALUOpType.add), // nop InstrS -> !wen
// WFI -> List(InstrI, FuType.alu, ALUOpType.add) // nop
// FENCE -> List(InstrB, FuType.mou, MOUOpType.fencei)
)
}
src/main/scala/xiangshan/backend/decode/isa/RVI.scala
浏览文件 @
e6cbcb18
...
...
@@ -73,8 +73,8 @@ object RV32I_BRUInstr extends HasInstrType {
def
BGEU
=
BitPat
(
"b???????_?????_?????_111_?????_1100011"
)
val
table
=
Array
(
JAL
->
List
(
InstrJ
,
FuType
.
jmp
,
BRU
OpType
.
jal
),
JALR
->
List
(
InstrI
,
FuType
.
jmp
,
BRU
OpType
.
jalr
),
JAL
->
List
(
InstrJ
,
FuType
.
jmp
,
Jump
OpType
.
jal
),
JALR
->
List
(
InstrI
,
FuType
.
jmp
,
Jump
OpType
.
jalr
),
BEQ
->
List
(
InstrB
,
FuType
.
alu
,
ALUOpType
.
beq
),
BNE
->
List
(
InstrB
,
FuType
.
alu
,
ALUOpType
.
bne
),
...
...
@@ -93,8 +93,8 @@ object RV32I_BRUInstr extends HasInstrType {
ALUOpType
.
bgeu
->
BTBtype
.
B
,
// ALUOpType.call -> BTBtype.J,
// ALUOpType.ret -> BTBtype.R,
BRU
OpType
.
jal
->
BTBtype
.
J
,
BRU
OpType
.
jalr
->
BTBtype
.
I
Jump
OpType
.
jal
->
BTBtype
.
J
,
Jump
OpType
.
jalr
->
BTBtype
.
I
)
}
...
...
src/main/scala/xiangshan/backend/decode/isa/RVZicsr.scala
浏览文件 @
e6cbcb18
...
...
@@ -3,6 +3,7 @@ package xiangshan.backend.decode.isa
import
chisel3._
import
chisel3.util._
import
xiangshan.FuType
import
xiangshan.backend._
import
xiangshan.backend.decode.HasInstrType
object
RVZicsrInstr
extends
HasInstrType
{
...
...
@@ -13,6 +14,12 @@ object RVZicsrInstr extends HasInstrType {
def
CSRRSI
=
BitPat
(
"b????????????_?????_110_?????_1110011"
)
def
CSRRCI
=
BitPat
(
"b????????????_?????_111_?????_1110011"
)
// fixme: add rvzicsr inst
val
table
=
Array
()
val
table
=
Array
(
CSRRW
->
List
(
InstrI
,
FuType
.
csr
,
CSROpType
.
wrt
),
CSRRS
->
List
(
InstrI
,
FuType
.
csr
,
CSROpType
.
set
),
CSRRC
->
List
(
InstrI
,
FuType
.
csr
,
CSROpType
.
clr
),
CSRRWI
->
List
(
InstrI
,
FuType
.
csr
,
CSROpType
.
wrti
),
CSRRSI
->
List
(
InstrI
,
FuType
.
csr
,
CSROpType
.
seti
),
CSRRCI
->
List
(
InstrI
,
FuType
.
csr
,
CSROpType
.
clri
)
)
}
src/main/scala/xiangshan/backend/exu/Exu.scala
浏览文件 @
e6cbcb18
...
...
@@ -56,27 +56,10 @@ abstract class Exu(val config: ExuConfig) extends XSModule {
}
object
Exu
{
val
jmpExeUnitCfg
=
ExuConfig
(
"JmpExu"
,
Array
(
jmpCfg
,
i2fCfg
),
enableBypass
=
false
)
val
jmpExeUnitCfg
=
ExuConfig
(
"JmpExu"
,
Array
(
jmpCfg
,
i2fCfg
,
csrCfg
),
enableBypass
=
false
)
val
aluExeUnitCfg
=
ExuConfig
(
"AluExu"
,
Array
(
aluCfg
),
enableBypass
=
true
)
val
mulExeUnitCfg
=
ExuConfig
(
"MulExu"
,
Array
(
mulCfg
),
enableBypass
=
false
)
val
divExeUnitCfg
=
ExuConfig
(
"DivExu"
,
Array
(
divCfg
),
enableBypass
=
false
)
val
mulDivExeUnitCfg
=
ExuConfig
(
"MulDivExu"
,
Array
(
mulCfg
,
divCfg
),
enableBypass
=
false
)
val
lsuExeUnitCfg
=
ExuConfig
(
"LsExu"
,
Array
(
lsuCfg
),
enableBypass
=
false
)
}
trait
HasExeUnits
{
val
aluExeUnits
=
Array
.
tabulate
(
exuParameters
.
AluCnt
)(
_
=>
Module
(
new
AluExeUnit
))
val
jmpExeUnit
=
Module
(
new
JmpExeUnit
)
val
mulExeUnits
=
Array
.
tabulate
(
exuParameters
.
MulCnt
)(
_
=>
Module
(
new
MulExeUnit
))
val
mduExeUnits
=
Array
.
tabulate
(
exuParameters
.
MduCnt
)(
_
=>
Module
(
new
MulDivExeUnit
))
// val fmacExeUnits = Array.tabulate(exuParameters.FmacCnt)(_ => Module(new Fmac))
// val fmiscExeUnits = Array.tabulate(exuParameters.FmiscCnt)(_ => Module(new Fmisc))
// val fmiscDivSqrtExeUnits = Array.tabulate(exuParameters.FmiscDivSqrtCnt)(_ => Module(new FmiscDivSqrt))
val
lsuExeUnits
=
Array
.
tabulate
(
exuParameters
.
StuCnt
)(
_
=>
Module
(
new
LsExeUnit
))
val
exeUnits
=
jmpExeUnit
+:
(
aluExeUnits
++
mulExeUnits
++
mduExeUnits
++
lsuExeUnits
)
exeUnits
.
foreach
(
_
.
io
.
dmem
:=
DontCare
)
exeUnits
.
foreach
(
_
.
io
.
scommit
:=
DontCare
)
}
src/main/scala/xiangshan/backend/exu/JmpExeUnit.scala
浏览文件 @
e6cbcb18
package
xiangshan.backend.exu
import
chisel3._
import
chisel3.util._
import
xiangshan._
import
xiangshan.FuType._
import
xiangshan.utils._
import
xiangshan.backend.regfile.RfWritePort
import
xiangshan.backend.fu.FunctionUnit._
import
xiangshan.backend.BRUOpType
// NOTE: BRUOpType is at backend/package.scala
// TODO: add csr
class
JmpExeUnit
extends
Exu
(
Exu
.
jmpExeUnitCfg
)
{
val
(
iovalid
,
src1
,
offset
,
func
,
pc
,
uop
)
=
(
io
.
in
.
valid
,
io
.
in
.
bits
.
src1
,
io
.
in
.
bits
.
uop
.
ctrl
.
imm
,
io
.
in
.
bits
.
uop
.
ctrl
.
fuOpType
,
SignExt
(
io
.
in
.
bits
.
uop
.
cf
.
pc
,
AddrBits
),
io
.
in
.
bits
.
uop
)
val
redirectHit
=
uop
.
brTag
.
needFlush
(
io
.
redirect
)
val
valid
=
iovalid
&&
!
redirectHit
val
isCSR
=
BRUOpType
.
isCSR
(
func
)
val
isFMV
=
BRUOpType
.
isFMV
(
func
)
val
isMOU
=
BRUOpType
.
isMOU
(
func
)
val
isJUMP
=
BRUOpType
.
isJUMP
(
func
)
// CSR
// FMV
// MOU
// JUMP
val
isRVC
=
uop
.
cf
.
isRVC
val
pcDelaySlot
=
Mux
(
isRVC
,
pc
+
2.
U
,
pc
+
4.
U
)
val
target
=
src1
+
offset
// NOTE: src1 is (pc/rf(rs1)), src2 is (offset)
import
xiangshan.
{
ExuOutput
,
FuType
,
XSConfig
}
import
xiangshan.backend.fu.
{
CSR
,
Jump
}
class
JmpExeUnit
(
implicit
val
p
:
XSConfig
)
extends
Exu
(
Exu
.
jmpExeUnitCfg
)
{
val
jmp
=
Module
(
new
Jump
)
jmp
.
io
.
out
.
ready
:=
io
.
out
.
ready
jmp
.
io
.
dmem
<>
DontCare
jmp
.
io
.
scommit
:=
DontCare
jmp
.
io
.
redirect
:=
io
.
redirect
val
csr
=
Module
(
new
CSR
)
csr
.
io
.
cfIn
:=
io
.
in
.
bits
.
uop
.
cf
csr
.
io
.
fpu_csr
:=
DontCare
csr
.
io
.
instrValid
:=
DontCare
csr
.
io
.
imemMMU
:=
DontCare
csr
.
io
.
dmemMMU
:=
DontCare
csr
.
io
.
out
.
ready
:=
io
.
out
.
ready
csr
.
io
.
in
.
bits
.
src3
:=
DontCare
val
csrOut
=
csr
.
access
(
valid
=
io
.
in
.
valid
&&
io
.
in
.
bits
.
uop
.
ctrl
.
fuType
===
FuType
.
csr
,
src1
=
io
.
in
.
bits
.
src1
,
src2
=
io
.
in
.
bits
.
src2
,
func
=
io
.
in
.
bits
.
uop
.
ctrl
.
fuOpType
)
io
.
out
.
bits
.
redirectValid
:=
valid
&&
isJUMP
io
.
out
.
bits
.
redirect
.
target
:=
target
io
.
out
.
bits
.
redirect
.
brTag
:=
uop
.
brTag
io
.
out
.
bits
.
redirect
.
isException
:=
false
.
B
io
.
out
.
bits
.
redirect
.
roqIdx
:=
uop
.
roqIdx
io
.
out
.
bits
.
redirect
.
freelistAllocPtr
:=
uop
.
freelistAllocPtr
val
csrExuOut
=
Wire
(
new
ExuOutput
)
csrExuOut
.
uop
:=
io
.
in
.
bits
.
uop
csrExuOut
.
data
:=
csrOut
csrExuOut
.
redirectValid
:=
csr
.
io
.
redirectValid
csrExuOut
.
redirect
.
brTag
:=
io
.
in
.
bits
.
uop
.
brTag
csrExuOut
.
redirect
.
isException
:=
false
.
B
csrExuOut
.
redirect
.
roqIdx
:=
io
.
in
.
bits
.
uop
.
roqIdx
csrExuOut
.
redirect
.
freelistAllocPtr
:=
io
.
in
.
bits
.
uop
.
freelistAllocPtr
csrExuOut
.
redirect
.
target
:=
csr
.
io
.
redirect
.
target
csrExuOut
.
debug
:=
DontCare
// Output
val
resCSR
=
WireInit
(
0.
U
(
XLEN
.
W
))
// TODO: implement it
val
resFMV
=
WireInit
(
0.
U
(
XLEN
.
W
))
// TODO: implement it
val
resMOU
=
WireInit
(
0.
U
(
XLEN
.
W
))
// TODO: implement it
val
resJMP
=
pcDelaySlot
val
res
=
ParallelMux
(
VecInit
(
isCSR
,
isFMV
,
isMOU
,
isJUMP
)
zip
VecInit
(
resCSR
,
resFMV
,
resMOU
,
resJMP
)
)
jmp
.
io
.
in
.
bits
:=
io
.
in
.
bits
jmp
.
io
.
in
.
valid
:=
io
.
in
.
valid
&&
io
.
in
.
bits
.
uop
.
ctrl
.
fuType
===
FuType
.
jmp
io
.
in
.
ready
:=
io
.
out
.
ready
io
.
out
.
valid
:=
valid
// TODO: CSR/MOU/FMV may need change it
io
.
out
.
bits
.
uop
<>
io
.
in
.
bits
.
uop
io
.
out
.
bits
.
data
:=
res
// NOTE: the debug info is for one-cycle exec, if FMV needs multi-cycle, may needs change it
XSDebug
(
io
.
in
.
valid
,
"In(%d %d) Out(%d %d) Redirect:(%d %d %d) brTag:%x\n"
,
io
.
in
.
valid
,
io
.
in
.
ready
,
io
.
out
.
valid
,
io
.
out
.
ready
,
io
.
redirect
.
valid
,
io
.
redirect
.
bits
.
isException
,
redirectHit
,
io
.
redirect
.
bits
.
brTag
.
value
)
XSDebug
(
io
.
in
.
valid
&&
isCSR
,
"src1:%x offset:%x func:%b type:CSR pc:%x\n"
,
src1
,
offset
,
func
,
pc
)
XSDebug
(
io
.
in
.
valid
&&
isFMV
,
"src1:%x offset:%x func:%b type:FMV pc:%x\n"
,
src1
,
offset
,
func
,
pc
)
XSDebug
(
io
.
in
.
valid
&&
isMOU
,
"src1:%x offset:%x func:%b type:MOU pc:%x\n"
,
src1
,
offset
,
func
,
pc
)
XSDebug
(
io
.
in
.
valid
&&
isJUMP
,
"src1:%x offset:%x func:%b type:JUMP pc:%x\n"
,
src1
,
offset
,
func
,
pc
)
XSDebug
(
io
.
in
.
valid
,
"Res:%x` CsrRes:%x FMV:%x Mou:%x Jmp:%x\n"
,
res
,
resCSR
,
resFMV
,
resMOU
,
resJMP
)
io
.
out
.
bits
:=
Mux
(
jmp
.
io
.
in
.
valid
,
jmp
.
io
.
out
.
bits
,
csrExuOut
)
io
.
out
.
valid
:=
io
.
in
.
valid
}
\ No newline at end of file
src/main/scala/xiangshan/backend/fu/CSR.scala
0 → 100644
浏览文件 @
e6cbcb18
此差异已折叠。
点击以展开。
src/main/scala/xiangshan/backend/fu/FunctionUnit.scala
浏览文件 @
e6cbcb18
...
...
@@ -23,9 +23,23 @@ case class FuConfig
hasRedirect
:
Boolean
)
class
FunctionUnitIO
extends
XSBundle
{
val
in
=
Flipped
(
Decoupled
(
new
Bundle
{
val
src1
=
Output
(
UInt
(
XLEN
.
W
))
val
src2
=
Output
(
UInt
(
XLEN
.
W
))
val
src3
=
Output
(
UInt
(
XLEN
.
W
))
val
func
=
Output
(
FuOpType
())
}))
val
out
=
Decoupled
(
Output
(
UInt
(
XLEN
.
W
)))
}
abstract
class
FunctionUnit
(
cfg
:
FuConfig
)
extends
XSModule
object
FunctionUnit
{
val
csrCfg
=
FuConfig
(
FuType
.
csr
,
1
,
0
,
writeIntRf
=
true
,
writeFpRf
=
false
,
hasRedirect
=
false
)
val
jmpCfg
=
FuConfig
(
FuType
.
jmp
,
1
,
0
,
writeIntRf
=
true
,
writeFpRf
=
false
,
hasRedirect
=
true
)
...
...
src/main/scala/xiangshan/backend/fu/Jump.scala
浏览文件 @
e6cbcb18
...
...
@@ -10,24 +10,16 @@ import xiangshan.backend.fu.FunctionUnit._
class
Jump
extends
FunctionUnit
(
jmpCfg
){
val
io
=
IO
(
new
ExuIO
)
override
def
toString
:
String
=
"Bru"
val
(
iovalid
,
src1
,
offset
,
func
,
pc
,
uop
)
=
(
io
.
in
.
valid
,
io
.
in
.
bits
.
src1
,
io
.
in
.
bits
.
uop
.
ctrl
.
imm
,
io
.
in
.
bits
.
uop
.
ctrl
.
fuOpType
,
SignExt
(
io
.
in
.
bits
.
uop
.
cf
.
pc
,
AddrBits
),
io
.
in
.
bits
.
uop
)
val
redirectHit
=
uop
.
brTag
.
needFlush
(
io
.
redirect
)
val
valid
=
iovalid
&&
!
redirectHit
val
isCSR
=
BRUOpType
.
isCSR
(
func
)
val
isFMV
=
BRUOpType
.
isFMV
(
func
)
val
isMOU
=
BRUOpType
.
isMOU
(
func
)
val
isJUMP
=
BRUOpType
.
isJUMP
(
func
)
// JUMP
val
isRVC
=
uop
.
cf
.
isRVC
val
pcDelaySlot
=
Mux
(
isRVC
,
pc
+
2.
U
,
pc
+
4.
U
)
val
target
=
src1
+
offset
// NOTE: src1 is (pc/rf(rs1)), src2 is (offset)
io
.
out
.
bits
.
redirectValid
:=
valid
&&
isJUMP
io
.
out
.
bits
.
redirectValid
:=
valid
io
.
out
.
bits
.
redirect
.
target
:=
target
io
.
out
.
bits
.
redirect
.
brTag
:=
uop
.
brTag
io
.
out
.
bits
.
redirect
.
isException
:=
false
.
B
...
...
@@ -35,26 +27,26 @@ class Jump extends FunctionUnit(jmpCfg){
io
.
out
.
bits
.
redirect
.
freelistAllocPtr
:=
uop
.
freelistAllocPtr
// Output
val
resCSR
=
WireInit
(
0.
U
(
XLEN
.
W
))
// TODO: implement it
val
resFMV
=
WireInit
(
0.
U
(
XLEN
.
W
))
// TODO: implement it
val
resMOU
=
WireInit
(
0.
U
(
XLEN
.
W
))
// TODO: implement it
val
resJMP
=
pcDelaySlot
val
res
=
ParallelMux
(
VecInit
(
isCSR
,
isFMV
,
isMOU
,
isJUMP
)
zip
VecInit
(
resCSR
,
resFMV
,
resMOU
,
resJMP
)
)
val
res
=
pcDelaySlot
io
.
in
.
ready
:=
io
.
out
.
ready
io
.
out
.
valid
:=
valid
// TODO: CSR/MOU/FMV may need change it
io
.
out
.
bits
.
uop
<>
io
.
in
.
bits
.
uop
io
.
out
.
bits
.
data
:=
res
io
.
dmem
<>
DontCare
io
.
out
.
bits
.
debug
<>
DontCare
// NOTE: the debug info is for one-cycle exec, if FMV needs multi-cycle, may needs change it
XSDebug
(
io
.
in
.
valid
,
"In(%d %d) Out(%d %d) Redirect:(%d %d %d) brTag:%x\n"
,
io
.
in
.
valid
,
io
.
in
.
ready
,
io
.
out
.
valid
,
io
.
out
.
ready
,
io
.
redirect
.
valid
,
io
.
redirect
.
bits
.
isException
,
redirectHit
,
io
.
redirect
.
bits
.
brTag
.
value
)
XSDebug
(
io
.
in
.
valid
&&
isCSR
,
"src1:%x offset:%x func:%b type:CSR pc:%x\n"
,
src1
,
offset
,
func
,
pc
)
XSDebug
(
io
.
in
.
valid
&&
isFMV
,
"src1:%x offset:%x func:%b type:FMV pc:%x\n"
,
src1
,
offset
,
func
,
pc
)
XSDebug
(
io
.
in
.
valid
&&
isMOU
,
"src1:%x offset:%x func:%b type:MOU pc:%x\n"
,
src1
,
offset
,
func
,
pc
)
XSDebug
(
io
.
in
.
valid
&&
isJUMP
,
"src1:%x offset:%x func:%b type:JUMP pc:%x\n"
,
src1
,
offset
,
func
,
pc
)
XSDebug
(
io
.
in
.
valid
,
"Res:%x` CsrRes:%x FMV:%x Mou:%x Jmp:%x\n"
,
res
,
resCSR
,
resFMV
,
resMOU
,
resJMP
)
io
.
in
.
valid
,
io
.
in
.
ready
,
io
.
out
.
valid
,
io
.
out
.
ready
,
io
.
redirect
.
valid
,
io
.
redirect
.
bits
.
isException
,
redirectHit
,
io
.
redirect
.
bits
.
brTag
.
value
)
XSDebug
(
io
.
in
.
valid
,
"src1:%x offset:%x func:%b type:JUMP pc:%x res:%x\n"
,
src1
,
offset
,
func
,
pc
,
res
)
}
src/main/scala/xiangshan/backend/package.scala
浏览文件 @
e6cbcb18
...
...
@@ -5,38 +5,22 @@ import chisel3.util._
package
object
backend
{
// jal csr move(x2f) mou
object
BRUOpType
{
// [2bit:Type]: 00:csr 01:move(x2f) mou(fence.i,etc) jump
// 0. csr
def
jmp
=
"b00_000"
.
U
def
wrt
=
"b00_001"
.
U
def
set
=
"b00_010"
.
U
def
clr
=
"b00_011"
.
U
def
wrti
=
"b00_101"
.
U
def
seti
=
"b00_110"
.
U
def
clri
=
"b00_111"
.
U
// 1. move(x2f)
// FIXME: temp decode, should be fixed when use it
def
fmv_w_x
=
"b01_000"
.
U
def
fmv_d_x
=
"b01_001"
.
U
// 2. mou
def
fence
=
"b01_000"
.
U
def
fencei
=
"b01_001"
.
U
def
sfence_vma
=
"b01_010"
.
U
// 3. jump
object
CSROpType
{
def
jmp
=
"b000"
.
U
def
wrt
=
"b001"
.
U
def
set
=
"b010"
.
U
def
clr
=
"b011"
.
U
def
wrti
=
"b101"
.
U
def
seti
=
"b110"
.
U
def
clri
=
"b111"
.
U
}
// jump
object
JumpOpType
{
def
jal
=
"b11_000"
.
U
def
jalr
=
"b11_010"
.
U
def
call
=
"b11_011"
.
U
def
ret
=
"b11_100"
.
U
def
isCSR
(
func
:
UInt
)
=
func
(
4
,
3
)===
0.
U
def
isFMV
(
func
:
UInt
)
=
func
(
4
,
3
)===
1.
U
def
isMOU
(
func
:
UInt
)
=
func
(
4
,
3
)===
2.
U
// TODO: change its name
def
isJUMP
(
func
:
UInt
)
=
func
(
4
,
3
)===
3.
U
}
...
...
src/main/scala/xiangshan/backend/roq/Roq.scala
浏览文件 @
e6cbcb18
...
...
@@ -46,6 +46,10 @@ class Roq(implicit val p: XSConfig) extends XSModule {
val
state
=
RegInit
(
s_idle
)
// Dispatch
val
csrEnRoq
=
io
.
dp1Req
.
map
(
i
=>
i
.
bits
.
ctrl
.
fuType
===
FuType
.
csr
)
val
hasCsr
=
RegInit
(
false
.
B
)
XSError
(!(
hasCsr
&&
state
===
s_idle
),
"CSR block should only happen in s_idle"
)
when
(
ringBufferEmpty
){
hasCsr
:=
false
.
B
}
val
validDispatch
=
VecInit
((
0
until
RenameWidth
).
map
(
io
.
dp1Req
(
_
).
valid
)).
asUInt
XSDebug
(
"(ready, valid): "
)
for
(
i
<-
0
until
RenameWidth
)
{
...
...
@@ -54,8 +58,11 @@ class Roq(implicit val p: XSConfig) extends XSModule {
microOp
(
ringBufferHead
+
offset
)
:=
io
.
dp1Req
(
i
).
bits
valid
(
ringBufferHead
+
offset
)
:=
true
.
B
writebacked
(
ringBufferHead
+
offset
)
:=
false
.
B
when
(
csrEnRoq
(
i
)){
hasCsr
:=
true
.
B
}
}
io
.
dp1Req
(
i
).
ready
:=
ringBufferAllowin
&&
!
valid
(
ringBufferHead
+
offset
)
&&
state
===
s_idle
io
.
dp1Req
(
i
).
ready
:=
(
ringBufferAllowin
&&
!
valid
(
ringBufferHead
+
offset
)
&&
state
===
s_idle
)
&&
(!
csrEnRoq
(
i
)
||
ringBufferEmpty
)
&&
!
hasCsr
io
.
roqIdxs
(
i
)
:=
ringBufferHeadExtended
+
offset
XSDebug
(
false
,
true
.
B
,
"(%d, %d) "
,
io
.
dp1Req
(
i
).
ready
,
io
.
dp1Req
(
i
).
valid
)
}
...
...
@@ -248,16 +255,6 @@ class Roq(implicit val p: XSConfig) extends XSModule {
BoringUtils
.
addSource
(
RegNext
(
0.
U
),
"difftestIntrNO"
)
//TODO: skip insts that commited in the same cycle ahead of exception
//csr debug signals
val
ModeM
=
WireInit
(
0x3
.
U
)
BoringUtils
.
addSource
(
ModeM
,
"difftestMode"
)
BoringUtils
.
addSource
(
emptyCsr
,
"difftestMstatus"
)
BoringUtils
.
addSource
(
emptyCsr
,
"difftestSstatus"
)
BoringUtils
.
addSource
(
emptyCsr
,
"difftestMepc"
)
BoringUtils
.
addSource
(
emptyCsr
,
"difftestSepc"
)
BoringUtils
.
addSource
(
emptyCsr
,
"difftestMcause"
)
BoringUtils
.
addSource
(
emptyCsr
,
"difftestScause"
)
class
Monitor
extends
BlackBox
{
val
io
=
IO
(
new
Bundle
{
val
clk
=
Input
(
Clock
())
...
...
src/main/scala/xiangshan/frontend/Ibuffer.scala
浏览文件 @
e6cbcb18
...
...
@@ -18,6 +18,7 @@ class Ibuffer extends XSModule {
io
.
out
(
i
).
bits
.
exceptionVec
:=
DontCare
io
.
out
(
i
).
bits
.
intrVec
:=
DontCare
io
.
out
(
i
).
bits
.
isBr
:=
DontCare
io
.
out
(
i
).
bits
.
crossPageIPFFix
:=
DontCare
}
//mask initial
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录