firewall changes: - implement a REJECT policy and enable it by default, reject packet...
[openwrt/staging/dedeckeh.git] / package / firewall / files / uci_firewall.sh
1 #!/bin/sh
2 # Copyright (C) 2008 John Crispin <blogic@openwrt.org>
3
4 . /etc/functions.sh
5
6 IPTABLES="echo iptables"
7 IPTABLES=iptables
8
9 config_clear
10 include /lib/network
11 scan_interfaces
12
13 CONFIG_APPEND=1
14 config_load firewall
15
16 config fw_zones
17 ZONE_LIST=$CONFIG_SECTION
18
19 DEF_INPUT=DROP
20 DEF_OUTPUT=DROP
21 DEF_FORWARD=DROP
22
23 load_policy() {
24 config_get input $1 input
25 config_get output $1 output
26 config_get forward $1 forward
27
28 [ -z "$input" ] && input=$DEF_INPUT
29 [ -z "$output" ] && output=$DEF_OUTPUT
30 [ -z "$forward" ] && forward=$DEF_FORWARD
31 }
32
33 create_zone() {
34 local exists
35
36 [ "$1" == "loopback" ] && return
37
38 config_get exists $ZONE_LIST $1
39 [ -n "$exists" ] && return
40 config_set $ZONE_LIST $1 1
41
42 $IPTABLES -N zone_$1
43 $IPTABLES -N zone_$1_ACCEPT
44 $IPTABLES -N zone_$1_DROP
45 $IPTABLES -N zone_$1_REJECT
46 $IPTABLES -N zone_$1_forward
47 $IPTABLES -A zone_$1_forward -j zone_$1_$5
48 $IPTABLES -A zone_$1 -j zone_$1_$3
49 $IPTABLES -A output -j zone_$1_$4
50 $IPTABLES -N zone_$1_nat -t nat
51 $IPTABLES -N zone_$1_prerouting -t nat
52 [ "$6" == "1" ] && $IPTABLES -t nat -A POSTROUTING -j zone_$1_nat
53 }
54
55 addif() {
56 local dev
57 config_get dev core $2
58 [ -n "$dev" -a "$dev" != "$1" ] && delif "$dev" "$2"
59 [ -n "$dev" -a "$dev" == "$1" ] && return
60 logger "adding $1 to firewall zone $2"
61 $IPTABLES -A input -i $1 -j zone_$2
62 $IPTABLES -I zone_$2_ACCEPT 1 -o $1 -j ACCEPT
63 $IPTABLES -I zone_$2_DROP 1 -o $1 -j DROP
64 $IPTABLES -I zone_$2_REJECT 1 -o $1 -j reject
65 $IPTABLES -I zone_$2_ACCEPT 1 -i $1 -j ACCEPT
66 $IPTABLES -I zone_$2_DROP 1 -i $1 -j DROP
67 $IPTABLES -I zone_$2_REJECT 1 -i $1 -j reject
68 $IPTABLES -I zone_$2_nat 1 -t nat -o $1 -j MASQUERADE
69 $IPTABLES -I PREROUTING 1 -t nat -i $1 -j zone_$2_prerouting
70 $IPTABLES -A forward -i $1 -j zone_$2_forward
71 uci_set_state firewall core "$2" "$1"
72 }
73
74 delif() {
75 logger "removing $1 from firewall zone $2"
76 $IPTABLES -D input -i $1 -j zone_$2
77 $IPTABLES -D zone_$2_ACCEPT -o $1 -j ACCEPT
78 $IPTABLES -D zone_$2_DROP -o $1 -j DROP
79 $IPTABLES -D zone_$2_REJECT -o $1 -j reject
80 $IPTABLES -D zone_$2_ACCEPT -i $1 -j ACCEPT
81 $IPTABLES -D zone_$2_DROP -i $1 -j DROP
82 $IPTABLES -D zone_$2_REJECT -i $1 -j reject
83 $IPTABLES -D zone_$2_nat -t nat -o $1 -j MASQUERADE
84 $IPTABLES -D PREROUTING -t nat -i $1 -j zone_$2_prerouting
85 $IPTABLES -D forward -i $1 -j zone_$2_forward
86 uci_revert_state firewall core "$2"
87 }
88
89 load_synflood() {
90 local rate=${1:-25}
91 local burst=${2:-50}
92 echo "Loading synflood protection"
93 $IPTABLES -N syn_flood
94 $IPTABLES -A syn_flood -p tcp --syn -m limit --limit $rate/second --limit-burst $burst -j RETURN
95 $IPTABLES -A syn_flood -j DROP
96 $IPTABLES -A INPUT -p tcp --syn -j syn_flood
97 }
98
99 fw_set_chain_policy() {
100 local chain=$1
101 local target=$2
102 [ "$target" == "REJECT" ] && {
103 $IPTABLES -A $chain -j reject
104 target=DROP
105 }
106 $IPTABLES -P $chain $target
107 }
108
109 fw_defaults() {
110 load_policy $1
111 DEF_INPUT=$input
112 DEF_OUTPUT=$output
113 DEF_FORWARD=$forward
114
115 echo 1 > /proc/sys/net/ipv4/tcp_syncookies
116 for f in /proc/sys/net/ipv4/conf/*/accept_redirects
117 do
118 echo 0 > $f
119 done
120 for f in /proc/sys/net/ipv4/conf/*/accept_source_route
121 do
122 echo 0 > $f
123 done
124
125 uci_revert_state firewall core
126 uci_set_state firewall core "" firewall_state
127
128 $IPTABLES -P INPUT DROP
129 $IPTABLES -P OUTPUT DROP
130 $IPTABLES -P FORWARD DROP
131
132 $IPTABLES -F
133 $IPTABLES -t mangle -F
134 $IPTABLES -t nat -F
135 $IPTABLES -t mangle -X
136 $IPTABLES -t nat -X
137 $IPTABLES -X
138
139 $IPTABLES -A INPUT -m state --state INVALID -j DROP
140 $IPTABLES -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
141
142 $IPTABLES -A OUTPUT -m state --state INVALID -j DROP
143 $IPTABLES -A OUTPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
144
145 $IPTABLES -A FORWARD -m state --state INVALID -j DROP
146 $IPTABLES -A FORWARD -p tcp --tcp-flags SYN,RST SYN -j TCPMSS --clamp-mss-to-pmtu
147 $IPTABLES -A FORWARD -m state --state RELATED,ESTABLISHED -j ACCEPT
148
149 $IPTABLES -A INPUT -i lo -j ACCEPT
150 $IPTABLES -A OUTPUT -o lo -j ACCEPT
151
152 config_get syn_flood $1 syn_flood
153 config_get syn_rate $1 syn_rate
154 config_get syn_burst $1 syn_burst
155 [ "$syn_flood" == "1" ] && load_synflood $syn_rate $syn_burst
156
157 $IPTABLES -N input
158 $IPTABLES -N output
159 $IPTABLES -N forward
160
161 $IPTABLES -A INPUT -j input
162 $IPTABLES -A OUTPUT -j output
163 $IPTABLES -A FORWARD -j forward
164
165 $IPTABLES -N reject
166 $IPTABLES -A reject -p tcp -j REJECT --reject-with tcp-reset
167 $IPTABLES -A reject -j REJECT --reject-with icmp-port-unreachable
168 }
169
170 fw_zone() {
171 local name
172 local network
173 local masq
174
175 config_get name $1 name
176 config_get network $1 network
177 config_get masq $1 masq
178 load_policy $1
179
180 [ -z "$network" ] && network=$name
181 create_zone "$name" "$network" "$input" "$output" "$forward" "$masq"
182 }
183
184 fw_rule() {
185 local src
186 local src_ip
187 local src_mac
188 local src_port
189 local src_mac
190 local dest
191 local dest_ip
192 local dest_port
193 local proto
194 local target
195 local ruleset
196
197 config_get src $1 src
198 config_get src_ip $1 src_ip
199 config_get src_mac $1 src_mac
200 config_get src_port $1 src_port
201 config_get dest $1 dest
202 config_get dest_ip $1 dest_ip
203 config_get dest_port $1 dest_port
204 config_get proto $1 proto
205 config_get target $1 target
206 config_get ruleset $1 ruleset
207
208 [ -z "$target" ] && target=DROP
209 [ -n "$src" ] && ZONE=zone_$src || ZONE=input
210 [ -n "$dest" ] && TARGET=zone_${dest}_$target || TARGET=$target
211 add_rule() {
212 $IPTABLES -I $ZONE 1 \
213 ${proto:+-p $proto} \
214 ${src_ip:+-s $src_ip} \
215 ${src_port:+--sport $src_port} \
216 ${src_mac:+-m mac --mac-source $src_mac} \
217 ${dest_ip:+-d $dest_ip} \
218 ${dest_port:+--dport $dest_port} \
219 -j $TARGET
220 }
221 [ "$proto" == "tcpudp" -o -z "$proto" ] && {
222 proto=tcp
223 add_rule
224 proto=udp
225 add_rule
226 return
227 }
228 add_rule
229 }
230
231 fw_forwarding() {
232 local src
233 local dest
234 local masq
235
236 config_get src $1 src
237 config_get dest $1 dest
238 [ -n "$src" ] && z_src=zone_${src}_forward || z_src=forward
239 [ -n "$dest" ] && z_dest=zone_${dest}_ACCEPT || z_dest=ACCEPT
240 $IPTABLES -I $z_src 1 -j $z_dest
241 }
242
243 fw_redirect() {
244 local src
245 local src_ip
246 local src_port
247 local src_dport
248 local src_mac
249 local dest_ip
250 local dest_port dest_port2
251 local proto
252
253 config_get src $1 src
254 config_get src_ip $1 src_ip
255 config_get src_port $1 src_port
256 config_get src_dport $1 src_dport
257 config_get src_mac $1 src_mac
258 config_get dest_ip $1 dest_ip
259 config_get dest_port $1 dest_port
260 config_get proto $1 proto
261 [ -z "$src" -o -z "$dest_ip" ] && { \
262 echo "redirect needs src and dest_ip"; return ; }
263
264 src_port_first=${src_port%-*}
265 src_port_last=${src_port#*-}
266 [ "$src_port_first" -ne "$src_port_last" ] && { \
267 src_port="$src_port_first:$src_port_last"; }
268
269 src_dport_first=${src_dport%-*}
270 src_dport_last=${src_dport#*-}
271 [ "$src_dport_first" -ne "$src_dport_last" ] && { \
272 src_dport="$src_dport_first:$src_dport_last"; }
273
274 dest_port2=$dest_port
275 dest_port_first=${dest_port2%-*}
276 dest_port_last=${dest_port2#*-}
277 [ "$dest_port_first" -ne "$dest_port_last" ] && { \
278 dest_port2="$dest_port_first:$dest_port_last"; }
279
280 add_rule() {
281 $IPTABLES -A zone_${src}_prerouting -t nat \
282 ${proto:+-p $proto} \
283 ${src_ip:+-s $src_ip} \
284 ${src_port:+--sport $src_port} \
285 ${src_dport:+--dport $src_dport} \
286 ${src_mac:+-m mac --mac-source $src_mac} \
287 -j DNAT --to-destination $dest_ip${dest_port:+:$dest_port}
288
289 $IPTABLES -I zone_${src}_forward 1 \
290 ${proto:+-p $proto} \
291 -d $dest_ip \
292 ${src_ip:+-s $src_ip} \
293 ${src_port:+--sport $src_port} \
294 ${dest_port2:+--dport $dest_port2} \
295 ${src_mac:+-m mac --mac-source $src_mac} \
296 -j ACCEPT
297 }
298 [ "$proto" == "tcpudp" -o -z "$proto" ] && {
299 proto=tcp
300 add_rule
301 proto=udp
302 add_rule
303 return
304 }
305 add_rule
306 }
307
308 fw_include() {
309 local path
310 config_get path $1 path
311 [ -e $path ] && . $path
312 }
313
314 fw_addif() {
315 local up
316 local ifname
317 config_get up $1 up
318 config_get ifname $1 ifname
319 [ -n "$up" ] || return 0
320 (ACTION="ifup" INTERFACE="$1" . /etc/hotplug.d/iface/20-firewall)
321 }
322
323 fw_custom_chains() {
324 $IPTABLES -N input_rule
325 $IPTABLES -N output_rule
326 $IPTABLES -N forwarding_rule
327 $IPTABLES -N prerouting_rule -t nat
328 $IPTABLES -N postrouting_rule -t nat
329 $IPTABLES -N input_wan
330 $IPTABLES -N forwarding_wan
331 $IPTABLES -N prerouting_wan -t nat
332
333 $IPTABLES -A INPUT -j input_rule
334 $IPTABLES -A OUTPUT -j output_rule
335 $IPTABLES -A FORWARD -j forwarding_rule
336 $IPTABLES -A PREROUTING -t nat -j prerouting_rule
337 $IPTABLES -A POSTROUTING -t nat -j postrouting_rule
338 $IPTABLES -A zone_wan -j input_wan
339 $IPTABLES -A zone_wan_forward -j forwarding_wan
340 $IPTABLES -A zone_wan_prerouting -t nat -j prerouting_wan
341 }
342
343 fw_init() {
344 echo "Loading defaults"
345 config_foreach fw_defaults defaults
346 echo "Loading zones"
347 config_foreach fw_zone zone
348 echo "Loading rules"
349 config_foreach fw_rule rule
350 echo "Loading forwarding"
351 config_foreach fw_forwarding forwarding
352 echo "Loading redirects"
353 config_foreach fw_redirect redirect
354 echo "Adding custom chains"
355 fw_custom_chains
356 echo "Loading includes"
357 config_foreach fw_include include
358 uci_set_state firewall core loaded 1
359 unset CONFIG_APPEND
360 config_load network
361 config_foreach fw_addif interface
362 fw_set_chain_policy INPUT $input
363 fw_set_chain_policy OUTPUT $output
364 fw_set_chain_policy FORWARD $forward
365 }
366
367 fw_stop() {
368 $IPTABLES -F
369 $IPTABLES -t mangle -F
370 $IPTABLES -t nat -F
371 $IPTABLES -t mangle -X
372 $IPTABLES -t nat -X
373 $IPTABLES -X
374 $IPTABLES -P INPUT ACCEPT
375 $IPTABLES -P OUTPUT ACCEPT
376 $IPTABLES -P FORWARD ACCEPT
377 uci_revert_state firewall core
378 }