Skip to content

Commit

Permalink
fjes: raise_intr_rxdata_task
Browse files Browse the repository at this point in the history
This patch add raise_intr_rxdata_task.
Extended Socket Network Device is shared memory
based, so someone's transmission denotes other's
reception. In order to notify receivers, sender
has to raise interruption of receivers.
raise_intr_rxdata_task does this work.

Signed-off-by: Taku Izumi <izumi.taku@jp.fujitsu.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
  • Loading branch information
Taku Izumi authored and David S. Miller committed Aug 24, 2015
1 parent 9acf51c commit b772b9d
Show file tree
Hide file tree
Showing 2 changed files with 67 additions and 0 deletions.
4 changes: 4 additions & 0 deletions drivers/net/fjes/fjes.h
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,10 @@ struct fjes_adapter {

bool irq_registered;

struct workqueue_struct *txrx_wq;

struct work_struct raise_intr_rxdata_task;

struct fjes_hw hw;
};

Expand Down
63 changes: 63 additions & 0 deletions drivers/net/fjes/fjes_main.c
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,7 @@ static int fjes_close(struct net_device *);
static int fjes_setup_resources(struct fjes_adapter *);
static void fjes_free_resources(struct fjes_adapter *);
static netdev_tx_t fjes_xmit_frame(struct sk_buff *, struct net_device *);
static void fjes_raise_intr_rxdata_task(struct work_struct *);
static irqreturn_t fjes_intr(int, void*);

static int fjes_acpi_add(struct acpi_device *);
Expand Down Expand Up @@ -276,6 +277,8 @@ static int fjes_close(struct net_device *netdev)

fjes_free_irq(adapter);

cancel_work_sync(&adapter->raise_intr_rxdata_task);

fjes_hw_wait_epstop(hw);

fjes_free_resources(adapter);
Expand Down Expand Up @@ -404,6 +407,54 @@ static void fjes_free_resources(struct fjes_adapter *adapter)
}
}

static void fjes_raise_intr_rxdata_task(struct work_struct *work)
{
struct fjes_adapter *adapter = container_of(work,
struct fjes_adapter, raise_intr_rxdata_task);
struct fjes_hw *hw = &adapter->hw;
enum ep_partner_status pstatus;
int max_epid, my_epid, epid;

my_epid = hw->my_epid;
max_epid = hw->max_epid;

for (epid = 0; epid < max_epid; epid++)
hw->ep_shm_info[epid].tx_status_work = 0;

for (epid = 0; epid < max_epid; epid++) {
if (epid == my_epid)
continue;

pstatus = fjes_hw_get_partner_ep_status(hw, epid);
if (pstatus == EP_PARTNER_SHARED) {
hw->ep_shm_info[epid].tx_status_work =
hw->ep_shm_info[epid].tx.info->v1i.tx_status;

if (hw->ep_shm_info[epid].tx_status_work ==
FJES_TX_DELAY_SEND_PENDING) {
hw->ep_shm_info[epid].tx.info->v1i.tx_status =
FJES_TX_DELAY_SEND_NONE;
}
}
}

for (epid = 0; epid < max_epid; epid++) {
if (epid == my_epid)
continue;

pstatus = fjes_hw_get_partner_ep_status(hw, epid);
if ((hw->ep_shm_info[epid].tx_status_work ==
FJES_TX_DELAY_SEND_PENDING) &&
(pstatus == EP_PARTNER_SHARED) &&
!(hw->ep_shm_info[epid].rx.info->v1i.rx_status)) {
fjes_hw_raise_interrupt(hw, epid,
REG_ICTL_MASK_RX_DATA);
}
}

usleep_range(500, 1000);
}

static int fjes_tx_send(struct fjes_adapter *adapter, int dest,
void *data, size_t len)
{
Expand All @@ -416,6 +467,9 @@ static int fjes_tx_send(struct fjes_adapter *adapter, int dest,

adapter->hw.ep_shm_info[dest].tx.info->v1i.tx_status =
FJES_TX_DELAY_SEND_PENDING;
if (!work_pending(&adapter->raise_intr_rxdata_task))
queue_work(adapter->txrx_wq,
&adapter->raise_intr_rxdata_task);

retval = 0;
return retval;
Expand Down Expand Up @@ -630,6 +684,11 @@ static int fjes_probe(struct platform_device *plat_dev)
adapter->force_reset = false;
adapter->open_guard = false;

adapter->txrx_wq = create_workqueue(DRV_NAME "/txrx");

INIT_WORK(&adapter->raise_intr_rxdata_task,
fjes_raise_intr_rxdata_task);

res = platform_get_resource(plat_dev, IORESOURCE_MEM, 0);
hw->hw_res.start = res->start;
hw->hw_res.size = res->end - res->start + 1;
Expand Down Expand Up @@ -669,6 +728,10 @@ static int fjes_remove(struct platform_device *plat_dev)
struct fjes_adapter *adapter = netdev_priv(netdev);
struct fjes_hw *hw = &adapter->hw;

cancel_work_sync(&adapter->raise_intr_rxdata_task);
if (adapter->txrx_wq)
destroy_workqueue(adapter->txrx_wq);

unregister_netdev(netdev);

fjes_hw_exit(hw);
Expand Down

0 comments on commit b772b9d

Please sign in to comment.