static void usb_urb_complete(struct urb *urb) { struct usb_data_stream *stream = urb->context; int ptype = usb_pipetype(urb->pipe); int i; u8 *b; dev_dbg_ratelimited(&stream->udev->dev, "%s: %s urb completed status=%d length=%d/%d pack_num=%d errors=%d\n", __func__, ptype == PIPE_ISOCHRONOUS ? "isoc" : "bulk", urb->status, urb->actual_length, urb->transfer_buffer_length, urb->number_of_packets, urb->error_count); switch (urb->status) { case 0: /* success */ case -ETIMEDOUT: /* NAK */ break; case -ECONNRESET: /* kill */ case -ENOENT: case -ESHUTDOWN: return; default: /* error */ dev_dbg_ratelimited(&stream->udev->dev, "%s: urb completition failed=%d\n", __func__, urb->status); break; } b = (u8 *) urb->transfer_buffer; switch (ptype) { case PIPE_ISOCHRONOUS: for (i = 0; i < urb->number_of_packets; i++) { if (urb->iso_frame_desc[i].status != 0) dev_dbg(&stream->udev->dev, "%s: iso frame descriptor has an error=%d\n", __func__, urb->iso_frame_desc[i].status); else if (urb->iso_frame_desc[i].actual_length > 0) stream->complete(stream, b + urb->iso_frame_desc[i].offset, urb->iso_frame_desc[i].actual_length); urb->iso_frame_desc[i].status = 0; urb->iso_frame_desc[i].actual_length = 0; } break; case PIPE_BULK: if (urb->actual_length > 0) stream->complete(stream, b, urb->actual_length); break; default: dev_err(&stream->udev->dev, "%s: unknown endpoint type in completition handler\n", KBUILD_MODNAME); return; } usb_submit_urb(urb, GFP_ATOMIC); }
static void mlxsw_pci_cqe_rdq_handle(struct mlxsw_pci *mlxsw_pci, struct mlxsw_pci_queue *q, u16 consumer_counter_limit, enum mlxsw_pci_cqe_v cqe_v, char *cqe) { struct pci_dev *pdev = mlxsw_pci->pdev; struct mlxsw_pci_queue_elem_info *elem_info; char *wqe; struct sk_buff *skb; struct mlxsw_rx_info rx_info; u16 byte_count; int err; elem_info = mlxsw_pci_queue_elem_info_consumer_get(q); skb = elem_info->u.sdq.skb; if (!skb) return; wqe = elem_info->elem; mlxsw_pci_wqe_frag_unmap(mlxsw_pci, wqe, 0, DMA_FROM_DEVICE); if (q->consumer_counter++ != consumer_counter_limit) dev_dbg_ratelimited(&pdev->dev, "Consumer counter does not match limit in RDQ\n"); if (mlxsw_pci_cqe_lag_get(cqe_v, cqe)) { rx_info.is_lag = true; rx_info.u.lag_id = mlxsw_pci_cqe_lag_id_get(cqe_v, cqe); rx_info.lag_port_index = mlxsw_pci_cqe_lag_subport_get(cqe_v, cqe); } else { rx_info.is_lag = false; rx_info.u.sys_port = mlxsw_pci_cqe_system_port_get(cqe); } rx_info.trap_id = mlxsw_pci_cqe_trap_id_get(cqe); byte_count = mlxsw_pci_cqe_byte_count_get(cqe); if (mlxsw_pci_cqe_crc_get(cqe_v, cqe)) byte_count -= ETH_FCS_LEN; skb_put(skb, byte_count); mlxsw_core_skb_receive(mlxsw_pci->core, skb, &rx_info); memset(wqe, 0, q->elem_size); err = mlxsw_pci_rdq_skb_alloc(mlxsw_pci, elem_info); if (err) dev_dbg_ratelimited(&pdev->dev, "Failed to alloc skb for RDQ\n"); /* Everything is set up, ring doorbell to pass elem to HW */ q->producer_counter++; mlxsw_pci_queue_doorbell_producer_ring(mlxsw_pci, q); return; }
/* Issues a cmd to cmd processor and waits for cmd completion */ static int bdc_issue_cmd(struct bdc *bdc, u32 cmd_sc, u32 param0, u32 param1, u32 param2) { u32 timeout = BDC_CMD_TIMEOUT; u32 cmd_status; u32 temp; bdc_writel(bdc->regs, BDC_CMDPAR0, param0); bdc_writel(bdc->regs, BDC_CMDPAR1, param1); bdc_writel(bdc->regs, BDC_CMDPAR2, param2); /* Issue the cmd */ /* Make sure the cmd params are written before asking HW to exec cmd */ wmb(); bdc_writel(bdc->regs, BDC_CMDSC, cmd_sc | BDC_CMD_CWS | BDC_CMD_SRD); do { temp = bdc_readl(bdc->regs, BDC_CMDSC); dev_dbg_ratelimited(bdc->dev, "cmdsc=%x", temp); cmd_status = BDC_CMD_CST(temp); if (cmd_status != BDC_CMDS_BUSY) { dev_dbg(bdc->dev, "command completed cmd_sts:%x\n", cmd_status); return cmd_status; } udelay(1); } while (timeout--); dev_err(bdc->dev, "command operation timedout cmd_status=%d\n", cmd_status); return cmd_status; }
int serial8250_request_dma(struct uart_8250_port *p) { struct uart_8250_dma *dma = p->dma; dma_cap_mask_t mask; /* Default slave configuration parameters */ dma->rxconf.direction = DMA_DEV_TO_MEM; dma->rxconf.src_addr_width = DMA_SLAVE_BUSWIDTH_1_BYTE; dma->rxconf.src_addr = p->port.mapbase + UART_RX; dma->txconf.direction = DMA_MEM_TO_DEV; dma->txconf.dst_addr_width = DMA_SLAVE_BUSWIDTH_1_BYTE; dma->txconf.dst_addr = p->port.mapbase + UART_TX; dma_cap_zero(mask); dma_cap_set(DMA_SLAVE, mask); /* Get a channel for RX */ dma->rxchan = dma_request_slave_channel_compat(mask, dma->fn, dma->rx_param, p->port.dev, "rx"); if (!dma->rxchan) return -ENODEV; dmaengine_slave_config(dma->rxchan, &dma->rxconf); /* Get a channel for TX */ dma->txchan = dma_request_slave_channel_compat(mask, dma->fn, dma->tx_param, p->port.dev, "tx"); if (!dma->txchan) { dma_release_channel(dma->rxchan); return -ENODEV; } dmaengine_slave_config(dma->txchan, &dma->txconf); /* RX buffer */ if (!dma->rx_size) dma->rx_size = PAGE_SIZE; dma->rx_buf = dma_alloc_coherent(dma->rxchan->device->dev, dma->rx_size, &dma->rx_addr, GFP_KERNEL); if (!dma->rx_buf) { dma_release_channel(dma->rxchan); dma_release_channel(dma->txchan); return -ENOMEM; } /* TX buffer */ dma->tx_addr = dma_map_single(dma->txchan->device->dev, p->port.state->xmit.buf, UART_XMIT_SIZE, DMA_TO_DEVICE); dev_dbg_ratelimited(p->port.dev, "got both dma channels\n"); return 0; }
static void mlxsw_pci_cqe_rdq_handle(struct mlxsw_pci *mlxsw_pci, struct mlxsw_pci_queue *q, u16 consumer_counter_limit, char *cqe) { struct pci_dev *pdev = mlxsw_pci->pdev; struct mlxsw_pci_queue_elem_info *elem_info; char *wqe; struct sk_buff *skb; struct mlxsw_rx_info rx_info; u16 byte_count; int err; elem_info = mlxsw_pci_queue_elem_info_consumer_get(q); skb = elem_info->u.sdq.skb; if (!skb) return; wqe = elem_info->elem; mlxsw_pci_wqe_frag_unmap(mlxsw_pci, wqe, 0, DMA_FROM_DEVICE); if (q->consumer_counter++ != consumer_counter_limit) dev_dbg_ratelimited(&pdev->dev, "Consumer counter does not match limit in RDQ\n"); /* We do not support lag now */ if (mlxsw_pci_cqe_lag_get(cqe)) goto drop; rx_info.sys_port = mlxsw_pci_cqe_system_port_get(cqe); rx_info.trap_id = mlxsw_pci_cqe_trap_id_get(cqe); byte_count = mlxsw_pci_cqe_byte_count_get(cqe); if (mlxsw_pci_cqe_crc_get(cqe)) byte_count -= ETH_FCS_LEN; skb_put(skb, byte_count); mlxsw_core_skb_receive(mlxsw_pci->core, skb, &rx_info); put_new_skb: memset(wqe, 0, q->elem_size); err = mlxsw_pci_rdq_skb_alloc(mlxsw_pci, elem_info); if (err && net_ratelimit()) dev_dbg(&pdev->dev, "Failed to alloc skb for RDQ\n"); /* Everything is set up, ring doorbell to pass elem to HW */ q->producer_counter++; mlxsw_pci_queue_doorbell_producer_ring(mlxsw_pci, q); return; drop: dev_kfree_skb_any(skb); goto put_new_skb; }
static int bcm2835_spi_transfer_one_poll(struct spi_master *master, struct spi_device *spi, struct spi_transfer *tfr, u32 cs, unsigned long long xfer_time_us) { struct bcm2835_spi *bs = spi_master_get_devdata(master); unsigned long timeout; /* enable HW block without interrupts */ bcm2835_wr(bs, BCM2835_SPI_CS, cs | BCM2835_SPI_CS_TA); /* fill in the fifo before timeout calculations * if we are interrupted here, then the data is * getting transferred by the HW while we are interrupted */ bcm2835_wr_fifo_blind(bs, BCM2835_SPI_FIFO_SIZE); /* set the timeout */ timeout = jiffies + BCM2835_SPI_POLLING_JIFFIES; /* loop until finished the transfer */ while (bs->rx_len) { /* fill in tx fifo with remaining data */ bcm2835_wr_fifo(bs); /* read from fifo as much as possible */ bcm2835_rd_fifo(bs); /* if there is still data pending to read * then check the timeout */ if (bs->rx_len && time_after(jiffies, timeout)) { dev_dbg_ratelimited(&spi->dev, "timeout period reached: jiffies: %lu remaining tx/rx: %d/%d - falling back to interrupt mode\n", jiffies - timeout, bs->tx_len, bs->rx_len); /* fall back to interrupt mode */ return bcm2835_spi_transfer_one_irq(master, spi, tfr, cs, false); } } /* Transfer complete - reset SPI HW */ bcm2835_spi_reset_hw(master); /* and return without waiting for completion */ return 0; }
static int bcm2835aux_spi_transfer_one_poll(struct spi_master *master, struct spi_device *spi, struct spi_transfer *tfr) { struct bcm2835aux_spi *bs = spi_master_get_devdata(master); unsigned long timeout; /* update statistics */ bs->count_transfer_polling++; /* configure spi */ bcm2835aux_wr(bs, BCM2835_AUX_SPI_CNTL1, bs->cntl[1]); bcm2835aux_wr(bs, BCM2835_AUX_SPI_CNTL0, bs->cntl[0]); /* set the timeout to at least 2 jiffies */ timeout = jiffies + 2 + HZ * polling_limit_us / 1000000; /* loop until finished the transfer */ while (bs->rx_len) { /* do common fifo handling */ bcm2835aux_spi_transfer_helper(bs); /* there is still data pending to read check the timeout */ if (bs->rx_len && time_after(jiffies, timeout)) { dev_dbg_ratelimited(&spi->dev, "timeout period reached: jiffies: %lu remaining tx/rx: %d/%d - falling back to interrupt mode\n", jiffies - timeout, bs->tx_len, bs->rx_len); /* forward to interrupt handler */ bs->count_transfer_irq_after_poll++; return __bcm2835aux_spi_transfer_one_irq(master, spi, tfr); } } /* and return without waiting for completion */ return 0; }
long pmem_direct_access(struct block_device *bdev, sector_t sector, void __pmem **kaddr, pfn_t *pfn, long size) { struct pmem_device *pmem = bdev->bd_queue->queuedata; resource_size_t offset = sector * 512 + pmem->data_offset; if (unlikely(is_bad_pmem(&pmem->bb, sector, size))) return -EIO; /* * Limit dax to a single page at a time given vmalloc()-backed * in the nfit_test case. */ if (get_nfit_res(pmem->phys_addr + offset)) { struct page *page; *kaddr = pmem->virt_addr + offset; page = vmalloc_to_page(pmem->virt_addr + offset); *pfn = page_to_pfn_t(page); dev_dbg_ratelimited(disk_to_dev(bdev->bd_disk)->parent, "%s: sector: %#llx pfn: %#lx\n", __func__, (unsigned long long) sector, page_to_pfn(page)); return PAGE_SIZE; } *kaddr = pmem->virt_addr + offset; *pfn = phys_to_pfn_t(pmem->phys_addr + offset, pmem->pfn_flags); /* * If badblocks are present, limit known good range to the * requested range. */ if (unlikely(pmem->bb.count)) return size; return pmem->size - pmem->pfn_pad - offset; }
static void mlxsw_pci_cqe_sdq_handle(struct mlxsw_pci *mlxsw_pci, struct mlxsw_pci_queue *q, u16 consumer_counter_limit, char *cqe) { struct pci_dev *pdev = mlxsw_pci->pdev; struct mlxsw_pci_queue_elem_info *elem_info; char *wqe; struct sk_buff *skb; int i; spin_lock(&q->lock); elem_info = mlxsw_pci_queue_elem_info_consumer_get(q); skb = elem_info->u.sdq.skb; wqe = elem_info->elem; for (i = 0; i < MLXSW_PCI_WQE_SG_ENTRIES; i++) mlxsw_pci_wqe_frag_unmap(mlxsw_pci, wqe, i, DMA_TO_DEVICE); dev_kfree_skb_any(skb); elem_info->u.sdq.skb = NULL; if (q->consumer_counter++ != consumer_counter_limit) dev_dbg_ratelimited(&pdev->dev, "Consumer counter does not match limit in SDQ\n"); spin_unlock(&q->lock); }
void serial8250_release_dma(struct uart_8250_port *p) { struct uart_8250_dma *dma = p->dma; if (!dma) return; /* Release RX resources */ dmaengine_terminate_sync(dma->rxchan); dma_free_coherent(dma->rxchan->device->dev, dma->rx_size, dma->rx_buf, dma->rx_addr); dma_release_channel(dma->rxchan); dma->rxchan = NULL; /* Release TX resources */ dmaengine_terminate_sync(dma->txchan); dma_unmap_single(dma->txchan->device->dev, dma->tx_addr, UART_XMIT_SIZE, DMA_TO_DEVICE); dma_release_channel(dma->txchan); dma->txchan = NULL; dma->tx_running = 0; dev_dbg_ratelimited(p->port.dev, "dma channels released\n"); }
int serial8250_request_dma(struct uart_8250_port *p) { struct uart_8250_dma *dma = p->dma; phys_addr_t rx_dma_addr = dma->rx_dma_addr ? dma->rx_dma_addr : p->port.mapbase; phys_addr_t tx_dma_addr = dma->tx_dma_addr ? dma->tx_dma_addr : p->port.mapbase; dma_cap_mask_t mask; struct dma_slave_caps caps; int ret; /* Default slave configuration parameters */ dma->rxconf.direction = DMA_DEV_TO_MEM; dma->rxconf.src_addr_width = DMA_SLAVE_BUSWIDTH_1_BYTE; dma->rxconf.src_addr = rx_dma_addr + UART_RX; dma->txconf.direction = DMA_MEM_TO_DEV; dma->txconf.dst_addr_width = DMA_SLAVE_BUSWIDTH_1_BYTE; dma->txconf.dst_addr = tx_dma_addr + UART_TX; dma_cap_zero(mask); dma_cap_set(DMA_SLAVE, mask); /* Get a channel for RX */ dma->rxchan = dma_request_slave_channel_compat(mask, dma->fn, dma->rx_param, p->port.dev, "rx"); if (!dma->rxchan) return -ENODEV; /* 8250 rx dma requires dmaengine driver to support pause/terminate */ ret = dma_get_slave_caps(dma->rxchan, &caps); if (ret) goto release_rx; if (!caps.cmd_pause || !caps.cmd_terminate || caps.residue_granularity == DMA_RESIDUE_GRANULARITY_DESCRIPTOR) { ret = -EINVAL; goto release_rx; } dmaengine_slave_config(dma->rxchan, &dma->rxconf); /* Get a channel for TX */ dma->txchan = dma_request_slave_channel_compat(mask, dma->fn, dma->tx_param, p->port.dev, "tx"); if (!dma->txchan) { ret = -ENODEV; goto release_rx; } /* 8250 tx dma requires dmaengine driver to support terminate */ ret = dma_get_slave_caps(dma->txchan, &caps); if (ret) goto err; if (!caps.cmd_terminate) { ret = -EINVAL; goto err; } dmaengine_slave_config(dma->txchan, &dma->txconf); /* RX buffer */ if (!dma->rx_size) dma->rx_size = PAGE_SIZE; dma->rx_buf = dma_alloc_coherent(dma->rxchan->device->dev, dma->rx_size, &dma->rx_addr, GFP_KERNEL); if (!dma->rx_buf) { ret = -ENOMEM; goto err; } /* TX buffer */ dma->tx_addr = dma_map_single(dma->txchan->device->dev, p->port.state->xmit.buf, UART_XMIT_SIZE, DMA_TO_DEVICE); if (dma_mapping_error(dma->txchan->device->dev, dma->tx_addr)) { dma_free_coherent(dma->rxchan->device->dev, dma->rx_size, dma->rx_buf, dma->rx_addr); ret = -ENOMEM; goto err; } dev_dbg_ratelimited(p->port.dev, "got both dma channels\n"); return 0; err: dma_release_channel(dma->txchan); release_rx: dma_release_channel(dma->rxchan); return ret; }