+static void
+ramips_ring_setup(struct raeth_priv *re)
+{
+ int len;
+ int i;
+
+ len = NUM_TX_DESC * sizeof(struct ramips_tx_dma);
+ memset(re->tx, 0, len);
+
+ for (i = 0; i < NUM_TX_DESC; i++) {
+ struct ramips_tx_dma *txd;
+
+ txd = &re->tx[i];
+ txd->txd4 = TX_DMA_QN(3) | TX_DMA_PN(1);
+ txd->txd2 = TX_DMA_LSO | TX_DMA_DONE;
+
+ if (re->tx_skb[i] != NULL) {
+ netdev_warn(re->netdev,
+ "dirty skb for TX desc %d\n", i);
+ re->tx_skb[i] = NULL;
+ }
+ }
+
+ len = NUM_RX_DESC * sizeof(struct ramips_rx_dma);
+ memset(re->rx, 0, len);
+
+ for (i = 0; i < NUM_RX_DESC; i++) {
+ dma_addr_t dma_addr;
+
+ BUG_ON(re->rx_skb[i] == NULL);
+ dma_addr = dma_map_single(&re->netdev->dev, re->rx_skb[i]->data,
+ MAX_RX_LENGTH, DMA_FROM_DEVICE);
+ re->rx_dma[i] = dma_addr;
+ re->rx[i].rxd1 = (unsigned int) dma_addr;
+ re->rx[i].rxd2 = RX_DMA_LSO;
+ }
+
+ /* flush descriptors */
+ wmb();
+}
+
+static void
+ramips_ring_cleanup(struct raeth_priv *re)
+{
+ int i;
+
+ for (i = 0; i < NUM_RX_DESC; i++)
+ if (re->rx_skb[i])
+ dma_unmap_single(&re->netdev->dev, re->rx_dma[i],
+ MAX_RX_LENGTH, DMA_FROM_DEVICE);
+
+ for (i = 0; i < NUM_TX_DESC; i++)
+ if (re->tx_skb[i]) {
+ dev_kfree_skb_any(re->tx_skb[i]);
+ re->tx_skb[i] = NULL;
+ }
+}
+