1) "#define ipi_spec_dst ipi_addr" in <netinet/in.h>
2) Change the IP_RECVPKTINFO option to control the generation of IP_PKTINFO control messages, the way it's done in Solaris. 3) Remove the superfluous IP_RECVPKTINFO control message. 4) Change the IP_PKTINFO option to do different things depending on the parameter it's supplied with: - If it's sizeof(int), assume it's being used as in Linux: - If it's non-zero, turn on the IP_RECVPKTINFO option. - If it's zero, turn off the IP_RECVPKTINFO option. - If it's sizeof(struct in_pktinfo), assume it's being used as in Solaris, to set a default for the source interface and/or source address for outgoing packets on the socket. 5) Return what Linux or Solaris compatible code expects, depending on data size, and just added a fallback to a Linux (and current NetBSD) compatible value if the size is unknown (as it is now), or, in the future, if the calling application specifies a receiving buffer that doesn't match either data item. From: Tom Ivar Helbekkmo
This commit is contained in:
parent
fe1f2b747b
commit
645664bc7b
|
@ -1,4 +1,4 @@
|
||||||
.\" $NetBSD: ip.4,v 1.40 2017/08/13 18:19:44 wiz Exp $
|
.\" $NetBSD: ip.4,v 1.41 2018/01/01 00:51:36 christos Exp $
|
||||||
.\"
|
.\"
|
||||||
.\" Copyright (c) 1983, 1991, 1993
|
.\" Copyright (c) 1983, 1991, 1993
|
||||||
.\" The Regents of the University of California. All rights reserved.
|
.\" The Regents of the University of California. All rights reserved.
|
||||||
|
@ -29,7 +29,7 @@
|
||||||
.\"
|
.\"
|
||||||
.\" @(#)ip.4 8.2 (Berkeley) 11/30/93
|
.\" @(#)ip.4 8.2 (Berkeley) 11/30/93
|
||||||
.\"
|
.\"
|
||||||
.Dd August 10, 2017
|
.Dd December 31, 2017
|
||||||
.Dt IP 4
|
.Dt IP 4
|
||||||
.Os
|
.Os
|
||||||
.Sh NAME
|
.Sh NAME
|
||||||
|
@ -96,8 +96,8 @@ setsockopt(s, IPPROTO_IP, IP_IPSEC_POLICY, buf, ipsec_get_policylen(buf));
|
||||||
.Ed
|
.Ed
|
||||||
.Pp
|
.Pp
|
||||||
The
|
The
|
||||||
.Dv IP_PKTINFO
|
.Dv IP_RECVPKTINFO
|
||||||
option can be used to turn on receiving of information about the source
|
option can be used to turn on receiving of information about the destination
|
||||||
address of the packet, and the interface index.
|
address of the packet, and the interface index.
|
||||||
The information is passed in a
|
The information is passed in a
|
||||||
.Vt struct in_pktinfo
|
.Vt struct in_pktinfo
|
||||||
|
@ -117,13 +117,24 @@ cmsg_type = IP_PKTINFO
|
||||||
.Pp
|
.Pp
|
||||||
For
|
For
|
||||||
.Xr sendmsg 2 ,
|
.Xr sendmsg 2 ,
|
||||||
the source address or output interface can be specified by adding
|
the source address or output interface can be specified by adding an
|
||||||
.Dv IP_PKTINFO
|
.Dv IP_PKTINFO
|
||||||
to the control part of the message on a
|
message to the control part of the message on a
|
||||||
.Dv SOCK_DGRAM
|
.Dv SOCK_DGRAM
|
||||||
or
|
or
|
||||||
.Dv SOCK_RAW
|
.Dv SOCK_RAW
|
||||||
socket.
|
socket. Setting ipi_ifindex will cause the primary address of that
|
||||||
|
interface to be used; setting ipi_addr will directly choose that address.
|
||||||
|
The IP_PKTINFO cmsghdr structure from a received message may be used
|
||||||
|
unchanged, in which case the outgoing message will be sent from the
|
||||||
|
address the incoming message was received on.
|
||||||
|
.Pp
|
||||||
|
Setting the
|
||||||
|
.Dv IP_PKTINFO
|
||||||
|
option on a socket, with the same
|
||||||
|
.Vt struct in_pktinfo
|
||||||
|
structure, will set the default source address to be used until set
|
||||||
|
again, unless explicitly overridden on a per-packet basis, as above.
|
||||||
.Pp
|
.Pp
|
||||||
The
|
The
|
||||||
.Dv IP_PORTALGO
|
.Dv IP_PORTALGO
|
||||||
|
@ -177,6 +188,18 @@ cmsg_level = IPPROTO_IP
|
||||||
cmsg_type = IP_RECVDSTADDR
|
cmsg_type = IP_RECVDSTADDR
|
||||||
.Ed
|
.Ed
|
||||||
.Pp
|
.Pp
|
||||||
|
For
|
||||||
|
.Xr sendmsg 2 ,
|
||||||
|
the source address can be specified by adding
|
||||||
|
.Dv IP_SENDSRCADDR
|
||||||
|
to the control part of the message on a
|
||||||
|
.Dv SOCK_DGRAM
|
||||||
|
or
|
||||||
|
.Dv SOCK_RAW
|
||||||
|
socket. The IP_RECVDSTADDR cmsghdr structure from a received message
|
||||||
|
may be used unchanged, in which case the outgoing message will be sent
|
||||||
|
from the address the incoming message was received on.
|
||||||
|
.Pp
|
||||||
If the
|
If the
|
||||||
.Dv IP_RECVIF
|
.Dv IP_RECVIF
|
||||||
option is enabled on a
|
option is enabled on a
|
||||||
|
@ -197,12 +220,6 @@ cmsg_level = IPPROTO_IP
|
||||||
cmsg_type = IP_RECVIF
|
cmsg_type = IP_RECVIF
|
||||||
.Ed
|
.Ed
|
||||||
.Pp
|
.Pp
|
||||||
The
|
|
||||||
.Dv IP_RECVPKTINFO
|
|
||||||
option is similar to the
|
|
||||||
.Dv IP_PKTINFO
|
|
||||||
one, only in this case the inbound information is returned.
|
|
||||||
.Pp
|
|
||||||
If the
|
If the
|
||||||
.Dv IP_RECVTTL
|
.Dv IP_RECVTTL
|
||||||
option is enabled on a
|
option is enabled on a
|
||||||
|
@ -452,6 +469,24 @@ An unknown socket option name was given; or
|
||||||
the IP option field was improperly formed; an option field was
|
the IP option field was improperly formed; an option field was
|
||||||
shorter than the minimum value or longer than the option buffer provided.
|
shorter than the minimum value or longer than the option buffer provided.
|
||||||
.El
|
.El
|
||||||
|
.Sh COMPATIBILITY
|
||||||
|
The
|
||||||
|
.Dv IP_RECVPKTINFO
|
||||||
|
option is used because it is directly compatible with Solaris, AIX, etc.,
|
||||||
|
and the
|
||||||
|
.Dv IP_PKTINFO
|
||||||
|
option is intended to be used in their manner, to set the default source
|
||||||
|
address for outgoing packets on a
|
||||||
|
.Dv SOCK_DGRAM
|
||||||
|
or
|
||||||
|
.Dv SOCK_RAW
|
||||||
|
socket. For compatibility with Linux, however, if you attempt to set the
|
||||||
|
.Dv IP_PKTINFO
|
||||||
|
option, using an integer parameter as a boolean value, this will
|
||||||
|
transparently manipulate the
|
||||||
|
.Dv IP_RECVPKTINFO
|
||||||
|
option instead. Source code compatbility with both environments is thus
|
||||||
|
maintained.
|
||||||
.Sh SEE ALSO
|
.Sh SEE ALSO
|
||||||
.Xr getsockopt 2 ,
|
.Xr getsockopt 2 ,
|
||||||
.Xr recv 2 ,
|
.Xr recv 2 ,
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $NetBSD: in.h,v 1.101 2017/08/10 04:31:58 ryo Exp $ */
|
/* $NetBSD: in.h,v 1.102 2018/01/01 00:51:36 christos Exp $ */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Copyright (c) 1982, 1986, 1990, 1993
|
* Copyright (c) 1982, 1986, 1990, 1993
|
||||||
|
@ -289,8 +289,10 @@ struct ip_opts {
|
||||||
#define IP_IPSEC_POLICY 22 /* struct; get/set security policy */
|
#define IP_IPSEC_POLICY 22 /* struct; get/set security policy */
|
||||||
#define IP_RECVTTL 23 /* bool; receive IP TTL w/dgram */
|
#define IP_RECVTTL 23 /* bool; receive IP TTL w/dgram */
|
||||||
#define IP_MINTTL 24 /* minimum TTL for packet or drop */
|
#define IP_MINTTL 24 /* minimum TTL for packet or drop */
|
||||||
#define IP_PKTINFO 25 /* int; send interface and src addr */
|
#define IP_PKTINFO 25 /* struct; set default src if/addr */
|
||||||
#define IP_RECVPKTINFO 26 /* int; send interface and dst addr */
|
#define IP_RECVPKTINFO 26 /* int; receive dst if/addr w/dgram */
|
||||||
|
|
||||||
|
#define IP_SENDSRCADDR IP_RECVDSTADDR /* FreeBSD compatibility */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Information sent in the control message of a datagram socket for
|
* Information sent in the control message of a datagram socket for
|
||||||
|
@ -301,6 +303,8 @@ struct in_pktinfo {
|
||||||
unsigned int ipi_ifindex; /* interface index */
|
unsigned int ipi_ifindex; /* interface index */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#define ipi_spec_dst ipi_addr /* Solaris/Linux compatibility */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Defaults and limits for options
|
* Defaults and limits for options
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $NetBSD: in_pcb.c,v 1.180 2017/12/15 04:03:46 ozaki-r Exp $ */
|
/* $NetBSD: in_pcb.c,v 1.181 2018/01/01 00:51:36 christos Exp $ */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
|
* Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
|
||||||
|
@ -93,7 +93,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <sys/cdefs.h>
|
#include <sys/cdefs.h>
|
||||||
__KERNEL_RCSID(0, "$NetBSD: in_pcb.c,v 1.180 2017/12/15 04:03:46 ozaki-r Exp $");
|
__KERNEL_RCSID(0, "$NetBSD: in_pcb.c,v 1.181 2018/01/01 00:51:36 christos Exp $");
|
||||||
|
|
||||||
#ifdef _KERNEL_OPT
|
#ifdef _KERNEL_OPT
|
||||||
#include "opt_inet.h"
|
#include "opt_inet.h"
|
||||||
|
@ -204,6 +204,7 @@ in_pcballoc(struct socket *so, void *v)
|
||||||
inp->inp_errormtu = -1;
|
inp->inp_errormtu = -1;
|
||||||
inp->inp_portalgo = PORTALGO_DEFAULT;
|
inp->inp_portalgo = PORTALGO_DEFAULT;
|
||||||
inp->inp_bindportonsend = false;
|
inp->inp_bindportonsend = false;
|
||||||
|
inp->inp_prefsrcip.s_addr = INADDR_ANY;
|
||||||
#if defined(IPSEC)
|
#if defined(IPSEC)
|
||||||
if (ipsec_enabled) {
|
if (ipsec_enabled) {
|
||||||
int error = ipsec_init_pcbpolicy(so, &inp->inp_sp);
|
int error = ipsec_init_pcbpolicy(so, &inp->inp_sp);
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $NetBSD: in_pcb.h,v 1.64 2017/08/10 04:31:58 ryo Exp $ */
|
/* $NetBSD: in_pcb.h,v 1.65 2018/01/01 00:51:36 christos Exp $ */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
|
* Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
|
||||||
|
@ -95,6 +95,7 @@ struct inpcb {
|
||||||
int inp_errormtu; /* MTU of last xmit status = EMSGSIZE */
|
int inp_errormtu; /* MTU of last xmit status = EMSGSIZE */
|
||||||
uint8_t inp_ip_minttl;
|
uint8_t inp_ip_minttl;
|
||||||
bool inp_bindportonsend;
|
bool inp_bindportonsend;
|
||||||
|
struct in_addr inp_prefsrcip; /* preferred src IP when wild */
|
||||||
};
|
};
|
||||||
|
|
||||||
#define inp_faddr inp_ip.ip_dst
|
#define inp_faddr inp_ip.ip_dst
|
||||||
|
@ -121,11 +122,9 @@ struct inpcb {
|
||||||
* Cancels INP_HDRINCL.
|
* Cancels INP_HDRINCL.
|
||||||
*/
|
*/
|
||||||
#define INP_RECVTTL 0x0800 /* receive incoming IP TTL */
|
#define INP_RECVTTL 0x0800 /* receive incoming IP TTL */
|
||||||
#define INP_PKTINFO 0x1000 /* receive dst packet info */
|
#define INP_RECVPKTINFO 0x1000 /* receive IP dst if/addr */
|
||||||
#define INP_RECVPKTINFO 0x2000 /* receive dst packet info */
|
|
||||||
#define INP_CONTROLOPTS (INP_RECVOPTS|INP_RECVRETOPTS|INP_RECVDSTADDR|\
|
#define INP_CONTROLOPTS (INP_RECVOPTS|INP_RECVRETOPTS|INP_RECVDSTADDR|\
|
||||||
INP_RECVIF|INP_RECVTTL|INP_RECVPKTINFO|\
|
INP_RECVIF|INP_RECVTTL|INP_RECVPKTINFO)
|
||||||
INP_PKTINFO)
|
|
||||||
|
|
||||||
#define sotoinpcb(so) ((struct inpcb *)(so)->so_pcb)
|
#define sotoinpcb(so) ((struct inpcb *)(so)->so_pcb)
|
||||||
#define inp_lock(inp) solock((inp)->inp_socket)
|
#define inp_lock(inp) solock((inp)->inp_socket)
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $NetBSD: ip_input.c,v 1.363 2017/11/24 14:03:25 roy Exp $ */
|
/* $NetBSD: ip_input.c,v 1.364 2018/01/01 00:51:36 christos Exp $ */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
|
* Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
|
||||||
|
@ -91,7 +91,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <sys/cdefs.h>
|
#include <sys/cdefs.h>
|
||||||
__KERNEL_RCSID(0, "$NetBSD: ip_input.c,v 1.363 2017/11/24 14:03:25 roy Exp $");
|
__KERNEL_RCSID(0, "$NetBSD: ip_input.c,v 1.364 2018/01/01 00:51:36 christos Exp $");
|
||||||
|
|
||||||
#ifdef _KERNEL_OPT
|
#ifdef _KERNEL_OPT
|
||||||
#include "opt_inet.h"
|
#include "opt_inet.h"
|
||||||
|
@ -1532,15 +1532,6 @@ ip_savecontrol(struct inpcb *inp, struct mbuf **mp, struct ip *ip,
|
||||||
}
|
}
|
||||||
|
|
||||||
if (inpflags & INP_RECVPKTINFO) {
|
if (inpflags & INP_RECVPKTINFO) {
|
||||||
struct in_pktinfo ipi;
|
|
||||||
ipi.ipi_addr = ip->ip_src;
|
|
||||||
ipi.ipi_ifindex = ifp->if_index;
|
|
||||||
*mp = sbcreatecontrol(&ipi,
|
|
||||||
sizeof(ipi), IP_RECVPKTINFO, IPPROTO_IP);
|
|
||||||
if (*mp)
|
|
||||||
mp = &(*mp)->m_next;
|
|
||||||
}
|
|
||||||
if (inpflags & INP_PKTINFO) {
|
|
||||||
struct in_pktinfo ipi;
|
struct in_pktinfo ipi;
|
||||||
ipi.ipi_addr = ip->ip_dst;
|
ipi.ipi_addr = ip->ip_dst;
|
||||||
ipi.ipi_ifindex = ifp->if_index;
|
ipi.ipi_ifindex = ifp->if_index;
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $NetBSD: ip_output.c,v 1.288 2017/12/22 11:22:37 ozaki-r Exp $ */
|
/* $NetBSD: ip_output.c,v 1.289 2018/01/01 00:51:36 christos Exp $ */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
|
* Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
|
||||||
|
@ -91,7 +91,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <sys/cdefs.h>
|
#include <sys/cdefs.h>
|
||||||
__KERNEL_RCSID(0, "$NetBSD: ip_output.c,v 1.288 2017/12/22 11:22:37 ozaki-r Exp $");
|
__KERNEL_RCSID(0, "$NetBSD: ip_output.c,v 1.289 2018/01/01 00:51:36 christos Exp $");
|
||||||
|
|
||||||
#ifdef _KERNEL_OPT
|
#ifdef _KERNEL_OPT
|
||||||
#include "opt_inet.h"
|
#include "opt_inet.h"
|
||||||
|
@ -1081,6 +1081,7 @@ ip_ctloutput(int op, struct socket *so, struct sockopt *sopt)
|
||||||
struct ip *ip = &inp->inp_ip;
|
struct ip *ip = &inp->inp_ip;
|
||||||
int inpflags = inp->inp_flags;
|
int inpflags = inp->inp_flags;
|
||||||
int optval = 0, error = 0;
|
int optval = 0, error = 0;
|
||||||
|
struct in_pktinfo pktinfo;
|
||||||
|
|
||||||
KASSERT(solocked(so));
|
KASSERT(solocked(so));
|
||||||
|
|
||||||
|
@ -1103,7 +1104,6 @@ ip_ctloutput(int op, struct socket *so, struct sockopt *sopt)
|
||||||
case IP_TOS:
|
case IP_TOS:
|
||||||
case IP_TTL:
|
case IP_TTL:
|
||||||
case IP_MINTTL:
|
case IP_MINTTL:
|
||||||
case IP_PKTINFO:
|
|
||||||
case IP_RECVOPTS:
|
case IP_RECVOPTS:
|
||||||
case IP_RECVRETOPTS:
|
case IP_RECVRETOPTS:
|
||||||
case IP_RECVDSTADDR:
|
case IP_RECVDSTADDR:
|
||||||
|
@ -1135,10 +1135,6 @@ ip_ctloutput(int op, struct socket *so, struct sockopt *sopt)
|
||||||
else \
|
else \
|
||||||
inpflags &= ~bit;
|
inpflags &= ~bit;
|
||||||
|
|
||||||
case IP_PKTINFO:
|
|
||||||
OPTSET(INP_PKTINFO);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case IP_RECVOPTS:
|
case IP_RECVOPTS:
|
||||||
OPTSET(INP_RECVOPTS);
|
OPTSET(INP_RECVOPTS);
|
||||||
break;
|
break;
|
||||||
|
@ -1164,6 +1160,45 @@ ip_ctloutput(int op, struct socket *so, struct sockopt *sopt)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case IP_PKTINFO:
|
||||||
|
error = sockopt_getint(sopt, &optval);
|
||||||
|
if (!error) {
|
||||||
|
/* Linux compatibility */
|
||||||
|
OPTSET(INP_RECVPKTINFO);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
error = sockopt_get(sopt, &pktinfo, sizeof(pktinfo));
|
||||||
|
if (error)
|
||||||
|
break;
|
||||||
|
|
||||||
|
if (pktinfo.ipi_ifindex == 0) {
|
||||||
|
inp->inp_prefsrcip = pktinfo.ipi_addr;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Solaris compatibility */
|
||||||
|
struct ifnet *ifp;
|
||||||
|
struct in_ifaddr *ia;
|
||||||
|
int s;
|
||||||
|
|
||||||
|
/* pick up primary address */
|
||||||
|
s = pserialize_read_enter();
|
||||||
|
ifp = if_byindex(pktinfo.ipi_ifindex);
|
||||||
|
if (ifp == NULL) {
|
||||||
|
pserialize_read_exit(s);
|
||||||
|
error = EADDRNOTAVAIL;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
ia = in_get_ia_from_ifp(ifp);
|
||||||
|
if (ia == NULL) {
|
||||||
|
pserialize_read_exit(s);
|
||||||
|
error = EADDRNOTAVAIL;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
inp->inp_prefsrcip = IA_SIN(ia)->sin_addr;
|
||||||
|
pserialize_read_exit(s);
|
||||||
|
break;
|
||||||
|
break;
|
||||||
#undef OPTSET
|
#undef OPTSET
|
||||||
|
|
||||||
case IP_MULTICAST_IF:
|
case IP_MULTICAST_IF:
|
||||||
|
@ -1239,7 +1274,6 @@ ip_ctloutput(int op, struct socket *so, struct sockopt *sopt)
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case IP_PKTINFO:
|
|
||||||
case IP_TOS:
|
case IP_TOS:
|
||||||
case IP_TTL:
|
case IP_TTL:
|
||||||
case IP_MINTTL:
|
case IP_MINTTL:
|
||||||
|
@ -1269,10 +1303,6 @@ ip_ctloutput(int op, struct socket *so, struct sockopt *sopt)
|
||||||
|
|
||||||
#define OPTBIT(bit) (inpflags & bit ? 1 : 0)
|
#define OPTBIT(bit) (inpflags & bit ? 1 : 0)
|
||||||
|
|
||||||
case IP_PKTINFO:
|
|
||||||
optval = OPTBIT(INP_PKTINFO);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case IP_RECVOPTS:
|
case IP_RECVOPTS:
|
||||||
optval = OPTBIT(INP_RECVOPTS);
|
optval = OPTBIT(INP_RECVOPTS);
|
||||||
break;
|
break;
|
||||||
|
@ -1300,6 +1330,35 @@ ip_ctloutput(int op, struct socket *so, struct sockopt *sopt)
|
||||||
error = sockopt_setint(sopt, optval);
|
error = sockopt_setint(sopt, optval);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case IP_PKTINFO:
|
||||||
|
/* XXX these tests fail until size gets propagated */
|
||||||
|
/* It needs to be passed through from the caller */
|
||||||
|
switch (sopt->sopt_size) {
|
||||||
|
case sizeof(int):
|
||||||
|
/* Linux compatibility */
|
||||||
|
optval = OPTBIT(INP_RECVPKTINFO);
|
||||||
|
error = sockopt_setint(sopt, optval);
|
||||||
|
break;
|
||||||
|
case sizeof(struct in_pktinfo):
|
||||||
|
/* Solaris compatibility */
|
||||||
|
pktinfo.ipi_ifindex = 0;
|
||||||
|
pktinfo.ipi_addr = inp->inp_prefsrcip;
|
||||||
|
error = sockopt_set(sopt, &pktinfo,
|
||||||
|
sizeof(pktinfo));
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
/*
|
||||||
|
* While size is stuck at 0, and, later, if
|
||||||
|
* the caller doesn't use an exactly sized
|
||||||
|
* recipient for the data, default to Linux
|
||||||
|
* compatibility
|
||||||
|
*/
|
||||||
|
optval = OPTBIT(INP_RECVPKTINFO);
|
||||||
|
error = sockopt_setint(sopt, optval);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
#if 0 /* defined(IPSEC) */
|
#if 0 /* defined(IPSEC) */
|
||||||
case IP_IPSEC_POLICY:
|
case IP_IPSEC_POLICY:
|
||||||
{
|
{
|
||||||
|
@ -1416,11 +1475,14 @@ ip_setpktopts(struct mbuf *control, struct ip_pktopts *pktopts, int *flags,
|
||||||
struct inpcb *inp, kauth_cred_t cred)
|
struct inpcb *inp, kauth_cred_t cred)
|
||||||
{
|
{
|
||||||
struct cmsghdr *cm;
|
struct cmsghdr *cm;
|
||||||
struct in_pktinfo *pktinfo;
|
struct in_pktinfo pktinfo;
|
||||||
int error;
|
int error;
|
||||||
|
|
||||||
pktopts->ippo_imo = inp->inp_moptions;
|
pktopts->ippo_imo = inp->inp_moptions;
|
||||||
sockaddr_in_init(&pktopts->ippo_laddr, &inp->inp_laddr, 0);
|
|
||||||
|
struct in_addr *ia = in_nullhost(inp->inp_prefsrcip) ? &inp->inp_laddr :
|
||||||
|
&inp->inp_prefsrcip;
|
||||||
|
sockaddr_in_init(&pktopts->ippo_laddr, ia, 0);
|
||||||
|
|
||||||
if (control == NULL)
|
if (control == NULL)
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -1446,13 +1508,23 @@ ip_setpktopts(struct mbuf *control, struct ip_pktopts *pktopts, int *flags,
|
||||||
|
|
||||||
switch (cm->cmsg_type) {
|
switch (cm->cmsg_type) {
|
||||||
case IP_PKTINFO:
|
case IP_PKTINFO:
|
||||||
if (cm->cmsg_len != CMSG_LEN(sizeof(struct in_pktinfo)))
|
if (cm->cmsg_len != CMSG_LEN(sizeof(pktinfo)))
|
||||||
return EINVAL;
|
return EINVAL;
|
||||||
|
memcpy(&pktinfo, CMSG_DATA(cm), sizeof(pktinfo));
|
||||||
pktinfo = (struct in_pktinfo *)CMSG_DATA(cm);
|
error = ip_pktinfo_prepare(&pktinfo, pktopts, flags,
|
||||||
error = ip_pktinfo_prepare(pktinfo, pktopts, flags,
|
|
||||||
cred);
|
cred);
|
||||||
if (error != 0)
|
if (error)
|
||||||
|
return error;
|
||||||
|
break;
|
||||||
|
case IP_SENDSRCADDR: /* FreeBSD compatibility */
|
||||||
|
if (cm->cmsg_len != CMSG_LEN(sizeof(struct in_addr)))
|
||||||
|
return EINVAL;
|
||||||
|
pktinfo.ipi_ifindex = 0;
|
||||||
|
pktinfo.ipi_addr =
|
||||||
|
((struct in_pktinfo *)CMSG_DATA(cm))->ipi_addr;
|
||||||
|
error = ip_pktinfo_prepare(&pktinfo, pktopts, flags,
|
||||||
|
cred);
|
||||||
|
if (error)
|
||||||
return error;
|
return error;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $NetBSD: param.h,v 1.554 2017/12/06 08:25:47 knakahara Exp $ */
|
/* $NetBSD: param.h,v 1.555 2018/01/01 00:51:36 christos Exp $ */
|
||||||
|
|
||||||
/*-
|
/*-
|
||||||
* Copyright (c) 1982, 1986, 1989, 1993
|
* Copyright (c) 1982, 1986, 1989, 1993
|
||||||
|
@ -67,7 +67,7 @@
|
||||||
* 2.99.9 (299000900)
|
* 2.99.9 (299000900)
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#define __NetBSD_Version__ 899000900 /* NetBSD 8.99.9 */
|
#define __NetBSD_Version__ 899001000 /* NetBSD 8.99.10 */
|
||||||
|
|
||||||
#define __NetBSD_Prereq__(M,m,p) (((((M) * 100000000) + \
|
#define __NetBSD_Prereq__(M,m,p) (((((M) * 100000000) + \
|
||||||
(m) * 1000000) + (p) * 100) <= __NetBSD_Version__)
|
(m) * 1000000) + (p) * 100) <= __NetBSD_Version__)
|
||||||
|
|
Loading…
Reference in New Issue