aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKristof Provost <kp@FreeBSD.org>2021-02-13 15:31:52 +0000
committerKristof Provost <kp@FreeBSD.org>2021-02-14 11:07:31 +0000
commit5e42cb139fc17f165c9c93ac97069dc7770490e2 (patch)
treeaa85016321fdd604492dfbffc6a900cbfe09b35a
parented782b9f5a7a05debe944a33b4ac9e5629a95803 (diff)
downloadsrc-5e42cb139fc17f165c9c93ac97069dc7770490e2.tar.gz
src-5e42cb139fc17f165c9c93ac97069dc7770490e2.zip
pf: Slightly relax pf_rule_addr validation
Ensure we don't reject no-route / urpf-failed addresses. PR: 253479 Reported by: michal AT microwave.sk Revied by: donner@ MFC after: 3 days Differential Revision: https://reviews.freebsd.org/D28650
-rw-r--r--sys/netpfil/pf/pf_ioctl.c47
1 files changed, 30 insertions, 17 deletions
diff --git a/sys/netpfil/pf/pf_ioctl.c b/sys/netpfil/pf/pf_ioctl.c
index 644a091808cd..edc8443dcc0a 100644
--- a/sys/netpfil/pf/pf_ioctl.c
+++ b/sys/netpfil/pf/pf_ioctl.c
@@ -1558,8 +1558,32 @@ pf_krule_to_rule(const struct pf_krule *krule, struct pf_rule *rule)
}
static int
+pf_check_rule_addr(const struct pf_rule_addr *addr)
+{
+
+ switch (addr->addr.type) {
+ case PF_ADDR_ADDRMASK:
+ case PF_ADDR_NOROUTE:
+ case PF_ADDR_DYNIFTL:
+ case PF_ADDR_TABLE:
+ case PF_ADDR_URPFFAILED:
+ case PF_ADDR_RANGE:
+ break;
+ default:
+ return (EINVAL);
+ }
+
+ if (addr->addr.p.dyn != NULL) {
+ return (EINVAL);
+ }
+
+ return (0);
+}
+
+static int
pf_rule_to_krule(const struct pf_rule *rule, struct pf_krule *krule)
{
+ int ret;
#ifndef INET
if (rule->af == AF_INET) {
@@ -1572,23 +1596,12 @@ pf_rule_to_krule(const struct pf_rule *rule, struct pf_krule *krule)
}
#endif /* INET6 */
- if (rule->src.addr.type != PF_ADDR_ADDRMASK &&
- rule->src.addr.type != PF_ADDR_DYNIFTL &&
- rule->src.addr.type != PF_ADDR_TABLE) {
- return (EINVAL);
- }
- if (rule->src.addr.p.dyn != NULL) {
- return (EINVAL);
- }
-
- if (rule->dst.addr.type != PF_ADDR_ADDRMASK &&
- rule->dst.addr.type != PF_ADDR_DYNIFTL &&
- rule->dst.addr.type != PF_ADDR_TABLE) {
- return (EINVAL);
- }
- if (rule->dst.addr.p.dyn != NULL) {
- return (EINVAL);
- }
+ ret = pf_check_rule_addr(&rule->src);
+ if (ret != 0)
+ return (ret);
+ ret = pf_check_rule_addr(&rule->dst);
+ if (ret != 0)
+ return (ret);
bzero(krule, sizeof(*krule));