diff --git a/kernel/drivers/net/can/rockchip/rockchip_canfd.c b/kernel/drivers/net/can/rockchip/rockchip_canfd.c index f28f4165bd..818ac06de9 100644 --- a/kernel/drivers/net/can/rockchip/rockchip_canfd.c +++ b/kernel/drivers/net/can/rockchip/rockchip_canfd.c @@ -292,8 +292,6 @@ static int set_normal_mode(struct net_device *ndev) val = rockchip_canfd_read(rcan, CAN_MODE); val |= WORK_MODE; - if (rcan->mode >= ROCKCHIP_CAN_MODE && rcan->txtorx) - val |= MODE_RXSTX; rockchip_canfd_write(rcan, CAN_MODE, val); netdev_dbg(ndev, "%s MODE=0x%08x\n", __func__, @@ -499,7 +497,7 @@ static void rockchip_canfd_tx_err_delay_work(struct work_struct *work) rockchip_canfd_write(rcan, CAN_CMD, CAN_TX0_REQ); schedule_delayed_work(&rcan->tx_err_work, 1); } else if (rcan->txtorx && rcan->mode >= ROCKCHIP_CAN_MODE && id & CAN_EFF_FLAG) { - schedule_delayed_work(&rcan->tx_err_work, 1); //rpdzkj + schedule_delayed_work(&rcan->tx_err_work, 1); } } @@ -552,6 +550,11 @@ static int rockchip_canfd_start_xmit(struct sk_buff *skb, dlc |= TX_FD_BRS_ENABLE; } + if (rcan->txtorx && rcan->mode >= ROCKCHIP_CAN_MODE && cf->can_id & CAN_EFF_FLAG) + rockchip_canfd_write(rcan, CAN_MODE, rockchip_canfd_read(rcan, CAN_MODE) | MODE_RXSTX); + else + rockchip_canfd_write(rcan, CAN_MODE, rockchip_canfd_read(rcan, CAN_MODE) & (~MODE_RXSTX)); + if (!rcan->txtorx && rcan->mode >= ROCKCHIP_CAN_MODE && cf->can_id & CAN_EFF_FLAG) { /* Two frames are sent consecutively. * Before the first frame is tx finished, @@ -618,10 +621,12 @@ static int rockchip_canfd_rx(struct net_device *ndev) if (rcan->txtorx) { if (rockchip_canfd_read(rcan, CAN_TX_CHECK_FIC) & FORMAT_MASK) { ret = rockchip_canfd_read(rcan, CAN_TXID) & CAN_SFF_MASK; - if (id_rockchip_canfd == ret) { + if ((id_rockchip_canfd == ret) && !(dlc & FORMAT_MASK)) { rockchip_canfd_write(rcan, CAN_TX_CHECK_FIC, ts | CAN_TX0_REQ); return 1; + } else { + return 1; } } } @@ -724,8 +729,9 @@ static int rockchip_canfd_err(struct net_device *ndev, u32 isr) } if (rcan->can.state >= CAN_STATE_BUS_OFF || - ((sta_reg & 0x20) == 0x20)) + ((sta_reg & 0x20) == 0x20)) { can_bus_off(ndev); + } stats->rx_packets++; stats->rx_bytes += cf->can_dlc; @@ -757,9 +763,11 @@ static irqreturn_t rockchip_canfd_interrupt(int irq, void *dev_id) if (rcan->txtorx && rcan->mode >= ROCKCHIP_CAN_MODE && dlc & FORMAT_MASK) { cancel_delayed_work(&rcan->tx_err_work); rockchip_canfd_write(rcan, CAN_TX_CHECK_FIC, FORMAT_MASK); - quota = (rockchip_canfd_read(rcan, CAN_RXFC) & - rcan->rx_fifo_mask) >> - rcan->rx_fifo_shift; + do { + quota = (rockchip_canfd_read(rcan, CAN_RXFC) & + rcan->rx_fifo_mask) >> + rcan->rx_fifo_shift; + } while (quota == 0); if (quota) { while (work_done < quota) work_done += rockchip_canfd_rx(ndev); diff --git a/kernel/net/can/raw.c b/kernel/net/can/raw.c index 069657f681..a55ac5a757 100644 --- a/kernel/net/can/raw.c +++ b/kernel/net/can/raw.c @@ -819,7 +819,7 @@ static int raw_sendmsg(struct socket *sock, struct msghdr *msg, size_t size) skb->sk = sk; skb->priority = sk->sk_priority; - err = can_send(skb, ro->loopback); + err = can_send(skb, 0); dev_put(dev);