On 2011-02-12, m <mutimir2...@yahoo.com> wrote:
>
> please take a look and tell if I'm missing something or is this a serious bug?
>
> #tcpdump -n -e -ttt -i pflog0
> tcpdump: listening on pflog0, link-type PFLOG
> Feb 12 15:40:18.181584 rule 704/(match) pass in on vlan2: 10.100.100.55.49747 
> > 10.7.13.115.25: S 1349727012:1349727012(0) win 5840 <mss 
> 1460,sackOK,timestamp 973726855[|tcp]> (DF) [tos 0x10]
>
>
> # pfctl -vvsr | grep @704
> @704 pass in log quick on vlan2 inet proto tcp from 10.100.100.0/24 to 
> 10.10.4.114 - 10.10.4.116 flags S/SA keep state
>
> So, the rule with the IP Range matches wrong dst address. If I rewrite a rule 
> without using a range, then it works OK.
>
> OpenBSD 4.7 GENERIC i386
>
> Thank You very much.

Confirmed, address ranges are broken on little-endian and it's
still present in -current.

I've tested this on v4/v6 LE, baking a BE kernel now. Any ok's?

Index: pf.c
===================================================================
RCS file: /cvs/src/sys/net/pf.c,v
retrieving revision 1.725
diff -u -p -r1.725 pf.c
--- pf.c        6 Feb 2011 23:12:12 -0000       1.725
+++ pf.c        12 Feb 2011 21:37:44 -0000
@@ -2180,8 +2180,8 @@ pf_match_addr_range(struct pf_addr *b, s
        switch (af) {
 #ifdef INET
        case AF_INET:
-               if ((a->addr32[0] < b->addr32[0]) ||
-                   (a->addr32[0] > e->addr32[0]))
+               if ((ntohl(a->addr32[0]) < ntohl(b->addr32[0])) ||
+                   (ntohl(a->addr32[0]) > ntohl(e->addr32[0])))
                        return (0);
                break;
 #endif /* INET */
@@ -2191,15 +2191,15 @@ pf_match_addr_range(struct pf_addr *b, s
 
                /* check a >= b */
                for (i = 0; i < 4; ++i)
-                       if (a->addr32[i] > b->addr32[i])
+                       if (ntohl(a->addr32[i]) > ntohl(b->addr32[i]))
                                break;
-                       else if (a->addr32[i] < b->addr32[i])
+                       else if (ntohl(a->addr32[i]) < ntohl(b->addr32[i]))
                                return (0);
                /* check a <= e */
                for (i = 0; i < 4; ++i)
-                       if (a->addr32[i] < e->addr32[i])
+                       if (ntohl(a->addr32[i]) < ntohl(e->addr32[i]))
                                break;
-                       else if (a->addr32[i] > e->addr32[i])
+                       else if (ntohl(a->addr32[i]) > ntohl(e->addr32[i]))
                                return (0);
                break;
        }

Reply via email to