X-Git-Url: http://www.sigaev.ru/git/gitweb.cgi?a=blobdiff_plain;f=udp.c;h=424860b3891d1f27072e5c2a8bf38d31237189d8;hb=0fd1e4bc60725bc8ce06b7720539f6c8a38341b6;hp=810369a2df46d754160f819ff6c13fb1f27cdab6;hpb=7c3bc2582d0e01893584511ae45324339079dd33;p=tedtools.git diff --git a/udp.c b/udp.c index 810369a..424860b 100644 --- a/udp.c +++ b/udp.c @@ -34,6 +34,9 @@ #include #include +#ifdef HAVE_HSTRERROR +#include +#endif #include "connection.h" #include "tlog.h" @@ -42,7 +45,7 @@ int TC_AcceptUdp(char *host, int port) { struct sockaddr_in serv_addr; - int sockfd, flags; + int sockfd, flags; if ( (sockfd = socket(AF_INET, SOCK_DGRAM, 0)) < 0) tlog(TL_CRIT|TL_EXIT, "udp socket %s", strerror(errno)); @@ -54,7 +57,23 @@ TC_AcceptUdp(char *host, int port) { memset(&serv_addr, 0, sizeof(serv_addr)); serv_addr.sin_family = AF_INET; - serv_addr.sin_addr.s_addr = inet_addr(host); + serv_addr.sin_addr.s_addr = (host && *host!='*') ? inet_addr(host) : htonl(INADDR_ANY); + if ( serv_addr.sin_addr.s_addr == INADDR_NONE ) { + struct hostent *ip_host; + + /* + * Can't parse address: it's a DNS Name + */ + ip_host = gethostbyname(host); + if ( ip_host && ip_host->h_addrtype == AF_INET ) { + memcpy(&serv_addr.sin_addr.s_addr, ip_host->h_addr_list[0], + sizeof(&serv_addr.sin_addr.s_addr)); + } else { + tlog(TL_CRIT,"gethostbyname: %s - %s", host, hstrerror(h_errno)); + close(sockfd); + return -1; + } + } serv_addr.sin_port = htons(port); if (bind(sockfd, (struct sockaddr *) &serv_addr, sizeof(serv_addr)) < 0) @@ -87,6 +106,12 @@ TC_getMsg( int sockfd, Msg *msg ) { tlog(TL_ALARM, "Got message %d bytes (should be al least %d)", n, TCMSGHDRSZ ); return CS_AGAIN; } + + /* + * convert from network byteorder + */ + pmsg->len = ntohl(pmsg->len); + pmsg->type = ntohl(pmsg->type); if ( pmsg->len > MSGMAXSIZE ) { tlog(TL_ALARM, "Messages (%d bytes) is too big", pmsg->len); @@ -107,6 +132,8 @@ TC_getMsg( int sockfd, Msg *msg ) { /* send */ u_int32_t TC_sendMsg( Msg *msg ) { + int msglen; + if ( msg->msg == NULL || msg->msg->len <=0 ) return CS_OK; @@ -115,6 +142,7 @@ TC_sendMsg( Msg *msg ) { if ( msg->sockfd <=0 ) { struct sockaddr_in cli_addr; + if ( (msg->sockfd = socket(AF_INET, SOCK_DGRAM, 0)) < 0) { tlog(TL_CRIT,"udp socket %s %d: %s", msg->host, msg->port, strerror(errno)); return CS_ERROR; @@ -134,10 +162,34 @@ TC_sendMsg( Msg *msg ) { memset(&(msg->host_addr), 0, sizeof(msg->host_addr)); msg->host_addr.sin_family = AF_INET; msg->host_addr.sin_addr.s_addr = inet_addr(msg->host); + if ( msg->host_addr.sin_addr.s_addr == INADDR_NONE ) { + struct hostent *ip_host; + + /* + * Can't parse address: it's a DNS Name + */ + ip_host = gethostbyname(msg->host); + if ( ip_host && ip_host->h_addrtype == AF_INET ) { + memcpy(&msg->host_addr.sin_addr.s_addr, ip_host->h_addr_list[0], + sizeof(&msg->host_addr.sin_addr.s_addr)); + } else { + tlog(TL_CRIT,"gethostbyname: %s - %s", msg->host, hstrerror(h_errno)); + close(msg->sockfd); + msg->sockfd=-1; + return CS_ERROR; + } + } msg->host_addr.sin_port = htons(msg->port); } - if (sendto(msg->sockfd, (void*)msg->msg, msg->msg->len, 0, (struct sockaddr *) &(msg->host_addr), sizeof(msg->host_addr)) != msg->msg->len) { + /* + * convert to network byteorder + */ + msglen = msg->msg->len; + msg->msg->len = htonl(msg->msg->len); + msg->msg->type = htonl(msg->msg->type); + + if (sendto(msg->sockfd, (void*)msg->msg, msglen, 0, (struct sockaddr *) &(msg->host_addr), sizeof(msg->host_addr)) != msglen) { tlog(TL_CRIT,"Can't send message to %s:%d : %s", msg->host, msg->port, strerror(errno)); close(msg->sockfd); msg->sockfd=-1;