drivers: ethernet: litex: use tx interrupt

use tx interrupt to check, if we can send something,
instead of checking the register periodically.

Signed-off-by: Fin Maaß <f.maass@vogl-electronic.com>
This commit is contained in:
Fin Maaß 2025-04-04 13:26:04 +02:00 committed by Benjamin Cabé
commit 86a52d9254

View file

@ -27,7 +27,7 @@ LOG_MODULE_REGISTER(LOG_MODULE_NAME);
#include "eth.h" #include "eth.h"
#define MAX_TX_FAILURE 100 #define MAX_TX_FAILURE K_MSEC(100)
#define ETH_LITEX_SLOT_SIZE 0x0800 #define ETH_LITEX_SLOT_SIZE 0x0800
@ -36,6 +36,7 @@ struct eth_litex_dev_data {
uint8_t mac_addr[6]; uint8_t mac_addr[6];
uint8_t txslot; uint8_t txslot;
struct k_mutex tx_mutex; struct k_mutex tx_mutex;
struct k_sem sem_tx_ready;
}; };
struct eth_litex_config { struct eth_litex_config {
@ -64,12 +65,10 @@ static int eth_initialize(const struct device *dev)
struct eth_litex_dev_data *context = dev->data; struct eth_litex_dev_data *context = dev->data;
k_mutex_init(&context->tx_mutex); k_mutex_init(&context->tx_mutex);
k_sem_init(&context->sem_tx_ready, 1, 1);
config->config_func(dev); config->config_func(dev);
/* TX event is disabled because it isn't used by this driver */
litex_write8(0, config->tx_ev_enable_addr);
if (config->random_mac_address) { if (config->random_mac_address) {
/* generate random MAC address */ /* generate random MAC address */
gen_random_mac(context->mac_addr, 0x10, 0xe2, 0xd5); gen_random_mac(context->mac_addr, 0x10, 0xe2, 0xd5);
@ -83,7 +82,7 @@ static int eth_tx(const struct device *dev, struct net_pkt *pkt)
uint16_t len; uint16_t len;
struct eth_litex_dev_data *context = dev->data; struct eth_litex_dev_data *context = dev->data;
const struct eth_litex_config *config = dev->config; const struct eth_litex_config *config = dev->config;
int attempts = 0; int ret;
k_mutex_lock(&context->tx_mutex, K_FOREVER); k_mutex_lock(&context->tx_mutex, K_FOREVER);
@ -97,13 +96,10 @@ static int eth_tx(const struct device *dev, struct net_pkt *pkt)
litex_write16(len, config->tx_length_addr); litex_write16(len, config->tx_length_addr);
/* wait for the device to be ready to transmit */ /* wait for the device to be ready to transmit */
while (litex_read8(config->tx_ready_addr) == 0) { ret = k_sem_take(&context->sem_tx_ready, MAX_TX_FAILURE);
if (attempts++ == MAX_TX_FAILURE) { if (ret < 0) {
goto error; goto error;
} };
k_sleep(K_MSEC(1));
}
/* start transmitting */ /* start transmitting */
litex_write8(1, config->tx_start_addr); litex_write8(1, config->tx_start_addr);
@ -166,12 +162,13 @@ static void eth_rx(const struct device *port)
static void eth_irq_handler(const struct device *port) static void eth_irq_handler(const struct device *port)
{ {
struct eth_litex_dev_data *context = port->data;
const struct eth_litex_config *config = port->config; const struct eth_litex_config *config = port->config;
/* check sram reader events (tx) */ /* check sram reader events (tx) */
if (litex_read8(config->tx_ev_pending_addr) & BIT(0)) { if (litex_read8(config->tx_ev_pending_addr) & BIT(0)) {
/* TX event is not enabled nor used by this driver; ack just k_sem_give(&context->sem_tx_ready);
* in case if some rogue TX event appeared
*/ /* ack reader irq */
litex_write8(BIT(0), config->tx_ev_pending_addr); litex_write8(BIT(0), config->tx_ev_pending_addr);
} }
@ -205,8 +202,14 @@ static int eth_set_config(const struct device *dev, enum ethernet_config_type ty
static int eth_start(const struct device *dev) static int eth_start(const struct device *dev)
{ {
struct eth_litex_dev_data *context = dev->data;
const struct eth_litex_config *config = dev->config; const struct eth_litex_config *config = dev->config;
if (litex_read8(config->tx_ready_addr)) {
k_sem_give(&context->sem_tx_ready);
}
litex_write8(1, config->tx_ev_enable_addr);
litex_write8(1, config->rx_ev_enable_addr); litex_write8(1, config->rx_ev_enable_addr);
litex_write8(BIT(0), config->tx_ev_pending_addr); litex_write8(BIT(0), config->tx_ev_pending_addr);
@ -219,6 +222,7 @@ static int eth_stop(const struct device *dev)
{ {
const struct eth_litex_config *config = dev->config; const struct eth_litex_config *config = dev->config;
litex_write8(0, config->tx_ev_enable_addr);
litex_write8(0, config->rx_ev_enable_addr); litex_write8(0, config->rx_ev_enable_addr);
return 0; return 0;