The branch main has been updated by kp:

URL: 
https://cgit.FreeBSD.org/src/commit/?id=da27faa01f27dd04915c204782542525d43ab7eb

commit da27faa01f27dd04915c204782542525d43ab7eb
Author:     Kristof Provost <k...@freebsd.org>
AuthorDate: 2025-07-01 15:18:20 +0000
Commit:     Kristof Provost <k...@freebsd.org>
CommitDate: 2025-07-03 07:16:14 +0000

    pfctl: fix parsing of '10/8'
    
    FreeBSD's getaddrinfo() differs a little from OpenBSD's, and it will resolve
    '10' to IPv4 address '0.0.0.10', wheres OpenBSD's will just fail. As a 
result we
    work out that '10/8' is '0.0.0.0/8', rather than the intended '10.0.0.0/8'.
    
    Reverse the order of operations: attempt to parse the address with
    inet_net_pton() first and only use getaddrinfo() if that fails.
    
    Sponsored by:   Rubicon Communications, LLC ("Netgate")
---
 sbin/pfctl/pfctl_parser.c | 30 +++++++++++++++---------------
 1 file changed, 15 insertions(+), 15 deletions(-)

diff --git a/sbin/pfctl/pfctl_parser.c b/sbin/pfctl/pfctl_parser.c
index 8eb9bd1d6f5a..cb083bd09344 100644
--- a/sbin/pfctl/pfctl_parser.c
+++ b/sbin/pfctl/pfctl_parser.c
@@ -1866,33 +1866,33 @@ host_ip(const char *s, int mask)
        struct addrinfo          hints, *res;
        struct node_host        *h = NULL;
 
+       h = calloc(1, sizeof(*h));
+       if (h == NULL)
+               err(1, "%s: calloc", __func__);
+       if (mask != -1) {
+               /* Try to parse 10/8 */
+               h->af = AF_INET;
+               if (inet_net_pton(AF_INET, s, &h->addr.v.a.addr.v4,
+                   sizeof(h->addr.v.a.addr.v4)) != -1)
+                       goto out;
+       }
+
        memset(&hints, 0, sizeof(hints));
        hints.ai_family = AF_UNSPEC;
        hints.ai_socktype = SOCK_DGRAM; /*dummy*/
        hints.ai_flags = AI_NUMERICHOST;
        if (getaddrinfo(s, NULL, &hints, &res) == 0) {
-               h = calloc(1, sizeof(*h));
-               if (h == NULL)
-                       err(1, "%s: calloc", __func__);
                h->af = res->ai_family;
                copy_satopfaddr(&h->addr.v.a.addr, res->ai_addr);
                if (h->af == AF_INET6)
                        h->ifindex =
                            ((struct sockaddr_in6 
*)res->ai_addr)->sin6_scope_id;
                freeaddrinfo(res);
-       } else { /* ie. for 10/8 parsing */
-               if (mask == -1)
-                       return (NULL);
-               h = calloc(1, sizeof(*h));
-               if (h == NULL)
-                       err(1, "%s: calloc", __func__);
-               h->af = AF_INET;
-               if (inet_net_pton(AF_INET, s, &h->addr.v.a.addr.v4,
-                       sizeof(h->addr.v.a.addr.v4)) == -1) {
-                       free(h);
-                       return (NULL);
-               }
+       } else {
+               free(h);
+               return (NULL);
        }
+out:
        set_ipmask(h, mask);
        h->ifname = NULL;
        h->next = NULL;

Reply via email to