mcp251xfd-tx.c 5.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205
  1. // SPDX-License-Identifier: GPL-2.0
  2. //
  3. // mcp251xfd - Microchip MCP251xFD Family CAN controller driver
  4. //
  5. // Copyright (c) 2019, 2020, 2021 Pengutronix,
  6. // Marc Kleine-Budde <[email protected]>
  7. //
  8. // Based on:
  9. //
  10. // CAN bus driver for Microchip 25XXFD CAN Controller with SPI Interface
  11. //
  12. // Copyright (c) 2019 Martin Sperl <[email protected]>
  13. //
  14. #include <asm/unaligned.h>
  15. #include <linux/bitfield.h>
  16. #include "mcp251xfd.h"
  17. static inline struct
  18. mcp251xfd_tx_obj *mcp251xfd_get_tx_obj_next(struct mcp251xfd_tx_ring *tx_ring)
  19. {
  20. u8 tx_head;
  21. tx_head = mcp251xfd_get_tx_head(tx_ring);
  22. return &tx_ring->obj[tx_head];
  23. }
  24. static void
  25. mcp251xfd_tx_obj_from_skb(const struct mcp251xfd_priv *priv,
  26. struct mcp251xfd_tx_obj *tx_obj,
  27. const struct sk_buff *skb,
  28. unsigned int seq)
  29. {
  30. const struct canfd_frame *cfd = (struct canfd_frame *)skb->data;
  31. struct mcp251xfd_hw_tx_obj_raw *hw_tx_obj;
  32. union mcp251xfd_tx_obj_load_buf *load_buf;
  33. u8 dlc;
  34. u32 id, flags;
  35. int len_sanitized = 0, len;
  36. if (cfd->can_id & CAN_EFF_FLAG) {
  37. u32 sid, eid;
  38. sid = FIELD_GET(MCP251XFD_REG_FRAME_EFF_SID_MASK, cfd->can_id);
  39. eid = FIELD_GET(MCP251XFD_REG_FRAME_EFF_EID_MASK, cfd->can_id);
  40. id = FIELD_PREP(MCP251XFD_OBJ_ID_EID_MASK, eid) |
  41. FIELD_PREP(MCP251XFD_OBJ_ID_SID_MASK, sid);
  42. flags = MCP251XFD_OBJ_FLAGS_IDE;
  43. } else {
  44. id = FIELD_PREP(MCP251XFD_OBJ_ID_SID_MASK, cfd->can_id);
  45. flags = 0;
  46. }
  47. /* Use the MCP2518FD mask even on the MCP2517FD. It doesn't
  48. * harm, only the lower 7 bits will be transferred into the
  49. * TEF object.
  50. */
  51. flags |= FIELD_PREP(MCP251XFD_OBJ_FLAGS_SEQ_MCP2518FD_MASK, seq);
  52. if (cfd->can_id & CAN_RTR_FLAG)
  53. flags |= MCP251XFD_OBJ_FLAGS_RTR;
  54. else
  55. len_sanitized = canfd_sanitize_len(cfd->len);
  56. /* CANFD */
  57. if (can_is_canfd_skb(skb)) {
  58. if (cfd->flags & CANFD_ESI)
  59. flags |= MCP251XFD_OBJ_FLAGS_ESI;
  60. flags |= MCP251XFD_OBJ_FLAGS_FDF;
  61. if (cfd->flags & CANFD_BRS)
  62. flags |= MCP251XFD_OBJ_FLAGS_BRS;
  63. dlc = can_fd_len2dlc(cfd->len);
  64. } else {
  65. dlc = can_get_cc_dlc((struct can_frame *)cfd,
  66. priv->can.ctrlmode);
  67. }
  68. flags |= FIELD_PREP(MCP251XFD_OBJ_FLAGS_DLC_MASK, dlc);
  69. load_buf = &tx_obj->buf;
  70. if (priv->devtype_data.quirks & MCP251XFD_QUIRK_CRC_TX)
  71. hw_tx_obj = &load_buf->crc.hw_tx_obj;
  72. else
  73. hw_tx_obj = &load_buf->nocrc.hw_tx_obj;
  74. put_unaligned_le32(id, &hw_tx_obj->id);
  75. put_unaligned_le32(flags, &hw_tx_obj->flags);
  76. /* Copy data */
  77. memcpy(hw_tx_obj->data, cfd->data, cfd->len);
  78. /* Clear unused data at end of CAN frame */
  79. if (MCP251XFD_SANITIZE_CAN && len_sanitized) {
  80. int pad_len;
  81. pad_len = len_sanitized - cfd->len;
  82. if (pad_len)
  83. memset(hw_tx_obj->data + cfd->len, 0x0, pad_len);
  84. }
  85. /* Number of bytes to be written into the RAM of the controller */
  86. len = sizeof(hw_tx_obj->id) + sizeof(hw_tx_obj->flags);
  87. if (MCP251XFD_SANITIZE_CAN)
  88. len += round_up(len_sanitized, sizeof(u32));
  89. else
  90. len += round_up(cfd->len, sizeof(u32));
  91. if (priv->devtype_data.quirks & MCP251XFD_QUIRK_CRC_TX) {
  92. u16 crc;
  93. mcp251xfd_spi_cmd_crc_set_len_in_ram(&load_buf->crc.cmd,
  94. len);
  95. /* CRC */
  96. len += sizeof(load_buf->crc.cmd);
  97. crc = mcp251xfd_crc16_compute(&load_buf->crc, len);
  98. put_unaligned_be16(crc, (void *)load_buf + len);
  99. /* Total length */
  100. len += sizeof(load_buf->crc.crc);
  101. } else {
  102. len += sizeof(load_buf->nocrc.cmd);
  103. }
  104. tx_obj->xfer[0].len = len;
  105. }
  106. static int mcp251xfd_tx_obj_write(const struct mcp251xfd_priv *priv,
  107. struct mcp251xfd_tx_obj *tx_obj)
  108. {
  109. return spi_async(priv->spi, &tx_obj->msg);
  110. }
  111. static bool mcp251xfd_tx_busy(const struct mcp251xfd_priv *priv,
  112. struct mcp251xfd_tx_ring *tx_ring)
  113. {
  114. if (mcp251xfd_get_tx_free(tx_ring) > 0)
  115. return false;
  116. netif_stop_queue(priv->ndev);
  117. /* Memory barrier before checking tx_free (head and tail) */
  118. smp_mb();
  119. if (mcp251xfd_get_tx_free(tx_ring) == 0) {
  120. netdev_dbg(priv->ndev,
  121. "Stopping tx-queue (tx_head=0x%08x, tx_tail=0x%08x, len=%d).\n",
  122. tx_ring->head, tx_ring->tail,
  123. tx_ring->head - tx_ring->tail);
  124. return true;
  125. }
  126. netif_start_queue(priv->ndev);
  127. return false;
  128. }
  129. netdev_tx_t mcp251xfd_start_xmit(struct sk_buff *skb,
  130. struct net_device *ndev)
  131. {
  132. struct mcp251xfd_priv *priv = netdev_priv(ndev);
  133. struct mcp251xfd_tx_ring *tx_ring = priv->tx;
  134. struct mcp251xfd_tx_obj *tx_obj;
  135. unsigned int frame_len;
  136. u8 tx_head;
  137. int err;
  138. if (can_dev_dropped_skb(ndev, skb))
  139. return NETDEV_TX_OK;
  140. if (mcp251xfd_tx_busy(priv, tx_ring))
  141. return NETDEV_TX_BUSY;
  142. tx_obj = mcp251xfd_get_tx_obj_next(tx_ring);
  143. mcp251xfd_tx_obj_from_skb(priv, tx_obj, skb, tx_ring->head);
  144. /* Stop queue if we occupy the complete TX FIFO */
  145. tx_head = mcp251xfd_get_tx_head(tx_ring);
  146. tx_ring->head++;
  147. if (mcp251xfd_get_tx_free(tx_ring) == 0)
  148. netif_stop_queue(ndev);
  149. frame_len = can_skb_get_frame_len(skb);
  150. err = can_put_echo_skb(skb, ndev, tx_head, frame_len);
  151. if (!err)
  152. netdev_sent_queue(priv->ndev, frame_len);
  153. err = mcp251xfd_tx_obj_write(priv, tx_obj);
  154. if (err)
  155. goto out_err;
  156. return NETDEV_TX_OK;
  157. out_err:
  158. netdev_err(priv->ndev, "ERROR in %s: %d\n", __func__, err);
  159. return NETDEV_TX_OK;
  160. }