drivers: ethernet: stm32: Enable transmitting with new driver
Use the new API in the transmit method
Signed-off-by: Bjarne von Horn <B.von_horn@wzl.rwth-aachen.de>
diff --git a/drivers/ethernet/eth_stm32_hal.c b/drivers/ethernet/eth_stm32_hal.c
index fc34cfb..9a89cb3 100644
--- a/drivers/ethernet/eth_stm32_hal.c
+++ b/drivers/ethernet/eth_stm32_hal.c
@@ -176,6 +176,20 @@
}
}
}
+
+/* allocate a tx buffer and mark it as used */
+static inline uint16_t allocate_tx_buffer(void)
+{
+ for (;;) {
+ for (uint16_t index = 0; index < ETH_TXBUFNB; index++) {
+ if (!dma_tx_buffer_header[index].used) {
+ dma_tx_buffer_header[index].used = true;
+ return index;
+ }
+ }
+ k_yield();
+ }
+}
#endif /* CONFIG_ETH_STM32_HAL_API_V2 */
#if defined(CONFIG_SOC_SERIES_STM32H7X) || defined(CONFIG_ETH_STM32_HAL_API_V2)
@@ -275,10 +289,16 @@
{
struct eth_stm32_hal_dev_data *dev_data = dev->data;
ETH_HandleTypeDef *heth;
- uint8_t *dma_buffer;
int res;
size_t total_len;
+#if defined(CONFIG_ETH_STM32_HAL_API_V2)
+ size_t remaining_read;
+ struct eth_stm32_tx_context ctx = {.pkt = pkt, .first_tx_buffer_index = 0};
+ struct eth_stm32_tx_buffer_header *buf_header = NULL;
+#else
+ uint8_t *dma_buffer;
__IO ETH_DMADescTypeDef *dma_tx_desc;
+#endif /* CONFIG_ETH_STM32_HAL_API_V2 */
HAL_StatusTypeDef hal_ret = HAL_OK;
#if defined(CONFIG_PTP_CLOCK_STM32_HAL)
bool timestamped_frame;
@@ -299,6 +319,10 @@
k_mutex_lock(&dev_data->tx_mutex, K_FOREVER);
+#if defined(CONFIG_ETH_STM32_HAL_API_V2)
+ ctx.first_tx_buffer_index = allocate_tx_buffer();
+ buf_header = &dma_tx_buffer_header[ctx.first_tx_buffer_index];
+#else /* CONFIG_ETH_STM32_HAL_API_V2 */
#if defined(CONFIG_SOC_SERIES_STM32H7X)
uint32_t cur_tx_desc_idx;
@@ -306,24 +330,52 @@
dma_tx_desc = (ETH_DMADescTypeDef *)heth->TxDescList.TxDesc[cur_tx_desc_idx];
#else
dma_tx_desc = heth->TxDesc;
-#endif
+#endif /* CONFIG_SOC_SERIES_STM32H7X */
while (IS_ETH_DMATXDESC_OWN(dma_tx_desc) != (uint32_t)RESET) {
k_yield();
}
+#endif /* CONFIG_ETH_STM32_HAL_API_V2 */
#if defined(CONFIG_PTP_CLOCK_STM32_HAL)
timestamped_frame = eth_is_ptp_pkt(net_pkt_iface(pkt), pkt);
if (timestamped_frame) {
/* Enable transmit timestamp */
-#if defined(CONFIG_SOC_SERIES_STM32H7X)
+#if defined(CONFIG_ETH_STM32_HAL_API_V2)
+ HAL_ETH_PTP_InsertTxTimestamp(heth);
+#elif defined(CONFIG_SOC_SERIES_STM32H7X)
dma_tx_desc->DESC2 |= ETH_DMATXNDESCRF_TTSE;
#else
dma_tx_desc->Status |= ETH_DMATXDESC_TTSE;
-#endif /* CONFIG_SOC_SERIES_STM32H7X */
+#endif /* CONFIG_ETH_STM32_HAL_API_V2 */
}
#endif /* CONFIG_PTP_CLOCK_STM32_HAL */
+#if defined(CONFIG_ETH_STM32_HAL_API_V2)
+ remaining_read = total_len;
+ /* fill and allocate buffer until remaining data fits in one buffer */
+ while (remaining_read > ETH_STM32_TX_BUF_SIZE) {
+ if (net_pkt_read(pkt, buf_header->tx_buff.buffer, ETH_STM32_TX_BUF_SIZE)) {
+ res = -ENOBUFS;
+ goto error;
+ }
+ const uint16_t next_buffer_id = allocate_tx_buffer();
+
+ buf_header->tx_buff.len = ETH_STM32_TX_BUF_SIZE;
+ /* append new buffer to the linked list */
+ buf_header->tx_buff.next = &dma_tx_buffer_header[next_buffer_id].tx_buff;
+ /* and adjust tail pointer */
+ buf_header = &dma_tx_buffer_header[next_buffer_id];
+ remaining_read -= ETH_STM32_TX_BUF_SIZE;
+ }
+ if (net_pkt_read(pkt, buf_header->tx_buff.buffer, remaining_read)) {
+ res = -ENOBUFS;
+ goto error;
+ }
+ buf_header->tx_buff.len = remaining_read;
+ buf_header->tx_buff.next = NULL;
+
+#else /* CONFIG_ETH_STM32_HAL_API_V2 */
#if defined(CONFIG_SOC_SERIES_STM32H7X)
dma_buffer = dma_tx_buffer[cur_tx_desc_idx];
#else
@@ -341,9 +393,18 @@
tx_buffer_def.buffer = dma_buffer;
tx_buffer_def.len = total_len;
tx_buffer_def.next = NULL;
+#endif /* CONFIG_SOC_SERIES_STM32H7X */
+#endif /* CONFIG_ETH_STM32_HAL_API_V2 */
+
+#if defined(CONFIG_SOC_SERIES_STM32H7X) || defined(CONFIG_ETH_STM32_HAL_API_V2)
tx_config.Length = total_len;
+#if defined(CONFIG_ETH_STM32_HAL_API_V2)
+ tx_config.pData = &ctx;
+ tx_config.TxBuffer = &dma_tx_buffer_header[ctx.first_tx_buffer_index].tx_buff;
+#else
tx_config.TxBuffer = &tx_buffer_def;
+#endif /* CONFIG_ETH_STM32_HAL_API_V2 */
/* Reset TX complete interrupt semaphore before TX request*/
k_sem_reset(&dev_data->tx_int_sem);
@@ -368,8 +429,10 @@
LOG_ERR("HAL_ETH_TransmitIT tx_int_sem take timeout");
res = -EIO;
+#ifndef CONFIG_ETH_STM32_HAL_API_V2
/* Content of the packet could be the reason for timeout */
LOG_HEXDUMP_ERR(dma_buffer, total_len, "eth packet timeout");
+#endif
/* Check for errors */
/* Ethernet device was put in error state */
@@ -422,9 +485,9 @@
res = -EIO;
goto error;
}
-#endif /* CONFIG_SOC_SERIES_STM32H7X */
+#endif /* CONFIG_SOC_SERIES_STM32H7X || CONFIG_ETH_STM32_HAL_API_V2 */
-#if defined(CONFIG_PTP_CLOCK_STM32_HAL)
+#if defined(CONFIG_PTP_CLOCK_STM32_HAL) && !defined(CONFIG_ETH_STM32_HAL_API_V2)
if (timestamped_frame) {
/* Retrieve transmission timestamp from last DMA TX descriptor */
#if defined(CONFIG_SOC_SERIES_STM32H7X)
@@ -484,10 +547,21 @@
net_if_add_tx_timestamp(pkt);
}
-#endif /* CONFIG_PTP_CLOCK_STM32_HAL */
+#endif /* CONFIG_PTP_CLOCK_STM32_HAL && !CONFIG_ETH_STM32_HAL_API_V2 */
res = 0;
error:
+
+#if defined(CONFIG_ETH_STM32_HAL_API_V2)
+ /* free package tx buffer */
+ if (res != 0) {
+ HAL_ETH_TxFreeCallback((uint32_t *)&ctx);
+ } else if (HAL_ETH_ReleaseTxPacket(heth) != HAL_OK) {
+ LOG_ERR("HAL_ETH_ReleaseTxPacket failed");
+ res = -EIO;
+ }
+#endif
+
k_mutex_unlock(&dev_data->tx_mutex);
return res;