[email protected] writes:

> Thanks for the patch. Unfortunately, I could not apply it to -7. I've
> tested -current. The problem seems to be solved.

Here it is, adjusted for the "netbsd-7" cvs tag:

--- sys/net/npf/npf_handler.c~  2017-03-30 17:26:49.458901595 +0200
+++ sys/net/npf/npf_handler.c   2017-03-30 17:29:52.833241529 +0200
@@ -146,7 +146,7 @@
        npf_conn_t *con;
        npf_rule_t *rl;
        npf_rproc_t *rp;
-       int error, retfl;
+       int error, retfl, flags;
        int decision;
 
        /*
@@ -164,9 +164,17 @@
        rp = NULL;
 
        /* Cache everything.  Determine whether it is an IP fragment. */
-       if (__predict_false(npf_cache_all(&npc) & NPC_IPFRAG)) {
+       flags = npf_cache_all(&npc);
+       if (__predict_false(flags & NPC_IPFRAG)) {
                /*
-                * Pass to IPv4 or IPv6 reassembly mechanism.
+                * We pass IPv6 fragments unconditionally
+                * The first IPv6 fragment is not marked as such
+                * and passes through the filter
+                */
+               if (flags & NPC_IP6)
+                       return 0;
+               /*
+                * Pass to IPv4 reassembly mechanism.
                 */
                error = npf_reassembly(&npc, mp);
                if (error) {
--- sys/net/npf/npf_inet.c~     2017-03-30 17:27:07.661343255 +0200
+++ sys/net/npf/npf_inet.c      2017-03-30 17:30:45.721564537 +0200
@@ -352,6 +352,7 @@
        case (IPV6_VERSION >> 4): {
                struct ip6_hdr *ip6;
                struct ip6_ext *ip6e;
+               struct ip6_frag *ip6f;
                size_t off, hlen;
 
                ip6 = nbuf_ensure_contig(nbuf, sizeof(struct ip6_hdr));
@@ -384,8 +385,21 @@
                                hlen = (ip6e->ip6e_len + 1) << 3;
                                break;
                        case IPPROTO_FRAGMENT:
+                               ip6f = nbuf_ensure_contig(nbuf, sizeof(*ip6f));
+                               if (ip6f == NULL)
+                                       return 0;
+                               /*
+                                * We treat the first fragment as a regular
+                                * packet and then we pass the rest of the
+                                * fragments unconditionally. This way if
+                                * the first packet passes the rest will
+                                * be able to reassembled, if not they will
+                                * be ignored. We can do better later.
+                                */
+                               if (ntohs(ip6f->ip6f_offlg & IP6F_OFF_MASK) != 
0)
+                                       flags |= NPC_IPFRAG;
+
                                hlen = sizeof(struct ip6_frag);
-                               flags |= NPC_IPFRAG;
                                break;
                        case IPPROTO_AH:
                                hlen = (ip6e->ip6e_len + 2) << 2;


-tih
-- 
Most people who graduate with CS degrees don't understand the significance
of Lisp.  Lisp is the most important idea in computer science.  --Alan Kay

Reply via email to