#include <rte_udp.h>
#include <rte_sctp.h>
#include <rte_arp.h>
+#include <rte_spinlock.h>
#include "iotlb.h"
#include "vhost.h"
}
vq = dev->virtqueue[queue_id];
+
+ rte_spinlock_lock(&vq->access_lock);
+
if (unlikely(vq->enabled == 0))
- return 0;
+ goto out_access_unlock;
if (dev->features & (1ULL << VIRTIO_F_IOMMU_PLATFORM))
vhost_user_iotlb_rd_lock(vq);
offsetof(struct vring_used, idx),
sizeof(vq->used->idx));
- vhost_vring_call(vq);
+ vhost_vring_call(dev, vq);
out:
if (dev->features & (1ULL << VIRTIO_F_IOMMU_PLATFORM))
vhost_user_iotlb_rd_unlock(vq);
+out_access_unlock:
+ rte_spinlock_unlock(&vq->access_lock);
+
return count;
}
}
vq = dev->virtqueue[queue_id];
+
+ rte_spinlock_lock(&vq->access_lock);
+
if (unlikely(vq->enabled == 0))
- return 0;
+ goto out_access_unlock;
if (dev->features & (1ULL << VIRTIO_F_IOMMU_PLATFORM))
vhost_user_iotlb_rd_lock(vq);
if (likely(vq->shadow_used_idx)) {
flush_shadow_used_ring(dev, vq);
- vhost_vring_call(vq);
+ vhost_vring_call(dev, vq);
}
out:
if (dev->features & (1ULL << VIRTIO_F_IOMMU_PLATFORM))
vhost_user_iotlb_rd_unlock(vq);
+out_access_unlock:
+ rte_spinlock_unlock(&vq->access_lock);
+
return pkt_idx;
}
}
}
-#define RARP_PKT_SIZE 64
-
-static int
-make_rarp_packet(struct rte_mbuf *rarp_mbuf, const struct ether_addr *mac)
-{
- struct ether_hdr *eth_hdr;
- struct arp_hdr *rarp;
-
- if (rarp_mbuf->buf_len < 64) {
- RTE_LOG(WARNING, VHOST_DATA,
- "failed to make RARP; mbuf size too small %u (< %d)\n",
- rarp_mbuf->buf_len, RARP_PKT_SIZE);
- return -1;
- }
-
- /* Ethernet header. */
- eth_hdr = rte_pktmbuf_mtod_offset(rarp_mbuf, struct ether_hdr *, 0);
- memset(eth_hdr->d_addr.addr_bytes, 0xff, ETHER_ADDR_LEN);
- ether_addr_copy(mac, ð_hdr->s_addr);
- eth_hdr->ether_type = htons(ETHER_TYPE_RARP);
-
- /* RARP header. */
- rarp = (struct arp_hdr *)(eth_hdr + 1);
- rarp->arp_hrd = htons(ARP_HRD_ETHER);
- rarp->arp_pro = htons(ETHER_TYPE_IPv4);
- rarp->arp_hln = ETHER_ADDR_LEN;
- rarp->arp_pln = 4;
- rarp->arp_op = htons(ARP_OP_REVREQUEST);
-
- ether_addr_copy(mac, &rarp->arp_data.arp_sha);
- ether_addr_copy(mac, &rarp->arp_data.arp_tha);
- memset(&rarp->arp_data.arp_sip, 0x00, 4);
- memset(&rarp->arp_data.arp_tip, 0x00, 4);
-
- rarp_mbuf->pkt_len = rarp_mbuf->data_len = RARP_PKT_SIZE;
-
- return 0;
-}
-
static __rte_always_inline void
put_zmbuf(struct zcopy_mbuf *zmbuf)
{
vq->used->idx += count;
vhost_log_used_vring(dev, vq, offsetof(struct vring_used, idx),
sizeof(vq->used->idx));
- vhost_vring_call(vq);
+ vhost_vring_call(dev, vq);
}
static __rte_always_inline struct zcopy_mbuf *
return true;
}
+static __rte_always_inline void
+restore_mbuf(struct rte_mbuf *m)
+{
+ uint32_t mbuf_size, priv_size;
+
+ while (m) {
+ priv_size = rte_pktmbuf_priv_size(m->pool);
+ mbuf_size = sizeof(struct rte_mbuf) + priv_size;
+ /* start of buffer is after mbuf structure and priv data */
+
+ m->buf_addr = (char *)m + mbuf_size;
+ m->buf_iova = rte_mempool_virt2iova(m) + mbuf_size;
+ m = m->next;
+ }
+}
+
uint16_t
rte_vhost_dequeue_burst(int vid, uint16_t queue_id,
struct rte_mempool *mbuf_pool, struct rte_mbuf **pkts, uint16_t count)
}
vq = dev->virtqueue[queue_id];
- if (unlikely(vq->enabled == 0))
+
+ if (unlikely(rte_spinlock_trylock(&vq->access_lock) == 0))
return 0;
+ if (unlikely(vq->enabled == 0))
+ goto out_access_unlock;
+
vq->batch_copy_nb_elems = 0;
if (dev->features & (1ULL << VIRTIO_F_IOMMU_PLATFORM))
nr_updated += 1;
TAILQ_REMOVE(&vq->zmbuf_list, zmbuf, next);
+ restore_mbuf(zmbuf->mbuf);
rte_pktmbuf_free(zmbuf->mbuf);
put_zmbuf(zmbuf);
vq->nr_zmbuf -= 1;
rte_atomic16_cmpset((volatile uint16_t *)
&dev->broadcast_rarp.cnt, 1, 0))) {
- rarp_mbuf = rte_pktmbuf_alloc(mbuf_pool);
+ rarp_mbuf = rte_net_make_rarp_packet(mbuf_pool, &dev->mac);
if (rarp_mbuf == NULL) {
RTE_LOG(ERR, VHOST_DATA,
- "Failed to allocate memory for mbuf.\n");
+ "Failed to make RARP packet.\n");
return 0;
}
-
- if (make_rarp_packet(rarp_mbuf, &dev->mac)) {
- rte_pktmbuf_free(rarp_mbuf);
- rarp_mbuf = NULL;
- } else {
- count -= 1;
- }
+ count -= 1;
}
free_entries = *((volatile uint16_t *)&vq->avail->idx) -
if (dev->features & (1ULL << VIRTIO_F_IOMMU_PLATFORM))
vhost_user_iotlb_rd_unlock(vq);
+out_access_unlock:
+ rte_spinlock_unlock(&vq->access_lock);
+
if (unlikely(rarp_mbuf != NULL)) {
/*
* Inject it to the head of "pkts" array, so that switch's mac