コード例 #1
0
ファイル: netmap.c プロジェクト: 8tab/qemu
/* The exported init function
 *
 * ... -net netmap,ifname="..."
 */
int net_init_netmap(const Netdev *netdev,
                    const char *name, NetClientState *peer, Error **errp)
{
    const NetdevNetmapOptions *netmap_opts = &netdev->u.netmap;
    struct nm_desc *nmd;
    NetClientState *nc;
    Error *err = NULL;
    NetmapState *s;

    nmd = netmap_open(netmap_opts, &err);
    if (err) {
        error_propagate(errp, err);
        return -1;
    }
    /* Create the object. */
    nc = qemu_new_net_client(&net_netmap_info, peer, "netmap", name);
    s = DO_UPCAST(NetmapState, nc, nc);
    s->nmd = nmd;
    s->tx = NETMAP_TXRING(nmd->nifp, 0);
    s->rx = NETMAP_RXRING(nmd->nifp, 0);
    s->vnet_hdr_len = 0;
    pstrcpy(s->ifname, sizeof(s->ifname), netmap_opts->ifname);
    netmap_read_poll(s, true); /* Initially only poll for reads. */

    return 0;
}
コード例 #2
0
ファイル: pcap.c プロジェクト: ChaosJohn/freebsd
pcap_t *
pcap_open_live(const char *device, int snaplen,
               int promisc, int to_ms, char *errbuf)
{
	struct pcap_ring *me;
	int l;

	(void)snaplen;	/* UNUSED */
	(void)errbuf;	/* UNUSED */
	if (!device) {
		D("missing device name");
		return NULL;
	}

	l = strlen(device) + 1;
	D("request to open %s snaplen %d promisc %d timeout %dms",
		device, snaplen, promisc, to_ms);
	me = calloc(1, sizeof(*me) + l);
	if (me == NULL) {
		D("failed to allocate struct for %s", device);
		return NULL;
	}
	me->me.ifname = (char *)(me + 1);
	strcpy((char *)me->me.ifname, device);
	if (netmap_open(&me->me, 0, promisc)) {
		D("error opening %s", device);
		free(me);
		return NULL;
	}
	me->to_ms = to_ms;

	return (pcap_t *)me;
}
コード例 #3
0
ファイル: peak_netmap.c プロジェクト: javarange/libpeak
unsigned int
peak_netmap_attach(const char *ifname)
{
	struct my_ring *slot = NULL;
	struct my_ring **me = NULL;
	struct pollfd *fd = NULL;
	unsigned int i;

	NETMAP_LOCK();

	/* lazy init */
	if (!NETMAP_COUNT()) {
		bzero(self, sizeof(*self));

		prealloc_init(&self->pkt_pool, NETMAP_MAX,
		    sizeof(struct _peak_netmap));
		prealloc_init(&self->me_pool, NETMAP_MAX,
		    sizeof(struct my_ring));
	}

	i = peak_netmap_find(ifname);
	if (i < NETMAP_COUNT()) {
		NETMAP_UNLOCK();
		alert("netmap interface %s already attached\n");
		return (1);
	}

	slot = NETMAP_GET();
	if (!slot) {
		NETMAP_UNLOCK();
		alert("netmap interface capacity reached\n");
		return (1);
	}

	bzero(slot, sizeof(*slot));

	me = &self->me[NETMAP_COUNT() - 1];
	fd = &self->fd[NETMAP_COUNT() - 1];

	slot->ifname = strdup(ifname);

	if (netmap_open(slot, 0, 1)) {
		free(slot->ifname);
		NETMAP_PUT(slot);
		NETMAP_UNLOCK();
		alert("could not open netmap device %s\n", ifname);
		return (1);
	}

	*me = slot;

	fd->fd = slot->fd;

	NETMAP_UNLOCK();

	return (0);
}
コード例 #4
0
/*
 * bridge [-v] if1 [if2]
 *
 * If only one name, or the two interfaces are the same,
 * bridges userland and the adapter. Otherwise bridge
 * two intefaces.
 */
int
main(int argc, char **argv)
{
	struct pollfd pollfd[2];
	int i, ch;
	u_int burst = 1024, wait_link = 4;
	struct my_ring me[2];
	char *ifa = NULL, *ifb = NULL;

	fprintf(stderr, "%s %s built %s %s\n",
		argv[0], version, __DATE__, __TIME__);

	bzero(me, sizeof(me));

	while ( (ch = getopt(argc, argv, "b:i:vw:")) != -1) {
		switch (ch) {
		default:
			D("bad option %c %s", ch, optarg);
			usage();
			break;
		case 'b':	/* burst */
			burst = atoi(optarg);
			break;
		case 'i':	/* interface */
			if (ifa == NULL)
				ifa = optarg;
			else if (ifb == NULL)
				ifb = optarg;
			else
				D("%s ignored, already have 2 interfaces",
					optarg);
			break;
		case 'v':
			verbose++;
			break;
		case 'w':
			wait_link = atoi(optarg);
			break;
		}

	}

	argc -= optind;
	argv += optind;

	if (argc > 1)
		ifa = argv[1];
	if (argc > 2)
		ifb = argv[2];
	if (argc > 3)
		burst = atoi(argv[3]);
	if (!ifb)
		ifb = ifa;
	if (!ifa) {
		D("missing interface");
		usage();
	}
	if (burst < 1 || burst > 8192) {
		D("invalid burst %d, set to 1024", burst);
		burst = 1024;
	}
	if (wait_link > 100) {
		D("invalid wait_link %d, set to 4", wait_link);
		wait_link = 4;
	}
	/* setup netmap interface #1. */
	me[0].ifname = ifa;
	me[1].ifname = ifb;
	if (!strcmp(ifa, ifb)) {
		D("same interface, endpoint 0 goes to host");
		i = NETMAP_SW_RING;
	} else {
		/* two different interfaces. Take all rings on if1 */
		i = 0;	// all hw rings
	}
	if (netmap_open(me, i, 1))
		return (1);
	me[1].mem = me[0].mem; /* copy the pointer, so only one mmap */
	if (netmap_open(me+1, 0, 1))
		return (1);

	/* setup poll(2) variables. */
	memset(pollfd, 0, sizeof(pollfd));
	for (i = 0; i < 2; i++) {
		pollfd[i].fd = me[i].fd;
		pollfd[i].events = (POLLIN);
	}

	D("Wait %d secs for link to come up...", wait_link);
	sleep(wait_link);
	D("Ready to go, %s 0x%x/%d <-> %s 0x%x/%d.",
		me[0].ifname, me[0].queueid, me[0].nifp->ni_rx_rings,
		me[1].ifname, me[1].queueid, me[1].nifp->ni_rx_rings);

	/* main loop */
	signal(SIGINT, sigint_h);
	while (!do_abort) {
		int n0, n1, ret;
		pollfd[0].events = pollfd[1].events = 0;
		pollfd[0].revents = pollfd[1].revents = 0;
		n0 = pkt_queued(me, 0);
		n1 = pkt_queued(me + 1, 0);
		if (n0)
			pollfd[1].events |= POLLOUT;
		else
			pollfd[0].events |= POLLIN;
		if (n1)
			pollfd[0].events |= POLLOUT;
		else
			pollfd[1].events |= POLLIN;
		ret = poll(pollfd, 2, 2500);
		if (ret <= 0 || verbose)
		    D("poll %s [0] ev %x %x rx %d@%d tx %d,"
			     " [1] ev %x %x rx %d@%d tx %d",
				ret <= 0 ? "timeout" : "ok",
				pollfd[0].events,
				pollfd[0].revents,
				pkt_queued(me, 0),
				me[0].rx->cur,
				pkt_queued(me, 1),
				pollfd[1].events,
				pollfd[1].revents,
				pkt_queued(me+1, 0),
				me[1].rx->cur,
				pkt_queued(me+1, 1)
			);
		if (ret < 0)
			continue;
		if (pollfd[0].revents & POLLERR) {
			D("error on fd0, rxcur %d@%d",
				me[0].rx->avail, me[0].rx->cur);
		}
		if (pollfd[1].revents & POLLERR) {
			D("error on fd1, rxcur %d@%d",
				me[1].rx->avail, me[1].rx->cur);
		}
		if (pollfd[0].revents & POLLOUT) {
			move(me + 1, me, burst);
			// XXX we don't need the ioctl */
			// ioctl(me[0].fd, NIOCTXSYNC, NULL);
		}
		if (pollfd[1].revents & POLLOUT) {
			move(me, me + 1, burst);
			// XXX we don't need the ioctl */
			// ioctl(me[1].fd, NIOCTXSYNC, NULL);
		}
	}
	D("exiting");
	netmap_close(me + 1);
	netmap_close(me + 0);

	return (0);
}