int destroyed;
rwlock_t destroyed_lock;
+
+ struct tasklet_struct tasklet;
};
struct sdp_device {
sizeof(*tx_sa) - offsetof(typeof(*tx_sa), busy));
}
-static inline void rx_ring_unlock(struct sdp_rx_ring *rx_ring,
- unsigned long *flags)
+static inline void rx_ring_unlock(struct sdp_rx_ring *rx_ring)
{
- read_unlock_irqrestore(&rx_ring->destroyed_lock, *flags);
+ read_unlock_bh(&rx_ring->destroyed_lock);
}
-static inline int rx_ring_trylock(struct sdp_rx_ring *rx_ring,
- unsigned long *flags)
+static inline int rx_ring_trylock(struct sdp_rx_ring *rx_ring)
{
- read_lock_irqsave(&rx_ring->destroyed_lock, *flags);
+ read_lock_bh(&rx_ring->destroyed_lock);
if (rx_ring->destroyed) {
- rx_ring_unlock(rx_ring, flags);
+ rx_ring_unlock(rx_ring);
return 0;
}
return 1;
static inline void rx_ring_destroy_lock(struct sdp_rx_ring *rx_ring)
{
- unsigned long flags;
-
- write_lock_irqsave(&rx_ring->destroyed_lock, flags);
+ write_lock_bh(&rx_ring->destroyed_lock);
rx_ring->destroyed = 1;
- write_unlock_irqrestore(&rx_ring->destroyed_lock, flags);
+ write_unlock_bh(&rx_ring->destroyed_lock);
}
static inline struct sdp_sock *sdp_sk(const struct sock *sk)
{
struct sock *sk = cq_context;
struct sdp_sock *ssk = sdp_sk(sk);
- unsigned long flags;
- int wc_processed = 0;
- int credits_before;
if (cq != ssk->rx_ring.cq) {
sdp_dbg(sk, "cq = %p, ssk->cq = %p\n", cq, ssk->rx_ring.cq);
sdp_prf(sk, NULL, "rx irq");
- if (!rx_ring_trylock(&ssk->rx_ring, &flags)) {
+ tasklet_hi_schedule(&ssk->rx_ring.tasklet);
+}
+
+static void sdp_process_rx(unsigned long data)
+{
+ struct sdp_sock *ssk = (struct sdp_sock *)data;
+ struct sock *sk = &ssk->isk.sk;
+ int wc_processed = 0;
+ int credits_before;
+
+ if (!rx_ring_trylock(&ssk->rx_ring)) {
sdp_dbg(&ssk->isk.sk, "ring destroyed. not polling it\n");
return;
}
}
sdp_arm_rx_cq(sk);
- rx_ring_unlock(&ssk->rx_ring, &flags);
+ rx_ring_unlock(&ssk->rx_ring);
}
static void sdp_rx_ring_purge(struct sdp_sock *ssk)
sdp_sk(&ssk->isk.sk)->rx_ring.cq = rx_cq;
INIT_WORK(&ssk->rx_comp_work, sdp_rx_comp_work);
+ tasklet_init(&ssk->rx_ring.tasklet, sdp_process_rx,
+ (unsigned long) ssk);
sdp_arm_rx_cq(&ssk->isk.sk);