firehol-params(5)

πŸ“¦
version 3.1.8 Β· 4 versions
, in debian trixie, ubuntu resolute, ubuntu stonking

πŸŽ€ firehol-params πŸŽ€

okay bestie, gather round, because this one is long and it's literally the master list of optional rule parameters. this is the manual page for firehol-params, living in section 5 of the manual, and it's coming at you from FireHOL 3.1.8. πŸ’–


✨ NAME ✨

firehol-params β€” optional rule parameters


🌸 SYNOPSIS 🌸

Common

{ src | src4 | src6 } [not] host

{ dst | dst4 | dst6 } [not] host

srctype [not] type

dsttype [not] type

proto [not] protocol

mac [not] macaddr

dscp [not] value class classid

mark [not] id

connmark [not] id

custommark [not] name id

rawmark [not] id

tos [not] id

custom β€œiptables-options...”

custom-in β€œiptables-options...”

custom-out β€œiptables-options...”

Router Only

inface [not] interface

outface [not] interface

physin [not] interface

physout [not] interface

Interface Only

uid [not] user

gid [not] group

Logging

connlog β€œlog text”

log β€œlog text” [level loglevel]

loglimit β€œlog text” [level loglevel]

Helpers Only

sport port

dport port

state state

ipset [not] name flags [no-counters]
[bytes-lt|bytes-eq|bytes-gt|bytes-not-eq number]
[packets-lt|packets-eq|packets-gt|packets-not-eq number] [options
custom-ipset-options]

limit limit burst

connlimit upto|above limit [mask mask] [saddr|daddr]

hashlimit name upto|above amount/period [burst amount] [mode
{srcip|srcport|dstip|dstport},...]  [srcmask prefix] [dstmask prefix]
[htable-size buckets] [htable-max entries] [htable-expire msec]
[htable-gcinterval msec]

πŸ¦‹ DESCRIPTION πŸ¦‹

okay so optional rule parameters are the little extra vibes you can tack onto a bunch of commands to narrow down exactly what they match. the key word is optional, and also not universal β€” not every command accepts every parameter, so please, for the love of everything, check the individual command you're using to see what it does and doesn't allow. πŸ™ˆ

every single match here is made against the REQUEST. FireHOL is out here being the responsible friend who automatically sets up the stateful rules needed to handle the replies in the reverse direction, so you don't have to. πŸ’…

for a statement to actually execute, all the matches have to be true. but plot twist β€” lots of these matches take multiple values, and in that case at least one of the values has to match. it's giving "everyone has to show up, but only one of you needs to bring the snacks".

example time, bestie:

server smtp accept src 1.1.1.1 dst 2.2.2.2

in that one above, every smtp request coming in from 1.1.1.1 and heading out to the smtp server 2.2.2.2 gets matched. iconic.

server smtp accept src 1.1.1.1 dst 2.2.2.2,3.3.3.3

and in that one, every smtp request coming in from 1.1.1.1 and going out to either smtp server 2.2.2.2 or 3.3.3.3 gets matched. see? one value matching is enough. 🫢

use the keyword not to match literally any value other than the one(s) you specified. no cap.

now, the logging parameters are the weird ones in the group chat β€” they do not affect the match at all. they just make a log message pop off. so obviously, since there's nothing to match, the logging parameters don't support the not option. makes sense, right? 😭

one more thing, and it's important: FireHOL is built so that if you specify a parameter that's also used internally by the command, it'll throw a warning at you β€” and then it uses the internal version anyway. so like, listen to the warning. ⭐


πŸ’– COMMON πŸ’–

src, dst

use src and dst to define the source and destination IP addresses of the request, respectively. host is where you put the IP or IPs you want matched. ✨

host can also point at an ipset, using this syntax: ipset:NAME, where NAME is the name of the ipset. heads up though β€” that ipset has to be of type hash:ip for this match to work. the source IP or the destination IP gets used for the match, depending on whether the ipset is given as src or dst.

and yes, you can absolutely mix IPs and ipsets together, like this:

src 1.1.1.1,ipset:NAME1,2.2.2.2,ipset:NAME2

examples, because examples are everything:

server4 smtp accept src not 192.0.2.1
server4 smtp accept dst 198.51.100.1
server4 smtp accept src not 192.0.2.1 dst 198.51.100.1
server6 smtp accept src not 2001:DB8:1::/64
server6 smtp accept dst 2001:DB8:2::/64
server6 smtp accept src not 2001:DB8:1::/64 dst 2001:DB8:2::/64

when you're trying to write rules for both IPv4 and IPv6, it's generally way easier to use the src4, src6, dst4 and dst6 pairs:

server46 smtp accept src4 192.0.2.1 src6 2001:DB8:1::/64
server46 smtp accept dst4 198.51.100.1 dst6 2001:DB8:2::/64
server46 smtp accept dst4 $d4 dst6 $d6 src4 not $d4 src6 not $s6
to keep the rules sane, if one of the 4/6 pair specifies not, then the other one has to as well. they're a package deal, fr fr.

and if you don't want to use both IPv4 and IPv6 addresses, you have to specify the rule as IPv4-only or IPv6-only. it's always possible to just write a second IPv4 or IPv6 only rule, so don't stress. πŸ’œ

srctype, dsttype

use srctype or dsttype to define the source or destination IP address type of the request. type is the address type category, the same one used in the kernel's network stack. it can be one of:

  • UNSPEC β€” an unspecified address (i.e. 0.0.0.0)
  • UNICAST β€” a unicast address
  • LOCAL β€” a local address
  • BROADCAST β€” a broadcast address
  • ANYCAST β€” an anycast address
  • MULTICAST β€” a multicast address
  • BLACKHOLE β€” a blackhole address
  • UNREACHABLE β€” an unreachable address
  • PROHIBIT β€” a prohibited address
  • THROW; NAT; XRESOLVE β€” undocumented πŸ‘€

see iptables(8) or run iptables -m addrtype --help for more info. and here's an example:

server smtp accept srctype not "UNREACHABLE PROHIBIT"

proto

use proto to match by protocol. the protocol can be any of the ones accepted by iptables(8). simple as that. πŸ¦‹

mac

use mac to match by MAC address. the macaddr matches against the β€œremote” host. in an interface, β€œremote” always means the non-local host. in a router, β€œremote” refers to the source of requests for servers β€” and it refers to the destination of requests for clients. examples:

# Only allow pop3 requests to the e6 host
client pop3 accept mac 00:01:01:00:00:e6

# Only allow hosts other than e7/e8 to access smtp
server smtp accept mac not "00:01:01:00:00:e7 00:01:01:00:00:e8"

dscp

use dscp to match the DSCP field on packets. for all the deets on DSCP values and classids, go peek at firehol-dscp(5). πŸ“š

server smtp accept dscp not "0x20 0x30"
server smtp accept dscp not class "BE EF"

mark

use mark to match marks set on packets. for details on mark ids, see firehol-mark(5).

server smtp accept mark not "20 55"

tos

use tos to match the TOS field on packets. for details on TOS ids, see firehol-tos(5).

server smtp accept tos not "Maximize-Throughput 0x10"

custom

use custom to pass arguments directly to iptables(8). all of the parameters have to live in a single quoted string. and if you want to pass an option to iptables(8) that itself contains a space, you need to quote strings the usual bash(1) way. like this:

server smtp accept custom "--some-option some-value"
server smtp accept custom "--some-option 'some-value second-value'"

🌈 ROUTER ONLY 🌈

inface, outface

use inface and outface to define the interface via which a request is received and forwarded, respectively. use the same format as firehol-interface(5). examples:

server smtp accept inface not eth0
server smtp accept inface not "eth0 eth1"
server smtp accept inface eth0 outface eth1

physin, physout

use physin and physout to define the physical interface via which a request is received or sent, in cases where the inface or outface is known to be a virtual interface β€” e.g. a bridge. use the same format as firehol-interface(5). example:

server smtp accept physin not eth0

🧚 INTERFACE ONLY 🧚

these parameters match information related to information gathered from the local host. they apply only to outgoing packets, and they're silently ignored for incoming requests and for requests that will be forwarded. πŸ™ˆ

Note the Linux kernel infrastructure that matched PID/SID and executable names with pid, sid and cmd has been removed, so those options can no longer be used. rip to them, they're gone gone. πŸ’€

uid

use uid to match the operating system user sending the traffic. the user is a username, a uid number, or a quoted list of the two.

for example, to limit which users can access POP3 and IMAP by preventing replies for certain users from being sent:

client "pop3 imap" accept user not "user1 user2 user3"

similarly, this one will allow all requests to reach the server but prevent replies unless the web server is running as apache:

server http accept user apache

gid

use gid to match the operating system group sending the traffic. the group is a group name, a gid number, or a quoted list of the two. same energy as uid, just for groups. πŸ‘‘


πŸŽ€ LOGGING πŸŽ€

connlog

use connlog to log only the first packet of a connection. not the whole saga β€” just the opening scene. πŸ’…

log, loglimit

use log or loglimit to log matching packets to syslog. and here's the thing that trips people up: unlike iptables(8) logging, this is not an action. FireHOL will produce multiple iptables(8) commands to accomplish both the action for the rule and the logging. it's doing the most so you don't have to. ✨

logging is controlled using the FIREHOL_LOG_OPTIONS and FIREHOL_LOG_LEVEL environment variables β€” go read firehol-defaults.conf(5) for that. loglimit additionally honours the FIREHOL_LOG_FREQUENCY and FIREHOL_LOG_BURST variables. πŸ“

specifying level (which takes the same values as FIREHOL_LOG_LEVEL) lets you override the log level for a single rule. one rule, one vibe. 😌

πŸ¦‹ HELPERS ONLY PARAMETERS πŸ¦‹

okay so this whole section is the backstage pass πŸ’… β€” these are the params FireHOL uses under the hood, and honestly you'll rarely need them in your config files. but bestie, when you DO need them? iconic.

πŸ’« dport, sport

ngl, FireHOL also ships dport, sport and limit, which get used internally and are rarely needed inside configuration files. like, they're the crew, not the main characters. but they slay when called upon.

dport and sport both require an argument port, which can be:

  • a name
  • a number
  • a range (FROM:TO)
  • a quoted list of ports

For dport, port specifies the destination port of a request, and it's lowkey useful when you're matching traffic to helper commands (such as nat) where there's no implicit port. 🎯

For sport, port specifies the source port of a request, and it's highkey useful when you're matching traffic to helper commands (such as nat) where there's no implicit port. πŸ’Œ


πŸ’« limit

limit requires the arguments frequency and burst, and it will limit the matching of traffic in both directions. both ways, no cap. πŸ”„


πŸ’« connlimit

connlimit matches on the number of connections per IP. it's been part of FireHOL since v3. πŸ‘‘

here's the breakdown, bestie:

  • saddr matches on source IP.
  • daddr matches on destination IP.
  • mask groups IPs with the mask given.
  • upto matches when the number of connections is up to the given limit.
  • above matches when the number of connections is above the given limit.
⚠️ okay this next bit is the important part, do NOT skip it ⚠️

The number of connections counted are system wide, not service specific. for example, for saddr, you cannot connlimit 2 connections for SSH and 4 for SMTP. if you connlimit 2 connections for SSH, then the first 2 connections of a client can be SSH. but if a client already has 2 connections to another service, the client will not be able to connect to SSH. it's giving shared budget, and the budget is SHARED. 😭

So, connlimit can safely be used:

  • with daddr to limit the connections a server can accept
  • with saddr to limit the total connections per client to all services

πŸ’« hashlimit

hashlimit has been added to FireHOL since v3. ✨

hashlimit uses hash buckets to express a rate limiting match (like the limit match) for a group of connections using a single iptables rule. grouping can be done per-hostgroup (source and/or destination address) and/or per-port. it gives you the ability to express β€œN packets per time quantum per group” or β€œN bytes per seconds” (see below for some examples). obsessed, honestly. 🫢

A hash limit type (upto, above) and a name are required. no exceptions, periodt.

🌸 the params

  • name β€” the name for the /proc/net/ipt_hashlimit/name entry.
  • upto amount[/second|/minute|/hour|/day] β€” match if the rate is below or equal to amount/quantum. it's specified either as a number, with an optional time quantum suffix (the default is 3/hour), or as amountb/second (number of bytes per second).
  • above amount[/second|/minute|/hour|/day] β€” match if the rate is above amount/quantum.
  • burst amount β€” maximum initial number of packets to match: this number gets recharged by one every time the limit specified above is not reached, up to this number; the default is 5. when byte-based rate matching is requested, this option specifies the amount of bytes that can exceed the given rate.
🚨 use burst with caution β€” if the entry expires, the burst value is reset too. so it's giving volatile, bestie. handle with care. 🚨
  • mode {srcip|srcport|dstip|dstport},... β€” a comma-separated list of objects to take into consideration. if no mode option is given, srcip,dstport is assumed.
  • srcmask prefix β€” when --hashlimit-mode srcip is used, all source addresses encountered will be grouped according to the given prefix length and the so-created subnet will be subject to hashlimit. prefix must be between (inclusive) 0 and 32. note that srcmask 0 is basically doing the same thing as not specifying srcip for mode, but is technically more expensive. πŸ’Έ
  • dstmask prefix β€” like srcmask, but for destination addresses.
  • htable-size buckets β€” the number of buckets of the hash table.
  • htable-max entries β€” maximum entries in the hash.
  • htable-expire msec β€” after how many milliseconds do hash entries expire.
  • htable-gcinterval msec β€” how many milliseconds between garbage collection intervals.

πŸŽ€ examples (these EAT)

matching on source host: β€œ1000 packets per second for every host in 192.168.0.0/16”

src 192.168.0.0/16 hashlimit mylimit mode srcip upto 1000/sec

matching on source port: β€œ100 packets per second for every service of 192.168.1.1”

src 192.168.1.1 hashlimit mylimit mode srcport upto 100/sec

matching on subnet: β€œ10000 packets per minute for every /28 subnet (groups of 8 addresses) in 10.0.0.0/8”

src 10.0.0.8 hashlimit mylimit mask 28 upto 10000/min

matching bytes per second: β€œflows exceeding 512kbyte/s”

hashlimit mylimit mode srcip,dstip,srcport,dstport above 512kb/s

matching bytes per second: β€œhosts that exceed 512kbyte/s, but permit up to 1Megabytes without matching”

hashlimit mylimit mode dstip above 512kb/s burst 1mb

🌈 SEE ALSO 🌈

go read these too, bestie, they're all part of the lore:


πŸ‘‘ AUTHORS πŸ‘‘

FireHOL Team. πŸ’– that's the whole squad. no notes.


and that's a wrap on firehol-params(5) bestie!! this was the FireHOL Reference, built 13 Apr 2025 β€” go forth and configure your firewall like the main character you are. slay responsibly, and remember: the facts never changed, only the vibe. πŸ’…βœ¨πŸ¦‹πŸŽ€πŸŒΈπŸ’œ

πŸ“¦ where this page comes from