Merge git://git.kernel.org/pub/scm/linux/kernel/git/davem/net-next
[deliverable/linux.git] / net / netfilter / xt_socket.c
index e092cb04632607f21f253d84a8692681a1fefe89..43e26c8811007fc1736c16d60f8e0c647f171d3a 100644 (file)
@@ -205,6 +205,7 @@ static bool
 socket_match(const struct sk_buff *skb, struct xt_action_param *par,
             const struct xt_socket_mtinfo1 *info)
 {
+       struct sk_buff *pskb = (struct sk_buff *)skb;
        struct sock *sk = skb->sk;
 
        if (!sk)
@@ -226,6 +227,10 @@ socket_match(const struct sk_buff *skb, struct xt_action_param *par,
                if (info->flags & XT_SOCKET_TRANSPARENT)
                        transparent = xt_socket_sk_is_transparent(sk);
 
+               if (info->flags & XT_SOCKET_RESTORESKMARK && !wildcard &&
+                   transparent)
+                       pskb->mark = sk->sk_mark;
+
                if (sk != skb->sk)
                        sock_gen_put(sk);
 
@@ -247,7 +252,7 @@ socket_mt4_v0(const struct sk_buff *skb, struct xt_action_param *par)
 }
 
 static bool
-socket_mt4_v1_v2(const struct sk_buff *skb, struct xt_action_param *par)
+socket_mt4_v1_v2_v3(const struct sk_buff *skb, struct xt_action_param *par)
 {
        return socket_match(skb, par, par->matchinfo);
 }
@@ -371,9 +376,10 @@ static struct sock *xt_socket_lookup_slow_v6(const struct sk_buff *skb,
 }
 
 static bool
-socket_mt6_v1_v2(const struct sk_buff *skb, struct xt_action_param *par)
+socket_mt6_v1_v2_v3(const struct sk_buff *skb, struct xt_action_param *par)
 {
        const struct xt_socket_mtinfo1 *info = (struct xt_socket_mtinfo1 *) par->matchinfo;
+       struct sk_buff *pskb = (struct sk_buff *)skb;
        struct sock *sk = skb->sk;
 
        if (!sk)
@@ -395,6 +401,10 @@ socket_mt6_v1_v2(const struct sk_buff *skb, struct xt_action_param *par)
                if (info->flags & XT_SOCKET_TRANSPARENT)
                        transparent = xt_socket_sk_is_transparent(sk);
 
+               if (info->flags & XT_SOCKET_RESTORESKMARK && !wildcard &&
+                   transparent)
+                       pskb->mark = sk->sk_mark;
+
                if (sk != skb->sk)
                        sock_gen_put(sk);
 
@@ -428,6 +438,19 @@ static int socket_mt_v2_check(const struct xt_mtchk_param *par)
        return 0;
 }
 
+static int socket_mt_v3_check(const struct xt_mtchk_param *par)
+{
+       const struct xt_socket_mtinfo3 *info =
+                                   (struct xt_socket_mtinfo3 *)par->matchinfo;
+
+       if (info->flags & ~XT_SOCKET_FLAGS_V3) {
+               pr_info("unknown flags 0x%x\n",
+                       info->flags & ~XT_SOCKET_FLAGS_V3);
+               return -EINVAL;
+       }
+       return 0;
+}
+
 static struct xt_match socket_mt_reg[] __read_mostly = {
        {
                .name           = "socket",
@@ -442,7 +465,7 @@ static struct xt_match socket_mt_reg[] __read_mostly = {
                .name           = "socket",
                .revision       = 1,
                .family         = NFPROTO_IPV4,
-               .match          = socket_mt4_v1_v2,
+               .match          = socket_mt4_v1_v2_v3,
                .checkentry     = socket_mt_v1_check,
                .matchsize      = sizeof(struct xt_socket_mtinfo1),
                .hooks          = (1 << NF_INET_PRE_ROUTING) |
@@ -454,7 +477,7 @@ static struct xt_match socket_mt_reg[] __read_mostly = {
                .name           = "socket",
                .revision       = 1,
                .family         = NFPROTO_IPV6,
-               .match          = socket_mt6_v1_v2,
+               .match          = socket_mt6_v1_v2_v3,
                .checkentry     = socket_mt_v1_check,
                .matchsize      = sizeof(struct xt_socket_mtinfo1),
                .hooks          = (1 << NF_INET_PRE_ROUTING) |
@@ -466,7 +489,7 @@ static struct xt_match socket_mt_reg[] __read_mostly = {
                .name           = "socket",
                .revision       = 2,
                .family         = NFPROTO_IPV4,
-               .match          = socket_mt4_v1_v2,
+               .match          = socket_mt4_v1_v2_v3,
                .checkentry     = socket_mt_v2_check,
                .matchsize      = sizeof(struct xt_socket_mtinfo1),
                .hooks          = (1 << NF_INET_PRE_ROUTING) |
@@ -478,13 +501,37 @@ static struct xt_match socket_mt_reg[] __read_mostly = {
                .name           = "socket",
                .revision       = 2,
                .family         = NFPROTO_IPV6,
-               .match          = socket_mt6_v1_v2,
+               .match          = socket_mt6_v1_v2_v3,
                .checkentry     = socket_mt_v2_check,
                .matchsize      = sizeof(struct xt_socket_mtinfo1),
                .hooks          = (1 << NF_INET_PRE_ROUTING) |
                                  (1 << NF_INET_LOCAL_IN),
                .me             = THIS_MODULE,
        },
+#endif
+       {
+               .name           = "socket",
+               .revision       = 3,
+               .family         = NFPROTO_IPV4,
+               .match          = socket_mt4_v1_v2_v3,
+               .checkentry     = socket_mt_v3_check,
+               .matchsize      = sizeof(struct xt_socket_mtinfo1),
+               .hooks          = (1 << NF_INET_PRE_ROUTING) |
+                                 (1 << NF_INET_LOCAL_IN),
+               .me             = THIS_MODULE,
+       },
+#ifdef XT_SOCKET_HAVE_IPV6
+       {
+               .name           = "socket",
+               .revision       = 3,
+               .family         = NFPROTO_IPV6,
+               .match          = socket_mt6_v1_v2_v3,
+               .checkentry     = socket_mt_v3_check,
+               .matchsize      = sizeof(struct xt_socket_mtinfo1),
+               .hooks          = (1 << NF_INET_PRE_ROUTING) |
+                                 (1 << NF_INET_LOCAL_IN),
+               .me             = THIS_MODULE,
+       },
 #endif
 };
 
This page took 0.028173 seconds and 5 git commands to generate.