Opennet Firmware
devel.sh
gehe zur Dokumentation dieser Datei
1 ## @defgroup devel Entwicklungswerkzeuge
2 ## @brief Funktionen, die lediglich für die Firmware-Entwicklung, nicht jedoch zur Laufzeit nützlich sind.
3 # Beginn der Doku-Gruppe
4 ## @{
5 
6 
7 # Ablage fuer profiling-Ergebnisse
8 PROFILING_DIR=/var/run/on-profiling
9 GIT_REPOSITORY_COMMIT_URL_FMT="https://dev.opennet-initiative.de/changeset/%s/on_firmware?format=diff"
10 
11 # erzeuge das Profiling-Verzeichnis (vorsorglich - es wird wohl unbenutzt bleiben)
12 mkdir -p "$PROFILING_DIR"
13 
14 
15 ## @fn list_installed_packages_by_size()
16 ## @brief Zeige alle installierten Pakete und ihren Größenbedarf an.
17 ## @details Dies erlaubt die Analyse des Flash-Bedarfs.
19  local fname
20  find /usr/lib/opkg/info/ -type f -name "*.control" | while read -r fname; do
21  grep "Installed-Size:" "$fname" \
22  | awk '{print $2, "\t", "'"$(basename "${fname%.control}")"'" }'
23  done | sort -n | awk 'BEGIN { summe=0 } { summe+=$1; print $0 } END { print summe }'
24 }
25 
26 
27 ## @fn clean_luci_restart()
28 ## @brief Starte den Webserver neu und lösche alle luci-Cache-Dateien und Kompilate.
29 ## @details Diese Funktion sollte nach Änderungen von luci-Templates oder -Code ausgeführt werden.
31  local rc_path="/etc/init.d/uhttpd"
32  [ -e "$rc_path" ] || return 0
33  "$rc_path" stop
34  rm -rf /var/luci-*
35  "$rc_path" start
36 }
37 
38 
39 ## @fn run_httpd_debug()
40 ## @brief Starte den Webserver im Debug-Modus zur Beobachtung von lua/luci-Ausgaben.
41 ## @details
43  /etc/init.d/uhttpd stop 2>/dev/null || true
44  rm -rf /var/luci-*
45  # ignoriere CTRL-C (wir ueberlassen das INT-Signal dem uhttpd-Prozess)
46  trap "" INT
47  local uhttpd_args="-f -h /www -x /cgi-bin -t 60 -T 30 -k 20 -A 1 -n 3 -N 100 -R -p 0.0.0.0:80 -s 0.0.0.0:443 -q"
48  [ -e /etc/uhttpd.crt ] && uhttpd_args="$uhttpd_args -C /etc/uhttpd.crt -K /etc/uhttpd.key"
49  # shellcheck disable=SC2086
50  uhttpd $uhttpd_args
51  /etc/init.d/uhttpd start
52 }
53 
54 
55 ## @fn get_function_names()
56 ## @brief Liefere die Namen aller Funktionen zurück.
58  grep -h "^[^_][a-z0-9_]*(" "${IPKG_INSTROOT:-}"/usr/lib/opennet/*.sh | sed 's/(.*//' | sort
59 }
60 
61 
62 ## @fn enable_profiling()
63 ## @brief Manipuliere die Funktionsheader in allen shell-Skripten der opennet-Pakete für das Sammeln von profiling-Informationen.
64 ## @details Diese Operation ist irreversibel - eine erneute Installation der Pakete ist der einzige saubere Weg zurück.
65 ## Die Ergebnisse sind anschließend im PROFILING_DIR verfügbar.
66 ## @see summary_profiling
67 enable_profiling() {
68  local message=
69  command -v bash >/dev/null || message="Failed to enable profiling - due to missing bash"
70  [ -e /usr/bin/date ] || message="Failed to enable profiling - due to missing coreutils-date"
71  if [ -z "$message" ]; then
72  # ersetze das shebang in allen Opennet-Skripten
73  # eventuell fehlen ein paar Dateien (Umbennungen usw. im Vergleich zum installierten Paket) -> überspringen
74  cat /usr/lib/opkg/info/on-*.list | grep -E '(bin/|\.sh$|etc/cron\.|/etc/hotplug\.d/|lib/opennet)' \
75  | while read -r fname; do [ -e "$fname" ] && echo "$fname"; true; done \
76  | xargs -n 200 -r sed -i -f "${IPKG_INSTROOT:-}/usr/lib/opennet/profiling.sed"
77  clear_caches
78  else
79  logger -t "on-profile" "$message"
80  echo >&2 "$message"
81  return 1
82  fi
83 }
84 
85 
86 ## @fn summary_profiling()
87 ## @brief Werte gesammelte profiling-Informationen aus.
88 ## @returns Jede Zeile beschreibt das kumulative Profiling einer Funktion:
89 ## Gesamtzeit, Anzahl der Aufrufe, durchschnittliche Verarbeitungszeit, Funktionsname
90 ## Die Zeiten sind jeweils in Millisekunden angegeben.
91 ## @details Als Verarbeitungszeit einer Funktion gilt dabei der gesamte Zeitunterschied zwischen Funktionseintritt und -ende.
92 ## @see enable_profiling
93 summary_profiling() {
94  local fname
95  # Kopfzeile
96  printf '%16s %16s %16s %s\n' "Duration [ms]" "Call count" "avgDuration [ms]" "Name"
97  find "$PROFILING_DIR" -type f | while read -r fname; do
98  # filtere Fehlmessungen (irgendwie tauchen dort Zahlen wie "27323677987" auf)
99  grep -v '^27[0-9]\{9\}$' "$fname" | awk '
100  BEGIN { summe=0; counter=0 }
101  { summe+=($1/1000); counter+=1 }
102  END { printf "%16d %16d %16d %s\n", summe, counter, int(summe/counter), "'"$(basename "$fname")"'"}'
103  done | sort -n
104 }
105 
106 
107 ## @fn apply_repository_patch()
108 ## @brief Wende einen commit aus dem Firmware-Repository als Patch an.
109 ## @param Eine oder mehrere Commit-IDs.
110 ## @details Dies kann die punktuelle Fehlerbehebung nach einem Release erleichtern.
111 ## Die Umgebungsvariable "ON_PATCH_ARGS" wird als Parameter für "patch" verwendet (z.B. "--reverse").
112 apply_repository_patch() {
113  # Patch-Argumente können beim Aufruf gesetzt werden - z.B. "--reverse"
114  local patch_args="${ON_PATCH_ARGS:-}"
115  # wir benötigen das Paket "patch"
116  is_package_installed "patch" || { opkg update && opkg install "patch"; }
117  local commit
118  local patch
119  for commit in "$@"; do
120  # Currently the git repository server uses the Opennet CA for its webserver
121  # certificate.
122  # shellcheck disable=SC2059,SC2086
123  patch=$(http_request "$(printf "$GIT_REPOSITORY_COMMIT_URL_FMT" "$commit")")
124  echo "$patch" | patch $patch_args -p4 --directory --dry-run /
125  echo "$patch" | patch $patch_args -p4 --directory /
126  done
127  clear_caches
128  clean_luci_restart
129 }
130 
131 # Ende der Doku-Gruppe
132 ## @}
get_function_names()
Liefere die Namen aller Funktionen zurück.
Definition: devel.sh:18
set eu grep root::etc shadow exit if command v chpasswd dev null
Definition: on-password:12
list_installed_packages_by_size()
Zeige alle installierten Pakete und ihren Größenbedarf an.
Definition: devel.sh:7
run_httpd_debug()
Starte den Webserver im Debug-Modus zur Beobachtung von lua/luci-Ausgaben.
Definition: devel.sh:15
done
Definition: core.sh:85
clean_luci_restart()
Starte den Webserver neu und lösche alle luci-Cache-Dateien und Kompilate.
Definition: devel.sh:11