static int rb_epoll_sched_event_timerfd(struct ev_entry *event, int when) { struct itimerspec ts; static char buf[FD_DESC_SZ + 8]; int fd; rb_fde_t *F; if((fd = timerfd_create(CLOCK_REALTIME, 0)) < 0) { rb_lib_log("timerfd_create: %s\n", strerror(errno)); return 0; } memset(&ts, 0, sizeof(ts)); ts.it_value.tv_sec = when; ts.it_value.tv_nsec = 0; if(event->frequency != 0) ts.it_interval = ts.it_value; if(timerfd_settime(fd, 0, &ts, NULL) < 0) { rb_lib_log("timerfd_settime: %s\n", strerror(errno)); close(fd); return 0; } rb_snprintf(buf, sizeof(buf), "timerfd: %s", event->name); F = rb_open(fd, RB_FD_UNKNOWN, buf); rb_set_nb(F); event->comm_ptr = F; rb_setselect(F, RB_SELECT_READ, rb_read_timerfd, event); return 1; }
void rb_epoll_init_event(void) { sigset_t ss; rb_fde_t *F; int sfd; rb_epoll_supports_event(); if(!can_do_timerfd) { sigemptyset(&ss); sigaddset(&ss, RTSIGNAL); sigprocmask(SIG_BLOCK, &ss, 0); sigemptyset(&ss); sigaddset(&ss, RTSIGNAL); sfd = signalfd(-1, &ss, 0); if(sfd == -1) { can_do_event = -1; return; } F = rb_open(sfd, RB_FD_UNKNOWN, "signalfd"); rb_set_nb(F); signalfd_handler(F, NULL); } }
rb_helper * rb_helper_start(const char *name, const char *fullpath, rb_helper_cb * read_cb, rb_helper_cb * error_cb) { rb_helper *helper; const char *parv[2]; char buf[128]; char fx[16], fy[16]; rb_fde_t *in_f[2]; rb_fde_t *out_f[2]; pid_t pid; if(access(fullpath, X_OK) == -1) return NULL; helper = rb_malloc(sizeof(rb_helper)); snprintf(buf, sizeof(buf), "%s helper - read", name); if(rb_pipe(&in_f[0], &in_f[1], buf) < 0) { rb_free(helper); return NULL; } snprintf(buf, sizeof(buf), "%s helper - write", name); if(rb_pipe(&out_f[0], &out_f[1], buf) < 0) { rb_free(helper); return NULL; } snprintf(fx, sizeof(fx), "%d", rb_get_fd(in_f[1])); snprintf(fy, sizeof(fy), "%d", rb_get_fd(out_f[0])); rb_set_nb(in_f[0]); rb_set_nb(in_f[1]); rb_set_nb(out_f[0]); rb_set_nb(out_f[1]); rb_setenv("IFD", fy, 1); rb_setenv("OFD", fx, 1); rb_setenv("MAXFD", "256", 1); snprintf(buf, sizeof(buf), "-ircd %s daemon", name); parv[0] = buf; parv[1] = NULL; #ifdef _WIN32 SetHandleInformation((HANDLE) rb_get_fd(in_f[1]), HANDLE_FLAG_INHERIT, 1); SetHandleInformation((HANDLE) rb_get_fd(out_f[0]), HANDLE_FLAG_INHERIT, 1); #endif pid = rb_spawn_process(fullpath, (const char **)parv); if(pid == -1) { rb_close(in_f[0]); rb_close(in_f[1]); rb_close(out_f[0]); rb_close(out_f[1]); rb_free(helper); return NULL; } rb_close(in_f[1]); rb_close(out_f[0]); rb_linebuf_newbuf(&helper->sendq); rb_linebuf_newbuf(&helper->recvq); helper->ifd = in_f[0]; helper->ofd = out_f[1]; helper->read_cb = read_cb; helper->error_cb = error_cb; helper->fork_count = 0; helper->pid = pid; return helper; }