Date: Wed, 25 Jun 2014 17:13:05 GMT From: dpl@FreeBSD.org To: svn-soc-all@FreeBSD.org Subject: socsvn commit: r270027 - in soc2014/dpl: . netmap-ipfw/sys/netpfil/ipfw Message-ID: <201406251713.s5PHD5l3087329@socsvn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: dpl Date: Wed Jun 25 17:13:04 2014 New Revision: 270027 URL: http://svnweb.FreeBSD.org/socsvn/?view=rev&rev=270027 Log: Added some notes about the isolating process. They will be extended in order as the project advances. ip_fw_rules.h and ip_fw2.c have been modified, isolation has been completed. Added: soc2014/dpl/notes Modified: soc2014/dpl/netmap-ipfw/sys/netpfil/ipfw/ip_fw2.c soc2014/dpl/netmap-ipfw/sys/netpfil/ipfw/ip_fw_rules.h Modified: soc2014/dpl/netmap-ipfw/sys/netpfil/ipfw/ip_fw2.c ============================================================================== --- soc2014/dpl/netmap-ipfw/sys/netpfil/ipfw/ip_fw2.c Wed Jun 25 16:12:14 2014 (r270026) +++ soc2014/dpl/netmap-ipfw/sys/netpfil/ipfw/ip_fw2.c Wed Jun 25 17:13:04 2014 (r270027) @@ -216,610 +216,6 @@ #define ICMP(p) ((struct icmphdr *)(p)) #define ICMP6(p) ((struct icmp6_hdr *)(p)) -static __inline int -icmptype_match(struct icmphdr *icmp, ipfw_insn_u32 *cmd) -{ - int type = icmp->icmp_type; - - return (type <= ICMP_MAXTYPE && (cmd->d[0] & (1<<type)) ); -} - -#define TT ( (1 << ICMP_ECHO) | (1 << ICMP_ROUTERSOLICIT) | \ - (1 << ICMP_TSTAMP) | (1 << ICMP_IREQ) | (1 << ICMP_MASKREQ) ) - -static int -is_icmp_query(struct icmphdr *icmp) -{ - int type = icmp->icmp_type; - - return (type <= ICMP_MAXTYPE && (TT & (1<<type)) ); -} -#undef TT - -/* - * The following checks use two arrays of 8 or 16 bits to store the - * bits that we want set or clear, respectively. They are in the - * low and high half of cmd->arg1 or cmd->d[0]. - * - * We scan options and store the bits we find set. We succeed if - * - * (want_set & ~bits) == 0 && (want_clear & ~bits) == want_clear - * - * The code is sometimes optimized not to store additional variables. - */ - -static int -flags_match(ipfw_insn *cmd, u_int8_t bits) -{ - u_char want_clear; - bits = ~bits; - - if ( ((cmd->arg1 & 0xff) & bits) != 0) - return 0; /* some bits we want set were clear */ - want_clear = (cmd->arg1 >> 8) & 0xff; - if ( (want_clear & bits) != want_clear) - return 0; /* some bits we want clear were set */ - return 1; -} - -static int -ipopts_match(struct ip *ip, ipfw_insn *cmd) -{ - int optlen, bits = 0; - u_char *cp = (u_char *)(ip + 1); - int x = (ip->ip_hl << 2) - sizeof (struct ip); - - for (; x > 0; x -= optlen, cp += optlen) { - int opt = cp[IPOPT_OPTVAL]; - - if (opt == IPOPT_EOL) - break; - if (opt == IPOPT_NOP) - optlen = 1; - else { - optlen = cp[IPOPT_OLEN]; - if (optlen <= 0 || optlen > x) - return 0; /* invalid or truncated */ - } - switch (opt) { - - default: - break; - - case IPOPT_LSRR: - bits |= IP_FW_IPOPT_LSRR; - break; - - case IPOPT_SSRR: - bits |= IP_FW_IPOPT_SSRR; - break; - - case IPOPT_RR: - bits |= IP_FW_IPOPT_RR; - break; - - case IPOPT_TS: - bits |= IP_FW_IPOPT_TS; - break; - } - } - return (flags_match(cmd, bits)); -} - -static int -tcpopts_match(struct tcphdr *tcp, ipfw_insn *cmd) -{ - int optlen, bits = 0; - u_char *cp = (u_char *)(tcp + 1); - int x = (tcp->th_off << 2) - sizeof(struct tcphdr); - - for (; x > 0; x -= optlen, cp += optlen) { - int opt = cp[0]; - if (opt == TCPOPT_EOL) - break; - if (opt == TCPOPT_NOP) - optlen = 1; - else { - optlen = cp[1]; - if (optlen <= 0) - break; - } - - switch (opt) { - - default: - break; - - case TCPOPT_MAXSEG: - bits |= IP_FW_TCPOPT_MSS; - break; - - case TCPOPT_WINDOW: - bits |= IP_FW_TCPOPT_WINDOW; - break; - - case TCPOPT_SACK_PERMITTED: - case TCPOPT_SACK: - bits |= IP_FW_TCPOPT_SACK; - break; - - case TCPOPT_TIMESTAMP: - bits |= IP_FW_TCPOPT_TS; - break; - - } - } - return (flags_match(cmd, bits)); -} - -static int -iface_match(struct ifnet *ifp, ipfw_insn_if *cmd, struct ip_fw_chain *chain, uint32_t *tablearg) -{ - if (ifp == NULL) /* no iface with this packet, match fails */ - return 0; - /* Check by name or by IP address */ - if (cmd->name[0] != '\0') { /* match by name */ - if (cmd->name[0] == '\1') /* use tablearg to match */ - return ipfw_lookup_table_extended(chain, cmd->p.glob, - ifp->if_xname, tablearg, IPFW_TABLE_INTERFACE); - /* Check name */ - if (cmd->p.glob) { - if (fnmatch(cmd->name, ifp->if_xname, 0) == 0) - return(1); - } else { - if (strncmp(ifp->if_xname, cmd->name, IFNAMSIZ) == 0) - return(1); - } - } else { -#if !defined(USERSPACE) && defined(__FreeBSD__) /* and OSX too ? */ - struct ifaddr *ia; - - if_addr_rlock(ifp); - TAILQ_FOREACH(ia, &ifp->if_addrhead, ifa_link) { - if (ia->ifa_addr->sa_family != AF_INET) - continue; - if (cmd->p.ip.s_addr == ((struct sockaddr_in *) - (ia->ifa_addr))->sin_addr.s_addr) { - if_addr_runlock(ifp); - return(1); /* match */ - } - } - if_addr_runlock(ifp); -#endif /* __FreeBSD__ */ - } - return(0); /* no match, fail ... */ -} - -/* - * The verify_path function checks if a route to the src exists and - * if it is reachable via ifp (when provided). - * - * The 'verrevpath' option checks that the interface that an IP packet - * arrives on is the same interface that traffic destined for the - * packet's source address would be routed out of. - * The 'versrcreach' option just checks that the source address is - * reachable via any route (except default) in the routing table. - * These two are a measure to block forged packets. This is also - * commonly known as "anti-spoofing" or Unicast Reverse Path - * Forwarding (Unicast RFP) in Cisco-ese. The name of the knobs - * is purposely reminiscent of the Cisco IOS command, - * - * ip verify unicast reverse-path - * ip verify unicast source reachable-via any - * - * which implements the same functionality. But note that the syntax - * is misleading, and the check may be performed on all IP packets - * whether unicast, multicast, or broadcast. - */ -static int -verify_path(struct in_addr src, struct ifnet *ifp, u_int fib) -{ -#if defined(USERSPACE) || !defined(__FreeBSD__) - return 0; -#else - struct route ro; - struct sockaddr_in *dst; - - bzero(&ro, sizeof(ro)); - - dst = (struct sockaddr_in *)&(ro.ro_dst); - dst->sin_family = AF_INET; - dst->sin_len = sizeof(*dst); - dst->sin_addr = src; - in_rtalloc_ign(&ro, 0, fib); - - if (ro.ro_rt == NULL) - return 0; - - /* - * If ifp is provided, check for equality with rtentry. - * We should use rt->rt_ifa->ifa_ifp, instead of rt->rt_ifp, - * in order to pass packets injected back by if_simloop(): - * routing entry (via lo0) for our own address - * may exist, so we need to handle routing assymetry. - */ - if (ifp != NULL && ro.ro_rt->rt_ifa->ifa_ifp != ifp) { - RTFREE(ro.ro_rt); - return 0; - } - - /* if no ifp provided, check if rtentry is not default route */ - if (ifp == NULL && - satosin(rt_key(ro.ro_rt))->sin_addr.s_addr == INADDR_ANY) { - RTFREE(ro.ro_rt); - return 0; - } - - /* or if this is a blackhole/reject route */ - if (ifp == NULL && ro.ro_rt->rt_flags & (RTF_REJECT|RTF_BLACKHOLE)) { - RTFREE(ro.ro_rt); - return 0; - } - - /* found valid route */ - RTFREE(ro.ro_rt); - return 1; -#endif /* __FreeBSD__ */ -} - -#ifdef INET6 -/* - * ipv6 specific rules here... - */ -static __inline int -icmp6type_match (int type, ipfw_insn_u32 *cmd) -{ - return (type <= ICMP6_MAXTYPE && (cmd->d[type/32] & (1<<(type%32)) ) ); -} - -static int -flow6id_match( int curr_flow, ipfw_insn_u32 *cmd ) -{ - int i; - for (i=0; i <= cmd->o.arg1; ++i ) - if (curr_flow == cmd->d[i] ) - return 1; - return 0; -} - -/* support for IP6_*_ME opcodes */ -static int -search_ip6_addr_net (struct in6_addr * ip6_addr) -{ - struct ifnet *mdc; - struct ifaddr *mdc2; - struct in6_ifaddr *fdm; - struct in6_addr copia; - - TAILQ_FOREACH(mdc, &V_ifnet, if_link) { - if_addr_rlock(mdc); - TAILQ_FOREACH(mdc2, &mdc->if_addrhead, ifa_link) { - if (mdc2->ifa_addr->sa_family == AF_INET6) { - fdm = (struct in6_ifaddr *)mdc2; - copia = fdm->ia_addr.sin6_addr; - /* need for leaving scope_id in the sock_addr */ - in6_clearscope(&copia); - if (IN6_ARE_ADDR_EQUAL(ip6_addr, &copia)) { - if_addr_runlock(mdc); - return 1; - } - } - } - if_addr_runlock(mdc); - } - return 0; -} - -static int -verify_path6(struct in6_addr *src, struct ifnet *ifp, u_int fib) -{ - struct route_in6 ro; - struct sockaddr_in6 *dst; - - bzero(&ro, sizeof(ro)); - - dst = (struct sockaddr_in6 * )&(ro.ro_dst); - dst->sin6_family = AF_INET6; - dst->sin6_len = sizeof(*dst); - dst->sin6_addr = *src; - - in6_rtalloc_ign(&ro, 0, fib); - if (ro.ro_rt == NULL) - return 0; - - /* - * if ifp is provided, check for equality with rtentry - * We should use rt->rt_ifa->ifa_ifp, instead of rt->rt_ifp, - * to support the case of sending packets to an address of our own. - * (where the former interface is the first argument of if_simloop() - * (=ifp), the latter is lo0) - */ - if (ifp != NULL && ro.ro_rt->rt_ifa->ifa_ifp != ifp) { - RTFREE(ro.ro_rt); - return 0; - } - - /* if no ifp provided, check if rtentry is not default route */ - if (ifp == NULL && - IN6_IS_ADDR_UNSPECIFIED(&satosin6(rt_key(ro.ro_rt))->sin6_addr)) { - RTFREE(ro.ro_rt); - return 0; - } - - /* or if this is a blackhole/reject route */ - if (ifp == NULL && ro.ro_rt->rt_flags & (RTF_REJECT|RTF_BLACKHOLE)) { - RTFREE(ro.ro_rt); - return 0; - } - - /* found valid route */ - RTFREE(ro.ro_rt); - return 1; - -} - -static int -is_icmp6_query(int icmp6_type) -{ - if ((icmp6_type <= ICMP6_MAXTYPE) && - (icmp6_type == ICMP6_ECHO_REQUEST || - icmp6_type == ICMP6_MEMBERSHIP_QUERY || - icmp6_type == ICMP6_WRUREQUEST || - icmp6_type == ICMP6_FQDN_QUERY || - icmp6_type == ICMP6_NI_QUERY)) - return (1); - - return (0); -} - -static void -send_reject6(struct ip_fw_args *args, int code, u_int hlen, struct ip6_hdr *ip6) -{ - struct mbuf *m; - - m = args->m; - if (code == ICMP6_UNREACH_RST && args->f_id.proto == IPPROTO_TCP) { - struct tcphdr *tcp; - tcp = (struct tcphdr *)((char *)ip6 + hlen); - - if ((tcp->th_flags & TH_RST) == 0) { - struct mbuf *m0; - m0 = ipfw_send_pkt(args->m, &(args->f_id), - ntohl(tcp->th_seq), ntohl(tcp->th_ack), - tcp->th_flags | TH_RST); - if (m0 != NULL) - ip6_output(m0, NULL, NULL, 0, NULL, NULL, - NULL); - } - FREE_PKT(m); - } else if (code != ICMP6_UNREACH_RST) { /* Send an ICMPv6 unreach. */ -#if 0 - /* - * Unlike above, the mbufs need to line up with the ip6 hdr, - * as the contents are read. We need to m_adj() the - * needed amount. - * The mbuf will however be thrown away so we can adjust it. - * Remember we did an m_pullup on it already so we - * can make some assumptions about contiguousness. - */ - if (args->L3offset) - m_adj(m, args->L3offset); -#endif - icmp6_error(m, ICMP6_DST_UNREACH, code, 0); - } else - FREE_PKT(m); - - args->m = NULL; -} - -#endif /* INET6 */ - - -/* - * sends a reject message, consuming the mbuf passed as an argument. - */ -static void -send_reject(struct ip_fw_args *args, int code, int iplen, struct ip *ip) -{ - -#if 0 - /* XXX When ip is not guaranteed to be at mtod() we will - * need to account for this */ - * The mbuf will however be thrown away so we can adjust it. - * Remember we did an m_pullup on it already so we - * can make some assumptions about contiguousness. - */ - if (args->L3offset) - m_adj(m, args->L3offset); -#endif - if (code != ICMP_REJECT_RST) { /* Send an ICMP unreach */ - icmp_error(args->m, ICMP_UNREACH, code, 0L, 0); - } else if (args->f_id.proto == IPPROTO_TCP) { - struct tcphdr *const tcp = - L3HDR(struct tcphdr, mtod(args->m, struct ip *)); - if ( (tcp->th_flags & TH_RST) == 0) { - struct mbuf *m; - m = ipfw_send_pkt(args->m, &(args->f_id), - ntohl(tcp->th_seq), ntohl(tcp->th_ack), - tcp->th_flags | TH_RST); - if (m != NULL) - ip_output(m, NULL, NULL, 0, NULL, NULL); - } - FREE_PKT(args->m); - } else - FREE_PKT(args->m); - args->m = NULL; -} - -/* - * Support for uid/gid/jail lookup. These tests are expensive - * (because we may need to look into the list of active sockets) - * so we cache the results. ugid_lookupp is 0 if we have not - * yet done a lookup, 1 if we succeeded, and -1 if we tried - * and failed. The function always returns the match value. - * We could actually spare the variable and use *uc, setting - * it to '(void *)check_uidgid if we have no info, NULL if - * we tried and failed, or any other value if successful. - */ -static int -check_uidgid(ipfw_insn_u32 *insn, struct ip_fw_args *args, int *ugid_lookupp, - struct ucred **uc) -{ -#if defined(USERSPACE) - return 0; // not supported in userspace -#else -#ifndef __FreeBSD__ - /* XXX */ - return cred_check(insn, proto, oif, - dst_ip, dst_port, src_ip, src_port, - (struct bsd_ucred *)uc, ugid_lookupp, ((struct mbuf *)inp)->m_skb); -#else /* FreeBSD */ - struct in_addr src_ip, dst_ip; - struct inpcbinfo *pi; - struct ipfw_flow_id *id; - struct inpcb *pcb, *inp; - struct ifnet *oif; - int lookupflags; - int match; - - id = &args->f_id; - inp = args->inp; - oif = args->oif; - - /* - * Check to see if the UDP or TCP stack supplied us with - * the PCB. If so, rather then holding a lock and looking - * up the PCB, we can use the one that was supplied. - */ - if (inp && *ugid_lookupp == 0) { - INP_LOCK_ASSERT(inp); - if (inp->inp_socket != NULL) { - *uc = crhold(inp->inp_cred); - *ugid_lookupp = 1; - } else - *ugid_lookupp = -1; - } - /* - * If we have already been here and the packet has no - * PCB entry associated with it, then we can safely - * assume that this is a no match. - */ - if (*ugid_lookupp == -1) - return (0); - if (id->proto == IPPROTO_TCP) { - lookupflags = 0; - pi = &V_tcbinfo; - } else if (id->proto == IPPROTO_UDP) { - lookupflags = INPLOOKUP_WILDCARD; - pi = &V_udbinfo; - } else - return 0; - lookupflags |= INPLOOKUP_RLOCKPCB; - match = 0; - if (*ugid_lookupp == 0) { - if (id->addr_type == 6) { -#ifdef INET6 - if (oif == NULL) - pcb = in6_pcblookup_mbuf(pi, - &id->src_ip6, htons(id->src_port), - &id->dst_ip6, htons(id->dst_port), - lookupflags, oif, args->m); - else - pcb = in6_pcblookup_mbuf(pi, - &id->dst_ip6, htons(id->dst_port), - &id->src_ip6, htons(id->src_port), - lookupflags, oif, args->m); -#else - *ugid_lookupp = -1; - return (0); -#endif - } else { - src_ip.s_addr = htonl(id->src_ip); - dst_ip.s_addr = htonl(id->dst_ip); - if (oif == NULL) - pcb = in_pcblookup_mbuf(pi, - src_ip, htons(id->src_port), - dst_ip, htons(id->dst_port), - lookupflags, oif, args->m); - else - pcb = in_pcblookup_mbuf(pi, - dst_ip, htons(id->dst_port), - src_ip, htons(id->src_port), - lookupflags, oif, args->m); - } - if (pcb != NULL) { - INP_RLOCK_ASSERT(pcb); - *uc = crhold(pcb->inp_cred); - *ugid_lookupp = 1; - INP_RUNLOCK(pcb); - } - if (*ugid_lookupp == 0) { - /* - * We tried and failed, set the variable to -1 - * so we will not try again on this packet. - */ - *ugid_lookupp = -1; - return (0); - } - } - if (insn->o.opcode == O_UID) - match = ((*uc)->cr_uid == (uid_t)insn->d[0]); - else if (insn->o.opcode == O_GID) - match = groupmember((gid_t)insn->d[0], *uc); - else if (insn->o.opcode == O_JAIL) - match = ((*uc)->cr_prison->pr_id == (int)insn->d[0]); - return (match); -#endif /* __FreeBSD__ */ -#endif /* not supported in userspace */ -} - -/* - * Helper function to set args with info on the rule after the matching - * one. slot is precise, whereas we guess rule_id as they are - * assigned sequentially. - */ -static inline void -set_match(struct ip_fw_args *args, int slot, - struct ip_fw_chain *chain) -{ - args->rule.chain_id = chain->id; - args->rule.slot = slot + 1; /* we use 0 as a marker */ - args->rule.rule_id = 1 + chain->map[slot]->id; - args->rule.rulenum = chain->map[slot]->rulenum; -} - -/* - * Helper function to enable cached rule lookups using - * x_next and next_rule fields in ipfw rule. - */ -static int -jump_fast(struct ip_fw_chain *chain, struct ip_fw *f, int num, - int tablearg, int jump_backwards) -{ - int f_pos; - - /* If possible use cached f_pos (in f->next_rule), - * whose version is written in f->next_rule - * (horrible hacks to avoid changing the ABI). - */ - if (num != IP_FW_TABLEARG && (uintptr_t)f->x_next == chain->id) - f_pos = (uintptr_t)f->next_rule; - else { - int i = IP_FW_ARG_TABLEARG(num); - /* make sure we do not jump backward */ - if (jump_backwards == 0 && i <= f->rulenum) - i = f->rulenum + 1; - f_pos = ipfw_find_rule(chain, i, 0); - /* update the cache */ - if (num != IP_FW_TABLEARG) { - f->next_rule = (void *)(uintptr_t)f_pos; - f->x_next = (void *)(uintptr_t)chain->id; - } - } - - return (f_pos); -} - /* * The main check routine for the firewall. * @@ -1339,15 +735,15 @@ case O_GID: case O_UID: case O_JAIL: - rule_jail(offset, proto, &cmd, args, ucred_lookup, ucred_cache); + rule_jail(&match, offset, proto, cmd, args, ucred_lookup, ucred_cache); break; case O_RECV: - rule_recv(&match, m, cmd, chain, &tablearg); + rule_recv(&match, cmd, m, chain, &tablearg); break; case O_XMIT: - rule_xmit(&match, oif, cmd, chain, &tableargs); + rule_xmit(&match, oif, cmd, chain, &tablearg); break; case O_VIA: @@ -1375,7 +771,7 @@ break; case O_DIVERTED: - rule_diverted(&match, args); + rule_diverted(&match, args, cmd); break; case O_PROTO: @@ -1383,25 +779,25 @@ break; case O_IP_SRC: - rule_src(&match, is_ipv4, cmd, src_ip); + rule_ip_src(&match, is_ipv4, cmd, &src_ip); break; case O_IP_SRC_LOOKUP: - case O_2_LOOKUP: - rule_2_lookup(&match, cmd, cmdlen, is_ipv4, is_ipv6, ip, dst_ip, src_ip, dst_port, src_port, offset, proto, ucred_lookup, ucred_cache, chain); + case O_IP_DST_LOOKUP: + rule_ip_dst_lookup(&match, cmd, cmdlen, args, &tablearg, is_ipv4, is_ipv6, ip, &dst_ip, &src_ip, dst_port, src_port, offset, proto, ucred_lookup, ucred_cache, chain); break; case O_IP_SRC_MASK: case O_IP_DST_MASK: - rule_ip_dst_mask(&match, is_ipv4, cmd, cmdlen, dst_ip, src_ip); + rule_ip_dst_mask(&match, is_ipv4, cmd, cmdlen, &dst_ip, &src_ip); break; case O_IP_SRC_ME: - rule_ip_sec_me(&match, src_ip, args); + rule_ip_src_me(&match, is_ipv4, is_ipv6, &src_ip, args); #ifdef INET6 /* FALLTHROUGH */ case O_IP6_SRC_ME: - rule_ip6_src_me(&match, is_ipv6, args) + rule_ip6_src_me(&match, is_ipv6, args); #endif break; @@ -1411,23 +807,23 @@ break; case O_IP_DST: - rule_ip_dst(&match, cmd, &dst_ip); + rule_ip_dst(&match, is_ipv4, cmd, &dst_ip); break; case O_IP_DST_ME: - rule_ip_dst_me(&match, is_ipv4, is_ipv6, dst_ip, dst_ip6); + rule_ip_dst_me(&match, args, is_ipv4, is_ipv6, &dst_ip); #ifdef INET6 /* FALLTHROUGH */ case O_IP6_DST_ME: - rule_ip6_dst_me(&match, args); + rule_ip6_dst_me(&match, args, is_ipv6); #endif break; case O_IP_SRCPORT: case O_IP_DSTPORT: - rule_ip_dstport(&match, proto, offset, cmd, cmdlen); + rule_ip_dstport(&match, proto, offset, cmd, cmdlen, dst_port, src_port); break; case O_ICMPTYPE: @@ -1436,7 +832,7 @@ #ifdef INET6 case O_ICMP6TYPE: - rule_icmp6type(&match, offset, proto, ulp, cmd); + rule_icmp6type(&match, offset, is_ipv6, proto, ulp, cmd); break; #endif /* INET6 */ @@ -1463,11 +859,11 @@ break; case O_DSCP: - rule_dscp(&match, is_ipv4, is_ipv6, cmd, ip) + rule_dscp(&match, is_ipv4, is_ipv6, cmd, ip); break; case O_TCPDATALEN: - rule_tcpdatalen(&match, proto, offset, ulp, iplen, cmdlen, cmd); + rule_tcpdatalen(&match, proto, offset, ulp, iplen, cmdlen, cmd, ip); break; case O_TCPFLAGS: @@ -1475,7 +871,8 @@ break; case O_TCPOPTS: - rule_tcpopts(&match, hlen, ulp, proto, offset, cmd); + if (rule_tcpopts(&match, hlen, ulp, proto, offset, cmd, m, args)) + goto pullup_failed; break; case O_TCPSEQ: @@ -1487,7 +884,7 @@ break; case O_TCPWIN: - rule_tcpwin(&match, proto, offset, cmd, ulp); + rule_tcpwin(&match, proto, offset, cmd, cmdlen, ulp); break; case O_ESTAB: @@ -1495,11 +892,11 @@ break; case O_ALTQ: - rule_altq(&match, cmd, m); + rule_altq(&match, cmd, m, ip); break; case O_LOG: - rule_log(&match, f, hlen, args, m, oif, offset, ip6f_mf, tablearg, ip) + rule_log(&match, f, hlen, args, m, oif, offset, ip6f_mf, tablearg, ip); break; case O_PROB: @@ -1507,15 +904,15 @@ break; case O_VERREVPATH: - rule_verrevpath(&match, oif, m, is_ipv6, args, scr_ip); + rule_verrevpath(&match, oif, m, is_ipv6, args, &src_ip); break; case O_VERSRCREACH: - rule_versrcreach(&match, hlen, oif, m, is_ipv6, args, scr_ip); + rule_versrcreach(&match, hlen, oif, is_ipv6, args, &src_ip); break; case O_ANTISPOOF: - rule_antispoof(&match, oif, hlen, is_ipv4, is_ipv6, src_ip, args, m); + rule_antispoof(&match, oif, hlen, is_ipv4, is_ipv6, &src_ip, args, m); break; case O_IPSEC: @@ -1527,7 +924,7 @@ #ifdef INET6 case O_IP6_SRC: - rule_ip6_src(&match, is_ipv6, args, cmd) + rule_ip6_src(&match, is_ipv6, args, cmd); break; case O_IP6_DST: @@ -1540,7 +937,7 @@ break; case O_FLOW6ID: - rule_flow6id(&match, args, cmd); + rule_flow6id(&match, is_ipv6, args, cmd); break; case O_EXT_HDR: @@ -1557,7 +954,7 @@ break; case O_TAG: - rule_tag(&match, cmd, m); + rule_tag(&match, cmd, m, tablearg); break; case O_FIB: /* try match the specified fib */ @@ -1565,11 +962,11 @@ break; case O_SOCKARG: - rule_sockarg(); + rule_sockarg(&match, is_ipv6, proto, &dst_ip, &src_ip, dst_port, src_port, args, &tablearg); break; case O_TAGGED: - rule_tagged(&match, cmd, cmdlen, m); + rule_tagged(&match, cmd, cmdlen, m, tablearg); break; /* @@ -1620,7 +1017,7 @@ case O_PROBE_STATE: case O_CHECK_STATE: - rule_check_state(&match, &dyn_dir, q, args, proto, ulp, pktlen, f, f_pos, chain, cmd, cmdlen, &l); + rule_check_state(&match, &dyn_dir, q, args, proto, ulp, pktlen, f, &f_pos, chain, cmd, &cmdlen, &l); break; case O_ACCEPT: @@ -1629,12 +1026,12 @@ case O_PIPE: case O_QUEUE: - rule_queue(args, f_pos, chain, cmd, &retval, &l, &done); + rule_queue(args, f_pos, chain, cmd, tablearg, &retval, &l, &done); break; case O_DIVERT: case O_TEE: - rule_tee(&l, &done, &retval, cmd, args, f_pos, chain); + rule_tee(&l, &done, &retval, cmd, args, f_pos, tablearg, chain); break; case O_COUNT: @@ -1642,7 +1039,7 @@ break; case O_SKIPTO: - rule_skipto(&match, &l, &cmd, &skip_or, &f_pos, f, pktlen, chain, cmd, tablearg); + rule_skipto(&match, &l, cmd, &cmdlen, &skip_or, &f_pos, f, pktlen, chain, tablearg); continue; break; /* NOTREACHED */ @@ -1652,11 +1049,11 @@ break; /* NOTREACHED */ case O_REJECT: - rule_reject(hlen, is_ipv4, offset, proto, ulp, m, dst_ip, args, cmd, iplen, ip); + rule_reject(hlen, is_ipv4, offset, proto, ulp, m, &dst_ip, args, cmd, iplen, ip); /* FALLTHROUGH */ #ifdef INET6 case O_UNREACH6: - rule_unreach6(hlen, is_ipv4, offset, proto, icmp6_type, m, args, cmd, ip); + rule_unreach6(hlen, is_ipv6, offset, proto, icmp6_type, m, args, cmd, ip); /* FALLTHROUGH */ #endif case O_DENY: @@ -1664,34 +1061,34 @@ break; case O_FORWARD_IP: - rule_forward_ip(args, q, dyn_dir, cmd, sa, &retval, &l, &done); + rule_forward_ip(args, q, f, dyn_dir, cmd, tablearg, &retval, &l, &done); break; #ifdef INET6 case O_FORWARD_IP6: - rule_forward_ip6(args, q, f, cmd, &retval, &l, &done); + rule_forward_ip6(args, q, f, dyn_dir, cmd, &retval, &l, &done); break; #endif case O_NETGRAPH: case O_NGTEE: - rule_ngtee(args, f_pos, chain, cmd, &retval, &l, &done); + rule_ngtee(args, f_pos, chain, cmd, tablearg, &retval, &l, &done); break; case O_SETFIB: - rule_setfib(f, pkglen, cmd, rt_numfibs, m, args, &l); + rule_setfib(f, pktlen, tablearg, cmd, m, args, &l); break; case O_SETDSCP: - rule_setdscp(cmd,); + rule_setdscp(cmd, ip, is_ipv4, is_ipv6, tablearg, f, pktlen, &l); break; case O_NAT: - rule_nat(args, f_pos, chain, cmd, &retval, &done, &l); + rule_nat(args, f_pos, chain, cmd, m, tablearg, &retval, &done, &l); break; case O_REASS: - rule_reass(f, pktlen, ip, args, m, &retval, &done, &l); + rule_reass(f, f_pos, chain, pktlen, ip, args, m, &retval, &done, &l); break; default: Modified: soc2014/dpl/netmap-ipfw/sys/netpfil/ipfw/ip_fw_rules.h ============================================================================== --- soc2014/dpl/netmap-ipfw/sys/netpfil/ipfw/ip_fw_rules.h Wed Jun 25 16:12:14 2014 (r270026) +++ soc2014/dpl/netmap-ipfw/sys/netpfil/ipfw/ip_fw_rules.h Wed Jun 25 17:13:04 2014 (r270027) @@ -1,3 +1,700 @@ +/* Includes XXX */ +#include <sys/cdefs.h> +__FBSDID("$FreeBSD: head/sys/netpfil/ipfw/ip_fw2.c 243711 2012-11-30 19:36:55Z melifaro $"); + +/* + * The FreeBSD IP packet firewall, main file + */ + +#include "opt_ipfw.h" +#include "opt_ipdivert.h" +#include "opt_inet.h" +#ifndef INET +#error "IPFIREWALL requires INET" +#endif /* INET */ +#include "opt_inet6.h" +#include "opt_ipsec.h" + +#include <sys/param.h> +#include <sys/systm.h> +#include <sys/condvar.h> +#include <sys/eventhandler.h> +#include <sys/malloc.h> +#include <sys/mbuf.h> +#include <sys/kernel.h> +#include <sys/lock.h> +#include <sys/jail.h> +#include <sys/module.h> +#include <sys/priv.h> +#include <sys/proc.h> +#include <sys/rwlock.h> +#include <sys/socket.h> +#include <sys/socketvar.h> +#include <sys/sysctl.h> +#include <sys/syslog.h> +#include <sys/ucred.h> +#include <net/ethernet.h> /* for ETHERTYPE_IP */ +#include <net/if.h> +#include <net/if_var.h> +#include <net/route.h> +#include <net/pfil.h> +#include <net/vnet.h> + +#include <netpfil/pf/pf_mtag.h> + +#include <netinet/in.h> +#include <netinet/in_var.h> +#include <netinet/in_pcb.h> +#include <netinet/ip.h> +#include <netinet/ip_var.h> +#include <netinet/ip_icmp.h> +#include <netinet/ip_fw.h> +#include <netinet/ip_carp.h> +#include <netinet/pim.h> +#include <netinet/tcp_var.h> +#include <netinet/udp.h> +#include <netinet/udp_var.h> +#include <netinet/sctp.h> + +#include <netinet/ip6.h> +#include <netinet/icmp6.h> +#ifdef INET6 +#include <netinet6/in6_pcb.h> +#include <netinet6/scope6_var.h> +#include <netinet6/ip6_var.h> +#endif + +#include <netpfil/ipfw/ip_fw_private.h> + +#include <machine/in_cksum.h> /* XXX for in_cksum */ + +#ifdef MAC +#include <security/mac/mac_framework.h> +#endif + +/* + * Some macros used in the various matching options. + * L3HDR maps an ipv4 pointer into a layer3 header pointer of type T + * Other macros just cast void * into the appropriate type + */ +#define L3HDR(T, ip) ((T *)((u_int32_t *)(ip) + (ip)->ip_hl)) +#define TCP(p) ((struct tcphdr *)(p)) +#define SCTP(p) ((struct sctphdr *)(p)) +#define UDP(p) ((struct udphdr *)(p)) +#define ICMP(p) ((struct icmphdr *)(p)) +#define ICMP6(p) ((struct icmp6_hdr *)(p)) + +/* This macro needs the calling function to have a tablearg argument */ +#define IP_FW_ARG_TABLEARG(a) (((a) == IP_FW_TABLEARG) ? tablearg : (a)) + +/* + * Auxiliar functions. *** DIFF OUTPUT TRUNCATED AT 1000 LINES ***
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201406251713.s5PHD5l3087329>