bool rch_push_data_block(rch_t *rch, data_block_t *data_blk) { if (!data_frame_push_data_block(rch->data_fr, data_blk)) { LOG(DBG, "RCH: block fail"); return false; } if (data_frame_blocks(rch->data_fr) != 1) { LOG(WTF, "block lenght != 1"); return false; } uint8_t data[(92 + 7) / 8]; const int size = data_frame_get_bytes(rch->data_fr, data); if (size != 64) { LOG(WTF, "invalid frame lenght"); return false; } if (!check_fcs(data, size)) { LOG(DBG, "invalid FCS"); return false; } rch->rch_data.naddrs = 0; for (int i = 0; i < ARRAY_LEN(rch->rch_data.addrs); ++i) { addr_parse(&rch->rch_data.addrs[rch->rch_data.naddrs], data + 2*i, 0); if (!addr_is_tti_no_st(&rch->rch_data.addrs[rch->rch_data.naddrs], true)) { ++rch->rch_data.naddrs; } } return true; }
int net_bind( const char name[], const char addr[], const char port[], const char ifce[], int protocol, int af ) { char addrbuf[FULL_ADDSTRLEN+1]; const int opt_on = 1; int sock; socklen_t addrlen; IP sockaddr; if( af == AF_INET ) { addrlen = sizeof(IP4); } else if( af == AF_INET6 ) { addrlen = sizeof(IP6); } else { log_err( "%s: Unknown address family value.", name ); return -1; } if( addr_parse( &sockaddr, addr, port, af ) != 0 ) { log_err( "%s: Failed to parse IP address '%s' and port '%s'.", name, addr, port ); return -1; } if( (sock = net_socket( name, ifce, protocol, af )) < 0 ) { return -1; } if( af == AF_INET6 ) { if( setsockopt( sock, IPPROTO_IPV6, IPV6_V6ONLY, &opt_on, sizeof(opt_on) ) < 0 ) { close( sock ); log_err( "%s: Failed to set socket option IPV6_V6ONLY: %s", name, strerror( errno )); return -1; } } if( bind( sock, (struct sockaddr*) &sockaddr, addrlen ) < 0 ) { close( sock ); log_err( "%s: Failed to bind socket to address: '%s'", name, strerror( errno ) ); return -1; } if( protocol == IPPROTO_TCP && listen( sock, 5 ) < 0 ) { close( sock ); log_err( "%s: Failed to listen on socket: '%s'", name, strerror( errno ) ); return -1; } log_info( ifce ? "%s: Bind to %s, interface %s" : "%s: Bind to %s", name, str_addr( &sockaddr, addrbuf ), ifce ); return sock; }
/*! \brief Check if query fits the template requirements. */ static int template_match(int state, synth_template_t *tpl, knot_pkt_t *pkt, struct query_data *qdata) { /* Parse address from query name. */ char addr_str[SOCKADDR_STRLEN] = { '\0' }; int ret = addr_parse(qdata, tpl, addr_str); if (ret != KNOT_EOK) { return state; /* Can't identify addr in QNAME, not applicable. */ } /* Match against template netblock. */ struct sockaddr_storage query_addr = { '\0' }; int provided_af = tpl->subnet.ss.ss_family; ret = sockaddr_set(&query_addr, provided_af, addr_str, 0); if (ret == KNOT_EOK) { ret = netblock_match(&tpl->subnet, &query_addr); } if (ret != 0) { return state; /* Out of our netblock, not applicable. */ } /* Check if the request is for an available query type. */ uint16_t qtype = knot_pkt_qtype(qdata->query); switch (tpl->type) { case SYNTH_FORWARD: if (!query_satisfied_by_family(qtype, provided_af)) { qdata->rcode = KNOT_RCODE_NOERROR; return NODATA; } break; case SYNTH_REVERSE: if (qtype != KNOT_RRTYPE_PTR && qtype != KNOT_RRTYPE_ANY) { qdata->rcode = KNOT_RCODE_NOERROR; return NODATA; } break; default: break; } /* Synthetise record from template. */ knot_rrset_t *rr = synth_rr(addr_str, tpl, pkt, qdata); if (rr == NULL) { qdata->rcode = KNOT_RCODE_SERVFAIL; return ERROR; } /* Insert synthetic response into packet. */ if (knot_pkt_put(pkt, 0, rr, KNOT_PF_FREE) != KNOT_EOK) { return ERROR; } /* Authoritative response. */ knot_wire_set_aa(pkt->wire); return HIT; }
/* handle 'GET /blacklist?1.2.3.4' */ void handle_blacklist( char *reply_buf, char *params ) { IP addr; if( addr_parse( &addr, params, NULL, AF_UNSPEC ) == 0 ) { kad_blacklist( &addr ); sprintf( reply_buf , "done\n" ); } else { sprintf( reply_buf , "failed\n" ); } }
void on_lookup_handle(const char *line, PurpleConnection *gc, PurpleBuddy *buddy) { purple_debug_info("plainprpl", "on_lookup_handle: %s\n", line); plain_plugin_state *pstate; plain_buddy_state *bstate; pstate = purple_connection_get_protocol_data(gc); bstate = purple_buddy_get_protocol_data(buddy); addr_parse(&bstate->addr, line, PLAIN_DEFAULT_PORT_STR, pstate->sockaf); }
int cmd_blacklist( REPLY *r, const char *addr_str ) { char addrbuf[FULL_ADDSTRLEN+1]; IP addr; if( addr_parse( &addr, addr_str, NULL, gconf->af ) != 0 ) { r_printf( r, "Invalid address.\n" ); return 1; } else { kad_blacklist( &addr ); r_printf( r, "Added to blacklist: %s\n", str_addr( &addr, addrbuf ) ); return 0; } }
void lpd_setup( void ) { int sock; g_packet_limit = PACKET_LIMIT_MAX; if( addr_parse( &g_lpd_addr, gconf->lpd_addr, LPD_PORT, gconf->af ) != 0 ) { log_err( "BOOT: Failed to parse IP address for '%s'.", gconf->lpd_addr ); } if( gconf->lpd_disable ) { return; } sock = create_receive_socket(); net_add_handler( sock, &handle_mcast ); }
void lpd_setup( void ) { g_packet_limit = PACKET_LIMIT_MAX; if( addr_parse( &g_lpd_addr, gconf->lpd_addr, DHT_PORT_MCAST, gconf->af ) != 0 ) { log_err( "BOOT: Failed to parse IP address for '%s'.", gconf->lpd_addr ); } if( gconf->lpd_disable ) { return; } /* * Use different sockets for sending and receiving because * MacOSX does not seem to allow it to be the same. */ g_sock_send = create_send_socket(); g_sock_recv = create_receive_socket(); net_add_handler( g_sock_recv, &bootstrap_handle_mcast ); }
/* from_strip() -- Transforms "Name <login@host>" into "login@host" or "login@host (Real name)" */ char *from_strip(char *str) { char *p; #if 0 (void)fprintf(stderr, "*** from_strip(): str = [%s]\n", str); #endif if(strncmp("From:", str, 5) == 0) { str += 5; } /* Remove the real name if necessary - just send the address */ if((p = addr_parse(str)) == (char *)NULL) { die("from_strip() -- addr_parse() failed"); } #if 0 (void)fprintf(stderr, "*** from_strip(): p = [%s]\n", p); #endif return(strdup(p)); }
int ot_tunneling_udp(int lfd) { fd_set initfds; fd_set rfds; int fd, nfds, ret, rcvlen; size_t buflen; unsigned char rcvbuf[65535]; /// Maxinum of UDP packet size is 65535 void* buf; udp_session_t* s; struct sockaddr_in caddr; /// Client address struct sockaddr_in raddr; /// Remote host address socklen_t raddr_len; socklen_t caddr_len; time_t curtime, gctime; struct timeval to; gctime = time(NULL); /// 1. Waiting client data or server data /// 2. Tunneling data /// 2.1 Got cilent data /// 2.1.1 Client is newly connected /// 2.1.1.1 Create an UDP session for it, then /// 2.1.1.2 Add relate fd to fdset, then /// 2.1.1.3 Tunneling data. /// 2.1.2 Client is exists in UDP session, just tunneling data /// 2.2 Got server data, get the related client addr, then tunneling data FD_ZERO(&initfds); FD_SET(lfd, &initfds); nfds = lfd; while (1) { /// Cleaning up timed out UDP sessions if (time(NULL) - gctime > otcfg_udp_ttl) { udps_cleanup(otcfg_udp_ttl); gctime = time(NULL); ///Rebuild fdset nfds = udps_fdset(&initfds); FD_SET(lfd, &initfds); if (lfd > nfds) { nfds = lfd; } } rfds = initfds; to.tv_sec = otcfg_udp_ttl + 1; to.tv_usec = 0; ret = select(nfds + 1, &rfds, NULL, NULL, &to); if (ret == -1) { OT_LOGE("select() error: %s\n", strerror(errno)); return -1; } else if (ret == 0) { OT_LOGD("select() timed out\n"); udps_cleanup(otcfg_udp_ttl); gctime = time(NULL); ///Rebuild fdset nfds = udps_fdset(&initfds); FD_SET(lfd, &initfds); if (lfd > nfds) { nfds = lfd; } continue; } curtime = time(NULL); if (FD_ISSET(lfd, &rfds)) { /// 在监听端口收到数据 memset(&caddr, 0x00, sizeof(caddr)); caddr_len = sizeof(caddr); rcvlen = recvfrom(lfd, rcvbuf, sizeof(rcvbuf), 0, (struct sockaddr*)&caddr, &caddr_len); if (rcvlen > 0) { OT_LOGD("Recived %d bytes from client %s:%d\n", rcvlen, inet_ntoa(caddr.sin_addr), ntohs(caddr.sin_port)); } else if (rcvlen == 0) { OT_LOGD("Client listen connection broken\n"); return 0; } else { OT_LOGE("recvfrom() fail: %s\n", strerror(errno)); continue; } s = udps_search_byladdr(caddr); if (s == NULL) { /// UDP Session is not exists udp_session_t stmp; stmp.laddr = caddr; stmp.laddr_len = sizeof(stmp.laddr); stmp.raddr = addr_parse(otcfg_target_host, otcfg_target_port); stmp.raddr_len = sizeof(stmp.raddr); /// Connect to remote stmp.fd = socket(AF_INET, SOCK_DGRAM, 0); if (stmp.fd < 0) { OT_LOGE("socket() fail while connecting to target host: %s\n", strerror(errno)); continue; } ret = connect(stmp.fd, (struct sockaddr*)&stmp.raddr, stmp.raddr_len); if (ret < 0) { OT_LOGE("connect() fail while connecting to target host: %s\n", strerror(errno)); continue; } else { OT_LOGI("Connect to %s:%d in UDP\n", inet_ntoa(stmp.raddr.sin_addr), ntohs(stmp.raddr.sin_port)); } /// Add to UDP session s = udps_add(stmp); if (s == NULL) { OT_LOGE("Can't add %s:%d to UDP session\n", inet_ntoa(stmp.laddr.sin_addr), ntohs(stmp.laddr.sin_port)); continue; } OT_LOGD("Added %s:%d to UDP session\n", inet_ntoa(stmp.laddr.sin_addr), ntohs(stmp.laddr.sin_port)); /// Update fdset if (stmp.fd > nfds) { nfds = stmp.fd; } FD_SET(stmp.fd, &initfds); } /// UDP session exists, or has been added /// Encode or decode data if (otcfg_side == OT_SIDE_SERVER) { /// Decode obfsem_decode(rcvbuf, rcvlen, &buf, &buflen); } else { /// Encode obfsem_encode(rcvbuf, rcvlen, &buf, &buflen); } /// Forwar data s->atime = curtime; ret = sendto(s->fd, buf, buflen, 0, (struct sockaddr*)&s->raddr, s->raddr_len); if (ret == 0) { OT_LOGI("Connection to target host %s:%d lost\n", inet_ntoa(s->raddr.sin_addr), ntohs(s->raddr.sin_port)); } else if (ret < 0) { OT_LOGD("sendto() fail: %s\n", strerror(errno)); } else { OT_LOGD("Sent %d bytes to target host %s:%d\n", ret, inet_ntoa(s->raddr.sin_addr), ntohs(s->raddr.sin_port)); } } /// 从远程主机收到数据 for (fd = 0; fd <= 1024; fd++) { /// FIXME: Should traverse UDP session rather than such bruce if (!FD_ISSET(fd, &rfds) || fd == lfd) { continue; } raddr_len = sizeof(raddr); rcvlen = recvfrom(fd, rcvbuf, sizeof(rcvbuf), 0, (struct sockaddr*)&raddr, &raddr_len); if (rcvlen > 0) { OT_LOGD("Recived %d bytes from remote %s:%d\n", rcvlen, inet_ntoa(raddr.sin_addr), ntohs(raddr.sin_port)); } else if (rcvlen == 0) { OT_LOGD("Remote connection broken\n"); continue; /// Continue handle next connection } else { OT_LOGE("recvfrom() fail: %s\n", strerror(errno)); continue; /// Continue handle next connection } s = udps_search_byfd(fd); if (s == NULL) { OT_LOGD("Unknown packet from %s:%d\n", inet_ntoa(raddr.sin_addr), ntohs(raddr.sin_port)); continue; } /// Encode or decode data if (otcfg_side == OT_SIDE_SERVER) { /// Encode obfsem_encode(rcvbuf, rcvlen, &buf, &buflen); } else { /// Decode obfsem_decode(rcvbuf, rcvlen, &buf, &buflen); } /// Forward data s->atime = curtime; ret = sendto(lfd, buf, buflen, 0, (struct sockaddr*)&s->laddr, s->laddr_len); if (ret == 0) { OT_LOGI("Connection to target host %s:%d lost\n", inet_ntoa(s->laddr.sin_addr), ntohs(s->laddr.sin_port)); } else if (ret < 0) { OT_LOGD("sendto() fail: %s\n", strerror(errno)); } else { OT_LOGD("Sent %d bytes to client host %s:%d\n", ret, inet_ntoa(s->laddr.sin_addr), ntohs(s->laddr.sin_port)); } } /// End of 遍历 UDP 连接列表 } /// End of while() }
int net_bind( const char *name, const char* addr, const char* port, const char* ifce, int protocol, int af ) { char addrbuf[FULL_ADDSTRLEN+1]; int sock; int val; IP sockaddr; if( af != AF_INET && af != AF_INET6 ) { log_err( "NET: Unknown address family value." ); return -1; } if( addr_parse( &sockaddr, addr, port, af ) != 0 ) { log_err( "NET: Failed to parse IP address '%s' and port '%s'.", addr, port ); return -1; } if( protocol == IPPROTO_TCP ) { sock = socket( sockaddr.ss_family, SOCK_STREAM, IPPROTO_TCP ); } else if( protocol == IPPROTO_UDP ) { sock = socket( sockaddr.ss_family, SOCK_DGRAM, IPPROTO_UDP ); } else { sock = -1; } if( sock < 0 ) { log_err( "NET: Failed to create socket: %s", strerror( errno ) ); return -1; } val = 1; if ( setsockopt( sock, SOL_SOCKET, SO_REUSEADDR, &val, sizeof(val) ) < 0 ) { close( sock ); log_err( "NET: Failed to set socket option SO_REUSEADDR: %s", strerror( errno )); return -1; } if( ifce && setsockopt( sock, SOL_SOCKET, SO_BINDTODEVICE, ifce, strlen( ifce ) ) ) { close( sock ); log_err( "NET: Unable to bind to device '%s': %s", ifce, strerror( errno ) ); return -1; } if( af == AF_INET6 ) { val = 1; if( setsockopt( sock, IPPROTO_IPV6, IPV6_V6ONLY, &val, sizeof(val) ) < 0 ) { close( sock ); log_err( "NET: Failed to set socket option IPV6_V6ONLY: %s", strerror( errno )); return -1; } } if( bind( sock, (struct sockaddr*) &sockaddr, sizeof(IP) ) < 0 ) { close( sock ); log_err( "NET: Failed to bind socket to address: '%s'", strerror( errno ) ); return -1; } if( net_set_nonblocking( sock ) < 0 ) { close( sock ); log_err( "NET: Failed to make socket nonblocking: '%s'", strerror( errno ) ); return -1; } if( protocol == IPPROTO_TCP && listen( sock, 5 ) < 0 ) { close( sock ); log_err( "NET: Failed to listen on socket: '%s'", strerror( errno ) ); return -1; } log_info( ifce ? "%s: Bind to %s, interface %s" : "%s: Bind to %s" , name, str_addr( &sockaddr, addrbuf ), ifce ); return sock; }
/* rcpt_parse() -- Break To|Cc|Bcc into individual addresses */ void rcpt_parse(char *str) { bool_t in_quotes = False, got_addr = False; char *p, *q, *r; #if 0 (void)fprintf(stderr, "*** rcpt_parse(): str = [%s]\n", str); #endif if((p = strdup(str)) == (char *)NULL) { die("rcpt_parse(): strdup() failed"); } q = p; /* Replace <CR>, <LF> and <TAB> */ while(*q) { switch(*q) { case '\t': case '\n': case '\r': *q = ' '; } q++; } q = p; #if 0 (void)fprintf(stderr, "*** rcpt_parse(): q = [%s]\n", q); #endif r = q; while(*q) { if(*q == '"') { in_quotes = (in_quotes ? False : True); } /* End of string? */ if(*(q + 1) == (char)NULL) { got_addr = True; } /* End of address? */ if((*q == ',') && (in_quotes == False)) { got_addr = True; *q = (char)NULL; } if(got_addr) { while(*r && isspace(*r)) r++; rcpt_save(addr_parse(r)); r = (q + 1); #if 0 (void)fprintf(stderr, "*** rcpt_parse(): r = [%s]\n", r); #endif got_addr = False; } q++; } free(p); }
/* ssmtp() -- send the message (exactly one) from stdin to the mailhub SMTP port */ int ssmtp(char *argv[]) { char b[(BUF_SZ + 2)], *buf = b+1, *p, *q; #ifdef MD5AUTH char challenge[(BUF_SZ + 1)]; #endif struct passwd *pw; int i, sock; uid_t uid; bool_t minus_v_save, leadingdot, linestart = True; int timeout = 0; int bufsize = sizeof(b)-1; b[0] = '.'; outbytes = 0; ht = &headers; uid = getuid(); if((pw = getpwuid(uid)) == (struct passwd *)NULL) { die("Could not find password entry for UID %d", uid); } get_arpadate(arpadate); if(read_config() == False) { log_event(LOG_INFO, "%s not found", config_file); } if((p = strtok(pw->pw_gecos, ";,"))) { if((gecos = strdup(p)) == (char *)NULL) { die("ssmtp() -- strdup() failed"); } } revaliases(pw); /* revaliases() may have defined this */ if(uad == (char *)NULL) { uad = append_domain(pw->pw_name); } rt = &rcpt_list; header_parse(stdin); #if 1 /* With FromLineOverride=YES set, try to recover sane MAIL FROM address */ uad = append_domain(uad); #endif from = from_format(uad, override_from); /* Now to the delivery of the message */ (void)signal(SIGALRM, (void(*)())handler); /* Catch SIGALRM */ (void)alarm((unsigned) MAXWAIT); /* Set initial timer */ if(setjmp(TimeoutJmpBuf) != 0) { /* Then the timer has gone off and we bail out */ die("Connection lost in middle of processing"); } if((sock = smtp_open(mailhost, port)) == -1) { die("Cannot open %s:%d", mailhost, port); } else if (use_starttls == False) /* no initial response after STARTTLS */ { if(smtp_okay(sock, buf) == False) die("Invalid response SMTP server"); } /* If user supplied username and password, then try ELHO */ if(auth_user) { outbytes += smtp_write(sock, "EHLO %s", hostname); } else { outbytes += smtp_write(sock, "HELO %s", hostname); } (void)alarm((unsigned) MEDWAIT); if(smtp_okay(sock, buf) == False) { die("%s (%s)", buf, hostname); } /* Try to log in if username was supplied */ if(auth_user) { #ifdef MD5AUTH if(auth_pass == (char *)NULL) { auth_pass = strdup(""); } if(auth_method && strcasecmp(auth_method, "cram-md5") == 0) { outbytes += smtp_write(sock, "AUTH CRAM-MD5"); (void)alarm((unsigned) MEDWAIT); if(smtp_read(sock, buf) != 3) { die("Server rejected AUTH CRAM-MD5 (%s)", buf); } strncpy(challenge, strchr(buf,' ') + 1, sizeof(challenge)); memset(buf, 0, bufsize); crammd5(challenge, auth_user, auth_pass, buf); } else { #endif memset(buf, 0, bufsize); to64frombits(buf, auth_user, strlen(auth_user)); if (use_oldauth) { outbytes += smtp_write(sock, "AUTH LOGIN %s", buf); } else { outbytes += smtp_write(sock, "AUTH LOGIN"); (void)alarm((unsigned) MEDWAIT); if(smtp_read(sock, buf) != 3) { die("Server didn't like our AUTH LOGIN (%s)", buf); } /* we assume server asked us for Username */ memset(buf, 0, bufsize); to64frombits(buf, auth_user, strlen(auth_user)); outbytes += smtp_write(sock, buf); } (void)alarm((unsigned) MEDWAIT); if(smtp_read(sock, buf) != 3) { die("Server didn't accept AUTH LOGIN (%s)", buf); } memset(buf, 0, bufsize); to64frombits(buf, auth_pass, strlen(auth_pass)); #ifdef MD5AUTH } #endif /* We do NOT want the password output to STDERR * even base64 encoded.*/ minus_v_save = minus_v; minus_v = False; outbytes += smtp_write(sock, "%s", buf); minus_v = minus_v_save; (void)alarm((unsigned) MEDWAIT); if(smtp_okay(sock, buf) == False) { die("Authorization failed (%s)", buf); } } /* Send "MAIL FROM:" line */ outbytes += smtp_write(sock, "MAIL FROM:<%s>", uad); (void)alarm((unsigned) MEDWAIT); if(smtp_okay(sock, buf) == 0) { die("%s", buf); } /* Send all the To: adresses */ /* Either we're using the -t option, or we're using the arguments */ if(minus_t) { if(rcpt_list.next == (rcpt_t *)NULL) { die("No recipients specified although -t option used"); } rt = &rcpt_list; while(rt->next) { p = rcpt_remap(rt->string); outbytes += smtp_write(sock, "RCPT TO:<%s>", p); (void)alarm((unsigned)MEDWAIT); if(smtp_okay(sock, buf) == 0) { die("RCPT TO:<%s> (%s)", p, buf); } rt = rt->next; } } else { for(i = 1; (argv[i] != NULL); i++) { p = strtok(argv[i], ","); while(p) { /* RFC822 Address -> "foo@bar" */ q = rcpt_remap(addr_parse(p)); outbytes += smtp_write(sock, "RCPT TO:<%s>", q); (void)alarm((unsigned) MEDWAIT); if(smtp_okay(sock, buf) == 0) { die("RCPT TO:<%s> (%s)", q, buf); } p = strtok(NULL, ","); } } } /* Send DATA */ outbytes += smtp_write(sock, "DATA"); (void)alarm((unsigned) MEDWAIT); if(smtp_read(sock, buf) != 3) { /* Oops, we were expecting "354 send your data" */ die("%s", buf); } outbytes += smtp_write(sock, "Received: by %s (sSMTP sendmail emulation); %s", hostname, arpadate); if(have_from == False) { outbytes += smtp_write(sock, "From: %s", from); } if(have_date == False) { outbytes += smtp_write(sock, "Date: %s", arpadate); } #ifdef HASTO_OPTION if(have_to == False) { outbytes += smtp_write(sock, "To: postmaster"); } #endif ht = &headers; while(ht->next) { outbytes += smtp_write(sock, "%s", ht->string); ht = ht->next; } (void)alarm((unsigned) MEDWAIT); /* End of headers, start body */ outbytes += smtp_write(sock, ""); /*prevent blocking on pipes, we really shouldnt be using stdio functions like fgets in the first place */ fcntl(STDIN_FILENO,F_SETFL,O_NONBLOCK); while(!feof(stdin)) { if (!fgets(buf, bufsize, stdin)) { /* if nothing was received, then no transmission * over smtp should be done */ sleep(1); /* don't hang forever when reading from stdin */ if (++timeout >= MEDWAIT) { log_event(LOG_ERR, "killed: timeout on stdin while reading body -- message saved to dead.letter."); die("Timeout on stdin while reading body"); } continue; } /* Trim off \n, double leading .'s */ leadingdot = standardise(buf, &linestart); if (linestart || feof(stdin)) { linestart = True; outbytes += smtp_write(sock, "%s", leadingdot ? b : buf); } else { if (log_level > 0) { log_event(LOG_INFO, "Sent a very long line in chunks"); } if (leadingdot) { outbytes += fd_puts(sock, b, sizeof(b)); } else { outbytes += fd_puts(sock, buf, bufsize); } } (void)alarm((unsigned) MEDWAIT); } if(!linestart) { smtp_write(sock, ""); } /* End of body */ outbytes += smtp_write(sock, "."); (void)alarm((unsigned) MAXWAIT); if(smtp_okay(sock, buf) == 0) { die("%s", buf); } /* Close connection */ (void)signal(SIGALRM, SIG_IGN); outbytes += smtp_write(sock, "QUIT"); (void)smtp_okay(sock, buf); (void)close(sock); log_event(LOG_INFO, "Sent mail for %s (%s) uid=%d username=%s outbytes=%d", from_strip(uad), buf, uid, pw->pw_name, outbytes); return(0); }
/* * Parse/Resolve various string representations of * IPv4/IPv6 addresses and optional port. * An address can also be a domain name. * A port can also be a service (e.g. 'www'). * * "<address>" * "<ipv4_address>:<port>" * "[<address>]" * "[<address>]:<port>" */ int addr_parse_full( IP *addr, const char full_addr_str[], const char default_port[], int af ) { char addr_buf[256]; char *addr_beg, *addr_tmp; char *last_colon; const char *addr_str = NULL; const char *port_str = NULL; size_t len; len = strlen( full_addr_str ); if( len >= (sizeof(addr_buf) - 1) ) { /* address too long */ return -1; } else { addr_beg = addr_buf; } memset( addr_buf, '\0', sizeof(addr_buf) ); memcpy( addr_buf, full_addr_str, len ); last_colon = strrchr( addr_buf, ':' ); if( addr_beg[0] == '[' ) { /* [<addr>] or [<addr>]:<port> */ addr_tmp = strrchr( addr_beg, ']' ); if( addr_tmp == NULL ) { /* broken format */ return -1; } *addr_tmp = '\0'; addr_str = addr_beg + 1; if( *(addr_tmp+1) == '\0' ) { port_str = default_port; } else if( *(addr_tmp+1) == ':' ) { port_str = addr_tmp + 2; } else { /* port expected */ return -1; } } else if( last_colon && last_colon == strchr( addr_buf, ':' ) ) { /* <non-ipv6-addr>:<port> */ addr_tmp = last_colon; if( addr_tmp ) { *addr_tmp = '\0'; addr_str = addr_buf; port_str = addr_tmp+1; } else { addr_str = addr_buf; port_str = default_port; } } else { /* <addr> */ addr_str = addr_buf; port_str = default_port; } return addr_parse( addr, addr_str, port_str, af ); }
int main(int argc, char *argv[]) { int rc; int argi; rc = inetping_init(&ev_ops); if (rc != EOK) { printf(NAME ": Failed connecting to internet ping service " "(%d).\n", rc); return 1; } argi = 1; if (argi < argc && str_cmp(argv[argi], "-r") == 0) { ping_repeat = true; ++argi; } else { ping_repeat = false; } if (argc - argi != 1) { print_syntax(); return 1; } /* Parse destination address */ rc = addr_parse(argv[argi], &dest_addr); if (rc != EOK) { printf(NAME ": Invalid address format.\n"); print_syntax(); return 1; } /* Determine source address */ rc = inetping_get_srcaddr(&dest_addr, &src_addr); if (rc != EOK) { printf(NAME ": Failed determining source address.\n"); return 1; } fid_t fid; if (ping_repeat) { fid = fibril_create(transmit_fibril, NULL); if (fid == 0) { printf(NAME ": Failed creating transmit fibril.\n"); return 1; } fibril_add_ready(fid); fid = fibril_create(input_fibril, NULL); if (fid == 0) { printf(NAME ": Failed creating input fibril.\n"); return 1; } fibril_add_ready(fid); } else { ping_send(1); } fibril_mutex_lock(&done_lock); rc = EOK; while (!done && rc != ETIMEOUT) { rc = fibril_condvar_wait_timeout(&done_cv, &done_lock, ping_repeat ? 0 : PING_TIMEOUT); } fibril_mutex_unlock(&done_lock); if (rc == ETIMEOUT) { printf(NAME ": Echo request timed out.\n"); return 1; } return 0; }