OpenCores
URL https://opencores.org/ocsvn/riscv_vhdl/riscv_vhdl/trunk

Subversion Repositories riscv_vhdl

[/] [riscv_vhdl/] [trunk/] [debugger/] [src/] [cpu_sysc_plugin/] [riverlib/] [core/] [csr.cpp] - Blame information for rev 4

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 4 sergeykhbr
/*
2
 *  Copyright 2018 Sergey Khabarov, sergeykhbr@gmail.com
3
 *
4
 *  Licensed under the Apache License, Version 2.0 (the "License");
5
 *  you may not use this file except in compliance with the License.
6
 *  You may obtain a copy of the License at
7
 *
8
 *      http://www.apache.org/licenses/LICENSE-2.0
9
 *
10
 *  Unless required by applicable law or agreed to in writing, software
11
 *  distributed under the License is distributed on an "AS IS" BASIS,
12
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
 *  See the License for the specific language governing permissions and
14
 *  limitations under the License.
15
 */
16
 
17
#include "csr.h"
18
#include "riscv-isa.h"
19
 
20
namespace debugger {
21
 
22
CsrRegs::CsrRegs(sc_module_name name_) : sc_module(name_) {
23
    SC_METHOD(comb);
24
    sensitive << i_nrst;
25
    sensitive << i_xret;
26
    sensitive << i_addr;
27
    sensitive << i_wena;
28
    sensitive << i_wdata;
29
    sensitive << i_break_mode;
30
    sensitive << i_breakpoint;
31
    sensitive << i_trap_ena;
32
    sensitive << i_trap_code;
33
    sensitive << i_trap_pc;
34
    sensitive << i_dport_ena;
35
    sensitive << i_dport_write;
36
    sensitive << i_dport_addr;
37
    sensitive << i_dport_wdata;
38
    sensitive << r.mtvec;
39
    sensitive << r.mscratch;
40
    sensitive << r.mbadaddr;
41
    sensitive << r.mode;
42
    sensitive << r.uie;
43
    sensitive << r.mie;
44
    sensitive << r.mpie;
45
    sensitive << r.mpp;
46
    sensitive << r.mepc;
47
    sensitive << r.trap_irq;
48
    sensitive << r.trap_code;
49
 
50
    SC_METHOD(registers);
51
    sensitive << i_clk.pos();
52
};
53
 
54
void CsrRegs::generateVCD(sc_trace_file *i_vcd, sc_trace_file *o_vcd) {
55
    if (o_vcd) {
56
        sc_trace(o_vcd, i_xret, "/top/proc0/csr0/i_xret");
57
        sc_trace(o_vcd, i_addr, "/top/proc0/csr0/i_addr");
58
        sc_trace(o_vcd, i_wena, "/top/proc0/csr0/i_wena");
59
        sc_trace(o_vcd, i_wdata, "/top/proc0/csr0/i_wdata");
60
        sc_trace(o_vcd, i_trap_ena, "/top/proc0/csr0/i_trap_ena");
61
        sc_trace(o_vcd, i_trap_code, "/top/proc0/csr0/i_trap_code");
62
        sc_trace(o_vcd, i_trap_pc, "/top/proc0/csr0/i_trap_pc");
63
        sc_trace(o_vcd, o_mode, "/top/proc0/csr0/o_mode");
64
        sc_trace(o_vcd, o_ie, "/top/proc0/csr0/o_ie");
65
        sc_trace(o_vcd, o_rdata, "/top/proc0/csr0/o_rdata");
66
        sc_trace(o_vcd, o_mtvec, "/top/proc0/csr0/o_mtvec");
67
        sc_trace(o_vcd, i_dport_ena, "/top/proc0/csr0/i_dport_ena");
68
        sc_trace(o_vcd, i_dport_write, "/top/proc0/csr0/i_dport_write");
69
        sc_trace(o_vcd, i_dport_addr, "/top/proc0/csr0/i_dport_addr");
70
        sc_trace(o_vcd, i_dport_wdata, "/top/proc0/csr0/i_dport_wdata");
71
        sc_trace(o_vcd, o_dport_rdata, "/top/proc0/csr0/o_dport_rdata");
72
    }
73
}
74
 
75
void CsrRegs::procedure_RegAccess(uint64_t iaddr, bool iwena,
76
                                 sc_uint<RISCV_ARCH> iwdata,
77
                                 RegistersType &ir, RegistersType *ov,
78
                                 sc_uint<RISCV_ARCH> *ordata) {
79
    *ordata = 0;
80
    switch (iaddr) {
81
    case CSR_misa:
82
        /** Base[XLEN-1:XLEN-2]
83
         *      1 = 32
84
         *      2 = 64
85
         *      3 = 128
86
         */
87
        (*ordata)(RISCV_ARCH-1, RISCV_ARCH-2) = 2;
88
        /** BitCharacterDescription
89
         * 0  A Atomic extension
90
         * 1  B Tentatively reserved for Bit operations extension
91
         * 2  C Compressed extension
92
         * 3  D Double-precision Foating-point extension
93
         * 4  E RV32E base ISA (embedded)
94
         * 5  F Single-precision Foating-point extension
95
         * 6  G Additional standard extensions present
96
         * 7  H Hypervisor mode implemented
97
         * 8  I RV32I/64I/128I base ISA
98
         * 9  J Reserved
99
         * 10 K Reserved
100
         * 11 L Tentatively reserved for Decimal Floating-Point extension
101
         * 12 M Integer Multiply/Divide extension
102
         * 13 N User-level interrupts supported
103
         * 14 O Reserved
104
         * 15 P Tentatively reserved for Packed-SIMD extension
105 2 sergeykhbr
         * 16 Q Quad-precision Foating-point extension
106
         * 17 R Reserved
107
         * 18 S Supervisor mode implemented
108
         * 19 T Tentatively reserved for Transactional Memory extension
109
         * 20 U User mode implemented
110
         * 21 V Tentatively reserved for Vector extension
111
         * 22 W Reserved
112
         * 23 X Non-standard extensions present
113
         * 24 Y Reserved
114
         * 25 Z Reserve
115
         */
116 4 sergeykhbr
        //(*ordata)['A' - 'A'] = 1;
117
        (*ordata)['I' - 'A'] = 1;
118
        (*ordata)['M' - 'A'] = 1;
119
        (*ordata)['U' - 'A'] = 1;
120
        (*ordata)['C' - 'A'] = 1;
121
        break;
122
    case CSR_mvendorid:
123
        break;
124
    case CSR_marchid:
125
        break;
126
    case CSR_mimplementationid:
127
        break;
128
    case CSR_mhartid:
129
        break;
130
    case CSR_uepc:// - User mode program counter
131
        break;
132
    case CSR_mstatus:// - Machine mode status register
133
        (*ordata)[0] = ir.uie;
134
        (*ordata)[3] = ir.mie;
135
        (*ordata)[7] = ir.mpie;
136
        (*ordata)(12, 11) = ir.mpp;
137
        if (iwena) {
138
            ov->uie = iwdata[0];
139
            ov->mie = iwdata[3];
140
            ov->mpie = iwdata[7];
141
            ov->mpp = iwdata(12, 11);
142
        }
143
        break;
144
    case CSR_medeleg:// - Machine exception delegation
145
        break;
146
    case CSR_mideleg:// - Machine itnerrupt delegation
147
        break;
148
    case CSR_mie:// - Machine interrupt enable bit
149
        break;
150
    case CSR_mtvec:
151
        (*ordata) = ir.mtvec;
152
        if (iwena) {
153
            ov->mtvec = iwdata;
154
        }
155
        break;
156
    case CSR_mtimecmp:// - Machine wall-clock timer compare value
157
        break;
158
    case CSR_mscratch:// - Machine scratch register
159
        (*ordata) = ir.mscratch;
160
        if (iwena) {
161
            ov->mscratch = iwdata;
162
        }
163
        break;
164
    case CSR_mepc:// - Machine program counter
165
        (*ordata) = ir.mepc;
166
        if (iwena) {
167
            ov->mepc = iwdata;
168
        }
169
        break;
170
    case CSR_mcause:// - Machine trap cause
171
        (*ordata) = 0;
172
        (*ordata)[63] = ir.trap_irq;
173
        (*ordata)(3, 0) = ir.trap_code;
174
        break;
175
    case CSR_mbadaddr:// - Machine bad address
176
        (*ordata) = ir.mbadaddr;
177
        break;
178
    case CSR_mip:// - Machine interrupt pending
179
        break;
180
    default:;
181
    }
182
 
183
}
184
 
185
void CsrRegs::comb() {
186
    sc_uint<RISCV_ARCH> wb_rdata = 0;
187
    sc_uint<RISCV_ARCH> wb_dport_rdata = 0;
188
    bool w_ie;
189
    bool w_dport_wena;
190
 
191
    v = r;
192
 
193
    w_dport_wena = i_dport_ena & i_dport_write;
194
 
195
    procedure_RegAccess(i_addr.read(), i_wena.read(), i_wdata.read(),
196
                        r, &v, &wb_rdata);
197
 
198
    procedure_RegAccess(i_dport_addr.read(), w_dport_wena,
199
                        i_dport_wdata.read(), r, &v, &wb_dport_rdata);
200
 
201
 
202
    if (i_addr.read() == CSR_mepc && i_xret.read()) {
203
        // Switch to previous mode
204
        v.mie = r.mpie;
205
        v.mpie = 1;
206
        v.mode = r.mpp;
207
        v.mpp = PRV_U;
208
    }
209
 
210
    if (i_trap_ena.read() && (i_break_mode.read() || !i_breakpoint.read())) {
211
        v.mie = 0;
212
        v.mpp = r.mode;
213
        v.mepc = i_trap_pc.read();
214
        v.mbadaddr = i_trap_pc.read();
215
        v.trap_code = i_trap_code.read()(3, 0);
216
        v.trap_irq = i_trap_code.read()[4];
217
        v.mode = PRV_M;
218
        switch (r.mode.read()) {
219
        case PRV_U:
220
            v.mpie = r.uie;
221
            break;
222
        case PRV_M:
223
            v.mpie = r.mie;
224
            break;
225
        default:;
226
        }
227
    }
228
 
229
    w_ie = 0;
230
    if ((r.mode.read() != PRV_M) || r.mie.read()) {
231
        w_ie = 1;
232
    }
233
 
234
    if (!i_nrst.read()) {
235
        v.mtvec = 0;
236
        v.mscratch = 0;
237
        v.mbadaddr = 0;
238
        v.mode = PRV_M;
239
        v.uie = 0;
240
        v.mie = 0;
241
        v.mpie = 0;
242
        v.mpp = 0;
243
        v.mepc = 0;
244
        v.trap_code = 0;
245
        v.trap_irq = 0;
246
    }
247
 
248
 
249
    o_rdata = wb_rdata;
250
    o_ie = w_ie;
251
    o_mode = r.mode;
252
    o_mtvec = r.mtvec.read()(BUS_ADDR_WIDTH - 1, 0);
253
    o_dport_rdata = wb_dport_rdata;
254
}
255
 
256
void CsrRegs::registers() {
257
    r = v;
258
}
259
 
260
}  // namespace debugger
261
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.