| @@ -130,8 +130,9 @@ static int ns_open(struct atm_vcc *vcc); · 129 unmodified lines |
| 130 | static void ns_close(struct atm_vcc *vcc); | 130 | static void ns_close(struct atm_vcc *vcc); |
| 131 | static void fill_tst(ns_dev * card, int n, vc_map * vc); | 131 | static void fill_tst(ns_dev * card, int n, vc_map * vc); |
| 132 | static int ns_send(struct atm_vcc *vcc, struct sk_buff *skb); | 132 | static int ns_send(struct atm_vcc *vcc, struct sk_buff *skb); |
| | 133 | static int ns_send_bh(struct atm_vcc *vcc, struct sk_buff *skb); |
| 133 | static int push_scqe(ns_dev * card, vc_map * vc, scq_info * scq, ns_scqe * tbd, | 134 | static int push_scqe(ns_dev * card, vc_map * vc, scq_info * scq, ns_scqe * tbd, |
| 134 | struct sk_buff *skb); | 135 | struct sk_buff *skb, bool may_sleep); |
| 135 | static void process_tsq(ns_dev * card); | 136 | static void process_tsq(ns_dev * card); |
| 136 | static void drain_scq(ns_dev * card, scq_info * scq, int pos); | 137 | static void drain_scq(ns_dev * card, scq_info * scq, int pos); |
| 137 | static void process_rsq(ns_dev * card); | 138 | static void process_rsq(ns_dev * card); |
| @@ -160,6 +161,7 @@ static const struct atmdev_ops atm_ops = { · 22 unmodified lines |
| 160 | .close = ns_close, | 161 | .close = ns_close, |
| 161 | .ioctl = ns_ioctl, | 162 | .ioctl = ns_ioctl, |
| 162 | .send = ns_send, | 163 | .send = ns_send, |
| | 164 | .send_bh = ns_send_bh, |
| 163 | .phy_put = ns_phy_put, | 165 | .phy_put = ns_phy_put, |
| 164 | .phy_get = ns_phy_get, | 166 | .phy_get = ns_phy_get, |
| 165 | .proc_read = ns_proc_read, | 167 | .proc_read = ns_proc_read, |
| @@ -1620,7 +1622,7 @@ static void fill_tst(ns_dev * card, int n, vc_map * vc) · 1454 unmodified lines |
| 1620 | card->tst_addr = new_tst; | 1622 | card->tst_addr = new_tst; |
| 1621 | } | 1623 | } |
| 1622 | | 1624 | |
| 1623 | static int ns_send(struct atm_vcc *vcc, struct sk_buff *skb) | 1625 | static int _ns_send(struct atm_vcc *vcc, struct sk_buff *skb, bool may_sleep) |
| 1624 | { | 1626 | { |
| 1625 | ns_dev *card; | 1627 | ns_dev *card; |
| 1626 | vc_map *vc; | 1628 | vc_map *vc; |
| @@ -1704,7 +1706,7 @@ static int ns_send(struct atm_vcc *vcc, struct sk_buff *skb) · 77 unmodified lines |
| 1704 | scq = card->scq0; | 1706 | scq = card->scq0; |
| 1705 | } | 1707 | } |
| 1706 | | 1708 | |
| 1707 | if (push_scqe(card, vc, scq, &scqe, skb) != 0) { | 1709 | if (push_scqe(card, vc, scq, &scqe, skb, may_sleep) != 0) { |
| 1708 | atomic_inc(&vcc->stats->tx_err); | 1710 | atomic_inc(&vcc->stats->tx_err); |
| 1709 | dev_kfree_skb_any(skb); | 1711 | dev_kfree_skb_any(skb); |
| 1710 | return -EIO; | 1712 | return -EIO; |
| @@ -1714,8 +1716,18 @@ static int ns_send(struct atm_vcc *vcc, struct sk_buff *skb) · 3 unmodified lines |
| 1714 | return 0; | 1716 | return 0; |
| 1715 | } | 1717 | } |
| 1716 | | 1718 | |
| | 1719 | static int ns_send(struct atm_vcc *vcc, struct sk_buff *skb) |
| | 1720 | { |
| | 1721 | return _ns_send(vcc, skb, true); |
| | 1722 | } |
| | 1723 | |
| | 1724 | static int ns_send_bh(struct atm_vcc *vcc, struct sk_buff *skb) |
| | 1725 | { |
| | 1726 | return _ns_send(vcc, skb, false); |
| | 1727 | } |
| | 1728 | |
| 1717 | static int push_scqe(ns_dev * card, vc_map * vc, scq_info * scq, ns_scqe * tbd, | 1729 | static int push_scqe(ns_dev * card, vc_map * vc, scq_info * scq, ns_scqe * tbd, |
| 1718 | struct sk_buff *skb) | 1730 | struct sk_buff *skb, bool may_sleep) |
| 1719 | { | 1731 | { |
| 1720 | unsigned long flags; | 1732 | unsigned long flags; |
| 1721 | ns_scqe tsr; | 1733 | ns_scqe tsr; |
| @@ -1726,7 +1738,7 @@ static int push_scqe(ns_dev * card, vc_map * vc, scq_info * scq, ns_scqe * tbd, · 4 unmodified lines |
| 1726 | | 1738 | |
| 1727 | spin_lock_irqsave(&scq->lock, flags); | 1739 | spin_lock_irqsave(&scq->lock, flags); |
| 1728 | while (scq->tail == scq->next) { | 1740 | while (scq->tail == scq->next) { |
| 1729 | if (in_interrupt()) { | 1741 | if (!may_sleep) { |
| 1730 | spin_unlock_irqrestore(&scq->lock, flags); | 1742 | spin_unlock_irqrestore(&scq->lock, flags); |
| 1731 | printk("nicstar%d: Error pushing TBD.\n", card->index); | 1743 | printk("nicstar%d: Error pushing TBD.\n", card->index); |
| 1732 | return 1; | 1744 | return 1; |
| @@ -1771,7 +1783,7 @@ static int push_scqe(ns_dev * card, vc_map * vc, scq_info * scq, ns_scqe * tbd, · 38 unmodified lines |
| 1771 | int has_run = 0; | 1783 | int has_run = 0; |
| 1772 | | 1784 | |
| 1773 | while (scq->tail == scq->next) { | 1785 | while (scq->tail == scq->next) { |
| 1774 | if (in_interrupt()) { | 1786 | if (!may_sleep) { |
| 1775 | data = scq_virt_to_bus(scq, scq->next); | 1787 | data = scq_virt_to_bus(scq, scq->next); |
| 1776 | ns_write_sram(card, scq->scd, &data, 1); | 1788 | ns_write_sram(card, scq->scd, &data, 1); |
| 1777 | spin_unlock_irqrestore(&scq->lock, flags); | 1789 | spin_unlock_irqrestore(&scq->lock, flags); |