Skip to content

Commit

Permalink
Core: added function for local source address cmsg.
Browse files Browse the repository at this point in the history
--HG--
branch : nginx
  • Loading branch information
vlhomutov committed Jan 25, 2022
1 parent 5535be9 commit 6903cdd
Show file tree
Hide file tree
Showing 3 changed files with 77 additions and 82 deletions.
92 changes: 10 additions & 82 deletions src/event/ngx_event_udp.c
Original file line number Diff line number Diff line change
Expand Up @@ -46,18 +46,8 @@ ngx_event_recvmsg(ngx_event_t *ev)
ngx_connection_t *c, *lc;
static u_char buffer[65535];

#if (NGX_HAVE_MSGHDR_MSG_CONTROL)

#if (NGX_HAVE_IP_RECVDSTADDR)
u_char msg_control[CMSG_SPACE(sizeof(struct in_addr))];
#elif (NGX_HAVE_IP_PKTINFO)
u_char msg_control[CMSG_SPACE(sizeof(struct in_pktinfo))];
#endif

#if (NGX_HAVE_INET6 && NGX_HAVE_IPV6_RECVPKTINFO)
u_char msg_control6[CMSG_SPACE(sizeof(struct in6_pktinfo))];
#endif

#if (NGX_HAVE_ADDRINFO_CMSG)
u_char msg_control[CMSG_SPACE(sizeof(ngx_addrinfo_t))];
#endif

if (ev->timedout) {
Expand Down Expand Up @@ -92,25 +82,13 @@ ngx_event_recvmsg(ngx_event_t *ev)
msg.msg_iov = iov;
msg.msg_iovlen = 1;

#if (NGX_HAVE_MSGHDR_MSG_CONTROL)

#if (NGX_HAVE_ADDRINFO_CMSG)
if (ls->wildcard) {
msg.msg_control = &msg_control;
msg.msg_controllen = sizeof(msg_control);

#if (NGX_HAVE_IP_RECVDSTADDR || NGX_HAVE_IP_PKTINFO)
if (ls->sockaddr->sa_family == AF_INET) {
msg.msg_control = &msg_control;
msg.msg_controllen = sizeof(msg_control);
}
#endif

#if (NGX_HAVE_INET6 && NGX_HAVE_IPV6_RECVPKTINFO)
if (ls->sockaddr->sa_family == AF_INET6) {
msg.msg_control = &msg_control6;
msg.msg_controllen = sizeof(msg_control6);
}
#endif
}

ngx_memzero(&msg_control, sizeof(msg_control));
}
#endif

n = recvmsg(lc->fd, &msg, 0);
Expand All @@ -129,7 +107,7 @@ ngx_event_recvmsg(ngx_event_t *ev)
return;
}

#if (NGX_HAVE_MSGHDR_MSG_CONTROL)
#if (NGX_HAVE_ADDRINFO_CMSG)
if (msg.msg_flags & (MSG_TRUNC|MSG_CTRUNC)) {
ngx_log_error(NGX_LOG_ALERT, ev->log, 0,
"recvmsg() truncated data");
Expand Down Expand Up @@ -159,7 +137,7 @@ ngx_event_recvmsg(ngx_event_t *ev)
local_sockaddr = ls->sockaddr;
local_socklen = ls->socklen;

#if (NGX_HAVE_MSGHDR_MSG_CONTROL)
#if (NGX_HAVE_ADDRINFO_CMSG)

if (ls->wildcard) {
struct cmsghdr *cmsg;
Expand All @@ -171,59 +149,9 @@ ngx_event_recvmsg(ngx_event_t *ev)
cmsg != NULL;
cmsg = CMSG_NXTHDR(&msg, cmsg))
{

#if (NGX_HAVE_IP_RECVDSTADDR)

if (cmsg->cmsg_level == IPPROTO_IP
&& cmsg->cmsg_type == IP_RECVDSTADDR
&& local_sockaddr->sa_family == AF_INET)
{
struct in_addr *addr;
struct sockaddr_in *sin;

addr = (struct in_addr *) CMSG_DATA(cmsg);
sin = (struct sockaddr_in *) local_sockaddr;
sin->sin_addr = *addr;

if (ngx_get_srcaddr_cmsg(cmsg, local_sockaddr) == NGX_OK) {
break;
}

#elif (NGX_HAVE_IP_PKTINFO)

if (cmsg->cmsg_level == IPPROTO_IP
&& cmsg->cmsg_type == IP_PKTINFO
&& local_sockaddr->sa_family == AF_INET)
{
struct in_pktinfo *pkt;
struct sockaddr_in *sin;

pkt = (struct in_pktinfo *) CMSG_DATA(cmsg);
sin = (struct sockaddr_in *) local_sockaddr;
sin->sin_addr = pkt->ipi_addr;

break;
}

#endif

#if (NGX_HAVE_INET6 && NGX_HAVE_IPV6_RECVPKTINFO)

if (cmsg->cmsg_level == IPPROTO_IPV6
&& cmsg->cmsg_type == IPV6_PKTINFO
&& local_sockaddr->sa_family == AF_INET6)
{
struct in6_pktinfo *pkt6;
struct sockaddr_in6 *sin6;

pkt6 = (struct in6_pktinfo *) CMSG_DATA(cmsg);
sin6 = (struct sockaddr_in6 *) local_sockaddr;
sin6->sin6_addr = pkt6->ipi6_addr;

break;
}

#endif

}
}

Expand Down
2 changes: 2 additions & 0 deletions src/event/ngx_event_udp.h
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,8 @@ typedef union {

size_t ngx_set_srcaddr_cmsg(struct cmsghdr *cmsg,
struct sockaddr *local_sockaddr);
ngx_int_t ngx_get_srcaddr_cmsg(struct cmsghdr *cmsg,
struct sockaddr *local_sockaddr);

#endif

Expand Down
65 changes: 65 additions & 0 deletions src/os/unix/ngx_udp_sendmsg_chain.c
Original file line number Diff line number Diff line change
Expand Up @@ -316,6 +316,71 @@ ngx_set_srcaddr_cmsg(struct cmsghdr *cmsg, struct sockaddr *local_sockaddr)
return 0;
}


ngx_int_t
ngx_get_srcaddr_cmsg(struct cmsghdr *cmsg, struct sockaddr *local_sockaddr)
{

#if (NGX_HAVE_IP_RECVDSTADDR)
struct in_addr *addr;
struct sockaddr_in *sin;
#elif (NGX_HAVE_IP_PKTINFO)
struct in_pktinfo *pkt;
struct sockaddr_in *sin;
#endif

#if (NGX_HAVE_INET6 && NGX_HAVE_IPV6_RECVPKTINFO)
struct in6_pktinfo *pkt6;
struct sockaddr_in6 *sin6;
#endif


#if (NGX_HAVE_IP_RECVDSTADDR)

if (cmsg->cmsg_level == IPPROTO_IP
&& cmsg->cmsg_type == IP_RECVDSTADDR
&& local_sockaddr->sa_family == AF_INET)
{
addr = (struct in_addr *) CMSG_DATA(cmsg);
sin = (struct sockaddr_in *) local_sockaddr;
sin->sin_addr = *addr;

return NGX_OK;
}

#elif (NGX_HAVE_IP_PKTINFO)

if (cmsg->cmsg_level == IPPROTO_IP
&& cmsg->cmsg_type == IP_PKTINFO
&& local_sockaddr->sa_family == AF_INET)
{
pkt = (struct in_pktinfo *) CMSG_DATA(cmsg);
sin = (struct sockaddr_in *) local_sockaddr;
sin->sin_addr = pkt->ipi_addr;

return NGX_OK;
}

#endif

#if (NGX_HAVE_INET6 && NGX_HAVE_IPV6_RECVPKTINFO)

if (cmsg->cmsg_level == IPPROTO_IPV6
&& cmsg->cmsg_type == IPV6_PKTINFO
&& local_sockaddr->sa_family == AF_INET6)
{
pkt6 = (struct in6_pktinfo *) CMSG_DATA(cmsg);
sin6 = (struct sockaddr_in6 *) local_sockaddr;
sin6->sin6_addr = pkt6->ipi6_addr;

return NGX_OK;
}

#endif

return NGX_DECLINED;
}

#endif


Expand Down

0 comments on commit 6903cdd

Please sign in to comment.