Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use small lock to protect resources related to ethernet. #15668

Merged
merged 1 commit into from
Jan 24, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 6 additions & 3 deletions arch/arm/src/c5471/c5471_ethernet.c
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@
#include <net/ethernet.h>

#include <nuttx/wdog.h>
#include <nuttx/irq.h>
#include <nuttx/spinlock.h>
#include <nuttx/arch.h>
#include <nuttx/wqueue.h>
#include <nuttx/net/ip.h>
Expand Down Expand Up @@ -299,6 +299,7 @@ struct c5471_driver_s
struct wdog_s c_txtimeout; /* TX timeout timer */
struct work_s c_irqwork; /* For deferring interrupt work to the work queue */
struct work_s c_pollwork; /* For deferring poll work to the work queue */
spinlock_t c_lock; /* Spinlock */

/* Note: According to the C547x documentation: "The software has to
* maintain two pointers to the current RX-CPU and TX-CPU descriptors.
Expand Down Expand Up @@ -1786,7 +1787,7 @@ static int c5471_ifdown(struct net_driver_s *dev)

/* Disable the Ethernet interrupt */

flags = enter_critical_section();
flags = spin_lock_irqsave(&priv->c_lock);
up_disable_irq(C5471_IRQ_ETHER);

/* Disable interrupts going from EIM Module to Interrupt Module. */
Expand All @@ -1809,7 +1810,7 @@ static int c5471_ifdown(struct net_driver_s *dev)
/* Reset the device */

priv->c_bifup = false;
leave_critical_section(flags);
spin_unlock_irqrestore(&priv->c_lock, flags);
return OK;
}

Expand Down Expand Up @@ -2335,6 +2336,8 @@ void arm_netinitialize(void)
#endif
g_c5471[0].c_dev.d_private = g_c5471; /* Used to recover private state from dev */

spin_lock_init(&g_c5471[0].c_lock); /* Initialize spinlock */

/* Register the device with the OS so that socket IOCTLs can be performed */

netdev_register(&g_c5471[0].c_dev, NET_LL_ETHERNET);
Expand Down
34 changes: 20 additions & 14 deletions arch/arm/src/lpc17xx_40xx/lpc17_40_ethernet.c
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@
#include <arpa/inet.h>

#include <nuttx/wdog.h>
#include <nuttx/irq.h>
#include <nuttx/spinlock.h>
#include <nuttx/arch.h>
#include <nuttx/wqueue.h>
#include <nuttx/signal.h>
Expand Down Expand Up @@ -298,6 +298,7 @@ struct lpc17_40_driver_s
struct work_s lp_rxwork; /* RX work continuation */
struct work_s lp_pollwork; /* Poll work continuation */
uint32_t status;
spinlock_t lp_lock; /* Spinlock */

/* This holds the information visible to the NuttX networking layer */

Expand Down Expand Up @@ -424,6 +425,7 @@ static inline void lpc17_40_txdescinit(struct lpc17_40_driver_s *priv);
static inline void lpc17_40_rxdescinit(struct lpc17_40_driver_s *priv);
static inline void lpc17_40_macmode(uint8_t mode);
static void lpc17_40_ethreset(struct lpc17_40_driver_s *priv);
static void lpc17_40_ethreset_nolock(struct lpc17_40_driver_s *priv);

/****************************************************************************
* Private Functions
Expand Down Expand Up @@ -1003,14 +1005,14 @@ static void lpc17_40_rxdone_work(void *arg)
* lp-txpending TX underrun state is in effect.
*/

flags = enter_critical_section();
flags = spin_lock_irqsave(&priv->lp_lock);
if (!priv->lp_txpending)
{
priv->lp_inten |= ETH_RXINTS;
lpc17_40_putreg(priv->lp_inten, LPC17_40_ETH_INTEN);
}

leave_critical_section(flags);
spin_unlock_irqrestore(&priv->lp_lock, flags);
}

/****************************************************************************
Expand Down Expand Up @@ -1534,7 +1536,7 @@ static int lpc17_40_ifdown(struct net_driver_s *dev)

/* Disable the Ethernet interrupt */

flags = enter_critical_section();
flags = spin_lock_irqsave(&priv->lp_lock);
up_disable_irq(LPC17_40_IRQ_ETH);

/* Cancel the TX timeout timers */
Expand All @@ -1543,9 +1545,9 @@ static int lpc17_40_ifdown(struct net_driver_s *dev)

/* Reset the device and mark it as down. */

lpc17_40_ethreset(priv);
lpc17_40_ethreset_nolock(priv);
priv->lp_ifup = false;
leave_critical_section(flags);
spin_unlock_irqrestore(&priv->lp_lock, flags);
return OK;
}

Expand Down Expand Up @@ -2909,14 +2911,8 @@ static inline void lpc17_40_macmode(uint8_t mode)
*
****************************************************************************/

static void lpc17_40_ethreset(struct lpc17_40_driver_s *priv)
static void lpc17_40_ethreset_nolock(struct lpc17_40_driver_s *priv)
{
irqstate_t flags;

/* Reset the MAC */

flags = enter_critical_section();

/* Put the MAC into the reset state */

lpc17_40_putreg((ETH_MAC1_TXRST | ETH_MAC1_MCSTXRST | ETH_MAC1_RXRST |
Expand Down Expand Up @@ -2965,7 +2961,15 @@ static void lpc17_40_ethreset(struct lpc17_40_driver_s *priv)
/* Clear any pending interrupts (shouldn't be any) */

lpc17_40_putreg(0xffffffff, LPC17_40_ETH_INTCLR);
leave_critical_section(flags);
}

static void lpc17_40_ethreset(struct lpc17_40_driver_s *priv)
{
irqstate_t flags;

flags = spin_lock_irqsave(&priv->lp_lock);
lpc17_40_ethreset_nolock(priv);
spin_unlock_irqrestore(&priv->lp_lock, flags);
}

/****************************************************************************
Expand Down Expand Up @@ -3033,6 +3037,8 @@ static inline int lpc17_40_ethinitialize(int intf)
#endif
priv->lp_dev.d_private = priv; /* Used to recover private state from dev */

spin_lock_init(&priv->lp_lock); /* Initialize spinlock */

#if CONFIG_LPC17_40_NINTERFACES > 1
# error "A mechanism to associate base address an IRQ with an interface is needed"
priv->lp_base = ??; /* Ethernet controller base address */
Expand Down
9 changes: 6 additions & 3 deletions arch/arm/src/lpc43xx/lpc43_ethernet.c
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@
#include <arpa/inet.h>

#include <nuttx/arch.h>
#include <nuttx/irq.h>
#include <nuttx/spinlock.h>
#include <nuttx/queue.h>
#include <nuttx/wdog.h>
#include <nuttx/wqueue.h>
Expand Down Expand Up @@ -512,6 +512,7 @@ struct lpc43_ethmac_s
struct wdog_s txtimeout; /* TX timeout timer */
struct work_s irqwork; /* For deferring work to the work queue */
struct work_s pollwork; /* For deferring work to the work queue */
spinlock_t lock; /* Spinlock */

/* This holds the information visible to the NuttX network */

Expand Down Expand Up @@ -2126,7 +2127,7 @@ static int lpc43_ifdown(struct net_driver_s *dev)

/* Disable the Ethernet interrupt */

flags = enter_critical_section();
flags = spin_lock_irqsave(&priv->lock);
up_disable_irq(LPC43M4_IRQ_ETHERNET);

/* Cancel the TX timeout timers */
Expand All @@ -2143,7 +2144,7 @@ static int lpc43_ifdown(struct net_driver_s *dev)
/* Mark the device "down" */

priv->ifup = false;
leave_critical_section(flags);
spin_unlock_irqrestore(&priv->lock, flags);
return OK;
}

Expand Down Expand Up @@ -3607,6 +3608,8 @@ static inline int lpc43_ethinitialize(void)
#endif
priv->dev.d_private = &g_lpc43ethmac; /* Used to recover private state from dev */

spin_lock_init(&priv->lock); /* Initialize spinlock */

/* Configure GPIO pins to support Ethernet */

lpc43_ethgpioconfig(priv);
Expand Down
13 changes: 8 additions & 5 deletions arch/arm/src/lpc54xx/lpc54_ethernet.c
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,7 @@
#include <arpa/inet.h>

#include <nuttx/arch.h>
#include <nuttx/irq.h>
#include <nuttx/spinlock.h>
#include <nuttx/queue.h>
#include <nuttx/wdog.h>
#include <nuttx/wqueue.h>
Expand Down Expand Up @@ -297,6 +297,7 @@ struct lpc54_ethdriver_s
struct work_s eth_pollwork; /* For deferring poll work to the work queue */
struct work_s eth_timeoutwork; /* For deferring timeout work to the work queue */
struct sq_queue_s eth_freebuf; /* Free packet buffers */
spinlock_t lock; /* Spinlock */

/* Ring state */

Expand Down Expand Up @@ -1450,7 +1451,7 @@ static void lpc54_eth_interrupt_work(void *arg)
lpc54_eth_channel_work(priv, 1);
}

/* Un-lock the network and re-enable Ethernet interrupts */
/* Un-eth_lock the network and re-enable Ethernet interrupts */

net_unlock();
up_enable_irq(LPC54_IRQ_ETHERNET);
Expand Down Expand Up @@ -2001,7 +2002,7 @@ static int lpc54_eth_ifdown(struct net_driver_s *dev)

/* Disable the Ethernet interrupt */

flags = enter_critical_section();
flags = spin_lock_irqsave(&priv->eth_lock);
up_disable_irq(LPC54_IRQ_ETHERNET);

/* Cancel the TX timeout timers */
Expand Down Expand Up @@ -2040,14 +2041,14 @@ static int lpc54_eth_ifdown(struct net_driver_s *dev)
if (ret < 0)
{
nerr("ERROR: lpc54_phy_reset failed: %d\n", ret);
leave_critical_section(flags);
spin_unlock_irqrestore(&priv->eth_lock, flags);
return ret;
}

/* Mark the device "down" */

priv->eth_bifup = 0;
leave_critical_section(flags);
spin_unlock_irqrestore(&priv->eth_lock, flags);
return OK;
}

Expand Down Expand Up @@ -2881,6 +2882,8 @@ void arm_netinitialize(void)
#endif
priv->eth_dev.d_private = &g_ethdriver; /* Used to recover private state from dev */

spin_lock_init(&priv->eth_lock); /* Initialize spinlock */

/* Configure GPIO pins to support Ethernet */

/* Common MIIM interface */
Expand Down
9 changes: 6 additions & 3 deletions arch/arm/src/stm32f7/stm32_ethernet.c
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@
#include <arpa/inet.h>

#include <nuttx/arch.h>
#include <nuttx/irq.h>
#include <nuttx/spinlock.h>
#include <nuttx/queue.h>
#include <nuttx/wdog.h>
#include <nuttx/wqueue.h>
Expand Down Expand Up @@ -614,6 +614,7 @@ struct stm32_ethmac_s
struct wdog_s txtimeout; /* TX timeout timer */
struct work_s irqwork; /* For deferring interrupt work to the work queue */
struct work_s pollwork; /* For deferring poll work to the work queue */
spinlock_t lock; /* Spinlock */

/* This holds the information visible to the NuttX network */

Expand Down Expand Up @@ -2359,7 +2360,7 @@ static int stm32_ifdown(struct net_driver_s *dev)

/* Disable the Ethernet interrupt */

flags = enter_critical_section();
flags = spin_lock_irqsave(&priv->lock);
up_disable_irq(STM32_IRQ_ETH);

/* Cancel the TX timeout timers */
Expand All @@ -2376,7 +2377,7 @@ static int stm32_ifdown(struct net_driver_s *dev)
/* Mark the device "down" */

priv->ifup = false;
leave_critical_section(flags);
spin_unlock_irqrestore(&priv->lock, flags);
return OK;
}

Expand Down Expand Up @@ -3931,6 +3932,8 @@ int stm32_ethinitialize(int intf)
priv->dev.d_private = g_stm32ethmac; /* Used to recover private state from dev */
priv->intf = intf; /* Remember the interface number */

spin_lock_init(&priv->lock); /* Initialize spinlock */

stm32_get_uniqueid(uid);
crc = crc64(uid, 12);

Expand Down
9 changes: 6 additions & 3 deletions arch/arm/src/stm32h5/stm32_ethernet.c
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@
#include <arpa/inet.h>

#include <nuttx/arch.h>
#include <nuttx/irq.h>
#include <nuttx/spinlock.h>
#include <nuttx/queue.h>
#include <nuttx/wdog.h>
#include <nuttx/wqueue.h>
Expand Down Expand Up @@ -613,6 +613,7 @@ struct stm32_ethmac_s
struct wdog_s txtimeout; /* TX timeout timer */
struct work_s irqwork; /* For deferring interrupt work to the work queue */
struct work_s pollwork; /* For deferring poll work to the work queue */
spinlock_t lock; /* Spinlock */

/* This holds the information visible to the NuttX network */

Expand Down Expand Up @@ -2472,7 +2473,7 @@ static int stm32_ifdown(struct net_driver_s *dev)

/* Disable the Ethernet interrupt */

flags = enter_critical_section();
flags = spin_lock_irqsave(&priv->lock);
up_disable_irq(STM32_IRQ_ETH);

/* Cancel the TX timeout timers */
Expand All @@ -2489,7 +2490,7 @@ static int stm32_ifdown(struct net_driver_s *dev)
/* Mark the device "down" */

priv->ifup = false;
leave_critical_section(flags);
spin_unlock_irqrestore(&priv->lock, flags);
return OK;
}

Expand Down Expand Up @@ -4192,6 +4193,8 @@ static inline int stm32_ethinitialize(int intf)
priv->dev.d_private = g_stm32ethmac; /* Used to recover private state */
priv->intf = intf; /* Remember the interface number */

spin_lock_init(&priv->lock); /* Initialize spinlock */

stm32_get_uniqueid(uid);
crc = crc64(uid, 12);

Expand Down
9 changes: 6 additions & 3 deletions arch/arm/src/stm32h7/stm32_ethernet.c
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@
#include <arpa/inet.h>

#include <nuttx/arch.h>
#include <nuttx/irq.h>
#include <nuttx/spinlock.h>
#include <nuttx/queue.h>
#include <nuttx/wdog.h>
#include <nuttx/wqueue.h>
Expand Down Expand Up @@ -614,6 +614,7 @@ struct stm32_ethmac_s
struct wdog_s txtimeout; /* TX timeout timer */
struct work_s irqwork; /* For deferring interrupt work to the work queue */
struct work_s pollwork; /* For deferring poll work to the work queue */
spinlock_t lock; /* Spinlock */

/* This holds the information visible to the NuttX network */

Expand Down Expand Up @@ -2473,7 +2474,7 @@ static int stm32_ifdown(struct net_driver_s *dev)

/* Disable the Ethernet interrupt */

flags = enter_critical_section();
flags = spin_lock_irqsave(&priv->lock);
up_disable_irq(STM32_IRQ_ETH);

/* Cancel the TX timeout timers */
Expand All @@ -2490,7 +2491,7 @@ static int stm32_ifdown(struct net_driver_s *dev)
/* Mark the device "down" */

priv->ifup = false;
leave_critical_section(flags);
spin_unlock_irqrestore(&priv->lock, flags);
return OK;
}

Expand Down Expand Up @@ -4191,6 +4192,8 @@ static inline int stm32_ethinitialize(int intf)
priv->dev.d_private = g_stm32ethmac; /* Used to recover private state */
priv->intf = intf; /* Remember the interface number */

spin_lock_init(&priv->lock); /* Initialize spinlock */

stm32_get_uniqueid(uid);
crc = crc64(uid, 12);

Expand Down
Loading
Loading