Index: pf.c =================================================================== RCS file: /cvs/src/sys/net/pf.c,v retrieving revision 1.1094 diff -u -p -r1.1094 pf.c --- pf.c 24 Jul 2020 18:17:15 -0000 1.1094 +++ pf.c 13 Oct 2020 03:15:44 -0000 @@ -5992,6 +5992,7 @@ pf_route(struct pf_pdesc *pd, struct pf_ struct sockaddr_in *dst, sin; struct rtentry *rt = NULL; struct ip *ip; + struct ifnet *rtifp = NULL; struct ifnet *ifp = NULL; struct pf_addr naddr; struct pf_src_node *sns[PF_SN_MAX]; @@ -6059,8 +6060,19 @@ pf_route(struct pf_pdesc *pd, struct pf_ s->rt_addr.v4.s_addr; ifp = s->rt_kif ? s->rt_kif->pfik_ifp : NULL; } - if (ifp == NULL) + + rt = rtalloc(sintosa(dst), RT_RESOLVE, rtableid); + if (!rtisvalid(rt)) { + ipstat_inc(ips_noroute); goto bad; + } + + if (ifp == NULL) { + rtifp = if_get(rt->rt_ifidx); + if (rtifp == NULL) + goto bad; + ifp = rtifp; + } if (pd->kif->pfik_ifp != ifp) { if (pf_test(AF_INET, PF_OUT, ifp, &m0) != PF_PASS) @@ -6074,12 +6086,6 @@ pf_route(struct pf_pdesc *pd, struct pf_ } ip = mtod(m0, struct ip *); } - - rt = rtalloc(sintosa(dst), RT_RESOLVE, rtableid); - if (!rtisvalid(rt)) { - ipstat_inc(ips_noroute); - goto bad; - } /* A locally generated packet may have invalid source address. */ if ((ntohl(ip->ip_src.s_addr) >> IN_CLASSA_NSHIFT) == IN_LOOPBACKNET && (ifp->if_flags & IFF_LOOPBACK) == 0) @@ -6133,6 +6139,7 @@ pf_route(struct pf_pdesc *pd, struct pf_ done: if (r->rt != PF_DUPTO) pd->m = NULL; + if_put(rtifp); rtfree(rt); return; @@ -6151,6 +6158,7 @@ pf_route6(struct pf_pdesc *pd, struct pf struct rtentry *rt = NULL; struct ip6_hdr *ip6; struct ifnet *ifp = NULL; + struct ifnet *rtifp = NULL; struct pf_addr naddr; struct pf_src_node *sns[PF_SN_MAX]; struct m_tag *mtag; @@ -6214,8 +6222,17 @@ pf_route6(struct pf_pdesc *pd, struct pf &s->rt_addr, AF_INET6); ifp = s->rt_kif ? s->rt_kif->pfik_ifp : NULL; } - if (ifp == NULL) + rt = rtalloc(sin6tosa(dst), RT_RESOLVE, rtableid); + if (!rtisvalid(rt)) { + ip6stat_inc(ip6s_noroute); goto bad; + } + if (ifp == NULL) { + rtifp = if_get(rt->rt_ifidx); + if (rtifp == NULL) + goto bad; + ifp = rtifp; + } if (pd->kif->pfik_ifp != ifp) { if (pf_test(AF_INET6, PF_OUT, ifp, &m0) != PF_PASS) @@ -6231,11 +6248,7 @@ pf_route6(struct pf_pdesc *pd, struct pf if (IN6_IS_SCOPE_EMBED(&dst->sin6_addr)) dst->sin6_addr.s6_addr16[1] = htons(ifp->if_index); - rt = rtalloc(sin6tosa(dst), RT_RESOLVE, rtableid); - if (!rtisvalid(rt)) { - ip6stat_inc(ip6s_noroute); - goto bad; - } + /* A locally generated packet may have invalid source address. */ if (IN6_IS_ADDR_LOOPBACK(&ip6->ip6_src) && (ifp->if_flags & IFF_LOOPBACK) == 0) @@ -6262,6 +6275,7 @@ pf_route6(struct pf_pdesc *pd, struct pf done: if (r->rt != PF_DUPTO) pd->m = NULL; + if_put(rtifp); rtfree(rt); return;