Commit c81baf47 authored by Tom Lendacky's avatar Tom Lendacky Committed by Linus Torvalds

[IPSEC]: Missing ipv6 policy checks.

parent 0946befc
...@@ -50,6 +50,7 @@ struct inet6_protocol ...@@ -50,6 +50,7 @@ struct inet6_protocol
struct inet6_skb_parm *opt, struct inet6_skb_parm *opt,
int type, int code, int offset, int type, int code, int offset,
__u32 info); __u32 info);
int no_policy;
}; };
#endif #endif
......
...@@ -330,6 +330,7 @@ static struct xfrm_type ah6_type = ...@@ -330,6 +330,7 @@ static struct xfrm_type ah6_type =
static struct inet6_protocol ah6_protocol = { static struct inet6_protocol ah6_protocol = {
.handler = xfrm6_rcv, .handler = xfrm6_rcv,
.err_handler = ah6_err, .err_handler = ah6_err,
.no_policy = 1,
}; };
int __init ah6_init(void) int __init ah6_init(void)
......
...@@ -499,6 +499,7 @@ static struct xfrm_type esp6_type = ...@@ -499,6 +499,7 @@ static struct xfrm_type esp6_type =
static struct inet6_protocol esp6_protocol = { static struct inet6_protocol esp6_protocol = {
.handler = xfrm6_rcv, .handler = xfrm6_rcv,
.err_handler = esp6_err, .err_handler = esp6_err,
.no_policy = 1,
}; };
int __init esp6_init(void) int __init esp6_init(void)
......
...@@ -43,6 +43,7 @@ ...@@ -43,6 +43,7 @@
#include <net/ndisc.h> #include <net/ndisc.h>
#include <net/ip6_route.h> #include <net/ip6_route.h>
#include <net/addrconf.h> #include <net/addrconf.h>
#include <net/xfrm.h>
...@@ -149,7 +150,14 @@ static inline int ip6_input_finish(struct sk_buff *skb) ...@@ -149,7 +150,14 @@ static inline int ip6_input_finish(struct sk_buff *skb)
hash = nexthdr & (MAX_INET_PROTOS - 1); hash = nexthdr & (MAX_INET_PROTOS - 1);
if ((ipprot = inet6_protos[hash]) != NULL) { if ((ipprot = inet6_protos[hash]) != NULL) {
int ret = ipprot->handler(&skb); int ret;
if (!ipprot->no_policy &&
!xfrm6_policy_check(NULL, XFRM_POLICY_IN, skb)) {
kfree_skb(skb);
return 0;
}
ret = ipprot->handler(&skb);
if (ret < 0) { if (ret < 0) {
nexthdr = -ret; nexthdr = -ret;
goto resubmit; goto resubmit;
...@@ -157,9 +165,11 @@ static inline int ip6_input_finish(struct sk_buff *skb) ...@@ -157,9 +165,11 @@ static inline int ip6_input_finish(struct sk_buff *skb)
IP6_INC_STATS_BH(Ip6InDelivers); IP6_INC_STATS_BH(Ip6InDelivers);
} else { } else {
if (!raw_sk) { if (!raw_sk) {
IP6_INC_STATS_BH(Ip6InUnknownProtos); if (xfrm6_policy_check(NULL, XFRM_POLICY_IN, skb)) {
icmpv6_param_prob(skb, ICMPV6_UNK_NEXTHDR, IP6_INC_STATS_BH(Ip6InUnknownProtos);
offsetof(struct ipv6hdr, nexthdr)); icmpv6_param_prob(skb, ICMPV6_UNK_NEXTHDR,
offsetof(struct ipv6hdr, nexthdr));
}
} else { } else {
IP6_INC_STATS_BH(Ip6InDelivers); IP6_INC_STATS_BH(Ip6InDelivers);
kfree_skb(skb); kfree_skb(skb);
......
...@@ -50,6 +50,7 @@ ...@@ -50,6 +50,7 @@
#include <net/addrconf.h> #include <net/addrconf.h>
#include <net/rawv6.h> #include <net/rawv6.h>
#include <net/icmp.h> #include <net/icmp.h>
#include <net/xfrm.h>
static __inline__ void ipv6_select_ident(struct sk_buff *skb, struct frag_hdr *fhdr) static __inline__ void ipv6_select_ident(struct sk_buff *skb, struct frag_hdr *fhdr)
{ {
...@@ -747,6 +748,9 @@ int ip6_forward(struct sk_buff *skb) ...@@ -747,6 +748,9 @@ int ip6_forward(struct sk_buff *skb)
if (ipv6_devconf.forwarding == 0) if (ipv6_devconf.forwarding == 0)
goto error; goto error;
if (!xfrm6_policy_check(NULL, XFRM_POLICY_FWD, skb))
goto drop;
skb->ip_summed = CHECKSUM_NONE; skb->ip_summed = CHECKSUM_NONE;
/* /*
...@@ -781,6 +785,9 @@ int ip6_forward(struct sk_buff *skb) ...@@ -781,6 +785,9 @@ int ip6_forward(struct sk_buff *skb)
return -ETIMEDOUT; return -ETIMEDOUT;
} }
if (!xfrm6_route_forward(skb))
goto drop;
/* IPv6 specs say nothing about it, but it is clear that we cannot /* IPv6 specs say nothing about it, but it is clear that we cannot
send redirects to source routed frames. send redirects to source routed frames.
*/ */
......
...@@ -2193,6 +2193,7 @@ struct proto tcpv6_prot = { ...@@ -2193,6 +2193,7 @@ struct proto tcpv6_prot = {
static struct inet6_protocol tcpv6_protocol = { static struct inet6_protocol tcpv6_protocol = {
.handler = tcp_v6_rcv, .handler = tcp_v6_rcv,
.err_handler = tcp_v6_err, .err_handler = tcp_v6_err,
.no_policy = 1,
}; };
extern struct proto_ops inet6_stream_ops; extern struct proto_ops inet6_stream_ops;
......
...@@ -955,6 +955,7 @@ static int udpv6_sendmsg(struct kiocb *iocb, struct sock *sk, struct msghdr *msg ...@@ -955,6 +955,7 @@ static int udpv6_sendmsg(struct kiocb *iocb, struct sock *sk, struct msghdr *msg
static struct inet6_protocol udpv6_protocol = { static struct inet6_protocol udpv6_protocol = {
.handler = udpv6_rcv, .handler = udpv6_rcv,
.err_handler = udpv6_err, .err_handler = udpv6_err,
.no_policy = 1,
}; };
#define LINE_LEN 190 #define LINE_LEN 190
......
...@@ -680,6 +680,7 @@ static int sctp6_rcv(struct sk_buff **pskb) ...@@ -680,6 +680,7 @@ static int sctp6_rcv(struct sk_buff **pskb)
static struct inet6_protocol sctpv6_protocol = { static struct inet6_protocol sctpv6_protocol = {
.handler = sctp6_rcv, .handler = sctp6_rcv,
.err_handler = sctp_v6_err, .err_handler = sctp_v6_err,
.no_policy = 1,
}; };
static struct sctp_af sctp_ipv6_specific = { static struct sctp_af sctp_ipv6_specific = {
......
...@@ -776,6 +776,7 @@ static struct inet_protosw sctp_stream_protosw = { ...@@ -776,6 +776,7 @@ static struct inet_protosw sctp_stream_protosw = {
static struct inet_protocol sctp_protocol = { static struct inet_protocol sctp_protocol = {
.handler = sctp_rcv, .handler = sctp_rcv,
.err_handler = sctp_v4_err, .err_handler = sctp_v4_err,
.no_policy = 1,
}; };
/* IPv4 address related functions. */ /* IPv4 address related functions. */
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment