void RunnerThread::run() { //cout << "MarSystemThread: running" << endl; m_system->updControl("mrs_bool/active", true); while(!m_stop && m_ticks) { //cout << "tick" << endl; process_requests(); m_system->tick(); for (const auto & mapping : m_shared->controls) mapping.second->push(); if (m_ticks > 0) --m_ticks; } m_system->updControl("mrs_bool/active", false); // make sure not to miss latest updates: process_requests(); }
int main(int argc,char **argv) { int s,port; if (argc<2){ printf("Usage: %s port\n",argv[0]); exit(1); } port=atoi(argv[1]); /* start server up */ s = start_server(port); if (s>=0){ printf("Server started on port %i\n",port); process_requests(s); } if (s==-1){ printf("Port reserved or out-of-range\n"); exit(1); } if (s==-2){ printf("Error creating socket\n"); exit(1); } fprintf(stderr,"udpft server exiting!\n"); return(1); }
int main(int argc, char *argv[]) { extern char *optarg; extern int optind; extern FILE *dbf; int opt; dbf = fopen("/dev/null", "w"); if (!dbf) dbf = stderr; cgi_setup(WEB_ROOT); while ((opt = getopt(argc, argv,"s:")) != EOF) { switch (opt) { case 's': pstrcpy(servicesf,optarg); break; } } print_header(); charset_initialise(); if (load_config()) { cgi_load_variables(NULL); process_requests(); show_services(); } print_footer(); return 0; }
// ************************************************************************************************* // @fn main // @brief Main routine // @param none // @return none // ************************************************************************************************* int main(void) { #ifdef EMU emu_init(); #endif // Init MCU init_application(); // Assign initial value to global variables init_global_variables(); #ifdef CONFIG_TEST // Branch to welcome screen test_mode(); #else display_all_off(); #endif // Main control loop: wait in low power mode until some event needs to be processed while(1) { // When idle go to LPM3 idle_loop(); // Process wake-up events if (button.all_flags || sys.all_flags) wakeup_event(); // Process actions requested by logic modules if (request.all_flags) process_requests(); // Before going to LPM3, update display if (display.all_flags) display_update(); } }
/** * Get an IP address as a string. * * @param sa host address * @param salen length of host address in @a sa * @param do_resolve use #GNUNET_NO to return numeric hostname * @param timeout how long to try resolving * @param callback function to call with hostnames * last callback is NULL when finished * @param cls closure for @a callback * @return handle that can be used to cancel the request */ struct GNUNET_RESOLVER_RequestHandle * GNUNET_RESOLVER_hostname_get (const struct sockaddr *sa, socklen_t salen, int do_resolve, struct GNUNET_TIME_Relative timeout, GNUNET_RESOLVER_HostnameCallback callback, void *cls) { struct GNUNET_RESOLVER_RequestHandle *rh; size_t ip_len; const void *ip; check_config (); switch (sa->sa_family) { case AF_INET: GNUNET_assert (salen == sizeof (struct sockaddr_in)); ip_len = sizeof (struct in_addr); ip = &((const struct sockaddr_in*)sa)->sin_addr; break; case AF_INET6: GNUNET_assert (salen == sizeof (struct sockaddr_in6)); ip_len = sizeof (struct in6_addr); ip = &((const struct sockaddr_in6*)sa)->sin6_addr; break; default: GNUNET_break (0); return NULL; } rh = GNUNET_malloc (sizeof (struct GNUNET_RESOLVER_RequestHandle) + salen); rh->name_callback = callback; rh->cls = cls; rh->af = sa->sa_family; rh->timeout = GNUNET_TIME_relative_to_absolute (timeout); memcpy (&rh[1], ip, ip_len); rh->data_len = ip_len; rh->direction = GNUNET_YES; rh->received_response = GNUNET_NO; if (GNUNET_NO == do_resolve) { rh->task = GNUNET_SCHEDULER_add_now (&numeric_reverse, rh); return rh; } GNUNET_CONTAINER_DLL_insert_tail (req_head, req_tail, rh); rh->was_queued = GNUNET_YES; if (NULL != s_task) { GNUNET_SCHEDULER_cancel (s_task); s_task = NULL; } process_requests (); return rh; }
void accept_connection(SOCKET listen_fd) { struct sockaddr_storage peeraddr; netperf_socklen_t peeraddrlen; #if defined(SO_KEEPALIVE) int on = 1; #endif if (debug) { fprintf(where, "%s: enter\n", __FUNCTION__); fflush(where); } peeraddrlen = sizeof(peeraddr); /* while server_control is only used by the WIN32 path, but why bother ifdef'ing it? and besides, do we *really* need knowledge of server_control in the WIN32 case? do we have to tell the child about *all* the listen endpoints? raj 2011-07-08 */ server_control = listen_fd; if ((server_sock = accept(listen_fd, (struct sockaddr *)&peeraddr, &peeraddrlen)) == INVALID_SOCKET) { fprintf(where, "%s: accept failure: %s (errno %d)\n", __FUNCTION__, strerror(errno), errno); fflush(where); exit(1); } #if defined(SO_KEEPALIVE) /* we are not terribly concerned if this does not work, it is merely duct tape added to belts and suspenders. raj 2011-07-08 */ setsockopt(server_sock, SOL_SOCKET, SO_KEEPALIVE, (const char *)&on, sizeof(on)); #endif if (spawn_on_accept) { spawn_child(); /* spawn_child() only returns when we are the parent */ close(server_sock); } else { process_requests(); } }
/** * Convert a string to one or more IP addresses. * * @param hostname the hostname to resolve * @param af AF_INET or AF_INET6; use AF_UNSPEC for "any" * @param callback function to call with addresses * @param callback_cls closure for callback * @param timeout how long to try resolving * @return handle that can be used to cancel the request, NULL on error */ struct GNUNET_RESOLVER_RequestHandle * GNUNET_RESOLVER_ip_get (const char *hostname, int af, struct GNUNET_TIME_Relative timeout, GNUNET_RESOLVER_AddressCallback callback, void *callback_cls) { struct GNUNET_RESOLVER_RequestHandle *rh; size_t slen; unsigned int i; struct in_addr v4; struct in6_addr v6; slen = strlen (hostname) + 1; if (slen + sizeof (struct GNUNET_RESOLVER_GetMessage) >= GNUNET_SERVER_MAX_MESSAGE_SIZE) { GNUNET_break (0); return NULL; } rh = GNUNET_malloc (sizeof (struct GNUNET_RESOLVER_RequestHandle) + slen); rh->af = af; rh->addr_callback = callback; rh->cls = callback_cls; memcpy (&rh[1], hostname, slen); rh->data_len = slen; rh->timeout = GNUNET_TIME_relative_to_absolute (timeout); rh->direction = GNUNET_NO; /* first, check if this is a numeric address */ if (((1 == inet_pton (AF_INET, hostname, &v4)) && ((af == AF_INET) || (af == AF_UNSPEC))) || ((1 == inet_pton (AF_INET6, hostname, &v6)) && ((af == AF_INET6) || (af == AF_UNSPEC)))) { rh->task = GNUNET_SCHEDULER_add_now (&numeric_resolution, rh); return rh; } /* then, check if this is a loopback address */ i = 0; while (loopback[i] != NULL) if (0 == strcasecmp (loopback[i++], hostname)) { rh->task = GNUNET_SCHEDULER_add_now (&loopback_resolution, rh); return rh; } GNUNET_CONTAINER_DLL_insert_tail (req_head, req_tail, rh); rh->was_queued = GNUNET_YES; if (s_task != GNUNET_SCHEDULER_NO_TASK) { GNUNET_SCHEDULER_cancel (s_task); s_task = GNUNET_SCHEDULER_NO_TASK; } process_requests (); return rh; }
int main(int argc, char ** argv) { unsigned int thread_count; int result = cloudi_initialize_thread_count(&thread_count); assert(result == cloudi_success); assert(thread_count == 1); process_requests_t data = {0}; process_requests(&data); return 0; }
/** * Now try to reconnect to the resolver service. * * @param cls NULL * @param tc scheduler context */ static void reconnect_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { r_task = GNUNET_SCHEDULER_NO_TASK; if (NULL == req_head) return; /* no work pending */ if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN)) return; LOG (GNUNET_ERROR_TYPE_DEBUG, "Trying to connect to DNS service\n"); client = GNUNET_CLIENT_connect ("resolver", resolver_cfg); if (NULL == client) { LOG (GNUNET_ERROR_TYPE_DEBUG, "Failed to connect, will try again later\n"); reconnect (); return; } process_requests (); }
int main(int argc, char ** argv) { if (argc != 4) { printf("Usage: %s thread_count protocol buffer_size", argv[0]); return 1; } int const count = atoi(argv[1]); char const * const protocol = argv[2]; int const buffer_size = atoi(argv[3]); assert(count == 1); process_requests_t data = {0, protocol, buffer_size}; process_requests(&data); return 0; }
int main(int argc, char *argv[]) { char *host = "localhost"; char *port = "50000"; int opt; while ((opt = getopt(argc, argv, "tuh:p:")) != -1) { switch (opt) { case 'h': host = optarg; break; case 'p': port = optarg; break; case '?': fprintf(stderr, "Unknown option: %c\n", optopt); exit(EXIT_FAILURE); default: fprintf(stderr, "Failed to parse command line arguments\n"); exit(EXIT_FAILURE); } } if (optind != argc) { fprintf(stderr, "Some unexpected command line arguments are given\n"); exit(EXIT_FAILURE); } int sockfd = create_socket(host, port); if (-1 == sockfd) { exit(EXIT_FAILURE); } process_requests(STDIN_FILENO, sockfd, STDOUT_FILENO); return 0; }
/* the routine we call when we are going to spawn/fork/whatnot a child process from the parent netserver daemon. raj 2011-07-08 */ void spawn_child() { #if defined(HAVE_FORK) if (debug) { fprintf(where, "%s: enter\n", __FUNCTION__); fflush(where); } /* flush the usual suspects */ fflush(stdin); fflush(stdout); fflush(stderr); fflush(where); signal(SIGCLD,SIG_IGN); switch (fork()) { case -1: fprintf(where, "%s: fork() error %s (errno %d)\n", __FUNCTION__, strerror(errno), errno); fflush(where); exit(1); case 0: /* we are the child, but not of inetd. we don't know if we are the child of a daemonized parent or not, so we still need to worry about the standard file descriptors. raj 2011-07-11 */ close_listens(listen_list); open_debug_file(); child = 1; netperf_daemon = 0; process_requests(); exit(0); break; default: /* we are the parent, not a great deal to do here, but we may want to reap some children */ #if !defined(HAVE_SETSID) /* Only call "waitpid()" if "setsid()" is not used. */ while(waitpid(-1, NULL, WNOHANG) > 0) { if (debug) { fprintf(where, "%s: reaped a child process\n", __FUNCTION__); } } #endif break; } #elif defined(WIN32) BOOL b; char *cmdline; int cmdline_length; int cmd_index; PROCESS_INFORMATION pi; STARTUPINFO si; int i; if (debug) { fprintf(where, "%s: enter\n", __FUNCTION__); fflush(where); } /* create the cmdline array based on strlen(program) + 80 chars */ cmdline_length = strlen(program) + 80; cmdline = malloc(cmdline_length + 1); // +1 for trailing null memset(&si, 0 , sizeof(STARTUPINFO)); si.cb = sizeof(STARTUPINFO); /* Pass the server_sock as stdin for the new process. Hopefully this will continue to be created with the OBJ_INHERIT attribute. */ si.hStdInput = (HANDLE)server_sock; si.hStdOutput = GetStdHandle(STD_OUTPUT_HANDLE); si.hStdError = GetStdHandle(STD_ERROR_HANDLE); si.dwFlags = STARTF_USESTDHANDLES; /* Build cmdline for child process */ strcpy(cmdline, program); cmd_index = strlen(cmdline); if (verbosity > 1) { cmd_index += snprintf(&cmdline[cmd_index], cmdline_length - cmd_index, " -v %d", verbosity); } for (i=0; i < debug; i++) { cmd_index += snprintf(&cmdline[cmd_index], cmdline_length - cmd_index, " -d"); } cmd_index += snprintf(&cmdline[cmd_index], cmdline_length - cmd_index, " -I %x", (int)(UINT_PTR)server_sock); /* are these -i settings even necessary? the command line scanning does not seem to do anything with them */ cmd_index += snprintf(&cmdline[cmd_index], cmdline_length - cmd_index, " -i %x", (int)(UINT_PTR)server_control); cmd_index += snprintf(&cmdline[cmd_index], cmdline_length - cmd_index, " -i %x", (int)(UINT_PTR)where); b = CreateProcess(NULL, /* Application Name */ cmdline, NULL, /* Process security attributes */ NULL, /* Thread security attributes */ TRUE, /* Inherit handles */ 0, /* Creation flags PROCESS_QUERY_INFORMATION, */ NULL, /* Enviornment */ NULL, /* Current directory */ &si, /* StartupInfo */ &pi); if (!b) { perror("CreateProcessfailure: "); free(cmdline); /* even though we exit :) */ exit(1); } /* We don't need the thread or process handles any more; let them go away on their own timeframe. */ CloseHandle(pi.hThread); CloseHandle(pi.hProcess); /* the caller/parent will close server_sock */ free(cmdline); #else fprintf(where, "%s called on platform which cannot spawn children\n", __FUNCTION__); fflush(where); exit(1); #endif /* HAVE_FORK */ }
int _cdecl main(int argc, char *argv[]) { #ifdef WIN32 WSADATA wsa_data ; /* Initialize the winsock lib do we still want version 2.2? */ if ( WSAStartup(MAKEWORD(2,2), &wsa_data) == SOCKET_ERROR ){ printf("WSAStartup() failed : %lu\n", GetLastError()) ; return -1 ; } #endif /* WIN32 */ /* Save away the program name */ program = (char *)malloc(strlen(argv[0]) + 1); if (program == NULL) { printf("malloc for program name failed!\n"); return -1 ; } strcpy(program, argv[0]); init_netserver_globals(); netlib_init(); strncpy(local_host_name,"",sizeof(local_host_name)); local_address_family = AF_UNSPEC; strncpy(listen_port,TEST_PORT,sizeof(listen_port)); scan_netserver_args(argc, argv); check_if_inetd(); if (child) { /* we are the child of either an inetd or parent netserver via spawning (Windows) rather than fork()ing. if we were fork()ed we would not be coming through this way. set_server_sock() must be called before open_debug_file() or there is a chance that we'll toast the descriptor when we do not wish it. */ set_server_sock(); open_debug_file(); process_requests(); } else if (daemon_parent) { /* we are the parent daemonized netserver process. accept_connections() will decide if we want to spawn a child process */ accept_connections(); } else { /* we are the top netserver process, so we have to create the listen endpoint(s) and decide if we want to daemonize */ setup_listens(local_host_name,listen_port,local_address_family); if (want_daemonize) { daemonize(); } accept_connections(); } unlink_empty_debug_file(); #ifdef WIN32 WSACleanup(); #endif return 0; }
void set_up_server() { struct servent *sp; /* server entity */ struct sockaddr_in server; struct sockaddr_in peeraddr; int server_control; int peeraddr_len; int ppid,pid; server.sin_port = htons(listen_port_num); server.sin_addr.s_addr = INADDR_ANY; server.sin_family = AF_INET; printf("Starting netserver at port %d\n",listen_port_num); server_control = socket (AF_INET,SOCK_STREAM,0); if (server_control < 0) { perror("server_set_up: creating the socket"); exit(1); } if (bind (server_control, (struct sockaddr *)&server, sizeof(struct sockaddr_in)) == -1) { perror("server_set_up: binding the socket"); exit (1); } if (listen (server_control,5) == -1) { perror("server_set_up: listening"); exit(1); } /* setpgrp(); */ switch (fork()) { case -1: perror("netperf server error"); exit(1); case 0: /* stdin/stderr should use fclose */ fclose(stdin); fclose(stderr); setpgrp(); /* some OS's have SIGCLD defined as SIGCHLD */ #ifndef SIGCLD #define SIGCLD SIGCHLD #endif /* SIGCLD */ signal(SIGCLD, SIG_IGN); for (;;) { peeraddr_len = sizeof(peeraddr); if ((server_sock=accept(server_control, (struct sockaddr *)&peeraddr, &peeraddr_len)) == -1) { printf("server_control: accept failed\n"); exit(1); } signal(SIGCLD, SIG_IGN); switch (fork()) { case -1: /* something went wrong */ exit(1); case 0: /* we are the child process */ close(server_control); process_requests(); exit(0); break; default: /* we are the parent process */ close(server_sock); /* we should try to "reap" some of our children. on some */ /* systems they are being left as defunct processes. we */ /* will call waitpid, looking for any child process, */ /* with the WNOHANG feature. when waitpid return a zero, */ /* we have reaped all the children there are to reap at */ /* the moment, so it is time to move on. raj 12/94 */ #ifndef DONT_WAIT while(waitpid(-1, NULL, WNOHANG) > 0) { } #endif /* DONT_WAIT */ break; } } /*for*/ break; /*case 0*/ default: exit (0); } }
int _cdecl main(int argc, char *argv[]) { int c; int not_inetd = 0; #ifdef WIN32 BOOL child = FALSE; #endif char arg1[BUFSIZ], arg2[BUFSIZ]; #ifndef PATH_MAX #define PATH_MAX MAX_PATH #endif char FileName[PATH_MAX]; /* for opening the debug log file */ struct sockaddr name; netperf_socklen_t namelen = sizeof(name); #ifdef WIN32 WSADATA wsa_data ; /* Initialize the winsock lib ( version 2.2 ) */ if ( WSAStartup(MAKEWORD(2,2), &wsa_data) == SOCKET_ERROR ){ printf("WSAStartup() failed : %d\n", GetLastError()) ; return 1 ; } #endif /* WIN32 */ /* Save away the program name */ program = (char *)malloc(strlen(argv[0]) + 1); if (program == NULL) { printf("malloc(%d) failed!\n", strlen(argv[0]) + 1); return 1 ; } strcpy(program, argv[0]); netlib_init(); /* Scan the command line to see if we are supposed to set-up our own */ /* listen socket instead of relying on inetd. */ /* first set a copy of initial values */ strncpy(local_host_name,"0.0.0.0",sizeof(local_host_name)); local_address_family = AF_UNSPEC; strncpy(listen_port,TEST_PORT,sizeof(listen_port)); while ((c = getopt(argc, argv, SERVER_ARGS)) != EOF) { switch (c) { case '?': case 'h': print_netserver_usage(); exit(1); case 'd': /* we want to set the debug file name sometime */ debug++; break; case 'L': not_inetd = 1; break_args_explicit(optarg,arg1,arg2); if (arg1[0]) { strncpy(local_host_name,arg1,sizeof(local_host_name)); } if (arg2[0]) { local_address_family = parse_address_family(arg2); /* if only the address family was set, we may need to set the local_host_name accordingly. since our defaults are IPv4 this should only be necessary if we have IPv6 support raj 2005-02-07 */ #if defined (AF_INET6) if (!arg1[0]) { strncpy(local_host_name,"::0",sizeof(local_host_name)); } #endif } break; case 'n': shell_num_cpus = atoi(optarg); if (shell_num_cpus > MAXCPUS) { fprintf(stderr, "netserver: This version can only support %d CPUs. Please", MAXCPUS); fprintf(stderr, " increase MAXCPUS in netlib.h and recompile.\n"); fflush(stderr); exit(1); } break; case 'p': /* we want to open a listen socket at a */ /* specified port number */ strncpy(listen_port,optarg,sizeof(listen_port)); not_inetd = 1; break; case '4': local_address_family = AF_INET; break; case '6': #if defined(AF_INET6) local_address_family = AF_INET6; strncpy(local_host_name,"::0",sizeof(local_host_name)); #else local_address_family = AF_UNSPEC; #endif break; case 'v': /* say how much to say */ verbosity = atoi(optarg); break; case 'V': printf("Netperf version %s\n",NETPERF_VERSION); exit(0); break; #ifdef WIN32 /*+*+SAF */ case 'I': child = TRUE; /* This is the handle we expect to inherit. */ /*+*+SAF server_sock = (HANDLE)atoi(optarg); */ break; case 'i': /* This is a handle we should NOT inherit. */ /*+*+SAF CloseHandle((HANDLE)atoi(optarg)); */ break; #endif } } /* +*+SAF I need a better way to find inherited handles I should close! */ /* +*+SAF Use DuplicateHandle to force inheritable attribute (or reset it)? */ /* unlink(DEBUG_LOG_FILE); */ strcpy(FileName, DEBUG_LOG_FILE); #ifndef WIN32 snprintf(&FileName[strlen(FileName)], sizeof(FileName) - strlen(FileName), "_%d", getpid()); if ((where = fopen(FileName, "w")) == NULL) { perror("netserver: debug file"); exit(1); } #else { if (child) { snprintf(&FileName[strlen(FileName)], sizeof(FileName) - strlen(FileName), "_%x", getpid()); } /* Hopefully, by closing stdout & stderr, the subsequent fopen calls will get mapped to the correct std handles. */ fclose(stdout); if ((where = fopen(FileName, "w")) == NULL) { perror("netserver: fopen of debug file as new stdout failed!"); exit(1); } fclose(stderr); if ((where = fopen(FileName, "w")) == NULL) { fprintf(stdout, "fopen of debug file as new stderr failed!\n"); exit(1); } } #endif #ifndef WIN32 chmod(DEBUG_LOG_FILE,0644); #endif #if WIN32 if (child) { server_sock = (SOCKET)GetStdHandle(STD_INPUT_HANDLE); } #endif /* if we are not a child of an inetd or the like, then we should open a socket and hang listens off of it. otherwise, we should go straight into processing requests. the do_listen() routine will sit in an infinite loop accepting connections and forking child processes. the child processes will call process_requests */ /* If fd 0 is not a socket then assume we're not being called */ /* from inetd and start server socket on the default port. */ /* this enhancement comes from [email protected] (Von Welch) */ if (not_inetd) { /* the user specified a port number on the command line */ set_up_server(local_host_name,listen_port,local_address_family); } #ifdef WIN32 /* OK, with Win2003 WinNT's POSIX subsystem is gone, and hence so is */ /* fork. But hopefully the kernel support will continue to exist */ /* for some time. We are not counting on the address space */ /* copy_on_write support, since it isn't exposed except through the */ /* NT native APIs (which are not public). We will try to use the */ /* InheritHandles flag in CreateProcess though since this is public */ /* and is used for more than just POSIX so hopefully it won't go */ /* away. */ else if (TRUE) { if (child) { process_requests(); } else { strncpy(listen_port,TEST_PORT,sizeof(listen_port)); set_up_server(local_host_name,listen_port,local_address_family); } } #endif #if !defined(__VMS) else if (getsockname(0, &name, &namelen) == SOCKET_ERROR) { /* we may not be a child of inetd */ if (errno == ENOTSOCK) { strncpy(listen_port,TEST_PORT,sizeof(listen_port)); set_up_server(local_host_name,listen_port,local_address_family); } } #endif /* !defined(__VMS) */ else { /* we are probably a child of inetd, or are being invoked via the VMS auxilliarly server mechanism */ #if !defined(__VMS) server_sock = 0; #else if ( (server_sock = socket(TCPIP$C_AUXS, SOCK_STREAM, 0)) == INVALID_SOCKET ) { perror("Failed to grab aux server socket" ); exit(1); } #endif /* !defined(__VMS) */ process_requests(); } #ifdef WIN32 /* Cleanup the winsock lib */ WSACleanup(); #endif return(0); }
int main(int argc, char **argv) { int sock; uid_t own_u; gid_t own_g; char *rpath = NULL; char *sock_name = NULL; struct stat stbuf; int c, option_index; #ifdef FS_IOC_GETVERSION int retval; struct statfs st_fs; #endif prog_name = g_path_get_basename(argv[0]); is_daemon = true; sock = -1; own_u = own_g = -1; while (1) { option_index = 0; c = getopt_long(argc, argv, "p:nh?f:s:u:g:", helper_opts, &option_index); if (c == -1) { break; } switch (c) { case 'p': rpath = g_strdup(optarg); break; case 'n': is_daemon = false; break; case 'f': sock = atoi(optarg); break; case 's': sock_name = g_strdup(optarg); break; case 'u': own_u = atoi(optarg); break; case 'g': own_g = atoi(optarg); break; case '?': case 'h': default: usage(); exit(EXIT_FAILURE); } } /* Parameter validation */ if ((sock_name == NULL && sock == -1) || rpath == NULL) { fprintf(stderr, "socket, socket descriptor or path not specified\n"); usage(); return -1; } if (sock_name && sock != -1) { fprintf(stderr, "both named socket and socket descriptor specified\n"); usage(); exit(EXIT_FAILURE); } if (sock_name && (own_u == -1 || own_g == -1)) { fprintf(stderr, "owner uid:gid not specified, "); fprintf(stderr, "owner uid:gid specifies who can access the socket file\n"); usage(); exit(EXIT_FAILURE); } if (lstat(rpath, &stbuf) < 0) { fprintf(stderr, "invalid path \"%s\" specified, %s\n", rpath, strerror(errno)); exit(EXIT_FAILURE); } if (!S_ISDIR(stbuf.st_mode)) { fprintf(stderr, "specified path \"%s\" is not directory\n", rpath); exit(EXIT_FAILURE); } if (is_daemon) { if (daemon(0, 0) < 0) { fprintf(stderr, "daemon call failed\n"); exit(EXIT_FAILURE); } openlog(PROGNAME, LOG_PID, LOG_DAEMON); } do_log(LOG_INFO, "Started\n"); if (sock_name) { sock = proxy_socket(sock_name, own_u, own_g); if (sock < 0) { goto error; } } if (chroot(rpath) < 0) { do_perror("chroot"); goto error; } if (chdir("/") < 0) { do_perror("chdir"); goto error; } get_version = false; #ifdef FS_IOC_GETVERSION /* check whether underlying FS support IOC_GETVERSION */ retval = statfs("/", &st_fs); if (!retval) { switch (st_fs.f_type) { case EXT2_SUPER_MAGIC: case BTRFS_SUPER_MAGIC: case REISERFS_SUPER_MAGIC: case XFS_SUPER_MAGIC: get_version = true; break; } } #endif umask(0); if (init_capabilities() < 0) { goto error; } process_requests(sock); error: g_free(rpath); g_free(sock_name); do_log(LOG_INFO, "Done\n"); closelog(); return 0; }
void loop(int server_s) { FD_ZERO(BOA_READ); FD_ZERO(BOA_WRITE); max_fd = -1; while (1) { /* handle signals here */ if (sighup_flag) sighup_run(); if (sigchld_flag) sigchld_run(); if (sigalrm_flag) sigalrm_run(); if (sigterm_flag) { /* sigterm_flag: * 1. caught, unprocessed. * 2. caught, stage 1 processed */ if (sigterm_flag == 1) { sigterm_stage1_run(); BOA_FD_CLR(req, server_s, BOA_READ); close(server_s); /* make sure the server isn't in the block list */ server_s = -1; } if (sigterm_flag == 2 && !request_ready && !request_block) { sigterm_stage2_run(); /* terminal */ } } else { if (total_connections > max_connections) { /* FIXME: for poll we don't subtract 20. why? */ BOA_FD_CLR(req, server_s, BOA_READ); } else { BOA_FD_SET(req, server_s, BOA_READ); /* server always set */ } } if (isREBOOTASP == 1) { if(last_req_after_upgrade != req_after_upgrade){ last_req_after_upgrade = req_after_upgrade; } } pending_requests = 0; /* max_fd is > 0 when something is blocked */ if (max_fd) { struct timeval req_timeout; /* timeval for select */ req_timeout.tv_sec = (request_ready ? 0 : default_timeout); req_timeout.tv_usec = 0l; /* reset timeout */ if (select(max_fd + 1, BOA_READ, BOA_WRITE, NULL, (request_ready || request_block ? &req_timeout : NULL)) == -1) { /* what is the appropriate thing to do here on EBADF */ if (errno == EINTR) { //fprintf(stderr,"####%s:%d isFWUPGRADE=%d isREBOOTASP=%d###\n", __FILE__, __LINE__ ,isFWUPGRADE , isREBOOTASP); //fprintf(stderr,"####%s:%d last_req_after_upgrade=%d req_after_upgrade=%d confirm_last_req=%d###\n", __FILE__, __LINE__ ,last_req_after_upgrade , req_after_upgrade, confirm_last_req); if (isFWUPGRADE !=0 && isREBOOTASP == 1 ) { if (last_req_after_upgrade == req_after_upgrade) confirm_last_req++; if (confirm_last_req >3) goto ToUpgrade; } else if(isCFGUPGRADE ==2 && isREBOOTASP == 1 ) { goto ToReboot; } else if (isFWUPGRADE ==0 && isREBOOTASP == 1) { if (last_req_after_upgrade == req_after_upgrade) confirm_last_req++; if (confirm_last_req >3) { isFWUPGRADE = 0; isREBOOTASP = 0; //isFAKEREBOOT = 0; confirm_last_req=0; } } continue; /* while(1) */ } else if (errno != EBADF) { DIE("select"); } } /* FIXME: optimize for when select returns 0 (timeout). * Thus avoiding many operations in fdset_update * and others. */ if (!sigterm_flag && FD_ISSET(server_s, BOA_READ)) { pending_requests = 1; } time(¤t_time); /* for "new" requests if we've been in * select too long */ /* if we skip this section (for example, if max_fd == 0), * then we aren't listening anyway, so we can't accept * new conns. Don't worry about it. */ } /* reset max_fd */ max_fd = -1; if (request_block) { /* move selected req's from request_block to request_ready */ fdset_update(); } /* any blocked req's move from request_ready to request_block */ if (pending_requests || request_ready) { if (isFWUPGRADE !=0 && isREBOOTASP == 1 ){ req_after_upgrade++; }else if(isFWUPGRADE ==0 && isREBOOTASP == 1){ req_after_upgrade++; } process_requests(server_s); continue; } ToUpgrade: if (isFWUPGRADE !=0 && isREBOOTASP == 1 ) { char buffer[200]; //fprintf(stderr,"\r\n [%s-%u] FirmwareUpgrade start",__FILE__,__LINE__); FirmwareUpgrade(firmware_data, firmware_len, 0, buffer); //fprintf(stderr,"\r\n [%s-%u] FirmwareUpgrade end",__FILE__,__LINE__); //system("echo 7 > /proc/gpio"); // disable system LED isFWUPGRADE=0; isREBOOTASP=0; //reboot_time = 5; break; } ToReboot: if(isCFGUPGRADE == 2 && isREBOOTASP ==1) { isCFGUPGRADE=0; isREBOOTASP=0; system("reboot"); for(;;); } } }
void set_up_server() { struct sockaddr_in server; struct sockaddr_in peeraddr; int server_control; int peeraddr_len; server.sin_port = htons(listen_port_num); server.sin_addr.s_addr = INADDR_ANY; server.sin_family = AF_INET; printf("Starting netserver at port %d\n",listen_port_num); server_control = socket (AF_INET,SOCK_STREAM,0); #ifdef WIN32 if (server_control == INVALID_SOCKET) #else if (server_control < 0) #endif /* WIN32 */ { perror("server_set_up: creating the socket"); exit(1); } if (bind (server_control, (struct sockaddr *)&server, sizeof(struct sockaddr_in)) == -1) { perror("server_set_up: binding the socket"); exit (1); } if (listen (server_control,5) == -1) { perror("server_set_up: listening"); exit(1); } /* setpgrp(); */ #if !defined(WIN32) && !defined(VXWORKS) switch (fork()) { case -1: perror("netperf server error"); exit(1); case 0: /* stdin/stderr should use fclose */ fclose(stdin); fclose(stderr); /* can I just use setsid on all systems? raj 4/96 */ #if defined(__NetBSD__) || defined(__bsdi__) || defined(sun) || defined(__FREEBSD__) setsid(); #else setpgrp(); #endif /* some OS's have SIGCLD defined as SIGCHLD */ #ifndef SIGCLD #define SIGCLD SIGCHLD #endif /* SIGCLD */ signal(SIGCLD, SIG_IGN); #endif /* WIN32 || VXWORKS*/ for (;;) { peeraddr_len = sizeof(peeraddr); if ((server_sock=accept(server_control, (struct sockaddr *)&peeraddr, &peeraddr_len)) == -1) { printf("server_control: accept failed\n"); exit(1); } #if defined(WIN32) || defined(VXWORKS) /* * Since we cannot fork this process , we cant fire any threads * as they all share the same global data . So we better allow * one request at at time */ process_requests() ; close (server_sock); /* pavel 5-Feb-1998 */ } #else signal(SIGCLD, SIG_IGN); switch (fork()) { case -1: /* something went wrong */ exit(1); case 0: /* we are the child process */ close(server_control); process_requests(); exit(0); break; default: /* we are the parent process */ close(server_sock); /* we should try to "reap" some of our children. on some */ /* systems they are being left as defunct processes. we */ /* will call waitpid, looking for any child process, */ /* with the WNOHANG feature. when waitpid return a zero, */ /* we have reaped all the children there are to reap at */ /* the moment, so it is time to move on. raj 12/94 */ #ifndef DONT_WAIT while(waitpid(-1, NULL, WNOHANG) > 0) { } #endif /* DONT_WAIT */ break; } } /*for*/ break; /*case 0*/ default: exit (0); }
void select_loop(int server_s) { FD_ZERO(&block_read_fdset); FD_ZERO(&block_write_fdset); /* set server_s and req_timeout */ req_timeout.tv_sec = (ka_timeout ? ka_timeout : REQUEST_TIMEOUT); req_timeout.tv_usec = 0l; /* reset timeout */ /* preset max_fd */ max_fd = -1; while (1) { if (sighup_flag) sighup_run(); if (sigchld_flag) sigchld_run(); if (sigalrm_flag) sigalrm_run(); if (sigterm_flag) { if (sigterm_flag == 1) sigterm_stage1_run(server_s); if (sigterm_flag == 2 /*&& !request_ready && !request_block*/) { sigterm_stage2_run(); } } /* reset max_fd */ max_fd = -1; if (request_block) { /* move selected req's from request_block to request_ready */ //fprintf(stderr, "fdsetupdated\n"); fdset_update(); } /* any blocked req's move from request_ready to request_block */ process_requests(server_s); if (!sigterm_flag && total_connections < (max_connections - 10) #if defined(TCSUPPORT_WEBSERVER_SSL) && http_mode != HTTPS_ONLY #endif ) { BOA_FD_SET(server_s, &block_read_fdset); } #if defined(TCSUPPORT_WEBSERVER_SSL) if (!sigterm_flag && total_connections < (max_connections - 10) && http_mode != HTTP_ONLY) { BOA_FD_SET(server_ssl, &block_read_fdset); } #endif req_timeout.tv_sec = (request_ready ? 0 : (ka_timeout ? ka_timeout : REQUEST_TIMEOUT)); req_timeout.tv_usec = 0l; /* reset timeout */ if (select(max_fd + 1, &block_read_fdset, &block_write_fdset, NULL, (request_ready || request_block ? &req_timeout : NULL)) == -1) { /* what is the appropriate thing to do here on EBADF */ if (errno == EINTR) { continue; /* while(1) */ } else if (errno != EBADF) { DIE("select"); } } time(¤t_time); if (FD_ISSET(server_s, &block_read_fdset)) { pending_requests = 1; } #if defined(TCSUPPORT_WEBSERVER_SSL) if (FD_ISSET(server_ssl, &block_read_fdset)) { ssl_pending_requests = 1; } #endif } }
void loop(int server_s) { struct pollfd pfd1[2][MAX_FD]; short which = 0, other = 1, temp; int server_pfd, watch_server; pfds = pfd1[which]; pfd_len = server_pfd = 0; watch_server = 1; while (1) { int timeout; time(¤t_time); if (sighup_flag) sighup_run(); if (sigchld_flag) sigchld_run(); if (sigalrm_flag) sigalrm_run(); if (sigterm_flag) { if (sigterm_flag == 1) { sigterm_stage1_run(); close(server_s); server_s = -1; /* remove server_pfd */ { unsigned int i, j; for(i = 0, j = 0;i < pfd_len;++i) { if (i == (unsigned) server_pfd) continue; pfd1[other][j].fd = pfd1[which][j].fd; pfd1[other][j].events = pfd1[which][j].events; ++j; } pfd_len = j; pfds = pfd1[other]; temp = other; other = which; which = temp; } watch_server = 0; } if (sigterm_flag == 2 && !request_ready && !request_block) { sigterm_stage2_run(); } } else { if (total_connections < max_connections) { server_pfd = pfd_len++; pfds[server_pfd].fd = server_s; pfds[server_pfd].events = BOA_READ; watch_server = 1; } else { watch_server = 0; } } /* If there are any requests ready, the timeout is 0. * If not, and there are any requests blocking, the * timeout is ka_timeout ? ka_timeout * 1000, otherwise * REQUEST_TIMEOUT * 1000. * -1 means forever */ pending_requests = 0; if (pfd_len) { timeout = (request_ready ? 0 : (request_block ? default_timeout : -1)); if (poll(pfds, pfd_len, timeout) == -1) { if (errno == EINTR) continue; /* while(1) */ } if (!sigterm_flag && watch_server) { /* */ if (pfds[server_pfd].revents & (POLLNVAL|POLLERR)) { /* problem with the server socket, unexpected */ log_error("server pfd revent contains " "POLLNVAL or POLLERR! Exiting."); exit(1); } else if (pfds[server_pfd].revents & BOA_READ) { pending_requests = 1; } } time(¤t_time); /* if pfd_len is 0, we didn't poll, so the current time * should be up-to-date, and we *won't* be accepting anyway */ } /* go through blocked and unblock them if possible */ /* also resets pfd_len and pfd to known blocked */ pfd_len = 0; if (request_block) { update_blocked(pfd1[other]); } /* swap pfd */ pfds = pfd1[other]; temp = other; other = which; which = temp; /* process any active requests */ process_requests(server_s); } }
/* process client requests */ int srv_loop( const char* ipaddr, int port, const char* mcast_addr ) { int rc, maxfd, err, nrdy, i; fd_set rset; struct timeval tmout, idle_tmout, *ptmout = NULL; tmfd_t *asock = NULL; size_t n = 0, nasock = 0, max_nasock = LQ_BACKLOG; sigset_t oset, bset; static const long IDLE_TMOUT_SEC = 30; assert( (port > 0) && mcast_addr && ipaddr ); (void)tmfprintf( g_flog, "Server is starting up, max clients = [%u]\n", g_uopt.max_clients ); asock = calloc (max_nasock, sizeof(*asock)); if (!asock) { mperror (g_flog, ENOMEM, "%s: calloc", __func__); return ERR_INTERNAL; } init_server_ctx( &g_srv, g_uopt.max_clients, (ipaddr[0] ? ipaddr : "0.0.0.0") , (uint16_t)port, mcast_addr ); g_srv.rcv_tmout = (u_short)g_uopt.rcv_tmout; g_srv.snd_tmout = RLY_SOCK_TIMEOUT; /* NB: server socket is non-blocking! */ if( 0 != (rc = setup_listener( ipaddr, port, &g_srv.lsockfd, g_uopt.lq_backlog )) ) { return rc; } sigemptyset (&bset); sigaddset (&bset, SIGINT); sigaddset (&bset, SIGQUIT); sigaddset (&bset, SIGCHLD); sigaddset (&bset, SIGTERM); (void) sigprocmask (SIG_BLOCK, &bset, &oset); TRACE( (void)tmfprintf( g_flog, "Entering server loop [%s]\n", SLOOP_TAG) ); while (1) { FD_ZERO( &rset ); FD_SET( g_srv.lsockfd, &rset ); FD_SET( g_srv.cpipe[0], &rset ); maxfd = (g_srv.lsockfd > g_srv.cpipe[0] ) ? g_srv.lsockfd : g_srv.cpipe[0]; for (i = 0; (size_t)i < nasock; ++i) { assert (asock[i].fd >= 0); FD_SET (asock[i].fd, &rset); if (asock[i].fd > maxfd) maxfd = asock[i].fd; } /* if there are accepted sockets - apply specified time-out */ tmout.tv_sec = g_uopt.ssel_tmout; tmout.tv_usec = 0; idle_tmout.tv_sec = IDLE_TMOUT_SEC; idle_tmout.tv_usec = 0; /* enforce *idle* select(2) timeout to alleviate signal contention */ ptmout = ((nasock > 0) && (g_uopt.ssel_tmout > 0)) ? &tmout : &idle_tmout; TRACE( (void)tmfprintf( g_flog, "Waiting for input from [%ld] fd's, " "%s timeout\n", (long)(2 + nasock), (ptmout ? "with" : "NO"))); if (ptmout && ptmout->tv_sec) { TRACE( (void)tmfprintf (g_flog, "select() timeout set to " "[%ld] seconds\n", ptmout->tv_sec) ); } (void) sigprocmask (SIG_UNBLOCK, &bset, NULL); if( must_quit() ) { TRACE( (void)tmfputs( "Must quit now\n", g_flog ) ); rc = 0; break; } nrdy = select (maxfd + 1, &rset, NULL, NULL, ptmout); err = errno; (void) sigprocmask (SIG_BLOCK, &bset, NULL); if( must_quit() ) { TRACE( (void)tmfputs( "Must quit now\n", g_flog ) ); rc = 0; break; } wait_terminated( &g_srv ); if( nrdy < 0 ) { if (EINTR == err) { TRACE( (void)tmfputs ("INTERRUPTED, yet " "will continue.\n", g_flog) ); rc = 0; continue; } mperror( g_flog, err, "%s: select", __func__ ); break; } TRACE( (void)tmfprintf (g_flog, "Got %ld requests\n", (long)nrdy) ); if (0 == nrdy) { /* time-out */ tmout_requests (asock, &nasock); rc = 0; continue; } if( FD_ISSET(g_srv.cpipe[0], &rset) ) { (void) tpstat_read( &g_srv ); if (--nrdy <= 0) continue; } if ((0 < nasock) && (0 < (nrdy - (FD_ISSET(g_srv.lsockfd, &rset) ? 1 : 0)))) { process_requests (asock, &nasock, &rset, &g_srv); /* n now contains # (yet) unprocessed accepted sockets */ } if (FD_ISSET(g_srv.lsockfd, &rset)) { if (nasock >= max_nasock) { (void) tmfprintf (g_flog, "Cannot accept sockets beyond " "the limit [%ld/%ld], skipping\n", (long)nasock, (long)max_nasock); } else { n = max_nasock - nasock; /* append asock */ accept_requests (g_srv.lsockfd, &(asock[nasock]), &n); nasock += n; } } } /* server loop */ TRACE( (void)tmfprintf( g_flog, "Exited server loop [%s]\n", SLOOP_TAG) ); for (i = 0; (size_t)i < nasock; ++i) { if (asock[i].fd > 0) (void) close (asock[i].fd); } free (asock); /* receive additional (blocked signals) */ (void) sigprocmask (SIG_SETMASK, &oset, NULL); wait_terminated( &g_srv ); terminate_all_clients( &g_srv ); wait_all( &g_srv ); if (0 != close( g_srv.lsockfd )) { mperror (g_flog, errno, "server socket close"); } free_server_ctx( &g_srv ); (void)tmfprintf( g_flog, "Server exits with rc=[%d]\n", rc ); return rc; }
void set_up_server(char hostname[], char port[], int af) { struct addrinfo hints; struct addrinfo *local_res; struct addrinfo *local_res_temp; struct sockaddr_storage peeraddr; netperf_socklen_t peeraddr_len = sizeof(peeraddr); SOCKET server_control; int on=1; int count; int error; int not_listening; #if !defined(WIN32) && !defined(MPE) && !defined(__VMS) FILE *rd_null_fp; /* Used to redirect from "/dev/null". */ FILE *wr_null_fp; /* Used to redirect to "/dev/null". */ #endif /* !WIN32 !MPE !__VMS */ if (debug) { fprintf(stderr, "set_up_server called with host '%s' port '%s' remfam %d\n", hostname, port, af); fflush(stderr); } memset(&hints,0,sizeof(hints)); hints.ai_family = af; hints.ai_socktype = SOCK_STREAM; hints.ai_protocol = IPPROTO_TCP; hints.ai_flags = AI_PASSIVE; count = 0; do { error = getaddrinfo((char *)hostname, (char *)port, &hints, &local_res); count += 1; if (error == EAI_AGAIN) { if (debug) { fprintf(stderr,"Sleeping on getaddrinfo EAI_AGAIN\n"); fflush(stderr); } sleep(1); } } while ((error == EAI_AGAIN) && (count <= 5)); if (error) { fprintf(stderr, "set_up_server: could not resolve remote '%s' port '%s' af %d", hostname, port, af); fprintf(stderr,"\n\tgetaddrinfo returned %d %s\n", error, gai_strerror(error)); exit(-1); } if (debug) { dump_addrinfo(stderr, local_res, hostname, port, af); } not_listening = 1; local_res_temp = local_res; while((local_res_temp != NULL) && (not_listening)) { fprintf(stderr, "Starting netserver at port %s\n", port); server_control = socket(local_res_temp->ai_family,SOCK_STREAM,0); if (server_control == INVALID_SOCKET) { perror("set_up_server could not allocate a socket"); exit(-1); } /* happiness and joy, keep going */ if (setsockopt(server_control, SOL_SOCKET, SO_REUSEADDR, (char *)&on , sizeof(on)) == SOCKET_ERROR) { if (debug) { perror("warning: set_up_server could not set SO_REUSEADDR"); } } /* still happy and joyful */ if ((bind (server_control, local_res_temp->ai_addr, local_res_temp->ai_addrlen) != SOCKET_ERROR) && (listen (server_control,5) != SOCKET_ERROR)) { not_listening = 0; break; } else { /* we consider a bind() or listen() failure a transient and try the next address */ if (debug) { perror("warning: set_up_server failed a bind or listen call\n"); } local_res_temp = local_res_temp->ai_next; continue; } } if (not_listening) { fprintf(stderr, "set_up_server could not establish a listen endpoint for %s port %s with family %s\n", host_name, port, inet_ftos(af)); fflush(stderr); exit(-1); } else { printf("Starting netserver at hostname %s port %s and family %s\n", hostname, port, inet_ftos(af)); } /* setpgrp(); */ #if !defined(WIN32) && !defined(MPE) && !defined(__VMS) /* Flush the standard I/O file descriptors before forking. */ fflush (stdin); fflush (stdout); fflush (stderr); #if defined(HAVE_FORK) switch (fork()) #else switch (vfork()) #endif { case -1: perror("netperf server error"); exit(1); case 0: /* Redirect stdin from "/dev/null". */ rd_null_fp = fopen ("/dev/null", "r"); if (rd_null_fp == NULL) { perror ("netserver: opening for reading: /dev/null"); exit (1); } if (close (STDIN_FILENO) == -1) { perror ("netserver: closing stdin file descriptor"); exit (1); } if (dup (fileno (rd_null_fp)) == -1) { perror ("netserver: duplicate /dev/null read file descr. to stdin"); exit (1); } /* Redirect stdout to the debug write file descriptor. */ if (close (STDOUT_FILENO) == -1) { perror ("netserver: closing stdout file descriptor"); exit (1); } if (dup (fileno (where)) == -1) { perror ("netserver: duplicate the debug write file descr. to stdout"); exit (1); } /* Redirect stderr to "/dev/null". */ wr_null_fp = fopen ("/dev/null", "w"); if (wr_null_fp == NULL) { perror ("netserver: opening for writing: /dev/null"); exit (1); } if (close (STDERR_FILENO) == -1) { perror ("netserver: closing stderr file descriptor"); exit (1); } if (dup (fileno (wr_null_fp)) == -1) { perror ("netserver: dupicate /dev/null write file descr. to stderr"); exit (1); } #ifndef NO_SETSID setsid(); #else setpgrp(); #endif /* NO_SETSID */ /* some OS's have SIGCLD defined as SIGCHLD */ #ifndef SIGCLD #define SIGCLD SIGCHLD #endif /* SIGCLD */ signal(SIGCLD, SIG_IGN); #endif /* !WIN32 !MPE !__VMS */ for (;;) { if ((server_sock=accept(server_control, (struct sockaddr *)&peeraddr, &peeraddr_len)) == INVALID_SOCKET) { printf("server_control: accept failed errno %d\n",errno); exit(1); } #if defined(MPE) || defined(__VMS) /* * Since we cannot fork this process , we cant fire any threads * as they all share the same global data . So we better allow * one request at at time */ process_requests() ; #elif WIN32 { BOOL b; char cmdline[80]; PROCESS_INFORMATION pi; STARTUPINFO si; int i; memset(&si, 0 , sizeof(STARTUPINFO)); si.cb = sizeof(STARTUPINFO); /* Pass the server_sock as stdin for the new process. */ /* Hopefully this will continue to be created with the OBJ_INHERIT attribute. */ si.hStdInput = (HANDLE)server_sock; si.hStdOutput = GetStdHandle(STD_OUTPUT_HANDLE); si.hStdError = GetStdHandle(STD_ERROR_HANDLE); si.dwFlags = STARTF_USESTDHANDLES; /* Build cmdline for child process */ strcpy(cmdline, program); if (verbosity > 1) { snprintf(&cmdline[strlen(cmdline)], sizeof(cmdline) - strlen(cmdline), " -v %d", verbosity); } for (i=0; i < debug; i++) { snprintf(&cmdline[strlen(cmdline)], sizeof(cmdline) - strlen(cmdline), " -d"); } snprintf(&cmdline[strlen(cmdline)], sizeof(cmdline) - strlen(cmdline), " -I %x", (int)(UINT_PTR)server_sock); snprintf(&cmdline[strlen(cmdline)], sizeof(cmdline) - strlen(cmdline), " -i %x", (int)(UINT_PTR)server_control); snprintf(&cmdline[strlen(cmdline)], sizeof(cmdline) - strlen(cmdline), " -i %x", (int)(UINT_PTR)where); b = CreateProcess(NULL, /* Application Name */ cmdline, NULL, /* Process security attributes */ NULL, /* Thread security attributes */ TRUE, /* Inherit handles */ 0, /* Creation flags PROCESS_QUERY_INFORMATION, */ NULL, /* Enviornment */ NULL, /* Current directory */ &si, /* StartupInfo */ &pi); if (!b) { perror("CreateProcessfailure: "); exit(1); } /* We don't need the thread or process handles any more; let them */ /* go away on their own timeframe. */ CloseHandle(pi.hThread); CloseHandle(pi.hProcess); /* And close the server_sock since the child will own it. */ close(server_sock); } #else signal(SIGCLD, SIG_IGN); #if defined(HAVE_FORK) switch (fork()) #else switch (vfork()) #endif { case -1: /* something went wrong */ exit(1); case 0: /* we are the child process */ close(server_control); process_requests(); exit(0); break; default: /* we are the parent process */ close(server_sock); /* we should try to "reap" some of our children. on some */ /* systems they are being left as defunct processes. we */ /* will call waitpid, looking for any child process, */ /* with the WNOHANG feature. when waitpid return a zero, */ /* we have reaped all the children there are to reap at */ /* the moment, so it is time to move on. raj 12/94 */ #ifndef DONT_WAIT #ifdef NO_SETSID /* Only call "waitpid()" if "setsid()" is not used. */ while(waitpid(-1, NULL, WNOHANG) > 0) { } #endif /* NO_SETSID */ #endif /* DONT_WAIT */ break; } #endif /* !WIN32 !MPE !__VMS */ } /*for*/ #if !defined(WIN32) && !defined(MPE) && !defined(__VMS) break; /*case 0*/ default: exit (0); } #endif /* !WIN32 !MPE !__VMS */ }
void select_loop(int server_s) { FD_ZERO(&block_read_fdset); FD_ZERO(&block_write_fdset); /* set server_s and req_timeout */ req_timeout.tv_sec = (ka_timeout ? ka_timeout : REQUEST_TIMEOUT); req_timeout.tv_usec = 0l; /* reset timeout */ /* preset max_fd */ max_fd = -1; while (1) { if (sighup_flag) sighup_run(); if (sigchld_flag) sigchld_run(); if (sigalrm_flag) sigalrm_run(); if (sigterm_flag) { if (sigterm_flag == 1) sigterm_stage1_run(server_s); if (sigterm_flag == 2 && !request_ready && !request_block) { sigterm_stage2_run(); } } /* reset max_fd */ max_fd = -1; if (request_block) /* move selected req's from request_block to request_ready */ fdset_update(); /* any blocked req's move from request_ready to request_block */ process_requests(server_s); if (!sigterm_flag && total_connections < (max_connections - 10)) { BOA_FD_SET(server_s, &block_read_fdset); /* server always set */ #ifdef SERVER_SSL if (do_sock < 2) BOA_FD_SET(server_ssl, &block_read_fdset); /* server always set */ #endif } req_timeout.tv_sec = (request_ready ? 0 : (ka_timeout ? ka_timeout : REQUEST_TIMEOUT)); req_timeout.tv_usec = 0l; /* reset timeout */ if (select(max_fd + 1, &block_read_fdset, &block_write_fdset, NULL, (request_ready || request_block ? &req_timeout : NULL)) == -1) { /* what is the appropriate thing to do here on EBADF */ if (errno == EINTR) continue; /* while(1) */ else if (errno != EBADF) { DIE("select"); } } time(¤t_time); if (FD_ISSET(server_s, &block_read_fdset)) pending_requests = 1; } }
void loop(int server_s) { FD_ZERO(BOA_READ); FD_ZERO(BOA_WRITE); max_fd = -1; while (1) { /* handle signals here */ if (sighup_flag) sighup_run(); if (sigchld_flag) sigchld_run(); if (sigalrm_flag) sigalrm_run(); if (sigterm_flag) { /* sigterm_flag: * 1. caught, unprocessed. * 2. caught, stage 1 processed */ if (sigterm_flag == 1) { sigterm_stage1_run(); BOA_FD_CLR(req, server_s, BOA_READ); close(server_s); /* make sure the server isn't in the block list */ server_s = -1; } if (sigterm_flag == 2 && !request_ready && !request_block) { sigterm_stage2_run(); /* terminal */ } } else { if (total_connections > max_connections) { /* FIXME: for poll we don't subtract 20. why? */ BOA_FD_CLR(req, server_s, BOA_READ); } else { BOA_FD_SET(req, server_s, BOA_READ); /* server always set */ } } pending_requests = 0; /* max_fd is > 0 when something is blocked */ if (max_fd) { struct timeval req_timeout; /* timeval for select */ req_timeout.tv_sec = (request_ready ? 0 : default_timeout); req_timeout.tv_usec = 0l; /* reset timeout */ if (select(max_fd + 1, BOA_READ, BOA_WRITE, NULL, (request_ready || request_block ? &req_timeout : NULL)) == -1) { /* what is the appropriate thing to do here on EBADF */ if (errno == EINTR) continue; /* while(1) */ else if (errno != EBADF) { DIE("select"); } } /* FIXME: optimize for when select returns 0 (timeout). * Thus avoiding many operations in fdset_update * and others. */ if (!sigterm_flag && FD_ISSET(server_s, BOA_READ)) { pending_requests = 1; } time(¤t_time); /* for "new" requests if we've been in * select too long */ /* if we skip this section (for example, if max_fd == 0), * then we aren't listening anyway, so we can't accept * new conns. Don't worry about it. */ } /* reset max_fd */ max_fd = -1; if (request_block) { /* move selected req's from request_block to request_ready */ fdset_update(); } /* any blocked req's move from request_ready to request_block */ if (pending_requests || request_ready) { process_requests(server_s); } } }
/** * Process response with a hostname for a DNS lookup. * * @param cls our "struct GNUNET_RESOLVER_RequestHandle" context * @param msg message with the hostname, NULL on error */ static void handle_response (void *cls, const struct GNUNET_MessageHeader *msg) { struct GNUNET_RESOLVER_RequestHandle *rh = cls; uint16_t size; LOG (GNUNET_ERROR_TYPE_DEBUG, "Receiving response from DNS service\n"); if (msg == NULL) { char buf[INET6_ADDRSTRLEN]; if (NULL != rh->name_callback) LOG (GNUNET_ERROR_TYPE_INFO, _("Timeout trying to resolve IP address `%s'.\n"), inet_ntop (rh->af, (const void *) &rh[1], buf, sizeof(buf))); else LOG (GNUNET_ERROR_TYPE_INFO, _("Timeout trying to resolve hostname `%s'.\n"), (const char *) &rh[1]); /* check if request was canceled */ if (rh->was_transmitted != GNUNET_SYSERR) { if (NULL != rh->name_callback) { /* no reverse lookup was successful, return ip as string */ if (rh->received_response == GNUNET_NO) rh->name_callback (rh->cls, no_resolve (rh->af, &rh[1], rh->data_len)); /* at least one reverse lookup was successful */ else rh->name_callback (rh->cls, NULL); } if (NULL != rh->addr_callback) rh->addr_callback (rh->cls, NULL, 0); } GNUNET_CONTAINER_DLL_remove (req_head, req_tail, rh); GNUNET_free (rh); GNUNET_CLIENT_disconnect (client); client = NULL; reconnect (); return; } if (GNUNET_MESSAGE_TYPE_RESOLVER_RESPONSE != ntohs (msg->type)) { GNUNET_break (0); GNUNET_CLIENT_disconnect (client); client = NULL; reconnect (); return; } size = ntohs (msg->size); /* message contains not data, just header */ if (size == sizeof (struct GNUNET_MessageHeader)) { /* check if request was canceled */ if (rh->was_transmitted != GNUNET_SYSERR) { if (NULL != rh->name_callback) rh->name_callback (rh->cls, NULL); if (NULL != rh->addr_callback) rh->addr_callback (rh->cls, NULL, 0); } GNUNET_CONTAINER_DLL_remove (req_head, req_tail, rh); GNUNET_free (rh); process_requests (); return; } /* return reverse lookup results to caller */ if (NULL != rh->name_callback) { const char *hostname; hostname = (const char *) &msg[1]; if (hostname[size - sizeof (struct GNUNET_MessageHeader) - 1] != '\0') { GNUNET_break (0); if (rh->was_transmitted != GNUNET_SYSERR) rh->name_callback (rh->cls, NULL); GNUNET_CONTAINER_DLL_remove (req_head, req_tail, rh); GNUNET_free (rh); GNUNET_CLIENT_disconnect (client); client = NULL; reconnect (); return; } LOG (GNUNET_ERROR_TYPE_DEBUG, "Resolver returns `%s' for IP `%s'.\n", hostname, GNUNET_a2s ((const void *) &rh[1], rh->data_len)); if (rh->was_transmitted != GNUNET_SYSERR) rh->name_callback (rh->cls, hostname); rh->received_response = GNUNET_YES; GNUNET_CLIENT_receive (client, &handle_response, rh, GNUNET_TIME_absolute_get_remaining (rh->timeout)); } /* return lookup results to caller */ if (NULL != rh->addr_callback) { struct sockaddr_in v4; struct sockaddr_in6 v6; const struct sockaddr *sa; socklen_t salen; const void *ip; size_t ip_len; ip = &msg[1]; ip_len = size - sizeof (struct GNUNET_MessageHeader); if (ip_len == sizeof (struct in_addr)) { memset (&v4, 0, sizeof (v4)); v4.sin_family = AF_INET; v4.sin_addr = *(struct in_addr*) ip; #if HAVE_SOCKADDR_IN_SIN_LEN v4.sin_len = sizeof (v4); #endif salen = sizeof (v4); sa = (const struct sockaddr *) &v4; } else if (ip_len == sizeof (struct in6_addr)) { memset (&v6, 0, sizeof (v6)); v6.sin6_family = AF_INET6; v6.sin6_addr = *(struct in6_addr*) ip; #if HAVE_SOCKADDR_IN_SIN_LEN v6.sin6_len = sizeof (v6); #endif salen = sizeof (v6); sa = (const struct sockaddr *) &v6; } else { GNUNET_break (0); if (rh->was_transmitted != GNUNET_SYSERR) rh->addr_callback (rh->cls, NULL, 0); GNUNET_CONTAINER_DLL_remove (req_head, req_tail, rh); GNUNET_free (rh); GNUNET_CLIENT_disconnect (client); client = NULL; reconnect (); return; } rh->addr_callback (rh->cls, sa, salen); GNUNET_CLIENT_receive (client, &handle_response, rh, GNUNET_TIME_absolute_get_remaining (rh->timeout)); } }