1c398230bSWarner Losh /*- 24d846d26SWarner Losh * SPDX-License-Identifier: BSD-2-Clause 3fe267a55SPedro F. Giffuni * 4b87ce554SLuigi Rizzo * Copyright (c) 2002-2009 Luigi Rizzo, Universita` di Pisa 5100ba1a6SJordan K. Hubbard * 69758b77fSLuigi Rizzo * Redistribution and use in source and binary forms, with or without 79758b77fSLuigi Rizzo * modification, are permitted provided that the following conditions 89758b77fSLuigi Rizzo * are met: 99758b77fSLuigi Rizzo * 1. Redistributions of source code must retain the above copyright 109758b77fSLuigi Rizzo * notice, this list of conditions and the following disclaimer. 119758b77fSLuigi Rizzo * 2. Redistributions in binary form must reproduce the above copyright 129758b77fSLuigi Rizzo * notice, this list of conditions and the following disclaimer in the 139758b77fSLuigi Rizzo * documentation and/or other materials provided with the distribution. 14100ba1a6SJordan K. Hubbard * 159758b77fSLuigi Rizzo * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 169758b77fSLuigi Rizzo * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 179758b77fSLuigi Rizzo * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 189758b77fSLuigi Rizzo * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 199758b77fSLuigi Rizzo * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 209758b77fSLuigi Rizzo * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 219758b77fSLuigi Rizzo * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 229758b77fSLuigi Rizzo * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 239758b77fSLuigi Rizzo * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 249758b77fSLuigi Rizzo * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 259758b77fSLuigi Rizzo * SUCH DAMAGE. 26100ba1a6SJordan K. Hubbard */ 27100ba1a6SJordan K. Hubbard 289758b77fSLuigi Rizzo #ifndef _IPFW2_H 299758b77fSLuigi Rizzo #define _IPFW2_H 309b932e9eSAndre Oppermann 31e4676ba6SJulian Elischer /* 32eb29d14cSRoman Kurakin * The default rule number. By the design of ip_fw, the default rule 33eb29d14cSRoman Kurakin * is the last one, so its number can also serve as the highest number 34eb29d14cSRoman Kurakin * allowed for a rule. The ip_fw code relies on both meanings of this 35eb29d14cSRoman Kurakin * constant. 368191aa7cSRoman Kurakin */ 378191aa7cSRoman Kurakin #define IPFW_DEFAULT_RULE 65535 388191aa7cSRoman Kurakin 397e767c79SAlexander V. Chernikov #define RESVD_SET 31 /*set for default and persistent rules*/ 407e767c79SAlexander V. Chernikov #define IPFW_MAX_SETS 32 /* Number of sets supported by ipfw*/ 41b074b7bbSAlexander V. Chernikov 42b074b7bbSAlexander V. Chernikov /* 4374b22066SAlexander V. Chernikov * Compat values for old clients 44f7b5554eSRoman Kurakin */ 4574b22066SAlexander V. Chernikov #ifndef _KERNEL 46732d27b3SAlexander V. Chernikov #define IPFW_TABLES_MAX 65535 47732d27b3SAlexander V. Chernikov #define IPFW_TABLES_DEFAULT 128 4874b22066SAlexander V. Chernikov #endif 49f7b5554eSRoman Kurakin 50f7b5554eSRoman Kurakin /* 51b87ce554SLuigi Rizzo * Most commands (queue, pipe, tag, untag, limit...) can have a 16-bit 521940fa77SAlexander V. Chernikov * argument between 1 and 65534. The value 0 (IP_FW_TARG) is used 531940fa77SAlexander V. Chernikov * to represent 'tablearg' value, e.g. indicate the use of a 'tablearg' 54b87ce554SLuigi Rizzo * result of the most recent table() lookup. 55b87ce554SLuigi Rizzo * Note that 16bit is only a historical limit, resulting from 56b87ce554SLuigi Rizzo * the use of a 16-bit fields for that value. In reality, we can have 571940fa77SAlexander V. Chernikov * 2^32 pipes, queues, tag values and so on. 58b87ce554SLuigi Rizzo */ 59b87ce554SLuigi Rizzo #define IPFW_ARG_MIN 1 60b87ce554SLuigi Rizzo #define IPFW_ARG_MAX 65534 611940fa77SAlexander V. Chernikov #define IP_FW_TABLEARG 65535 /* Compat value for old clients */ 621940fa77SAlexander V. Chernikov #define IP_FW_TARG 0 /* Current tablearg value */ 63d6eb9b02SAndrey V. Elsukov #define IP_FW_NAT44_GLOBAL 65535 /* arg1 value for "nat global" */ 64b87ce554SLuigi Rizzo 65b87ce554SLuigi Rizzo /* 669527ec6eSAndrey V. Elsukov * Number of entries in the call stack of the call/return commands. 679527ec6eSAndrey V. Elsukov * Call stack currently is an uint16_t array with rule numbers. 689527ec6eSAndrey V. Elsukov */ 699527ec6eSAndrey V. Elsukov #define IPFW_CALLSTACK_SIZE 16 709527ec6eSAndrey V. Elsukov 71f8bee51aSAlexander V. Chernikov /* IP_FW3 header/opcodes */ 72f8bee51aSAlexander V. Chernikov typedef struct _ip_fw3_opheader { 73f8bee51aSAlexander V. Chernikov uint16_t opcode; /* Operation opcode */ 74d3a4f924SAlexander V. Chernikov uint16_t version; /* Opcode version */ 75d3a4f924SAlexander V. Chernikov uint16_t reserved[2]; /* Align to 64-bit boundary */ 76f8bee51aSAlexander V. Chernikov } ip_fw3_opheader; 77f8bee51aSAlexander V. Chernikov 7818ad4197SAlexander V. Chernikov /* IP_FW3 opcodes */ 79f8bee51aSAlexander V. Chernikov #define IP_FW_TABLE_XADD 86 /* add entry */ 80f8bee51aSAlexander V. Chernikov #define IP_FW_TABLE_XDEL 87 /* delete entry */ 81d3a4f924SAlexander V. Chernikov #define IP_FW_TABLE_XGETSIZE 88 /* get table size (deprecated) */ 82f8bee51aSAlexander V. Chernikov #define IP_FW_TABLE_XLIST 89 /* list table contents */ 83d3a4f924SAlexander V. Chernikov #define IP_FW_TABLE_XDESTROY 90 /* destroy table */ 849490a627SAlexander V. Chernikov #define IP_FW_TABLES_XLIST 92 /* list all tables */ 859490a627SAlexander V. Chernikov #define IP_FW_TABLE_XINFO 93 /* request info for one table */ 869490a627SAlexander V. Chernikov #define IP_FW_TABLE_XFLUSH 94 /* flush table data */ 879490a627SAlexander V. Chernikov #define IP_FW_TABLE_XCREATE 95 /* create new table */ 88adf3b2b9SAlexander V. Chernikov #define IP_FW_TABLE_XMODIFY 96 /* modify existing table */ 89563b5ab1SAlexander V. Chernikov #define IP_FW_XGET 97 /* Retrieve configuration */ 90a73d728dSAlexander V. Chernikov #define IP_FW_XADD 98 /* add rule */ 91a73d728dSAlexander V. Chernikov #define IP_FW_XDEL 99 /* del rule */ 92a73d728dSAlexander V. Chernikov #define IP_FW_XMOVE 100 /* move rules to different set */ 93a73d728dSAlexander V. Chernikov #define IP_FW_XZERO 101 /* clear accounting */ 94a73d728dSAlexander V. Chernikov #define IP_FW_XRESETLOG 102 /* zero rules logs */ 95a73d728dSAlexander V. Chernikov #define IP_FW_SET_SWAP 103 /* Swap between 2 sets */ 96a73d728dSAlexander V. Chernikov #define IP_FW_SET_MOVE 104 /* Move one set to another one */ 97a73d728dSAlexander V. Chernikov #define IP_FW_SET_ENABLE 105 /* Enable/disable sets */ 98a73d728dSAlexander V. Chernikov #define IP_FW_TABLE_XFIND 106 /* finds an entry */ 99a73d728dSAlexander V. Chernikov #define IP_FW_XIFLIST 107 /* list tracked interfaces */ 100a73d728dSAlexander V. Chernikov #define IP_FW_TABLES_ALIST 108 /* list table algorithms */ 101a73d728dSAlexander V. Chernikov #define IP_FW_TABLE_XSWAP 109 /* swap two tables */ 1020cba2b28SAlexander V. Chernikov #define IP_FW_TABLE_VLIST 110 /* dump table value hash */ 103d3a4f924SAlexander V. Chernikov 104d6164b77SAlexander V. Chernikov #define IP_FW_NAT44_XCONFIG 111 /* Create/modify NAT44 instance */ 105d6164b77SAlexander V. Chernikov #define IP_FW_NAT44_DESTROY 112 /* Destroys NAT44 instance */ 106d6164b77SAlexander V. Chernikov #define IP_FW_NAT44_XGETCONFIG 113 /* Get NAT44 instance config */ 107d6164b77SAlexander V. Chernikov #define IP_FW_NAT44_LIST_NAT 114 /* List all NAT44 instances */ 108d6164b77SAlexander V. Chernikov #define IP_FW_NAT44_XGETLOG 115 /* Get log from NAT44 instance */ 109d6164b77SAlexander V. Chernikov 110be8bc457SAlexander V. Chernikov #define IP_FW_DUMP_SOPTCODES 116 /* Dump available sopts/versions */ 1115dc5a0e0SAndrey V. Elsukov #define IP_FW_DUMP_SRVOBJECTS 117 /* Dump existing named objects */ 112be8bc457SAlexander V. Chernikov 113d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64STL_CREATE 130 /* Create stateless NAT64 instance */ 114d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64STL_DESTROY 131 /* Destroy stateless NAT64 instance */ 115d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64STL_CONFIG 132 /* Modify stateless NAT64 instance */ 116d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64STL_LIST 133 /* List stateless NAT64 instances */ 117d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64STL_STATS 134 /* Get NAT64STL instance statistics */ 118d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64STL_RESET_STATS 135 /* Reset NAT64STL instance statistics */ 119d8caf56eSAndrey V. Elsukov 120d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64LSN_CREATE 140 /* Create stateful NAT64 instance */ 121d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64LSN_DESTROY 141 /* Destroy stateful NAT64 instance */ 122d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64LSN_CONFIG 142 /* Modify stateful NAT64 instance */ 123d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64LSN_LIST 143 /* List stateful NAT64 instances */ 124d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64LSN_STATS 144 /* Get NAT64LSN instance statistics */ 125d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64LSN_LIST_STATES 145 /* Get stateful NAT64 states */ 126d8caf56eSAndrey V. Elsukov #define IP_FW_NAT64LSN_RESET_STATS 146 /* Reset NAT64LSN instance statistics */ 127d8caf56eSAndrey V. Elsukov 128b867e84eSAndrey V. Elsukov #define IP_FW_NPTV6_CREATE 150 /* Create NPTv6 instance */ 129b867e84eSAndrey V. Elsukov #define IP_FW_NPTV6_DESTROY 151 /* Destroy NPTv6 instance */ 130b867e84eSAndrey V. Elsukov #define IP_FW_NPTV6_CONFIG 152 /* Modify NPTv6 instance */ 131b867e84eSAndrey V. Elsukov #define IP_FW_NPTV6_LIST 153 /* List NPTv6 instances */ 132b867e84eSAndrey V. Elsukov #define IP_FW_NPTV6_STATS 154 /* Get NPTv6 instance statistics */ 13357fb3b7aSAndrey V. Elsukov #define IP_FW_NPTV6_RESET_STATS 155 /* Reset NPTv6 instance statistics */ 134b867e84eSAndrey V. Elsukov 1355c04f73eSAndrey V. Elsukov #define IP_FW_NAT64CLAT_CREATE 160 /* Create clat NAT64 instance */ 1365c04f73eSAndrey V. Elsukov #define IP_FW_NAT64CLAT_DESTROY 161 /* Destroy clat NAT64 instance */ 1375c04f73eSAndrey V. Elsukov #define IP_FW_NAT64CLAT_CONFIG 162 /* Modify clat NAT64 instance */ 1385c04f73eSAndrey V. Elsukov #define IP_FW_NAT64CLAT_LIST 163 /* List clat NAT64 instances */ 1395c04f73eSAndrey V. Elsukov #define IP_FW_NAT64CLAT_STATS 164 /* Get NAT64CLAT instance statistics */ 1405c04f73eSAndrey V. Elsukov #define IP_FW_NAT64CLAT_RESET_STATS 165 /* Reset NAT64CLAT instance statistics */ 1415c04f73eSAndrey V. Elsukov 142d3a4f924SAlexander V. Chernikov /* 1439758b77fSLuigi Rizzo * The kernel representation of ipfw rules is made of a list of 1449758b77fSLuigi Rizzo * 'instructions' (for all practical purposes equivalent to BPF 1459758b77fSLuigi Rizzo * instructions), which specify which fields of the packet 146330462a3SBernd Walter * (or its metadata) should be analysed. 147e4676ba6SJulian Elischer * 1489758b77fSLuigi Rizzo * Each instruction is stored in a structure which begins with 1499758b77fSLuigi Rizzo * "ipfw_insn", and can contain extra fields depending on the 1509758b77fSLuigi Rizzo * instruction type (listed below). 151330462a3SBernd Walter * Note that the code is written so that individual instructions 152330462a3SBernd Walter * have a size which is a multiple of 32 bits. This means that, if 153330462a3SBernd Walter * such structures contain pointers or other 64-bit entities, 154330462a3SBernd Walter * (there is just one instance now) they may end up unaligned on 155330462a3SBernd Walter * 64-bit architectures, so the must be handled with care. 1569758b77fSLuigi Rizzo * 1579758b77fSLuigi Rizzo * "enum ipfw_opcodes" are the opcodes supported. We can have up 15831c88a30SChristian S.J. Peron * to 256 different opcodes. When adding new opcodes, they should 15931c88a30SChristian S.J. Peron * be appended to the end of the opcode list before O_LAST_OPCODE, 16031c88a30SChristian S.J. Peron * this will prevent the ABI from being broken, otherwise users 16131c88a30SChristian S.J. Peron * will have to recompile ipfw(8) when they update the kernel. 162e4676ba6SJulian Elischer */ 163e4676ba6SJulian Elischer 1649758b77fSLuigi Rizzo enum ipfw_opcodes { /* arguments (4 byte each) */ 1659758b77fSLuigi Rizzo O_NOP, 1669758b77fSLuigi Rizzo 1679758b77fSLuigi Rizzo O_IP_SRC, /* u32 = IP */ 1689758b77fSLuigi Rizzo O_IP_SRC_MASK, /* ip = IP/mask */ 1699758b77fSLuigi Rizzo O_IP_SRC_ME, /* none */ 1709758b77fSLuigi Rizzo O_IP_SRC_SET, /* u32=base, arg1=len, bitmap */ 1719758b77fSLuigi Rizzo 1729758b77fSLuigi Rizzo O_IP_DST, /* u32 = IP */ 1739758b77fSLuigi Rizzo O_IP_DST_MASK, /* ip = IP/mask */ 1749758b77fSLuigi Rizzo O_IP_DST_ME, /* none */ 1759758b77fSLuigi Rizzo O_IP_DST_SET, /* u32=base, arg1=len, bitmap */ 1769758b77fSLuigi Rizzo 1779758b77fSLuigi Rizzo O_IP_SRCPORT, /* (n)port list:mask 4 byte ea */ 1789758b77fSLuigi Rizzo O_IP_DSTPORT, /* (n)port list:mask 4 byte ea */ 1799758b77fSLuigi Rizzo O_PROTO, /* arg1=protocol */ 1809758b77fSLuigi Rizzo 1819758b77fSLuigi Rizzo O_MACADDR2, /* 2 mac addr:mask */ 1829758b77fSLuigi Rizzo O_MAC_TYPE, /* same as srcport */ 1839758b77fSLuigi Rizzo 1849758b77fSLuigi Rizzo O_LAYER2, /* none */ 1859758b77fSLuigi Rizzo O_IN, /* none */ 1869758b77fSLuigi Rizzo O_FRAG, /* none */ 1879758b77fSLuigi Rizzo 1889758b77fSLuigi Rizzo O_RECV, /* none */ 1899758b77fSLuigi Rizzo O_XMIT, /* none */ 1909758b77fSLuigi Rizzo O_VIA, /* none */ 1919758b77fSLuigi Rizzo 1929758b77fSLuigi Rizzo O_IPOPT, /* arg1 = 2*u8 bitmap */ 1939758b77fSLuigi Rizzo O_IPLEN, /* arg1 = len */ 1949758b77fSLuigi Rizzo O_IPID, /* arg1 = id */ 1959758b77fSLuigi Rizzo 1969758b77fSLuigi Rizzo O_IPTOS, /* arg1 = id */ 1975e43aef8SLuigi Rizzo O_IPPRECEDENCE, /* arg1 = precedence << 5 */ 1989758b77fSLuigi Rizzo O_IPTTL, /* arg1 = TTL */ 1999758b77fSLuigi Rizzo 2009758b77fSLuigi Rizzo O_IPVER, /* arg1 = version */ 2019758b77fSLuigi Rizzo O_UID, /* u32 = id */ 2029758b77fSLuigi Rizzo O_GID, /* u32 = id */ 2039758b77fSLuigi Rizzo O_ESTAB, /* none (tcp established) */ 2049758b77fSLuigi Rizzo O_TCPFLAGS, /* arg1 = 2*u8 bitmap */ 2059758b77fSLuigi Rizzo O_TCPWIN, /* arg1 = desired win */ 2069758b77fSLuigi Rizzo O_TCPSEQ, /* u32 = desired seq. */ 2079758b77fSLuigi Rizzo O_TCPACK, /* u32 = desired seq. */ 2089758b77fSLuigi Rizzo O_ICMPTYPE, /* u32 = icmp bitmap */ 2099758b77fSLuigi Rizzo O_TCPOPTS, /* arg1 = 2*u8 bitmap */ 2109758b77fSLuigi Rizzo 211010dabb0SCrist J. Clark O_VERREVPATH, /* none */ 21222b5770bSAndre Oppermann O_VERSRCREACH, /* none */ 213010dabb0SCrist J. Clark 2149758b77fSLuigi Rizzo O_PROBE_STATE, /* none */ 2159758b77fSLuigi Rizzo O_KEEP_STATE, /* none */ 2169758b77fSLuigi Rizzo O_LIMIT, /* ipfw_insn_limit */ 2179758b77fSLuigi Rizzo O_LIMIT_PARENT, /* dyn_type, not an opcode. */ 218f030c151SLuigi Rizzo 2199758b77fSLuigi Rizzo /* 220f030c151SLuigi Rizzo * These are really 'actions'. 2219758b77fSLuigi Rizzo */ 2229758b77fSLuigi Rizzo 2239758b77fSLuigi Rizzo O_LOG, /* ipfw_insn_log */ 2249758b77fSLuigi Rizzo O_PROB, /* u32 = match probability */ 2259758b77fSLuigi Rizzo 2269758b77fSLuigi Rizzo O_CHECK_STATE, /* none */ 2279758b77fSLuigi Rizzo O_ACCEPT, /* none */ 2289758b77fSLuigi Rizzo O_DENY, /* none */ 2299758b77fSLuigi Rizzo O_REJECT, /* arg1=icmp arg (same as deny) */ 2309758b77fSLuigi Rizzo O_COUNT, /* none */ 2319758b77fSLuigi Rizzo O_SKIPTO, /* arg1=next rule number */ 2329758b77fSLuigi Rizzo O_PIPE, /* arg1=pipe number */ 2339758b77fSLuigi Rizzo O_QUEUE, /* arg1=queue number */ 2349758b77fSLuigi Rizzo O_DIVERT, /* arg1=port number */ 2359758b77fSLuigi Rizzo O_TEE, /* arg1=port number */ 2369758b77fSLuigi Rizzo O_FORWARD_IP, /* fwd sockaddr */ 2379758b77fSLuigi Rizzo O_FORWARD_MAC, /* fwd mac */ 238ff2f6fe8SPaolo Pisati O_NAT, /* nope */ 239eb2e4119SPaolo Pisati O_REASS, /* none */ 240f030c151SLuigi Rizzo 241f030c151SLuigi Rizzo /* 242f030c151SLuigi Rizzo * More opcodes. 243f030c151SLuigi Rizzo */ 244f030c151SLuigi Rizzo O_IPSEC, /* has ipsec history */ 245cd8b5ae0SRuslan Ermilov O_IP_SRC_LOOKUP, /* arg1=table number, u32=value */ 246cd8b5ae0SRuslan Ermilov O_IP_DST_LOOKUP, /* arg1=table number, u32=value */ 2475af87d0eSDavid E. O'Brien O_ANTISPOOF, /* none */ 24831c88a30SChristian S.J. Peron O_JAIL, /* u32 = id */ 249974dfe30SBrian Feldman O_ALTQ, /* u32 = altq classif. qid */ 2506daf7ebdSBrian Feldman O_DIVERTED, /* arg1=bitmap (1:loop, 2:out) */ 251c99ee9e0SBrian Feldman O_TCPDATALEN, /* arg1 = tcp data len */ 2528195404bSBrooks Davis O_IP6_SRC, /* address without mask */ 2538195404bSBrooks Davis O_IP6_SRC_ME, /* my addresses */ 2548195404bSBrooks Davis O_IP6_SRC_MASK, /* address with the mask */ 2558195404bSBrooks Davis O_IP6_DST, 2568195404bSBrooks Davis O_IP6_DST_ME, 2578195404bSBrooks Davis O_IP6_DST_MASK, 2588195404bSBrooks Davis O_FLOW6ID, /* for flow id tag in the ipv6 pkt */ 2598195404bSBrooks Davis O_ICMP6TYPE, /* icmp6 packet type filtering */ 2608195404bSBrooks Davis O_EXT_HDR, /* filtering for ipv6 extension header */ 2618195404bSBrooks Davis O_IP6, 262f030c151SLuigi Rizzo 263670742a1SGleb Smirnoff /* 264670742a1SGleb Smirnoff * actions for ng_ipfw 265670742a1SGleb Smirnoff */ 266670742a1SGleb Smirnoff O_NETGRAPH, /* send to ng_ipfw */ 267670742a1SGleb Smirnoff O_NGTEE, /* copy to ng_ipfw */ 268670742a1SGleb Smirnoff 26957cd6d26SMax Laier O_IP4, 27057cd6d26SMax Laier 2719066356bSBjoern A. Zeeb O_UNREACH6, /* arg1=icmpv6 code arg (deny) */ 2729066356bSBjoern A. Zeeb 2736a7d5cb6SOleg Bulyzhin O_TAG, /* arg1=tag number */ 2746a7d5cb6SOleg Bulyzhin O_TAGGED, /* arg1=tag number */ 2756a7d5cb6SOleg Bulyzhin 2768b07e49aSJulian Elischer O_SETFIB, /* arg1=FIB number */ 2778b07e49aSJulian Elischer O_FIB, /* arg1=FIB desired fib number */ 2788b07e49aSJulian Elischer 279ae99fd0eSLuigi Rizzo O_SOCKARG, /* socket argument */ 280ae99fd0eSLuigi Rizzo 2819527ec6eSAndrey V. Elsukov O_CALLRETURN, /* arg1=called rule number */ 2829527ec6eSAndrey V. Elsukov 2838a006adbSBjoern A. Zeeb O_FORWARD_IP6, /* fwd sockaddr_in6 */ 2848a006adbSBjoern A. Zeeb 285ae01d73cSAlexander V. Chernikov O_DSCP, /* 2 u32 = DSCP mask */ 286ae01d73cSAlexander V. Chernikov O_SETDSCP, /* arg1=DSCP value */ 287914bffb6SAlexander V. Chernikov O_IP_FLOW_LOOKUP, /* arg1=table number, u32=value */ 288ae01d73cSAlexander V. Chernikov 2892acdf79fSAndrey V. Elsukov O_EXTERNAL_ACTION, /* arg1=id of external action handler */ 2902acdf79fSAndrey V. Elsukov O_EXTERNAL_INSTANCE, /* arg1=id of eaction handler instance */ 29111c56650SAndrey V. Elsukov O_EXTERNAL_DATA, /* variable length data */ 2922acdf79fSAndrey V. Elsukov 293f7c4fdeeSAndrey V. Elsukov O_SKIP_ACTION, /* none */ 294978f2d17SAndrey V. Elsukov O_TCPMSS, /* arg1=MSS value */ 295f7c4fdeeSAndrey V. Elsukov 29681cac390SArseny Smalyuk O_MAC_SRC_LOOKUP, /* arg1=table number, u32=value */ 29781cac390SArseny Smalyuk O_MAC_DST_LOOKUP, /* arg1=table number, u32=value */ 29881cac390SArseny Smalyuk 299fc727ad6SBoris Lytochkin O_SETMARK, /* u32 = value */ 300fc727ad6SBoris Lytochkin O_MARK, /* 2 u32 = value, bitmask */ 301fc727ad6SBoris Lytochkin 3029758b77fSLuigi Rizzo O_LAST_OPCODE /* not an opcode! */ 303e4676ba6SJulian Elischer }; 304e4676ba6SJulian Elischer 305100ba1a6SJordan K. Hubbard /* 30681cac390SArseny Smalyuk * Defines key types used by lookup instruction 30781cac390SArseny Smalyuk */ 30881cac390SArseny Smalyuk enum ipfw_table_lookup_type { 30981cac390SArseny Smalyuk LOOKUP_DST_IP, 31081cac390SArseny Smalyuk LOOKUP_SRC_IP, 31181cac390SArseny Smalyuk LOOKUP_DST_PORT, 31281cac390SArseny Smalyuk LOOKUP_SRC_PORT, 31381cac390SArseny Smalyuk LOOKUP_UID, 31481cac390SArseny Smalyuk LOOKUP_JAIL, 31581cac390SArseny Smalyuk LOOKUP_DSCP, 31681cac390SArseny Smalyuk LOOKUP_DST_MAC, 31781cac390SArseny Smalyuk LOOKUP_SRC_MAC, 318fc727ad6SBoris Lytochkin LOOKUP_MARK, 31981cac390SArseny Smalyuk }; 32081cac390SArseny Smalyuk 32181cac390SArseny Smalyuk /* 3228195404bSBrooks Davis * The extension header are filtered only for presence using a bit 3238195404bSBrooks Davis * vector with a flag for each header. 3248195404bSBrooks Davis */ 3258195404bSBrooks Davis #define EXT_FRAGMENT 0x1 3268195404bSBrooks Davis #define EXT_HOPOPTS 0x2 3278195404bSBrooks Davis #define EXT_ROUTING 0x4 3288195404bSBrooks Davis #define EXT_AH 0x8 3298195404bSBrooks Davis #define EXT_ESP 0x10 3309066356bSBjoern A. Zeeb #define EXT_DSTOPTS 0x20 3317a92401aSBjoern A. Zeeb #define EXT_RTHDR0 0x40 3327a92401aSBjoern A. Zeeb #define EXT_RTHDR2 0x80 3338195404bSBrooks Davis 3348195404bSBrooks Davis /* 3359758b77fSLuigi Rizzo * Template for instructions. 336100ba1a6SJordan K. Hubbard * 3379758b77fSLuigi Rizzo * ipfw_insn is used for all instructions which require no operands, 3389758b77fSLuigi Rizzo * a single 16-bit value (arg1), or a couple of 8-bit values. 3399758b77fSLuigi Rizzo * 3409758b77fSLuigi Rizzo * For other instructions which require different/larger arguments 3419758b77fSLuigi Rizzo * we have derived structures, ipfw_insn_*. 3429758b77fSLuigi Rizzo * 3439758b77fSLuigi Rizzo * The size of the instruction (in 32-bit words) is in the low 3449758b77fSLuigi Rizzo * 6 bits of "len". The 2 remaining bits are used to implement 3459758b77fSLuigi Rizzo * NOT and OR on individual instructions. Given a type, you can 3469758b77fSLuigi Rizzo * compute the length to be put in "len" using F_INSN_SIZE(t) 3479758b77fSLuigi Rizzo * 3489758b77fSLuigi Rizzo * F_NOT negates the match result of the instruction. 3499758b77fSLuigi Rizzo * 3509758b77fSLuigi Rizzo * F_OR is used to build or blocks. By default, instructions 3519758b77fSLuigi Rizzo * are evaluated as part of a logical AND. An "or" block 3529758b77fSLuigi Rizzo * { X or Y or Z } contains F_OR set in all but the last 3539758b77fSLuigi Rizzo * instruction of the block. A match will cause the code 3549758b77fSLuigi Rizzo * to skip past the last instruction of the block. 3559758b77fSLuigi Rizzo * 3569758b77fSLuigi Rizzo * NOTA BENE: in a couple of places we assume that 3579758b77fSLuigi Rizzo * sizeof(ipfw_insn) == sizeof(u_int32_t) 3589758b77fSLuigi Rizzo * this needs to be fixed. 3599758b77fSLuigi Rizzo * 360100ba1a6SJordan K. Hubbard */ 3619758b77fSLuigi Rizzo typedef struct _ipfw_insn { /* template for instructions */ 362a81c165bSAlex Richardson _Alignas(_Alignof(u_int32_t)) u_int8_t opcode; 3631f6ef666SRobert Watson u_int8_t len; /* number of 32-bit words */ 3649758b77fSLuigi Rizzo #define F_NOT 0x80 3659758b77fSLuigi Rizzo #define F_OR 0x40 3669758b77fSLuigi Rizzo #define F_LEN_MASK 0x3f 3679758b77fSLuigi Rizzo #define F_LEN(cmd) ((cmd)->len & F_LEN_MASK) 3689758b77fSLuigi Rizzo 3699758b77fSLuigi Rizzo u_int16_t arg1; 3709758b77fSLuigi Rizzo } ipfw_insn; 371100ba1a6SJordan K. Hubbard 372d60315beSLuigi Rizzo /* 3739758b77fSLuigi Rizzo * The F_INSN_SIZE(type) computes the size, in 4-byte words, of 3749758b77fSLuigi Rizzo * a given type. 375d60315beSLuigi Rizzo */ 3769758b77fSLuigi Rizzo #define F_INSN_SIZE(t) ((sizeof (t))/sizeof(u_int32_t)) 377d60315beSLuigi Rizzo 3789758b77fSLuigi Rizzo /* 3799758b77fSLuigi Rizzo * This is used to store an array of 16-bit entries (ports etc.) 3809758b77fSLuigi Rizzo */ 3819758b77fSLuigi Rizzo typedef struct _ipfw_insn_u16 { 3829758b77fSLuigi Rizzo ipfw_insn o; 3839758b77fSLuigi Rizzo u_int16_t ports[2]; /* there may be more */ 3849758b77fSLuigi Rizzo } ipfw_insn_u16; 385d60315beSLuigi Rizzo 3869758b77fSLuigi Rizzo /* 3879758b77fSLuigi Rizzo * This is used to store an array of 32-bit entries 3889758b77fSLuigi Rizzo * (uid, single IPv4 addresses etc.) 3899758b77fSLuigi Rizzo */ 3909758b77fSLuigi Rizzo typedef struct _ipfw_insn_u32 { 3919758b77fSLuigi Rizzo ipfw_insn o; 3929758b77fSLuigi Rizzo u_int32_t d[1]; /* one or more */ 3939758b77fSLuigi Rizzo } ipfw_insn_u32; 3949758b77fSLuigi Rizzo 3959758b77fSLuigi Rizzo /* 3969758b77fSLuigi Rizzo * This is used to store IP addr-mask pairs. 3979758b77fSLuigi Rizzo */ 3989758b77fSLuigi Rizzo typedef struct _ipfw_insn_ip { 3999758b77fSLuigi Rizzo ipfw_insn o; 4009758b77fSLuigi Rizzo struct in_addr addr; 4019758b77fSLuigi Rizzo struct in_addr mask; 4029758b77fSLuigi Rizzo } ipfw_insn_ip; 4039758b77fSLuigi Rizzo 4049758b77fSLuigi Rizzo /* 405f030c151SLuigi Rizzo * This is used to forward to a given address (ip). 4069758b77fSLuigi Rizzo */ 4079758b77fSLuigi Rizzo typedef struct _ipfw_insn_sa { 4089758b77fSLuigi Rizzo ipfw_insn o; 4099758b77fSLuigi Rizzo struct sockaddr_in sa; 4109758b77fSLuigi Rizzo } ipfw_insn_sa; 4119758b77fSLuigi Rizzo 4129758b77fSLuigi Rizzo /* 4138a006adbSBjoern A. Zeeb * This is used to forward to a given address (ipv6). 4148a006adbSBjoern A. Zeeb */ 4158a006adbSBjoern A. Zeeb typedef struct _ipfw_insn_sa6 { 4168a006adbSBjoern A. Zeeb ipfw_insn o; 4178a006adbSBjoern A. Zeeb struct sockaddr_in6 sa; 4188a006adbSBjoern A. Zeeb } ipfw_insn_sa6; 4198a006adbSBjoern A. Zeeb 4208a006adbSBjoern A. Zeeb /* 4219758b77fSLuigi Rizzo * This is used for MAC addr-mask pairs. 4229758b77fSLuigi Rizzo */ 4239758b77fSLuigi Rizzo typedef struct _ipfw_insn_mac { 4249758b77fSLuigi Rizzo ipfw_insn o; 4259758b77fSLuigi Rizzo u_char addr[12]; /* dst[6] + src[6] */ 4269758b77fSLuigi Rizzo u_char mask[12]; /* dst[6] + src[6] */ 4279758b77fSLuigi Rizzo } ipfw_insn_mac; 4289758b77fSLuigi Rizzo 4299758b77fSLuigi Rizzo /* 430f030c151SLuigi Rizzo * This is used for interface match rules (recv xx, xmit xx). 4319758b77fSLuigi Rizzo */ 4329758b77fSLuigi Rizzo typedef struct _ipfw_insn_if { 4339758b77fSLuigi Rizzo ipfw_insn o; 434830cc178SLuigi Rizzo union { 4359758b77fSLuigi Rizzo struct in_addr ip; 4369bf40edeSBrooks Davis int glob; 4372c452b20SAlexander V. Chernikov uint16_t kidx; 4389758b77fSLuigi Rizzo } p; 4399758b77fSLuigi Rizzo char name[IFNAMSIZ]; 4409758b77fSLuigi Rizzo } ipfw_insn_if; 441830cc178SLuigi Rizzo 4429758b77fSLuigi Rizzo /* 443974dfe30SBrian Feldman * This is used for storing an altq queue id number. 444974dfe30SBrian Feldman */ 445974dfe30SBrian Feldman typedef struct _ipfw_insn_altq { 446974dfe30SBrian Feldman ipfw_insn o; 447974dfe30SBrian Feldman u_int32_t qid; 448974dfe30SBrian Feldman } ipfw_insn_altq; 449974dfe30SBrian Feldman 450974dfe30SBrian Feldman /* 4519758b77fSLuigi Rizzo * This is used for limit rules. 45225549c00SJosef Karthauser */ 4539758b77fSLuigi Rizzo typedef struct _ipfw_insn_limit { 4549758b77fSLuigi Rizzo ipfw_insn o; 4559758b77fSLuigi Rizzo u_int8_t _pad; 4569758b77fSLuigi Rizzo u_int8_t limit_mask; /* combination of DYN_* below */ 457830cc178SLuigi Rizzo #define DYN_SRC_ADDR 0x1 458830cc178SLuigi Rizzo #define DYN_SRC_PORT 0x2 459830cc178SLuigi Rizzo #define DYN_DST_ADDR 0x4 460830cc178SLuigi Rizzo #define DYN_DST_PORT 0x8 46125549c00SJosef Karthauser 4629758b77fSLuigi Rizzo u_int16_t conn_limit; 4639758b77fSLuigi Rizzo } ipfw_insn_limit; 464e4676ba6SJulian Elischer 46506dae58bSJosef Karthauser /* 466f030c151SLuigi Rizzo * This is used for log instructions. 4679758b77fSLuigi Rizzo */ 4689758b77fSLuigi Rizzo typedef struct _ipfw_insn_log { 4699758b77fSLuigi Rizzo ipfw_insn o; 4709758b77fSLuigi Rizzo u_int32_t max_log; /* how many do we log -- 0 = all */ 4719758b77fSLuigi Rizzo u_int32_t log_left; /* how many left to log */ 4729758b77fSLuigi Rizzo } ipfw_insn_log; 4739758b77fSLuigi Rizzo 474d6164b77SAlexander V. Chernikov /* Legacy NAT structures, compat only */ 475d6164b77SAlexander V. Chernikov #ifndef _KERNEL 476bb5081a7SRobert Watson /* 477bb5081a7SRobert Watson * Data structures required by both ipfw(8) and ipfw(4) but not part of the 478bcf5b9faSRobert Watson * management API are protected by IPFW_INTERNAL. 479bb5081a7SRobert Watson */ 480bb5081a7SRobert Watson #ifdef IPFW_INTERNAL 481ff2f6fe8SPaolo Pisati /* Server pool support (LSNAT). */ 482ff2f6fe8SPaolo Pisati struct cfg_spool { 483ff2f6fe8SPaolo Pisati LIST_ENTRY(cfg_spool) _next; /* chain of spool instances */ 484ff2f6fe8SPaolo Pisati struct in_addr addr; 485ff2f6fe8SPaolo Pisati u_short port; 486ff2f6fe8SPaolo Pisati }; 487bb5081a7SRobert Watson #endif 488ff2f6fe8SPaolo Pisati 489ff2f6fe8SPaolo Pisati /* Redirect modes id. */ 490ff2f6fe8SPaolo Pisati #define REDIR_ADDR 0x01 491ff2f6fe8SPaolo Pisati #define REDIR_PORT 0x02 492ff2f6fe8SPaolo Pisati #define REDIR_PROTO 0x04 493ff2f6fe8SPaolo Pisati 494bb5081a7SRobert Watson #ifdef IPFW_INTERNAL 495ff2f6fe8SPaolo Pisati /* Nat redirect configuration. */ 496ff2f6fe8SPaolo Pisati struct cfg_redir { 497ff2f6fe8SPaolo Pisati LIST_ENTRY(cfg_redir) _next; /* chain of redir instances */ 498ff2f6fe8SPaolo Pisati u_int16_t mode; /* type of redirect mode */ 499ff2f6fe8SPaolo Pisati struct in_addr laddr; /* local ip address */ 500ff2f6fe8SPaolo Pisati struct in_addr paddr; /* public ip address */ 501ff2f6fe8SPaolo Pisati struct in_addr raddr; /* remote ip address */ 502ff2f6fe8SPaolo Pisati u_short lport; /* local port */ 503ff2f6fe8SPaolo Pisati u_short pport; /* public port */ 504ff2f6fe8SPaolo Pisati u_short rport; /* remote port */ 505ff2f6fe8SPaolo Pisati u_short pport_cnt; /* number of public ports */ 506ff2f6fe8SPaolo Pisati u_short rport_cnt; /* number of remote ports */ 507ff2f6fe8SPaolo Pisati int proto; /* protocol: tcp/udp */ 508ff2f6fe8SPaolo Pisati struct alias_link **alink; 509ff2f6fe8SPaolo Pisati /* num of entry in spool chain */ 510ff2f6fe8SPaolo Pisati u_int16_t spool_cnt; 511ff2f6fe8SPaolo Pisati /* chain of spool instances */ 512ff2f6fe8SPaolo Pisati LIST_HEAD(spool_chain, cfg_spool) spool_chain; 513ff2f6fe8SPaolo Pisati }; 514bb5081a7SRobert Watson #endif 515ff2f6fe8SPaolo Pisati 516bb5081a7SRobert Watson #ifdef IPFW_INTERNAL 517ff2f6fe8SPaolo Pisati /* Nat configuration data struct. */ 518ff2f6fe8SPaolo Pisati struct cfg_nat { 519ff2f6fe8SPaolo Pisati /* chain of nat instances */ 520ff2f6fe8SPaolo Pisati LIST_ENTRY(cfg_nat) _next; 521ff2f6fe8SPaolo Pisati int id; /* nat id */ 522ff2f6fe8SPaolo Pisati struct in_addr ip; /* nat ip address */ 523ff2f6fe8SPaolo Pisati char if_name[IF_NAMESIZE]; /* interface name */ 524ff2f6fe8SPaolo Pisati int mode; /* aliasing mode */ 525ff2f6fe8SPaolo Pisati struct libalias *lib; /* libalias instance */ 526ff2f6fe8SPaolo Pisati /* number of entry in spool chain */ 527ff2f6fe8SPaolo Pisati int redir_cnt; 528ff2f6fe8SPaolo Pisati /* chain of redir instances */ 529ff2f6fe8SPaolo Pisati LIST_HEAD(redir_chain, cfg_redir) redir_chain; 530ff2f6fe8SPaolo Pisati }; 531bb5081a7SRobert Watson #endif 532ff2f6fe8SPaolo Pisati 533ff2f6fe8SPaolo Pisati #define SOF_NAT sizeof(struct cfg_nat) 534ff2f6fe8SPaolo Pisati #define SOF_REDIR sizeof(struct cfg_redir) 535ff2f6fe8SPaolo Pisati #define SOF_SPOOL sizeof(struct cfg_spool) 536ff2f6fe8SPaolo Pisati 537d6164b77SAlexander V. Chernikov #endif /* ifndef _KERNEL */ 538d6164b77SAlexander V. Chernikov 539d6164b77SAlexander V. Chernikov struct nat44_cfg_spool { 540d6164b77SAlexander V. Chernikov struct in_addr addr; 541d6164b77SAlexander V. Chernikov uint16_t port; 542d6164b77SAlexander V. Chernikov uint16_t spare; 543d6164b77SAlexander V. Chernikov }; 544d6164b77SAlexander V. Chernikov #define NAT44_REDIR_ADDR 0x01 545d6164b77SAlexander V. Chernikov #define NAT44_REDIR_PORT 0x02 546d6164b77SAlexander V. Chernikov #define NAT44_REDIR_PROTO 0x04 547d6164b77SAlexander V. Chernikov 548d6164b77SAlexander V. Chernikov /* Nat redirect configuration. */ 549d6164b77SAlexander V. Chernikov struct nat44_cfg_redir { 550d6164b77SAlexander V. Chernikov struct in_addr laddr; /* local ip address */ 551d6164b77SAlexander V. Chernikov struct in_addr paddr; /* public ip address */ 552d6164b77SAlexander V. Chernikov struct in_addr raddr; /* remote ip address */ 553d6164b77SAlexander V. Chernikov uint16_t lport; /* local port */ 554d6164b77SAlexander V. Chernikov uint16_t pport; /* public port */ 555d6164b77SAlexander V. Chernikov uint16_t rport; /* remote port */ 556d6164b77SAlexander V. Chernikov uint16_t pport_cnt; /* number of public ports */ 557d6164b77SAlexander V. Chernikov uint16_t rport_cnt; /* number of remote ports */ 558d6164b77SAlexander V. Chernikov uint16_t mode; /* type of redirect mode */ 559d6164b77SAlexander V. Chernikov uint16_t spool_cnt; /* num of entry in spool chain */ 560d6164b77SAlexander V. Chernikov uint16_t spare; 561d6164b77SAlexander V. Chernikov uint32_t proto; /* protocol: tcp/udp */ 562d6164b77SAlexander V. Chernikov }; 563d6164b77SAlexander V. Chernikov 564d6164b77SAlexander V. Chernikov /* Nat configuration data struct. */ 565d6164b77SAlexander V. Chernikov struct nat44_cfg_nat { 566d6164b77SAlexander V. Chernikov char name[64]; /* nat name */ 567d6164b77SAlexander V. Chernikov char if_name[64]; /* interface name */ 568d6164b77SAlexander V. Chernikov uint32_t size; /* structure size incl. redirs */ 569d6164b77SAlexander V. Chernikov struct in_addr ip; /* nat IPv4 address */ 570d6164b77SAlexander V. Chernikov uint32_t mode; /* aliasing mode */ 571d6164b77SAlexander V. Chernikov uint32_t redir_cnt; /* number of entry in spool chain */ 572a08cdb6cSNeel Chauhan u_short alias_port_lo; /* low range for port aliasing */ 573a08cdb6cSNeel Chauhan u_short alias_port_hi; /* high range for port aliasing */ 574d6164b77SAlexander V. Chernikov }; 575d6164b77SAlexander V. Chernikov 576ff2f6fe8SPaolo Pisati /* Nat command. */ 577ff2f6fe8SPaolo Pisati typedef struct _ipfw_insn_nat { 578ff2f6fe8SPaolo Pisati ipfw_insn o; 579ff2f6fe8SPaolo Pisati struct cfg_nat *nat; 580ff2f6fe8SPaolo Pisati } ipfw_insn_nat; 581ff2f6fe8SPaolo Pisati 5828195404bSBrooks Davis /* Apply ipv6 mask on ipv6 addr */ 5835786c6b9SAndrey V. Elsukov #define APPLY_MASK(addr,mask) do { \ 5848195404bSBrooks Davis (addr)->__u6_addr.__u6_addr32[0] &= (mask)->__u6_addr.__u6_addr32[0]; \ 5858195404bSBrooks Davis (addr)->__u6_addr.__u6_addr32[1] &= (mask)->__u6_addr.__u6_addr32[1]; \ 5868195404bSBrooks Davis (addr)->__u6_addr.__u6_addr32[2] &= (mask)->__u6_addr.__u6_addr32[2]; \ 5875786c6b9SAndrey V. Elsukov (addr)->__u6_addr.__u6_addr32[3] &= (mask)->__u6_addr.__u6_addr32[3]; \ 5885786c6b9SAndrey V. Elsukov } while (0) 5898195404bSBrooks Davis 5908195404bSBrooks Davis /* Structure for ipv6 */ 5918195404bSBrooks Davis typedef struct _ipfw_insn_ip6 { 5928195404bSBrooks Davis ipfw_insn o; 5938195404bSBrooks Davis struct in6_addr addr6; 5948195404bSBrooks Davis struct in6_addr mask6; 5958195404bSBrooks Davis } ipfw_insn_ip6; 5968195404bSBrooks Davis 5978195404bSBrooks Davis /* Used to support icmp6 types */ 5988195404bSBrooks Davis typedef struct _ipfw_insn_icmp6 { 5998195404bSBrooks Davis ipfw_insn o; 6008195404bSBrooks Davis uint32_t d[7]; /* XXX This number si related to the netinet/icmp6.h 6018195404bSBrooks Davis * define ICMP6_MAXTYPE 6028195404bSBrooks Davis * as follows: n = ICMP6_MAXTYPE/32 + 1 6038195404bSBrooks Davis * Actually is 203 6048195404bSBrooks Davis */ 6058195404bSBrooks Davis } ipfw_insn_icmp6; 6068195404bSBrooks Davis 6079758b77fSLuigi Rizzo /* 6089758b77fSLuigi Rizzo * Here we have the structure representing an ipfw rule. 60932f967a3SLuigi Rizzo * 6107e767c79SAlexander V. Chernikov * Layout: 6117e767c79SAlexander V. Chernikov * struct ip_fw_rule 6127e767c79SAlexander V. Chernikov * [ counter block, size = rule->cntr_len ] 6137e767c79SAlexander V. Chernikov * [ one or more instructions, size = rule->cmd_len * 4 ] 6147e767c79SAlexander V. Chernikov * 6157e767c79SAlexander V. Chernikov * It starts with a general area (with link fields). 6167e767c79SAlexander V. Chernikov * Counter block may be next (if rule->cntr_len > 0), 6179758b77fSLuigi Rizzo * followed by an array of one or more instructions, which the code 6187e767c79SAlexander V. Chernikov * accesses as an array of 32-bit values. rule->cmd_len represents 6197e767c79SAlexander V. Chernikov * the total instructions legth in u32 worrd, while act_ofs represents 6207e767c79SAlexander V. Chernikov * rule action offset in u32 words. 6219758b77fSLuigi Rizzo * 6229758b77fSLuigi Rizzo * When assembling instruction, remember the following: 6239758b77fSLuigi Rizzo * 6249758b77fSLuigi Rizzo * + if a rule has a "keep-state" (or "limit") option, then the 6259758b77fSLuigi Rizzo * first instruction (at r->cmd) MUST BE an O_PROBE_STATE 6269758b77fSLuigi Rizzo * + if a rule has a "log" option, then the first action 6279758b77fSLuigi Rizzo * (at ACTION_PTR(r)) MUST be O_LOG 628974dfe30SBrian Feldman * + if a rule has an "altq" option, it comes after "log" 6296a7d5cb6SOleg Bulyzhin * + if a rule has an O_TAG option, it comes after "log" and "altq" 6309758b77fSLuigi Rizzo * 6317e767c79SAlexander V. Chernikov * 6327e767c79SAlexander V. Chernikov * All structures (excluding instructions) are u64-aligned. 6337e767c79SAlexander V. Chernikov * Please keep this. 63432f967a3SLuigi Rizzo */ 63532f967a3SLuigi Rizzo 6367e767c79SAlexander V. Chernikov struct ip_fw_rule { 6377e767c79SAlexander V. Chernikov uint16_t act_ofs; /* offset of action in 32-bit units */ 6387e767c79SAlexander V. Chernikov uint16_t cmd_len; /* # of 32-bit words in cmd */ 6397e767c79SAlexander V. Chernikov uint16_t spare; 6407e767c79SAlexander V. Chernikov uint8_t set; /* rule set (0..31) */ 6417e767c79SAlexander V. Chernikov uint8_t flags; /* rule flags */ 6427e767c79SAlexander V. Chernikov uint32_t rulenum; /* rule number */ 6437e767c79SAlexander V. Chernikov uint32_t id; /* rule id */ 6447e767c79SAlexander V. Chernikov 6457e767c79SAlexander V. Chernikov ipfw_insn cmd[1]; /* storage for commands */ 6467e767c79SAlexander V. Chernikov }; 6477e767c79SAlexander V. Chernikov #define IPFW_RULE_NOOPT 0x01 /* Has no options in body */ 648094d6f8dSAndrey V. Elsukov #define IPFW_RULE_JUSTOPTS 0x02 /* new format of rule body */ 6497e767c79SAlexander V. Chernikov 6507e767c79SAlexander V. Chernikov /* Unaligned version */ 6517e767c79SAlexander V. Chernikov 6527e767c79SAlexander V. Chernikov /* Base ipfw rule counter block. */ 6537e767c79SAlexander V. Chernikov struct ip_fw_bcounter { 6547e767c79SAlexander V. Chernikov uint16_t size; /* Size of counter block, bytes */ 6557e767c79SAlexander V. Chernikov uint8_t flags; /* flags for given block */ 6567e767c79SAlexander V. Chernikov uint8_t spare; 6577e767c79SAlexander V. Chernikov uint32_t timestamp; /* tv_sec of last match */ 6587e767c79SAlexander V. Chernikov uint64_t pcnt; /* Packet counter */ 6597e767c79SAlexander V. Chernikov uint64_t bcnt; /* Byte counter */ 6607e767c79SAlexander V. Chernikov }; 6617e767c79SAlexander V. Chernikov 6627e767c79SAlexander V. Chernikov #ifndef _KERNEL 6637e767c79SAlexander V. Chernikov /* 6647e767c79SAlexander V. Chernikov * Legacy rule format 6657e767c79SAlexander V. Chernikov */ 6669758b77fSLuigi Rizzo struct ip_fw { 667de240d10SLuigi Rizzo struct ip_fw *x_next; /* linked list of rules */ 668a8c102a2SLuigi Rizzo struct ip_fw *next_rule; /* ptr to next [skipto] rule */ 669f030c151SLuigi Rizzo /* 'next_rule' is used to pass up 'set_disable' status */ 670f030c151SLuigi Rizzo 671dda10d62SOleg Bulyzhin uint16_t act_ofs; /* offset of action in 32-bit units */ 672dda10d62SOleg Bulyzhin uint16_t cmd_len; /* # of 32-bit words in cmd */ 673dda10d62SOleg Bulyzhin uint16_t rulenum; /* rule number */ 674dda10d62SOleg Bulyzhin uint8_t set; /* rule set (0..31) */ 675dda10d62SOleg Bulyzhin uint8_t _pad; /* padding */ 676dda10d62SOleg Bulyzhin uint32_t id; /* rule id */ 6779758b77fSLuigi Rizzo 6789758b77fSLuigi Rizzo /* These fields are present in all rules. */ 679dda10d62SOleg Bulyzhin uint64_t pcnt; /* Packet counter */ 680dda10d62SOleg Bulyzhin uint64_t bcnt; /* Byte counter */ 681dda10d62SOleg Bulyzhin uint32_t timestamp; /* tv_sec of last match */ 6829758b77fSLuigi Rizzo 6839758b77fSLuigi Rizzo ipfw_insn cmd[1]; /* storage for commands */ 6849758b77fSLuigi Rizzo }; 6857e767c79SAlexander V. Chernikov #endif 6869758b77fSLuigi Rizzo 6879758b77fSLuigi Rizzo #define ACTION_PTR(rule) \ 6889758b77fSLuigi Rizzo (ipfw_insn *)( (u_int32_t *)((rule)->cmd) + ((rule)->act_ofs) ) 6899758b77fSLuigi Rizzo 6907e767c79SAlexander V. Chernikov #define RULESIZE(rule) (sizeof(*(rule)) + (rule)->cmd_len * 4 - 4) 6917e767c79SAlexander V. Chernikov 692f9f7bde3SLuigi Rizzo #if 1 // should be moved to in.h 693100ba1a6SJordan K. Hubbard /* 6949758b77fSLuigi Rizzo * This structure is used as a flow mask and a flow id for various 6959758b77fSLuigi Rizzo * parts of the code. 696f9f7bde3SLuigi Rizzo * addr_type is used in userland and kernel to mark the address type. 697f9f7bde3SLuigi Rizzo * fib is used in the kernel to record the fib in use. 698f9f7bde3SLuigi Rizzo * _flags is used in the kernel to store tcp flags for dynamic rules. 69903c61266SLuigi Rizzo */ 70003c61266SLuigi Rizzo struct ipfw_flow_id { 701cc4d3c30SLuigi Rizzo uint32_t dst_ip; 702cc4d3c30SLuigi Rizzo uint32_t src_ip; 703cc4d3c30SLuigi Rizzo uint16_t dst_port; 704cc4d3c30SLuigi Rizzo uint16_t src_port; 705b99a6823SAndrey V. Elsukov uint8_t fib; /* XXX: must be uint16_t */ 706cc4d3c30SLuigi Rizzo uint8_t proto; 707f9f7bde3SLuigi Rizzo uint8_t _flags; /* protocol-specific flags */ 708f9f7bde3SLuigi Rizzo uint8_t addr_type; /* 4=ip4, 6=ip6, 1=ether ? */ 709cc4d3c30SLuigi Rizzo struct in6_addr dst_ip6; 7108195404bSBrooks Davis struct in6_addr src_ip6; 711cc4d3c30SLuigi Rizzo uint32_t flow_id6; 712f9f7bde3SLuigi Rizzo uint32_t extra; /* queue/pipe or frag_id */ 71303c61266SLuigi Rizzo }; 714cc4d3c30SLuigi Rizzo #endif 71503c61266SLuigi Rizzo 716b99a6823SAndrey V. Elsukov #define IS_IP4_FLOW_ID(id) ((id)->addr_type == 4) 7178195404bSBrooks Davis #define IS_IP6_FLOW_ID(id) ((id)->addr_type == 6) 7188195404bSBrooks Davis 71903c61266SLuigi Rizzo /* 720f030c151SLuigi Rizzo * Dynamic ipfw rule. 72103c61266SLuigi Rizzo */ 7229758b77fSLuigi Rizzo typedef struct _ipfw_dyn_rule ipfw_dyn_rule; 7239758b77fSLuigi Rizzo 7249758b77fSLuigi Rizzo struct _ipfw_dyn_rule { 7259758b77fSLuigi Rizzo ipfw_dyn_rule *next; /* linked list of rules. */ 726830cc178SLuigi Rizzo struct ip_fw *rule; /* pointer to rule */ 727f030c151SLuigi Rizzo /* 'rule' is used to pass up the rule number (from the parent) */ 728f030c151SLuigi Rizzo 7299758b77fSLuigi Rizzo ipfw_dyn_rule *parent; /* pointer to parent rule */ 7309758b77fSLuigi Rizzo u_int64_t pcnt; /* packet match counter */ 7319758b77fSLuigi Rizzo u_int64_t bcnt; /* byte match counter */ 732330462a3SBernd Walter struct ipfw_flow_id id; /* (masked) flow id */ 733330462a3SBernd Walter u_int32_t expire; /* expire time */ 73403c61266SLuigi Rizzo u_int32_t bucket; /* which bucket in hash table */ 73525549c00SJosef Karthauser u_int32_t state; /* state of this rule (typically a 73625549c00SJosef Karthauser * combination of TCP flags) 73725549c00SJosef Karthauser */ 738d66f9c86SAndrey V. Elsukov #define IPFW_DYN_ORPHANED 0x40000 /* state's parent rule was deleted */ 739a8c102a2SLuigi Rizzo u_int32_t ack_fwd; /* most recent ACKs in forward */ 740a8c102a2SLuigi Rizzo u_int32_t ack_rev; /* and reverse directions (used */ 741a8c102a2SLuigi Rizzo /* to generate keepalives) */ 74232f967a3SLuigi Rizzo u_int16_t dyn_type; /* rule type */ 74332f967a3SLuigi Rizzo u_int16_t count; /* refcount */ 744ed22e564SAndrey V. Elsukov u_int16_t kidx; /* index of named object */ 745ed22e564SAndrey V. Elsukov } __packed __aligned(8); 74603c61266SLuigi Rizzo 74703c61266SLuigi Rizzo /* 74837afa1e8SUgen J.S. Antsilevich * Definitions for IP option names. 74937afa1e8SUgen J.S. Antsilevich */ 75037afa1e8SUgen J.S. Antsilevich #define IP_FW_IPOPT_LSRR 0x01 75137afa1e8SUgen J.S. Antsilevich #define IP_FW_IPOPT_SSRR 0x02 75237afa1e8SUgen J.S. Antsilevich #define IP_FW_IPOPT_RR 0x04 75337afa1e8SUgen J.S. Antsilevich #define IP_FW_IPOPT_TS 0x08 75437afa1e8SUgen J.S. Antsilevich 75537afa1e8SUgen J.S. Antsilevich /* 7569714563dSDan Moschuk * Definitions for TCP option names. 7579714563dSDan Moschuk */ 7589714563dSDan Moschuk #define IP_FW_TCPOPT_MSS 0x01 7599714563dSDan Moschuk #define IP_FW_TCPOPT_WINDOW 0x02 7609714563dSDan Moschuk #define IP_FW_TCPOPT_SACK 0x04 7619714563dSDan Moschuk #define IP_FW_TCPOPT_TS 0x08 7629714563dSDan Moschuk #define IP_FW_TCPOPT_CC 0x10 7639714563dSDan Moschuk 7649758b77fSLuigi Rizzo #define ICMP_REJECT_RST 0x100 /* fake ICMP code (send a TCP RST) */ 7659066356bSBjoern A. Zeeb #define ICMP6_UNREACH_RST 0x100 /* fake ICMPv6 code (send a TCP RST) */ 766665c8a2eSMichael Tuexen #define ICMP_REJECT_ABORT 0x101 /* fake ICMP code (send an SCTP ABORT) */ 767665c8a2eSMichael Tuexen #define ICMP6_UNREACH_ABORT 0x101 /* fake ICMPv6 code (send an SCTP ABORT) */ 7689758b77fSLuigi Rizzo 7699714563dSDan Moschuk /* 770cd8b5ae0SRuslan Ermilov * These are used for lookup tables. 771cd8b5ae0SRuslan Ermilov */ 772f8bee51aSAlexander V. Chernikov 773c21034b7SAlexander V. Chernikov #define IPFW_TABLE_ADDR 1 /* Table for holding IPv4/IPv6 prefixes */ 774f8bee51aSAlexander V. Chernikov #define IPFW_TABLE_INTERFACE 2 /* Table for holding interface names */ 775b23d5de9SAlexander V. Chernikov #define IPFW_TABLE_NUMBER 3 /* Table for holding ports/uid/gid/etc */ 776914bffb6SAlexander V. Chernikov #define IPFW_TABLE_FLOW 4 /* Table for holding flow data */ 77781cac390SArseny Smalyuk #define IPFW_TABLE_MAC 5 /* Table for holding mac address prefixes */ 77881cac390SArseny Smalyuk #define IPFW_TABLE_MAXTYPE 5 /* Maximum valid number */ 779ac35ff17SAlexander V. Chernikov 780c21034b7SAlexander V. Chernikov #define IPFW_TABLE_CIDR IPFW_TABLE_ADDR /* compat */ 781c21034b7SAlexander V. Chernikov 782adf3b2b9SAlexander V. Chernikov /* Value types */ 7830cba2b28SAlexander V. Chernikov #define IPFW_VTYPE_LEGACY 0xFFFFFFFF /* All data is filled in */ 7840cba2b28SAlexander V. Chernikov #define IPFW_VTYPE_SKIPTO 0x00000001 /* skipto/call/callreturn */ 7850cba2b28SAlexander V. Chernikov #define IPFW_VTYPE_PIPE 0x00000002 /* pipe/queue */ 7860cba2b28SAlexander V. Chernikov #define IPFW_VTYPE_FIB 0x00000004 /* setfib */ 7870cba2b28SAlexander V. Chernikov #define IPFW_VTYPE_NAT 0x00000008 /* nat */ 7880cba2b28SAlexander V. Chernikov #define IPFW_VTYPE_DSCP 0x00000010 /* dscp */ 7890cba2b28SAlexander V. Chernikov #define IPFW_VTYPE_TAG 0x00000020 /* tag/untag */ 7900cba2b28SAlexander V. Chernikov #define IPFW_VTYPE_DIVERT 0x00000040 /* divert/tee */ 7910cba2b28SAlexander V. Chernikov #define IPFW_VTYPE_NETGRAPH 0x00000080 /* netgraph/ngtee */ 7922530ed9eSAndrey V. Elsukov #define IPFW_VTYPE_LIMIT 0x00000100 /* limit */ 7930cba2b28SAlexander V. Chernikov #define IPFW_VTYPE_NH4 0x00000200 /* IPv4 nexthop */ 7940cba2b28SAlexander V. Chernikov #define IPFW_VTYPE_NH6 0x00000400 /* IPv6 nexthop */ 795fc727ad6SBoris Lytochkin #define IPFW_VTYPE_MARK 0x00000800 /* [fw]mark */ 796f8bee51aSAlexander V. Chernikov 79781cac390SArseny Smalyuk /* MAC/InfiniBand/etc address length */ 79881cac390SArseny Smalyuk #define IPFW_MAX_L2_ADDR_LEN 20 79981cac390SArseny Smalyuk 800cd8b5ae0SRuslan Ermilov typedef struct _ipfw_table_entry { 801cd8b5ae0SRuslan Ermilov in_addr_t addr; /* network address */ 802cd8b5ae0SRuslan Ermilov u_int32_t value; /* value */ 803cd8b5ae0SRuslan Ermilov u_int16_t tbl; /* table number */ 804cd8b5ae0SRuslan Ermilov u_int8_t masklen; /* mask length */ 805cd8b5ae0SRuslan Ermilov } ipfw_table_entry; 806cd8b5ae0SRuslan Ermilov 807f8bee51aSAlexander V. Chernikov typedef struct _ipfw_table_xentry { 808f8bee51aSAlexander V. Chernikov uint16_t len; /* Total entry length */ 809f8bee51aSAlexander V. Chernikov uint8_t type; /* entry type */ 810f8bee51aSAlexander V. Chernikov uint8_t masklen; /* mask length */ 811f8bee51aSAlexander V. Chernikov uint16_t tbl; /* table number */ 812c3015737SAlexander V. Chernikov uint16_t flags; /* record flags */ 813f8bee51aSAlexander V. Chernikov uint32_t value; /* value */ 814f8bee51aSAlexander V. Chernikov union { 815f8bee51aSAlexander V. Chernikov /* Longest field needs to be aligned by 4-byte boundary */ 816f8bee51aSAlexander V. Chernikov struct in6_addr addr6; /* IPv6 address */ 817f8bee51aSAlexander V. Chernikov char iface[IF_NAMESIZE]; /* interface name */ 818f8bee51aSAlexander V. Chernikov } k; 819f8bee51aSAlexander V. Chernikov } ipfw_table_xentry; 820c3015737SAlexander V. Chernikov #define IPFW_TCF_INET 0x01 /* CIDR flags: IPv4 record */ 821f8bee51aSAlexander V. Chernikov 822cd8b5ae0SRuslan Ermilov typedef struct _ipfw_table { 823cd8b5ae0SRuslan Ermilov u_int32_t size; /* size of entries in bytes */ 824cd8b5ae0SRuslan Ermilov u_int32_t cnt; /* # of entries */ 825cd8b5ae0SRuslan Ermilov u_int16_t tbl; /* table number */ 826cd8b5ae0SRuslan Ermilov ipfw_table_entry ent[0]; /* entries */ 827cd8b5ae0SRuslan Ermilov } ipfw_table; 828cd8b5ae0SRuslan Ermilov 829f8bee51aSAlexander V. Chernikov typedef struct _ipfw_xtable { 830b074b7bbSAlexander V. Chernikov ip_fw3_opheader opheader; /* IP_FW3 opcode */ 831f8bee51aSAlexander V. Chernikov uint32_t size; /* size of entries in bytes */ 832f8bee51aSAlexander V. Chernikov uint32_t cnt; /* # of entries */ 833f8bee51aSAlexander V. Chernikov uint16_t tbl; /* table number */ 834f8bee51aSAlexander V. Chernikov uint8_t type; /* table type */ 835f8bee51aSAlexander V. Chernikov ipfw_table_xentry xent[0]; /* entries */ 836f8bee51aSAlexander V. Chernikov } ipfw_xtable; 837f8bee51aSAlexander V. Chernikov 8389f7d47b0SAlexander V. Chernikov typedef struct _ipfw_obj_tlv { 839b074b7bbSAlexander V. Chernikov uint16_t type; /* TLV type */ 840ac35ff17SAlexander V. Chernikov uint16_t flags; /* TLV-specific flags */ 841563b5ab1SAlexander V. Chernikov uint32_t length; /* Total length, aligned to u64 */ 8429f7d47b0SAlexander V. Chernikov } ipfw_obj_tlv; 843563b5ab1SAlexander V. Chernikov #define IPFW_TLV_TBL_NAME 1 844563b5ab1SAlexander V. Chernikov #define IPFW_TLV_TBLNAME_LIST 2 845563b5ab1SAlexander V. Chernikov #define IPFW_TLV_RULE_LIST 3 8466447bae6SAlexander V. Chernikov #define IPFW_TLV_DYNSTATE_LIST 4 847ac35ff17SAlexander V. Chernikov #define IPFW_TLV_TBL_ENT 5 8486447bae6SAlexander V. Chernikov #define IPFW_TLV_DYN_ENT 6 8497e767c79SAlexander V. Chernikov #define IPFW_TLV_RULE_ENT 7 85068394ec8SAlexander V. Chernikov #define IPFW_TLV_TBLENT_LIST 8 851a73d728dSAlexander V. Chernikov #define IPFW_TLV_RANGE 9 8522acdf79fSAndrey V. Elsukov #define IPFW_TLV_EACTION 10 853b867e84eSAndrey V. Elsukov #define IPFW_TLV_COUNTERS 11 854d8caf56eSAndrey V. Elsukov #define IPFW_TLV_OBJDATA 12 855ed22e564SAndrey V. Elsukov #define IPFW_TLV_STATE_NAME 14 8562acdf79fSAndrey V. Elsukov 8572acdf79fSAndrey V. Elsukov #define IPFW_TLV_EACTION_BASE 1000 8582acdf79fSAndrey V. Elsukov #define IPFW_TLV_EACTION_NAME(arg) (IPFW_TLV_EACTION_BASE + (arg)) 859b074b7bbSAlexander V. Chernikov 860d8caf56eSAndrey V. Elsukov typedef struct _ipfw_obj_data { 861d8caf56eSAndrey V. Elsukov ipfw_obj_tlv head; 862d8caf56eSAndrey V. Elsukov void *data[0]; 863d8caf56eSAndrey V. Elsukov } ipfw_obj_data; 864d8caf56eSAndrey V. Elsukov 865b074b7bbSAlexander V. Chernikov /* Object name TLV */ 8669f7d47b0SAlexander V. Chernikov typedef struct _ipfw_obj_ntlv { 8679f7d47b0SAlexander V. Chernikov ipfw_obj_tlv head; /* TLV header */ 868b074b7bbSAlexander V. Chernikov uint16_t idx; /* Name index */ 8692685841bSAndrey V. Elsukov uint8_t set; /* set, if applicable */ 870ac35ff17SAlexander V. Chernikov uint8_t type; /* object type, if applicable */ 8712685841bSAndrey V. Elsukov uint32_t spare; /* unused */ 872b074b7bbSAlexander V. Chernikov char name[64]; /* Null-terminated name */ 8739f7d47b0SAlexander V. Chernikov } ipfw_obj_ntlv; 874b074b7bbSAlexander V. Chernikov 875914bffb6SAlexander V. Chernikov /* IPv4/IPv6 L4 flow description */ 876914bffb6SAlexander V. Chernikov struct tflow_entry { 877914bffb6SAlexander V. Chernikov uint8_t af; 878914bffb6SAlexander V. Chernikov uint8_t proto; 879914bffb6SAlexander V. Chernikov uint16_t spare; 880914bffb6SAlexander V. Chernikov uint16_t sport; 881914bffb6SAlexander V. Chernikov uint16_t dport; 882914bffb6SAlexander V. Chernikov union { 883914bffb6SAlexander V. Chernikov struct { 884914bffb6SAlexander V. Chernikov struct in_addr sip; 885914bffb6SAlexander V. Chernikov struct in_addr dip; 886914bffb6SAlexander V. Chernikov } a4; 887914bffb6SAlexander V. Chernikov struct { 888914bffb6SAlexander V. Chernikov struct in6_addr sip6; 889914bffb6SAlexander V. Chernikov struct in6_addr dip6; 890914bffb6SAlexander V. Chernikov } a6; 891914bffb6SAlexander V. Chernikov } a; 892914bffb6SAlexander V. Chernikov }; 893914bffb6SAlexander V. Chernikov 894fc727ad6SBoris Lytochkin /* 64-byte structure representing multi-field table value */ 8950cba2b28SAlexander V. Chernikov typedef struct _ipfw_table_value { 8960cba2b28SAlexander V. Chernikov uint32_t tag; /* O_TAG/O_TAGGED */ 8970cba2b28SAlexander V. Chernikov uint32_t pipe; /* O_PIPE/O_QUEUE */ 8980cba2b28SAlexander V. Chernikov uint16_t divert; /* O_DIVERT/O_TEE */ 8990cba2b28SAlexander V. Chernikov uint16_t skipto; /* skipto, CALLRET */ 9000cba2b28SAlexander V. Chernikov uint32_t netgraph; /* O_NETGRAPH/O_NGTEE */ 9010cba2b28SAlexander V. Chernikov uint32_t fib; /* O_SETFIB */ 9020cba2b28SAlexander V. Chernikov uint32_t nat; /* O_NAT */ 9030cba2b28SAlexander V. Chernikov uint32_t nh4; 9040cba2b28SAlexander V. Chernikov uint8_t dscp; 9052530ed9eSAndrey V. Elsukov uint8_t spare0; 906fc727ad6SBoris Lytochkin uint16_t kidx; /* value kernel index */ 9070cba2b28SAlexander V. Chernikov struct in6_addr nh6; 9080cba2b28SAlexander V. Chernikov uint32_t limit; /* O_LIMIT */ 9092530ed9eSAndrey V. Elsukov uint32_t zoneid; /* scope zone id for nh6 */ 910fc727ad6SBoris Lytochkin uint32_t mark; /* O_SETMARK/O_MARK */ 911fc727ad6SBoris Lytochkin uint32_t refcnt; /* XXX 64-bit in kernel */ 9120cba2b28SAlexander V. Chernikov } ipfw_table_value; 9130cba2b28SAlexander V. Chernikov 914ac35ff17SAlexander V. Chernikov /* Table entry TLV */ 915ac35ff17SAlexander V. Chernikov typedef struct _ipfw_obj_tentry { 916ac35ff17SAlexander V. Chernikov ipfw_obj_tlv head; /* TLV header */ 917ac35ff17SAlexander V. Chernikov uint8_t subtype; /* subtype (IPv4,IPv6) */ 918ac35ff17SAlexander V. Chernikov uint8_t masklen; /* mask length */ 9193a845e10SAlexander V. Chernikov uint8_t result; /* request result */ 9203a845e10SAlexander V. Chernikov uint8_t spare0; 9214bbd1577SAlexander V. Chernikov uint16_t idx; /* Table name index */ 9223a845e10SAlexander V. Chernikov uint16_t spare1; 923ac35ff17SAlexander V. Chernikov union { 924ac35ff17SAlexander V. Chernikov /* Longest field needs to be aligned by 8-byte boundary */ 925ac35ff17SAlexander V. Chernikov struct in_addr addr; /* IPv4 address */ 926ac35ff17SAlexander V. Chernikov uint32_t key; /* uid/gid/port */ 927ac35ff17SAlexander V. Chernikov struct in6_addr addr6; /* IPv6 address */ 928ac35ff17SAlexander V. Chernikov char iface[IF_NAMESIZE]; /* interface name */ 92981cac390SArseny Smalyuk u_char mac[IPFW_MAX_L2_ADDR_LEN]; /* MAC address */ 930914bffb6SAlexander V. Chernikov struct tflow_entry flow; 931ac35ff17SAlexander V. Chernikov } k; 9324bbd1577SAlexander V. Chernikov union { 9330cba2b28SAlexander V. Chernikov ipfw_table_value value; /* value data */ 9340cba2b28SAlexander V. Chernikov uint32_t kidx; /* value kernel index */ 9354bbd1577SAlexander V. Chernikov } v; 936ac35ff17SAlexander V. Chernikov } ipfw_obj_tentry; 937ac35ff17SAlexander V. Chernikov #define IPFW_TF_UPDATE 0x01 /* Update record if exists */ 9383a845e10SAlexander V. Chernikov /* Container TLV */ 9393a845e10SAlexander V. Chernikov #define IPFW_CTF_ATOMIC 0x01 /* Perform atomic operation */ 9403a845e10SAlexander V. Chernikov /* Operation results */ 9413a845e10SAlexander V. Chernikov #define IPFW_TR_IGNORED 0 /* Entry was ignored (rollback) */ 942a4641f4eSPedro F. Giffuni #define IPFW_TR_ADDED 1 /* Entry was successfully added */ 943a4641f4eSPedro F. Giffuni #define IPFW_TR_UPDATED 2 /* Entry was successfully updated*/ 944a4641f4eSPedro F. Giffuni #define IPFW_TR_DELETED 3 /* Entry was successfully deleted*/ 9453a845e10SAlexander V. Chernikov #define IPFW_TR_LIMIT 4 /* Entry was ignored (limit) */ 9463a845e10SAlexander V. Chernikov #define IPFW_TR_NOTFOUND 5 /* Entry was not found */ 9473a845e10SAlexander V. Chernikov #define IPFW_TR_EXISTS 6 /* Entry already exists */ 9483a845e10SAlexander V. Chernikov #define IPFW_TR_ERROR 7 /* Request has failed (unknown) */ 949ac35ff17SAlexander V. Chernikov 9506447bae6SAlexander V. Chernikov typedef struct _ipfw_obj_dyntlv { 9516447bae6SAlexander V. Chernikov ipfw_obj_tlv head; 9526447bae6SAlexander V. Chernikov ipfw_dyn_rule state; 9536447bae6SAlexander V. Chernikov } ipfw_obj_dyntlv; 9546447bae6SAlexander V. Chernikov #define IPFW_DF_LAST 0x01 /* Last state in chain */ 9556447bae6SAlexander V. Chernikov 956563b5ab1SAlexander V. Chernikov /* Containter TLVs */ 957563b5ab1SAlexander V. Chernikov typedef struct _ipfw_obj_ctlv { 958563b5ab1SAlexander V. Chernikov ipfw_obj_tlv head; /* TLV header */ 959563b5ab1SAlexander V. Chernikov uint32_t count; /* Number of sub-TLVs */ 9607e767c79SAlexander V. Chernikov uint16_t objsize; /* Single object size */ 9617e767c79SAlexander V. Chernikov uint8_t version; /* TLV version */ 9623a845e10SAlexander V. Chernikov uint8_t flags; /* TLV-specific flags */ 963563b5ab1SAlexander V. Chernikov } ipfw_obj_ctlv; 964563b5ab1SAlexander V. Chernikov 965a73d728dSAlexander V. Chernikov /* Range TLV */ 966a73d728dSAlexander V. Chernikov typedef struct _ipfw_range_tlv { 967a73d728dSAlexander V. Chernikov ipfw_obj_tlv head; /* TLV header */ 968a73d728dSAlexander V. Chernikov uint32_t flags; /* Range flags */ 969a73d728dSAlexander V. Chernikov uint16_t start_rule; /* Range start */ 970a73d728dSAlexander V. Chernikov uint16_t end_rule; /* Range end */ 971a73d728dSAlexander V. Chernikov uint32_t set; /* Range set to match */ 972a73d728dSAlexander V. Chernikov uint32_t new_set; /* New set to move/swap to */ 973a73d728dSAlexander V. Chernikov } ipfw_range_tlv; 974a73d728dSAlexander V. Chernikov #define IPFW_RCFLAG_RANGE 0x01 /* rule range is set */ 975a73d728dSAlexander V. Chernikov #define IPFW_RCFLAG_ALL 0x02 /* match ALL rules */ 976a73d728dSAlexander V. Chernikov #define IPFW_RCFLAG_SET 0x04 /* match rules in given set */ 977d66f9c86SAndrey V. Elsukov #define IPFW_RCFLAG_DYNAMIC 0x08 /* match only dynamic states */ 9782930362fSAlexander V. Chernikov /* User-settable flags */ 9792930362fSAlexander V. Chernikov #define IPFW_RCFLAG_USER (IPFW_RCFLAG_RANGE | IPFW_RCFLAG_ALL | \ 980d66f9c86SAndrey V. Elsukov IPFW_RCFLAG_SET | IPFW_RCFLAG_DYNAMIC) 9812930362fSAlexander V. Chernikov /* Internally used flags */ 982*78e4dbc3SGordon Bergling #define IPFW_RCFLAG_DEFAULT 0x0100 /* Do not skip default rule */ 983a73d728dSAlexander V. Chernikov 9845f379342SAlexander V. Chernikov typedef struct _ipfw_ta_tinfo { 985914bffb6SAlexander V. Chernikov uint32_t flags; /* Format flags */ 9865f379342SAlexander V. Chernikov uint32_t spare; 9875f379342SAlexander V. Chernikov uint8_t taclass4; /* algorithm class */ 9885f379342SAlexander V. Chernikov uint8_t spare4; 9895f379342SAlexander V. Chernikov uint16_t itemsize4; /* item size in runtime */ 9905f379342SAlexander V. Chernikov uint32_t size4; /* runtime structure size */ 9915f379342SAlexander V. Chernikov uint32_t count4; /* number of items in runtime */ 9925f379342SAlexander V. Chernikov uint8_t taclass6; /* algorithm class */ 9935f379342SAlexander V. Chernikov uint8_t spare6; 9945f379342SAlexander V. Chernikov uint16_t itemsize6; /* item size in runtime */ 9955f379342SAlexander V. Chernikov uint32_t size6; /* runtime structure size */ 9965f379342SAlexander V. Chernikov uint32_t count6; /* number of items in runtime */ 9975f379342SAlexander V. Chernikov } ipfw_ta_tinfo; 998914bffb6SAlexander V. Chernikov #define IPFW_TACLASS_HASH 1 /* algo is based on hash */ 999914bffb6SAlexander V. Chernikov #define IPFW_TACLASS_ARRAY 2 /* algo is based on array */ 1000914bffb6SAlexander V. Chernikov #define IPFW_TACLASS_RADIX 3 /* algo is based on radix tree */ 1001914bffb6SAlexander V. Chernikov 1002914bffb6SAlexander V. Chernikov #define IPFW_TATFLAGS_DATA 0x0001 /* Has data filled in */ 10035f379342SAlexander V. Chernikov #define IPFW_TATFLAGS_AFDATA 0x0002 /* Separate data per AF */ 10045f379342SAlexander V. Chernikov #define IPFW_TATFLAGS_AFITEM 0x0004 /* diff. items per AF */ 1005914bffb6SAlexander V. Chernikov 10069f7d47b0SAlexander V. Chernikov typedef struct _ipfw_xtable_info { 1007c21034b7SAlexander V. Chernikov uint8_t type; /* table type (addr,iface,..) */ 1008914bffb6SAlexander V. Chernikov uint8_t tflags; /* type flags */ 1009adf3b2b9SAlexander V. Chernikov uint16_t mflags; /* modification flags */ 10104f43138aSAlexander V. Chernikov uint16_t flags; /* generic table flags */ 10110cba2b28SAlexander V. Chernikov uint16_t spare[3]; 10120cba2b28SAlexander V. Chernikov uint32_t vmask; /* bitmask with value types */ 10139f7d47b0SAlexander V. Chernikov uint32_t set; /* set table is in */ 10149f7d47b0SAlexander V. Chernikov uint32_t kidx; /* kernel index */ 10159f7d47b0SAlexander V. Chernikov uint32_t refcnt; /* number of references */ 10169f7d47b0SAlexander V. Chernikov uint32_t count; /* Number of records */ 1017914bffb6SAlexander V. Chernikov uint32_t size; /* Total size of records(export)*/ 10184c0c07a5SAlexander V. Chernikov uint32_t limit; /* Max number of records */ 10199f7d47b0SAlexander V. Chernikov char tablename[64]; /* table name */ 1020914bffb6SAlexander V. Chernikov char algoname[64]; /* algorithm name */ 10215f379342SAlexander V. Chernikov ipfw_ta_tinfo ta_info; /* additional algo stats */ 10229f7d47b0SAlexander V. Chernikov } ipfw_xtable_info; 10234f43138aSAlexander V. Chernikov /* Generic table flags */ 10244f43138aSAlexander V. Chernikov #define IPFW_TGFLAGS_LOCKED 0x01 /* Tables is locked from changes*/ 10254f43138aSAlexander V. Chernikov /* Table type-specific flags */ 1026914bffb6SAlexander V. Chernikov #define IPFW_TFFLAG_SRCIP 0x01 1027914bffb6SAlexander V. Chernikov #define IPFW_TFFLAG_DSTIP 0x02 1028914bffb6SAlexander V. Chernikov #define IPFW_TFFLAG_SRCPORT 0x04 1029914bffb6SAlexander V. Chernikov #define IPFW_TFFLAG_DSTPORT 0x08 1030914bffb6SAlexander V. Chernikov #define IPFW_TFFLAG_PROTO 0x10 10314f43138aSAlexander V. Chernikov /* Table modification flags */ 10324f43138aSAlexander V. Chernikov #define IPFW_TMFLAGS_LIMIT 0x0002 /* Change limit value */ 10334f43138aSAlexander V. Chernikov #define IPFW_TMFLAGS_LOCK 0x0004 /* Change table lock state */ 10349f7d47b0SAlexander V. Chernikov 103568394ec8SAlexander V. Chernikov typedef struct _ipfw_iface_info { 103668394ec8SAlexander V. Chernikov char ifname[64]; /* interface name */ 103768394ec8SAlexander V. Chernikov uint32_t ifindex; /* interface index */ 103868394ec8SAlexander V. Chernikov uint32_t flags; /* flags */ 103968394ec8SAlexander V. Chernikov uint32_t refcnt; /* number of references */ 104068394ec8SAlexander V. Chernikov uint32_t gencnt; /* number of changes */ 104168394ec8SAlexander V. Chernikov uint64_t spare; 104268394ec8SAlexander V. Chernikov } ipfw_iface_info; 104368394ec8SAlexander V. Chernikov #define IPFW_IFFLAG_RESOLVED 0x01 /* Interface exists */ 104468394ec8SAlexander V. Chernikov 10459d099b4fSAlexander V. Chernikov typedef struct _ipfw_ta_info { 1046914bffb6SAlexander V. Chernikov char algoname[64]; /* algorithm name */ 10479d099b4fSAlexander V. Chernikov uint32_t type; /* lookup type */ 10489d099b4fSAlexander V. Chernikov uint32_t flags; 10499d099b4fSAlexander V. Chernikov uint32_t refcnt; 10509d099b4fSAlexander V. Chernikov uint32_t spare0; 10519d099b4fSAlexander V. Chernikov uint64_t spare1; 10529d099b4fSAlexander V. Chernikov } ipfw_ta_info; 10539d099b4fSAlexander V. Chernikov 1054b074b7bbSAlexander V. Chernikov typedef struct _ipfw_obj_header { 1055b074b7bbSAlexander V. Chernikov ip_fw3_opheader opheader; /* IP_FW3 opcode */ 105681d3153dSAlexander V. Chernikov uint32_t spare; 1057b074b7bbSAlexander V. Chernikov uint16_t idx; /* object name index */ 10589f7d47b0SAlexander V. Chernikov uint8_t objtype; /* object type */ 10599f7d47b0SAlexander V. Chernikov uint8_t objsubtype; /* object subtype */ 10609f7d47b0SAlexander V. Chernikov ipfw_obj_ntlv ntlv; /* object name tlv */ 1061b074b7bbSAlexander V. Chernikov } ipfw_obj_header; 10629f7d47b0SAlexander V. Chernikov 10639f7d47b0SAlexander V. Chernikov typedef struct _ipfw_obj_lheader { 10649f7d47b0SAlexander V. Chernikov ip_fw3_opheader opheader; /* IP_FW3 opcode */ 1065ac35ff17SAlexander V. Chernikov uint32_t set_mask; /* disabled set mask */ 10669f7d47b0SAlexander V. Chernikov uint32_t count; /* Total objects count */ 106768394ec8SAlexander V. Chernikov uint32_t size; /* Total size (incl. header) */ 10689f7d47b0SAlexander V. Chernikov uint32_t objsize; /* Size of one object */ 10699f7d47b0SAlexander V. Chernikov } ipfw_obj_lheader; 1070b074b7bbSAlexander V. Chernikov 10717e767c79SAlexander V. Chernikov #define IPFW_CFG_GET_STATIC 0x01 10727e767c79SAlexander V. Chernikov #define IPFW_CFG_GET_STATES 0x02 10737e767c79SAlexander V. Chernikov #define IPFW_CFG_GET_COUNTERS 0x04 1074563b5ab1SAlexander V. Chernikov typedef struct _ipfw_cfg_lheader { 1075563b5ab1SAlexander V. Chernikov ip_fw3_opheader opheader; /* IP_FW3 opcode */ 1076ac35ff17SAlexander V. Chernikov uint32_t set_mask; /* enabled set mask */ 10777e767c79SAlexander V. Chernikov uint32_t spare; 1078563b5ab1SAlexander V. Chernikov uint32_t flags; /* Request flags */ 1079563b5ab1SAlexander V. Chernikov uint32_t size; /* neded buffer size */ 1080563b5ab1SAlexander V. Chernikov uint32_t start_rule; 1081563b5ab1SAlexander V. Chernikov uint32_t end_rule; 1082563b5ab1SAlexander V. Chernikov } ipfw_cfg_lheader; 1083563b5ab1SAlexander V. Chernikov 1084a73d728dSAlexander V. Chernikov typedef struct _ipfw_range_header { 1085a73d728dSAlexander V. Chernikov ip_fw3_opheader opheader; /* IP_FW3 opcode */ 1086a73d728dSAlexander V. Chernikov ipfw_range_tlv range; 1087a73d728dSAlexander V. Chernikov } ipfw_range_header; 1088a73d728dSAlexander V. Chernikov 1089be8bc457SAlexander V. Chernikov typedef struct _ipfw_sopt_info { 1090be8bc457SAlexander V. Chernikov uint16_t opcode; 1091be8bc457SAlexander V. Chernikov uint8_t version; 1092be8bc457SAlexander V. Chernikov uint8_t dir; 1093be8bc457SAlexander V. Chernikov uint8_t spare; 1094be8bc457SAlexander V. Chernikov uint64_t refcnt; 1095be8bc457SAlexander V. Chernikov } ipfw_sopt_info; 1096be8bc457SAlexander V. Chernikov 10979758b77fSLuigi Rizzo #endif /* _IPFW2_H */ 1098