cachepc-qemu

Fork of AMDESE/qemu with changes for cachepc side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-qemu
Log | Files | Refs | Submodules | LICENSE | sfeed.txt

can_sja1000.c (30000B)


      1/*
      2 * CAN device - SJA1000 chip emulation for QEMU
      3 *
      4 * Copyright (c) 2013-2014 Jin Yang
      5 * Copyright (c) 2014-2018 Pavel Pisa
      6 *
      7 * Initial development supported by Google GSoC 2013 from RTEMS project slot
      8 *
      9 * Permission is hereby granted, free of charge, to any person obtaining a copy
     10 * of this software and associated documentation files (the "Software"), to deal
     11 * in the Software without restriction, including without limitation the rights
     12 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
     13 * copies of the Software, and to permit persons to whom the Software is
     14 * furnished to do so, subject to the following conditions:
     15 *
     16 * The above copyright notice and this permission notice shall be included in
     17 * all copies or substantial portions of the Software.
     18 *
     19 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
     20 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
     21 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
     22 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
     23 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
     24 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
     25 * THE SOFTWARE.
     26 */
     27
     28#include "qemu/osdep.h"
     29#include "qemu/log.h"
     30#include "chardev/char.h"
     31#include "hw/irq.h"
     32#include "migration/vmstate.h"
     33#include "net/can_emu.h"
     34
     35#include "can_sja1000.h"
     36
     37#ifndef DEBUG_FILTER
     38#define DEBUG_FILTER 0
     39#endif /*DEBUG_FILTER*/
     40
     41#ifndef DEBUG_CAN
     42#define DEBUG_CAN 0
     43#endif /*DEBUG_CAN*/
     44
     45#define DPRINTF(fmt, ...) \
     46    do { \
     47        if (DEBUG_CAN) { \
     48            qemu_log("[cansja]: " fmt , ## __VA_ARGS__); \
     49        } \
     50    } while (0)
     51
     52static void can_sja_software_reset(CanSJA1000State *s)
     53{
     54    s->mode        &= ~0x31;
     55    s->mode        |= 0x01;
     56    s->status_pel  &= ~0x37;
     57    s->status_pel  |= 0x34;
     58
     59    s->rxbuf_start = 0x00;
     60    s->rxmsg_cnt   = 0x00;
     61    s->rx_cnt      = 0x00;
     62}
     63
     64void can_sja_hardware_reset(CanSJA1000State *s)
     65{
     66    /* Reset by hardware, p10 */
     67    s->mode        = 0x01;
     68    s->status_pel  = 0x3c;
     69    s->interrupt_pel = 0x00;
     70    s->clock       = 0x00;
     71    s->rxbuf_start = 0x00;
     72    s->rxmsg_cnt   = 0x00;
     73    s->rx_cnt      = 0x00;
     74
     75    s->control     = 0x01;
     76    s->status_bas  = 0x0c;
     77    s->interrupt_bas = 0x00;
     78
     79    qemu_irq_lower(s->irq);
     80}
     81
     82static
     83void can_sja_single_filter(struct qemu_can_filter *filter,
     84            const uint8_t *acr,  const uint8_t *amr, int extended)
     85{
     86    if (extended) {
     87        filter->can_id = (uint32_t)acr[0] << 21;
     88        filter->can_id |= (uint32_t)acr[1] << 13;
     89        filter->can_id |= (uint32_t)acr[2] << 5;
     90        filter->can_id |= (uint32_t)acr[3] >> 3;
     91        if (acr[3] & 4) {
     92            filter->can_id |= QEMU_CAN_RTR_FLAG;
     93        }
     94
     95        filter->can_mask = (uint32_t)amr[0] << 21;
     96        filter->can_mask |= (uint32_t)amr[1] << 13;
     97        filter->can_mask |= (uint32_t)amr[2] << 5;
     98        filter->can_mask |= (uint32_t)amr[3] >> 3;
     99        filter->can_mask = ~filter->can_mask & QEMU_CAN_EFF_MASK;
    100        if (!(amr[3] & 4)) {
    101            filter->can_mask |= QEMU_CAN_RTR_FLAG;
    102        }
    103    } else {
    104        filter->can_id = (uint32_t)acr[0] << 3;
    105        filter->can_id |= (uint32_t)acr[1] >> 5;
    106        if (acr[1] & 0x10) {
    107            filter->can_id |= QEMU_CAN_RTR_FLAG;
    108        }
    109
    110        filter->can_mask = (uint32_t)amr[0] << 3;
    111        filter->can_mask |= (uint32_t)amr[1] << 5;
    112        filter->can_mask = ~filter->can_mask & QEMU_CAN_SFF_MASK;
    113        if (!(amr[1] & 0x10)) {
    114            filter->can_mask |= QEMU_CAN_RTR_FLAG;
    115        }
    116    }
    117}
    118
    119static
    120void can_sja_dual_filter(struct qemu_can_filter *filter,
    121            const uint8_t *acr,  const uint8_t *amr, int extended)
    122{
    123    if (extended) {
    124        filter->can_id = (uint32_t)acr[0] << 21;
    125        filter->can_id |= (uint32_t)acr[1] << 13;
    126
    127        filter->can_mask = (uint32_t)amr[0] << 21;
    128        filter->can_mask |= (uint32_t)amr[1] << 13;
    129        filter->can_mask = ~filter->can_mask & QEMU_CAN_EFF_MASK & ~0x1fff;
    130    } else {
    131        filter->can_id = (uint32_t)acr[0] << 3;
    132        filter->can_id |= (uint32_t)acr[1] >> 5;
    133        if (acr[1] & 0x10) {
    134            filter->can_id |= QEMU_CAN_RTR_FLAG;
    135        }
    136
    137        filter->can_mask = (uint32_t)amr[0] << 3;
    138        filter->can_mask |= (uint32_t)amr[1] >> 5;
    139        filter->can_mask = ~filter->can_mask & QEMU_CAN_SFF_MASK;
    140        if (!(amr[1] & 0x10)) {
    141            filter->can_mask |= QEMU_CAN_RTR_FLAG;
    142        }
    143    }
    144}
    145
    146/* Details in DS-p22, what we need to do here is to test the data. */
    147static
    148int can_sja_accept_filter(CanSJA1000State *s,
    149                                 const qemu_can_frame *frame)
    150{
    151
    152    struct qemu_can_filter filter;
    153
    154    if (s->clock & 0x80) { /* PeliCAN Mode */
    155        if (s->mode & (1 << 3)) { /* Single mode. */
    156            if (frame->can_id & QEMU_CAN_EFF_FLAG) { /* EFF */
    157                can_sja_single_filter(&filter,
    158                    s->code_mask + 0, s->code_mask + 4, 1);
    159
    160                if (!can_bus_filter_match(&filter, frame->can_id)) {
    161                    return 0;
    162                }
    163            } else { /* SFF */
    164                can_sja_single_filter(&filter,
    165                    s->code_mask + 0, s->code_mask + 4, 0);
    166
    167                if (!can_bus_filter_match(&filter, frame->can_id)) {
    168                    return 0;
    169                }
    170
    171                if (frame->can_id & QEMU_CAN_RTR_FLAG) { /* RTR */
    172                    return 1;
    173                }
    174
    175                if (frame->can_dlc == 0) {
    176                    return 1;
    177                }
    178
    179                if ((frame->data[0] & ~(s->code_mask[6])) !=
    180                   (s->code_mask[2] & ~(s->code_mask[6]))) {
    181                    return 0;
    182                }
    183
    184                if (frame->can_dlc < 2) {
    185                    return 1;
    186                }
    187
    188                if ((frame->data[1] & ~(s->code_mask[7])) ==
    189                    (s->code_mask[3] & ~(s->code_mask[7]))) {
    190                    return 1;
    191                }
    192
    193                return 0;
    194            }
    195        } else { /* Dual mode */
    196            if (frame->can_id & QEMU_CAN_EFF_FLAG) { /* EFF */
    197                can_sja_dual_filter(&filter,
    198                    s->code_mask + 0, s->code_mask + 4, 1);
    199
    200                if (can_bus_filter_match(&filter, frame->can_id)) {
    201                    return 1;
    202                }
    203
    204                can_sja_dual_filter(&filter,
    205                    s->code_mask + 2, s->code_mask + 6, 1);
    206
    207                if (can_bus_filter_match(&filter, frame->can_id)) {
    208                    return 1;
    209                }
    210
    211                return 0;
    212            } else {
    213                can_sja_dual_filter(&filter,
    214                    s->code_mask + 0, s->code_mask + 4, 0);
    215
    216                if (can_bus_filter_match(&filter, frame->can_id)) {
    217                    uint8_t expect;
    218                    uint8_t mask;
    219                    expect = s->code_mask[1] << 4;
    220                    expect |= s->code_mask[3] & 0x0f;
    221
    222                    mask = s->code_mask[5] << 4;
    223                    mask |= s->code_mask[7] & 0x0f;
    224                        mask = ~mask & 0xff;
    225
    226                    if ((frame->data[0] & mask) ==
    227                        (expect & mask)) {
    228                        return 1;
    229                    }
    230                }
    231
    232                can_sja_dual_filter(&filter,
    233                    s->code_mask + 2, s->code_mask + 6, 0);
    234
    235                if (can_bus_filter_match(&filter, frame->can_id)) {
    236                    return 1;
    237                }
    238
    239                return 0;
    240            }
    241        }
    242    }
    243
    244    return 1;
    245}
    246
    247static void can_display_msg(const char *prefix, const qemu_can_frame *msg)
    248{
    249    int i;
    250    FILE *logfile = qemu_log_lock();
    251
    252    qemu_log("%s%03X [%01d] %s %s",
    253             prefix,
    254             msg->can_id & QEMU_CAN_EFF_MASK,
    255             msg->can_dlc,
    256             msg->can_id & QEMU_CAN_EFF_FLAG ? "EFF" : "SFF",
    257             msg->can_id & QEMU_CAN_RTR_FLAG ? "RTR" : "DAT");
    258
    259    for (i = 0; i < msg->can_dlc; i++) {
    260        qemu_log(" %02X", msg->data[i]);
    261    }
    262    qemu_log("\n");
    263    qemu_log_flush();
    264    qemu_log_unlock(logfile);
    265}
    266
    267static void buff2frame_pel(const uint8_t *buff, qemu_can_frame *frame)
    268{
    269    uint8_t i;
    270
    271    frame->flags = 0;
    272    frame->can_id = 0;
    273    if (buff[0] & 0x40) { /* RTR */
    274        frame->can_id = QEMU_CAN_RTR_FLAG;
    275    }
    276    frame->can_dlc = buff[0] & 0x0f;
    277
    278    if (frame->can_dlc > 8) {
    279        frame->can_dlc = 8;
    280    }
    281
    282    if (buff[0] & 0x80) { /* Extended */
    283        frame->can_id |= QEMU_CAN_EFF_FLAG;
    284        frame->can_id |= buff[1] << 21; /* ID.28~ID.21 */
    285        frame->can_id |= buff[2] << 13; /* ID.20~ID.13 */
    286        frame->can_id |= buff[3] <<  5;
    287        frame->can_id |= buff[4] >>  3;
    288        for (i = 0; i < frame->can_dlc; i++) {
    289            frame->data[i] = buff[5 + i];
    290        }
    291        for (; i < 8; i++) {
    292            frame->data[i] = 0;
    293        }
    294    } else {
    295        frame->can_id |= buff[1] <<  3;
    296        frame->can_id |= buff[2] >>  5;
    297        for (i = 0; i < frame->can_dlc; i++) {
    298            frame->data[i] = buff[3 + i];
    299        }
    300        for (; i < 8; i++) {
    301            frame->data[i] = 0;
    302        }
    303    }
    304}
    305
    306
    307static void buff2frame_bas(const uint8_t *buff, qemu_can_frame *frame)
    308{
    309    uint8_t i;
    310
    311    frame->flags = 0;
    312    frame->can_id = ((buff[0] << 3) & (0xff << 3)) + ((buff[1] >> 5) & 0x07);
    313    if (buff[1] & 0x10) { /* RTR */
    314        frame->can_id = QEMU_CAN_RTR_FLAG;
    315    }
    316    frame->can_dlc = buff[1] & 0x0f;
    317
    318    if (frame->can_dlc > 8) {
    319        frame->can_dlc = 8;
    320    }
    321
    322    for (i = 0; i < frame->can_dlc; i++) {
    323        frame->data[i] = buff[2 + i];
    324    }
    325    for (; i < 8; i++) {
    326        frame->data[i] = 0;
    327    }
    328}
    329
    330
    331static int frame2buff_pel(const qemu_can_frame *frame, uint8_t *buff)
    332{
    333    int i;
    334    int dlen = frame->can_dlc;
    335
    336    if (frame->can_id & QEMU_CAN_ERR_FLAG) { /* error frame, NOT support now. */
    337        return -1;
    338    }
    339
    340    if (dlen > 8) {
    341        return -1;
    342    }
    343
    344    buff[0] = 0x0f & frame->can_dlc; /* DLC */
    345    if (frame->can_id & QEMU_CAN_RTR_FLAG) { /* RTR */
    346        buff[0] |= (1 << 6);
    347    }
    348    if (frame->can_id & QEMU_CAN_EFF_FLAG) { /* EFF */
    349        buff[0] |= (1 << 7);
    350        buff[1] = extract32(frame->can_id, 21, 8); /* ID.28~ID.21 */
    351        buff[2] = extract32(frame->can_id, 13, 8); /* ID.20~ID.13 */
    352        buff[3] = extract32(frame->can_id, 5, 8);  /* ID.12~ID.05 */
    353        buff[4] = extract32(frame->can_id, 0, 5) << 3; /* ID.04~ID.00,xxx */
    354        for (i = 0; i < dlen; i++) {
    355            buff[5 + i] = frame->data[i];
    356        }
    357        return dlen + 5;
    358    } else { /* SFF */
    359        buff[1] = extract32(frame->can_id, 3, 8); /* ID.10~ID.03 */
    360        buff[2] = extract32(frame->can_id, 0, 3) << 5; /* ID.02~ID.00,xxxxx */
    361        for (i = 0; i < dlen; i++) {
    362            buff[3 + i] = frame->data[i];
    363        }
    364
    365        return dlen + 3;
    366    }
    367
    368    return -1;
    369}
    370
    371static int frame2buff_bas(const qemu_can_frame *frame, uint8_t *buff)
    372{
    373    int i;
    374    int dlen = frame->can_dlc;
    375
    376     /*
    377      * EFF, no support for BasicMode
    378      * No use for Error frames now,
    379      * they could be used in future to update SJA1000 error state
    380      */
    381    if ((frame->can_id & QEMU_CAN_EFF_FLAG) ||
    382       (frame->can_id & QEMU_CAN_ERR_FLAG)) {
    383        return -1;
    384    }
    385
    386    if (dlen > 8) {
    387        return -1;
    388    }
    389
    390    buff[0] = extract32(frame->can_id, 3, 8); /* ID.10~ID.03 */
    391    buff[1] = extract32(frame->can_id, 0, 3) << 5; /* ID.02~ID.00,xxxxx */
    392    if (frame->can_id & QEMU_CAN_RTR_FLAG) { /* RTR */
    393        buff[1] |= (1 << 4);
    394    }
    395    buff[1] |= frame->can_dlc & 0x0f;
    396    for (i = 0; i < dlen; i++) {
    397        buff[2 + i] = frame->data[i];
    398    }
    399
    400    return dlen + 2;
    401}
    402
    403static void can_sja_update_pel_irq(CanSJA1000State *s)
    404{
    405    if (s->interrupt_en & s->interrupt_pel) {
    406        qemu_irq_raise(s->irq);
    407    } else {
    408        qemu_irq_lower(s->irq);
    409    }
    410}
    411
    412static void can_sja_update_bas_irq(CanSJA1000State *s)
    413{
    414    if ((s->control >> 1) & s->interrupt_bas) {
    415        qemu_irq_raise(s->irq);
    416    } else {
    417        qemu_irq_lower(s->irq);
    418    }
    419}
    420
    421void can_sja_mem_write(CanSJA1000State *s, hwaddr addr, uint64_t val,
    422                       unsigned size)
    423{
    424    qemu_can_frame   frame;
    425    uint32_t         tmp;
    426    uint8_t          tmp8, count;
    427
    428
    429    DPRINTF("write 0x%02llx addr 0x%02x\n",
    430            (unsigned long long)val, (unsigned int)addr);
    431
    432    if (addr > CAN_SJA_MEM_SIZE) {
    433        return ;
    434    }
    435
    436    if (s->clock & 0x80) { /* PeliCAN Mode */
    437        switch (addr) {
    438        case SJA_MOD: /* Mode register */
    439            s->mode = 0x1f & val;
    440            if ((s->mode & 0x01) && ((val & 0x01) == 0)) {
    441                /* Go to operation mode from reset mode. */
    442                if (s->mode & (1 << 3)) { /* Single mode. */
    443                    /* For EFF */
    444                    can_sja_single_filter(&s->filter[0],
    445                        s->code_mask + 0, s->code_mask + 4, 1);
    446
    447                    /* For SFF */
    448                    can_sja_single_filter(&s->filter[1],
    449                        s->code_mask + 0, s->code_mask + 4, 0);
    450
    451                    can_bus_client_set_filters(&s->bus_client, s->filter, 2);
    452                } else { /* Dual mode */
    453                    /* For EFF */
    454                    can_sja_dual_filter(&s->filter[0],
    455                        s->code_mask + 0, s->code_mask + 4, 1);
    456
    457                    can_sja_dual_filter(&s->filter[1],
    458                        s->code_mask + 2, s->code_mask + 6, 1);
    459
    460                    /* For SFF */
    461                    can_sja_dual_filter(&s->filter[2],
    462                        s->code_mask + 0, s->code_mask + 4, 0);
    463
    464                    can_sja_dual_filter(&s->filter[3],
    465                        s->code_mask + 2, s->code_mask + 6, 0);
    466
    467                    can_bus_client_set_filters(&s->bus_client, s->filter, 4);
    468                }
    469
    470                s->rxmsg_cnt = 0;
    471                s->rx_cnt = 0;
    472            }
    473            break;
    474
    475        case SJA_CMR: /* Command register. */
    476            if (0x01 & val) { /* Send transmission request. */
    477                buff2frame_pel(s->tx_buff, &frame);
    478                if (DEBUG_FILTER) {
    479                    can_display_msg("[cansja]: Tx request " , &frame);
    480                }
    481
    482                /*
    483                 * Clear transmission complete status,
    484                 * and Transmit Buffer Status.
    485                 * write to the backends.
    486                 */
    487                s->status_pel &= ~(3 << 2);
    488
    489                can_bus_client_send(&s->bus_client, &frame, 1);
    490
    491                /*
    492                 * Set transmission complete status
    493                 * and Transmit Buffer Status.
    494                 */
    495                s->status_pel |= (3 << 2);
    496
    497                /* Clear transmit status. */
    498                s->status_pel &= ~(1 << 5);
    499                s->interrupt_pel |= 0x02;
    500                can_sja_update_pel_irq(s);
    501            }
    502            if (0x04 & val) { /* Release Receive Buffer */
    503                if (s->rxmsg_cnt <= 0) {
    504                    break;
    505                }
    506
    507                tmp8 = s->rx_buff[s->rxbuf_start]; count = 0;
    508                if (tmp8 & (1 << 7)) { /* EFF */
    509                    count += 2;
    510                }
    511                count += 3;
    512                if (!(tmp8 & (1 << 6))) { /* DATA */
    513                    count += (tmp8 & 0x0f);
    514                }
    515
    516                if (DEBUG_FILTER) {
    517                    qemu_log("[cansja]: message released from "
    518                             "Rx FIFO cnt=%d, count=%d\n", s->rx_cnt, count);
    519                }
    520
    521                s->rxbuf_start += count;
    522                s->rxbuf_start %= SJA_RCV_BUF_LEN;
    523
    524                s->rx_cnt -= count;
    525                s->rxmsg_cnt--;
    526                if (s->rxmsg_cnt == 0) {
    527                    s->status_pel &= ~(1 << 0);
    528                    s->interrupt_pel &= ~(1 << 0);
    529                    can_sja_update_pel_irq(s);
    530                }
    531            }
    532            if (0x08 & val) { /* Clear data overrun */
    533                s->status_pel &= ~(1 << 1);
    534                s->interrupt_pel &= ~(1 << 3);
    535                can_sja_update_pel_irq(s);
    536            }
    537            break;
    538        case SJA_SR: /* Status register */
    539        case SJA_IR: /* Interrupt register */
    540            break; /* Do nothing */
    541        case SJA_IER: /* Interrupt enable register */
    542            s->interrupt_en = val;
    543            break;
    544        case 16: /* RX frame information addr16-28. */
    545            s->status_pel |= (1 << 5); /* Set transmit status. */
    546            /* fallthrough */
    547        case 17 ... 28:
    548            if (s->mode & 0x01) { /* Reset mode */
    549                if (addr < 24) {
    550                    s->code_mask[addr - 16] = val;
    551                }
    552            } else { /* Operation mode */
    553                s->tx_buff[addr - 16] = val; /* Store to TX buffer directly. */
    554            }
    555            break;
    556        case SJA_CDR:
    557            s->clock = val;
    558            break;
    559        }
    560    } else { /* Basic Mode */
    561        switch (addr) {
    562        case SJA_BCAN_CTR: /* Control register, addr 0 */
    563            if ((s->control & 0x01) && ((val & 0x01) == 0)) {
    564                /* Go to operation mode from reset mode. */
    565                s->filter[0].can_id = (s->code << 3) & (0xff << 3);
    566                tmp = (~(s->mask << 3)) & (0xff << 3);
    567                tmp |= QEMU_CAN_EFF_FLAG; /* Only Basic CAN Frame. */
    568                s->filter[0].can_mask = tmp;
    569                can_bus_client_set_filters(&s->bus_client, s->filter, 1);
    570
    571                s->rxmsg_cnt = 0;
    572                s->rx_cnt = 0;
    573            } else if (!(s->control & 0x01) && !(val & 0x01)) {
    574                can_sja_software_reset(s);
    575            }
    576
    577            s->control = 0x1f & val;
    578            break;
    579        case SJA_BCAN_CMR: /* Command register, addr 1 */
    580            if (0x01 & val) { /* Send transmission request. */
    581                buff2frame_bas(s->tx_buff, &frame);
    582                if (DEBUG_FILTER) {
    583                    can_display_msg("[cansja]: Tx request " , &frame);
    584                }
    585
    586                /*
    587                 * Clear transmission complete status,
    588                 * and Transmit Buffer Status.
    589                 */
    590                s->status_bas &= ~(3 << 2);
    591
    592                /* write to the backends. */
    593                can_bus_client_send(&s->bus_client, &frame, 1);
    594
    595                /*
    596                 * Set transmission complete status,
    597                 * and Transmit Buffer Status.
    598                 */
    599                s->status_bas |= (3 << 2);
    600
    601                /* Clear transmit status. */
    602                s->status_bas &= ~(1 << 5);
    603                s->interrupt_bas |= 0x02;
    604                can_sja_update_bas_irq(s);
    605            }
    606            if (0x04 & val) { /* Release Receive Buffer */
    607                if (s->rxmsg_cnt <= 0) {
    608                    break;
    609                }
    610
    611                tmp8 = s->rx_buff[(s->rxbuf_start + 1) % SJA_RCV_BUF_LEN];
    612                count = 2 + (tmp8 & 0x0f);
    613
    614                if (DEBUG_FILTER) {
    615                    qemu_log("[cansja]: message released from "
    616                             "Rx FIFO cnt=%d, count=%d\n", s->rx_cnt, count);
    617                }
    618
    619                s->rxbuf_start += count;
    620                s->rxbuf_start %= SJA_RCV_BUF_LEN;
    621                s->rx_cnt -= count;
    622                s->rxmsg_cnt--;
    623
    624                if (s->rxmsg_cnt == 0) {
    625                    s->status_bas &= ~(1 << 0);
    626                    s->interrupt_bas &= ~(1 << 0);
    627                    can_sja_update_bas_irq(s);
    628                }
    629            }
    630            if (0x08 & val) { /* Clear data overrun */
    631                s->status_bas &= ~(1 << 1);
    632                s->interrupt_bas &= ~(1 << 3);
    633                can_sja_update_bas_irq(s);
    634            }
    635            break;
    636        case 4:
    637            s->code = val;
    638            break;
    639        case 5:
    640            s->mask = val;
    641            break;
    642        case 10:
    643            s->status_bas |= (1 << 5); /* Set transmit status. */
    644            /* fallthrough */
    645        case 11 ... 19:
    646            if ((s->control & 0x01) == 0) { /* Operation mode */
    647                s->tx_buff[addr - 10] = val; /* Store to TX buffer directly. */
    648            }
    649            break;
    650        case SJA_CDR:
    651            s->clock = val;
    652            break;
    653        }
    654    }
    655}
    656
    657uint64_t can_sja_mem_read(CanSJA1000State *s, hwaddr addr, unsigned size)
    658{
    659    uint64_t temp = 0;
    660
    661    DPRINTF("read addr 0x%02x ...\n", (unsigned int)addr);
    662
    663    if (addr > CAN_SJA_MEM_SIZE) {
    664        return 0;
    665    }
    666
    667    if (s->clock & 0x80) { /* PeliCAN Mode */
    668        switch (addr) {
    669        case SJA_MOD: /* Mode register, addr 0 */
    670            temp = s->mode;
    671            break;
    672        case SJA_CMR: /* Command register, addr 1 */
    673            temp = 0x00; /* Command register, cannot be read. */
    674            break;
    675        case SJA_SR: /* Status register, addr 2 */
    676            temp = s->status_pel;
    677            break;
    678        case SJA_IR: /* Interrupt register, addr 3 */
    679            temp = s->interrupt_pel;
    680            s->interrupt_pel = 0;
    681            if (s->rxmsg_cnt) {
    682                s->interrupt_pel |= (1 << 0); /* Receive interrupt. */
    683            }
    684            can_sja_update_pel_irq(s);
    685            break;
    686        case SJA_IER: /* Interrupt enable register, addr 4 */
    687            temp = s->interrupt_en;
    688            break;
    689        case 5: /* Reserved */
    690        case 6: /* Bus timing 0, hardware related, not support now. */
    691        case 7: /* Bus timing 1, hardware related, not support now. */
    692        case 8: /*
    693                 * Output control register, hardware related,
    694                 * not supported for now.
    695                 */
    696        case 9: /* Test. */
    697        case 10 ... 15: /* Reserved */
    698            temp = 0x00;
    699            break;
    700
    701        case 16 ... 28:
    702            if (s->mode & 0x01) { /* Reset mode */
    703                if (addr < 24) {
    704                    temp = s->code_mask[addr - 16];
    705                } else {
    706                    temp = 0x00;
    707                }
    708            } else { /* Operation mode */
    709                temp = s->rx_buff[(s->rxbuf_start + addr - 16) %
    710                       SJA_RCV_BUF_LEN];
    711            }
    712            break;
    713        case SJA_CDR:
    714            temp = s->clock;
    715            break;
    716        default:
    717            temp = 0xff;
    718        }
    719    } else { /* Basic Mode */
    720        switch (addr) {
    721        case SJA_BCAN_CTR: /* Control register, addr 0 */
    722            temp = s->control;
    723            break;
    724        case SJA_BCAN_SR: /* Status register, addr 2 */
    725            temp = s->status_bas;
    726            break;
    727        case SJA_BCAN_IR: /* Interrupt register, addr 3 */
    728            temp = s->interrupt_bas;
    729            s->interrupt_bas = 0;
    730            if (s->rxmsg_cnt) {
    731                s->interrupt_bas |= (1 << 0); /* Receive interrupt. */
    732            }
    733            can_sja_update_bas_irq(s);
    734            break;
    735        case 4:
    736            temp = s->code;
    737            break;
    738        case 5:
    739            temp = s->mask;
    740            break;
    741        case 20 ... 29:
    742            temp = s->rx_buff[(s->rxbuf_start + addr - 20) % SJA_RCV_BUF_LEN];
    743            break;
    744        case 31:
    745            temp = s->clock;
    746            break;
    747        default:
    748            temp = 0xff;
    749            break;
    750        }
    751    }
    752    DPRINTF("read addr 0x%02x, %d bytes, content 0x%02lx\n",
    753            (int)addr, size, (long unsigned int)temp);
    754
    755    return temp;
    756}
    757
    758bool can_sja_can_receive(CanBusClientState *client)
    759{
    760    CanSJA1000State *s = container_of(client, CanSJA1000State, bus_client);
    761
    762    if (s->clock & 0x80) { /* PeliCAN Mode */
    763        if (s->mode & 0x01) { /* reset mode. */
    764            return false;
    765        }
    766    } else { /* BasicCAN mode */
    767        if (s->control & 0x01) {
    768            return false;
    769        }
    770    }
    771
    772    return true; /* always return true, when operation mode */
    773}
    774
    775ssize_t can_sja_receive(CanBusClientState *client, const qemu_can_frame *frames,
    776                        size_t frames_cnt)
    777{
    778    CanSJA1000State *s = container_of(client, CanSJA1000State, bus_client);
    779    static uint8_t rcv[SJA_MSG_MAX_LEN];
    780    int i;
    781    int ret = -1;
    782    const qemu_can_frame *frame = frames;
    783
    784    if (frames_cnt <= 0) {
    785        return 0;
    786    }
    787    if (frame->flags & QEMU_CAN_FRMF_TYPE_FD) {
    788        if (DEBUG_FILTER) {
    789            can_display_msg("[cansja]: ignor fd frame ", frame);
    790        }
    791        return 1;
    792    }
    793
    794    if (DEBUG_FILTER) {
    795        can_display_msg("[cansja]: receive ", frame);
    796    }
    797
    798    if (s->clock & 0x80) { /* PeliCAN Mode */
    799
    800        /* the CAN controller is receiving a message */
    801        s->status_pel |= (1 << 4);
    802
    803        if (can_sja_accept_filter(s, frame) == 0) {
    804            s->status_pel &= ~(1 << 4);
    805            if (DEBUG_FILTER) {
    806                qemu_log("[cansja]: filter rejects message\n");
    807            }
    808            return ret;
    809        }
    810
    811        ret = frame2buff_pel(frame, rcv);
    812        if (ret < 0) {
    813            s->status_pel &= ~(1 << 4);
    814            if (DEBUG_FILTER) {
    815                qemu_log("[cansja]: message store failed\n");
    816            }
    817            return ret; /* maybe not support now. */
    818        }
    819
    820        if (s->rx_cnt + ret > SJA_RCV_BUF_LEN) { /* Data overrun. */
    821            s->status_pel |= (1 << 1); /* Overrun status */
    822            s->interrupt_pel |= (1 << 3);
    823            s->status_pel &= ~(1 << 4);
    824            if (DEBUG_FILTER) {
    825                qemu_log("[cansja]: receive FIFO overrun\n");
    826            }
    827            can_sja_update_pel_irq(s);
    828            return ret;
    829        }
    830        s->rx_cnt += ret;
    831        s->rxmsg_cnt++;
    832        if (DEBUG_FILTER) {
    833            qemu_log("[cansja]: message stored in receive FIFO\n");
    834        }
    835
    836        for (i = 0; i < ret; i++) {
    837            s->rx_buff[(s->rx_ptr++) % SJA_RCV_BUF_LEN] = rcv[i];
    838        }
    839        s->rx_ptr %= SJA_RCV_BUF_LEN; /* update the pointer. */
    840
    841        s->status_pel |= 0x01; /* Set the Receive Buffer Status. DS-p23 */
    842        s->interrupt_pel |= 0x01;
    843        s->status_pel &= ~(1 << 4);
    844        s->status_pel |= (1 << 0);
    845        can_sja_update_pel_irq(s);
    846    } else { /* BasicCAN mode */
    847
    848        /* the CAN controller is receiving a message */
    849        s->status_bas |= (1 << 4);
    850
    851        ret = frame2buff_bas(frame, rcv);
    852        if (ret < 0) {
    853            s->status_bas &= ~(1 << 4);
    854            if (DEBUG_FILTER) {
    855                qemu_log("[cansja]: message store failed\n");
    856            }
    857            return ret; /* maybe not support now. */
    858        }
    859
    860        if (s->rx_cnt + ret > SJA_RCV_BUF_LEN) { /* Data overrun. */
    861            s->status_bas |= (1 << 1); /* Overrun status */
    862            s->status_bas &= ~(1 << 4);
    863            s->interrupt_bas |= (1 << 3);
    864            can_sja_update_bas_irq(s);
    865            if (DEBUG_FILTER) {
    866                qemu_log("[cansja]: receive FIFO overrun\n");
    867            }
    868            return ret;
    869        }
    870        s->rx_cnt += ret;
    871        s->rxmsg_cnt++;
    872
    873        if (DEBUG_FILTER) {
    874            qemu_log("[cansja]: message stored\n");
    875        }
    876
    877        for (i = 0; i < ret; i++) {
    878            s->rx_buff[(s->rx_ptr++) % SJA_RCV_BUF_LEN] = rcv[i];
    879        }
    880        s->rx_ptr %= SJA_RCV_BUF_LEN; /* update the pointer. */
    881
    882        s->status_bas |= 0x01; /* Set the Receive Buffer Status. DS-p15 */
    883        s->status_bas &= ~(1 << 4);
    884        s->interrupt_bas |= (1 << 0);
    885        can_sja_update_bas_irq(s);
    886    }
    887    return 1;
    888}
    889
    890static CanBusClientInfo can_sja_bus_client_info = {
    891    .can_receive = can_sja_can_receive,
    892    .receive = can_sja_receive,
    893};
    894
    895
    896int can_sja_connect_to_bus(CanSJA1000State *s, CanBusState *bus)
    897{
    898    s->bus_client.info = &can_sja_bus_client_info;
    899
    900    if (!bus) {
    901        return -EINVAL;
    902    }
    903
    904    if (can_bus_insert_client(bus, &s->bus_client) < 0) {
    905        return -1;
    906    }
    907
    908    return 0;
    909}
    910
    911void can_sja_disconnect(CanSJA1000State *s)
    912{
    913    can_bus_remove_client(&s->bus_client);
    914}
    915
    916int can_sja_init(CanSJA1000State *s, qemu_irq irq)
    917{
    918    s->irq = irq;
    919
    920    qemu_irq_lower(s->irq);
    921
    922    can_sja_hardware_reset(s);
    923
    924    return 0;
    925}
    926
    927const VMStateDescription vmstate_qemu_can_filter = {
    928    .name = "qemu_can_filter",
    929    .version_id = 1,
    930    .minimum_version_id = 1,
    931    .minimum_version_id_old = 1,
    932    .fields = (VMStateField[]) {
    933        VMSTATE_UINT32(can_id, qemu_can_filter),
    934        VMSTATE_UINT32(can_mask, qemu_can_filter),
    935        VMSTATE_END_OF_LIST()
    936    }
    937};
    938
    939static int can_sja_post_load(void *opaque, int version_id)
    940{
    941    CanSJA1000State *s = opaque;
    942    if (s->clock & 0x80) { /* PeliCAN Mode */
    943        can_sja_update_pel_irq(s);
    944    } else {
    945        can_sja_update_bas_irq(s);
    946    }
    947    return 0;
    948}
    949
    950/* VMState is needed for live migration of QEMU images */
    951const VMStateDescription vmstate_can_sja = {
    952    .name = "can_sja",
    953    .version_id = 1,
    954    .minimum_version_id = 1,
    955    .minimum_version_id_old = 1,
    956    .post_load = can_sja_post_load,
    957    .fields = (VMStateField[]) {
    958        VMSTATE_UINT8(mode, CanSJA1000State),
    959
    960        VMSTATE_UINT8(status_pel, CanSJA1000State),
    961        VMSTATE_UINT8(interrupt_pel, CanSJA1000State),
    962        VMSTATE_UINT8(interrupt_en, CanSJA1000State),
    963        VMSTATE_UINT8(rxmsg_cnt, CanSJA1000State),
    964        VMSTATE_UINT8(rxbuf_start, CanSJA1000State),
    965        VMSTATE_UINT8(clock, CanSJA1000State),
    966
    967        VMSTATE_BUFFER(code_mask, CanSJA1000State),
    968        VMSTATE_BUFFER(tx_buff, CanSJA1000State),
    969
    970        VMSTATE_BUFFER(rx_buff, CanSJA1000State),
    971
    972        VMSTATE_UINT32(rx_ptr, CanSJA1000State),
    973        VMSTATE_UINT32(rx_cnt, CanSJA1000State),
    974
    975        VMSTATE_UINT8(control, CanSJA1000State),
    976
    977        VMSTATE_UINT8(status_bas, CanSJA1000State),
    978        VMSTATE_UINT8(interrupt_bas, CanSJA1000State),
    979        VMSTATE_UINT8(code, CanSJA1000State),
    980        VMSTATE_UINT8(mask, CanSJA1000State),
    981
    982        VMSTATE_STRUCT_ARRAY(filter, CanSJA1000State, 4, 0,
    983                             vmstate_qemu_can_filter, qemu_can_filter),
    984
    985
    986        VMSTATE_END_OF_LIST()
    987    }
    988};