12f74ae28SJasvinder Singh /* SPDX-License-Identifier: BSD-3-Clause
22f74ae28SJasvinder Singh * Copyright(c) 2010-2018 Intel Corporation
32f74ae28SJasvinder Singh */
42f74ae28SJasvinder Singh
52f74ae28SJasvinder Singh #include <netinet/in.h>
6742bde12SBruce Richardson #ifdef RTE_EXEC_ENV_LINUX
72f74ae28SJasvinder Singh #include <linux/if.h>
82f74ae28SJasvinder Singh #include <linux/if_tun.h>
92f74ae28SJasvinder Singh #endif
102f74ae28SJasvinder Singh #include <sys/ioctl.h>
112f74ae28SJasvinder Singh
122f74ae28SJasvinder Singh #include <fcntl.h>
132f74ae28SJasvinder Singh #include <stdio.h>
142f74ae28SJasvinder Singh #include <stdlib.h>
152f74ae28SJasvinder Singh #include <string.h>
162f74ae28SJasvinder Singh #include <unistd.h>
172f74ae28SJasvinder Singh
187959831bSJasvinder Singh #include <rte_string_fns.h>
197959831bSJasvinder Singh
202f74ae28SJasvinder Singh #include "tap.h"
212f74ae28SJasvinder Singh
222f74ae28SJasvinder Singh #define TAP_DEV "/dev/net/tun"
232f74ae28SJasvinder Singh
242f74ae28SJasvinder Singh static struct tap_list tap_list;
252f74ae28SJasvinder Singh
262f74ae28SJasvinder Singh int
tap_init(void)272f74ae28SJasvinder Singh tap_init(void)
282f74ae28SJasvinder Singh {
292f74ae28SJasvinder Singh TAILQ_INIT(&tap_list);
302f74ae28SJasvinder Singh
312f74ae28SJasvinder Singh return 0;
322f74ae28SJasvinder Singh }
332f74ae28SJasvinder Singh
342f74ae28SJasvinder Singh struct tap *
tap_find(const char * name)352f74ae28SJasvinder Singh tap_find(const char *name)
362f74ae28SJasvinder Singh {
372f74ae28SJasvinder Singh struct tap *tap;
382f74ae28SJasvinder Singh
392f74ae28SJasvinder Singh if (name == NULL)
402f74ae28SJasvinder Singh return NULL;
412f74ae28SJasvinder Singh
422f74ae28SJasvinder Singh TAILQ_FOREACH(tap, &tap_list, node)
432f74ae28SJasvinder Singh if (strcmp(tap->name, name) == 0)
442f74ae28SJasvinder Singh return tap;
452f74ae28SJasvinder Singh
462f74ae28SJasvinder Singh return NULL;
472f74ae28SJasvinder Singh }
482f74ae28SJasvinder Singh
49742bde12SBruce Richardson #ifndef RTE_EXEC_ENV_LINUX
502f74ae28SJasvinder Singh
512f74ae28SJasvinder Singh struct tap *
tap_create(const char * name __rte_unused)522f74ae28SJasvinder Singh tap_create(const char *name __rte_unused)
532f74ae28SJasvinder Singh {
542f74ae28SJasvinder Singh return NULL;
552f74ae28SJasvinder Singh }
562f74ae28SJasvinder Singh
572f74ae28SJasvinder Singh #else
582f74ae28SJasvinder Singh
592f74ae28SJasvinder Singh struct tap *
tap_create(const char * name)602f74ae28SJasvinder Singh tap_create(const char *name)
612f74ae28SJasvinder Singh {
622f74ae28SJasvinder Singh struct tap *tap;
632f74ae28SJasvinder Singh struct ifreq ifr;
642f74ae28SJasvinder Singh int fd, status;
652f74ae28SJasvinder Singh
662f74ae28SJasvinder Singh /* Check input params */
672f74ae28SJasvinder Singh if ((name == NULL) ||
682f74ae28SJasvinder Singh tap_find(name))
692f74ae28SJasvinder Singh return NULL;
702f74ae28SJasvinder Singh
712f74ae28SJasvinder Singh /* Resource create */
722f74ae28SJasvinder Singh fd = open(TAP_DEV, O_RDWR | O_NONBLOCK);
732f74ae28SJasvinder Singh if (fd < 0)
742f74ae28SJasvinder Singh return NULL;
752f74ae28SJasvinder Singh
762f74ae28SJasvinder Singh memset(&ifr, 0, sizeof(ifr));
772f74ae28SJasvinder Singh ifr.ifr_flags = IFF_TAP | IFF_NO_PI; /* No packet information */
78*f9acaf84SBruce Richardson strlcpy(ifr.ifr_name, name, IFNAMSIZ);
792f74ae28SJasvinder Singh
802f74ae28SJasvinder Singh status = ioctl(fd, TUNSETIFF, (void *) &ifr);
810015ea27SReshma Pattan if (status < 0) {
820015ea27SReshma Pattan close(fd);
832f74ae28SJasvinder Singh return NULL;
840015ea27SReshma Pattan }
852f74ae28SJasvinder Singh
862f74ae28SJasvinder Singh /* Node allocation */
872f74ae28SJasvinder Singh tap = calloc(1, sizeof(struct tap));
880015ea27SReshma Pattan if (tap == NULL) {
890015ea27SReshma Pattan close(fd);
902f74ae28SJasvinder Singh return NULL;
910015ea27SReshma Pattan }
922f74ae28SJasvinder Singh /* Node fill in */
937959831bSJasvinder Singh strlcpy(tap->name, name, sizeof(tap->name));
942f74ae28SJasvinder Singh tap->fd = fd;
952f74ae28SJasvinder Singh
962f74ae28SJasvinder Singh /* Node add to list */
972f74ae28SJasvinder Singh TAILQ_INSERT_TAIL(&tap_list, tap, node);
982f74ae28SJasvinder Singh
992f74ae28SJasvinder Singh return tap;
1002f74ae28SJasvinder Singh }
1012f74ae28SJasvinder Singh
1022f74ae28SJasvinder Singh #endif
103