Пример #1
0
Файл: open.c Проект: lb1a/avfs
static int do_open(const char *path, int flags, mode_t mode, char *pathbuf)
{
    int serverfh;
    int holderfd;
    int fh;

    serverfh = cmd_open(path, flags, mode, pathbuf, &holderfd);
    if(serverfh < 0) {
        real_close(holderfd, 1);
        return serverfh;
    }

    fh = get_handle();
    if(fh < 0) {
        cmd_close(serverfh);
        real_close(holderfd, 1);
        return fh;
    }
    
    fcntl(holderfd, F_SETFD, FD_CLOEXEC);

    __av_dtable[fh].serverfh = serverfh;
    __av_dtable[fh].holderfd = holderfd;

    return fh;
}
Пример #2
0
_PUBLIC_ int swrap_close(int fd)
{
	struct socket_info *si = find_socket_info(fd);
	int ret;

	if (!si) {
		return real_close(fd);
	}

	SWRAP_DLIST_REMOVE(sockets, si);

	if (si->myname && si->peername) {
		swrap_dump_packet(si, NULL, SWRAP_CLOSE_SEND, NULL, 0);
	}

	ret = real_close(fd);

	if (si->myname && si->peername) {
		swrap_dump_packet(si, NULL, SWRAP_CLOSE_RECV, NULL, 0);
		swrap_dump_packet(si, NULL, SWRAP_CLOSE_ACK, NULL, 0);
	}

	if (si->path) free(si->path);
	if (si->myname) free(si->myname);
	if (si->peername) free(si->peername);
	if (si->tmp_path) {
		unlink(si->tmp_path);
		free(si->tmp_path);
	}
	free(si);

	return ret;
}
Пример #3
0
int close(int fd)
{
	if (iscsi_fd_list[fd].is_iscsi == 1) {
		int i;

		if (iscsi_fd_list[fd].dup2fd >= 0) {
			iscsi_fd_list[fd].is_iscsi = 0;
			iscsi_fd_list[fd].dup2fd   = -1;
			real_close(fd);
			return 0;
		}

		/* are there any FDs dup2ed onto this ? */
		for(i = 0; i < ISCSI_MAX_FD; i++) {
			if (iscsi_fd_list[i].dup2fd == fd) {
				break;
			}
		}
		if (i < ISCSI_MAX_FD) {
			int j;

			/* yes there are DUPs onto fd, make i the new real device and repoint all other
			 * duplicates
			 */
			memcpy(&iscsi_fd_list[i], &iscsi_fd_list[fd], sizeof(struct iscsi_fd_list));
			iscsi_fd_list[i].dup2fd = -1;

			memset(&iscsi_fd_list[fd], 0, sizeof(struct iscsi_fd_list));
			iscsi_fd_list[fd].dup2fd = -1;

			iscsi_fd_list[i].iscsi->fd = i;
			real_close(fd);

			for(j = 0; j < ISCSI_MAX_FD; j++) {
				if (j != i && iscsi_fd_list[j].dup2fd == fd) {
					iscsi_fd_list[j].dup2fd = i;
				}
			}

			return 0;
		}

		iscsi_fd_list[fd].is_iscsi = 0;
		iscsi_fd_list[fd].dup2fd   = -1;
		iscsi_destroy_context(iscsi_fd_list[fd].iscsi);
		iscsi_fd_list[fd].iscsi    = NULL;

		return 0;
	}

        return real_close(fd);
}
Пример #4
0
int close(int fd)
{

  init();

  if (forked && fd == ssl_socket)
  {
    forked = 0;
    SSL_shutdown(ssl_ssl);
    SSL_free(ssl_ssl);
    return real_close(ssl_socket);
  }

  return real_close(fd);
}
Пример #5
0
int inverse_hash_memory(const struct hash *hash, void *p, size_t n)
{
    const char *waitless_dir = getenv(WAITLESS_DIR);
    if (!waitless_dir)
        die("WAITLESS_DIR not set");
    int dn = strlen(waitless_dir), in = strlen(INVERSE);
    int total = dn + in + 3 + SHOW_HASH_SIZE;
    if (total > PATH_MAX)
        die("WAITLESS_DIR is too long: %d > %d", dn, PATH_MAX - total + dn);

    // path = "waitless_dir/inverse/hash[0:2]/hash"
    char path[total];
    memcpy(path, waitless_dir, dn);
    memcpy(path+dn, INVERSE, in);
    show_hash(path+dn+in+3, SHOW_HASH_SIZE, hash);
    memcpy(path+dn+in, path+dn+in+3, 2);
    path[dn+in+2] = '/';

    // Read path
    // TODO: do enough file locking to prevent reading a partially written file
    int fd = real_open(path, O_RDONLY, 0);
    if (fd < 0)
        die("inverse_hash_memory: failed to open %s: %s", path, strerror(errno));
    size_t r = read(fd, p, n);
    if (r < 0)
        die("inverse_hash_memory: read failed: %s", strerror(errno));
    real_close(fd);
    return r;
}
Пример #6
0
int fork()
{
  int pid;


  init();

  if (forked)
  {
    return real_fork();
  }


  pid = real_fork();

  if (pid == 0)
  {
    forked = 1;
  } else if (pid > 0)
  {
    // no SSL_shutdown(ssl_ssl) as it also terminates connection in fork!
    SSL_free(ssl_ssl);
    real_close(ssl_socket);
  }

  return pid;
}
Пример #7
0
Файл: open.c Проект: lb1a/avfs
static void free_handle(int fh)
{
    if(FD_OK(fh)) 
        __av_dtable[fh].isvirtual = 0;

    real_close(fh, 1);
}
Пример #8
0
void uterm_vt_deallocate(struct uterm_vt *vt)
{
	unsigned int mode;

	if (!vt || !vt->vtm || vt->mode == UTERM_VT_DEAD)
		return;

	mode = vt->mode;
	vt->mode = UTERM_VT_DEAD;

	if (mode == UTERM_VT_REAL) {
		real_close(vt);
	} else if (mode == UTERM_VT_FAKE) {
		ev_eloop_unregister_idle_cb(vt->vtm->eloop, vt_idle_event,
					    vt);
		vt_call(vt, UTERM_VT_DEACTIVATE);
	}
	ev_eloop_unregister_signal_cb(vt->vtm->eloop, SIGUSR2, vt_sigusr2, vt);
	ev_eloop_unregister_signal_cb(vt->vtm->eloop, SIGUSR1, vt_sigusr1, vt);
	kmscon_dlist_unlink(&vt->list);
	uterm_input_sleep(vt->input);
	uterm_input_unref(vt->input);
	vt->vtm = NULL;
	uterm_vt_unref(vt);
}
Пример #9
0
int accept(int s, struct sockaddr *addr, socklen_t *addrlen)
{
  int socket, ssl_err;
  SSL *ssl;

  init();

  socket = real_accept(s,addr,addrlen);

  if (socket < 0) // error, no actual socket
  {
    return socket;
  }

  ssl = SSL_new(ssl_ctx);
  SSL_set_fd(ssl, socket);
  ssl_err = SSL_accept(ssl);
  if(ssl_err <= 0)
  {
    ERR_print_errors_fp(stdout);
    SSL_shutdown(ssl);
    SSL_free(ssl);
    real_close(socket);
    return -1; // XXX set errno?
  }

  ssl_socket = socket;
  ssl_ssl = ssl;

  return socket;
}
Пример #10
0
/** Cleans up client_to_free and returns the next client */
void cli_client_cleanup( cli_client_t* client_to_free ) {
    /* initial cleanup */
    if(client_to_free->fd < 0)
        real_close(-client_to_free->fd);
    else
        close(client_to_free->fd);

    search_state_destroy( &client_to_free->state );
}
Пример #11
0
void uart_cleanup(void) {
    native_async_read_cleanup();

    for (uart_t uart = 0; uart < UART_NUMOF; uart++) {
        if (uart_config[uart].rx_cb != NULL) {
            real_close(tty_fds[uart]);
        }
    }
}
Пример #12
0
void stat_cache_update(struct hash *hash, const char *path, const struct hash *path_hash, int do_hash)
{
    initialize();

    // lstat the file
    struct stat st;
    if (real_lstat(path, &st) < 0) {
        int errno_ = errno;
        if (errno_ == ENOENT || errno_ == ENOTDIR) {
            // Set hash to zero to represent nonexistent file
            memset(hash, 0, sizeof(struct hash));
            return;
        }
        die("lstat(\"%s\") failed: %s", path, strerror(errno_));
    }

    // TODO: We currently ignore the S_ISLNK flag, which assumes that traced
    // processes never detect symlinks via lstat and never create them.

    // For now we go the simple route and hold the stat_cache lock for the
    // entire duration of the hash computation.  In future we may want to drop
    // the lock while we compute the hash.  Alternatively, switching to a finer
    // grain locking discipline might avoid the problem.
    shared_map_lock(&stat_cache);

    // Lookup entry, creating it if necessary, and check if it's up to date
    struct stat_cache_entry *entry;
    if (!shared_map_lookup(&stat_cache, path_hash, (void**)&entry, 1)
        || entry->st_mtimespec.tv_nsec != st.st_mtimespec.tv_nsec
        || entry->st_mtimespec.tv_sec != st.st_mtimespec.tv_sec
        || entry->st_size != st.st_size
        || entry->st_ino != st.st_ino
        || (do_hash && hash_is_all_one(&entry->contents_hash)))
    {
        // Entry is new or out of date.  In either case, compute hash and
        // record new stat details.
        entry->st_ino = st.st_ino;
        entry->st_mtimespec = st.st_mtimespec;
        entry->st_size = st.st_size;

        if (do_hash) {
            // Hash the file
            int fd = real_open(path, O_RDONLY, 0);
            if (fd < 0)
                die("can't open '%s' to compute hash", path);
            hash_fd(&entry->contents_hash, fd);
            real_close(fd);
        }
        else
            memset(&entry->contents_hash, -1, sizeof(struct hash));
    }
    shared_map_unlock(&stat_cache);
    if (do_hash)
        *hash = entry->contents_hash;
    else
        memset(hash, -1, sizeof(struct hash));
}
Пример #13
0
Файл: open.c Проект: lb1a/avfs
static int virt_close(int fd, int undersc)
{
    int res;

    if(!FD_OK(fd) || !ISVIRTUAL(fd))
        res =  real_close(fd, undersc);
    else {
        int errnosave = errno;
        res = cmd_close(SERVERFH(fd));
        real_close(__av_dtable[fd].holderfd, 1);
        free_handle(fd);
        if(res < 0) 
            errno = -res, res = -1;
        else
            errno = errnosave;
    }

    return res;
}
Пример #14
0
void remember_hash_memory(struct hash *hash, const void *p, size_t n)
{
    hash_memory(hash, p, n);

    const char *waitless_dir = getenv(WAITLESS_DIR);
    if (!waitless_dir)
        die("WAITLESS_DIR not set");
    int dn = strlen(waitless_dir), in = strlen(INVERSE);
    int total = dn + in + 3 + SHOW_HASH_SIZE;
    if (total > PATH_MAX)
        die("WAITLESS_DIR is too long: %d > %d", dn, PATH_MAX - total + dn);

    // path = "waitless_dir/inverse/hash[0:2]/hash"
    char path[total];
    memcpy(path, waitless_dir, dn);
    memcpy(path+dn, INVERSE, in);
    show_hash(path+dn+in+3, SHOW_HASH_SIZE, hash);
    memcpy(path+dn+in, path+dn+in+3, 2);
    path[dn+in+2] = '/';

retry:;

    // Try to open path for exclusive create
    int fd = real_open(path, O_WRONLY | O_CREAT | O_EXCL, 0644);
    if (fd < 0) {
        // Failed: either file exists (great!) or we need to make directories
        int errno_ = errno;
        if (errno_ == EEXIST) {
            // If the file exists, we assume it already has the desired contents
            // (go cryptographic hashing).
            return;
        }
        else if (errno_ == ENOENT) {
            // Create the necessary directory components
            path[dn+in-1] = 0;
            if (mkdir(path, 0755) < 0 && errno != EEXIST)
                die("mkdir(\"%s\") failed: %s", path, strerror(errno));
            path[dn+in-1] = '/';
            path[dn+in+2] = 0;
            if (mkdir(path, 0755) < 0 && errno != EEXIST)
                die("mkdir(\"%s\") failed: %s", path, strerror(errno));
            path[dn+in+2] = '/';

            // Try to open again.  Note that it's possible to hit EEXIST on
            // retry if another thread is trying to remember the same hash.
            goto retry;
        }
        die("failed to create %s: %s", path, strerror(errno_));
    }

    if (write(fd, p, n) != n)
        die("remember_hash_memory: write failed: %s", strerror(errno));
    if (real_close(fd) < 0)
        die("remember_hash_memory: close failed: %s", strerror(errno));
}
Пример #15
0
int close(int fd)
{
    if (smbw_fd(fd)) {
        return smbw_close(fd);
    }
    if (smbw_local_fd(fd)) {
        errno = EBADF;
        return -1;
    }

    return real_close(fd);
}
Пример #16
0
void netdev2_tap_cleanup(netdev2_tap_t *dev)
{
    /* Do we have a device */
    if (!dev) {
        return;
    }

    /* cleanup signal handling */
    native_async_read_cleanup();

    /* close the tap device */
    real_close(dev->tap_fd);
}
Пример #17
0
Файл: open.c Проект: lb1a/avfs
static int get_handle()
{
    int fh = -1;
    char dummyfile[64];
    int numtries;
    
    for(numtries = 0; numtries < 10; numtries++) {
        strcpy(dummyfile, "/tmp/.avfs_dummyfile_XXXXXX");
        mktemp(dummyfile);
        if(dummyfile[0] != '\0') {
            fh = real_open(dummyfile, O_RDONLY | O_CREAT | O_EXCL, 0600, 1,
                           1, 0);
            real_unlink(dummyfile);
        }
        if(fh != -1)
            break;
    }

    if(fh == -1)
        return -EIO;
  
    if(!FD_OK(fh)) {
        real_close(fh, 1);
        return -EIO;
    }

    if(ISVIRTUAL(fh)) {
        real_close(fh, 1);
        __av_dtable[fh].isvirtual = 0;
        return -EFAULT;
    }

    fcntl(fh, F_SETFD, FD_CLOEXEC); 

    __av_dtable[fh].isvirtual = 1;

    return fh;
}
Пример #18
0
int close(int fd)
{
    static int (*real_close)(int fd);
    int ret;

    if (!real_close) {
        real_close = dlsym(RTLD_NEXT, "close");
    }

    ret = real_close(fd);
    if (ret == 0 && fd == usb_fd) {
        logit("(%4u) closing fd=%d\n", getpid(), fd);
        usb_fd = -1;
    }
    return ret;
}
Пример #19
0
void netdev2_tap_cleanup(netdev2_tap_t *dev)
{
    /* Do we have a device */
    if (!dev) {
        return;
    }

    /* cleanup signal handling */
    unregister_interrupt(SIGIO);
#ifdef __MACH__
    kill(_sigio_child_pid, SIGKILL);
#endif

    /* close the tap device */
    real_close(dev->tap_fd);
}
Пример #20
0
int
close(int fd) 
{
  int retval;

  print_trace ("%*sclose(%d)=...\n", indent, "",
	       fd);
  indent+=2;

  /* call the real close function */
  retval = real_close (fd);

  indent-=2;
  print_trace ("%*sclose(%d)=%d\n", indent, "", 
	       fd, retval);

  return retval;
}
Пример #21
0
int reboot_arch(int mode)
{
    (void) mode;

    printf("\n\n\t\t!! REBOOT !!\n\n");
#ifdef MODULE_UART0
    /* TODO: close stdio fds */
#endif
#ifdef MODULE_NATIVENET
    if (_native_tap_fd != -1) {
        real_close(_native_tap_fd);
    }
#endif

    if (real_execve(_native_argv[0], _native_argv, NULL) == -1) {
        err(EXIT_FAILURE, "reboot: execve");
    }

    errx(EXIT_FAILURE, "reboot: this should not have been reached");
}
Пример #22
0
/*
 * Both action_close_read and action_close_write are called before the actual
 * close call in order to take advantage of the open file descriptor.  For read,
 * we use fstat to verify that the file hasn't changed, and for write we reuse
 * the file descriptor to compute the hash of the written file.
 *
 * TODO: There is an unfortunate  race condition when writing a file.
 * We currently hash the output file after it is fully written, which means
 * that another process could modify the file before the close.  I believe
 * the only reliable way to avoid this race condition is to intercept the write
 * stream and compute the hash as the data is written out.  Happily, that's
 * something we want to do anyway.
 *
 * For context: the way it should work is that we should compute the hash value
 * that we would have gotten in isolation regardless of when other processes
 * try to stomp on our files.  That way, even if we get the modification times
 * wrong, blowing away the stat_cache and rerunning will detect the change and
 * rebuild the necessary files.
 */
int close(int fd)
{
    wlog("close(%d)", fd);

    struct fd_info *info = 0;
    if (!inside_libc) {
        info = fd_map_find(fd);
        if (info) {
            if (info->count == 1 && !(info->flags & WO_PIPE)) {
                if (info->flags & O_WRONLY)
                    action_close_write(fd);
            }
            fd_map_close(fd);
        }
    }

    int ret = real_close(fd);

    if (info && ret < 0)
        die("error on close(%d): %s", fd, strerror(errno));

    return ret;
}
Пример #23
0
int close(int fd)
{
	if (nfs_fd_list[fd].is_nfs == 1) {
		int i;

		LD_NFS_DPRINTF(9, "close(%d)", fd);

		nfs_fd_list[fd].is_nfs = 0;

		nfs_close(nfs_fd_list[fd].nfs, nfs_fd_list[fd].fh);
		nfs_fd_list[fd].fh = NULL;

		nfs_destroy_context(nfs_fd_list[fd].nfs);
		nfs_fd_list[fd].nfs = NULL;

		free(discard_const(nfs_fd_list[fd].path));
		nfs_fd_list[fd].path = NULL;

		return 0;
	}

        return real_close(fd);
}
Пример #24
0
int close(int fd)
{
	static int (*real_close)(int) = NULL;
	int ret;
	struct fsocket_ioctl_arg arg;

	if (fsocket_channel_fd >= 0) {
		arg.fd = fd;

		if (fsocket_fd_set[fd])
			fsocket_fd_set[fd] = 0;

		ret = ioctl(fsocket_channel_fd, FSOCKET_IOC_CLOSE, &arg);
		if (ret < 0) {
			FSOCKET_ERR("FSOCKET:Close failed!\n");
		}
	} else {
		if (!real_close)
			real_close = dlsym(RTLD_NEXT, "close");
		ret = real_close(fd);
	}

	return ret;
}
Пример #25
0
/* 
 * Copyright (c) 2008-2010 Wind River Systems; see
 * guts/COPYRIGHT for information.
 *
 * static int
 * wrap_close(int fd) {
 *	int rc = -1;
 */
	/* this cleans up an internal table, and shouldn't even
	 * make it to the server.
	 */
	pseudo_client_op(OP_CLOSE, 0, fd, -1, 0, 0);
	rc = real_close(fd);

/*	return rc;
 * }
 */
Пример #26
0
int tap_init(char *name)
{

#ifdef __MACH__ /* OSX */
    char clonedev[255] = "/dev/"; /* XXX bad size */
    strncpy(clonedev+5, name, 250);
#elif defined(__FreeBSD__)
    char clonedev[255] = "/dev/"; /* XXX bad size */
    strncpy(clonedev+5, name, 250);
#else /* Linux */
    struct ifreq ifr;
    const char *clonedev = "/dev/net/tun";
#endif

    /* implicitly create the tap interface */
    if ((_native_tap_fd = open(clonedev , O_RDWR)) == -1) {
        err(EXIT_FAILURE, "open(%s)", clonedev);
    }

#if (defined(__MACH__) || defined(__FreeBSD__)) /* OSX/FreeBSD */
    struct ifaddrs* iflist;
    if (getifaddrs(&iflist) == 0) {
        for (struct ifaddrs *cur = iflist; cur; cur = cur->ifa_next) {
            if ((cur->ifa_addr->sa_family == AF_LINK) && (strcmp(cur->ifa_name, name) == 0) && cur->ifa_addr) {
                struct sockaddr_dl* sdl = (struct sockaddr_dl*)cur->ifa_addr;
                memcpy(_native_tap_mac, LLADDR(sdl), sdl->sdl_alen);
                break;
            }
        }

        freeifaddrs(iflist);
    }
#else /* Linux */
    memset(&ifr, 0, sizeof(ifr));
    ifr.ifr_flags = IFF_TAP | IFF_NO_PI;
    strncpy(ifr.ifr_name, name, IFNAMSIZ);

    if (ioctl(_native_tap_fd, TUNSETIFF, (void *)&ifr) == -1) {
        _native_in_syscall++;
        warn("ioctl TUNSETIFF");
        warnx("probably the tap interface (%s) does not exist or is already in use", name);
        exit(EXIT_FAILURE);
    }

    /* TODO: use strncpy */
    strcpy(name, ifr.ifr_name);


    /* get MAC address */
    memset (&ifr, 0, sizeof (ifr));
    snprintf (ifr.ifr_name, sizeof (ifr.ifr_name), "%s", name);
    if (ioctl(_native_tap_fd, SIOCGIFHWADDR, &ifr) == -1) {
        _native_in_syscall++;
        warn("ioctl SIOCGIFHWADDR");
        if (real_close(_native_tap_fd) == -1) {
            warn("close");
        }
        exit(EXIT_FAILURE);
    }
    memcpy(_native_tap_mac, ifr.ifr_hwaddr.sa_data, ETHER_ADDR_LEN);
#endif
    DEBUG("_native_tap_mac: %02x:%02x:%02x:%02x:%02x:%02x\n", _native_tap_mac[0], _native_tap_mac[1], _native_tap_mac[2], _native_tap_mac[3], _native_tap_mac[4], _native_tap_mac[5]);

    unsigned char *eui_64 = (unsigned char*)&_native_net_addr_long;
    eui_64[0] = _native_tap_mac[0];
    eui_64[1] = _native_tap_mac[1];
    eui_64[2] = _native_tap_mac[2];
    eui_64[3] = 0xff;
    eui_64[4] = 0xfe;
    eui_64[5] = _native_tap_mac[3];
    eui_64[6] = _native_tap_mac[4];
    eui_64[7] = _native_tap_mac[5];

    /* configure signal handler for fds */
    register_interrupt(SIGIO, _native_handle_tap_input);

#ifdef __MACH__
    /* tuntap signalled IO is not working in OSX,
     * check http://sourceforge.net/p/tuntaposx/bugs/17/ */
    sigio_child();
#else
    /* configure fds to send signals on io */
    if (fcntl(_native_tap_fd, F_SETOWN, _native_pid) == -1) {
        err(EXIT_FAILURE, "tap_init(): fcntl(F_SETOWN)");
    }

    /* set file access mode to nonblocking */
    if (fcntl(_native_tap_fd, F_SETFL, O_NONBLOCK|O_ASYNC) == -1) {
        err(EXIT_FAILURE, "tap_init(): fcntl(F_SETFL)");
    }
#endif /* not OSX */

    DEBUG("RIOT native tap initialized.\n");
    return _native_tap_fd;
}
Пример #27
0
static int _init(dev_eth_t *ethdev)
{
    dev_eth_tap_t *dev = (dev_eth_tap_t*)ethdev;

    /* check device parametrs */
    if (dev == NULL) {
        return -ENODEV;
    }

    char *name = dev->tap_name;
#ifdef __MACH__ /* OSX */
    char clonedev[255] = "/dev/"; /* XXX bad size */
    strncpy(clonedev + 5, name, 250);
#elif defined(__FreeBSD__)
    char clonedev[255] = "/dev/"; /* XXX bad size */
    strncpy(clonedev + 5, name, 250);
#else /* Linux */
    struct ifreq ifr;
    const char *clonedev = "/dev/net/tun";
#endif
    /* initialize device descriptor */
    dev->promiscous = 0;
    /* implicitly create the tap interface */
    if ((dev->tap_fd = real_open(clonedev , O_RDWR)) == -1) {
        err(EXIT_FAILURE, "open(%s)", clonedev);
    }
#if (defined(__MACH__) || defined(__FreeBSD__)) /* OSX/FreeBSD */
    struct ifaddrs *iflist;
    if (real_getifaddrs(&iflist) == 0) {
        for (struct ifaddrs *cur = iflist; cur; cur = cur->ifa_next) {
            if ((cur->ifa_addr->sa_family == AF_LINK) && (strcmp(cur->ifa_name, name) == 0) && cur->ifa_addr) {
                struct sockaddr_dl *sdl = (struct sockaddr_dl *)cur->ifa_addr;
                memcpy(dev->addr, LLADDR(sdl), sdl->sdl_alen);
                break;
            }
        }
        real_freeifaddrs(iflist);
    }
#else /* Linux */
    memset(&ifr, 0, sizeof(ifr));
    ifr.ifr_flags = IFF_TAP | IFF_NO_PI;
    strncpy(ifr.ifr_name, name, IFNAMSIZ);
    if (real_ioctl(dev->tap_fd, TUNSETIFF, (void *)&ifr) == -1) {
        _native_in_syscall++;
        warn("ioctl TUNSETIFF");
        warnx("probably the tap interface (%s) does not exist or is already in use", name);
        real_exit(EXIT_FAILURE);
    }

    /* get MAC address */
    memset(&ifr, 0, sizeof(ifr));
    snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "%s", name);
    if (real_ioctl(dev->tap_fd, SIOCGIFHWADDR, &ifr) == -1) {
        _native_in_syscall++;
        warn("ioctl SIOCGIFHWADDR");
        if (real_close(dev->tap_fd) == -1) {
            warn("close");
        }
        real_exit(EXIT_FAILURE);
    }
    memcpy(dev->addr, ifr.ifr_hwaddr.sa_data, NG_ETHERNET_ADDR_LEN);

    /* change mac addr so it differs from what the host is using */
    dev->addr[5]++;
#endif
    DEBUG("ng_tapnet_init(): dev->addr = %02x:%02x:%02x:%02x:%02x:%02x\n",
            dev->addr[0], dev->addr[1], dev->addr[2],
            dev->addr[3], dev->addr[4], dev->addr[5]);
    /* configure signal handler for fds */
    register_interrupt(SIGIO, _tap_isr);
#ifdef __MACH__
    /* tuntap signalled IO is not working in OSX,
     * * check http://sourceforge.net/p/tuntaposx/bugs/17/ */
    _sigio_child(dev);
#else
    /* configure fds to send signals on io */
    if (fcntl(dev->tap_fd, F_SETOWN, _native_pid) == -1) {
        err(EXIT_FAILURE, "ng_tapnet_init(): fcntl(F_SETOWN)");
    }
    /* set file access mode to non-blocking */
    if (fcntl(dev->tap_fd, F_SETFL, O_NONBLOCK | O_ASYNC) == -1) {
        err(EXIT_FAILURE, "ng_tabnet_init(): fcntl(F_SETFL)");
    }
#endif /* not OSX */
    DEBUG("ng_tapnet: initialized.\n");
    return 0;
}
Пример #28
0
pid_t
flume_fork (int nfds, const int close_fds[], int confined)
{
  pid_t pid;

  int tmp_pipe[2];
  int hack_pipe[2];
  int rc;
  int child_ctl_fd;
  int i;
  int parent_ctl = flume_myctlsock ();

  if (parent_ctl < 0) {
    FLUME_SET_ERRNO (FLUME_EMANAGEMENT);
    return -1;
  }

  rc = pipe (tmp_pipe);
  if (rc < 0)
    return rc;

  // A hack to make sure child_ctl_fd doesn't conflict with fd 0,1,2
  rc = pipe (hack_pipe);
  if (rc < 0)
    return rc;

  child_ctl_fd = flume_dup_ctl_sock ();

  real_close (hack_pipe[0]);
  real_close (hack_pipe[1]);

  pid = fork ();

  if (pid > 0) {
    real_close (child_ctl_fd);
    real_close (tmp_pipe[0]);
    rc = write (tmp_pipe[1], (void *)&pid, sizeof (pid));
    if (rc < 0) {
      fprintf (stderr, "fork: write on temporary pipe (fds %d, %d) failed rc %d errno %d!\n", 
               tmp_pipe[0], tmp_pipe[1], rc, errno);
    }
    real_close (tmp_pipe[1]);

  } else if (pid == 0) {

    /*
     * Flume's libc caches our pid (since it sometimes involves a call to
     * the RM).  At this point, we need to clear that cache for obvious
     * reasons.
     */
    flume_clear_pid ();

    /*
     * close all pids we were supposed to close
     */
    for (i = 0; i < nfds; i ++) {
      real_close (close_fds[i]);
    }
    real_close (parent_ctl);
    real_close (tmp_pipe[1]);
    flume_setctlsock (child_ctl_fd);

    /*
     * The primary purpose of this read is to ensure that the parent
     * has closed his end of our control socket. If he does not,
     * then checks in confine_me will fail.  Confine_me is called
     * from inside of finish_fork.
     *
     * The second purpose is to get our pid, which we could have done a
     * different way, but we're reading data anyways....
     */
    rc = read (tmp_pipe[0], (void *)&pid, sizeof (pid));
    if (rc != sizeof (pid)) {
      fprintf (stderr,  "fork: short read from parent: %d\n", rc);
      rc = -1;
    } else {
      real_close (tmp_pipe[0]);

      /*
       * Will do 3 important things:
       *   1.  Will make a flume proc_t structure for this proces.
       *   2.  Will confine this process.
       *   3.  Will set the unix pid on the flume side.
       * 
       * Note, internally, flume must check if this process is confineable.
       * That is, it must check that the CTL sock is legit, that there
       * are no other files open, and that this proc has no
       * writable mmap'ed regions.
       *
       */
      rc = flume_finish_fork (child_ctl_fd, pid, confined);
    }

  } else {
    fprintf (stderr, "fork: fork failed!\n");
    rc = pid;
  }

  return rc;
}
Пример #29
0
static int _init(netdev2_t *netdev)
{
    DEBUG("%s:%s:%u\n", RIOT_FILE_RELATIVE, __func__, __LINE__);

    netdev2_tap_t *dev = (netdev2_tap_t*)netdev;

    /* check device parametrs */
    if (dev == NULL) {
        return -ENODEV;
    }

    char *name = dev->tap_name;
#ifdef __MACH__ /* OSX */
    char clonedev[255] = "/dev/"; /* XXX bad size */
    strncpy(clonedev + 5, name, 250);
#elif defined(__FreeBSD__)
    char clonedev[255] = "/dev/"; /* XXX bad size */
    strncpy(clonedev + 5, name, 250);
#else /* Linux */
    struct ifreq ifr;
    const char *clonedev = "/dev/net/tun";
#endif
    /* initialize device descriptor */
    dev->promiscous = 0;
    /* implicitly create the tap interface */
    if ((dev->tap_fd = real_open(clonedev, O_RDWR | O_NONBLOCK)) == -1) {
        err(EXIT_FAILURE, "open(%s)", clonedev);
    }
#if (defined(__MACH__) || defined(__FreeBSD__)) /* OSX/FreeBSD */
    struct ifaddrs *iflist;
    if (real_getifaddrs(&iflist) == 0) {
        for (struct ifaddrs *cur = iflist; cur; cur = cur->ifa_next) {
            if ((cur->ifa_addr->sa_family == AF_LINK) && (strcmp(cur->ifa_name, name) == 0) && cur->ifa_addr) {
                struct sockaddr_dl *sdl = (struct sockaddr_dl *)cur->ifa_addr;
                memcpy(dev->addr, LLADDR(sdl), sdl->sdl_alen);
                break;
            }
        }
        real_freeifaddrs(iflist);
    }
#else /* Linux */
    memset(&ifr, 0, sizeof(ifr));
    ifr.ifr_flags = IFF_TAP | IFF_NO_PI;
    strncpy(ifr.ifr_name, name, IFNAMSIZ);
    if (real_ioctl(dev->tap_fd, TUNSETIFF, (void *)&ifr) == -1) {
        _native_in_syscall++;
        warn("ioctl TUNSETIFF");
        warnx("probably the tap interface (%s) does not exist or is already in use", name);
        real_exit(EXIT_FAILURE);
    }

    /* get MAC address */
    memset(&ifr, 0, sizeof(ifr));
    snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "%s", name);
    if (real_ioctl(dev->tap_fd, SIOCGIFHWADDR, &ifr) == -1) {
        _native_in_syscall++;
        warn("ioctl SIOCGIFHWADDR");
        if (real_close(dev->tap_fd) == -1) {
            warn("close");
        }
        real_exit(EXIT_FAILURE);
    }
    memcpy(dev->addr, ifr.ifr_hwaddr.sa_data, ETHERNET_ADDR_LEN);

    /* change mac addr so it differs from what the host is using */
    dev->addr[5]++;
#endif
    DEBUG("gnrc_tapnet_init(): dev->addr = %02x:%02x:%02x:%02x:%02x:%02x\n",
            dev->addr[0], dev->addr[1], dev->addr[2],
            dev->addr[3], dev->addr[4], dev->addr[5]);

    /* configure signal handler for fds */
    native_async_read_setup();
    native_async_read_add_handler(dev->tap_fd, NULL, _tap_isr);

#ifdef MODULE_NETSTATS_L2
    memset(&netdev->stats, 0, sizeof(netstats_t));
#endif
    DEBUG("gnrc_tapnet: initialized.\n");
    return 0;
}
Пример #30
0
int close(int fd)
{
  fdatasync(fd);

  return real_close(fd);
}