コード例 #1
0
static netdev_tx_t
kni_loopback_xmit(struct sk_buff *skb,
                  struct net_device *dev)
{
  skb_orphan(skb);
  if (skb->vlan_tci == 1){
    //Need to be sent to the fastpath
    kni_net_tx(skb, dev);
  }else{
    /* it's OK to use per_cpu_ptr() because BHs are off */
    netif_rx(skb);
  }
  
  return NETDEV_TX_OK;
}
コード例 #2
0
ファイル: kni_net.c プロジェクト: RIFTIO/RIFT.ware
/*
 * RX: loopback with enqueue/dequeue fifos and sk buffer copies.
 */
static void
kni_net_rx_lo_fifo_skb(struct kni_dev *kni)
{
	unsigned ret;
	uint32_t len;
	unsigned i, num_rq, num_fq, num;
	struct rte_kni_mbuf *kva;
	struct rte_kni_mbuf *va[MBUF_BURST_SZ];
	void * data_kva;

	struct sk_buff *skb;
	struct net_device *dev = kni->net_dev;

	/* Get the number of entries in rx_q */
	num_rq = kni_fifo_count(kni->rx_q);

	/* Get the number of free entries in free_q */
	num_fq = kni_fifo_free_count(kni->free_q);

	/* Calculate the number of entries to dequeue from rx_q */
	num = min(num_rq, num_fq);
	num = min(num, (unsigned)MBUF_BURST_SZ);

	/* Return if no entry to dequeue from rx_q */
	if (num == 0)
		return;

	/* Burst dequeue mbufs from rx_q */
	ret = kni_fifo_get(kni->rx_q, (void **)va, num);
	if (ret == 0)
		return;

	/* Copy mbufs to sk buffer and then call tx interface */
	for (i = 0; i < num; i++) {
		kva = (void *)va[i] - kni->mbuf_va + kni->mbuf_kva;
		len = kva->data_len;
		data_kva = kva->buf_addr + kva->data_off - kni->mbuf_va +
				kni->mbuf_kva;

		skb = dev_alloc_skb(len + 2);
		if (skb == NULL)
			KNI_ERR("Out of mem, dropping pkts\n");
		else {
                  /* Align IP on 16B boundary */
                  skb_reserve(skb, 2);
                  memcpy(skb_put(skb, len), data_kva, len);
                  skb->dev = dev;
                  skb->ip_summed = CHECKSUM_UNNECESSARY;
                  dev_kfree_skb(skb);
		}

		/* Simulate real usage, allocate/copy skb twice */
		skb = dev_alloc_skb(len + 2);
		if (skb == NULL) {
			KNI_ERR("Out of mem, dropping pkts\n");
			kni->stats.rx_dropped++;
		}
		else {
                  /* Align IP on 16B boundary */
			skb_reserve(skb, 2);
			memcpy(skb_put(skb, len), data_kva, len);
			skb->dev = dev;
			skb->ip_summed = CHECKSUM_UNNECESSARY;

			kni->stats.rx_bytes += len;
			kni->stats.rx_packets++;

			/* call tx interface */
			kni_net_tx(skb, dev);
		}
	}

	/* enqueue all the mbufs from rx_q into free_q */
	ret = kni_fifo_put(kni->free_q, (void **)&va, num);
	if (ret != num)
		/* Failing should not happen */
		KNI_ERR("Fail to enqueue mbufs into free_q\n");
}