2 * QEMU model of the Xilinx ZynqMP CAN controller.
3 * This implementation is based on the following datasheet:
4 * https://www.xilinx.com/support/documentation/user_guides/ug1085-zynq-ultrascale-trm.pdf
6 * Copyright (c) 2020 Xilinx Inc.
8 * Written-by: Vikram Garhwal<fnu.vikram@xilinx.com>
10 * Based on QEMU CAN Device emulation implemented by Jin Yang, Deniz Eren and
13 * Permission is hereby granted, free of charge, to any person obtaining a copy
14 * of this software and associated documentation files (the "Software"), to deal
15 * in the Software without restriction, including without limitation the rights
16 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
17 * copies of the Software, and to permit persons to whom the Software is
18 * furnished to do so, subject to the following conditions:
20 * The above copyright notice and this permission notice shall be included in
21 * all copies or substantial portions of the Software.
23 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
24 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
25 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
26 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
27 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
28 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
32 #include "qemu/osdep.h"
33 #include "hw/sysbus.h"
34 #include "hw/register.h"
36 #include "qapi/error.h"
37 #include "qemu/bitops.h"
39 #include "qemu/cutils.h"
40 #include "migration/vmstate.h"
41 #include "hw/qdev-properties.h"
42 #include "net/can_emu.h"
43 #include "net/can_host.h"
44 #include "qemu/event_notifier.h"
45 #include "qom/object_interfaces.h"
46 #include "hw/net/xlnx-zynqmp-can.h"
49 #ifndef XLNX_ZYNQMP_CAN_ERR_DEBUG
50 #define XLNX_ZYNQMP_CAN_ERR_DEBUG 0
56 REG32(SOFTWARE_RESET_REGISTER
, 0x0)
57 FIELD(SOFTWARE_RESET_REGISTER
, CEN
, 1, 1)
58 FIELD(SOFTWARE_RESET_REGISTER
, SRST
, 0, 1)
59 REG32(MODE_SELECT_REGISTER
, 0x4)
60 FIELD(MODE_SELECT_REGISTER
, SNOOP
, 2, 1)
61 FIELD(MODE_SELECT_REGISTER
, LBACK
, 1, 1)
62 FIELD(MODE_SELECT_REGISTER
, SLEEP
, 0, 1)
63 REG32(ARBITRATION_PHASE_BAUD_RATE_PRESCALER_REGISTER
, 0x8)
64 FIELD(ARBITRATION_PHASE_BAUD_RATE_PRESCALER_REGISTER
, BRP
, 0, 8)
65 REG32(ARBITRATION_PHASE_BIT_TIMING_REGISTER
, 0xc)
66 FIELD(ARBITRATION_PHASE_BIT_TIMING_REGISTER
, SJW
, 7, 2)
67 FIELD(ARBITRATION_PHASE_BIT_TIMING_REGISTER
, TS2
, 4, 3)
68 FIELD(ARBITRATION_PHASE_BIT_TIMING_REGISTER
, TS1
, 0, 4)
69 REG32(ERROR_COUNTER_REGISTER
, 0x10)
70 FIELD(ERROR_COUNTER_REGISTER
, REC
, 8, 8)
71 FIELD(ERROR_COUNTER_REGISTER
, TEC
, 0, 8)
72 REG32(ERROR_STATUS_REGISTER
, 0x14)
73 FIELD(ERROR_STATUS_REGISTER
, ACKER
, 4, 1)
74 FIELD(ERROR_STATUS_REGISTER
, BERR
, 3, 1)
75 FIELD(ERROR_STATUS_REGISTER
, STER
, 2, 1)
76 FIELD(ERROR_STATUS_REGISTER
, FMER
, 1, 1)
77 FIELD(ERROR_STATUS_REGISTER
, CRCER
, 0, 1)
78 REG32(STATUS_REGISTER
, 0x18)
79 FIELD(STATUS_REGISTER
, SNOOP
, 12, 1)
80 FIELD(STATUS_REGISTER
, ACFBSY
, 11, 1)
81 FIELD(STATUS_REGISTER
, TXFLL
, 10, 1)
82 FIELD(STATUS_REGISTER
, TXBFLL
, 9, 1)
83 FIELD(STATUS_REGISTER
, ESTAT
, 7, 2)
84 FIELD(STATUS_REGISTER
, ERRWRN
, 6, 1)
85 FIELD(STATUS_REGISTER
, BBSY
, 5, 1)
86 FIELD(STATUS_REGISTER
, BIDLE
, 4, 1)
87 FIELD(STATUS_REGISTER
, NORMAL
, 3, 1)
88 FIELD(STATUS_REGISTER
, SLEEP
, 2, 1)
89 FIELD(STATUS_REGISTER
, LBACK
, 1, 1)
90 FIELD(STATUS_REGISTER
, CONFIG
, 0, 1)
91 REG32(INTERRUPT_STATUS_REGISTER
, 0x1c)
92 FIELD(INTERRUPT_STATUS_REGISTER
, TXFEMP
, 14, 1)
93 FIELD(INTERRUPT_STATUS_REGISTER
, TXFWMEMP
, 13, 1)
94 FIELD(INTERRUPT_STATUS_REGISTER
, RXFWMFLL
, 12, 1)
95 FIELD(INTERRUPT_STATUS_REGISTER
, WKUP
, 11, 1)
96 FIELD(INTERRUPT_STATUS_REGISTER
, SLP
, 10, 1)
97 FIELD(INTERRUPT_STATUS_REGISTER
, BSOFF
, 9, 1)
98 FIELD(INTERRUPT_STATUS_REGISTER
, ERROR
, 8, 1)
99 FIELD(INTERRUPT_STATUS_REGISTER
, RXNEMP
, 7, 1)
100 FIELD(INTERRUPT_STATUS_REGISTER
, RXOFLW
, 6, 1)
101 FIELD(INTERRUPT_STATUS_REGISTER
, RXUFLW
, 5, 1)
102 FIELD(INTERRUPT_STATUS_REGISTER
, RXOK
, 4, 1)
103 FIELD(INTERRUPT_STATUS_REGISTER
, TXBFLL
, 3, 1)
104 FIELD(INTERRUPT_STATUS_REGISTER
, TXFLL
, 2, 1)
105 FIELD(INTERRUPT_STATUS_REGISTER
, TXOK
, 1, 1)
106 FIELD(INTERRUPT_STATUS_REGISTER
, ARBLST
, 0, 1)
107 REG32(INTERRUPT_ENABLE_REGISTER
, 0x20)
108 FIELD(INTERRUPT_ENABLE_REGISTER
, ETXFEMP
, 14, 1)
109 FIELD(INTERRUPT_ENABLE_REGISTER
, ETXFWMEMP
, 13, 1)
110 FIELD(INTERRUPT_ENABLE_REGISTER
, ERXFWMFLL
, 12, 1)
111 FIELD(INTERRUPT_ENABLE_REGISTER
, EWKUP
, 11, 1)
112 FIELD(INTERRUPT_ENABLE_REGISTER
, ESLP
, 10, 1)
113 FIELD(INTERRUPT_ENABLE_REGISTER
, EBSOFF
, 9, 1)
114 FIELD(INTERRUPT_ENABLE_REGISTER
, EERROR
, 8, 1)
115 FIELD(INTERRUPT_ENABLE_REGISTER
, ERXNEMP
, 7, 1)
116 FIELD(INTERRUPT_ENABLE_REGISTER
, ERXOFLW
, 6, 1)
117 FIELD(INTERRUPT_ENABLE_REGISTER
, ERXUFLW
, 5, 1)
118 FIELD(INTERRUPT_ENABLE_REGISTER
, ERXOK
, 4, 1)
119 FIELD(INTERRUPT_ENABLE_REGISTER
, ETXBFLL
, 3, 1)
120 FIELD(INTERRUPT_ENABLE_REGISTER
, ETXFLL
, 2, 1)
121 FIELD(INTERRUPT_ENABLE_REGISTER
, ETXOK
, 1, 1)
122 FIELD(INTERRUPT_ENABLE_REGISTER
, EARBLST
, 0, 1)
123 REG32(INTERRUPT_CLEAR_REGISTER
, 0x24)
124 FIELD(INTERRUPT_CLEAR_REGISTER
, CTXFEMP
, 14, 1)
125 FIELD(INTERRUPT_CLEAR_REGISTER
, CTXFWMEMP
, 13, 1)
126 FIELD(INTERRUPT_CLEAR_REGISTER
, CRXFWMFLL
, 12, 1)
127 FIELD(INTERRUPT_CLEAR_REGISTER
, CWKUP
, 11, 1)
128 FIELD(INTERRUPT_CLEAR_REGISTER
, CSLP
, 10, 1)
129 FIELD(INTERRUPT_CLEAR_REGISTER
, CBSOFF
, 9, 1)
130 FIELD(INTERRUPT_CLEAR_REGISTER
, CERROR
, 8, 1)
131 FIELD(INTERRUPT_CLEAR_REGISTER
, CRXNEMP
, 7, 1)
132 FIELD(INTERRUPT_CLEAR_REGISTER
, CRXOFLW
, 6, 1)
133 FIELD(INTERRUPT_CLEAR_REGISTER
, CRXUFLW
, 5, 1)
134 FIELD(INTERRUPT_CLEAR_REGISTER
, CRXOK
, 4, 1)
135 FIELD(INTERRUPT_CLEAR_REGISTER
, CTXBFLL
, 3, 1)
136 FIELD(INTERRUPT_CLEAR_REGISTER
, CTXFLL
, 2, 1)
137 FIELD(INTERRUPT_CLEAR_REGISTER
, CTXOK
, 1, 1)
138 FIELD(INTERRUPT_CLEAR_REGISTER
, CARBLST
, 0, 1)
139 REG32(TIMESTAMP_REGISTER
, 0x28)
140 FIELD(TIMESTAMP_REGISTER
, CTS
, 0, 1)
144 REG32(TXFIFO_ID
, 0x30)
145 FIELD(TXFIFO_ID
, IDH
, 21, 11)
146 FIELD(TXFIFO_ID
, SRRRTR
, 20, 1)
147 FIELD(TXFIFO_ID
, IDE
, 19, 1)
148 FIELD(TXFIFO_ID
, IDL
, 1, 18)
149 FIELD(TXFIFO_ID
, RTR
, 0, 1)
150 REG32(TXFIFO_DLC
, 0x34)
151 FIELD(TXFIFO_DLC
, DLC
, 28, 4)
152 REG32(TXFIFO_DATA1
, 0x38)
153 FIELD(TXFIFO_DATA1
, DB0
, 24, 8)
154 FIELD(TXFIFO_DATA1
, DB1
, 16, 8)
155 FIELD(TXFIFO_DATA1
, DB2
, 8, 8)
156 FIELD(TXFIFO_DATA1
, DB3
, 0, 8)
157 REG32(TXFIFO_DATA2
, 0x3c)
158 FIELD(TXFIFO_DATA2
, DB4
, 24, 8)
159 FIELD(TXFIFO_DATA2
, DB5
, 16, 8)
160 FIELD(TXFIFO_DATA2
, DB6
, 8, 8)
161 FIELD(TXFIFO_DATA2
, DB7
, 0, 8)
162 REG32(TXHPB_ID
, 0x40)
163 FIELD(TXHPB_ID
, IDH
, 21, 11)
164 FIELD(TXHPB_ID
, SRRRTR
, 20, 1)
165 FIELD(TXHPB_ID
, IDE
, 19, 1)
166 FIELD(TXHPB_ID
, IDL
, 1, 18)
167 FIELD(TXHPB_ID
, RTR
, 0, 1)
168 REG32(TXHPB_DLC
, 0x44)
169 FIELD(TXHPB_DLC
, DLC
, 28, 4)
170 REG32(TXHPB_DATA1
, 0x48)
171 FIELD(TXHPB_DATA1
, DB0
, 24, 8)
172 FIELD(TXHPB_DATA1
, DB1
, 16, 8)
173 FIELD(TXHPB_DATA1
, DB2
, 8, 8)
174 FIELD(TXHPB_DATA1
, DB3
, 0, 8)
175 REG32(TXHPB_DATA2
, 0x4c)
176 FIELD(TXHPB_DATA2
, DB4
, 24, 8)
177 FIELD(TXHPB_DATA2
, DB5
, 16, 8)
178 FIELD(TXHPB_DATA2
, DB6
, 8, 8)
179 FIELD(TXHPB_DATA2
, DB7
, 0, 8)
180 REG32(RXFIFO_ID
, 0x50)
181 FIELD(RXFIFO_ID
, IDH
, 21, 11)
182 FIELD(RXFIFO_ID
, SRRRTR
, 20, 1)
183 FIELD(RXFIFO_ID
, IDE
, 19, 1)
184 FIELD(RXFIFO_ID
, IDL
, 1, 18)
185 FIELD(RXFIFO_ID
, RTR
, 0, 1)
186 REG32(RXFIFO_DLC
, 0x54)
187 FIELD(RXFIFO_DLC
, DLC
, 28, 4)
188 FIELD(RXFIFO_DLC
, RXT
, 0, 16)
189 REG32(RXFIFO_DATA1
, 0x58)
190 FIELD(RXFIFO_DATA1
, DB0
, 24, 8)
191 FIELD(RXFIFO_DATA1
, DB1
, 16, 8)
192 FIELD(RXFIFO_DATA1
, DB2
, 8, 8)
193 FIELD(RXFIFO_DATA1
, DB3
, 0, 8)
194 REG32(RXFIFO_DATA2
, 0x5c)
195 FIELD(RXFIFO_DATA2
, DB4
, 24, 8)
196 FIELD(RXFIFO_DATA2
, DB5
, 16, 8)
197 FIELD(RXFIFO_DATA2
, DB6
, 8, 8)
198 FIELD(RXFIFO_DATA2
, DB7
, 0, 8)
200 FIELD(AFR
, UAF4
, 3, 1)
201 FIELD(AFR
, UAF3
, 2, 1)
202 FIELD(AFR
, UAF2
, 1, 1)
203 FIELD(AFR
, UAF1
, 0, 1)
205 FIELD(AFMR1
, AMIDH
, 21, 11)
206 FIELD(AFMR1
, AMSRR
, 20, 1)
207 FIELD(AFMR1
, AMIDE
, 19, 1)
208 FIELD(AFMR1
, AMIDL
, 1, 18)
209 FIELD(AFMR1
, AMRTR
, 0, 1)
211 FIELD(AFIR1
, AIIDH
, 21, 11)
212 FIELD(AFIR1
, AISRR
, 20, 1)
213 FIELD(AFIR1
, AIIDE
, 19, 1)
214 FIELD(AFIR1
, AIIDL
, 1, 18)
215 FIELD(AFIR1
, AIRTR
, 0, 1)
217 FIELD(AFMR2
, AMIDH
, 21, 11)
218 FIELD(AFMR2
, AMSRR
, 20, 1)
219 FIELD(AFMR2
, AMIDE
, 19, 1)
220 FIELD(AFMR2
, AMIDL
, 1, 18)
221 FIELD(AFMR2
, AMRTR
, 0, 1)
223 FIELD(AFIR2
, AIIDH
, 21, 11)
224 FIELD(AFIR2
, AISRR
, 20, 1)
225 FIELD(AFIR2
, AIIDE
, 19, 1)
226 FIELD(AFIR2
, AIIDL
, 1, 18)
227 FIELD(AFIR2
, AIRTR
, 0, 1)
229 FIELD(AFMR3
, AMIDH
, 21, 11)
230 FIELD(AFMR3
, AMSRR
, 20, 1)
231 FIELD(AFMR3
, AMIDE
, 19, 1)
232 FIELD(AFMR3
, AMIDL
, 1, 18)
233 FIELD(AFMR3
, AMRTR
, 0, 1)
235 FIELD(AFIR3
, AIIDH
, 21, 11)
236 FIELD(AFIR3
, AISRR
, 20, 1)
237 FIELD(AFIR3
, AIIDE
, 19, 1)
238 FIELD(AFIR3
, AIIDL
, 1, 18)
239 FIELD(AFIR3
, AIRTR
, 0, 1)
241 FIELD(AFMR4
, AMIDH
, 21, 11)
242 FIELD(AFMR4
, AMSRR
, 20, 1)
243 FIELD(AFMR4
, AMIDE
, 19, 1)
244 FIELD(AFMR4
, AMIDL
, 1, 18)
245 FIELD(AFMR4
, AMRTR
, 0, 1)
247 FIELD(AFIR4
, AIIDH
, 21, 11)
248 FIELD(AFIR4
, AISRR
, 20, 1)
249 FIELD(AFIR4
, AIIDE
, 19, 1)
250 FIELD(AFIR4
, AIIDL
, 1, 18)
251 FIELD(AFIR4
, AIRTR
, 0, 1)
253 static void can_update_irq(XlnxZynqMPCANState
*s
)
257 /* Watermark register interrupts. */
258 if ((fifo32_num_free(&s
->tx_fifo
) / CAN_FRAME_SIZE
) >
259 ARRAY_FIELD_EX32(s
->regs
, WIR
, EW
)) {
260 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, TXFWMEMP
, 1);
263 if ((fifo32_num_used(&s
->rx_fifo
) / CAN_FRAME_SIZE
) >
264 ARRAY_FIELD_EX32(s
->regs
, WIR
, FW
)) {
265 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, RXFWMFLL
, 1);
269 if (fifo32_num_used(&s
->rx_fifo
) >= CAN_FRAME_SIZE
) {
270 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, RXNEMP
, 1);
274 if (fifo32_is_empty(&s
->tx_fifo
)) {
275 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, TXFEMP
, 1);
278 if (fifo32_is_full(&s
->tx_fifo
)) {
279 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, TXFLL
, 1);
282 if (fifo32_is_full(&s
->txhpb_fifo
)) {
283 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, TXBFLL
, 1);
286 irq
= s
->regs
[R_INTERRUPT_STATUS_REGISTER
];
287 irq
&= s
->regs
[R_INTERRUPT_ENABLE_REGISTER
];
289 trace_xlnx_can_update_irq(s
->regs
[R_INTERRUPT_STATUS_REGISTER
],
290 s
->regs
[R_INTERRUPT_ENABLE_REGISTER
], irq
);
291 qemu_set_irq(s
->irq
, irq
);
294 static void can_ier_post_write(RegisterInfo
*reg
, uint64_t val
)
296 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(reg
->opaque
);
301 static uint64_t can_icr_pre_write(RegisterInfo
*reg
, uint64_t val
)
303 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(reg
->opaque
);
305 s
->regs
[R_INTERRUPT_STATUS_REGISTER
] &= ~val
;
311 static void can_config_reset(XlnxZynqMPCANState
*s
)
313 /* Reset all the configuration registers. */
314 register_reset(&s
->reg_info
[R_SOFTWARE_RESET_REGISTER
]);
315 register_reset(&s
->reg_info
[R_MODE_SELECT_REGISTER
]);
317 &s
->reg_info
[R_ARBITRATION_PHASE_BAUD_RATE_PRESCALER_REGISTER
]);
318 register_reset(&s
->reg_info
[R_ARBITRATION_PHASE_BIT_TIMING_REGISTER
]);
319 register_reset(&s
->reg_info
[R_STATUS_REGISTER
]);
320 register_reset(&s
->reg_info
[R_INTERRUPT_STATUS_REGISTER
]);
321 register_reset(&s
->reg_info
[R_INTERRUPT_ENABLE_REGISTER
]);
322 register_reset(&s
->reg_info
[R_INTERRUPT_CLEAR_REGISTER
]);
323 register_reset(&s
->reg_info
[R_WIR
]);
326 static void can_config_mode(XlnxZynqMPCANState
*s
)
328 register_reset(&s
->reg_info
[R_ERROR_COUNTER_REGISTER
]);
329 register_reset(&s
->reg_info
[R_ERROR_STATUS_REGISTER
]);
331 /* Put XlnxZynqMPCAN in configuration mode. */
332 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, CONFIG
, 1);
333 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, WKUP
, 0);
334 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, SLP
, 0);
335 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, BSOFF
, 0);
336 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, ERROR
, 0);
337 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, RXOFLW
, 0);
338 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, RXOK
, 0);
339 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, TXOK
, 0);
340 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, ARBLST
, 0);
345 static void update_status_register_mode_bits(XlnxZynqMPCANState
*s
)
347 bool sleep_status
= ARRAY_FIELD_EX32(s
->regs
, STATUS_REGISTER
, SLEEP
);
348 bool sleep_mode
= ARRAY_FIELD_EX32(s
->regs
, MODE_SELECT_REGISTER
, SLEEP
);
349 /* Wake up interrupt bit. */
350 bool wakeup_irq_val
= sleep_status
&& (sleep_mode
== 0);
351 /* Sleep interrupt bit. */
352 bool sleep_irq_val
= sleep_mode
&& (sleep_status
== 0);
354 /* Clear previous core mode status bits. */
355 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, LBACK
, 0);
356 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, SLEEP
, 0);
357 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, SNOOP
, 0);
358 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, NORMAL
, 0);
360 /* set current mode bit and generate irqs accordingly. */
361 if (ARRAY_FIELD_EX32(s
->regs
, MODE_SELECT_REGISTER
, LBACK
)) {
362 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, LBACK
, 1);
363 } else if (ARRAY_FIELD_EX32(s
->regs
, MODE_SELECT_REGISTER
, SLEEP
)) {
364 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, SLEEP
, 1);
365 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, SLP
,
367 } else if (ARRAY_FIELD_EX32(s
->regs
, MODE_SELECT_REGISTER
, SNOOP
)) {
368 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, SNOOP
, 1);
371 * If all bits are zero then XlnxZynqMPCAN is set in normal mode.
373 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, NORMAL
, 1);
374 /* Set wakeup interrupt bit. */
375 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, WKUP
,
382 static void can_exit_sleep_mode(XlnxZynqMPCANState
*s
)
384 ARRAY_FIELD_DP32(s
->regs
, MODE_SELECT_REGISTER
, SLEEP
, 0);
385 update_status_register_mode_bits(s
);
388 static void generate_frame(qemu_can_frame
*frame
, uint32_t *data
)
390 frame
->can_id
= data
[0];
391 frame
->can_dlc
= FIELD_EX32(data
[1], TXFIFO_DLC
, DLC
);
393 frame
->data
[0] = FIELD_EX32(data
[2], TXFIFO_DATA1
, DB3
);
394 frame
->data
[1] = FIELD_EX32(data
[2], TXFIFO_DATA1
, DB2
);
395 frame
->data
[2] = FIELD_EX32(data
[2], TXFIFO_DATA1
, DB1
);
396 frame
->data
[3] = FIELD_EX32(data
[2], TXFIFO_DATA1
, DB0
);
398 frame
->data
[4] = FIELD_EX32(data
[3], TXFIFO_DATA2
, DB7
);
399 frame
->data
[5] = FIELD_EX32(data
[3], TXFIFO_DATA2
, DB6
);
400 frame
->data
[6] = FIELD_EX32(data
[3], TXFIFO_DATA2
, DB5
);
401 frame
->data
[7] = FIELD_EX32(data
[3], TXFIFO_DATA2
, DB4
);
404 static bool tx_ready_check(XlnxZynqMPCANState
*s
)
406 if (ARRAY_FIELD_EX32(s
->regs
, SOFTWARE_RESET_REGISTER
, SRST
)) {
407 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
409 qemu_log_mask(LOG_GUEST_ERROR
, "%s: Attempting to transfer data while"
410 " data while controller is in reset mode.\n",
415 if (ARRAY_FIELD_EX32(s
->regs
, SOFTWARE_RESET_REGISTER
, CEN
) == 0) {
416 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
418 qemu_log_mask(LOG_GUEST_ERROR
, "%s: Attempting to transfer"
419 " data while controller is in configuration mode. Reset"
420 " the core so operations can start fresh.\n",
425 if (ARRAY_FIELD_EX32(s
->regs
, STATUS_REGISTER
, SNOOP
)) {
426 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
428 qemu_log_mask(LOG_GUEST_ERROR
, "%s: Attempting to transfer"
429 " data while controller is in SNOOP MODE.\n",
437 static void read_tx_frame(XlnxZynqMPCANState
*s
, Fifo32
*fifo
, uint32_t *data
)
439 unsigned used
= fifo32_num_used(fifo
);
440 bool is_txhpb
= fifo
== &s
->txhpb_fifo
;
443 used
%= CAN_FRAME_SIZE
;
446 * Frame Message Format
448 * Each frame includes four words (16 bytes). Software must read and write
449 * all four words regardless of the actual number of data bytes and valid
450 * fields in the message.
451 * If software misbehave (not writing all four words), we use the previous
452 * registers content to initialize each missing word.
454 * If used is 1 then ID, DLC and DATA1 are missing.
455 * if used is 2 then ID and DLC are missing.
456 * if used is 3 then only ID is missing.
459 data
[0] = s
->regs
[is_txhpb
? R_TXHPB_ID
: R_TXFIFO_ID
];
461 data
[0] = fifo32_pop(fifo
);
463 if (used
== 1 || used
== 2) {
464 data
[1] = s
->regs
[is_txhpb
? R_TXHPB_DLC
: R_TXFIFO_DLC
];
466 data
[1] = fifo32_pop(fifo
);
469 data
[2] = s
->regs
[is_txhpb
? R_TXHPB_DATA1
: R_TXFIFO_DATA1
];
471 data
[2] = fifo32_pop(fifo
);
473 /* DATA2 triggered the transfer thus is always available */
474 data
[3] = fifo32_pop(fifo
);
477 qemu_log_mask(LOG_GUEST_ERROR
,
478 "%s: Incomplete CAN frame (only %u/%u slots used)\n",
479 TYPE_XLNX_ZYNQMP_CAN
, used
, CAN_FRAME_SIZE
);
483 static void transfer_fifo(XlnxZynqMPCANState
*s
, Fifo32
*fifo
)
485 qemu_can_frame frame
;
486 uint32_t data
[CAN_FRAME_SIZE
];
488 bool can_tx
= tx_ready_check(s
);
491 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
493 qemu_log_mask(LOG_GUEST_ERROR
, "%s: Controller is not enabled for data"
494 " transfer.\n", path
);
499 while (!fifo32_is_empty(fifo
)) {
500 read_tx_frame(s
, fifo
, data
);
502 if (ARRAY_FIELD_EX32(s
->regs
, STATUS_REGISTER
, LBACK
)) {
504 * Controller is in loopback. In Loopback mode, the CAN core
505 * transmits a recessive bitstream on to the XlnxZynqMPCAN Bus.
506 * Any message transmitted is looped back to the RX line and
507 * acknowledged. The XlnxZynqMPCAN core receives any message
510 if (fifo32_is_full(&s
->rx_fifo
)) {
511 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, RXOFLW
, 1);
513 for (i
= 0; i
< CAN_FRAME_SIZE
; i
++) {
514 fifo32_push(&s
->rx_fifo
, data
[i
]);
517 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, RXOK
, 1);
520 /* Normal mode Tx. */
521 generate_frame(&frame
, data
);
523 trace_xlnx_can_tx_data(frame
.can_id
, frame
.can_dlc
,
524 frame
.data
[0], frame
.data
[1],
525 frame
.data
[2], frame
.data
[3],
526 frame
.data
[4], frame
.data
[5],
527 frame
.data
[6], frame
.data
[7]);
528 can_bus_client_send(&s
->bus_client
, &frame
, 1);
532 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, TXOK
, 1);
533 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, TXBFLL
, 0);
535 if (ARRAY_FIELD_EX32(s
->regs
, STATUS_REGISTER
, SLEEP
)) {
536 can_exit_sleep_mode(s
);
542 static uint64_t can_srr_pre_write(RegisterInfo
*reg
, uint64_t val
)
544 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(reg
->opaque
);
546 ARRAY_FIELD_DP32(s
->regs
, SOFTWARE_RESET_REGISTER
, CEN
,
547 FIELD_EX32(val
, SOFTWARE_RESET_REGISTER
, CEN
));
549 if (FIELD_EX32(val
, SOFTWARE_RESET_REGISTER
, SRST
)) {
550 trace_xlnx_can_reset(val
);
552 /* First, core will do software reset then will enter in config mode. */
556 if (ARRAY_FIELD_EX32(s
->regs
, SOFTWARE_RESET_REGISTER
, CEN
) == 0) {
560 * Leave config mode. Now XlnxZynqMPCAN core will enter normal,
561 * sleep, snoop or loopback mode depending upon LBACK, SLEEP, SNOOP
564 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, CONFIG
, 0);
566 ptimer_transaction_begin(s
->can_timer
);
567 ptimer_set_count(s
->can_timer
, 0);
568 ptimer_transaction_commit(s
->can_timer
);
570 /* XlnxZynqMPCAN is out of config mode. It will send pending data. */
571 transfer_fifo(s
, &s
->txhpb_fifo
);
572 transfer_fifo(s
, &s
->tx_fifo
);
575 update_status_register_mode_bits(s
);
577 return s
->regs
[R_SOFTWARE_RESET_REGISTER
];
580 static uint64_t can_msr_pre_write(RegisterInfo
*reg
, uint64_t val
)
582 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(reg
->opaque
);
586 * Multiple mode set check. This is done to make sure user doesn't set
589 multi_mode
= FIELD_EX32(val
, MODE_SELECT_REGISTER
, LBACK
) +
590 FIELD_EX32(val
, MODE_SELECT_REGISTER
, SLEEP
) +
591 FIELD_EX32(val
, MODE_SELECT_REGISTER
, SNOOP
);
593 if (multi_mode
> 1) {
594 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
596 qemu_log_mask(LOG_GUEST_ERROR
, "%s: Attempting to config"
597 " several modes simultaneously. One mode will be selected"
598 " according to their priority: LBACK > SLEEP > SNOOP.\n",
602 if (ARRAY_FIELD_EX32(s
->regs
, SOFTWARE_RESET_REGISTER
, CEN
) == 0) {
603 /* We are in configuration mode, any mode can be selected. */
604 s
->regs
[R_MODE_SELECT_REGISTER
] = val
;
606 bool sleep_mode_bit
= FIELD_EX32(val
, MODE_SELECT_REGISTER
, SLEEP
);
608 ARRAY_FIELD_DP32(s
->regs
, MODE_SELECT_REGISTER
, SLEEP
, sleep_mode_bit
);
610 if (FIELD_EX32(val
, MODE_SELECT_REGISTER
, LBACK
)) {
611 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
613 qemu_log_mask(LOG_GUEST_ERROR
, "%s: Attempting to set"
614 " LBACK mode without setting CEN bit as 0.\n",
616 } else if (FIELD_EX32(val
, MODE_SELECT_REGISTER
, SNOOP
)) {
617 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
619 qemu_log_mask(LOG_GUEST_ERROR
, "%s: Attempting to set"
620 " SNOOP mode without setting CEN bit as 0.\n",
624 update_status_register_mode_bits(s
);
627 return s
->regs
[R_MODE_SELECT_REGISTER
];
630 static uint64_t can_brpr_pre_write(RegisterInfo
*reg
, uint64_t val
)
632 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(reg
->opaque
);
634 /* Only allow writes when in config mode. */
635 if (ARRAY_FIELD_EX32(s
->regs
, SOFTWARE_RESET_REGISTER
, CEN
)) {
636 return s
->regs
[R_ARBITRATION_PHASE_BAUD_RATE_PRESCALER_REGISTER
];
642 static uint64_t can_btr_pre_write(RegisterInfo
*reg
, uint64_t val
)
644 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(reg
->opaque
);
646 /* Only allow writes when in config mode. */
647 if (ARRAY_FIELD_EX32(s
->regs
, SOFTWARE_RESET_REGISTER
, CEN
)) {
648 return s
->regs
[R_ARBITRATION_PHASE_BIT_TIMING_REGISTER
];
654 static uint64_t can_tcr_pre_write(RegisterInfo
*reg
, uint64_t val
)
656 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(reg
->opaque
);
658 if (FIELD_EX32(val
, TIMESTAMP_REGISTER
, CTS
)) {
659 ptimer_transaction_begin(s
->can_timer
);
660 ptimer_set_count(s
->can_timer
, 0);
661 ptimer_transaction_commit(s
->can_timer
);
667 static void update_rx_fifo(XlnxZynqMPCANState
*s
, const qemu_can_frame
*frame
)
669 bool filter_pass
= false;
670 uint16_t timestamp
= 0;
672 /* If no filter is enabled. Message will be stored in FIFO. */
673 if (!((ARRAY_FIELD_EX32(s
->regs
, AFR
, UAF1
)) |
674 (ARRAY_FIELD_EX32(s
->regs
, AFR
, UAF2
)) |
675 (ARRAY_FIELD_EX32(s
->regs
, AFR
, UAF3
)) |
676 (ARRAY_FIELD_EX32(s
->regs
, AFR
, UAF4
)))) {
681 * Messages that pass any of the acceptance filters will be stored in
684 if (ARRAY_FIELD_EX32(s
->regs
, AFR
, UAF1
)) {
685 uint32_t id_masked
= s
->regs
[R_AFMR1
] & frame
->can_id
;
686 uint32_t filter_id_masked
= s
->regs
[R_AFMR1
] & s
->regs
[R_AFIR1
];
688 if (filter_id_masked
== id_masked
) {
693 if (ARRAY_FIELD_EX32(s
->regs
, AFR
, UAF2
)) {
694 uint32_t id_masked
= s
->regs
[R_AFMR2
] & frame
->can_id
;
695 uint32_t filter_id_masked
= s
->regs
[R_AFMR2
] & s
->regs
[R_AFIR2
];
697 if (filter_id_masked
== id_masked
) {
702 if (ARRAY_FIELD_EX32(s
->regs
, AFR
, UAF3
)) {
703 uint32_t id_masked
= s
->regs
[R_AFMR3
] & frame
->can_id
;
704 uint32_t filter_id_masked
= s
->regs
[R_AFMR3
] & s
->regs
[R_AFIR3
];
706 if (filter_id_masked
== id_masked
) {
711 if (ARRAY_FIELD_EX32(s
->regs
, AFR
, UAF4
)) {
712 uint32_t id_masked
= s
->regs
[R_AFMR4
] & frame
->can_id
;
713 uint32_t filter_id_masked
= s
->regs
[R_AFMR4
] & s
->regs
[R_AFIR4
];
715 if (filter_id_masked
== id_masked
) {
721 trace_xlnx_can_rx_fifo_filter_reject(frame
->can_id
, frame
->can_dlc
);
725 /* Store the message in fifo if it passed through any of the filters. */
726 if (filter_pass
&& frame
->can_dlc
<= MAX_DLC
) {
728 if (fifo32_is_full(&s
->rx_fifo
)) {
729 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, RXOFLW
, 1);
731 timestamp
= CAN_TIMER_MAX
- ptimer_get_count(s
->can_timer
);
733 fifo32_push(&s
->rx_fifo
, frame
->can_id
);
735 fifo32_push(&s
->rx_fifo
, deposit32(0, R_RXFIFO_DLC_DLC_SHIFT
,
736 R_RXFIFO_DLC_DLC_LENGTH
,
738 deposit32(0, R_RXFIFO_DLC_RXT_SHIFT
,
739 R_RXFIFO_DLC_RXT_LENGTH
,
742 /* First 32 bit of the data. */
743 fifo32_push(&s
->rx_fifo
, deposit32(0, R_RXFIFO_DATA1_DB3_SHIFT
,
744 R_RXFIFO_DATA1_DB3_LENGTH
,
746 deposit32(0, R_RXFIFO_DATA1_DB2_SHIFT
,
747 R_RXFIFO_DATA1_DB2_LENGTH
,
749 deposit32(0, R_RXFIFO_DATA1_DB1_SHIFT
,
750 R_RXFIFO_DATA1_DB1_LENGTH
,
752 deposit32(0, R_RXFIFO_DATA1_DB0_SHIFT
,
753 R_RXFIFO_DATA1_DB0_LENGTH
,
755 /* Last 32 bit of the data. */
756 fifo32_push(&s
->rx_fifo
, deposit32(0, R_RXFIFO_DATA2_DB7_SHIFT
,
757 R_RXFIFO_DATA2_DB7_LENGTH
,
759 deposit32(0, R_RXFIFO_DATA2_DB6_SHIFT
,
760 R_RXFIFO_DATA2_DB6_LENGTH
,
762 deposit32(0, R_RXFIFO_DATA2_DB5_SHIFT
,
763 R_RXFIFO_DATA2_DB5_LENGTH
,
765 deposit32(0, R_RXFIFO_DATA2_DB4_SHIFT
,
766 R_RXFIFO_DATA2_DB4_LENGTH
,
769 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, RXOK
, 1);
770 trace_xlnx_can_rx_data(frame
->can_id
, frame
->can_dlc
,
771 frame
->data
[0], frame
->data
[1],
772 frame
->data
[2], frame
->data
[3],
773 frame
->data
[4], frame
->data
[5],
774 frame
->data
[6], frame
->data
[7]);
781 static uint64_t can_rxfifo_post_read_id(RegisterInfo
*reg
, uint64_t val
)
783 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(reg
->opaque
);
784 unsigned used
= fifo32_num_used(&s
->rx_fifo
);
786 if (used
< CAN_FRAME_SIZE
) {
787 ARRAY_FIELD_DP32(s
->regs
, INTERRUPT_STATUS_REGISTER
, RXUFLW
, 1);
789 val
= s
->regs
[R_RXFIFO_ID
] = fifo32_pop(&s
->rx_fifo
);
790 s
->regs
[R_RXFIFO_DLC
] = fifo32_pop(&s
->rx_fifo
);
791 s
->regs
[R_RXFIFO_DATA1
] = fifo32_pop(&s
->rx_fifo
);
792 s
->regs
[R_RXFIFO_DATA2
] = fifo32_pop(&s
->rx_fifo
);
799 static void can_filter_enable_post_write(RegisterInfo
*reg
, uint64_t val
)
801 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(reg
->opaque
);
803 if (ARRAY_FIELD_EX32(s
->regs
, AFR
, UAF1
) &&
804 ARRAY_FIELD_EX32(s
->regs
, AFR
, UAF2
) &&
805 ARRAY_FIELD_EX32(s
->regs
, AFR
, UAF3
) &&
806 ARRAY_FIELD_EX32(s
->regs
, AFR
, UAF4
)) {
807 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, ACFBSY
, 1);
809 ARRAY_FIELD_DP32(s
->regs
, STATUS_REGISTER
, ACFBSY
, 0);
813 static uint64_t can_filter_mask_pre_write(RegisterInfo
*reg
, uint64_t val
)
815 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(reg
->opaque
);
816 uint32_t reg_idx
= (reg
->access
->addr
) / 4;
817 uint32_t filter_number
= (reg_idx
- R_AFMR1
) / 2;
819 /* modify an acceptance filter, the corresponding UAF bit should be '0'. */
820 if (!(s
->regs
[R_AFR
] & (1 << filter_number
))) {
821 s
->regs
[reg_idx
] = val
;
823 trace_xlnx_can_filter_mask_pre_write(filter_number
, s
->regs
[reg_idx
]);
825 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
827 qemu_log_mask(LOG_GUEST_ERROR
, "%s: Acceptance filter %d"
828 " mask is not set as corresponding UAF bit is not 0.\n",
829 path
, filter_number
+ 1);
832 return s
->regs
[reg_idx
];
835 static uint64_t can_filter_id_pre_write(RegisterInfo
*reg
, uint64_t val
)
837 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(reg
->opaque
);
838 uint32_t reg_idx
= (reg
->access
->addr
) / 4;
839 uint32_t filter_number
= (reg_idx
- R_AFIR1
) / 2;
841 if (!(s
->regs
[R_AFR
] & (1 << filter_number
))) {
842 s
->regs
[reg_idx
] = val
;
844 trace_xlnx_can_filter_id_pre_write(filter_number
, s
->regs
[reg_idx
]);
846 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
848 qemu_log_mask(LOG_GUEST_ERROR
, "%s: Acceptance filter %d"
849 " id is not set as corresponding UAF bit is not 0.\n",
850 path
, filter_number
+ 1);
853 return s
->regs
[reg_idx
];
856 static void can_tx_post_write(RegisterInfo
*reg
, uint64_t val
)
858 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(reg
->opaque
);
860 bool is_txhpb
= reg
->access
->addr
> A_TXFIFO_DATA2
;
862 bool initiate_transfer
= (reg
->access
->addr
== A_TXFIFO_DATA2
) ||
863 (reg
->access
->addr
== A_TXHPB_DATA2
);
865 Fifo32
*f
= is_txhpb
? &s
->txhpb_fifo
: &s
->tx_fifo
;
867 if (!fifo32_is_full(f
)) {
870 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
872 qemu_log_mask(LOG_GUEST_ERROR
, "%s: TX FIFO is full.\n", path
);
875 /* Initiate the message send if TX register is written. */
876 if (initiate_transfer
&&
877 ARRAY_FIELD_EX32(s
->regs
, SOFTWARE_RESET_REGISTER
, CEN
)) {
884 static const RegisterAccessInfo can_regs_info
[] = {
885 { .name
= "SOFTWARE_RESET_REGISTER",
886 .addr
= A_SOFTWARE_RESET_REGISTER
,
888 .pre_write
= can_srr_pre_write
,
889 },{ .name
= "MODE_SELECT_REGISTER",
890 .addr
= A_MODE_SELECT_REGISTER
,
892 .pre_write
= can_msr_pre_write
,
893 },{ .name
= "ARBITRATION_PHASE_BAUD_RATE_PRESCALER_REGISTER",
894 .addr
= A_ARBITRATION_PHASE_BAUD_RATE_PRESCALER_REGISTER
,
896 .pre_write
= can_brpr_pre_write
,
897 },{ .name
= "ARBITRATION_PHASE_BIT_TIMING_REGISTER",
898 .addr
= A_ARBITRATION_PHASE_BIT_TIMING_REGISTER
,
900 .pre_write
= can_btr_pre_write
,
901 },{ .name
= "ERROR_COUNTER_REGISTER",
902 .addr
= A_ERROR_COUNTER_REGISTER
,
905 },{ .name
= "ERROR_STATUS_REGISTER",
906 .addr
= A_ERROR_STATUS_REGISTER
,
909 },{ .name
= "STATUS_REGISTER", .addr
= A_STATUS_REGISTER
,
913 },{ .name
= "INTERRUPT_STATUS_REGISTER",
914 .addr
= A_INTERRUPT_STATUS_REGISTER
,
918 },{ .name
= "INTERRUPT_ENABLE_REGISTER",
919 .addr
= A_INTERRUPT_ENABLE_REGISTER
,
921 .post_write
= can_ier_post_write
,
922 },{ .name
= "INTERRUPT_CLEAR_REGISTER",
923 .addr
= A_INTERRUPT_CLEAR_REGISTER
,
925 .pre_write
= can_icr_pre_write
,
926 },{ .name
= "TIMESTAMP_REGISTER",
927 .addr
= A_TIMESTAMP_REGISTER
,
929 .pre_write
= can_tcr_pre_write
,
930 },{ .name
= "WIR", .addr
= A_WIR
,
933 },{ .name
= "TXFIFO_ID", .addr
= A_TXFIFO_ID
,
934 .post_write
= can_tx_post_write
,
935 },{ .name
= "TXFIFO_DLC", .addr
= A_TXFIFO_DLC
,
937 .post_write
= can_tx_post_write
,
938 },{ .name
= "TXFIFO_DATA1", .addr
= A_TXFIFO_DATA1
,
939 .post_write
= can_tx_post_write
,
940 },{ .name
= "TXFIFO_DATA2", .addr
= A_TXFIFO_DATA2
,
941 .post_write
= can_tx_post_write
,
942 },{ .name
= "TXHPB_ID", .addr
= A_TXHPB_ID
,
943 .post_write
= can_tx_post_write
,
944 },{ .name
= "TXHPB_DLC", .addr
= A_TXHPB_DLC
,
946 .post_write
= can_tx_post_write
,
947 },{ .name
= "TXHPB_DATA1", .addr
= A_TXHPB_DATA1
,
948 .post_write
= can_tx_post_write
,
949 },{ .name
= "TXHPB_DATA2", .addr
= A_TXHPB_DATA2
,
950 .post_write
= can_tx_post_write
,
951 },{ .name
= "RXFIFO_ID", .addr
= A_RXFIFO_ID
,
953 .post_read
= can_rxfifo_post_read_id
,
954 },{ .name
= "RXFIFO_DLC", .addr
= A_RXFIFO_DLC
,
956 },{ .name
= "RXFIFO_DATA1", .addr
= A_RXFIFO_DATA1
,
957 },{ .name
= "RXFIFO_DATA2", .addr
= A_RXFIFO_DATA2
,
958 },{ .name
= "AFR", .addr
= A_AFR
,
960 .post_write
= can_filter_enable_post_write
,
961 },{ .name
= "AFMR1", .addr
= A_AFMR1
,
962 .pre_write
= can_filter_mask_pre_write
,
963 },{ .name
= "AFIR1", .addr
= A_AFIR1
,
964 .pre_write
= can_filter_id_pre_write
,
965 },{ .name
= "AFMR2", .addr
= A_AFMR2
,
966 .pre_write
= can_filter_mask_pre_write
,
967 },{ .name
= "AFIR2", .addr
= A_AFIR2
,
968 .pre_write
= can_filter_id_pre_write
,
969 },{ .name
= "AFMR3", .addr
= A_AFMR3
,
970 .pre_write
= can_filter_mask_pre_write
,
971 },{ .name
= "AFIR3", .addr
= A_AFIR3
,
972 .pre_write
= can_filter_id_pre_write
,
973 },{ .name
= "AFMR4", .addr
= A_AFMR4
,
974 .pre_write
= can_filter_mask_pre_write
,
975 },{ .name
= "AFIR4", .addr
= A_AFIR4
,
976 .pre_write
= can_filter_id_pre_write
,
980 static void xlnx_zynqmp_can_ptimer_cb(void *opaque
)
982 /* No action required on the timer rollover. */
985 static const MemoryRegionOps can_ops
= {
986 .read
= register_read_memory
,
987 .write
= register_write_memory
,
988 .endianness
= DEVICE_LITTLE_ENDIAN
,
990 .min_access_size
= 4,
991 .max_access_size
= 4,
995 static void xlnx_zynqmp_can_reset_init(Object
*obj
, ResetType type
)
997 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(obj
);
1000 for (i
= R_RXFIFO_ID
; i
< ARRAY_SIZE(s
->reg_info
); ++i
) {
1001 register_reset(&s
->reg_info
[i
]);
1004 ptimer_transaction_begin(s
->can_timer
);
1005 ptimer_set_count(s
->can_timer
, 0);
1006 ptimer_transaction_commit(s
->can_timer
);
1009 static void xlnx_zynqmp_can_reset_hold(Object
*obj
, ResetType type
)
1011 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(obj
);
1014 for (i
= 0; i
< R_RXFIFO_ID
; ++i
) {
1015 register_reset(&s
->reg_info
[i
]);
1019 * Reset FIFOs when CAN model is reset. This will clear the fifo writes
1020 * done by post_write which gets called from register_reset function,
1021 * post_write handle will not be able to trigger tx because CAN will be
1022 * disabled when software_reset_register is cleared first.
1024 fifo32_reset(&s
->rx_fifo
);
1025 fifo32_reset(&s
->tx_fifo
);
1026 fifo32_reset(&s
->txhpb_fifo
);
1029 static bool xlnx_zynqmp_can_can_receive(CanBusClientState
*client
)
1031 XlnxZynqMPCANState
*s
= container_of(client
, XlnxZynqMPCANState
,
1034 if (ARRAY_FIELD_EX32(s
->regs
, SOFTWARE_RESET_REGISTER
, SRST
)) {
1035 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
1037 qemu_log_mask(LOG_GUEST_ERROR
, "%s: Controller is in reset state.\n",
1042 if ((ARRAY_FIELD_EX32(s
->regs
, SOFTWARE_RESET_REGISTER
, CEN
)) == 0) {
1043 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
1045 qemu_log_mask(LOG_GUEST_ERROR
, "%s: Controller is disabled. Incoming"
1046 " messages will be discarded.\n", path
);
1053 static ssize_t
xlnx_zynqmp_can_receive(CanBusClientState
*client
,
1054 const qemu_can_frame
*buf
, size_t buf_size
) {
1055 XlnxZynqMPCANState
*s
= container_of(client
, XlnxZynqMPCANState
,
1057 const qemu_can_frame
*frame
= buf
;
1059 if (buf_size
<= 0) {
1060 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
1062 qemu_log_mask(LOG_GUEST_ERROR
, "%s: Error in the data received.\n",
1067 if (ARRAY_FIELD_EX32(s
->regs
, STATUS_REGISTER
, SNOOP
)) {
1068 /* Snoop Mode: Just keep the data. no response back. */
1069 update_rx_fifo(s
, frame
);
1070 } else if ((ARRAY_FIELD_EX32(s
->regs
, STATUS_REGISTER
, SLEEP
))) {
1072 * XlnxZynqMPCAN is in sleep mode. Any data on bus will bring it to wake
1075 can_exit_sleep_mode(s
);
1076 update_rx_fifo(s
, frame
);
1077 } else if ((ARRAY_FIELD_EX32(s
->regs
, STATUS_REGISTER
, SLEEP
)) == 0) {
1078 update_rx_fifo(s
, frame
);
1081 * XlnxZynqMPCAN will not participate in normal bus communication
1082 * and will not receive any messages transmitted by other CAN nodes.
1084 trace_xlnx_can_rx_discard(s
->regs
[R_STATUS_REGISTER
]);
1090 static CanBusClientInfo can_xilinx_bus_client_info
= {
1091 .can_receive
= xlnx_zynqmp_can_can_receive
,
1092 .receive
= xlnx_zynqmp_can_receive
,
1095 static int xlnx_zynqmp_can_connect_to_bus(XlnxZynqMPCANState
*s
,
1098 s
->bus_client
.info
= &can_xilinx_bus_client_info
;
1100 if (can_bus_insert_client(bus
, &s
->bus_client
) < 0) {
1106 static void xlnx_zynqmp_can_realize(DeviceState
*dev
, Error
**errp
)
1108 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(dev
);
1111 if (xlnx_zynqmp_can_connect_to_bus(s
, s
->canbus
) < 0) {
1112 g_autofree
char *path
= object_get_canonical_path(OBJECT(s
));
1114 error_setg(errp
, "%s: xlnx_zynqmp_can_connect_to_bus"
1120 /* Create RX FIFO, TXFIFO, TXHPB storage. */
1121 fifo32_create(&s
->rx_fifo
, RXFIFO_SIZE
);
1122 fifo32_create(&s
->tx_fifo
, RXFIFO_SIZE
);
1123 fifo32_create(&s
->txhpb_fifo
, CAN_FRAME_SIZE
);
1125 /* Allocate a new timer. */
1126 s
->can_timer
= ptimer_init(xlnx_zynqmp_can_ptimer_cb
, s
,
1127 PTIMER_POLICY_LEGACY
);
1129 ptimer_transaction_begin(s
->can_timer
);
1131 ptimer_set_freq(s
->can_timer
, s
->cfg
.ext_clk_freq
);
1132 ptimer_set_limit(s
->can_timer
, CAN_TIMER_MAX
, 1);
1133 ptimer_run(s
->can_timer
, 0);
1134 ptimer_transaction_commit(s
->can_timer
);
1137 static void xlnx_zynqmp_can_init(Object
*obj
)
1139 XlnxZynqMPCANState
*s
= XLNX_ZYNQMP_CAN(obj
);
1140 SysBusDevice
*sbd
= SYS_BUS_DEVICE(obj
);
1142 RegisterInfoArray
*reg_array
;
1144 memory_region_init(&s
->iomem
, obj
, TYPE_XLNX_ZYNQMP_CAN
,
1145 XLNX_ZYNQMP_CAN_R_MAX
* 4);
1146 reg_array
= register_init_block32(DEVICE(obj
), can_regs_info
,
1147 ARRAY_SIZE(can_regs_info
),
1148 s
->reg_info
, s
->regs
,
1150 XLNX_ZYNQMP_CAN_ERR_DEBUG
,
1151 XLNX_ZYNQMP_CAN_R_MAX
* 4);
1153 memory_region_add_subregion(&s
->iomem
, 0x00, ®_array
->mem
);
1154 sysbus_init_mmio(sbd
, &s
->iomem
);
1155 sysbus_init_irq(SYS_BUS_DEVICE(obj
), &s
->irq
);
1158 static const VMStateDescription vmstate_can
= {
1159 .name
= TYPE_XLNX_ZYNQMP_CAN
,
1161 .minimum_version_id
= 1,
1162 .fields
= (const VMStateField
[]) {
1163 VMSTATE_FIFO32(rx_fifo
, XlnxZynqMPCANState
),
1164 VMSTATE_FIFO32(tx_fifo
, XlnxZynqMPCANState
),
1165 VMSTATE_FIFO32(txhpb_fifo
, XlnxZynqMPCANState
),
1166 VMSTATE_UINT32_ARRAY(regs
, XlnxZynqMPCANState
, XLNX_ZYNQMP_CAN_R_MAX
),
1167 VMSTATE_PTIMER(can_timer
, XlnxZynqMPCANState
),
1168 VMSTATE_END_OF_LIST(),
1172 static Property xlnx_zynqmp_can_properties
[] = {
1173 DEFINE_PROP_UINT32("ext_clk_freq", XlnxZynqMPCANState
, cfg
.ext_clk_freq
,
1175 DEFINE_PROP_LINK("canbus", XlnxZynqMPCANState
, canbus
, TYPE_CAN_BUS
,
1177 DEFINE_PROP_END_OF_LIST(),
1180 static void xlnx_zynqmp_can_class_init(ObjectClass
*klass
, void *data
)
1182 DeviceClass
*dc
= DEVICE_CLASS(klass
);
1183 ResettableClass
*rc
= RESETTABLE_CLASS(klass
);
1185 rc
->phases
.enter
= xlnx_zynqmp_can_reset_init
;
1186 rc
->phases
.hold
= xlnx_zynqmp_can_reset_hold
;
1187 dc
->realize
= xlnx_zynqmp_can_realize
;
1188 device_class_set_props(dc
, xlnx_zynqmp_can_properties
);
1189 dc
->vmsd
= &vmstate_can
;
1192 static const TypeInfo can_info
= {
1193 .name
= TYPE_XLNX_ZYNQMP_CAN
,
1194 .parent
= TYPE_SYS_BUS_DEVICE
,
1195 .instance_size
= sizeof(XlnxZynqMPCANState
),
1196 .class_init
= xlnx_zynqmp_can_class_init
,
1197 .instance_init
= xlnx_zynqmp_can_init
,
1200 static void can_register_types(void)
1202 type_register_static(&can_info
);
1205 type_init(can_register_types
)