]> git.ipfire.org Git - people/ms/network.git/blob - functions.zone
Execute hooks faster by sourcing them.
[people/ms/network.git] / functions.zone
1 #!/bin/bash
2 ###############################################################################
3 # #
4 # IPFire.org - A linux based firewall #
5 # Copyright (C) 2010 Michael Tremer & Christian Schmidt #
6 # #
7 # This program is free software: you can redistribute it and/or modify #
8 # it under the terms of the GNU General Public License as published by #
9 # the Free Software Foundation, either version 3 of the License, or #
10 # (at your option) any later version. #
11 # #
12 # This program is distributed in the hope that it will be useful, #
13 # but WITHOUT ANY WARRANTY; without even the implied warranty of #
14 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the #
15 # GNU General Public License for more details. #
16 # #
17 # You should have received a copy of the GNU General Public License #
18 # along with this program. If not, see <http://www.gnu.org/licenses/>. #
19 # #
20 ###############################################################################
21
22 function zone_dir() {
23 local zone=${1}
24
25 echo "${NETWORK_ZONE_DIR}/zones/${zone}"
26 }
27
28 function zone_exists() {
29 local zone=${1}
30 assert isset zone
31
32 [ -d "$(zone_dir ${zone})" ]
33 }
34
35 function zone_match() {
36 local match
37
38 local i
39 for i in ${VALID_ZONES}; do
40 match="${match}|${i}[0-9]{1,5}"
41 done
42
43 echo "${match:1:${#match}}"
44 }
45
46 function zone_name_is_valid() {
47 local zone=${1}
48 assert isset zone
49
50 [[ ${zone} =~ $(zone_match) ]]
51 }
52
53 function zone_is_local() {
54 local zone=${1}
55
56 [[ "${zone:0:${#ZONE_LOCAL}}" = "${ZONE_LOCAL}" ]]
57 }
58
59 function zone_is_nonlocal() {
60 local zone=${1}
61
62 [[ "${zone:0:${#ZONE_NONLOCAL}}" = "${ZONE_NONLOCAL}" ]]
63 }
64
65 function zone_get_hook() {
66 local zone=${1}
67 assert isset zone
68
69 config_get_hook $(zone_dir ${zone})/settings
70 }
71
72 function zone_start() {
73 # This function will bring up the zone
74 # 'asynchronously' with help of systemd.
75
76 local zone=${1}
77 assert zone_exists ${zone}
78
79 service_start "network@${zone}"
80 }
81
82 function zone_stop() {
83 # This function will bring down the zone
84 # 'asynchronously' with help of systemd.
85
86 local zone=${1}
87 assert zone_exists ${zone}
88
89 service_stop "network@${zone}"
90 }
91
92 function zone_create() {
93 local zone=${1}
94 local hook=${2}
95 shift 2
96
97 if ! zone_name_is_valid ${zone}; then
98 error "Zone name '${zone}' is not valid."
99 return ${EXIT_ERROR}
100 fi
101
102 if zone_exists ${zone}; then
103 error "Zone '${zone}' does already exist."
104 return ${EXIT_ERROR}
105 fi
106
107 if ! hook_zone_exists ${hook}; then
108 error "Hook '${hook}' does not exist."
109 return ${EXIT_ERROR}
110 fi
111
112 mkdir -p $(zone_dir ${zone})
113
114 # Create directories for configs and ports
115 mkdir -p $(zone_dir ${zone})/{configs,ports}
116
117 hook_zone_exec ${hook} create ${zone} $@
118 local ret=$?
119
120 # Maybe the zone create hook did not exit correctly.
121 # If this is the case we remove the created zone immediately.
122 if [ "${ret}" = "${EXIT_ERROR}" ]; then
123 zone_remove_now ${zone}
124 fi
125 }
126
127 function zone_edit() {
128 local zone=${1}
129 shift
130
131 if ! zone_exists ${zone}; then
132 error "Zone '${zone}' does not exist."
133 return ${EXIT_ERROR}
134 fi
135
136 # Check if the zone is tagged for removal.
137 if zone_has_remove_tag ${zone}; then
138 error "You cannot edit a zone that is tagged for removal."
139 return ${EXIT_ERROR}
140 fi
141
142 local hook=$(config_get_hook $(zone_dir ${zone})/settings)
143
144 if [ -z "${hook}" ]; then
145 error "Config file did not provide any hook."
146 return ${EXIT_ERROR}
147 fi
148
149 if ! hook_zone_exists ${hook}; then
150 error "Hook '${hook}' does not exist."
151 return ${EXIT_ERROR}
152 fi
153
154 hook_zone_exec ${hook} edit ${zone} $@
155 }
156
157
158 function zone_remove() {
159 local zone=${1}
160 assert zone_exists ${zone}
161
162 # Make the zone for removal.
163 touch $(zone_dir ${zone})/.remove
164
165 log INFO "Zone '${zone}' has been tagged for removal."
166 }
167
168 function zone_has_remove_tag() {
169 local zone=${1}
170 assert zone_exists ${zone}
171
172 [ -e "$(zone_dir ${zone})/.remove" ]
173 }
174
175 # This function will remove the given zone
176 # RIGHT NOW. Use zone_remove to remove it
177 # at the next status change.
178 function zone_remove_now() {
179 local zone=${1}
180 assert zone_exists ${zone}
181
182 log INFO "Removing zone '${zone}' right now."
183
184 # Force the zone down.
185 zone_is_up ${zone} && zone_set_down ${zone}
186
187 rm -rf $(zone_dir ${zone})
188 }
189
190 function zone_up() {
191 local zone=${1}
192 shift
193
194 if ! zone_exists ${zone}; then
195 error "Zone '${zone}' does not exist."
196 return ${EXIT_ERROR}
197 fi
198
199 # Check if a zone has got the remove tag.
200 if zone_has_remove_tag ${zone}; then
201 error "Cannot bring up any zone which is to be removed."
202 return ${EXIT_ERROR}
203 fi
204
205 local hook=$(config_get_hook $(zone_dir ${zone})/settings)
206
207 if [ -z "${hook}" ]; then
208 error "Config file did not provide any hook."
209 return ${EXIT_ERROR}
210 fi
211
212 if ! hook_zone_exists ${hook}; then
213 error "Hook '${hook}' does not exist."
214 return ${EXIT_ERROR}
215 fi
216
217 zone_db ${zone} starting
218
219 hook_zone_exec ${hook} up ${zone} $@
220
221 zone_db ${zone} started
222 }
223
224 function zone_down() {
225 local zone=${1}
226 shift
227
228 if ! zone_exists ${zone}; then
229 error "Zone '${zone}' does not exist."
230 return ${EXIT_ERROR}
231 fi
232
233 local hook=$(config_get_hook $(zone_dir ${zone})/settings)
234
235 if [ -z "${hook}" ]; then
236 error "Config file did not provide any hook."
237 return ${EXIT_ERROR}
238 fi
239
240 if ! hook_zone_exists ${hook}; then
241 error "Hook '${hook}' does not exist."
242 return ${EXIT_ERROR}
243 fi
244
245 zone_db ${zone} stopping
246
247 hook_zone_exec ${hook} down ${zone} $@
248
249 zone_db ${zone} stopped
250
251 # Remove the zone, if it has got a remove tag.
252 if zone_has_remove_tag ${zone}; then
253 zone_remove_now ${zone}
254 fi
255 }
256
257 function zone_status() {
258 local zone=${1}
259 shift
260
261 if ! zone_exists ${zone}; then
262 error "Zone '${zone}' does not exist."
263 return ${EXIT_ERROR}
264 fi
265
266 local hook=$(config_get_hook $(zone_dir ${zone})/settings)
267
268 if [ -z "${hook}" ]; then
269 error "Config file did not provide any hook."
270 return ${EXIT_ERROR}
271 fi
272
273 if ! hook_zone_exists ${hook}; then
274 error "Hook '${hook}' does not exist."
275 return ${EXIT_ERROR}
276 fi
277
278 hook_zone_exec ${hook} status ${zone} $@
279
280 # Show that the zone it to be removed soon.
281 if zone_has_remove_tag ${zone}; then
282 warning "This zone is tagged for removal."
283 fi
284 }
285
286 function zone_port() {
287 local zone=${1}
288 local action=${2}
289 shift 2
290
291 assert isset zone
292 assert isset action
293 assert zone_exists ${zone}
294
295 # Aliases
296 case "${action}" in
297 del|delete|remove)
298 action="rem"
299 ;;
300 esac
301
302 case "${action}" in
303 add|edit|rem)
304 zone_port_${action} ${zone} $@
305 ;;
306 *)
307 error "Unrecognized argument: ${action}"
308 cli_usage root-zone-port-subcommands
309 exit ${EXIT_ERROR}
310 ;;
311 esac
312 }
313
314 function zone_port_add() {
315 local zone=${1}
316 shift
317
318 assert isset zone
319
320 local hook=$(zone_get_hook ${zone})
321
322 assert isset hook
323
324 hook_zone_exec ${hook} port_add ${zone} $@
325 }
326
327 function zone_port_edit() {
328 zone_port_cmd edit $@
329 }
330
331 function zone_port_rem() {
332 zone_port_cmd rem $@
333 }
334
335 function zone_port_cmd() {
336 local cmd=${1}
337 local zone=${2}
338 local port=${3}
339 shift 3
340
341 assert isset zone
342 assert isset port
343
344 local hook_zone=$(zone_get_hook ${zone})
345 local hook_port=$(port_get_hook ${port})
346
347 assert isset hook_zone
348 assert isset hook_port
349
350 hook_zone_port_exec ${hook_zone} ${hook_port} ${cmd} ${zone} ${port} $@
351 }
352
353 function zone_port_up() {
354 zone_port_cmd up $@
355 }
356
357 function zone_port_down() {
358 zone_port_cmd down $@
359 }
360
361 function zone_get_ports() {
362 local zone=${1}
363
364 assert isset zone
365
366 local port
367 for port in $(zone_dir ${zone})/ports/*; do
368 port=$(basename ${port})
369
370 if port_exists ${port}; then
371 echo "${port}"
372 fi
373 done
374 }
375
376 function zone_has_port() {
377 # Check, if the given port is configured
378 # in this zone.
379
380 local zone=${1}
381 local port=${2}
382 shift 2
383
384 assert isset zone
385 assert isset port
386
387 [ -e "$(zone_dir ${zone})/ports/${port}" ]
388 }
389
390 # XXX overwritten some lines below
391 function zone_config() {
392 local zone=${1}
393 shift
394
395 if ! zone_exists ${zone}; then
396 error "Zone '${zone}' does not exist."
397 return ${EXIT_ERROR}
398 fi
399
400 local hook=$(config_get_hook $(zone_dir ${zone})/settings)
401
402 if [ -z "${hook}" ]; then
403 error "Config file did not provide any hook."
404 return ${EXIT_ERROR}
405 fi
406
407 if ! hook_zone_exists ${hook}; then
408 error "Hook '${hook}' does not exist."
409 return ${EXIT_ERROR}
410 fi
411
412 hook_zone_exec ${hook} config ${zone} $@
413 }
414
415 function zone_config() {
416 local zone=${1}
417 local action=${2}
418 shift 2
419
420 assert isset zone
421 assert isset action
422 assert zone_exists ${zone}
423
424 # Aliases
425 case "${action}" in
426 del|delete|remove)
427 action="rem"
428 ;;
429 esac
430
431 case "${action}" in
432 create|edit|rem)
433 zone_config_${action} ${zone} $@
434 ;;
435 *)
436 error "Unrecognized argument: ${action}"
437 cli_usage root-zone-config-subcommands
438 exit ${EXIT_ERROR}
439 ;;
440 esac
441 }
442
443 function zone_config_option() {
444 local zone=${1}
445 local option=${2}
446 local default=${3}
447 shift 2
448
449 assert isset zone
450 assert isset option
451
452 (
453 VALUE="${default}"
454 zone_config_read ${zone}
455
456 VALUE="${!option}"
457 echo "${VALUE}"
458 )
459 }
460
461 function zone_config_create() {
462 local zone=${1}
463 shift
464
465 assert isset zone
466
467 local hook=$(zone_get_hook ${zone})
468
469 assert isset hook
470
471 hook_zone_exec ${hook} config_create ${zone} $@
472 }
473
474 function zone_show() {
475 local zone=${1}
476
477 echo "${zone}"
478 echo " Type: $(zone_get_hook ${zone})"
479 echo
480 }
481
482 function zones_show() {
483 local zone
484
485 for zone in $(zones_get $@); do
486 zone_show ${zone}
487 done
488 }
489
490 function zones_get_all() {
491 local zone
492 for zone in $(zone_dir)/*; do
493 zone=$(basename ${zone})
494 zone_exists ${zone} || continue
495
496 echo "${zone}"
497 done
498 }
499
500 function zones_get_local() {
501 local zone
502 for zone in $(zones_get_all); do
503 zone_is_local ${zone} && echo "${zone}"
504 done
505 }
506
507 function zones_get_nonlocal() {
508 local zone
509 for zone in $(zones_get_all); do
510 zone_is_nonlocal ${zone} && echo "${zone}"
511 done
512 }
513
514 function zones_get() {
515 local local=1
516 local remote=1
517
518 local zones
519
520 while [ $# -gt 0 ]; do
521 case "${1}" in
522 --local-only)
523 local=1
524 remote=0
525 ;;
526 --remote-only)
527 local=0
528 remote=1
529 ;;
530 --all)
531 local=1
532 remote=1
533 ;;
534 *)
535 if zone_name_is_valid ${1}; then
536 zones="${zones} ${1}"
537 else
538 warning "Unrecognized argument '${1}'"
539 fi
540 ;;
541 esac
542 shift
543 done
544
545 if [ -n "${zones}" ]; then
546 local zone
547 for zone in ${zones}; do
548 zone_exists ${zone} && echo "${zone}"
549 done
550 exit ${EXIT_OK}
551 fi
552
553 if [ ${local} -eq 1 ] && [ ${remote} -eq 1 ]; then
554 zones_get_all
555 elif [ ${local} -eq 1 ]; then
556 zones_get_local
557 elif [ ${remote} -eq 1 ]; then
558 zones_get_nonlocal
559 fi
560 }
561
562 function zone_ports_list() {
563 local zone=${1}
564
565 local port
566 for port in $(zone_dir ${zone})/ports/*; do
567 [ -e "${port}" ] || continue
568
569 echo $(basename ${port})
570 done
571 }
572
573 function zone_ports_cmd() {
574 local cmd=${1}
575 local zone=${2}
576 shift 2
577
578 assert isset cmd
579 assert isset zone
580
581 assert zone_exists ${zone}
582
583 local hook=$(zone_get_hook ${zone})
584
585 local port
586 for port in $(zone_get_ports ${zone}); do
587 hook_zone_exec ${hook} ${cmd} ${zone} ${port} $@
588 done
589 }
590
591 function zone_ports_up() {
592 zone_ports_cmd port_up $@
593 }
594
595 function zone_ports_down() {
596 zone_ports_cmd port_down $@
597 }
598
599 function zone_ports_status() {
600 zone_ports_cmd port_status $@
601 }
602
603 function zone_configs_list() {
604 local zone=${1}
605
606 local config
607 for config in $(zone_dir ${zone})/configs/*; do
608 [ -e "${config}" ] || continue
609
610 basename ${config}
611 done
612 }
613
614 function zone_configs_cmd() {
615 local cmd=${1}
616 local zone=${2}
617 shift 2
618
619 local hook_zone=$(config_get_hook $(zone_dir ${zone})/settings)
620
621 local hook_config
622 local config
623 for config in $(zone_configs_list ${zone}); do
624 hook_config=$(config_get_hook $(zone_dir ${zone})/configs/${config})
625
626 hook_zone_config_exec ${hook_zone} ${hook_config} ${cmd} ${zone} ${config} $@
627 done
628 }
629
630 function zone_configs_up() {
631 zone_configs_cmd up $@
632 }
633
634 function zone_configs_down() {
635 zone_configs_cmd down $@
636 }
637
638 function zone_configs_status() {
639 zone_configs_cmd config_status $@
640 }
641
642 function zone_has_ip() {
643 device_has_ip $@
644 }
645
646 function zone_db() {
647 local zone=${1}
648 local action=${2}
649 shift 2
650
651 case "${action}" in
652 starting|started|stopping|stopped)
653 db_connection_update ${zone} ${action}
654 ;;
655 esac
656 }
657
658 function zone_is_up() {
659 local zone=${1}
660
661 device_is_up ${zone}
662 }
663
664 function zone_is_down() {
665 ! zone_is_up $@
666 }
667
668 function zone_get_supported_port_hooks() {
669 local zone=${1}
670
671 local hook=$(zone_get_hook ${zone})
672
673 hook_zone_ports_get_all ${hook}
674 }
675
676 function zone_get_supported_config_hooks() {
677 local zone=${1}
678
679 local hook=$(zone_get_hook ${zone})
680
681 hook_zone_configs_get_all ${hook}
682 }
683
684 function zone_file() {
685 local zone=${1}
686
687 assert isset zone
688
689 echo "$(zone_dir ${zone})/settings"
690 }
691
692 function zone_config_read() {
693 local zone=${1}
694
695 assert isset zone
696
697 config_read $(zone_file ${zone})
698 }
699
700 function zone_config_write() {
701 local zone=${1}
702
703 assert isset zone
704
705 config_write $(zone_file ${zone}) ${HOOK_SETTINGS}
706 }
707
708 function zone_config_set() {
709 local zone=${1}
710 shift
711 local args="$@"
712
713 assert isset zone
714
715 (
716 zone_config_read ${zone}
717
718 for arg in ${args}; do
719 eval "${arg}"
720 done
721
722 zone_config_write ${zone}
723 )
724 }
725
726 function zone_config_get() {
727 local zone=${1}
728 local key=${2}
729
730 assert isset zone
731 assert isset key
732
733 (
734 zone_config_read ${zone}
735
736 echo "${!key}"
737 )
738 }