static void adapter_hard_reset(elp_device * adapter) { int timeout; CHECK_NULL(adapter); /* * take FLSH and ATTN high */ OUTB(CONTROL_ATTN|CONTROL_FLSH, adapter->io_addr+PORT_CONTROL); /* * wait for a little bit */ for (timeout = jiffies + 20; jiffies <= timeout; ) ; /* * now take them low */ OUTB(0, adapter->io_addr+PORT_CONTROL); /* * wait for a little bit */ for (timeout = jiffies + 20; jiffies <= timeout; ) ; /* * now hang around until the board gets it's act together */ for (timeout = jiffies + (100 * 15); jiffies <= timeout; ) if (GET_ASF() != ASF_PCB_END) break; }
static int send_pcb(struct net_device *dev, pcb_struct * pcb) { int i; unsigned long timeout; elp_device *adapter = dev->priv; unsigned long flags; check_3c505_dma(dev); if (adapter->dmaing && adapter->current_dma.direction == 0) return FALSE; /* Avoid contention */ if (test_and_set_bit(1, &adapter->send_pcb_semaphore)) { if (elp_debug >= 3) { printk(KERN_DEBUG "%s: send_pcb entered while threaded\n", dev->name); } return FALSE; } /* * load each byte into the command register and * wait for the HCRE bit to indicate the adapter * had read the byte */ set_hsf(dev, 0); if (send_pcb_slow(dev->base_addr, pcb->command)) goto abort; spin_lock_irqsave(&adapter->lock, flags); if (send_pcb_fast(dev->base_addr, pcb->length)) goto sti_abort; for (i = 0; i < pcb->length; i++) { if (send_pcb_fast(dev->base_addr, pcb->data.raw[i])) goto sti_abort; } outb_control(adapter->hcr_val | 3, dev); /* signal end of PCB */ outb_command(2 + pcb->length, dev->base_addr); /* now wait for the acknowledgement */ spin_unlock_irqrestore(&adapter->lock, flags); for (timeout = jiffies + 5*HZ/100; time_before(jiffies, timeout);) { switch (GET_ASF(dev->base_addr)) { case ASF_PCB_ACK: adapter->send_pcb_semaphore = 0; return TRUE; case ASF_PCB_NAK: #ifdef ELP_DEBUG printk(KERN_DEBUG "%s: send_pcb got NAK\n", dev->name); #endif goto abort; } } if (elp_debug >= 1) printk(KERN_DEBUG "%s: timeout waiting for PCB acknowledge (status %02x)\n", dev->name, inb_status(dev->base_addr)); goto abort; sti_abort: spin_unlock_irqrestore(&adapter->lock, flags); abort: adapter->send_pcb_semaphore = 0; return FALSE; }
static int send_pcb(elp_device * adapter, pcb_struct * pcb) { int i; int cont; int retry = 0; int timeout; CHECK_NULL(pcb); CHECK_NULL(adapter); if (pcb->length > MAX_PCB_DATA) printk(invalid_pcb_msg, pcb->length, filename, __LINE__); while (1) { cont = 1; /* * load each byte into the command register and * wait for the HCRE bit to indicate the adapter * had read the byte */ SET_HSF(0); OUTB(pcb->command, (adapter->io_addr)+PORT_COMMAND); cont = WAIT_HCRE(5); if (cont) { OUTB(pcb->length, (adapter->io_addr)+PORT_COMMAND); cont = WAIT_HCRE(2); } for (i = 0; cont && (i < pcb->length); i++) { OUTB(pcb->data.raw[i], (adapter->io_addr)+PORT_COMMAND); cont = WAIT_HCRE(2); } /* set the host status bits to indicate end of PCB */ /* send the total packet length as well */ /* wait for the adapter to indicate that it has read the PCB */ if (cont) { SET_HSF(HSF_PCB_END); OUTB(2+pcb->length, adapter->io_addr+PORT_COMMAND); timeout = jiffies + 6; while (jiffies < timeout) { i = GET_ASF(); if ((i == ASF_PCB_ACK) || (i == ASF_PCB_NAK)) break; } if (jiffies >= timeout) TIMEOUT_MSG(); if (i == ASF_PCB_ACK) { SET_HSF(0); return TRUE; } else if (i == ASF_PCB_NAK) { SET_HSF(0); printk("%s: PCB send was NAKed\n", adapter->name); { int to = jiffies + 5; while (jiffies < to) ; } } } if (elp_debug >= 2) printk("%s: NAK/timeout on send PCB\n", adapter->name); if ((retry++ & 7) == 0) printk("%s: retry #%i on send PCB\n", adapter->name, retry); } return FALSE; }
static bool send_pcb(struct net_device *dev, pcb_struct * pcb) { int i; unsigned long timeout; elp_device *adapter = netdev_priv(dev); unsigned long flags; check_3c505_dma(dev); if (adapter->dmaing && adapter->current_dma.direction == 0) return false; if (test_and_set_bit(1, &adapter->send_pcb_semaphore)) { if (elp_debug >= 3) { pr_debug("%s: send_pcb entered while threaded\n", dev->name); } return false; } set_hsf(dev, 0); if (send_pcb_slow(dev->base_addr, pcb->command)) goto abort; spin_lock_irqsave(&adapter->lock, flags); if (send_pcb_fast(dev->base_addr, pcb->length)) goto sti_abort; for (i = 0; i < pcb->length; i++) { if (send_pcb_fast(dev->base_addr, pcb->data.raw[i])) goto sti_abort; } outb_control(adapter->hcr_val | 3, dev); outb_command(2 + pcb->length, dev->base_addr); spin_unlock_irqrestore(&adapter->lock, flags); for (timeout = jiffies + 5*HZ/100; time_before(jiffies, timeout);) { switch (GET_ASF(dev->base_addr)) { case ASF_PCB_ACK: adapter->send_pcb_semaphore = 0; return true; case ASF_PCB_NAK: #ifdef ELP_DEBUG pr_debug("%s: send_pcb got NAK\n", dev->name); #endif goto abort; } } if (elp_debug >= 1) pr_debug("%s: timeout waiting for PCB acknowledge (status %02x)\n", dev->name, inb_status(dev->base_addr)); goto abort; sti_abort: spin_unlock_irqrestore(&adapter->lock, flags); abort: adapter->send_pcb_semaphore = 0; return false; }