int Ctcs::Connect() { ssize_t r; m_last_timestamp = now; if( _s2sin(m_host, m_port, &m_sin) < 0 ){ CONSOLE.Warning(2, "warn, get CTCS ip address failed."); return -1; } m_sock = socket(AF_INET, SOCK_STREAM, 0); if( INVALID_SOCKET == m_sock ) return -1; if( setfd_nonblock(m_sock) < 0 ){ CLOSE_SOCKET(m_sock); m_sock = INVALID_SOCKET; return -1; } r = connect_nonb(m_sock, (struct sockaddr *)&m_sin); if( r == -1 ){ CLOSE_SOCKET(m_sock); m_sock = INVALID_SOCKET; return -1; }else if( r == -2 ){ m_status = DT_TRACKER_CONNECTING; }else{ m_status = DT_TRACKER_READY; if(*cfg_verbose) CONSOLE.Debug("Connected to CTCS"); if( Send_Protocol() != 0 && errno != EINPROGRESS ){ CONSOLE.Warning(2, "warn, send protocol to CTCS failed: %s", strerror(errno)); return -1; } if( Send_Auth() != 0 && errno != EINPROGRESS ){ CONSOLE.Warning(2, "warn, send password to CTCS failed: %s", strerror(errno)); return -1; } if( Send_Torrent(BTCONTENT.GetPeerId(), BTCONTENT.GetMetainfoFile()) < 0 && errno != EINPROGRESS ){ CONSOLE.Warning(2, "warn, send torrent to CTCS failed: %s", strerror(errno)); return -1; } } return 0; }
int btTracker::Connect() { ssize_t r; time(&m_last_timestamp); if (_s2sin(m_host, m_port, &m_sin) < 0) { CONSOLE.Warning(2, "warn, get tracker's ip address failed."); return -1; } m_sock = socket(AF_INET, SOCK_STREAM, 0); if (INVALID_SOCKET == m_sock) return -1; // we only need to bind if we have specified an ip // we need it to bind here before the connect!!!! if (cfg_listen_ip != 0) { struct sockaddr_in addr; // clear the struct as requested in the manpages memset(&addr, 0, sizeof(sockaddr_in)); // set the type addr.sin_family = AF_INET; // we want the system to choose port addr.sin_port = 0; // set the defined ip from the commandline addr.sin_addr.s_addr = cfg_listen_ip; // bind it or return... if (bind (m_sock, (struct sockaddr *) &addr, sizeof(struct sockaddr_in)) != 0) { CONSOLE.Warning(1, "warn, can't set up tracker connection: %s", strerror(errno)); return -1; } } if (setfd_nonblock(m_sock) < 0) { CLOSE_SOCKET(m_sock); return -1; } r = connect_nonb(m_sock, (struct sockaddr *) &m_sin); if (r == -1) { CLOSE_SOCKET(m_sock); return -1; } else if (r == -2) m_status = T_CONNECTING; else { if (arg_verbose) CONSOLE.Debug("Connected to tracker"); if (0 == SendRequest()) m_status = T_READY; else { CLOSE_SOCKET(m_sock); return -1; } } return 0; }
int su_serv_create(su_serv_t *psvr, const SA *saddr, socklen_t servlen, int nthread) { if (nthread <= 0) { errno = EINVAL; return -1; } psvr->fd = socket(saddr->sa_family, SOCK_DGRAM, 0); if (psvr->fd < 0) { err_ret("serv %x create failed, socket error", psvr); return -1; } if (bind(psvr->fd, saddr, servlen) < 0) { close(psvr->fd); psvr->fd = -1; return -1; } if (setfd_nonblock(psvr->fd) < 0) { close(psvr->fd); psvr->fd = -1; return -1; } memset(&psvr->servaddr, 0, sizeof(SAUN)); memcpy(&psvr->servaddr, saddr, servlen); psvr->servlen = servlen; psvr->seq = 0; psvr->rttinit = 0; psvr->retry = RTT_MAXNREXMT; psvr->ackwaitnum = 0; list_init(&psvr->ackrecvls); list_init(&psvr->synrecvls); list_init(&psvr->lsackcache); rbt_init(&psvr->rbackcache, cache_getkey, search_cache_cmp); pthread_mutex_init(&psvr->mutex, 0); pthread_mutex_init(&psvr->lock, 0); pthread_cond_init(&psvr->ackcond, 0); pthread_cond_init(&psvr->syncond, 0); pthread_mutex_init(&psvr->cachelock, 0); if (su_serv_thread_install(psvr, nthread) < 0) { pthread_mutex_destroy(&psvr->mutex); pthread_mutex_destroy(&psvr->lock); pthread_mutex_destroy(&psvr->cachelock); pthread_cond_destroy(&psvr->ackcond); pthread_cond_destroy(&psvr->syncond); close(psvr->fd); psvr->fd = -1; return -1; } pthread_mutex_lock(&emutex); if (sugem == 0) { sugem = Em_open(100, -1, 0, 0, 0); Em_run(sugem); struct timeval now; gettimeofday(&now, 0); srand(now.tv_sec % 1000 + now.tv_usec); } psvr->sid = rand() % 65535; pthread_mutex_unlock(&emutex); memset(&psvr->fe, 0, sizeof(fe_t)); fe_init(&psvr->fe, sugem, psvr->fd); fe_set(&psvr->fe, EPOLLIN, handle_su_serv_recv); fe_set(&psvr->fe, EPOLLET, 0); Fe_em_add(&psvr->fe); return psvr->fd; }
int su_peer_create_bind(su_peer_t *psar, int port, const SA *destaddr, socklen_t destlen) { psar->fd = socket(destaddr->sa_family, SOCK_DGRAM, 0); if (psar->fd < 0) { err_ret("peer %x create failed, socket error", psar); return -1; } if (port > 0 && port <= 65535) { void *paddr; SA4 s4; SA6 s6; switch (destaddr->sa_family) { case PF_INET: memcpy(&s4, destaddr, destlen); /* for sin_family and more... */ s4.sin_port = htons(port); inet_pton(PF_INET, "0.0.0.0", &s4.sin_addr.s_addr); paddr = &s4; break; case PF_INET6: memcpy(&s6, destaddr, destlen); /* for sin6_family and more... */ s6.sin6_port = htons(port); inet_pton(PF_INET6, "::", &s6.sin6_addr.__in6_u); paddr = &s6; break; default: close(psar->fd); psar->fd = -1; errno = EINVAL; return -1; } int reuse = 1; if (setsockopt(psar->fd, SOL_SOCKET, SO_REUSEADDR, &reuse, sizeof(int)) < 0) { close(psar->fd); psar->fd = -1; return -1; } if (bind(psar->fd, paddr, destlen) < 0) { close(psar->fd); psar->fd = -1; return -1; } } if (setfd_nonblock(psar->fd) < 0) { close(psar->fd); psar->fd = -1; return -1; } memset(&psar->destaddr, 0, sizeof(SAUN)); memcpy(&psar->destaddr, destaddr, destlen); psar->destlen = destlen; psar->seq = 0; psar->rttinit = 0; psar->retry = RTT_MAXNREXMT; psar->ackwaitnum = 0; list_init(&psar->ackrecvls); list_init(&psar->synrecvls); list_init(&psar->lsackcache); rbt_init(&psar->rbackcache, cache_getkey, search_cache_cmp); psar->nowsynframe = 0; pthread_mutex_init(&psar->mutex, 0); pthread_mutex_init(&psar->lock, 0); pthread_cond_init(&psar->ackcond, 0); pthread_cond_init(&psar->syncond, 0); pthread_mutex_init(&psar->cachelock, 0); if (su_peer_thread_install(psar) < 0) { pthread_mutex_destroy(&psar->mutex); pthread_mutex_destroy(&psar->lock); pthread_cond_destroy(&psar->ackcond); pthread_cond_destroy(&psar->syncond); pthread_mutex_destroy(&psar->cachelock); close(psar->fd); psar->fd = -1; return -1; } pthread_mutex_lock(&emutex); if (sugem == 0) { sugem = Em_open(100, -1, 0, 0, 0); Em_run(sugem, 1); struct timeval now; gettimeofday(&now, 0); srand(now.tv_sec % 1000 + now.tv_usec); } psar->sid = rand() % 65535; pthread_mutex_unlock(&emutex); memset(&psar->fe, 0, sizeof(fe_t)); fe_init(&psar->fe, sugem, psar->fd); fe_set(&psar->fe, EPOLLIN, handle_su_peer_recv); fe_set(&psar->fe, EPOLLET, 0); Fe_em_add(&psar->fe); return psar->fd; }
int btTracker::Connect() { struct sockaddr_in sin; ssize_t r; m_result = DT_NORMAL; m_last_timestamp = now; if( _s2sin(m_spec->host, m_spec->port, &sin) < 0 ){ CONSOLE.Warning(2, "warn, get tracker's ip address failed."); return -1; } m_sock = socket(AF_INET, SOCK_STREAM, 0); if( INVALID_SOCKET == m_sock ){ CONSOLE.Warning(2, "warn, tracker socket allocation failed: %s", strerror(errno)); return -1; } /* we only need to bind if we have specified an ip we need it to bind here before the connect! */ if( *cfg_listen_ip != 0 ){ struct sockaddr_in addr; // clear the struct as requested in the manpages memset(&addr, 0, sizeof(sockaddr_in)); // set the type addr.sin_family = AF_INET; // we want the system to choose port addr.sin_port = 0; // set the defined ip from the commandline addr.sin_addr.s_addr = *cfg_listen_ip; // bind it or return... if( bind(m_sock, (struct sockaddr *)&addr, sizeof(struct sockaddr_in)) != 0 ){ CONSOLE.Warning(1, "warn, can't set up tracker connection: %s", strerror(errno)); return -1; } } if( setfd_nonblock(m_sock) < 0 ){ CONSOLE.Warning(2, "warn, tracker socket setup failed: %s", strerror(errno)); CLOSE_SOCKET(m_sock); m_sock = INVALID_SOCKET; return -1; } r = connect_nonb(m_sock, (struct sockaddr *)&sin); if( r == -1 ){ CONSOLE.Warning(2, "warn, connect to tracker at %s failed: %s", m_spec->url, strerror(errno)); CLOSE_SOCKET(m_sock); m_sock = INVALID_SOCKET; return -1; }else if( r == -2 ){ if(*cfg_verbose) CONSOLE.Debug("Connecting to tracker at %s", m_spec->url); m_status = DT_TRACKER_CONNECTING; }else{ if(*cfg_verbose) CONSOLE.Debug("Connected to tracker at %s", m_spec->url); if( 0 == SendRequest() ) m_status = DT_TRACKER_READY; else{ CLOSE_SOCKET(m_sock); m_sock = INVALID_SOCKET; return -1; } } return 0; }
int main(int argc, char *argv[]) { pid_t child_pid; int child_exit_status; struct termios tty_attr; struct winsize window_size; int pty_master; /* for select */ fd_set readfds; fd_set writefds; unsigned err_n_rpty = 0; unsigned err_n_wpty = 0; unsigned err_n_stdin = 0; unsigned err_n_stdout = 0; int done = 0; /* the ring buffers */ char inbuf_mem[BUFSIZE]; char outbuf_mem[BUFSIZE]; struct ring_buffer inbuf; struct ring_buffer outbuf; rb_init(&inbuf, inbuf_mem, sizeof(inbuf_mem)); rb_init(&outbuf, outbuf_mem, sizeof(outbuf_mem)); if (argc == 1) { printf("usage: %s PROGRAM [ARGS]...\n", argv[0]); exit(1); } /* We need I/O calls to fail with EINTR on SIGCHLD... */ if (signal(SIGCHLD, sigchld_handler) == SIG_ERR) { perror("signal(SIGCHLD,...)"); exit(EX_OSERR); } if (isatty(STDIN_FILENO)) { /* get terminal parameters associated with stdout */ if (tcgetattr(STDOUT_FILENO, &tty_attr) < 0) { perror("tcgetattr(stdout,...)"); exit(EX_OSERR); } /* get window size */ if (ioctl(STDOUT_FILENO, TIOCGWINSZ, &window_size) < 0) { perror("ioctl(stdout,...)"); exit(1); } child_pid = forkpty(&pty_master, NULL, &tty_attr, &window_size); } else { /* not interactive */ child_pid = forkpty(&pty_master, NULL, NULL, NULL); } if (child_pid < 0) { perror("forkpty()"); exit(EX_OSERR); } if (child_pid == 0) { /* in the child */ struct termios s_tty_attr; if (tcgetattr(STDIN_FILENO, &s_tty_attr)) { perror("tcgetattr(stdin,...)"); exit(EXIT_FAILURE); } /* Turn off echo */ s_tty_attr.c_lflag &= ~(ECHO | ECHOE | ECHOK | ECHONL); /* Also turn of NL to CR?LF on output */ s_tty_attr.c_oflag &= ~(ONLCR); if (tcsetattr(STDIN_FILENO, TCSANOW, &s_tty_attr)) { perror("tcsetattr(stdin,...)"); exit(EXIT_FAILURE); } if (execvp(argv[1], argv + 1)) { perror("execvp()"); exit(EXIT_FAILURE); } } /* Non blocking mode for all file descriptors. */ setfd_nonblock(pty_master); setfd_nonblock(STDIN_FILENO); setfd_nonblock(STDOUT_FILENO); if (isatty(STDIN_FILENO)) { if (tty_semi_raw(STDIN_FILENO) < 0) { perror("tty_semi_raw(stdin)"); } if (atexit(tty_atexit) < 0) { perror("atexit()"); } } do { /* Accept events only on fds, that we can handle now. */ int do_select = 0; FD_ZERO(&readfds); FD_ZERO(&writefds); if (rb_space(&outbuf) > 0 && err_n_rpty < MAXRETR) { FD_SET(pty_master, &readfds); do_select = 1; } if (!rb_isempty(&inbuf) && err_n_wpty < MAXRETR) { FD_SET(pty_master, &writefds); do_select = 1; } if (rb_space(&inbuf) > 0 && err_n_stdin < MAXRETR) { FD_SET(STDIN_FILENO, &readfds); do_select = 1; } if (!rb_isempty(&outbuf) && err_n_stdout < MAXRETR) { FD_SET(STDOUT_FILENO, &writefds); do_select = 1; } if (!do_select) { #ifdef DEBUG fprintf(stderr, "No I/O job for us, calling waitpid()...\n"); #endif while (waitpid(child_pid, &child_exit_status, 0) < 0) { /* nothing */ } break; } errno = 0; int select_rc = select(pty_master + 1, &readfds, &writefds, NULL, NULL); if (select_rc < 0 && errno != EINTR) { perror("select()"); exit(EX_IOERR); } #ifdef DEBUG fprintf(stderr, "select() returned %d\n", select_rc); #endif if (FD_ISSET(STDOUT_FILENO, &writefds)) { #ifdef DEBUG fprintf(stderr, "stdout can be written\n"); #endif ssize_t n = rb_write(&outbuf, STDOUT_FILENO); if (n <= 0 && n != EINTR && n != EAGAIN) err_n_stdout++; #ifdef DEBUG if (n >= 0) fprintf(stderr, "%d bytes written into stdout\n", n); else perror("write(stdout,...)"); #endif } if (FD_ISSET(pty_master, &writefds)) { #ifdef DEBUG fprintf(stderr, "pty_master can be written\n"); #endif ssize_t n = rb_write(&inbuf, pty_master); if (n <= 0 && n != EINTR && n != EAGAIN) err_n_wpty++; #ifdef DEBUG if (n >= 0) fprintf(stderr, "%d bytes written into pty_master\n", n); else perror("write(pty_master,...)"); #endif } if (FD_ISSET(STDIN_FILENO, &readfds)) { #ifdef DEBUG fprintf(stderr, "stdin can be read\n"); #endif ssize_t n = rb_read(&inbuf, STDIN_FILENO); if (n <= 0 && n != EINTR && n != EAGAIN) err_n_stdin++; #ifdef DEBUG if (n >= 0) fprintf(stderr, "%d bytes read from stdin\n", n); else perror("read(stdin,...)"); #endif } if (FD_ISSET(pty_master, &readfds)) { #ifdef DEBUG fprintf(stderr, "pty_master can be read\n"); #endif ssize_t n = rb_read(&outbuf, pty_master); if (n <= 0 && n != EINTR && n != EAGAIN) err_n_rpty++; #ifdef DEBUG if (n >= 0) fprintf(stderr, "%d bytes read from pty_master\n", n); else perror("read(pty_master,...)"); #endif } if (!done && waitpid(child_pid, &child_exit_status, WNOHANG) > 0) done = 1; } while (!done || !(rb_isempty(&inbuf) || err_n_wpty >= MAXRETR) || !(rb_isempty(&outbuf) || err_n_stdout >= MAXRETR)); #ifdef DEBUG fprintf(stderr, "inbuf: %u bytes left, outbuf: %u bytes left\n", inbuf.count, outbuf.count); fprintf(stderr, "err_n_rpty=%u, err_n_wpty=%u, err_n_stdin=%u, err_n_stdout=%u\n", err_n_rpty, err_n_wpty, err_n_stdin, err_n_stdout); #endif if (WIFEXITED(child_exit_status)) exit(WEXITSTATUS(child_exit_status)); else if (WIFSIGNALED(child_exit_status)) exit(128 + WTERMSIG(child_exit_status)); exit(EXIT_FAILURE); }