miniupnpd: Retreive PCP packed IPV6 destination address
This commit is contained in:
parent
5f288bf804
commit
d851ad4c25
|
@ -2102,6 +2102,7 @@ main(int argc, char * * argv)
|
||||||
len = ReceiveNATPMPOrPCPPacket(snatpmp[i],
|
len = ReceiveNATPMPOrPCPPacket(snatpmp[i],
|
||||||
(struct sockaddr *)&senderaddr,
|
(struct sockaddr *)&senderaddr,
|
||||||
&senderaddrlen,
|
&senderaddrlen,
|
||||||
|
NULL,
|
||||||
msg_buff, sizeof(msg_buff));
|
msg_buff, sizeof(msg_buff));
|
||||||
if (len < 1)
|
if (len < 1)
|
||||||
continue;
|
continue;
|
||||||
|
@ -2111,7 +2112,7 @@ main(int argc, char * * argv)
|
||||||
&senderaddr);
|
&senderaddr);
|
||||||
} else { /* everything else can be PCP */
|
} else { /* everything else can be PCP */
|
||||||
ProcessIncomingPCPPacket(snatpmp[i], msg_buff, len,
|
ProcessIncomingPCPPacket(snatpmp[i], msg_buff, len,
|
||||||
(struct sockaddr *)&senderaddr);
|
(struct sockaddr *)&senderaddr, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
#else
|
#else
|
||||||
|
@ -2127,16 +2128,19 @@ main(int argc, char * * argv)
|
||||||
unsigned char msg_buff[PCP_MAX_LEN];
|
unsigned char msg_buff[PCP_MAX_LEN];
|
||||||
struct sockaddr_in6 senderaddr;
|
struct sockaddr_in6 senderaddr;
|
||||||
socklen_t senderaddrlen;
|
socklen_t senderaddrlen;
|
||||||
|
struct sockaddr_in6 receiveraddr;
|
||||||
int len;
|
int len;
|
||||||
memset(msg_buff, 0, PCP_MAX_LEN);
|
memset(msg_buff, 0, PCP_MAX_LEN);
|
||||||
senderaddrlen = sizeof(senderaddr);
|
senderaddrlen = sizeof(senderaddr);
|
||||||
len = ReceiveNATPMPOrPCPPacket(spcp_v6,
|
len = ReceiveNATPMPOrPCPPacket(spcp_v6,
|
||||||
(struct sockaddr *)&senderaddr,
|
(struct sockaddr *)&senderaddr,
|
||||||
&senderaddrlen,
|
&senderaddrlen,
|
||||||
|
&receiveraddr,
|
||||||
msg_buff, sizeof(msg_buff));
|
msg_buff, sizeof(msg_buff));
|
||||||
if(len >= 1)
|
if(len >= 1)
|
||||||
ProcessIncomingPCPPacket(spcp_v6, msg_buff, len,
|
ProcessIncomingPCPPacket(spcp_v6, msg_buff, len,
|
||||||
(struct sockaddr *)&senderaddr);
|
(struct sockaddr *)&senderaddr,
|
||||||
|
&receiveraddr);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
/* process SSDP packets */
|
/* process SSDP packets */
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $Id: natpmp.c,v 1.43 2014/03/24 10:49:45 nanard Exp $ */
|
/* $Id: natpmp.c,v 1.47 2014/05/19 12:51:52 nanard Exp $ */
|
||||||
/* MiniUPnP project
|
/* MiniUPnP project
|
||||||
* (c) 2007-2014 Thomas Bernard
|
* (c) 2007-2014 Thomas Bernard
|
||||||
* http://miniupnp.free.fr/ or http://miniupnp.tuxfamily.org/
|
* http://miniupnp.free.fr/ or http://miniupnp.tuxfamily.org/
|
||||||
|
@ -14,6 +14,7 @@
|
||||||
#include <sys/socket.h>
|
#include <sys/socket.h>
|
||||||
#include <netinet/in.h>
|
#include <netinet/in.h>
|
||||||
#include <arpa/inet.h>
|
#include <arpa/inet.h>
|
||||||
|
#include <sys/uio.h>
|
||||||
|
|
||||||
#include "macros.h"
|
#include "macros.h"
|
||||||
#include "config.h"
|
#include "config.h"
|
||||||
|
@ -161,9 +162,63 @@ static void FillPublicAddressResponse(unsigned char * resp, in_addr_t senderaddr
|
||||||
*/
|
*/
|
||||||
int ReceiveNATPMPOrPCPPacket(int s, struct sockaddr * senderaddr,
|
int ReceiveNATPMPOrPCPPacket(int s, struct sockaddr * senderaddr,
|
||||||
socklen_t * senderaddrlen,
|
socklen_t * senderaddrlen,
|
||||||
|
struct sockaddr_in6 * receiveraddr,
|
||||||
unsigned char * msg_buff, size_t msg_buff_size)
|
unsigned char * msg_buff, size_t msg_buff_size)
|
||||||
{
|
{
|
||||||
|
#if IPV6_PKTINFO
|
||||||
|
struct iovec iov;
|
||||||
|
uint8_t c[1000];
|
||||||
|
struct msghdr msg;
|
||||||
|
int n;
|
||||||
|
struct cmsghdr *h;
|
||||||
|
|
||||||
|
iov.iov_base = msg_buff;
|
||||||
|
iov.iov_len = msg_buff_size;
|
||||||
|
memset(&msg, 0, sizeof(msg));
|
||||||
|
msg.msg_iov = &iov;
|
||||||
|
msg.msg_iovlen = 1;
|
||||||
|
msg.msg_name = senderaddr;
|
||||||
|
msg.msg_namelen = *senderaddrlen;
|
||||||
|
msg.msg_control = c;
|
||||||
|
msg.msg_controllen = sizeof(c);
|
||||||
|
|
||||||
|
n = recvmsg(s, &msg, 0);
|
||||||
|
if(n < 0) {
|
||||||
|
/* EAGAIN, EWOULDBLOCK and EINTR : silently ignore (retry next time)
|
||||||
|
* other errors : log to LOG_ERR */
|
||||||
|
if(errno != EAGAIN &&
|
||||||
|
errno != EWOULDBLOCK &&
|
||||||
|
errno != EINTR) {
|
||||||
|
syslog(LOG_ERR, "recvmsg(natpmp): %m");
|
||||||
|
}
|
||||||
|
return n;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(receiveraddr) {
|
||||||
|
memset(receiveraddr, 0, sizeof(struct sockaddr_in6));
|
||||||
|
}
|
||||||
|
if ((msg.msg_flags & MSG_TRUNC) || (msg.msg_flags & MSG_CTRUNC)) {
|
||||||
|
syslog(LOG_WARNING, "%s: truncated message",
|
||||||
|
"ReceiveNATPMPOrPCPPacket");
|
||||||
|
}
|
||||||
|
for(h = CMSG_FIRSTHDR(&msg); h;
|
||||||
|
h = CMSG_NXTHDR(&msg, h)) {
|
||||||
|
if(h->cmsg_level == IPPROTO_IPV6 && h->cmsg_type == IPV6_PKTINFO) {
|
||||||
|
char tmp[INET6_ADDRSTRLEN];
|
||||||
|
struct in6_pktinfo *ipi6 = (struct in6_pktinfo *)CMSG_DATA(h);
|
||||||
|
syslog(LOG_DEBUG, "%s: packet destination: %s scope_id=%u",
|
||||||
|
"ReceiveNATPMPOrPCPPacket",
|
||||||
|
inet_ntop(AF_INET6, &ipi6->ipi6_addr, tmp, sizeof(tmp)),
|
||||||
|
ipi6->ipi6_ifindex);
|
||||||
|
if(receiveraddr) {
|
||||||
|
receiveraddr->sin6_addr = ipi6->ipi6_addr;
|
||||||
|
receiveraddr->sin6_scope_id = ipi6->ipi6_ifindex;
|
||||||
|
receiveraddr->sin6_family = AF_INET6;
|
||||||
|
receiveraddr->sin6_port = htons(NATPMP_PORT);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#else
|
||||||
int n;
|
int n;
|
||||||
|
|
||||||
n = recvfrom(s, msg_buff, msg_buff_size, 0,
|
n = recvfrom(s, msg_buff, msg_buff_size, 0,
|
||||||
|
@ -179,6 +234,7 @@ int ReceiveNATPMPOrPCPPacket(int s, struct sockaddr * senderaddr,
|
||||||
}
|
}
|
||||||
return n;
|
return n;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
return n;
|
return n;
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,8 +20,10 @@
|
||||||
|
|
||||||
int OpenAndConfNATPMPSockets(int * sockets);
|
int OpenAndConfNATPMPSockets(int * sockets);
|
||||||
|
|
||||||
|
/* receiveraddr is only used with IPV6 sockets */
|
||||||
int ReceiveNATPMPOrPCPPacket(int s, struct sockaddr * senderaddr,
|
int ReceiveNATPMPOrPCPPacket(int s, struct sockaddr * senderaddr,
|
||||||
socklen_t * senderaddrlen,
|
socklen_t * senderaddrlen,
|
||||||
|
struct sockaddr_in6 * receiveraddr,
|
||||||
unsigned char * msg_buff, size_t msg_buff_size);
|
unsigned char * msg_buff, size_t msg_buff_size);
|
||||||
|
|
||||||
void ProcessIncomingNATPMPPacket(int s, unsigned char * msg_buff, int len,
|
void ProcessIncomingNATPMPPacket(int s, unsigned char * msg_buff, int len,
|
||||||
|
|
|
@ -1538,7 +1538,8 @@ static void createPCPResponse(unsigned char *response, pcp_info_t *pcp_msg_info)
|
||||||
}
|
}
|
||||||
|
|
||||||
int ProcessIncomingPCPPacket(int s, unsigned char *buff, int len,
|
int ProcessIncomingPCPPacket(int s, unsigned char *buff, int len,
|
||||||
const struct sockaddr * senderaddr)
|
const struct sockaddr *senderaddr,
|
||||||
|
const struct sockaddr_in6 *receiveraddr)
|
||||||
{
|
{
|
||||||
pcp_info_t pcp_msg_info;
|
pcp_info_t pcp_msg_info;
|
||||||
struct lan_addr_s * lan_addr;
|
struct lan_addr_s * lan_addr;
|
||||||
|
@ -1591,6 +1592,7 @@ int ProcessIncomingPCPPacket(int s, unsigned char *buff, int len,
|
||||||
len = PCP_MIN_LEN;
|
len = PCP_MIN_LEN;
|
||||||
else
|
else
|
||||||
len = (len + 3) & ~3; /* round up resp. length to multiple of 4 */
|
len = (len + 3) & ~3; /* round up resp. length to multiple of 4 */
|
||||||
|
/* TODO : send using receiveraddr as source address */
|
||||||
len = sendto_or_schedule(s, buff, len, 0, senderaddr,
|
len = sendto_or_schedule(s, buff, len, 0, senderaddr,
|
||||||
(senderaddr->sa_family == AF_INET) ?
|
(senderaddr->sa_family == AF_INET) ?
|
||||||
sizeof(struct sockaddr_in) :
|
sizeof(struct sockaddr_in) :
|
||||||
|
@ -1625,6 +1627,13 @@ int OpenAndConfPCPv6Socket(void)
|
||||||
syslog(LOG_WARNING, "%s: setsockopt(IPV6_V6ONLY): %m",
|
syslog(LOG_WARNING, "%s: setsockopt(IPV6_V6ONLY): %m",
|
||||||
"OpenAndConfPCPv6Socket");
|
"OpenAndConfPCPv6Socket");
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
#ifdef IPV6_RECVPKTINFO
|
||||||
|
/* see RFC3542 */
|
||||||
|
if(setsockopt(s, IPPROTO_IPV6, IPV6_RECVPKTINFO, &i, sizeof(i)) < 0) {
|
||||||
|
syslog(LOG_WARNING, "%s: setsockopt(IPV6_RECVPKTINFO): %m",
|
||||||
|
"OpenAndConfPCPv6Socket");
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
if(!set_non_blocking(s)) {
|
if(!set_non_blocking(s)) {
|
||||||
syslog(LOG_WARNING, "%s: set_non_blocking(): %m",
|
syslog(LOG_WARNING, "%s: set_non_blocking(): %m",
|
||||||
|
|
|
@ -39,10 +39,13 @@ POSSIBILITY OF SUCH DAMAGE.
|
||||||
struct sockaddr;
|
struct sockaddr;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
* receiveraddr is only used for IPV6
|
||||||
|
*
|
||||||
* returns 0 upon success 1 otherwise
|
* returns 0 upon success 1 otherwise
|
||||||
*/
|
*/
|
||||||
int ProcessIncomingPCPPacket(int s, unsigned char *msg_buff, int len,
|
int ProcessIncomingPCPPacket(int s, unsigned char *msg_buff, int len,
|
||||||
const struct sockaddr *senderaddr);
|
const struct sockaddr *senderaddr,
|
||||||
|
const struct sockaddr_in6 *receiveraddr);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* returns the socket
|
* returns the socket
|
||||||
|
|
Loading…
Reference in New Issue