Login
[x]
Log in using an account from:
Fedora Account System
Red Hat Associate
Red Hat Customer
Or login using a Red Hat Bugzilla account
Forgot Password
Login:
Hide Forgot
Create an Account
Red Hat Bugzilla – Attachment 147802 Details for
Bug 228066
[Patch] net-snmp-5.3.1-local-addr-v2.patch breaks TCP
[?]
New
Simple Search
Advanced Search
My Links
Browse
Requests
Reports
Current State
Search
Tabular reports
Graphical reports
Duplicates
Other Reports
User Changes
Plotly Reports
Bug Status
Bug Severity
Non-Defaults
|
Product Dashboard
Help
Page Help!
Bug Writing Guidelines
What's new
Browser Support Policy
5.0.4.rh83 Release notes
FAQ
Guides index
User guide
Web Services
Contact
Legal
This site requires JavaScript to be enabled to function correctly, please enable it.
[patch]
Suggested replacement for net-snmp-5.3.1-local-addr-v2.patch
net-snmp-5.3.1-local-addr-v3.patch (text/plain), 13.96 KB, created by
Jan Andres
on 2007-02-09 20:15:19 UTC
(
hide
)
Description:
Suggested replacement for net-snmp-5.3.1-local-addr-v2.patch
Filename:
MIME Type:
Creator:
Jan Andres
Created:
2007-02-09 20:15:19 UTC
Size:
13.96 KB
patch
obsolete
>diff -ur net-snmp-5.3.1/snmplib/snmpTCPDomain.c net-snmp-5.3.1-fixed/snmplib/snmpTCPDomain.c >--- net-snmp-5.3.1/snmplib/snmpTCPDomain.c 2005-09-16 12:30:48.000000000 +0200 >+++ net-snmp-5.3.1-fixed/snmplib/snmpTCPDomain.c 2007-02-09 20:52:29.112680146 +0100 >@@ -44,6 +44,12 @@ > #include <net-snmp/library/snmpUDPDomain.h> > #include <net-snmp/library/snmpTCPDomain.h> > >+/* Copied from snmpUDPDomain.c */ >+typedef struct netsnmp_udp_addr_pair_s { >+ struct sockaddr_in remote_addr; >+ struct in_addr local_addr; >+} netsnmp_udp_addr_pair; >+ > oid netsnmp_snmpTCPDomain[] = { TRANSPORT_DOMAIN_TCP_IP }; > static netsnmp_tdomain tcpDomain; > >@@ -55,18 +61,23 @@ > static char * > netsnmp_tcp_fmtaddr(netsnmp_transport *t, void *data, int len) > { >- struct sockaddr_in *to = NULL; >+ netsnmp_udp_addr_pair *addr_pair = NULL; > >- if (data != NULL && len == sizeof(struct sockaddr_in)) { >- to = (struct sockaddr_in *) data; >- } else if (t != NULL && t->data != NULL && >- t->data_length == sizeof(struct sockaddr_in)) { >- to = (struct sockaddr_in *) t->data; >+ if (data != NULL && len == sizeof(netsnmp_udp_addr_pair)) { >+ addr_pair = (netsnmp_udp_addr_pair *) data; >+ } else if (t != NULL && t->data != NULL) { >+ addr_pair = (netsnmp_udp_addr_pair *) t->data; > } >- if (to == NULL) { >+ >+ if (addr_pair == NULL) { > return strdup("TCP: unknown"); > } else { >- char tmp[64]; >+ struct sockaddr_in *to = NULL; >+ char tmp[64]; >+ to = (struct sockaddr_in *) &(addr_pair->remote_addr); >+ if (to == NULL) { >+ return strdup("TCP: unknown"); >+ } > > sprintf(tmp, "TCP: [%s]:%hd", > inet_ntoa(to->sin_addr), ntohs(to->sin_port)); >@@ -163,19 +174,21 @@ > netsnmp_tcp_accept(netsnmp_transport *t) > { > struct sockaddr *farend = NULL; >+ netsnmp_udp_addr_pair *addr_pair = NULL; > int newsock = -1, sockflags = 0; > socklen_t farendlen = sizeof(struct sockaddr_in); > char *str = NULL; > >- farend = (struct sockaddr *) malloc(sizeof(struct sockaddr_in)); >+ addr_pair = (netsnmp_udp_addr_pair *)malloc(sizeof(netsnmp_udp_addr_pair)); > >- if (farend == NULL) { >+ if (addr_pair == NULL) { > /* > * Indicate that the acceptance of this socket failed. > */ > DEBUGMSGTL(("netsnmp_tcp", "accept: malloc failed\n")); > return -1; > } >+ farend = (struct sockaddr_in *) &(addr_pair->remote_addr); > > if (t != NULL && t->sock >= 0) { > newsock = accept(t->sock, farend, &farendlen); >@@ -191,8 +204,8 @@ > free(t->data); > } > >- t->data = farend; >- t->data_length = farendlen; >+ t->data = addr_pair; >+ t->data_length = sizeof(netsnmp_udp_addr_pair); > str = netsnmp_tcp_fmtaddr(NULL, farend, farendlen); > DEBUGMSGTL(("netsnmp_tcp", "accept succeeded (from %s)\n", str)); > free(str); >@@ -238,6 +251,7 @@ > netsnmp_tcp_transport(struct sockaddr_in *addr, int local) > { > netsnmp_transport *t = NULL; >+ netsnmp_udp_addr_pair *addr_pair = NULL; > int rc = 0; > > >@@ -251,13 +265,14 @@ > } > memset(t, 0, sizeof(netsnmp_transport)); > >- t->data = malloc(sizeof(struct sockaddr_in)); >- if (t->data == NULL) { >+ addr_pair = (netsnmp_udp_addr_pair *)malloc(sizeof(netsnmp_udp_addr_pair)); >+ if (addr_pair == NULL) { > netsnmp_transport_free(t); > return NULL; > } >- t->data_length = sizeof(struct sockaddr_in); >- memcpy(t->data, addr, sizeof(struct sockaddr_in)); >+ t->data = addr_pair; >+ t->data_length = sizeof(netsnmp_udp_addr_pair); >+ memcpy(&(addr_pair->remote_addr), addr, sizeof(struct sockaddr_in)); > > t->domain = netsnmp_snmpTCPDomain; > t->domain_length = >diff -ur net-snmp-5.3.1/snmplib/snmpUDPDomain.c net-snmp-5.3.1-fixed/snmplib/snmpUDPDomain.c >--- net-snmp-5.3.1/snmplib/snmpUDPDomain.c 2005-11-05 23:01:42.000000000 +0100 >+++ net-snmp-5.3.1-fixed/snmplib/snmpUDPDomain.c 2007-02-09 20:53:10.626567462 +0100 >@@ -64,6 +64,11 @@ > > static netsnmp_tdomain udpDomain; > >+typedef struct netsnmp_udp_addr_pair_s { >+ struct sockaddr_in remote_addr; >+ struct in_addr local_addr; >+} netsnmp_udp_addr_pair; >+ > /* > * not static, since snmpUDPIPv6Domain needs it, but not public, either. > * (ie don't put it in a public header.) >@@ -78,17 +83,23 @@ > static char * > netsnmp_udp_fmtaddr(netsnmp_transport *t, void *data, int len) > { >- struct sockaddr_in *to = NULL; >+ netsnmp_udp_addr_pair *addr_pair = NULL; > >- if (data != NULL && len == sizeof(struct sockaddr_in)) { >- to = (struct sockaddr_in *) data; >+ if (data != NULL && len == sizeof(netsnmp_udp_addr_pair)) { >+ addr_pair = (netsnmp_udp_addr_pair *) data; > } else if (t != NULL && t->data != NULL) { >- to = (struct sockaddr_in *) t->data; >+ addr_pair = (netsnmp_udp_addr_pair *) t->data; > } >- if (to == NULL) { >+ >+ if (addr_pair == NULL) { > return strdup("UDP: unknown"); > } else { >+ struct sockaddr_in *to = NULL; > char tmp[64]; >+ to = (struct sockaddr_in *) &(addr_pair->remote_addr); >+ if (to == NULL) { >+ return strdup("UDP: unknown"); >+ } > > sprintf(tmp, "UDP: [%s]:%hu", > inet_ntoa(to->sin_addr), ntohs(to->sin_port)); >@@ -98,6 +109,77 @@ > > > >+#ifdef IP_PKTINFO >+ >+# define netsnmp_dstaddr(x) (&(((struct in_pktinfo *)(CMSG_DATA(x)))->ipi_addr)) >+ >+static int netsnmp_udp_recvfrom(int s, char *buf, int len, struct sockaddr *from, int *fromlen, struct in_addr *dstip) >+{ >+ int r; >+ struct iovec iov[1]; >+ char cmsg[CMSG_SPACE(sizeof(struct in_pktinfo))]; >+ struct cmsghdr *cmsgptr; >+ struct msghdr msg; >+ >+ iov[0].iov_base = buf; >+ iov[0].iov_len = len; >+ >+ memset(&msg, 0, sizeof msg); >+ msg.msg_name = from; >+ msg.msg_namelen = *fromlen; >+ msg.msg_iov = iov; >+ msg.msg_iovlen = 1; >+ msg.msg_control = &cmsg; >+ msg.msg_controllen = sizeof(cmsg); >+ >+ r = recvmsg(s, &msg, 0); >+ >+ if (r == -1) { >+ return -1; >+ } >+ >+ DEBUGMSGTL(("netsnmp_udp", "got source addr: %s\n", inet_ntoa(((struct sockaddr_in *)from)->sin_addr))); >+ for (cmsgptr = CMSG_FIRSTHDR(&msg); cmsgptr != NULL; cmsgptr = CMSG_NXTHDR(&msg, cmsgptr)) { >+ if (cmsgptr->cmsg_level == SOL_IP && cmsgptr->cmsg_type == IP_PKTINFO) { >+ memcpy((void *) dstip, netsnmp_dstaddr(cmsgptr), sizeof(struct in_addr)); >+ DEBUGMSGTL(("netsnmp_udp", "got destination (local) addr %s\n", >+ inet_ntoa(*dstip))); >+ } >+ } >+ return r; >+} >+ >+static int netsnmp_udp_sendto(int fd, struct in_addr *srcip, struct sockaddr *remote, >+ char *data, int len) >+{ >+ struct iovec iov = { data, len }; >+ struct { >+ struct cmsghdr cm; >+ struct in_pktinfo ipi; >+ } cmsg = { >+ .cm = { >+ .cmsg_len = sizeof(struct cmsghdr) + sizeof(struct in_pktinfo), >+ .cmsg_level = SOL_IP, >+ .cmsg_type = IP_PKTINFO, >+ }, >+ .ipi = { >+ .ipi_ifindex = 0, >+ .ipi_spec_dst = srcip ? srcip->s_addr : 0, >+ }, >+ }; >+ struct msghdr m = { >+ .msg_name = remote, >+ .msg_namelen = sizeof(struct sockaddr_in), >+ .msg_iov = &iov, >+ .msg_iovlen = 1, >+ .msg_control = &cmsg, >+ .msg_controllen = sizeof(cmsg), >+ .msg_flags = 0, >+ }; >+ return sendmsg(fd, &m, MSG_NOSIGNAL|MSG_DONTWAIT); >+} >+#endif /* IP_PKTINFO */ >+ > /* > * You can write something into opaque that will subsequently get passed back > * to your send function if you like. For instance, you might want to >@@ -110,27 +192,33 @@ > { > int rc = -1; > socklen_t fromlen = sizeof(struct sockaddr); >+ netsnmp_udp_addr_pair *addr_pair = NULL; > struct sockaddr *from; > > if (t != NULL && t->sock >= 0) { >- from = (struct sockaddr *) malloc(sizeof(struct sockaddr_in)); >- if (from == NULL) { >+ addr_pair = (netsnmp_udp_addr_pair *) malloc(sizeof(netsnmp_udp_addr_pair)); >+ if (addr_pair == NULL) { > *opaque = NULL; > *olength = 0; > return -1; > } else { >- memset(from, 0, fromlen); >+ memset(addr_pair, 0, sizeof(netsnmp_udp_addr_pair)); >+ from = (struct sockaddr *) &(addr_pair->remote_addr); > } > > while (rc < 0) { >- rc = recvfrom(t->sock, buf, size, 0, from, &fromlen); >+#if defined IP_PKTINFO >+ rc = netsnmp_udp_recvfrom(t->sock, buf, size, from, &fromlen, &(addr_pair->local_addr)); >+#else >+ rc = recvfrom(t->sock, buf, size, 0, from, &fromlen); >+#endif /* IP_PKTINFO */ > if (rc < 0 && errno != EINTR) { > break; > } > } > > if (rc >= 0) { >- char *str = netsnmp_udp_fmtaddr(NULL, from, fromlen); >+ char *str = netsnmp_udp_fmtaddr(NULL, addr_pair, sizeof(netsnmp_udp_addr_pair)); > DEBUGMSGTL(("netsnmp_udp", > "recvfrom fd %d got %d bytes (from %s)\n", > t->sock, rc, str)); >@@ -139,8 +227,8 @@ > DEBUGMSGTL(("netsnmp_udp", "recvfrom fd %d err %d (\"%s\")\n", > t->sock, errno, strerror(errno))); > } >- *opaque = (void *)from; >- *olength = sizeof(struct sockaddr_in); >+ *opaque = (void *)addr_pair; >+ *olength = sizeof(netsnmp_udp_addr_pair); > } > return rc; > } >@@ -152,24 +240,31 @@ > void **opaque, int *olength) > { > int rc = -1; >+ netsnmp_udp_addr_pair *addr_pair = NULL; > struct sockaddr *to = NULL; > > if (opaque != NULL && *opaque != NULL && >- *olength == sizeof(struct sockaddr_in)) { >- to = (struct sockaddr *) (*opaque); >+ *olength == sizeof(netsnmp_udp_addr_pair)) { >+ addr_pair = (netsnmp_udp_addr_pair *) (*opaque); > } else if (t != NULL && t->data != NULL && >- t->data_length == sizeof(struct sockaddr_in)) { >- to = (struct sockaddr *) (t->data); >+ t->data_length == sizeof(netsnmp_udp_addr_pair)) { >+ addr_pair = (netsnmp_udp_addr_pair *) (t->data); > } > >+ to = (struct sockaddr *) &(addr_pair->remote_addr); >+ > if (to != NULL && t != NULL && t->sock >= 0) { >- char *str = netsnmp_udp_fmtaddr(NULL, (void *) to, >- sizeof(struct sockaddr_in)); >+ char *str = netsnmp_udp_fmtaddr(NULL, (void *) addr_pair, >+ sizeof(netsnmp_udp_addr_pair)); > DEBUGMSGTL(("netsnmp_udp", "send %d bytes from %p to %s on fd %d\n", > size, buf, str, t->sock)); > free(str); > while (rc < 0) { >- rc = sendto(t->sock, buf, size, 0, to, sizeof(struct sockaddr)); >+#if defined IP_PKTINFO >+ rc = netsnmp_udp_sendto(t->sock, addr_pair ? &(addr_pair->local_addr) : NULL, to, buf, size); >+#else >+ rc = sendto(t->sock, buf, size, 0, to, sizeof(struct sockaddr)); >+#endif /* IP_PKTINFO */ > if (rc < 0 && errno != EINTR) { > DEBUGMSGTL(("netsnmp_udp", "sendto error, rc %d (errno %d)\n", > rc, errno)); >@@ -486,18 +581,26 @@ > int rc = 0; > char *str = NULL; > char *client_socket = NULL; >+ netsnmp_udp_addr_pair *addr_pair = NULL; > > if (addr == NULL || addr->sin_family != AF_INET) { > return NULL; > } > >+ addr_pair = (struct udp_addr_pair *) malloc(sizeof(netsnmp_udp_addr_pair)); >+ if (addr_pair == NULL) { >+ return NULL; >+ } >+ memset(addr_pair, 0, sizeof(netsnmp_udp_addr_pair)); >+ memcpy(&(addr_pair->remote_addr), addr, sizeof(struct sockaddr_in)); >+ > t = (netsnmp_transport *) malloc(sizeof(netsnmp_transport)); > if (t == NULL) { > return NULL; > } > >- str = netsnmp_udp_fmtaddr(NULL, (void *)addr, >- sizeof(struct sockaddr_in)); >+ str = netsnmp_udp_fmtaddr(NULL, (void *)addr_pair, >+ sizeof(netsnmp_udp_addr_pair)); > DEBUGMSGTL(("netsnmp_udp", "open %s %s:%d\n", local ? "local" : "remote", > str,addr->sin_port)); > free(str); >@@ -532,6 +635,18 @@ > t->local[5] = (htons(addr->sin_port) & 0x00ff) >> 0; > t->local_length = 6; > >+#ifdef IP_PKTINFO >+ { >+ int sockopt = 1; >+ int sockoptlen = sizeof(int); >+ if (setsockopt(t->sock, SOL_IP, IP_PKTINFO, &sockopt, sizeof sockopt) == -1) { >+ DEBUGMSGTL(("netsnmp_udp", "couldn't set IP_PKTINFO: %s\n", >+ strerror(errno))); >+ return NULL; >+ } >+ DEBUGMSGTL(("netsnmp_udp", "set IP_PKTINFO\n")); >+ } >+#endif > rc = bind(t->sock, (struct sockaddr *) addr, > sizeof(struct sockaddr)); > if (rc != 0) { >@@ -561,7 +676,7 @@ > * transport-specific data pointer for later use by netsnmp_udp_send. > */ > >- t->data = malloc(sizeof(struct sockaddr_in)); >+ t->data = malloc(sizeof(netsnmp_udp_addr_pair)); > t->remote = malloc(6); > if (t->data == NULL || t->remote == NULL) { > netsnmp_transport_free(t); >@@ -571,8 +686,8 @@ > t->remote[4] = (htons(addr->sin_port) & 0xff00) >> 8; > t->remote[5] = (htons(addr->sin_port) & 0x00ff) >> 0; > t->remote_length = 6; >- memcpy(t->data, addr, sizeof(struct sockaddr_in)); >- t->data_length = sizeof(struct sockaddr_in); >+ memcpy(t->data, addr_pair, sizeof(netsnmp_udp_addr_pair)); >+ t->data_length = sizeof(netsnmp_udp_addr_pair); > } > > /* >@@ -993,7 +1108,8 @@ > char **contextName) > { > com2SecEntry *c; >- struct sockaddr_in *from = (struct sockaddr_in *) opaque; >+ netsnmp_udp_addr_pair *addr_pair = (netsnmp_udp_addr_pair *) opaque; >+ struct sockaddr_in *from = (struct sockaddr_in *) &(addr_pair->remote_addr); > char *ztcommunity = NULL; > > if (secName != NULL) { >@@ -1015,7 +1131,7 @@ > * name. > */ > >- if (opaque == NULL || olength != sizeof(struct sockaddr_in) || >+ if (opaque == NULL || olength != sizeof(netsnmp_udp_addr_pair) || > from->sin_family != AF_INET) { > DEBUGMSGTL(("netsnmp_udp_getSecName", > "no IPv4 source address in PDU?\n"));
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 228066
: 147802