Opennet Firmware
olsr.sh
gehe zur Dokumentation dieser Datei
1 ## @defgroup olsr OLSR
2 ## @brief Konfiguration und Abfrage des OLSR-Diensts. Einlesen von Diensten announciert via olsrd-nameservice.
3 # Beginn der Doku-Gruppe
4 ## @{
5 
6 # shellcheck disable=SC2034
7 OLSR_NAMESERVICE_SERVICE_TRIGGER=/usr/sbin/on_nameservice_trigger
8 SERVICES_FILE=/var/run/services_olsr
9 # shellcheck disable=SC2034
10 OLSR_HTTP_PORT=8080
11 OLSR_UPDATE_LOCK_FILE=/var/run/on-update-olsr-interfaces.lock
12 
13 
14 # uebertrage die Netzwerke, die derzeit der Zone "opennet" zugeordnet sind, in die olsr-Konfiguration
15 # Anschliessend wird olsr und die firewall neugestartet.
16 # Dieses Skript sollte via hotplug bei Aenderungen der Netzwerkkonfiguration ausgefuehrt werden.
17 # Fuer jedes Interface wird eine separate UCI-Sektion angelegt.
19  trap 'error_trap update_olsr_interfaces "$*"' EXIT
20  local uci_prefix
21  local interfaces
22  local current
23  interfaces="$(get_zone_interfaces "$ZONE_MESH") $(get_zone_raw_devices "$ZONE_MESH")"
24  for uci_prefix in $(find_all_uci_sections "olsrd" "Interface"); do
25  current=$(uci_get "${uci_prefix}.interface")
26  if echo "$interfaces" | grep -qFw "$current"; then
27  # OLSR fuer das Interface aktivieren
28  uci set "${uci_prefix}.ignore=0"
29  else
30  # Interfaces entfernen, die nicht mehr in der on-Zone sind
31  uci_delete "$uci_prefix"
32  fi
33  done
34  # alle fehlenden Interfaces neu anlegen
35  for current in $interfaces; do
36  uci_prefix=$(find_first_uci_section "olsrd" "Interface" "interface=$current")
37  # existiert es bereits? Dann wurde es oben konfiguriert.
38  [ -n "$uci_prefix" ] && continue
39  uci_prefix="olsrd.$(uci add olsrd Interface)"
40  uci set "${uci_prefix}.interface=$current"
41  uci set "${uci_prefix}.ignore=0"
42  done
43  # prevent recursive trigger chaining
44  if acquire_lock "$OLSR_UPDATE_LOCK_FILE" 5 5; then
46  update_opennet_zone_masquerading
47  apply_changes olsrd
48  rm -f "$OLSR_UPDATE_LOCK_FILE"
49  fi
50 }
51 
52 
53 # Pruefe das angegebene olsrd-Plugin aktiv ist und aktiviere es, falls dies nicht der Fall sein sollte.
54 # Das Ergebnis ist die uci-Sektion (z.B. "olsrd.@LoadPlugin[1]") als String.
55 get_and_enable_olsrd_library_uci_prefix() {
56  trap 'error_trap get_and_enable_olsrd_library_uci_prefix "$*"' EXIT
57  local lib_file
58  local uci_prefix=
59  local library="olsrd_$1"
60  local current
61  current=$(for uci_prefix in $(find_all_uci_sections olsrd LoadPlugin); do
62  # die Bibliothek beginnt mit dem Namen - danach folgt die genaue Versionsnummer
63  uci_get "${uci_prefix}.library" | grep -q "^$library"'\.so' && echo "$uci_prefix"
64  true
65  done | tail -1)
66  if [ -n "$current" ]; then
67  uci_prefix=$(echo "$current" | cut -f 1 -d = | sed 's/\.library$//')
68  else
69  lib_file=$(find /usr/lib -type f -name "${library}.*")
70  if [ -z "$lib_file" ]; then
71  msg_error "Failed to find olsrd '$library' plugin. Some Opennet services will fail."
72  trap "" EXIT && return 1
73  fi
74  uci_prefix="olsrd.$(uci add olsrd LoadPlugin)"
75  uci set "${uci_prefix}.library=$(basename "$lib_file")"
76  fi
77  # Plugin aktivieren; Praefix ausgeben
78  if [ -n "$uci_prefix" ]; then
79  # moeglicherweise vorhandenen 'ignore'-Parameter abschalten
80  uci_is_true "$(uci_get "${uci_prefix}.ignore" 0)" && uci set "${uci_prefix}.ignore=0"
81  echo "$uci_prefix"
82  fi
83  return 0
84 }
85 
86 
87 # Setze die Einstellung MainIP in der olsr-Konfiguration:
88 # Quelle 1: der erste Parameter
89 # Quelle 2: on-core.settings.on_id
90 # Quelle 3: die vorkonfigurierte Standard-IP
91 # Anschliessend ist "apply_changes olsrd" erforderlich.
92 olsr_set_main_ip() {
93  trap 'error_trap olsr_set_main_ip "$*"' EXIT
94  # Auslesen der aktuellen, bzw. der Standard-IP
95  local main_ip
96  if [ $# -eq 1 ]; then
97  main_ip="$1"
98  else
99  main_ip=$(get_main_ip)
100  fi
101 
102  # die Main-IP ist die erste IP dieses Geraets
103  uci set "olsrd.@olsrd[0].MainIp=$main_ip"
104 }
105 
106 
107 # Ermittle welche olsr-Module konfiguriert sind, ohne dass die Library vorhanden ist.
108 # Deaktiviere diese Module - fuer ein sauberes boot-Log.
109 disable_missing_olsr_modules() {
110  trap 'error_trap disable_missing_olsr_modules "$*"' EXIT
111  local libpath=/usr/lib
112  local libfile
113  local uci_prefix
114  local ignore
115  for uci_prefix in $(find_all_uci_sections "olsrd" "LoadPlugin"); do
116  libfile=$(uci_get "${uci_prefix}.library")
117  ignore=$(uci_get "${uci_prefix}.ignore")
118  [ -n "$ignore" ] && uci_is_true "$ignore" && continue
119  if [ ! -e "$libpath/$libfile" ]; then
120  msg_info "Disabling missing olsr module '$libfile'"
121  uci set "${uci_prefix}.ignore=1"
122  fi
123  done
124  apply_changes olsrd
125 }
126 
127 
128 ## @fn olsr_sync_routing_tables()
129 ## @brief Synchronisiere die olsrd-Routingtabellen-Konfiguration mit den iproute-Routingtabellennummern.
130 ## @details Im Konfliktfall wird die olsrd-Konfiguration an die iproute-Konfiguration angepasst.
132  trap 'error_trap olsr_sync_routing_tables "$*"' EXIT
133  local olsr_name
134  local iproute_name
135  local olsr_id
136  local iproute_id
137  while read -r olsr_name iproute_name; do
138  olsr_id=$(uci_get "olsrd.@olsrd[0].$olsr_name")
139  iproute_id=$(get_routing_table_id "$iproute_name")
140  # beide sind gesetzt und identisch? Alles ok ...
141  [ -n "$olsr_id" ] && [ "$olsr_id" = "$iproute_id" ] && continue
142  # eventuell Tabelle erzeugen, falls sie noch nicht existiert
143  [ -z "$iproute_id" ] && iproute_id=$(add_routing_table "$iproute_name")
144  # olsr passt sich im Zweifel der iproute-Nummer an
145  [ "$olsr_id" = "$iproute_id" ] || uci set "olsrd.@olsrd[0].$olsr_name=$iproute_id"
146  done << EOF
147 RtTable $ROUTING_TABLE_MESH
148 RtTableDefault $ROUTING_TABLE_MESH_DEFAULT
149 EOF
150  apply_changes olsrd
151 }
152 
153 
154 # Einlesen eines olsrd-Nameservice-Service.
155 # Details zum Eingabe- und Ausgabeformat: siehe "get_olsr_services".
156 parse_olsr_service_descriptions() {
157  awk -f /usr/lib/opennet/olsr_parse_service_descriptions.awk
158 }
159 
160 
161 # Parse die olsr-Service-Datei
162 # Die Service-Datei enthaelt Zeilen streng definierter Form (durchgesetzt vom nameservice-Plugin).
163 # Beispielhafte Eintraege:
164 # http://192.168.0.15:8080|tcp|ugw upload:3 download:490 ping:108 #192.168.2.15
165 # dns://192.168.10.4:53|udp|dns #192.168.10.4
166 # Parameter: service-Type (z.B. "gw", "dns", "ntp", "mesh")
167 # Ergebnis (tab-separiert):
168 # SERVICE SCHEME IP PORT PROTO PATH DETAILS
169 # Im Fall von "http://192.168.0.15:8080|tcp|ugw upload:3 download:490 ping:108" entspricht dies:
170 # ugw http 192.168.0.15 8080 tcp / upload:3 download:490 ping:108
171 # shellcheck disable=SC2120
172 get_olsr_services() {
173  trap 'error_trap get_olsr_services "$*"' EXIT
174  local wanted_type="${1:-}"
175  local filter_service
176  [ ! -e "$SERVICES_FILE" ] && msg_debug "no olsr-services file found: $SERVICES_FILE" && return 0
177  sort "$SERVICES_FILE" | uniq | \
178  parse_olsr_service_descriptions | \
179  # filtere die Ergebnisse nach einem Service-Typ, falls selbiger als erster Parameter angegeben wurde
180  awk '{ if (("'"$wanted_type"'" == "") || ("'"$wanted_type"'" == $1)) print $0; }'
181  return 0
182 }
183 
184 
185 ## @fn update_olsr_services()
186 ## @brief Verarbeite die aktuelle Dienst-Liste aus dem olsrd-nameservice-Plugin.
187 ## @details Veraltete Dienste werden entfernt. Eventuelle Änderungen der DNS- und NTP-Serverliste
188 ## werden angewandt.
190  trap 'error_trap update_olsr_services "$*"' EXIT
191  local scheme
192  local ip
193  local port
194  local path
195  local proto
196  local service
197  local details
198  local olsr_services
199  # aktuell verbreitete Dienste benachrichtigen
200  # shellcheck disable=SC2119
201  olsr_services=$(get_olsr_services)
202  # leere Liste? Keine Verbindung mit der Wolke? Keine Aktualisierung, keine Beraeumung ...
203  [ -z "$olsr_services" ] && return
204  echo "$olsr_services" | notify_services "olsr" >/dev/null
205  # aktualisiere DNS- und NTP-Dienste
206  apply_changes on-core
207 }
208 
209 
211 ## @brief Entferne OLSR-Dienste, deren Einträge veraltet sind.
212 ## @details Diese Funktion sollte etwa stündlich ausgeführt werden.
214  local service_name
215  local timestamp
216  local min_timestamp
217  min_timestamp=$(($(get_uptime_minutes) - $(get_on_core_default "olsr_service_expire_minutes")))
218  # veraltete Dienste entfernen (nur falls die uptime groesser ist als die Verfallszeit)
219  if [ "$min_timestamp" -gt 0 ]; then
220  get_services | filter_services_by_value "source" "olsr" | pipe_service_attribute "timestamp" "0" \
221  | while read -r service_name timestamp; do
222  # der Service ist zu lange nicht aktualisiert worden
223  if [ -z "$timestamp" ] || [ "$timestamp" -lt "$min_timestamp" ]; then
224  delete_service "$service_name"
225  fi
226  done
227  fi
228  # aktualisiere DNS- und NTP-Dienste
229  apply_changes on-core
230 }
231 
232 
233 ## @fn request_olsrd_txtinfo()
234 ## @brief Sende eine Anfrage an das txtinfo-Interface von olsrd
235 ## @param request Der zu sende Request-Pfad (z.B. "lin" oder "nei")
236 ## @details Bei Problemen mit dem Verbindungsaufbau erscheint ein Hinweis im syslog.
238  local request="$1"
239  if ! echo "/$request" | timeout 4 nc localhost 2006 2>/dev/null; then
240  # keine Fehlermeldung, falls wir uns gerade noch im Boot-Prozess befinden
241  # Dies tritt besonders nach einem Reboot via Web-Interface auf, da dann die Status-Seite
242  # noch während des Hochfahrens abgerufen wird.
243  [ "$(get_uptime_seconds)" -lt 180 ] || msg_error "request_olsrd_txtinfo: olsrd is not responding"
244  fi | if [ "$request" = "con" ] || [ "$request" = "all" ]; then
245  # die Konfiguration und "all" sind ein unklares Format (fuer Menschen)
246  cat
247  else
248  # alle nicht-Daten-Zeilen entfernen:
249  # * loesche alle Zeilen, bis die erste Zeile beginnend mit "Table: " erkannt wird
250  # * loesche die darauffolgende Zeile, sowie alle leeren Zeilen
251  awk 'BEGIN { in_body=0;}
252  { if (/^Table: /) { in_body=1; } else if (in_body == 1) { print; }}' \
253  | sed '1d; /^$/d'
254  fi
255 }
256 
257 # Ende der Doku-Gruppe
258 ## @}
uci_delete(uci_path)
Lösche ein UCI-Element.
Definition: uci.sh:46
get_services(service_type)
Liefere alle Dienste zurueck, die dem angegebenen Typ zugeordnet sind. Falls kein Typ angegben wird...
Definition: services.sh:68
remove_old_olsr_services()
Entferne OLSR-Dienste, deren Einträge veraltet sind.
Definition: olsr.sh:16
olsr_sync_routing_tables()
Synchronisiere die olsrd-Routingtabellen-Konfiguration mit den iproute-Routingtabellennummern.
Definition: olsr.sh:7
set eu case in network wireless firewall on function update_olsr_interfaces
Definition: 500-on-olsr:9
get_routing_table_id(table_name)
Ermittle die Nummer der namentlich gegebenen Routing-Tabelle.
Definition: routing.sh:49
pipe_service_attribute(key, default)
Liefere zu einer Reihe von Diensten ein gewähltes Attribut dieser Dienste zurück. ...
Definition: services.sh:63
add_routing_table(table_name)
Erstelle einen neuen Routing-Tabellen-Eintrag.
Definition: routing.sh:56
filter_services_by_value(key, value)
Definition: services.sh:74
set eu grep root::etc shadow exit if command v chpasswd dev null
Definition: on-password:12
request_olsrd_txtinfo(request)
Sende eine Anfrage an das txtinfo-Interface von olsrd.
Definition: olsr.sh:21
msg_info(message)
Informationen und Fehlermeldungen ins syslog schreiben.
Definition: core.sh:15
notify_services(source)
Siehe "notify_service" - jedoch effizienter im Umgang mit einer großen Anzahl von Diensten...
Definition: services.sh:23
msg_debug(message)
Debug-Meldungen ins syslog schreiben.
Definition: core.sh:9
set eu on function print_services services log for dir in etc on services d var on services volatile d
Definition: services:13
msg_error(message)
Die Fehlermeldungen werden in die Standard-Fehlerausgabe und ins syslog geschrieben.
Definition: core.sh:22
initialize_olsrd_policy_routing()
Policy-Routing-Initialisierung nach dem System-Boot und nach Interface-Hotplug-Ereignissen.
Definition: routing.sh:44
done
Definition: core.sh:85
update_olsr_services()
Verarbeite die aktuelle Dienst-Liste aus dem olsrd-nameservice-Plugin.
Definition: olsr.sh:12