1 //
2 // Copyright 2015 Ettus Research LLC
3 // Copyright 2018 Ettus Research, a National Instruments Company
4 //
5 // SPDX-License-Identifier: GPL-3.0-or-later
6 //
7 
8 #ifndef INCLUDED_DBOARD_TWINRX_IO_HPP
9 #define INCLUDED_DBOARD_TWINRX_IO_HPP
10 
11 #include <uhd/types/wb_iface.hpp>
12 #include <uhd/usrp/dboard_base.hpp>
13 #include <uhd/utils/soft_register.hpp>
14 #include <uhdlib/usrp/cores/gpio_atr_3000.hpp>
15 #include <boost/thread.hpp>
16 
17 namespace uhd { namespace usrp { namespace dboard { namespace twinrx {
18 
19 static const uint32_t SET_ALL_BITS = 0xFFFFFFFF;
20 
21 namespace cpld {
addr(uint8_t cpld_num,uint8_t cpld_addr)22 static wb_iface::wb_addr_type addr(uint8_t cpld_num, uint8_t cpld_addr)
23 {
24     // Decode CPLD addressing for the following bitmap:
25     // {CPLD1_EN, CPLD2_EN, CPLD3_EN, CPLD4_EN, CPLD_ADDR[2:0]}
26     uint8_t addr = 0;
27     switch (cpld_num) {
28         case 1:
29             addr = 0x8 << 3;
30             break;
31         case 2:
32             addr = 0x4 << 3;
33             break;
34         case 3:
35             addr = 0x2 << 3;
36             break;
37         case 4:
38             addr = 0x1 << 3;
39             break;
40         default:
41             UHD_THROW_INVALID_CODE_PATH();
42     }
43     return static_cast<wb_iface::wb_addr_type>(addr | (cpld_addr & 0x7));
44 }
45 
get_reg(wb_iface::wb_addr_type addr)46 static uint32_t get_reg(wb_iface::wb_addr_type addr)
47 {
48     return static_cast<uint32_t>(addr) & 0x7;
49 }
50 } // namespace cpld
51 
52 class twinrx_gpio : public wb_iface
53 {
54 public:
55     typedef std::shared_ptr<twinrx_gpio> sptr;
56 
57     //----------------------------------------------
58     // Public GPIO fields
59     UHD_DEFINE_SOFT_REG_FIELD(FIELD_LO2_CE_CH1, /*width*/ 1, /*shift*/ 0); // GPIO[0] OUT
60     UHD_DEFINE_SOFT_REG_FIELD(FIELD_LO2_CE_CH2, /*width*/ 1, /*shift*/ 1); // GPIO[1] OUT
61     UHD_DEFINE_SOFT_REG_FIELD(
62         FIELD_LO2_MUXOUT_CH1, /*width*/ 1, /*shift*/ 2); // GPIO[2]       IN
63     UHD_DEFINE_SOFT_REG_FIELD(
64         FIELD_LO2_MUXOUT_CH2, /*width*/ 1, /*shift*/ 3); // GPIO[3]       IN
65     UHD_DEFINE_SOFT_REG_FIELD(FIELD_LO2_LD_CH1, /*width*/ 1, /*shift*/ 4); // GPIO[4] IN
66     UHD_DEFINE_SOFT_REG_FIELD(FIELD_LO2_LD_CH2, /*width*/ 1, /*shift*/ 5); // GPIO[5] IN
67     // NO CONNECT //GPIO[8:6] PRIVATE //GPIO[15:9] NO CONNECT //GPIO[16]
68     UHD_DEFINE_SOFT_REG_FIELD(
69         FIELD_LO1_CE_CH1, /*width*/ 1, /*shift*/ 17); // GPIO[17]      OUT
70     UHD_DEFINE_SOFT_REG_FIELD(
71         FIELD_LO1_CE_CH2, /*width*/ 1, /*shift*/ 18); // GPIO[18]      OUT
72     UHD_DEFINE_SOFT_REG_FIELD(
73         FIELD_LO1_MUXOUT_CH1, /*width*/ 1, /*shift*/ 19); // GPIO[19]      IN
74     UHD_DEFINE_SOFT_REG_FIELD(
75         FIELD_LO1_MUXOUT_CH2, /*width*/ 1, /*shift*/ 20); // GPIO[20]      IN
76     // NO CONNECT //GPIO[21:23]
77     UHD_DEFINE_SOFT_REG_FIELD(FIELD_SWPS_CLK, /*width*/ 1, /*shift*/ 24); // GPIO[24] IN
78     UHD_DEFINE_SOFT_REG_FIELD(
79         FIELD_SWPS_PWR_GOOD, /*width*/ 1, /*shift*/ 25); // GPIO[25]      IN
80     UHD_DEFINE_SOFT_REG_FIELD(FIELD_SWPS_EN, /*width*/ 1, /*shift*/ 26); // GPIO[26] OUT
81     // PRIVATE //GPIO[27:31]
82     //----------------------------------------------
83 
twinrx_gpio(dboard_iface::sptr iface)84     twinrx_gpio(dboard_iface::sptr iface) : _db_iface(iface)
85     {
86         _db_iface->set_gpio_ddr(dboard_iface::UNIT_BOTH, GPIO_OUTPUT_MASK, SET_ALL_BITS);
87         _db_iface->set_pin_ctrl(dboard_iface::UNIT_BOTH, GPIO_PINCTRL_MASK, SET_ALL_BITS);
88         _db_iface->set_gpio_out(dboard_iface::UNIT_BOTH, 0, ~GPIO_PINCTRL_MASK);
89     }
90 
~twinrx_gpio()91     ~twinrx_gpio()
92     {
93         _db_iface->set_gpio_ddr(dboard_iface::UNIT_BOTH, ~GPIO_OUTPUT_MASK, SET_ALL_BITS);
94     }
95 
set_field(const uhd::soft_reg_field_t field,const uint32_t value)96     void set_field(const uhd::soft_reg_field_t field, const uint32_t value)
97     {
98         boost::lock_guard<boost::mutex> lock(_mutex);
99         using namespace soft_reg_field;
100 
101         _db_iface->set_gpio_out(
102             dboard_iface::UNIT_BOTH, (value << shift(field)), mask<uint32_t>(field));
103     }
104 
get_field(const uhd::soft_reg_field_t field)105     uint32_t get_field(const uhd::soft_reg_field_t field)
106     {
107         boost::lock_guard<boost::mutex> lock(_mutex);
108         using namespace soft_reg_field;
109         return (_db_iface->read_gpio(dboard_iface::UNIT_BOTH) & mask<uint32_t>(field))
110                >> shift(field);
111     }
112 
113     // CPLD register write-only interface
poke32(const wb_addr_type addr,const uint32_t data)114     void poke32(const wb_addr_type addr, const uint32_t data)
115     {
116         boost::lock_guard<boost::mutex> lock(_mutex);
117         using namespace soft_reg_field;
118 
119         // Step 1: Write the reg offset and data to the GPIO bus and de-assert all enables
120         _db_iface->set_gpio_out(dboard_iface::UNIT_BOTH,
121             (cpld::get_reg(addr) << shift(CPLD_FULL_ADDR)) | (data << shift(CPLD_DATA)),
122             mask<uint32_t>(CPLD_FULL_ADDR) | mask<uint32_t>(CPLD_DATA));
123         // Sleep for 166ns to ensure that we don't toggle the enables too quickly
124         // The underlying sleep function rounds to microsecond precision.
125         _db_iface->sleep(boost::chrono::nanoseconds(166));
126         // Step 2: Write the reg offset and data, and assert the necessary enable
127         _db_iface->set_gpio_out(dboard_iface::UNIT_BOTH,
128             (static_cast<uint32_t>(addr) << shift(CPLD_FULL_ADDR))
129                 | (data << shift(CPLD_DATA)),
130             mask<uint32_t>(CPLD_FULL_ADDR) | mask<uint32_t>(CPLD_DATA));
131     }
132 
133 private: // Members/definitions
134     static const uint32_t GPIO_OUTPUT_MASK  = 0xFC06FE03;
135     static const uint32_t GPIO_PINCTRL_MASK = 0x00000000;
136 
137     // Private GPIO fields
138     UHD_DEFINE_SOFT_REG_FIELD(CPLD_FULL_ADDR, /*width*/ 7, /*shift*/ 9); // GPIO[15:9]
139     UHD_DEFINE_SOFT_REG_FIELD(CPLD_DATA, /*width*/ 5, /*shift*/ 27); // GPIO[31:27]
140 
141     // Members
142     dboard_iface::sptr _db_iface;
143     boost::mutex _mutex;
144 };
145 
146 class twinrx_cpld_regmap : public uhd::soft_regmap_t
147 {
148 public:
149     typedef std::shared_ptr<twinrx_cpld_regmap> sptr;
150 
151     //----------------------------------------------
152     // IF CCA: CPLD 1
153     //----------------------------------------------
154     class if0_reg0_t : public uhd::soft_reg32_wo_t
155     {
156     public:
157         UHD_DEFINE_SOFT_REG_FIELD(AMP_HB_IF1_EN_CH1, /*width*/ 1, /*shift*/ 0);
158         UHD_DEFINE_SOFT_REG_FIELD(AMP_LO2_EN_CH1, /*width*/ 1, /*shift*/ 1);
159         UHD_DEFINE_SOFT_REG_FIELD(AMP_LO2_EN_CH2, /*width*/ 1, /*shift*/ 2);
160         UHD_DEFINE_SOFT_REG_FIELD(SW19_CTRL_CH2, /*width*/ 1, /*shift*/ 3);
161         UHD_DEFINE_SOFT_REG_FIELD(SW20_CTRL_CH2, /*width*/ 1, /*shift*/ 4);
162 
if0_reg0_t()163         if0_reg0_t()
164             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 1, /*reg*/ 0), OPTIMIZED_FLUSH)
165         {
166             set(REGISTER, 0);
167         }
168     } if0_reg0;
169 
170     class if0_reg1_t : public uhd::soft_reg32_wo_t
171     {
172     public:
173         UHD_DEFINE_SOFT_REG_FIELD(SW20_CTRL_CH1, /*width*/ 1, /*shift*/ 2);
174 
if0_reg1_t()175         if0_reg1_t()
176             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 1, /*reg*/ 1), OPTIMIZED_FLUSH)
177         {
178             set(REGISTER, 0);
179         }
180     } if0_reg1;
181 
182     class if0_reg2_t : public uhd::soft_reg32_wo_t
183     {
184     public:
185         UHD_DEFINE_SOFT_REG_FIELD(AMP_LB_IF1_EN_CH2, /*width*/ 1, /*shift*/ 0);
186         UHD_DEFINE_SOFT_REG_FIELD(AMP_LB_IF1_EN_CH1, /*width*/ 1, /*shift*/ 1);
187         UHD_DEFINE_SOFT_REG_FIELD(LO2_LE_CH1, /*width*/ 1, /*shift*/ 3);
188         UHD_DEFINE_SOFT_REG_FIELD(LO2_LE_CH2, /*width*/ 1, /*shift*/ 4);
189 
if0_reg2_t()190         if0_reg2_t()
191             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 1, /*reg*/ 2), OPTIMIZED_FLUSH)
192         {
193             set(REGISTER, 0);
194         }
195     } if0_reg2;
196 
197     class if0_reg3_t : public uhd::soft_reg32_wo_t
198     {
199     public:
200         UHD_DEFINE_SOFT_REG_FIELD(SW24_CTRL_CH1, /*width*/ 1, /*shift*/ 1);
201         UHD_DEFINE_SOFT_REG_FIELD(SW13_CTRL_CH1, /*width*/ 1, /*shift*/ 2);
202         UHD_DEFINE_SOFT_REG_FIELD(IF1_IF2_EN_CH1, /*width*/ 1, /*shift*/ 3);
203 
if0_reg3_t()204         if0_reg3_t()
205             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 1, /*reg*/ 3), OPTIMIZED_FLUSH)
206         {
207             set(REGISTER, 0);
208         }
209     } if0_reg3;
210 
211     class if0_reg4_t : public uhd::soft_reg32_wo_t
212     {
213     public:
214         UHD_DEFINE_SOFT_REG_FIELD(SW21_CTRL_CH2, /*width*/ 1, /*shift*/ 0);
215         UHD_DEFINE_SOFT_REG_FIELD(SW25_CTRL, /*width*/ 1, /*shift*/ 1);
216         UHD_DEFINE_SOFT_REG_FIELD(IF1_IF2_EN_CH2, /*width*/ 1, /*shift*/ 2);
217         UHD_DEFINE_SOFT_REG_FIELD(SW19_CTRL_CH1, /*width*/ 1, /*shift*/ 3);
218         UHD_DEFINE_SOFT_REG_FIELD(SW21_CTRL_CH1, /*width*/ 1, /*shift*/ 4);
219 
if0_reg4_t()220         if0_reg4_t()
221             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 1, /*reg*/ 4), OPTIMIZED_FLUSH)
222         {
223             set(REGISTER, 0);
224         }
225     } if0_reg4;
226 
227     class if0_reg6_t : public uhd::soft_reg32_wo_t
228     {
229     public:
230         UHD_DEFINE_SOFT_REG_FIELD(AMP_HB_IF1_EN_CH2, /*width*/ 1, /*shift*/ 0);
231         UHD_DEFINE_SOFT_REG_FIELD(SW13_CTRL_CH2, /*width*/ 1, /*shift*/ 2);
232 
if0_reg6_t()233         if0_reg6_t()
234             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 1, /*reg*/ 6), OPTIMIZED_FLUSH)
235         {
236             set(REGISTER, 0);
237         }
238     } if0_reg6;
239 
240     class if0_reg7_t : public uhd::soft_reg32_wo_t
241     {
242     public:
243         UHD_DEFINE_SOFT_REG_FIELD(SW24_CTRL_CH2, /*width*/ 1, /*shift*/ 0);
244 
if0_reg7_t()245         if0_reg7_t()
246             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 1, /*reg*/ 7), OPTIMIZED_FLUSH)
247         {
248             set(REGISTER, 0);
249         }
250     } if0_reg7;
251 
252     //----------------------------------------------
253     // RF CCA: CPLD 2
254     //----------------------------------------------
255     class rf0_reg0_t : public uhd::soft_reg32_wo_t
256     {
257     public:
258         UHD_DEFINE_SOFT_REG_FIELD(ATTEN_IN_CH1, /*width*/ 5, /*shift*/ 0);
259 
rf0_reg0_t()260         rf0_reg0_t()
261             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 2, /*reg*/ 0), OPTIMIZED_FLUSH)
262         {
263             set(REGISTER, 0);
264         }
265     } rf0_reg0;
266 
267     class rf0_reg1_t : public uhd::soft_reg32_wo_t
268     {
269     public:
270         UHD_DEFINE_SOFT_REG_FIELD(SWPA1_CTL_CH1, /*width*/ 1, /*shift*/ 1);
271         UHD_DEFINE_SOFT_REG_FIELD(HB_PREAMP_EN_CH1, /*width*/ 1, /*shift*/ 2);
272         UHD_DEFINE_SOFT_REG_FIELD(LB_PREAMP_EN_CH1, /*width*/ 1, /*shift*/ 3);
273         UHD_DEFINE_SOFT_REG_FIELD(SWPA3_CTRL_CH2, /*width*/ 1, /*shift*/ 4);
274 
rf0_reg1_t()275         rf0_reg1_t()
276             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 2, /*reg*/ 1), OPTIMIZED_FLUSH)
277         {
278             set(REGISTER, 0);
279         }
280     } rf0_reg1;
281 
282     class rf0_reg2_t : public uhd::soft_reg32_wo_t
283     {
284     public:
285         UHD_DEFINE_SOFT_REG_FIELD(SW6_CTRL_CH1, /*width*/ 1, /*shift*/ 0);
286         UHD_DEFINE_SOFT_REG_FIELD(SW5_CTRL_CH1, /*width*/ 1, /*shift*/ 1);
287         UHD_DEFINE_SOFT_REG_FIELD(SW4_CTRL_CH1, /*width*/ 1, /*shift*/ 2);
288         UHD_DEFINE_SOFT_REG_FIELD(LO1_LE_CH1, /*width*/ 1, /*shift*/ 3);
289         UHD_DEFINE_SOFT_REG_FIELD(LO1_LE_CH2, /*width*/ 1, /*shift*/ 4);
290 
rf0_reg2_t()291         rf0_reg2_t()
292             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 2, /*reg*/ 2), OPTIMIZED_FLUSH)
293         {
294             set(REGISTER, 0);
295         }
296     } rf0_reg2;
297 
298     class rf0_reg3_t : public uhd::soft_reg32_wo_t
299     {
300     public:
301         UHD_DEFINE_SOFT_REG_FIELD(SW9_CTRL_CH2, /*width*/ 2, /*shift*/ 0);
302         UHD_DEFINE_SOFT_REG_FIELD(SW7_CTRL_CH1, /*width*/ 2, /*shift*/ 2);
303 
rf0_reg3_t()304         rf0_reg3_t()
305             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 2, /*reg*/ 3), OPTIMIZED_FLUSH)
306         {
307             set(REGISTER, 0);
308         }
309     } rf0_reg3;
310 
311     class rf0_reg4_t : public uhd::soft_reg32_wo_t
312     {
313     public:
314         UHD_DEFINE_SOFT_REG_FIELD(ATTEN_IN_CH2, /*width*/ 5, /*shift*/ 0);
315 
rf0_reg4_t()316         rf0_reg4_t()
317             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 2, /*reg*/ 4), OPTIMIZED_FLUSH)
318         {
319             set(REGISTER, 0);
320         }
321     } rf0_reg4;
322 
323     class rf0_reg5_t : public uhd::soft_reg32_wo_t
324     {
325     public:
326         UHD_DEFINE_SOFT_REG_FIELD(SW9_CTRL_CH1, /*width*/ 2, /*shift*/ 0);
327         UHD_DEFINE_SOFT_REG_FIELD(HB_PREAMP_EN_CH2, /*width*/ 1, /*shift*/ 2);
328         UHD_DEFINE_SOFT_REG_FIELD(SW3_CTRL_CH1, /*width*/ 1, /*shift*/ 4);
329 
rf0_reg5_t()330         rf0_reg5_t()
331             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 2, /*reg*/ 5), OPTIMIZED_FLUSH)
332         {
333             set(REGISTER, 0);
334         }
335     } rf0_reg5;
336 
337     class rf0_reg6_t : public uhd::soft_reg32_wo_t
338     {
339     public:
340         UHD_DEFINE_SOFT_REG_FIELD(SW6_CTRL_CH2, /*width*/ 1, /*shift*/ 0);
341         UHD_DEFINE_SOFT_REG_FIELD(SW5_CTRL_CH2, /*width*/ 1, /*shift*/ 1);
342         UHD_DEFINE_SOFT_REG_FIELD(SW4_CTRL_CH2, /*width*/ 1, /*shift*/ 2);
343         UHD_DEFINE_SOFT_REG_FIELD(SWPA4_CTRL_CH2, /*width*/ 1, /*shift*/ 4);
344 
rf0_reg6_t()345         rf0_reg6_t()
346             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 2, /*reg*/ 6), OPTIMIZED_FLUSH)
347         {
348             set(REGISTER, 0);
349         }
350     } rf0_reg6;
351 
352     class rf0_reg7_t : public uhd::soft_reg32_wo_t
353     {
354     public:
355         UHD_DEFINE_SOFT_REG_FIELD(SWPA1_CTRL_CH2, /*width*/ 1, /*shift*/ 0);
356         UHD_DEFINE_SOFT_REG_FIELD(SWPA3_CTRL_CH1, /*width*/ 1, /*shift*/ 1);
357         UHD_DEFINE_SOFT_REG_FIELD(SW3_CTRL_CH2, /*width*/ 1, /*shift*/ 2);
358         UHD_DEFINE_SOFT_REG_FIELD(SW7_CTRL_CH2, /*width*/ 2, /*shift*/ 3);
359 
rf0_reg7_t()360         rf0_reg7_t()
361             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 2, /*reg*/ 7), OPTIMIZED_FLUSH)
362         {
363             set(REGISTER, 0);
364         }
365     } rf0_reg7;
366 
367     //----------------------------------------------
368     // RF CCA: CPLD 3
369     //----------------------------------------------
370     class rf1_reg0_t : public uhd::soft_reg32_wo_t
371     {
372     public:
373         UHD_DEFINE_SOFT_REG_FIELD(ATTEN_HB_CH1, /*width*/ 5, /*shift*/ 0);
374 
rf1_reg0_t()375         rf1_reg0_t()
376             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 3, /*reg*/ 0), OPTIMIZED_FLUSH)
377         {
378             set(REGISTER, 0);
379         }
380     } rf1_reg0;
381 
382     class rf1_reg1_t : public uhd::soft_reg32_wo_t
383     {
384     public:
385         UHD_DEFINE_SOFT_REG_FIELD(SW17_CTRL_CH1, /*width*/ 1, /*shift*/ 0);
386         UHD_DEFINE_SOFT_REG_FIELD(AMP_LO1_EN_CH1, /*width*/ 1, /*shift*/ 1);
387         UHD_DEFINE_SOFT_REG_FIELD(SW16_CTRL_CH1, /*width*/ 1, /*shift*/ 2);
388         UHD_DEFINE_SOFT_REG_FIELD(SW15_CTRL_CH1, /*width*/ 1, /*shift*/ 3);
389         UHD_DEFINE_SOFT_REG_FIELD(SW14_CTRL_CH1, /*width*/ 1, /*shift*/ 4);
390 
rf1_reg1_t()391         rf1_reg1_t()
392             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 3, /*reg*/ 1), OPTIMIZED_FLUSH)
393         {
394             set(REGISTER, 0);
395         }
396     } rf1_reg1;
397 
398     class rf1_reg2_t : public uhd::soft_reg32_wo_t
399     {
400     public:
401         UHD_DEFINE_SOFT_REG_FIELD(SW12_CTRL_CH1, /*width*/ 1, /*shift*/ 0);
402         UHD_DEFINE_SOFT_REG_FIELD(AMP_HB_EN_CH1, /*width*/ 1, /*shift*/ 1);
403         UHD_DEFINE_SOFT_REG_FIELD(HB_PRESEL_PGA_EN_CH2, /*width*/ 1, /*shift*/ 2);
404 
rf1_reg2_t()405         rf1_reg2_t()
406             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 3, /*reg*/ 2), OPTIMIZED_FLUSH)
407         {
408             set(REGISTER, 0);
409         }
410     } rf1_reg2;
411 
412     class rf1_reg3_t : public uhd::soft_reg32_wo_t
413     {
414     public:
415         UHD_DEFINE_SOFT_REG_FIELD(SW23_CTRL, /*width*/ 1, /*shift*/ 0);
416         UHD_DEFINE_SOFT_REG_FIELD(SW22_CTRL_CH1, /*width*/ 1, /*shift*/ 1);
417         UHD_DEFINE_SOFT_REG_FIELD(SW10_CTRL_CH1, /*width*/ 2, /*shift*/ 2);
418 
rf1_reg3_t()419         rf1_reg3_t()
420             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 3, /*reg*/ 3), OPTIMIZED_FLUSH)
421         {
422             set(REGISTER, 0);
423         }
424     } rf1_reg3;
425 
426     class rf1_reg4_t : public uhd::soft_reg32_wo_t
427     {
428     public:
429         UHD_DEFINE_SOFT_REG_FIELD(ATTEN_HB_CH2, /*width*/ 5, /*shift*/ 0);
430 
rf1_reg4_t()431         rf1_reg4_t()
432             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 3, /*reg*/ 4), OPTIMIZED_FLUSH)
433         {
434             set(REGISTER, 0);
435         }
436     } rf1_reg4;
437 
438     class rf1_reg5_t : public uhd::soft_reg32_wo_t
439     {
440     public:
441         UHD_DEFINE_SOFT_REG_FIELD(AMP_LO1_EN_CH2, /*width*/ 1, /*shift*/ 0);
442         UHD_DEFINE_SOFT_REG_FIELD(SW15_CTRL_CH2, /*width*/ 1, /*shift*/ 1);
443         UHD_DEFINE_SOFT_REG_FIELD(SW14_CTRL_CH2, /*width*/ 1, /*shift*/ 2);
444         UHD_DEFINE_SOFT_REG_FIELD(SW18_CTRL_CH1, /*width*/ 1, /*shift*/ 4);
445 
rf1_reg5_t()446         rf1_reg5_t()
447             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 3, /*reg*/ 5), OPTIMIZED_FLUSH)
448         {
449             set(REGISTER, 0);
450         }
451     } rf1_reg5;
452 
453     class rf1_reg6_t : public uhd::soft_reg32_wo_t
454     {
455     public:
456         UHD_DEFINE_SOFT_REG_FIELD(HB_PRESEL_PGA_EN_CH1, /*width*/ 1, /*shift*/ 0);
457         UHD_DEFINE_SOFT_REG_FIELD(SW17_CTRL_CH2, /*width*/ 1, /*shift*/ 2);
458         UHD_DEFINE_SOFT_REG_FIELD(SW16_CTRL_CH2, /*width*/ 1, /*shift*/ 3);
459         UHD_DEFINE_SOFT_REG_FIELD(PREAMP2_EN_CH2, /*width*/ 1, /*shift*/ 4);
460 
rf1_reg6_t()461         rf1_reg6_t()
462             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 3, /*reg*/ 6), OPTIMIZED_FLUSH)
463         {
464             set(REGISTER, 0);
465         }
466     } rf1_reg6;
467 
468     class rf1_reg7_t : public uhd::soft_reg32_wo_t
469     {
470     public:
471         UHD_DEFINE_SOFT_REG_FIELD(SW22_CTRL_CH2, /*width*/ 1, /*shift*/ 0);
472         UHD_DEFINE_SOFT_REG_FIELD(SW10_CTRL_CH2, /*width*/ 2, /*shift*/ 1);
473         UHD_DEFINE_SOFT_REG_FIELD(SW12_CTRL_CH2, /*width*/ 1, /*shift*/ 3);
474         UHD_DEFINE_SOFT_REG_FIELD(AMP_HB_EN_CH2, /*width*/ 1, /*shift*/ 4);
475 
rf1_reg7_t()476         rf1_reg7_t()
477             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 3, /*reg*/ 7), OPTIMIZED_FLUSH)
478         {
479             set(REGISTER, 0);
480         }
481     } rf1_reg7;
482 
483     //----------------------------------------------
484     // RF CCA: CPLD 4
485     //----------------------------------------------
486     class rf2_reg0_t : public uhd::soft_reg32_wo_t
487     {
488     public:
489         UHD_DEFINE_SOFT_REG_FIELD(ATTEN_LB_CH1, /*width*/ 5, /*shift*/ 0);
490 
rf2_reg0_t()491         rf2_reg0_t()
492             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 4, /*reg*/ 0), OPTIMIZED_FLUSH)
493         {
494             set(REGISTER, 0);
495         }
496     } rf2_reg0;
497 
498     class rf2_reg2_t : public uhd::soft_reg32_wo_t
499     {
500     public:
501         UHD_DEFINE_SOFT_REG_FIELD(SW11_CTRL_CH1, /*width*/ 1, /*shift*/ 0);
502         UHD_DEFINE_SOFT_REG_FIELD(AMP_LB_EN_CH1, /*width*/ 1, /*shift*/ 1);
503         UHD_DEFINE_SOFT_REG_FIELD(SWPA2_CTRL_CH1, /*width*/ 1, /*shift*/ 2);
504 
rf2_reg2_t()505         rf2_reg2_t()
506             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 4, /*reg*/ 2), OPTIMIZED_FLUSH)
507         {
508             set(REGISTER, 0);
509         }
510     } rf2_reg2;
511 
512     class rf2_reg3_t : public uhd::soft_reg32_wo_t
513     {
514     public:
515         UHD_DEFINE_SOFT_REG_FIELD(PREAMP2_EN_CH1, /*width*/ 1, /*shift*/ 0);
516         UHD_DEFINE_SOFT_REG_FIELD(SW18_CTRL_CH2, /*width*/ 1, /*shift*/ 1);
517         UHD_DEFINE_SOFT_REG_FIELD(SW8_CTRL_CH1, /*width*/ 2, /*shift*/ 2);
518 
rf2_reg3_t()519         rf2_reg3_t()
520             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 4, /*reg*/ 3), OPTIMIZED_FLUSH)
521         {
522             set(REGISTER, 0);
523         }
524     } rf2_reg3;
525 
526     class rf2_reg4_t : public uhd::soft_reg32_wo_t
527     {
528     public:
529         UHD_DEFINE_SOFT_REG_FIELD(ATTEN_LB_CH2, /*width*/ 5, /*shift*/ 0);
530 
rf2_reg4_t()531         rf2_reg4_t()
532             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 4, /*reg*/ 4), OPTIMIZED_FLUSH)
533         {
534             set(REGISTER, 0);
535         }
536     } rf2_reg4;
537 
538     class rf2_reg5_t : public uhd::soft_reg32_wo_t
539     {
540     public:
541         UHD_DEFINE_SOFT_REG_FIELD(SWPA2_CTRL_CH2, /*width*/ 1, /*shift*/ 0);
542 
rf2_reg5_t()543         rf2_reg5_t()
544             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 4, /*reg*/ 5), OPTIMIZED_FLUSH)
545         {
546             set(REGISTER, 0);
547         }
548     } rf2_reg5;
549 
550     class rf2_reg6_t : public uhd::soft_reg32_wo_t
551     {
552     public:
553         UHD_DEFINE_SOFT_REG_FIELD(LB_PREAMP_EN_CH2, /*width*/ 1, /*shift*/ 0);
554 
rf2_reg6_t()555         rf2_reg6_t()
556             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 4, /*reg*/ 6), OPTIMIZED_FLUSH)
557         {
558             set(REGISTER, 0);
559         }
560     } rf2_reg6;
561 
562     class rf2_reg7_t : public uhd::soft_reg32_wo_t
563     {
564     public:
565         UHD_DEFINE_SOFT_REG_FIELD(SWPA4_CTRL_CH1, /*width*/ 1, /*shift*/ 0);
566         UHD_DEFINE_SOFT_REG_FIELD(SW8_CTRL_CH2, /*width*/ 2, /*shift*/ 1);
567         UHD_DEFINE_SOFT_REG_FIELD(SW11_CTRL_CH2, /*width*/ 1, /*shift*/ 3);
568         UHD_DEFINE_SOFT_REG_FIELD(AMP_LB_EN_CH2, /*width*/ 1, /*shift*/ 4);
569 
rf2_reg7_t()570         rf2_reg7_t()
571             : uhd::soft_reg32_wo_t(cpld::addr(/*cpld*/ 4, /*reg*/ 7), OPTIMIZED_FLUSH)
572         {
573             set(REGISTER, 0);
574         }
575     } rf2_reg7;
576 
twinrx_cpld_regmap()577     twinrx_cpld_regmap() : soft_regmap_t("twinrx_cpld")
578     {
579         // IF CCA: CPLD 1
580         add_to_map(if0_reg0, "if0_reg0");
581         add_to_map(if0_reg1, "if0_reg1");
582         add_to_map(if0_reg2, "if0_reg2");
583         add_to_map(if0_reg3, "if0_reg3");
584         add_to_map(if0_reg4, "if0_reg4");
585         add_to_map(if0_reg6, "if0_reg6");
586         add_to_map(if0_reg7, "if0_reg7");
587         // RF CCA: CPLD 2
588         add_to_map(rf0_reg0, "rf0_reg0");
589         add_to_map(rf0_reg1, "rf0_reg1");
590         add_to_map(rf0_reg2, "rf0_reg2");
591         add_to_map(rf0_reg3, "rf0_reg3");
592         add_to_map(rf0_reg4, "rf0_reg4");
593         add_to_map(rf0_reg5, "rf0_reg5");
594         add_to_map(rf0_reg6, "rf0_reg6");
595         add_to_map(rf0_reg7, "rf0_reg7");
596         // RF CCA: CPLD 3
597         add_to_map(rf1_reg0, "rf1_reg0");
598         add_to_map(rf1_reg1, "rf1_reg1");
599         add_to_map(rf1_reg2, "rf1_reg2");
600         add_to_map(rf1_reg3, "rf1_reg3");
601         add_to_map(rf1_reg4, "rf1_reg4");
602         add_to_map(rf1_reg5, "rf1_reg5");
603         add_to_map(rf1_reg6, "rf1_reg6");
604         add_to_map(rf1_reg7, "rf1_reg7");
605         // RF CCA: CPLD 4
606         add_to_map(rf2_reg0, "rf2_reg0");
607         add_to_map(rf2_reg2, "rf2_reg2");
608         add_to_map(rf2_reg3, "rf2_reg3");
609         add_to_map(rf2_reg4, "rf2_reg4");
610         add_to_map(rf2_reg5, "rf2_reg5");
611         add_to_map(rf2_reg6, "rf2_reg6");
612         add_to_map(rf2_reg7, "rf2_reg7");
613     }
614 };
615 
616 }}}} // namespace uhd::usrp::dboard::twinrx
617 
618 #endif /* INCLUDED_DBOARD_TWINRX_IO_HPP */
619