xlnx-zynqmp-can.c (41791B)
1/* 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 5 * 6 * Copyright (c) 2020 Xilinx Inc. 7 * 8 * Written-by: Vikram Garhwal<fnu.vikram@xilinx.com> 9 * 10 * Based on QEMU CAN Device emulation implemented by Jin Yang, Deniz Eren and 11 * Pavel Pisa 12 * 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: 19 * 20 * The above copyright notice and this permission notice shall be included in 21 * all copies or substantial portions of the Software. 22 * 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 29 * THE SOFTWARE. 30 */ 31 32#include "qemu/osdep.h" 33#include "hw/sysbus.h" 34#include "hw/register.h" 35#include "hw/irq.h" 36#include "qapi/error.h" 37#include "qemu/bitops.h" 38#include "qemu/log.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" 47#include "trace.h" 48 49#ifndef XLNX_ZYNQMP_CAN_ERR_DEBUG 50#define XLNX_ZYNQMP_CAN_ERR_DEBUG 0 51#endif 52 53#define MAX_DLC 8 54#undef ERROR 55 56REG32(SOFTWARE_RESET_REGISTER, 0x0) 57 FIELD(SOFTWARE_RESET_REGISTER, CEN, 1, 1) 58 FIELD(SOFTWARE_RESET_REGISTER, SRST, 0, 1) 59REG32(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) 63REG32(ARBITRATION_PHASE_BAUD_RATE_PRESCALER_REGISTER, 0x8) 64 FIELD(ARBITRATION_PHASE_BAUD_RATE_PRESCALER_REGISTER, BRP, 0, 8) 65REG32(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) 69REG32(ERROR_COUNTER_REGISTER, 0x10) 70 FIELD(ERROR_COUNTER_REGISTER, REC, 8, 8) 71 FIELD(ERROR_COUNTER_REGISTER, TEC, 0, 8) 72REG32(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) 78REG32(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) 91REG32(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) 107REG32(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) 123REG32(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) 139REG32(TIMESTAMP_REGISTER, 0x28) 140 FIELD(TIMESTAMP_REGISTER, CTS, 0, 1) 141REG32(WIR, 0x2c) 142 FIELD(WIR, EW, 8, 8) 143 FIELD(WIR, FW, 0, 8) 144REG32(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) 150REG32(TXFIFO_DLC, 0x34) 151 FIELD(TXFIFO_DLC, DLC, 28, 4) 152REG32(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) 157REG32(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) 162REG32(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) 168REG32(TXHPB_DLC, 0x44) 169 FIELD(TXHPB_DLC, DLC, 28, 4) 170REG32(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) 175REG32(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) 180REG32(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) 186REG32(RXFIFO_DLC, 0x54) 187 FIELD(RXFIFO_DLC, DLC, 28, 4) 188 FIELD(RXFIFO_DLC, RXT, 0, 16) 189REG32(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) 194REG32(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) 199REG32(AFR, 0x60) 200 FIELD(AFR, UAF4, 3, 1) 201 FIELD(AFR, UAF3, 2, 1) 202 FIELD(AFR, UAF2, 1, 1) 203 FIELD(AFR, UAF1, 0, 1) 204REG32(AFMR1, 0x64) 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) 210REG32(AFIR1, 0x68) 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) 216REG32(AFMR2, 0x6c) 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) 222REG32(AFIR2, 0x70) 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) 228REG32(AFMR3, 0x74) 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) 234REG32(AFIR3, 0x78) 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) 240REG32(AFMR4, 0x7c) 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) 246REG32(AFIR4, 0x80) 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) 252 253static void can_update_irq(XlnxZynqMPCANState *s) 254{ 255 uint32_t irq; 256 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); 261 } 262 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); 266 } 267 268 /* RX Interrupts. */ 269 if (fifo32_num_used(&s->rx_fifo) >= CAN_FRAME_SIZE) { 270 ARRAY_FIELD_DP32(s->regs, INTERRUPT_STATUS_REGISTER, RXNEMP, 1); 271 } 272 273 /* TX interrupts. */ 274 if (fifo32_is_empty(&s->tx_fifo)) { 275 ARRAY_FIELD_DP32(s->regs, INTERRUPT_STATUS_REGISTER, TXFEMP, 1); 276 } 277 278 if (fifo32_is_full(&s->tx_fifo)) { 279 ARRAY_FIELD_DP32(s->regs, INTERRUPT_STATUS_REGISTER, TXFLL, 1); 280 } 281 282 if (fifo32_is_full(&s->txhpb_fifo)) { 283 ARRAY_FIELD_DP32(s->regs, INTERRUPT_STATUS_REGISTER, TXBFLL, 1); 284 } 285 286 irq = s->regs[R_INTERRUPT_STATUS_REGISTER]; 287 irq &= s->regs[R_INTERRUPT_ENABLE_REGISTER]; 288 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); 292} 293 294static void can_ier_post_write(RegisterInfo *reg, uint64_t val) 295{ 296 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(reg->opaque); 297 298 can_update_irq(s); 299} 300 301static uint64_t can_icr_pre_write(RegisterInfo *reg, uint64_t val) 302{ 303 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(reg->opaque); 304 305 s->regs[R_INTERRUPT_STATUS_REGISTER] &= ~val; 306 can_update_irq(s); 307 308 return 0; 309} 310 311static void can_config_reset(XlnxZynqMPCANState *s) 312{ 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]); 316 register_reset( 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]); 324} 325 326static void can_config_mode(XlnxZynqMPCANState *s) 327{ 328 register_reset(&s->reg_info[R_ERROR_COUNTER_REGISTER]); 329 register_reset(&s->reg_info[R_ERROR_STATUS_REGISTER]); 330 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); 341 342 can_update_irq(s); 343} 344 345static void update_status_register_mode_bits(XlnxZynqMPCANState *s) 346{ 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); 353 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); 359 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, 366 sleep_irq_val); 367 } else if (ARRAY_FIELD_EX32(s->regs, MODE_SELECT_REGISTER, SNOOP)) { 368 ARRAY_FIELD_DP32(s->regs, STATUS_REGISTER, SNOOP, 1); 369 } else { 370 /* 371 * If all bits are zero then XlnxZynqMPCAN is set in normal mode. 372 */ 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, 376 wakeup_irq_val); 377 } 378 379 can_update_irq(s); 380} 381 382static void can_exit_sleep_mode(XlnxZynqMPCANState *s) 383{ 384 ARRAY_FIELD_DP32(s->regs, MODE_SELECT_REGISTER, SLEEP, 0); 385 update_status_register_mode_bits(s); 386} 387 388static void generate_frame(qemu_can_frame *frame, uint32_t *data) 389{ 390 frame->can_id = data[0]; 391 frame->can_dlc = FIELD_EX32(data[1], TXFIFO_DLC, DLC); 392 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); 397 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); 402} 403 404static bool tx_ready_check(XlnxZynqMPCANState *s) 405{ 406 if (ARRAY_FIELD_EX32(s->regs, SOFTWARE_RESET_REGISTER, SRST)) { 407 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 408 409 qemu_log_mask(LOG_GUEST_ERROR, "%s: Attempting to transfer data while" 410 " data while controller is in reset mode.\n", 411 path); 412 return false; 413 } 414 415 if (ARRAY_FIELD_EX32(s->regs, SOFTWARE_RESET_REGISTER, CEN) == 0) { 416 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 417 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", 421 path); 422 return false; 423 } 424 425 if (ARRAY_FIELD_EX32(s->regs, STATUS_REGISTER, SNOOP)) { 426 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 427 428 qemu_log_mask(LOG_GUEST_ERROR, "%s: Attempting to transfer" 429 " data while controller is in SNOOP MODE.\n", 430 path); 431 return false; 432 } 433 434 return true; 435} 436 437static void transfer_fifo(XlnxZynqMPCANState *s, Fifo32 *fifo) 438{ 439 qemu_can_frame frame; 440 uint32_t data[CAN_FRAME_SIZE]; 441 int i; 442 bool can_tx = tx_ready_check(s); 443 444 if (!can_tx) { 445 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 446 447 qemu_log_mask(LOG_GUEST_ERROR, "%s: Controller is not enabled for data" 448 " transfer.\n", path); 449 can_update_irq(s); 450 return; 451 } 452 453 while (!fifo32_is_empty(fifo)) { 454 for (i = 0; i < CAN_FRAME_SIZE; i++) { 455 data[i] = fifo32_pop(fifo); 456 } 457 458 if (ARRAY_FIELD_EX32(s->regs, STATUS_REGISTER, LBACK)) { 459 /* 460 * Controller is in loopback. In Loopback mode, the CAN core 461 * transmits a recessive bitstream on to the XlnxZynqMPCAN Bus. 462 * Any message transmitted is looped back to the RX line and 463 * acknowledged. The XlnxZynqMPCAN core receives any message 464 * that it transmits. 465 */ 466 if (fifo32_is_full(&s->rx_fifo)) { 467 ARRAY_FIELD_DP32(s->regs, INTERRUPT_STATUS_REGISTER, RXOFLW, 1); 468 } else { 469 for (i = 0; i < CAN_FRAME_SIZE; i++) { 470 fifo32_push(&s->rx_fifo, data[i]); 471 } 472 473 ARRAY_FIELD_DP32(s->regs, INTERRUPT_STATUS_REGISTER, RXOK, 1); 474 } 475 } else { 476 /* Normal mode Tx. */ 477 generate_frame(&frame, data); 478 479 trace_xlnx_can_tx_data(frame.can_id, frame.can_dlc, 480 frame.data[0], frame.data[1], 481 frame.data[2], frame.data[3], 482 frame.data[4], frame.data[5], 483 frame.data[6], frame.data[7]); 484 can_bus_client_send(&s->bus_client, &frame, 1); 485 } 486 } 487 488 ARRAY_FIELD_DP32(s->regs, INTERRUPT_STATUS_REGISTER, TXOK, 1); 489 ARRAY_FIELD_DP32(s->regs, STATUS_REGISTER, TXBFLL, 0); 490 491 if (ARRAY_FIELD_EX32(s->regs, STATUS_REGISTER, SLEEP)) { 492 can_exit_sleep_mode(s); 493 } 494 495 can_update_irq(s); 496} 497 498static uint64_t can_srr_pre_write(RegisterInfo *reg, uint64_t val) 499{ 500 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(reg->opaque); 501 502 ARRAY_FIELD_DP32(s->regs, SOFTWARE_RESET_REGISTER, CEN, 503 FIELD_EX32(val, SOFTWARE_RESET_REGISTER, CEN)); 504 505 if (FIELD_EX32(val, SOFTWARE_RESET_REGISTER, SRST)) { 506 trace_xlnx_can_reset(val); 507 508 /* First, core will do software reset then will enter in config mode. */ 509 can_config_reset(s); 510 } 511 512 if (ARRAY_FIELD_EX32(s->regs, SOFTWARE_RESET_REGISTER, CEN) == 0) { 513 can_config_mode(s); 514 } else { 515 /* 516 * Leave config mode. Now XlnxZynqMPCAN core will enter normal, 517 * sleep, snoop or loopback mode depending upon LBACK, SLEEP, SNOOP 518 * register states. 519 */ 520 ARRAY_FIELD_DP32(s->regs, STATUS_REGISTER, CONFIG, 0); 521 522 ptimer_transaction_begin(s->can_timer); 523 ptimer_set_count(s->can_timer, 0); 524 ptimer_transaction_commit(s->can_timer); 525 526 /* XlnxZynqMPCAN is out of config mode. It will send pending data. */ 527 transfer_fifo(s, &s->txhpb_fifo); 528 transfer_fifo(s, &s->tx_fifo); 529 } 530 531 update_status_register_mode_bits(s); 532 533 return s->regs[R_SOFTWARE_RESET_REGISTER]; 534} 535 536static uint64_t can_msr_pre_write(RegisterInfo *reg, uint64_t val) 537{ 538 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(reg->opaque); 539 uint8_t multi_mode; 540 541 /* 542 * Multiple mode set check. This is done to make sure user doesn't set 543 * multiple modes. 544 */ 545 multi_mode = FIELD_EX32(val, MODE_SELECT_REGISTER, LBACK) + 546 FIELD_EX32(val, MODE_SELECT_REGISTER, SLEEP) + 547 FIELD_EX32(val, MODE_SELECT_REGISTER, SNOOP); 548 549 if (multi_mode > 1) { 550 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 551 552 qemu_log_mask(LOG_GUEST_ERROR, "%s: Attempting to config" 553 " several modes simultaneously. One mode will be selected" 554 " according to their priority: LBACK > SLEEP > SNOOP.\n", 555 path); 556 } 557 558 if (ARRAY_FIELD_EX32(s->regs, SOFTWARE_RESET_REGISTER, CEN) == 0) { 559 /* We are in configuration mode, any mode can be selected. */ 560 s->regs[R_MODE_SELECT_REGISTER] = val; 561 } else { 562 bool sleep_mode_bit = FIELD_EX32(val, MODE_SELECT_REGISTER, SLEEP); 563 564 ARRAY_FIELD_DP32(s->regs, MODE_SELECT_REGISTER, SLEEP, sleep_mode_bit); 565 566 if (FIELD_EX32(val, MODE_SELECT_REGISTER, LBACK)) { 567 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 568 569 qemu_log_mask(LOG_GUEST_ERROR, "%s: Attempting to set" 570 " LBACK mode without setting CEN bit as 0.\n", 571 path); 572 } else if (FIELD_EX32(val, MODE_SELECT_REGISTER, SNOOP)) { 573 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 574 575 qemu_log_mask(LOG_GUEST_ERROR, "%s: Attempting to set" 576 " SNOOP mode without setting CEN bit as 0.\n", 577 path); 578 } 579 580 update_status_register_mode_bits(s); 581 } 582 583 return s->regs[R_MODE_SELECT_REGISTER]; 584} 585 586static uint64_t can_brpr_pre_write(RegisterInfo *reg, uint64_t val) 587{ 588 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(reg->opaque); 589 590 /* Only allow writes when in config mode. */ 591 if (ARRAY_FIELD_EX32(s->regs, SOFTWARE_RESET_REGISTER, CEN)) { 592 return s->regs[R_ARBITRATION_PHASE_BAUD_RATE_PRESCALER_REGISTER]; 593 } 594 595 return val; 596} 597 598static uint64_t can_btr_pre_write(RegisterInfo *reg, uint64_t val) 599{ 600 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(reg->opaque); 601 602 /* Only allow writes when in config mode. */ 603 if (ARRAY_FIELD_EX32(s->regs, SOFTWARE_RESET_REGISTER, CEN)) { 604 return s->regs[R_ARBITRATION_PHASE_BIT_TIMING_REGISTER]; 605 } 606 607 return val; 608} 609 610static uint64_t can_tcr_pre_write(RegisterInfo *reg, uint64_t val) 611{ 612 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(reg->opaque); 613 614 if (FIELD_EX32(val, TIMESTAMP_REGISTER, CTS)) { 615 ptimer_transaction_begin(s->can_timer); 616 ptimer_set_count(s->can_timer, 0); 617 ptimer_transaction_commit(s->can_timer); 618 } 619 620 return 0; 621} 622 623static void update_rx_fifo(XlnxZynqMPCANState *s, const qemu_can_frame *frame) 624{ 625 bool filter_pass = false; 626 uint16_t timestamp = 0; 627 628 /* If no filter is enabled. Message will be stored in FIFO. */ 629 if (!((ARRAY_FIELD_EX32(s->regs, AFR, UAF1)) | 630 (ARRAY_FIELD_EX32(s->regs, AFR, UAF2)) | 631 (ARRAY_FIELD_EX32(s->regs, AFR, UAF3)) | 632 (ARRAY_FIELD_EX32(s->regs, AFR, UAF4)))) { 633 filter_pass = true; 634 } 635 636 /* 637 * Messages that pass any of the acceptance filters will be stored in 638 * the RX FIFO. 639 */ 640 if (ARRAY_FIELD_EX32(s->regs, AFR, UAF1)) { 641 uint32_t id_masked = s->regs[R_AFMR1] & frame->can_id; 642 uint32_t filter_id_masked = s->regs[R_AFMR1] & s->regs[R_AFIR1]; 643 644 if (filter_id_masked == id_masked) { 645 filter_pass = true; 646 } 647 } 648 649 if (ARRAY_FIELD_EX32(s->regs, AFR, UAF2)) { 650 uint32_t id_masked = s->regs[R_AFMR2] & frame->can_id; 651 uint32_t filter_id_masked = s->regs[R_AFMR2] & s->regs[R_AFIR2]; 652 653 if (filter_id_masked == id_masked) { 654 filter_pass = true; 655 } 656 } 657 658 if (ARRAY_FIELD_EX32(s->regs, AFR, UAF3)) { 659 uint32_t id_masked = s->regs[R_AFMR3] & frame->can_id; 660 uint32_t filter_id_masked = s->regs[R_AFMR3] & s->regs[R_AFIR3]; 661 662 if (filter_id_masked == id_masked) { 663 filter_pass = true; 664 } 665 } 666 667 if (ARRAY_FIELD_EX32(s->regs, AFR, UAF4)) { 668 uint32_t id_masked = s->regs[R_AFMR4] & frame->can_id; 669 uint32_t filter_id_masked = s->regs[R_AFMR4] & s->regs[R_AFIR4]; 670 671 if (filter_id_masked == id_masked) { 672 filter_pass = true; 673 } 674 } 675 676 if (!filter_pass) { 677 trace_xlnx_can_rx_fifo_filter_reject(frame->can_id, frame->can_dlc); 678 return; 679 } 680 681 /* Store the message in fifo if it passed through any of the filters. */ 682 if (filter_pass && frame->can_dlc <= MAX_DLC) { 683 684 if (fifo32_is_full(&s->rx_fifo)) { 685 ARRAY_FIELD_DP32(s->regs, INTERRUPT_STATUS_REGISTER, RXOFLW, 1); 686 } else { 687 timestamp = CAN_TIMER_MAX - ptimer_get_count(s->can_timer); 688 689 fifo32_push(&s->rx_fifo, frame->can_id); 690 691 fifo32_push(&s->rx_fifo, deposit32(0, R_RXFIFO_DLC_DLC_SHIFT, 692 R_RXFIFO_DLC_DLC_LENGTH, 693 frame->can_dlc) | 694 deposit32(0, R_RXFIFO_DLC_RXT_SHIFT, 695 R_RXFIFO_DLC_RXT_LENGTH, 696 timestamp)); 697 698 /* First 32 bit of the data. */ 699 fifo32_push(&s->rx_fifo, deposit32(0, R_TXFIFO_DATA1_DB3_SHIFT, 700 R_TXFIFO_DATA1_DB3_LENGTH, 701 frame->data[0]) | 702 deposit32(0, R_TXFIFO_DATA1_DB2_SHIFT, 703 R_TXFIFO_DATA1_DB2_LENGTH, 704 frame->data[1]) | 705 deposit32(0, R_TXFIFO_DATA1_DB1_SHIFT, 706 R_TXFIFO_DATA1_DB1_LENGTH, 707 frame->data[2]) | 708 deposit32(0, R_TXFIFO_DATA1_DB0_SHIFT, 709 R_TXFIFO_DATA1_DB0_LENGTH, 710 frame->data[3])); 711 /* Last 32 bit of the data. */ 712 fifo32_push(&s->rx_fifo, deposit32(0, R_TXFIFO_DATA2_DB7_SHIFT, 713 R_TXFIFO_DATA2_DB7_LENGTH, 714 frame->data[4]) | 715 deposit32(0, R_TXFIFO_DATA2_DB6_SHIFT, 716 R_TXFIFO_DATA2_DB6_LENGTH, 717 frame->data[5]) | 718 deposit32(0, R_TXFIFO_DATA2_DB5_SHIFT, 719 R_TXFIFO_DATA2_DB5_LENGTH, 720 frame->data[6]) | 721 deposit32(0, R_TXFIFO_DATA2_DB4_SHIFT, 722 R_TXFIFO_DATA2_DB4_LENGTH, 723 frame->data[7])); 724 725 ARRAY_FIELD_DP32(s->regs, INTERRUPT_STATUS_REGISTER, RXOK, 1); 726 trace_xlnx_can_rx_data(frame->can_id, frame->can_dlc, 727 frame->data[0], frame->data[1], 728 frame->data[2], frame->data[3], 729 frame->data[4], frame->data[5], 730 frame->data[6], frame->data[7]); 731 } 732 733 can_update_irq(s); 734 } 735} 736 737static uint64_t can_rxfifo_pre_read(RegisterInfo *reg, uint64_t val) 738{ 739 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(reg->opaque); 740 741 if (!fifo32_is_empty(&s->rx_fifo)) { 742 val = fifo32_pop(&s->rx_fifo); 743 } else { 744 ARRAY_FIELD_DP32(s->regs, INTERRUPT_STATUS_REGISTER, RXUFLW, 1); 745 } 746 747 can_update_irq(s); 748 return val; 749} 750 751static void can_filter_enable_post_write(RegisterInfo *reg, uint64_t val) 752{ 753 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(reg->opaque); 754 755 if (ARRAY_FIELD_EX32(s->regs, AFR, UAF1) && 756 ARRAY_FIELD_EX32(s->regs, AFR, UAF2) && 757 ARRAY_FIELD_EX32(s->regs, AFR, UAF3) && 758 ARRAY_FIELD_EX32(s->regs, AFR, UAF4)) { 759 ARRAY_FIELD_DP32(s->regs, STATUS_REGISTER, ACFBSY, 1); 760 } else { 761 ARRAY_FIELD_DP32(s->regs, STATUS_REGISTER, ACFBSY, 0); 762 } 763} 764 765static uint64_t can_filter_mask_pre_write(RegisterInfo *reg, uint64_t val) 766{ 767 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(reg->opaque); 768 uint32_t reg_idx = (reg->access->addr) / 4; 769 uint32_t filter_number = (reg_idx - R_AFMR1) / 2; 770 771 /* modify an acceptance filter, the corresponding UAF bit should be '0'. */ 772 if (!(s->regs[R_AFR] & (1 << filter_number))) { 773 s->regs[reg_idx] = val; 774 775 trace_xlnx_can_filter_mask_pre_write(filter_number, s->regs[reg_idx]); 776 } else { 777 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 778 779 qemu_log_mask(LOG_GUEST_ERROR, "%s: Acceptance filter %d" 780 " mask is not set as corresponding UAF bit is not 0.\n", 781 path, filter_number + 1); 782 } 783 784 return s->regs[reg_idx]; 785} 786 787static uint64_t can_filter_id_pre_write(RegisterInfo *reg, uint64_t val) 788{ 789 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(reg->opaque); 790 uint32_t reg_idx = (reg->access->addr) / 4; 791 uint32_t filter_number = (reg_idx - R_AFIR1) / 2; 792 793 if (!(s->regs[R_AFR] & (1 << filter_number))) { 794 s->regs[reg_idx] = val; 795 796 trace_xlnx_can_filter_id_pre_write(filter_number, s->regs[reg_idx]); 797 } else { 798 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 799 800 qemu_log_mask(LOG_GUEST_ERROR, "%s: Acceptance filter %d" 801 " id is not set as corresponding UAF bit is not 0.\n", 802 path, filter_number + 1); 803 } 804 805 return s->regs[reg_idx]; 806} 807 808static void can_tx_post_write(RegisterInfo *reg, uint64_t val) 809{ 810 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(reg->opaque); 811 812 bool is_txhpb = reg->access->addr > A_TXFIFO_DATA2; 813 814 bool initiate_transfer = (reg->access->addr == A_TXFIFO_DATA2) || 815 (reg->access->addr == A_TXHPB_DATA2); 816 817 Fifo32 *f = is_txhpb ? &s->txhpb_fifo : &s->tx_fifo; 818 819 if (!fifo32_is_full(f)) { 820 fifo32_push(f, val); 821 } else { 822 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 823 824 qemu_log_mask(LOG_GUEST_ERROR, "%s: TX FIFO is full.\n", path); 825 } 826 827 /* Initiate the message send if TX register is written. */ 828 if (initiate_transfer && 829 ARRAY_FIELD_EX32(s->regs, SOFTWARE_RESET_REGISTER, CEN)) { 830 transfer_fifo(s, f); 831 } 832 833 can_update_irq(s); 834} 835 836static const RegisterAccessInfo can_regs_info[] = { 837 { .name = "SOFTWARE_RESET_REGISTER", 838 .addr = A_SOFTWARE_RESET_REGISTER, 839 .rsvd = 0xfffffffc, 840 .pre_write = can_srr_pre_write, 841 },{ .name = "MODE_SELECT_REGISTER", 842 .addr = A_MODE_SELECT_REGISTER, 843 .rsvd = 0xfffffff8, 844 .pre_write = can_msr_pre_write, 845 },{ .name = "ARBITRATION_PHASE_BAUD_RATE_PRESCALER_REGISTER", 846 .addr = A_ARBITRATION_PHASE_BAUD_RATE_PRESCALER_REGISTER, 847 .rsvd = 0xffffff00, 848 .pre_write = can_brpr_pre_write, 849 },{ .name = "ARBITRATION_PHASE_BIT_TIMING_REGISTER", 850 .addr = A_ARBITRATION_PHASE_BIT_TIMING_REGISTER, 851 .rsvd = 0xfffffe00, 852 .pre_write = can_btr_pre_write, 853 },{ .name = "ERROR_COUNTER_REGISTER", 854 .addr = A_ERROR_COUNTER_REGISTER, 855 .rsvd = 0xffff0000, 856 .ro = 0xffffffff, 857 },{ .name = "ERROR_STATUS_REGISTER", 858 .addr = A_ERROR_STATUS_REGISTER, 859 .rsvd = 0xffffffe0, 860 .w1c = 0x1f, 861 },{ .name = "STATUS_REGISTER", .addr = A_STATUS_REGISTER, 862 .reset = 0x1, 863 .rsvd = 0xffffe000, 864 .ro = 0x1fff, 865 },{ .name = "INTERRUPT_STATUS_REGISTER", 866 .addr = A_INTERRUPT_STATUS_REGISTER, 867 .reset = 0x6000, 868 .rsvd = 0xffff8000, 869 .ro = 0x7fff, 870 },{ .name = "INTERRUPT_ENABLE_REGISTER", 871 .addr = A_INTERRUPT_ENABLE_REGISTER, 872 .rsvd = 0xffff8000, 873 .post_write = can_ier_post_write, 874 },{ .name = "INTERRUPT_CLEAR_REGISTER", 875 .addr = A_INTERRUPT_CLEAR_REGISTER, 876 .rsvd = 0xffff8000, 877 .pre_write = can_icr_pre_write, 878 },{ .name = "TIMESTAMP_REGISTER", 879 .addr = A_TIMESTAMP_REGISTER, 880 .rsvd = 0xfffffffe, 881 .pre_write = can_tcr_pre_write, 882 },{ .name = "WIR", .addr = A_WIR, 883 .reset = 0x3f3f, 884 .rsvd = 0xffff0000, 885 },{ .name = "TXFIFO_ID", .addr = A_TXFIFO_ID, 886 .post_write = can_tx_post_write, 887 },{ .name = "TXFIFO_DLC", .addr = A_TXFIFO_DLC, 888 .rsvd = 0xfffffff, 889 .post_write = can_tx_post_write, 890 },{ .name = "TXFIFO_DATA1", .addr = A_TXFIFO_DATA1, 891 .post_write = can_tx_post_write, 892 },{ .name = "TXFIFO_DATA2", .addr = A_TXFIFO_DATA2, 893 .post_write = can_tx_post_write, 894 },{ .name = "TXHPB_ID", .addr = A_TXHPB_ID, 895 .post_write = can_tx_post_write, 896 },{ .name = "TXHPB_DLC", .addr = A_TXHPB_DLC, 897 .rsvd = 0xfffffff, 898 .post_write = can_tx_post_write, 899 },{ .name = "TXHPB_DATA1", .addr = A_TXHPB_DATA1, 900 .post_write = can_tx_post_write, 901 },{ .name = "TXHPB_DATA2", .addr = A_TXHPB_DATA2, 902 .post_write = can_tx_post_write, 903 },{ .name = "RXFIFO_ID", .addr = A_RXFIFO_ID, 904 .ro = 0xffffffff, 905 .post_read = can_rxfifo_pre_read, 906 },{ .name = "RXFIFO_DLC", .addr = A_RXFIFO_DLC, 907 .rsvd = 0xfff0000, 908 .post_read = can_rxfifo_pre_read, 909 },{ .name = "RXFIFO_DATA1", .addr = A_RXFIFO_DATA1, 910 .post_read = can_rxfifo_pre_read, 911 },{ .name = "RXFIFO_DATA2", .addr = A_RXFIFO_DATA2, 912 .post_read = can_rxfifo_pre_read, 913 },{ .name = "AFR", .addr = A_AFR, 914 .rsvd = 0xfffffff0, 915 .post_write = can_filter_enable_post_write, 916 },{ .name = "AFMR1", .addr = A_AFMR1, 917 .pre_write = can_filter_mask_pre_write, 918 },{ .name = "AFIR1", .addr = A_AFIR1, 919 .pre_write = can_filter_id_pre_write, 920 },{ .name = "AFMR2", .addr = A_AFMR2, 921 .pre_write = can_filter_mask_pre_write, 922 },{ .name = "AFIR2", .addr = A_AFIR2, 923 .pre_write = can_filter_id_pre_write, 924 },{ .name = "AFMR3", .addr = A_AFMR3, 925 .pre_write = can_filter_mask_pre_write, 926 },{ .name = "AFIR3", .addr = A_AFIR3, 927 .pre_write = can_filter_id_pre_write, 928 },{ .name = "AFMR4", .addr = A_AFMR4, 929 .pre_write = can_filter_mask_pre_write, 930 },{ .name = "AFIR4", .addr = A_AFIR4, 931 .pre_write = can_filter_id_pre_write, 932 } 933}; 934 935static void xlnx_zynqmp_can_ptimer_cb(void *opaque) 936{ 937 /* No action required on the timer rollover. */ 938} 939 940static const MemoryRegionOps can_ops = { 941 .read = register_read_memory, 942 .write = register_write_memory, 943 .endianness = DEVICE_LITTLE_ENDIAN, 944 .valid = { 945 .min_access_size = 4, 946 .max_access_size = 4, 947 }, 948}; 949 950static void xlnx_zynqmp_can_reset_init(Object *obj, ResetType type) 951{ 952 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(obj); 953 unsigned int i; 954 955 for (i = R_RXFIFO_ID; i < ARRAY_SIZE(s->reg_info); ++i) { 956 register_reset(&s->reg_info[i]); 957 } 958 959 ptimer_transaction_begin(s->can_timer); 960 ptimer_set_count(s->can_timer, 0); 961 ptimer_transaction_commit(s->can_timer); 962} 963 964static void xlnx_zynqmp_can_reset_hold(Object *obj) 965{ 966 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(obj); 967 unsigned int i; 968 969 for (i = 0; i < R_RXFIFO_ID; ++i) { 970 register_reset(&s->reg_info[i]); 971 } 972 973 /* 974 * Reset FIFOs when CAN model is reset. This will clear the fifo writes 975 * done by post_write which gets called from register_reset function, 976 * post_write handle will not be able to trigger tx because CAN will be 977 * disabled when software_reset_register is cleared first. 978 */ 979 fifo32_reset(&s->rx_fifo); 980 fifo32_reset(&s->tx_fifo); 981 fifo32_reset(&s->txhpb_fifo); 982} 983 984static bool xlnx_zynqmp_can_can_receive(CanBusClientState *client) 985{ 986 XlnxZynqMPCANState *s = container_of(client, XlnxZynqMPCANState, 987 bus_client); 988 989 if (ARRAY_FIELD_EX32(s->regs, SOFTWARE_RESET_REGISTER, SRST)) { 990 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 991 992 qemu_log_mask(LOG_GUEST_ERROR, "%s: Controller is in reset state.\n", 993 path); 994 return false; 995 } 996 997 if ((ARRAY_FIELD_EX32(s->regs, SOFTWARE_RESET_REGISTER, CEN)) == 0) { 998 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 999 1000 qemu_log_mask(LOG_GUEST_ERROR, "%s: Controller is disabled. Incoming" 1001 " messages will be discarded.\n", path); 1002 return false; 1003 } 1004 1005 return true; 1006} 1007 1008static ssize_t xlnx_zynqmp_can_receive(CanBusClientState *client, 1009 const qemu_can_frame *buf, size_t buf_size) { 1010 XlnxZynqMPCANState *s = container_of(client, XlnxZynqMPCANState, 1011 bus_client); 1012 const qemu_can_frame *frame = buf; 1013 1014 if (buf_size <= 0) { 1015 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 1016 1017 qemu_log_mask(LOG_GUEST_ERROR, "%s: Error in the data received.\n", 1018 path); 1019 return 0; 1020 } 1021 1022 if (ARRAY_FIELD_EX32(s->regs, STATUS_REGISTER, SNOOP)) { 1023 /* Snoop Mode: Just keep the data. no response back. */ 1024 update_rx_fifo(s, frame); 1025 } else if ((ARRAY_FIELD_EX32(s->regs, STATUS_REGISTER, SLEEP))) { 1026 /* 1027 * XlnxZynqMPCAN is in sleep mode. Any data on bus will bring it to wake 1028 * up state. 1029 */ 1030 can_exit_sleep_mode(s); 1031 update_rx_fifo(s, frame); 1032 } else if ((ARRAY_FIELD_EX32(s->regs, STATUS_REGISTER, SLEEP)) == 0) { 1033 update_rx_fifo(s, frame); 1034 } else { 1035 /* 1036 * XlnxZynqMPCAN will not participate in normal bus communication 1037 * and will not receive any messages transmitted by other CAN nodes. 1038 */ 1039 trace_xlnx_can_rx_discard(s->regs[R_STATUS_REGISTER]); 1040 } 1041 1042 return 1; 1043} 1044 1045static CanBusClientInfo can_xilinx_bus_client_info = { 1046 .can_receive = xlnx_zynqmp_can_can_receive, 1047 .receive = xlnx_zynqmp_can_receive, 1048}; 1049 1050static int xlnx_zynqmp_can_connect_to_bus(XlnxZynqMPCANState *s, 1051 CanBusState *bus) 1052{ 1053 s->bus_client.info = &can_xilinx_bus_client_info; 1054 1055 if (can_bus_insert_client(bus, &s->bus_client) < 0) { 1056 return -1; 1057 } 1058 return 0; 1059} 1060 1061static void xlnx_zynqmp_can_realize(DeviceState *dev, Error **errp) 1062{ 1063 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(dev); 1064 1065 if (s->canbus) { 1066 if (xlnx_zynqmp_can_connect_to_bus(s, s->canbus) < 0) { 1067 g_autofree char *path = object_get_canonical_path(OBJECT(s)); 1068 1069 error_setg(errp, "%s: xlnx_zynqmp_can_connect_to_bus" 1070 " failed.", path); 1071 return; 1072 } 1073 } 1074 1075 /* Create RX FIFO, TXFIFO, TXHPB storage. */ 1076 fifo32_create(&s->rx_fifo, RXFIFO_SIZE); 1077 fifo32_create(&s->tx_fifo, RXFIFO_SIZE); 1078 fifo32_create(&s->txhpb_fifo, CAN_FRAME_SIZE); 1079 1080 /* Allocate a new timer. */ 1081 s->can_timer = ptimer_init(xlnx_zynqmp_can_ptimer_cb, s, 1082 PTIMER_POLICY_DEFAULT); 1083 1084 ptimer_transaction_begin(s->can_timer); 1085 1086 ptimer_set_freq(s->can_timer, s->cfg.ext_clk_freq); 1087 ptimer_set_limit(s->can_timer, CAN_TIMER_MAX, 1); 1088 ptimer_run(s->can_timer, 0); 1089 ptimer_transaction_commit(s->can_timer); 1090} 1091 1092static void xlnx_zynqmp_can_init(Object *obj) 1093{ 1094 XlnxZynqMPCANState *s = XLNX_ZYNQMP_CAN(obj); 1095 SysBusDevice *sbd = SYS_BUS_DEVICE(obj); 1096 1097 RegisterInfoArray *reg_array; 1098 1099 memory_region_init(&s->iomem, obj, TYPE_XLNX_ZYNQMP_CAN, 1100 XLNX_ZYNQMP_CAN_R_MAX * 4); 1101 reg_array = register_init_block32(DEVICE(obj), can_regs_info, 1102 ARRAY_SIZE(can_regs_info), 1103 s->reg_info, s->regs, 1104 &can_ops, 1105 XLNX_ZYNQMP_CAN_ERR_DEBUG, 1106 XLNX_ZYNQMP_CAN_R_MAX * 4); 1107 1108 memory_region_add_subregion(&s->iomem, 0x00, ®_array->mem); 1109 sysbus_init_mmio(sbd, &s->iomem); 1110 sysbus_init_irq(SYS_BUS_DEVICE(obj), &s->irq); 1111} 1112 1113static const VMStateDescription vmstate_can = { 1114 .name = TYPE_XLNX_ZYNQMP_CAN, 1115 .version_id = 1, 1116 .minimum_version_id = 1, 1117 .fields = (VMStateField[]) { 1118 VMSTATE_FIFO32(rx_fifo, XlnxZynqMPCANState), 1119 VMSTATE_FIFO32(tx_fifo, XlnxZynqMPCANState), 1120 VMSTATE_FIFO32(txhpb_fifo, XlnxZynqMPCANState), 1121 VMSTATE_UINT32_ARRAY(regs, XlnxZynqMPCANState, XLNX_ZYNQMP_CAN_R_MAX), 1122 VMSTATE_PTIMER(can_timer, XlnxZynqMPCANState), 1123 VMSTATE_END_OF_LIST(), 1124 } 1125}; 1126 1127static Property xlnx_zynqmp_can_properties[] = { 1128 DEFINE_PROP_UINT32("ext_clk_freq", XlnxZynqMPCANState, cfg.ext_clk_freq, 1129 CAN_DEFAULT_CLOCK), 1130 DEFINE_PROP_LINK("canbus", XlnxZynqMPCANState, canbus, TYPE_CAN_BUS, 1131 CanBusState *), 1132 DEFINE_PROP_END_OF_LIST(), 1133}; 1134 1135static void xlnx_zynqmp_can_class_init(ObjectClass *klass, void *data) 1136{ 1137 DeviceClass *dc = DEVICE_CLASS(klass); 1138 ResettableClass *rc = RESETTABLE_CLASS(klass); 1139 1140 rc->phases.enter = xlnx_zynqmp_can_reset_init; 1141 rc->phases.hold = xlnx_zynqmp_can_reset_hold; 1142 dc->realize = xlnx_zynqmp_can_realize; 1143 device_class_set_props(dc, xlnx_zynqmp_can_properties); 1144 dc->vmsd = &vmstate_can; 1145} 1146 1147static const TypeInfo can_info = { 1148 .name = TYPE_XLNX_ZYNQMP_CAN, 1149 .parent = TYPE_SYS_BUS_DEVICE, 1150 .instance_size = sizeof(XlnxZynqMPCANState), 1151 .class_init = xlnx_zynqmp_can_class_init, 1152 .instance_init = xlnx_zynqmp_can_init, 1153}; 1154 1155static void can_register_types(void) 1156{ 1157 type_register_static(&can_info); 1158} 1159 1160type_init(can_register_types)