/* a player request to play with a robot. the robot will be launched in the server-side */ STATIC TEG_STATUS token_robot( int fd, char *str ) { PSPLAYER pJ; int newfd; PLAY_DEBUG("token_robot()\n"); if( player_whoisfd(fd, &pJ ) != TEG_STATUS_SUCCESS ) goto error; if( ! pJ->is_player ) goto error; if( JUEGO_EMPEZADO ) goto error; if( launch_robot(&newfd, "--connected") != TEG_STATUS_SUCCESS ) goto error; fd_add( newfd ); return TEG_STATUS_SUCCESS; error: net_print(fd,TOKEN_ERROR"="TOKEN_ROBOT"\n"); return TEG_STATUS_PARSEERROR; }
/* * Funzione che inizializza la socket di ascolto tcp. * Ritorna 0 in caso successo e -1 in caso di errore. */ int set_listen_socket(unsigned short port) { struct sockaddr_in my_addr; int on = 1; if ((tcp_listen = tcp_socket()) < 0) { perror("set_listen_socket error - can't initialize tcp socket"); return -1; } if (setsockopt(tcp_listen, SOL_SOCKET, SO_REUSEADDR, &on, sizeof(on)) < 0) { perror("set_listen_socket error - setsockopt failed"); return -1; } printf("PORT: %d\n", ntohs(port)); set_addr_any(&my_addr, ntohs(port)); if (inet_bind(tcp_listen, &my_addr)){ perror ("set_listen_socket error - bind failed on tcp socket"); return -1; } if (listen(tcp_listen, BACKLOG) < 0) { perror ("set_listen_socket error - listen failed on tcp socket"); return -1; } fd_add(tcp_listen); return 0; }
int fd_add(int fd, int type, fd_func_t func, void *data) { fd_t *efd, **eptr; fd_set *fds; if (type != FD_READ && type != FD_WRITE && type != FD_EXCEPTION) { if (((type & FD_READ) && fd_add(fd, FD_READ, func, data)) || ((type & FD_WRITE) && fd_add(fd, FD_WRITE, func, data)) || ((type & FD_EXCEPTION) && fd_add(fd, FD_EXCEPTION, func, data))) { fd_max = 0; for (eptr = &fd_list; *eptr; eptr = &(*eptr)->next) { if ((*eptr)->fd == fd) { efd = *eptr; *eptr = (*eptr)->next; free_fd_t(efd); } fd_max = MAX((*eptr)->fd, fd); } return -1; } return 0; } /* TODO if (!(efd = fd_find(fd, type, func, data)) && ...)*/ if (!(efd = alloc_fd_t(fd, type, func, data))) return -1; if (!(fds = fd_set_choose(type, &fd_read, &fd_write, &fd_excep))) { free_fd_t(efd); return -1; } fd_max = MAX(fd, fd_max); if (!FD_ISSET(fd, fds)) FD_SET(fd, fds); for (eptr = &fd_list; *eptr; eptr = &((*eptr)->next)) { if (fd <= (*eptr)->fd) break; } efd->next = *eptr; *eptr = efd; return 0; }
bool input_init() { if(!fd_add(STDIN_FILENO)) return false; /* Commands & packet input processing */ event_busy_add(input_process, NULL); return true; }
/* * Funzione prova a connetersi ai superpeer indicati nella lista passata come parametro. * Ritorna 0 in caso di successo e -1 se si è verificato un errore o se non è riuscita * a connettersi a nessun superpeer della lista. */ int join_overlay(const struct sockaddr_in *sp_addr_list, int list_len) { int i, ok = 1; int sock_tmp; int addr_check = 0; int j, nread; struct sockaddr_in *addr_list; struct packet recv_pck; if (list_len > max_tcp_sock / 2) { near_str = (char *)realloc(near_str, list_len * 2 * ADDR_STR_LEN); memset(near_str + max_tcp_sock * ADDR_STR_LEN, 0, (list_len * 2 - max_tcp_sock) * ADDR_STR_LEN); max_tcp_sock = list_len * 2; } for (i = 0; i < list_len; i ++) { if (get_near_by_addr(&sp_addr_list[i]) != NULL) { continue; } if (ok) { if ((sock_tmp = tcp_socket()) < 0) { perror("join_overlay error - can't initialize tcp socket"); return -1; } //printf("SOCKET: %d\n", sock_tmp); // printf("LISTLEN: %d\n", list_len); } printf("join_overlay - addr: %s:%d\n", inet_ntoa(sp_addr_list[i].sin_addr), ntohs(sp_addr_list[i].sin_port)); if (tcp_connect(sock_tmp, &sp_addr_list[i]) < 0) { perror("join_overlay error - can't connect to superpeer"); ok = 0; continue; //provo il prossimo indirizzo } else { printf("Connected with superpeer %s:%d\n", inet_ntoa(sp_addr_list[i].sin_addr), ntohs(sp_addr_list[i].sin_port)); if (addr_check == 0) { get_local_addr(sock_tmp, &myaddr); addr_check = 1; } ok = 1; if ((nread = recv_packet_tcp(sock_tmp, &recv_pck)) < 0) { perror("join_overlay error - recv_packet_tcp failed\n"); return -1; } else if (nread == 0) { printf("join_overlay - connection closed by superpeer\n"); if (close(sock_tmp) < 0) { perror("join_overlay error - close failed"); return -1; } continue; } if (!strncmp(recv_pck.cmd, CMD_ACK, CMD_STR_LEN)) { if (write(sock_tmp, (char *)&conf.udp_port, sizeof(conf.udp_port)) < 0) { perror("join_overlay error - write failed\n"); return -1; } fd_add(sock_tmp); if (insert_near(sock_tmp, &sp_addr_list[i]) < 0) { fprintf(stderr, "join_overlay error - insert_near failed\n"); return -1; } addr2str(near_str + nsock * 6, sp_addr_list[i].sin_addr.s_addr, sp_addr_list[i].sin_port); addr_list = str_to_addr(near_str, max_tcp_sock); for(j = 0; j < max_tcp_sock; j ++){ printf("join_overlay - near %s:%d\n", inet_ntoa(addr_list[j].sin_addr), ntohs(addr_list[j].sin_port)); } nsock ++; } else if (!strncmp(recv_pck.cmd, CMD_ERR, CMD_STR_LEN)) { printf("RICEVUTO ERR\n"); printf("join_overlay - connection closed by superpeer\n"); if (close(sock_tmp) < 0) { perror("join_overlay error - close failed"); return -1; } continue; } else { fprintf(stderr, "join_overlay error - packet not expected\n"); if (close(sock_tmp) < 0) { perror("join_overlay error - close failed"); return -1; } continue; } } } if (!ok) { close(sock_tmp); } if (nsock != list_len) { printf("join_overlay error - can't connect to all superpeer in the list\n"); return 1; } return 0; }
int accept_conn(int tcp_list) { int j, rc; int sock_tmp; int nread; unsigned short port; struct sockaddr_in *addr_list; struct sockaddr_in addr; unsigned int len = sizeof(struct sockaddr_in); struct packet send_pck; if ((sock_tmp = accept(tcp_list, (struct sockaddr*)&addr, &len)) < 0) { perror("accept_conn error - accept failed"); return -1; } if (nsock >= max_tcp_sock) { printf("accept_conn - can't accept more connection %s:%u\n", inet_ntoa(addr.sin_addr), ntohs(addr.sin_port)); new_err_packet(&send_pck, 0); if (send_packet_tcp(sock_tmp, &send_pck) < 0) { perror("bad write"); return -1; } if (close(sock_tmp) < 0) { perror("accept_conn error - close failed"); return -1; } return 0; } new_ack_packet(&send_pck, 0); if (send_packet_tcp(sock_tmp, &send_pck) < 0) { perror("bad write"); return -1; } if ((nread = read(sock_tmp, (char *)&port, sizeof(port))) != sizeof(port)) { if (nread < 0) { perror("accept_conn error - read failed"); } else { fprintf(stderr, "accept_conn error - bad packet format\n"); } return -1; } printf("connessione accettata da %s:%d\n", inet_ntoa(addr.sin_addr), ntohs(addr.sin_port)); fd_add(sock_tmp); addr.sin_port = port; if ((rc = pthread_mutex_lock(&NEAR_LIST_LOCK)) != 0) { fprintf(stderr, "accept_conn error - can't acquire lock: %s\n", strerror(rc)); return -1; } if (insert_near(sock_tmp, &addr) < 0) { fprintf(stderr, "join_overlay error - insert_near failed\n"); return -1; } set_near(); printf("accept_conn setto la stringa dei vicini\n"); if ((rc = pthread_mutex_unlock(&NEAR_LIST_LOCK)) != 0) { fprintf(stderr, "accept_conn error - can't release lock: %s\n", strerror(rc)); return -1; } addr_list = str_to_addr(near_str, max_tcp_sock); for(j = 0 ; j < max_tcp_sock; j ++){ printf("accept - near %s:%d\n", inet_ntoa(addr_list[j].sin_addr), ntohs(addr_list[j].sin_port)); } nsock ++; return 0; }
int service_start(const char *name, int sock, service_limit_func_t *limitfunc, service_command_func_t *commandfunc, int argc, char *argv[]) { struct service *service; struct service_connection *sconn, *sconntmp; fd_set fds; int maxfd, nfds, serrno; assert(argc == 2); pjdlog_init(PJDLOG_MODE_STD); pjdlog_debug_set(atoi(argv[1])); service = service_alloc(name, limitfunc, commandfunc); if (service == NULL) return (errno); if (service_connection_add(service, sock, NULL) == NULL) { serrno = errno; service_free(service); return (serrno); } for (;;) { FD_ZERO(&fds); maxfd = -1; for (sconn = service_connection_first(service); sconn != NULL; sconn = service_connection_next(sconn)) { maxfd = fd_add(&fds, maxfd, service_connection_get_sock(sconn)); } PJDLOG_ASSERT(maxfd >= 0); PJDLOG_ASSERT(maxfd + 1 <= (int)FD_SETSIZE); nfds = select(maxfd + 1, &fds, NULL, NULL, NULL); if (nfds < 0) { if (errno != EINTR) pjdlog_errno(LOG_ERR, "select() failed"); continue; } else if (nfds == 0) { /* Timeout. */ PJDLOG_ABORT("select() timeout"); continue; } for (sconn = service_connection_first(service); sconn != NULL; sconn = sconntmp) { /* * Prepare for connection to be removed from the list * on failure. */ sconntmp = service_connection_next(sconn); if (FD_ISSET(service_connection_get_sock(sconn), &fds)) service_message(service, sconn); } if (service_connection_first(service) == NULL) { /* * No connections left, exiting. */ break; } } return (0); }
int do_loop(void) { int efd; int sfd; int rc; int connfd; struct epoll_event event; struct epoll_event *events; tor_array_t *cache_sock; cache_sock = tor_array_new(TOR_MAX_EVENT, sizeof(http_context *)); events = calloc(TOR_MAX_EVENT, sizeof(struct epoll_event)); if (!events) { perror(""); exit(EXIT_FAILURE); } rc = 0; sfd = create_and_bind(INADDR_ANY, config.port); if (sfd < 0) { exit(EXIT_FAILURE); } rc = set_fl(sfd, O_NONBLOCK); if (rc < 0) { exit(EXIT_FAILURE); } rc = listen(sfd, 10); if (rc < 0) { perror("listen"); exit(EXIT_FAILURE); } efd = epoll_create1(0); if (efd < 0) { perror(""); exit(EXIT_FAILURE); } if (fd_add(efd, sfd) < 0) exit(EXIT_FAILURE); int i, n; http_context *http; for (;;) { n = epoll_wait(efd, events, TOR_MAX_EVENT, -1); for (i = 0; i < n; i++) { if ((events[i].events & EPOLLERR) || (events[i].events & EPOLLHUP) || !(events[i].events & EPOLLIN)) { close(events[i].data.fd); tor_log_err("epoll error %d\n", events[i].data.fd); } else if (events[i].data.fd == sfd) { for (;;) { connfd = accept(sfd, NULL, NULL); if (connfd == -1) { if ((errno != EAGAIN) && (errno != EWOULDBLOCK)) { perror("accept"); } break; } if (set_fl(connfd, O_NONBLOCK) < 0) { perror("set_fl"); exit(EXIT_FAILURE); } if (fd_add(efd, connfd) < 0) { perror("fd_add"); exit(EXIT_FAILURE); } http = http_new(connfd, list_dir, sock_read, writen_nonblock); fprintf(stderr, "put fd = %d:sfd = %d http = %p\n", connfd, sfd, http); tor_array_put(cache_sock, connfd, &http); } } else { fprintf(stderr, "get fd = %d\n", events[i].data.fd); http = *(http_context **)tor_array_get(cache_sock, events[i].data.fd); fprintf(stderr, "fd = %d\n", http->fd); http_read_head(http); do_process(http); http_free(http); } } fprintf(stderr, "=============\n"); } close(sfd); close(efd); }
int main(int argc, char **argv) { struct epoll_event events[1024]; int pending; int i, n, r; (void) argc; if (argv[1] == NULL || (n_conns = atoi(argv[1])) == 0) n_conns = 100; /* x2 for both ends of streams, +2 for server and timerfd conn_rec */ E(conns = calloc(n_conns * 2 + 2, sizeof(*conns))); E(client_conns = calloc(n_conns, sizeof(**client_conns))); E(server_conns = calloc(n_conns, sizeof(**server_conns))); E(epfd = epoll_create1(0)); E(svfd = socket(AF_INET, SOCK_STREAM|SOCK_NONBLOCK, 0)); { int yes = 1; E(setsockopt(svfd, SOL_SOCKET, SO_REUSEADDR, &yes, sizeof yes)); } { struct sockaddr_in s; s.sin_addr.s_addr = htonl(INADDR_LOOPBACK); s.sin_family = AF_INET; s.sin_port = htons(PORT); E(bind(svfd, (struct sockaddr *) &s, sizeof s)); } E(listen(svfd, 1024)); fd_add(svfd, EPOLLIN); for (pending = i = 0; i < n_conns; i++) { struct sockaddr_in s; conn_rec *c; int fd; E(fd = socket(AF_INET, SOCK_STREAM|SOCK_NONBLOCK, 0)); s.sin_addr.s_addr = htonl(INADDR_LOOPBACK); s.sin_family = AF_INET; s.sin_port = htons(PORT); if (connect(fd, (struct sockaddr *) &s, sizeof s) == 0) c = fd_add(fd, EPOLLIN); else if (errno != EINPROGRESS) report_error("connect", errno); else { c = fd_add(fd, EPOLLOUT); pending++; } client_conns[n_client_conns++] = c; } while (pending) { E(n = epoll_wait(epfd, events, ARRAY_SIZE(events), -1)); for (i = 0; i < n; i++) { conn_rec *c = events[i].data.ptr; if (c->fd == svfd) { struct sockaddr_in s; socklen_t len; int fd; len = sizeof s; E(fd = accept4(svfd, (struct sockaddr *) &s, &len, SOCK_NONBLOCK)); server_conns[n_server_conns++] = fd_add(fd, EPOLLIN); } else { socklen_t len; int status; len = sizeof status; E(getsockopt(c->fd, SOL_SOCKET, SO_ERROR, &status, &len)); if (status) report_error("getsockopt(SO_ERROR)", EINVAL); fd_mod(c, EPOLLIN); pending--; } } } //assert(n_client_conns == n_server_conns); for (i = 0; i < n_client_conns; i++) { conn_rec *c = client_conns[i]; r = write(c->fd, "PING", 4); //assert(r == 4); fd_mod(c, EPOLLIN|EPOLLOUT); c->events = EPOLLIN; } for (i = 0; i < n_server_conns; i++) { conn_rec *c = server_conns[i]; do_write(c->fd, "PONG", 4); fd_mod(c, EPOLLIN|EPOLLOUT); c->events = EPOLLIN; } fd_add(make_timer_fd(2000), EPOLLIN); while (1) { E(n = epoll_wait(epfd, events, ARRAY_SIZE(events), -1)); for (i = 0; i < n; i++) { conn_rec *c = events[i].data.ptr; if (c->fd == tmfd) { do_read(c->fd); do_report(); continue; } if ((events[i].events & EPOLLIN) & (c->events & EPOLLIN)) { do_read(c->fd); c->events = EPOLLOUT; continue; } if ((events[i].events & EPOLLOUT) & (c->events & EPOLLOUT)) { do_write(c->fd, "PING", 4); c->events = EPOLLIN; continue; } } } return 0; }
void main_loop( void ) { int listenfd,fd, nready; struct sockaddr client; ssize_t client_len; fd_set read_set; struct timeval timeout, timeofday_old, timeofday_new; struct timezone tz; listenfd = net_listen(NULL,g_server.port); if( listenfd < 0 ) return; max_fd=listenfd; FD_ZERO(&all_set); FD_SET(listenfd,&all_set); if( g_server.with_console ) { FD_SET(CONSOLE_FD, &all_set); } #define TIMEOUT_SEC (180) /* 3 minutes */ /* 5 minutes */ timeout.tv_sec = TIMEOUT_SEC; timeout.tv_usec = 0; gettimeofday( &timeofday_old, &tz ); memset( &tz, 0, sizeof(tz) ); while(1) { read_set = all_set; nready = select( max_fd+1, &read_set, NULL, NULL, &timeout ); /* recompute the timeout */ if( gettimeofday( &timeofday_new, &tz ) == 0 ) { int s = timeofday_new.tv_sec - timeofday_old.tv_sec; if( TIMEOUT_SEC > s ) timeout.tv_sec = TIMEOUT_SEC - s; else timeout.tv_sec = TIMEOUT_SEC; /* it is aprox 3 minutes */ if( s == 0 ) timeout.tv_usec = timeofday_new.tv_usec - timeofday_old.tv_usec; else timeout.tv_usec = 0; /* may occur sometimes */ if( s > TIMEOUT_SEC ) { timeout.tv_sec = TIMEOUT_SEC; timeout.tv_usec = 0; gettimeofday( &timeofday_old, &tz ); server_is_idle(); } } /* error ?*/ if( nready == -1 ) { if(errno!=EINTR) { fprintf(stderr,_("tegserver: Abnormal error in select()\n")); perror("tegserver:"); } continue; /* timeout ? */ } else if( nready == 0 ) { MAIN_DEBUG("timeout\n"); timeout.tv_sec = TIMEOUT_SEC; timeout.tv_usec = 0; gettimeofday( &timeofday_old, &tz ); server_is_idle(); continue; } /* new client */ if(FD_ISSET( listenfd, &read_set) ) { MAIN_DEBUG("new client\n"); client_len = sizeof( client ); fd = accept( listenfd, (struct sockaddr *)&client, &client_len ); if( fd != -1 ) fd_add( fd ); if(--nready <= 0) continue; } /* input from console */ if( g_server.with_console && FD_ISSET(CONSOLE_FD, &read_set)) { TEG_STATUS ts = console_handle(CONSOLE_FD); if(ts==TEG_STATUS_GAMEOVER || ts==TEG_STATUS_CONNCLOSED) server_exit(listenfd); if(--nready <= 0) continue; } /* input from players */ for(fd=0;fd<=max_fd;fd++) { if( (fd!=listenfd && fd!=CONSOLE_FD) && FD_ISSET(fd,&read_set) ) { if(play_teg( fd )==TEG_STATUS_CONNCLOSED) { MAIN_DEBUG("closing connection\n"); /* kick robots if they are alone */ player_kick_unparent_robots(); } if(--nready <= 0) break; } } } }