--- snmplib/snmpUDPDomain.c.original 2007-11-20 16:43:55.000000000 +0000 +++ snmplib/snmpUDPDomain.c 2007-11-20 17:43:29.000000000 +0000 @@ -103,12 +103,26 @@ struct sockaddr_in *to = NULL; char tmp[64]; to = (struct sockaddr_in *) &(addr_pair->remote_addr); + /* Using strdup on the output of inet_ntoa is important! */ + /* "inet_ntoa" uses a statically allocated buffer to store + its information. To use two in a row, the first needs + to be saved somewhere else so that the second does not + overwrite it. However, it is important to remember that + all "strdup" calls MUST be freed. */ if (to == NULL) { - return strdup("UDP: unknown"); + sprintf(tmp, "UDP: [%s]->unknown", + inet_ntoa(addr_pair->local_addr)); + } else { + /* This will store the first address from strdup so that the second + call will not overwrite it. */ + char* local_addr_copy = strdup( inet_ntoa(addr_pair->local_addr) ); + sprintf(tmp, "UDP: [%s]->[%s]:%hu", + local_addr_copy, + inet_ntoa(to->sin_addr), ntohs(to->sin_port)); + /* Remember, we must free our copy now. */ + free( local_addr_copy ); } - sprintf(tmp, "UDP: [%s]:%hu", - inet_ntoa(to->sin_addr), ntohs(to->sin_port)); return strdup(tmp); } } @@ -666,11 +680,23 @@ NETSNMP_DS_LIB_CLIENT_ADDR); if (client_socket) { struct sockaddr_in client_addr; + int ret; netsnmp_sockaddr_in2(&client_addr, client_socket, NULL); + addr_pair.local_addr = client_addr.sin_addr; client_addr.sin_port = 0; - bind(t->sock, (struct sockaddr *)&client_addr, + ret = bind(t->sock, (struct sockaddr *)&client_addr, sizeof(struct sockaddr)); + if(ret) + DEBUGMSGTL(("netsnmp_udp", "failed to bind for clientaddr: %d %s\n", + errno,strerror(errno))); + /* TODO: should we exit here? */ } + + str = netsnmp_udp_fmtaddr(NULL, (void *)&addr_pair, + sizeof(netsnmp_udp_addr_pair)); + DEBUGMSGTL(("netsnmp_udp", "client open %s\n", str)); + free(str); + /* * Save the (remote) address in the * transport-specific data pointer for later use by netsnmp_udp_send.