Changeset View
Changeset View
Standalone View
Standalone View
sys/netinet6/raw_ip6.c
Show First 20 Lines • Show All 331 Lines • ▼ Show 20 Lines | if (last != NULL) { | ||||
IP6STAT_DEC(ip6s_delivered); | IP6STAT_DEC(ip6s_delivered); | ||||
} | } | ||||
return (IPPROTO_DONE); | return (IPPROTO_DONE); | ||||
} | } | ||||
void | void | ||||
rip6_ctlinput(int cmd, struct sockaddr *sa, void *d) | rip6_ctlinput(int cmd, struct sockaddr *sa, void *d) | ||||
{ | { | ||||
struct ip6_hdr *ip6; | |||||
struct mbuf *m; | |||||
int off = 0; | |||||
struct ip6ctlparam *ip6cp = NULL; | struct ip6ctlparam *ip6cp = NULL; | ||||
const struct sockaddr_in6 *sa6_src = NULL; | const struct sockaddr_in6 *sa6_src = NULL; | ||||
void *cmdarg; | void *cmdarg; | ||||
struct inpcb *(*notify)(struct inpcb *, int) = in6_rtchange; | struct inpcb *(*notify)(struct inpcb *, int) = in6_rtchange; | ||||
if (sa->sa_family != AF_INET6 || | if (sa->sa_family != AF_INET6 || | ||||
sa->sa_len != sizeof(struct sockaddr_in6)) | sa->sa_len != sizeof(struct sockaddr_in6)) | ||||
return; | return; | ||||
if ((unsigned)cmd >= PRC_NCMDS) | if ((unsigned)cmd >= PRC_NCMDS) | ||||
return; | return; | ||||
if (PRC_IS_REDIRECT(cmd)) | if (PRC_IS_REDIRECT(cmd)) | ||||
notify = in6_rtchange, d = NULL; | notify = in6_rtchange, d = NULL; | ||||
else if (cmd == PRC_HOSTDEAD) | else if (cmd == PRC_HOSTDEAD) | ||||
d = NULL; | d = NULL; | ||||
else if (inet6ctlerrmap[cmd] == 0) | else if (inet6ctlerrmap[cmd] == 0) | ||||
return; | return; | ||||
/* | /* | ||||
* If the parameter is from icmp6, decode it. | * If the parameter is from icmp6, decode it. | ||||
*/ | */ | ||||
if (d != NULL) { | if (d != NULL) { | ||||
ip6cp = (struct ip6ctlparam *)d; | ip6cp = (struct ip6ctlparam *)d; | ||||
m = ip6cp->ip6c_m; | |||||
ip6 = ip6cp->ip6c_ip6; | |||||
off = ip6cp->ip6c_off; | |||||
cmdarg = ip6cp->ip6c_cmdarg; | cmdarg = ip6cp->ip6c_cmdarg; | ||||
sa6_src = ip6cp->ip6c_src; | sa6_src = ip6cp->ip6c_src; | ||||
} else { | } else { | ||||
m = NULL; | |||||
ip6 = NULL; | |||||
cmdarg = NULL; | cmdarg = NULL; | ||||
sa6_src = &sa6_any; | sa6_src = &sa6_any; | ||||
} | } | ||||
(void) in6_pcbnotify(&V_ripcbinfo, sa, 0, | (void) in6_pcbnotify(&V_ripcbinfo, sa, 0, | ||||
(const struct sockaddr *)sa6_src, 0, cmd, cmdarg, notify); | (const struct sockaddr *)sa6_src, 0, cmd, cmdarg, notify); | ||||
} | } | ||||
/* | /* | ||||
* Generate IPv6 header and pass packet to ip6_output. Tack on options user | * Generate IPv6 header and pass packet to ip6_output. Tack on options user | ||||
* may have setup with control call. | * may have setup with control call. | ||||
*/ | */ | ||||
int | int | ||||
rip6_output(struct mbuf *m, struct socket *so, ...) | rip6_output(struct mbuf *m, struct socket *so, ...) | ||||
{ | { | ||||
struct mbuf *control; | struct mbuf *control; | ||||
struct m_tag *mtag; | struct m_tag *mtag; | ||||
struct sockaddr_in6 *dstsock; | struct sockaddr_in6 *dstsock; | ||||
struct in6_addr *dst; | |||||
struct ip6_hdr *ip6; | struct ip6_hdr *ip6; | ||||
struct inpcb *in6p; | struct inpcb *in6p; | ||||
u_int plen = m->m_pkthdr.len; | u_int plen = m->m_pkthdr.len; | ||||
int error = 0; | int error = 0; | ||||
struct ip6_pktopts opt, *optp; | struct ip6_pktopts opt, *optp; | ||||
struct ifnet *oifp = NULL; | struct ifnet *oifp = NULL; | ||||
int type = 0, code = 0; /* for ICMPv6 output statistics only */ | int type = 0, code = 0; /* for ICMPv6 output statistics only */ | ||||
int scope_ambiguous = 0; | int scope_ambiguous = 0; | ||||
int use_defzone = 0; | int use_defzone = 0; | ||||
int hlim = 0; | int hlim = 0; | ||||
struct in6_addr in6a; | struct in6_addr in6a; | ||||
va_list ap; | va_list ap; | ||||
va_start(ap, so); | va_start(ap, so); | ||||
dstsock = va_arg(ap, struct sockaddr_in6 *); | dstsock = va_arg(ap, struct sockaddr_in6 *); | ||||
control = va_arg(ap, struct mbuf *); | control = va_arg(ap, struct mbuf *); | ||||
va_end(ap); | va_end(ap); | ||||
in6p = sotoinpcb(so); | in6p = sotoinpcb(so); | ||||
INP_WLOCK(in6p); | INP_WLOCK(in6p); | ||||
dst = &dstsock->sin6_addr; | |||||
if (control != NULL) { | if (control != NULL) { | ||||
if ((error = ip6_setpktopts(control, &opt, | if ((error = ip6_setpktopts(control, &opt, | ||||
in6p->in6p_outputopts, so->so_cred, | in6p->in6p_outputopts, so->so_cred, | ||||
so->so_proto->pr_protocol)) != 0) { | so->so_proto->pr_protocol)) != 0) { | ||||
goto bad; | goto bad; | ||||
} | } | ||||
optp = &opt; | optp = &opt; | ||||
} else | } else | ||||
▲ Show 20 Lines • Show All 485 Lines • Show Last 20 Lines |