4 clint_t::clint_t(std::vector
<processor_t
*>& procs
)
5 : procs(procs
), mtimecmp(procs
.size())
11 * 4000 mtimecmp hart 0 lo
12 * 4004 mtimecmp hart 0 hi
13 * 4008 mtimecmp hart 1 lo
14 * 400c mtimecmp hart 1 hi
20 #define MTIMECMP_BASE 0x4000
21 #define MTIME_BASE 0xbff8
23 bool clint_t::load(reg_t addr
, size_t len
, uint8_t* bytes
)
25 if (addr
>= MSIP_BASE
&& addr
+ len
<= MSIP_BASE
+ procs
.size()*sizeof(msip_t
)) {
26 std::vector
<msip_t
> msip(procs
.size());
27 for (size_t i
= 0; i
< procs
.size(); ++i
)
28 msip
[i
] = !!(procs
[i
]->state
.mip
& MIP_MSIP
);
29 memcpy(bytes
, (uint8_t*)&msip
[0] + addr
- MSIP_BASE
, len
);
30 } else if (addr
>= MTIMECMP_BASE
&& addr
+ len
<= MTIMECMP_BASE
+ procs
.size()*sizeof(mtimecmp_t
)) {
31 memcpy(bytes
, (uint8_t*)&mtimecmp
[0] + addr
- MTIMECMP_BASE
, len
);
32 } else if (addr
>= MTIME_BASE
&& addr
+ len
<= MTIME_BASE
+ sizeof(mtime_t
)) {
33 memcpy(bytes
, (uint8_t*)&mtime
+ addr
- MTIME_BASE
, len
);
40 bool clint_t::store(reg_t addr
, size_t len
, const uint8_t* bytes
)
42 if (addr
>= MSIP_BASE
&& addr
+ len
<= MSIP_BASE
+ procs
.size()*sizeof(msip_t
)) {
43 std::vector
<msip_t
> msip(procs
.size());
44 std::vector
<msip_t
> mask(procs
.size(), 0);
45 memcpy((uint8_t*)&msip
[0] + addr
- MSIP_BASE
, bytes
, len
);
46 memset((uint8_t*)&mask
[0] + addr
- MSIP_BASE
, 0xff, len
);
47 for (size_t i
= 0; i
< procs
.size(); ++i
) {
48 if (!(mask
[i
] & 0xFF)) continue;
49 procs
[i
]->state
.mip
&= ~MIP_MSIP
;
51 procs
[i
]->state
.mip
|= MIP_MSIP
;
53 } else if (addr
>= MTIMECMP_BASE
&& addr
+ len
<= MTIMECMP_BASE
+ procs
.size()*sizeof(mtimecmp_t
)) {
54 memcpy((uint8_t*)&mtimecmp
[0] + addr
- MTIMECMP_BASE
, bytes
, len
);
55 } else if (addr
>= MTIME_BASE
&& addr
+ len
<= MTIME_BASE
+ sizeof(mtime_t
)) {
56 memcpy((uint8_t*)&mtime
+ addr
- MTIME_BASE
, bytes
, len
);
64 void clint_t::increment(reg_t inc
)
67 for (size_t i
= 0; i
< procs
.size(); i
++) {
68 procs
[i
]->state
.mip
&= ~MIP_MTIP
;
69 if (mtime
>= mtimecmp
[i
])
70 procs
[i
]->state
.mip
|= MIP_MTIP
;