lowRISC Contributors | 802543a | 2019-08-31 12:12:56 +0100 | [diff] [blame] | 1 | // Copyright lowRISC contributors. |
| 2 | // Licensed under the Apache License, Version 2.0, see LICENSE for details. |
| 3 | // SPDX-License-Identifier: Apache-2.0 |
| 4 | // |
| 5 | // Register Package auto-generated by `reggen` containing data structure |
Eunchan Kim | 51461cd | 2019-09-18 14:00:49 -0700 | [diff] [blame] | 6 | <% |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 7 | from topgen import lib # TODO: Split lib to common lib module |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 8 | |
| 9 | from reggen.access import HwAccess, SwRdAccess, SwWrAccess |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 10 | from reggen.register import Register |
| 11 | from reggen.multi_register import MultiRegister |
Rupert Swarbrick | ede9480 | 2021-02-08 09:16:50 +0000 | [diff] [blame] | 12 | |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 13 | from reggen import gen_rtl |
| 14 | |
Rupert Swarbrick | 611a642 | 2021-02-12 11:56:48 +0000 | [diff] [blame] | 15 | localparams = block.params.get_localparams() |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 16 | |
| 17 | addr_widths = gen_rtl.get_addr_widths(block) |
Rupert Swarbrick | 269bb3d | 2021-02-23 15:41:56 +0000 | [diff] [blame] | 18 | |
| 19 | lblock = block.name.lower() |
| 20 | ublock = lblock.upper() |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 21 | |
| 22 | def reg_pfx(reg): |
| 23 | return '{}_{}'.format(ublock, reg.name.upper()) |
| 24 | |
| 25 | def reg_resname(reg): |
| 26 | return '{}_RESVAL'.format(reg_pfx(reg)) |
| 27 | |
| 28 | def field_resname(reg, field): |
| 29 | return '{}_{}_RESVAL'.format(reg_pfx(reg), field.name.upper()) |
| 30 | |
Eunchan Kim | 51461cd | 2019-09-18 14:00:49 -0700 | [diff] [blame] | 31 | %>\ |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 32 | <%def name="typedefs_for_iface(iface_name, iface_desc, for_iface, rb)">\ |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 33 | <% |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 34 | hdr = gen_rtl.make_box_quote('Typedefs for registers' + for_iface) |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 35 | %>\ |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 36 | % for r in rb.all_regs: |
| 37 | % if r.get_n_bits(["q"]): |
| 38 | % if hdr: |
| 39 | |
| 40 | ${hdr} |
| 41 | % endif |
| 42 | <% |
| 43 | r0 = gen_rtl.get_r0(r) |
| 44 | hdr = None |
| 45 | %>\ |
| 46 | |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 47 | typedef struct packed { |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 48 | % if r.is_homogeneous(): |
| 49 | ## If we have a homogeneous register or multireg, there is just one field |
| 50 | ## (possibly replicated many times). The typedef is for one copy of that |
| 51 | ## field. |
| 52 | <% |
| 53 | field = r.get_field_list()[0] |
| 54 | field_q_width = field.get_n_bits(r0.hwext, ['q']) |
| 55 | field_q_bits = lib.bitarray(field_q_width, 2) |
| 56 | %>\ |
| 57 | logic ${field_q_bits} q; |
| 58 | % if field.hwqe: |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 59 | logic qe; |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 60 | % endif |
| 61 | % if field.hwre or (r0.shadowed and r0.hwext): |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 62 | logic re; |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 63 | % endif |
| 64 | % if r0.shadowed and not r0.hwext: |
Pirmin Vogel | ab9d1ca | 2020-05-25 14:52:55 +0200 | [diff] [blame] | 65 | logic err_update; |
| 66 | logic err_storage; |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 67 | % endif |
| 68 | % else: |
| 69 | ## We are inhomogeneous, which means there is more than one different |
| 70 | ## field. Generate a reg2hw typedef that packs together all the fields of |
| 71 | ## the register. |
| 72 | % for f in r0.fields: |
| 73 | % if f.get_n_bits(r0.hwext, ["q"]) >= 1: |
| 74 | <% |
| 75 | field_q_width = f.get_n_bits(r0.hwext, ['q']) |
| 76 | field_q_bits = lib.bitarray(field_q_width, 2) |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 77 | |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 78 | struct_name = f.name.lower() |
| 79 | %>\ |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 80 | struct packed { |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 81 | logic ${field_q_bits} q; |
| 82 | % if f.hwqe: |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 83 | logic qe; |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 84 | % endif |
| 85 | % if f.hwre or (r0.shadowed and r0.hwext): |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 86 | logic re; |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 87 | % endif |
| 88 | % if r0.shadowed and not r0.hwext: |
Pirmin Vogel | ab9d1ca | 2020-05-25 14:52:55 +0200 | [diff] [blame] | 89 | logic err_update; |
| 90 | logic err_storage; |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 91 | % endif |
| 92 | } ${struct_name}; |
| 93 | %endif |
| 94 | %endfor |
| 95 | %endif |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 96 | } ${gen_rtl.get_reg_tx_type(block, r, False)}; |
Michael Schaffner | a2c51d9 | 2019-09-27 16:38:24 -0700 | [diff] [blame] | 97 | %endif |
Michael Schaffner | 9a94b6c | 2019-09-25 16:17:35 -0700 | [diff] [blame] | 98 | % endfor |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 99 | % for r in rb.all_regs: |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 100 | % if r.get_n_bits(["d"]): |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 101 | % if hdr: |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 102 | |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 103 | ${hdr} |
| 104 | % endif |
| 105 | <% |
| 106 | r0 = gen_rtl.get_r0(r) |
| 107 | hdr = None |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 108 | %>\ |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 109 | |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 110 | typedef struct packed { |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 111 | % if r.is_homogeneous(): |
| 112 | ## If we have a homogeneous register or multireg, there is just one field |
| 113 | ## (possibly replicated many times). The typedef is for one copy of that |
| 114 | ## field. |
| 115 | <% |
| 116 | field = r.get_field_list()[0] |
| 117 | field_d_width = field.get_n_bits(r0.hwext, ['d']) |
| 118 | field_d_bits = lib.bitarray(field_d_width, 2) |
| 119 | %>\ |
| 120 | logic ${field_d_bits} d; |
| 121 | % if not r0.hwext: |
| 122 | logic de; |
Michael Schaffner | a2c51d9 | 2019-09-27 16:38:24 -0700 | [diff] [blame] | 123 | % endif |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 124 | % else: |
| 125 | ## We are inhomogeneous, which means there is more than one different |
| 126 | ## field. Generate a hw2reg typedef that packs together all the fields of |
| 127 | ## the register. |
| 128 | % for f in r0.fields: |
| 129 | % if f.get_n_bits(r0.hwext, ["d"]) >= 1: |
| 130 | <% |
| 131 | field_d_width = f.get_n_bits(r0.hwext, ['d']) |
| 132 | field_d_bits = lib.bitarray(field_d_width, 2) |
| 133 | |
| 134 | struct_name = f.name.lower() |
| 135 | %>\ |
| 136 | struct packed { |
| 137 | logic ${field_d_bits} d; |
| 138 | % if not r0.hwext: |
| 139 | logic de; |
| 140 | % endif |
| 141 | } ${struct_name}; |
| 142 | %endif |
| 143 | %endfor |
| 144 | %endif |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 145 | } ${gen_rtl.get_reg_tx_type(block, r, True)}; |
Michael Schaffner | a2c51d9 | 2019-09-27 16:38:24 -0700 | [diff] [blame] | 146 | % endif |
| 147 | % endfor |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 148 | </%def>\ |
| 149 | <%def name="reg2hw_for_iface(iface_name, iface_desc, for_iface, rb)">\ |
lowRISC Contributors | 802543a | 2019-08-31 12:12:56 +0100 | [diff] [blame] | 150 | <% |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 151 | nbits = rb.get_n_bits(["q", "qe", "re"]) |
lowRISC Contributors | 802543a | 2019-08-31 12:12:56 +0100 | [diff] [blame] | 152 | packbit = 0 |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 153 | %>\ |
Michael Schaffner | 9a92bea | 2019-09-30 18:13:14 -0700 | [diff] [blame] | 154 | % if nbits > 0: |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 155 | |
| 156 | // Register -> HW type${for_iface} |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 157 | typedef struct packed { |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 158 | % for r in rb.all_regs: |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 159 | % if r.get_n_bits(["q"]): |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 160 | <% |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 161 | r0 = gen_rtl.get_r0(r) |
| 162 | struct_type = gen_rtl.get_reg_tx_type(block, r, False) |
| 163 | struct_width = r0.get_n_bits(['q', 'qe', 're']) |
| 164 | |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 165 | if isinstance(r, MultiRegister): |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 166 | struct_type += " [{}:0]".format(r.count - 1) |
| 167 | struct_width *= r.count |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 168 | |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 169 | msb = nbits - packbit - 1 |
| 170 | lsb = msb - struct_width + 1 |
| 171 | packbit += struct_width |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 172 | %>\ |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 173 | ${struct_type} ${r0.name.lower()}; // [${msb}:${lsb}] |
lowRISC Contributors | 802543a | 2019-08-31 12:12:56 +0100 | [diff] [blame] | 174 | % endif |
| 175 | % endfor |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 176 | } ${gen_rtl.get_iface_tx_type(block, iface_name, False)}; |
Michael Schaffner | 9a92bea | 2019-09-30 18:13:14 -0700 | [diff] [blame] | 177 | % endif |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 178 | </%def>\ |
| 179 | <%def name="hw2reg_for_iface(iface_name, iface_desc, for_iface, rb)">\ |
lowRISC Contributors | 802543a | 2019-08-31 12:12:56 +0100 | [diff] [blame] | 180 | <% |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 181 | nbits = rb.get_n_bits(["d", "de"]) |
lowRISC Contributors | 802543a | 2019-08-31 12:12:56 +0100 | [diff] [blame] | 182 | packbit = 0 |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 183 | %>\ |
Michael Schaffner | 9a92bea | 2019-09-30 18:13:14 -0700 | [diff] [blame] | 184 | % if nbits > 0: |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 185 | |
| 186 | // HW -> register type${for_iface} |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 187 | typedef struct packed { |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 188 | % for r in rb.all_regs: |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 189 | % if r.get_n_bits(["d"]): |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 190 | <% |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 191 | r0 = gen_rtl.get_r0(r) |
| 192 | struct_type = gen_rtl.get_reg_tx_type(block, r, True) |
| 193 | struct_width = r0.get_n_bits(['d', 'de']) |
| 194 | |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 195 | if isinstance(r, MultiRegister): |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 196 | struct_type += " [{}:0]".format(r.count - 1) |
| 197 | struct_width *= r.count |
Rupert Swarbrick | 5e62ebc | 2020-11-25 11:27:46 +0000 | [diff] [blame] | 198 | |
Rupert Swarbrick | 5e62ebc | 2020-11-25 11:27:46 +0000 | [diff] [blame] | 199 | msb = nbits - packbit - 1 |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 200 | lsb = msb - struct_width + 1 |
| 201 | packbit += struct_width |
Eunchan Kim | 668ea2e | 2019-11-12 15:44:08 -0800 | [diff] [blame] | 202 | %>\ |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 203 | ${struct_type} ${r0.name.lower()}; // [${msb}:${lsb}] |
lowRISC Contributors | 802543a | 2019-08-31 12:12:56 +0100 | [diff] [blame] | 204 | % endif |
| 205 | % endfor |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 206 | } ${gen_rtl.get_iface_tx_type(block, iface_name, True)}; |
| 207 | % endif |
| 208 | </%def>\ |
| 209 | <%def name="offsets_for_iface(iface_name, iface_desc, for_iface, rb)">\ |
| 210 | % if not rb.flat_regs: |
| 211 | <% return STOP_RENDERING %> |
Michael Schaffner | 9a92bea | 2019-09-30 18:13:14 -0700 | [diff] [blame] | 212 | % endif |
lowRISC Contributors | 802543a | 2019-08-31 12:12:56 +0100 | [diff] [blame] | 213 | |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 214 | // Register offsets${for_iface} |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 215 | <% |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 216 | aw_name, aw = addr_widths[iface_name] |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 217 | %>\ |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 218 | % for r in rb.flat_regs: |
Rupert Swarbrick | c5841b7 | 2021-02-15 08:25:02 +0000 | [diff] [blame] | 219 | <% |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 220 | value = "{}'h {:x}".format(aw, r.offset) |
| 221 | %>\ |
| 222 | parameter logic [${aw_name}-1:0] ${reg_pfx(r)}_OFFSET = ${value}; |
| 223 | % endfor |
| 224 | </%def>\ |
| 225 | <%def name="hwext_resvals_for_iface(iface_name, iface_desc, for_iface, rb)">\ |
| 226 | <% |
| 227 | hwext_regs = [r for r in rb.flat_regs if r.hwext] |
Rupert Swarbrick | c5841b7 | 2021-02-15 08:25:02 +0000 | [diff] [blame] | 228 | %>\ |
| 229 | % if hwext_regs: |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 230 | |
| 231 | // Reset values for hwext registers and their fields${for_iface} |
Rupert Swarbrick | c5841b7 | 2021-02-15 08:25:02 +0000 | [diff] [blame] | 232 | % for reg in hwext_regs: |
| 233 | <% |
| 234 | reg_width = reg.get_width() |
| 235 | reg_msb = reg_width - 1 |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 236 | reg_resval = "{}'h {:x}".format(reg_width, reg.resval) |
Rupert Swarbrick | c5841b7 | 2021-02-15 08:25:02 +0000 | [diff] [blame] | 237 | %>\ |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 238 | parameter logic [${reg_msb}:0] ${reg_resname(reg)} = ${reg_resval}; |
Rupert Swarbrick | 66e4093 | 2021-02-16 13:11:27 +0000 | [diff] [blame] | 239 | % for field in reg.fields: |
| 240 | % if field.resval is not None: |
| 241 | <% |
| 242 | field_width = field.bits.width() |
| 243 | field_msb = field_width - 1 |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 244 | field_resval = "{}'h {:x}".format(field_width, field.resval) |
Rupert Swarbrick | 66e4093 | 2021-02-16 13:11:27 +0000 | [diff] [blame] | 245 | %>\ |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 246 | parameter logic [${field_msb}:0] ${field_resname(reg, field)} = ${field_resval}; |
Rupert Swarbrick | 66e4093 | 2021-02-16 13:11:27 +0000 | [diff] [blame] | 247 | % endif |
| 248 | % endfor |
Rupert Swarbrick | c5841b7 | 2021-02-15 08:25:02 +0000 | [diff] [blame] | 249 | % endfor |
Rupert Swarbrick | c5841b7 | 2021-02-15 08:25:02 +0000 | [diff] [blame] | 250 | % endif |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 251 | </%def>\ |
| 252 | <%def name="windows_for_iface(iface_name, iface_desc, for_iface, rb)">\ |
| 253 | % if rb.windows: |
| 254 | <% |
| 255 | aw_name, aw = addr_widths[iface_name] |
| 256 | %>\ |
| 257 | |
| 258 | // Window parameters${for_iface} |
| 259 | % for i,w in enumerate(rb.windows): |
Rupert Swarbrick | bc2bc58 | 2021-02-09 13:30:37 +0000 | [diff] [blame] | 260 | <% |
| 261 | win_pfx = '{}_{}'.format(ublock, w.name.upper()) |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 262 | base_txt_val = "{}'h {:x}".format(aw, w.offset) |
Rupert Swarbrick | cfcfbce | 2021-03-09 14:14:30 +0000 | [diff] [blame] | 263 | size_txt_val = "'h {:x}".format(w.size_in_bytes) |
lowRISC Contributors | 802543a | 2019-08-31 12:12:56 +0100 | [diff] [blame] | 264 | |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 265 | offset_type = 'logic [{}-1:0]'.format(aw_name) |
| 266 | size_type = 'int unsigned' |
| 267 | max_type_len = max(len(offset_type), len(size_type)) |
| 268 | |
| 269 | offset_type += ' ' * (max_type_len - len(offset_type)) |
| 270 | size_type += ' ' * (max_type_len - len(size_type)) |
| 271 | |
| 272 | %>\ |
| 273 | parameter ${offset_type} ${win_pfx}_OFFSET = ${base_txt_val}; |
| 274 | parameter ${size_type} ${win_pfx}_SIZE = ${size_txt_val}; |
| 275 | % endfor |
Rupert Swarbrick | c5841b7 | 2021-02-15 08:25:02 +0000 | [diff] [blame] | 276 | % endif |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 277 | </%def>\ |
| 278 | <%def name="reg_data_for_iface(iface_name, iface_desc, for_iface, rb)">\ |
| 279 | % if rb.flat_regs: |
| 280 | <% |
| 281 | lpfx = gen_rtl.get_type_name_pfx(block, iface_name) |
| 282 | upfx = lpfx.upper() |
| 283 | idx_len = len("{}".format(len(rb.flat_regs) - 1)) |
| 284 | %>\ |
| 285 | |
| 286 | // Register index${for_iface} |
Eunchan Kim | 51461cd | 2019-09-18 14:00:49 -0700 | [diff] [blame] | 287 | typedef enum int { |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 288 | % for r in rb.flat_regs: |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 289 | ${ublock}_${r.name.upper()}${"" if loop.last else ","} |
Eunchan Kim | 51461cd | 2019-09-18 14:00:49 -0700 | [diff] [blame] | 290 | % endfor |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 291 | } ${lpfx}_id_e; |
Eunchan Kim | 51461cd | 2019-09-18 14:00:49 -0700 | [diff] [blame] | 292 | |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 293 | // Register width information to check illegal writes${for_iface} |
| 294 | parameter logic [3:0] ${upfx}_PERMIT [${len(rb.flat_regs)}] = '{ |
| 295 | % for i, r in enumerate(rb.flat_regs): |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 296 | <% |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 297 | index_str = "{}".format(i).rjust(idx_len) |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 298 | width = r.get_width() |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 299 | if width > 24: |
| 300 | mask = '1111' |
| 301 | elif width > 16: |
| 302 | mask = '0111' |
| 303 | elif width > 8: |
| 304 | mask = '0011' |
| 305 | else: |
| 306 | mask = '0001' |
| 307 | |
| 308 | comma = ',' if i < len(rb.flat_regs) - 1 else ' ' |
Rupert Swarbrick | 4d64536 | 2021-02-08 17:17:05 +0000 | [diff] [blame] | 309 | %>\ |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 310 | 4'b ${mask}${comma} // index[${index_str}] ${ublock}_${r.name.upper()} |
| 311 | % endfor |
Eunchan Kim | 51461cd | 2019-09-18 14:00:49 -0700 | [diff] [blame] | 312 | }; |
Rupert Swarbrick | 200d8b4 | 2021-03-08 12:32:11 +0000 | [diff] [blame] | 313 | % endif |
| 314 | </%def>\ |
| 315 | |
| 316 | package ${lblock}_reg_pkg; |
| 317 | % if localparams: |
| 318 | |
| 319 | // Param list |
| 320 | % for param in localparams: |
| 321 | parameter ${param.param_type} ${param.name} = ${param.value}; |
| 322 | % endfor |
| 323 | % endif |
| 324 | |
| 325 | // Address widths within the block |
| 326 | % for param_name, width in addr_widths.values(): |
| 327 | parameter int ${param_name} = ${width}; |
| 328 | % endfor |
| 329 | <% |
| 330 | just_default = len(block.reg_blocks) == 1 and None in block.reg_blocks |
| 331 | %>\ |
| 332 | % for iface_name, rb in block.reg_blocks.items(): |
| 333 | <% |
| 334 | iface_desc = iface_name or 'default' |
| 335 | for_iface = '' if just_default else ' for {} interface'.format(iface_desc) |
| 336 | %>\ |
| 337 | ${typedefs_for_iface(iface_name, iface_desc, for_iface, rb)}\ |
| 338 | ${reg2hw_for_iface(iface_name, iface_desc, for_iface, rb)}\ |
| 339 | ${hw2reg_for_iface(iface_name, iface_desc, for_iface, rb)}\ |
| 340 | ${offsets_for_iface(iface_name, iface_desc, for_iface, rb)}\ |
| 341 | ${hwext_resvals_for_iface(iface_name, iface_desc, for_iface, rb)}\ |
| 342 | ${windows_for_iface(iface_name, iface_desc, for_iface, rb)}\ |
| 343 | ${reg_data_for_iface(iface_name, iface_desc, for_iface, rb)}\ |
| 344 | % endfor |
| 345 | |
lowRISC Contributors | 802543a | 2019-08-31 12:12:56 +0100 | [diff] [blame] | 346 | endpackage |
Eunchan Kim | 51461cd | 2019-09-18 14:00:49 -0700 | [diff] [blame] | 347 | |