Exemple #1
0
static int
select_del(void *arg, struct event *ev)
{
	struct selectop *sop = arg;

	check_selectop(sop);
	if (ev->ev_events & EV_SIGNAL)
		return (evsignal_del(ev));

	if (sop->event_fds < ev->ev_fd) {
		check_selectop(sop);
		return (0);
	}

	if (ev->ev_events & EV_READ) {
		FD_CLR(ev->ev_fd, sop->event_readset_in);
		sop->event_r_by_fd[ev->ev_fd] = NULL;
	}

	if (ev->ev_events & EV_WRITE) {
		FD_CLR(ev->ev_fd, sop->event_writeset_in);
		sop->event_w_by_fd[ev->ev_fd] = NULL;
	}

	check_selectop(sop);
	return (0);
}
Exemple #2
0
static int
select_del(void *arg, struct event *ev)
{
	struct selectop *sop = arg;

	check_selectop(sop);
	if (ev->ev_events & EV_SIGNAL) // deal with signal event
		return (evsignal_del(ev));

	if (sop->event_fds < ev->ev_fd) { // event_fds is the current exist largest fd, so the removed fd should be not larger than it
		check_selectop(sop);
		return (0);
	}

	if (ev->ev_events & EV_READ) { // the event is registered for READ
		FD_CLR(ev->ev_fd, sop->event_readset_in); // remove the fd from select read set
		sop->event_r_by_fd[ev->ev_fd] = NULL; // remove fd from array
	}

	if (ev->ev_events & EV_WRITE) {
		FD_CLR(ev->ev_fd, sop->event_writeset_in);
		sop->event_w_by_fd[ev->ev_fd] = NULL;
	}

	check_selectop(sop);
	return (0);
}
Exemple #3
0
static int
devpoll_del(void *arg, struct event *ev)
{
	struct devpollop *devpollop = arg;
	struct evdevpoll *evdp;
	int fd, events;
	int needwritedelete = 1, needreaddelete = 1;

	if (ev->ev_events & OPAL_EV_SIGNAL)
		return (evsignal_del(ev));

	fd = ev->ev_fd;
	if (fd >= devpollop->nfds)
		return (0);
	evdp = &devpollop->fds[fd];

	events = 0;
	if (ev->ev_events & OPAL_EV_READ)
		events |= POLLIN;
	if (ev->ev_events & OPAL_EV_WRITE)
		events |= POLLOUT;

	/*
	 * The only way to remove an fd from the /dev/poll monitored set is
	 * to use POLLREMOVE by itself.  This removes ALL events for the fd 
	 * provided so if we care about two events and are only removing one 
	 * we must re-add the other event after POLLREMOVE.
	 */

	if (devpoll_queue(devpollop, fd, POLLREMOVE) != 0)
		return(-1);

	if ((events & (POLLIN|POLLOUT)) != (POLLIN|POLLOUT)) {
		/*
		 * We're not deleting all events, so we must resubmit the
		 * event that we are still interested in if one exists.
		 */

		if ((events & POLLIN) && evdp->evwrite != NULL) {
			/* Deleting read, still care about write */
			devpoll_queue(devpollop, fd, POLLOUT);
			needwritedelete = 0;
		} else if ((events & POLLOUT) && evdp->evread != NULL) {
			/* Deleting write, still care about read */
			devpoll_queue(devpollop, fd, POLLIN);
			needreaddelete = 0;
		}
	}

	if (needreaddelete)
		evdp->evread = NULL;
	if (needwritedelete)
		evdp->evwrite = NULL;

	return (0);
}
Exemple #4
0
int unset_signals(){
    for(std::vector<struct event *>::iterator i = signals.begin();
        i != signals.end();
        ++i)
    {
        evsignal_del(*i);
        event_free(*i);
    }
    return 0;
}
Exemple #5
0
static int
poll_del(void *arg, struct event *ev)
{
	struct pollop *pop = arg;
	struct pollfd *pfd = NULL;
	int i;

	if (ev->ev_events & EV_SIGNAL)
		return (evsignal_del(ev));

	if (!(ev->ev_events & (EV_READ|EV_WRITE)))
		return (0);

	poll_check_ok(pop);
	i = pop->idxplus1_by_fd[ev->ev_fd] - 1;
	if (i < 0)
		return (-1);

	/* Do we still want to read or write? */
	pfd = &pop->event_set[i];
	if (ev->ev_events & EV_READ) {
		pfd->events &= ~POLLIN;
		pop->event_r_back[i] = NULL;
	}
	if (ev->ev_events & EV_WRITE) {
		pfd->events &= ~POLLOUT;
		pop->event_w_back[i] = NULL;
	}
	poll_check_ok(pop);
	if (pfd->events)
		/* Another event cares about that fd. */
		return (0);

	/* Okay, so we aren't interested in that fd anymore. */
	pop->idxplus1_by_fd[ev->ev_fd] = 0;

	--pop->nfds;
	if (i != pop->nfds) {
		/* 
		 * Shift the last pollfd down into the now-unoccupied
		 * position.
		 */
		memcpy(&pop->event_set[i], &pop->event_set[pop->nfds],
		       sizeof(struct pollfd));
		pop->event_r_back[i] = pop->event_r_back[pop->nfds];
		pop->event_w_back[i] = pop->event_w_back[pop->nfds];
		pop->idxplus1_by_fd[pop->event_set[i].fd] = i + 1;
	}

	poll_check_ok(pop);
	return (0);
}
Exemple #6
0
static int
epoll_del(void *arg, struct event *ev)
{
	struct epollop *epollop = arg;
	struct epoll_event epev = {0, {0}};
	struct evepoll *evep;
	int fd, events, op;
	int needwritedelete = 1, needreaddelete = 1;

	if (ev->ev_events & EV_SIGNAL)
		return (evsignal_del(ev));

	fd = ev->ev_fd;
	if (fd >= epollop->nfds)
		return (0);
	evep = &epollop->fds[fd];

	op = EPOLL_CTL_DEL;
	events = 0;
	//删除相应fd上的相应事件
	if (ev->ev_events & EV_READ)
		events |= EPOLLIN;
	if (ev->ev_events & EV_WRITE)
		events |= EPOLLOUT;

	if ((events & (EPOLLIN|EPOLLOUT)) != (EPOLLIN|EPOLLOUT)) {
		//若fd上不同时存在EPOLLIN 和EPOLLOUT事件时
		if ((events & EPOLLIN) && evep->evwrite != NULL) {
			//删除read 不删除write
			needwritedelete = 0;
			events = EPOLLOUT;
			op = EPOLL_CTL_MOD;
		} else if ((events & EPOLLOUT) && evep->evread != NULL) {
			needreaddelete = 0;
			events = EPOLLIN;
			op = EPOLL_CTL_MOD;
		}
	}

	epev.events = events;
	epev.data.fd = fd;

	if (needreaddelete)
		evep->evread = NULL;
	if (needwritedelete)
		evep->evwrite = NULL;

	if (epoll_ctl(epollop->epfd, op, fd, &epev) == -1)
		return (-1);

	return (0);
}
static void
foreign_event_loop_cleanup_libevent(void)
{
	/* cleanup the foreign loop assets */

	evtimer_del(timer_outer_event);
	event_free(timer_outer_event);
	evsignal_del(sighandler_event);
	event_free(sighandler_event);

	event_base_loop(loop_event, 0);
	event_base_free(loop_event);
}
Exemple #8
0
int
epoll_del(void *arg, struct event *ev)
{
	struct epollop *epollop = arg;
	struct epoll_event epev;
	struct evepoll *evep;
	int fd, events, op;
	int needwritedelete = 1, needreaddelete = 1;

	if (ev->ev_events & EV_SIGNAL)
		return (evsignal_del(&epollop->evsigmask, ev));

	fd = ev->ev_fd;
	if (fd >= epollop->nfds)
		return (0);
	evep = &epollop->fds[fd];

	op = EPOLL_CTL_DEL;
	events = 0;

	if (ev->ev_events & EV_READ)
		events |= EPOLLIN;
	if (ev->ev_events & EV_WRITE)
		events |= EPOLLOUT;

	if ((events & (EPOLLIN|EPOLLOUT)) != (EPOLLIN|EPOLLOUT)) {
		if ((events & EPOLLIN) && evep->evwrite != NULL) {
			needwritedelete = 0;
			events = EPOLLOUT;
			op = EPOLL_CTL_MOD;
		} else if ((events & EPOLLOUT) && evep->evread != NULL) {
			needreaddelete = 0;
			events = EPOLLIN;
			op = EPOLL_CTL_MOD;
		}
	}

	epev.events = events;
	epev.data.ptr = evep;

	if (epoll_ctl(epollop->epfd, op, fd, &epev) == -1)
		return (-1);

	if (needreaddelete)
		evep->evread = NULL;
	if (needwritedelete)
		evep->evwrite = NULL;

	return (0);
}
Exemple #9
0
int main()
{
    struct event_base *eb;
    struct event *ev1, *ev2;

    pthread_t pid;

    /*init event_base*/
    eb = event_base_new();
    assert(eb);

    ev1 = evsignal_new(eb, SIGUSR1, signal_handler, (void*)0x1);
    assert(ev1);
    assert(evsignal_add(ev1, NULL) == 0);

    ev2 = evsignal_new(eb, SIGUSR2, signal_handler, (void*)0x2);
    assert(ev2);
    assert(evsignal_add(ev2, NULL) == 0);

    assert(pthread_create(&pid, NULL, emit_signal, NULL) == 0);

    /*start loop*/
    assert(event_base_loop(eb, EVLOOP_ONCE) == 0);

    assert(pthread_join(pid, NULL) == 0);

    assert(evsignal_del(ev1) == 0);
    assert(evsignal_del(ev2) == 0);
    event_free(ev1);
    event_free(ev2);

    /*destroy event_base*/
    event_base_free(eb);

    return 0;
}
Exemple #10
0
int main(int argc, char **argv)
{
	int error;
	app_subsys **ss;
	int exit_signals[2] = {SIGTERM, SIGINT};
	struct event terminators[2];
    struct event dumper;
	bool conftest = false;
	int opt;
	int i;

	red_srand();
	while ((opt = getopt(argc, argv, "h?vtc:p:")) != -1) {
		switch (opt) {
		case 't':
			conftest = true;
			break;
		case 'c':
			confname = optarg;
			break;
		case 'p':
			pidfile = optarg;
			break;
		case 'v':
			puts(redsocks_version);
			return EXIT_SUCCESS;
		default:
			printf(
				"Usage: %s [-?hvt] [-c config] [-p pidfile]\n"
				"  -h, -?       this message\n"
				"  -v           print version\n"
				"  -t           test config syntax\n"
				"  -p           write pid to pidfile\n",
				argv[0]);
			return (opt == '?' || opt == 'h') ? EXIT_SUCCESS : EXIT_FAILURE;
		}
	}


	FILE *f = fopen(confname, "r");
	if (!f) {
		perror("Unable to open config file");
		return EXIT_FAILURE;
	}

	parser_context* parser = parser_start(f, NULL);
	if (!parser) {
		perror("Not enough memory for parser");
		return EXIT_FAILURE;
	}

	FOREACH(ss, subsystems)
		if ((*ss)->conf_section)
			parser_add_section(parser, (*ss)->conf_section);
	error = parser_run(parser);
	parser_stop(parser);
	fclose(f);

	if (error)
		return EXIT_FAILURE;

	if (conftest)
		return EXIT_SUCCESS;

	// Initialize global event base
	g_event_base = event_base_new();
	if (!g_event_base)
		return EXIT_FAILURE;
		
	memset(&dumper, 0, sizeof(dumper));
	memset(terminators, 0, sizeof(terminators));

	FOREACH(ss, subsystems) {
		if ((*ss)->init) {
			error = (*ss)->init();
			if (error)
				goto shutdown;
		}
	}

	if (pidfile) {
		f = fopen(pidfile, "w");
		if (!f) {
			perror("Unable to open pidfile for write");
			return EXIT_FAILURE;
		}
		fprintf(f, "%d\n", getpid());
		fclose(f);
	}

	assert(SIZEOF_ARRAY(exit_signals) == SIZEOF_ARRAY(terminators));
	for (i = 0; i < SIZEOF_ARRAY(exit_signals); i++) {
		evsignal_assign(&terminators[i], get_event_base(), exit_signals[i], terminate, NULL);
		if (evsignal_add(&terminators[i], NULL) != 0) {
			log_errno(LOG_ERR, "signal_add");
			goto shutdown;
		}
	}

    evsignal_assign(&dumper, get_event_base(), SIGUSR1, dump_handler, NULL);
    if (evsignal_add(&dumper, NULL) != 0) {
        log_errno(LOG_ERR, "evsignal_add");
        goto shutdown;
    }

	log_error(LOG_NOTICE, "redsocks started");

	event_base_dispatch(g_event_base);

	log_error(LOG_NOTICE, "redsocks goes down");

shutdown:
    if (evsignal_initialized(&dumper)) {
        if (evsignal_del(&dumper) != 0)
		    log_errno(LOG_WARNING, "signal_del");
        memset(&dumper, 0, sizeof(dumper));
    }

	for (i = 0; i < SIZEOF_ARRAY(exit_signals); i++) {
		if (evsignal_initialized(&terminators[i])) {
			if (evsignal_del(&terminators[i]) != 0)
				log_errno(LOG_WARNING, "signal_del");
			memset(&terminators[i], 0, sizeof(terminators[i]));
		}
	}

	for (--ss; ss >= subsystems; ss--)
		if ((*ss)->fini)
			(*ss)->fini();

	if (g_event_base)
		event_base_free(g_event_base);
	
	return !error ? EXIT_SUCCESS : EXIT_FAILURE;
}
Exemple #11
0
static int
evport_del (void *arg, struct event *ev)
{

  struct evport_data *evpd = arg;

  struct fd_info *fdi;
  int i;
  int associated = 1;

  check_evportop (evpd);

  /*
   * Delegate, if it's not ours to handle
   */

  if (ev->ev_events & EV_SIGNAL)
    {
      return (evsignal_del (ev) );
    }

  if (evpd->ed_nevents < ev->ev_fd)
    {
      return (-1);
    }

  for (i = 0; i < EVENTS_PER_GETN; ++i)
    {
      if (evpd->ed_pending[i] == ev->ev_fd)
        {
          associated = 0;
          break;
        }
    }

  fdi = &evpd->ed_fds[ev->ev_fd];

  if (ev->ev_events & EV_READ)
    fdi->fdi_revt = NULL;

  if (ev->ev_events & EV_WRITE)
    fdi->fdi_wevt = NULL;

  if (associated)
    {
      if (!FDI_HAS_EVENTS (fdi) &&
              port_dissociate (evpd->ed_port, PORT_SOURCE_FD,
                               ev->ev_fd) == -1)
        {
          /*
           * Ignre EBADFD error the fd could have been closed
           * before event_del() was called.
           */
          if (errno != EBADFD)
            {
              event_warn ("port_dissociate");
              return (-1);
            }
        }

      else
        {
          if (FDI_HAS_EVENTS (fdi) )
            {
              return (reassociate (evpd, fdi, ev->ev_fd) );
            }
        }
    }

  else
    {
      if (fdi->fdi_revt == NULL && fdi->fdi_wevt == NULL)
        {
          evpd->ed_pending[i] = -1;
        }
    }

  return 0;
}
Exemple #12
0
int main(int argc, char *argv[])
{
	struct event_base *base = NULL;

	struct event *sigint_event = NULL;
	struct event *sigterm_event = NULL;
	
	struct rtsp_server_param rs_param;
	struct rtsp_server *rs = NULL;

    slog_init(SLOG_DEBUG);

	/* create event base */
	base = event_base_new();
	if (!base) {
		SLOG(SLOG_ERROR, "failed to create event base");
		return -1;
	}
	
	/* install signal handle */
	sigint_event = evsignal_new(base, SIGINT, signal_quit_cb, (void *)base);
	if (!sigint_event) {
		SLOG(SLOG_ERROR, "failed to create sigint event");
		goto failed;
	}
	sigterm_event = evsignal_new(base, SIGTERM, signal_quit_cb, (void *)base);
	if (!sigterm_event) {
		SLOG(SLOG_ERROR, "failed to create sigterm event");
		goto failed;
	}
	event_add(sigint_event, NULL);
	event_add(sigterm_event, NULL);

	/* init rtsp-server param */
	rs_param.port = 8554;
	rs_param.enable_http_tunnel = 1;
	rs_param.http_tunnel_port = 8080;
	rs_param.udp_port_range[0] = 20000;
	rs_param.udp_port_range[1] = 30000;
	rs_param.max_sessions = 10;

	/* start up rtsp-server */
	rs = rtsp_server_new(base, &rs_param);
	if (!rs) {
		SLOG(SLOG_ERROR, "failed to create rtsp server");
		goto failed;
	}
	
	/* start eventloop */
	event_base_dispatch(base);
	/* fall throught when normal exit */

    SLOG(SLOG_NOTICE, "server exit");
failed:
	if (rs)
		rtsp_server_free(rs);
	
	/* uninstall signal handler */
	if (sigterm_event)
		evsignal_del(sigterm_event);
	if (sigint_event)
		evsignal_del(sigint_event);
	
	if (base)
		event_base_free(base);

	return 0;
}