Inetd für ds26 >= 14.4

kriegaex schrieb:
Wenn man sich ein wenig einliest, stößt man als Alternative zu inetd und tcpwrapper (als Sicherheitskrücke) schnell auf den längst etablierten xinetd, der die Zugangskontrolle integriert hat.
Die Frage ist, ob man die Zugangskontrolle, die tcpwrapper oder
xinetd bieten, überhaupt braucht. Ich gehe davon aus, daß die meisten Dienste (mit Ausnahme von SSH) nur im internen Netz verwendet werden.
 
kriegaex schrieb:
Daran, daß inetd zur Busybox gehört, hatte ich nicht gedacht. Dann nehmen wir den auch.
Noch ein Hinweis zum inetd der Busybox bzw. zur Busybox allgemein.
Hier ein size des Moduls:
Code:
> size source/ref-8mb_26/busybox-1.4.1/networking/inetd.o
   text    data     bss     dec     hex filename
  12924     188    1348   14460    387c source/ref-8mb_26/busybox-1.4.1/networking/inetd.o
Mir ist gerade aufgefallen, daß BSS 1348 Bytes hat, davon 1024 für eine Variable char line[1024] für das Einlesen einer Zeile. Das wirkt sich zwar nicht auf die Größe im Dateisystem aus, bedeutet aber, daß jeder einzelne Prozeß, der Busybox ausführt, 1348 Bytes extra belegt, und zwar unnütz, wenn er nicht gerade inetd ausführt. Es wäre sinnvoll, das Programm so zu ändern, daß zumindest diese Variable nicht so viel Platz belegt, wenn sie nicht verwendet wird. Also entweder den Platz am Stack belegen oder mit malloc beim Aufruf von inetd.
Eine elegantere Lösung wäre, alle globalen Variablen eines Busybox Applets in eine eigene Struktur zu packen und diese nur zu belegen, wenn das entsprechende Applet aufgerufen wird. Noch schöner wäre es, wenn man den Linker dazu bewegen könnte, den Platz für die BSS-Segmente aller Applets übereinander zu legen, da diese ja nicht gleichzeitig verwendet werden
 
Das mit der BSS ist ein guter Punkt. Ich hab die Busybox in meinem Patch entsprechend angepasst (siehe Post #1). Dadurch ist die BSS nur mehr 180 Byte.
 
So, die vorläufig 'Komplettlösung' von mir ist jetzt fertig. Siehe Post #1.
 
Wie zwischenzeitlich schon erwähnt, wäre eine sinnvolle Konsequenz aus der Nutzung des inetd, auch das AVM-WebIf über selbigen laufen zu lassen, zumal der websrv im Normalbetrieb schon einiges an Speicher belegt; in meinem Fall laut 'top' immerhin 5,6%.

Leider hat websrv wohl wie gesagt keinen inetd-Modus. Soweit ich bisher herausfinden konnte, macht websrv an sich aber auch gar nichts spezielles; sämtliche Anfragen werden über webcm abgewickelt. Es sollte daher prinzipiell möglich sein, websrv komplett zu entfernen und durch einen anderen httpd zu ersetzen.

Als erste Idee kommt einem natürlich der Busybox-Httpd, den wir ja sowieso schon an Bord haben. Leider funktioniert bei diesem das Zusammenspiel zwischen httpd und webcm nicht korrekt; die Webseiten laufen nicht. Ausprobieren kann das jeder leicht selbst: einfach mal den httpd mit
Code:
httpd -p 82 -h /usr/www/html
starten und dann auf entsprechend auf Port 82 ausprobieren. Meine Vermutung ist jetzt, dass evtl. irgend etwas am Environment der CGI-Scripte dem webcm fehlt. In einem Test habe ich mal verschiedene der von websrv gesetzten Variablen mittels eines Wrapper-Scripts an webcm übergeben, aber leider auch erfolglos.

Ich habe dann mal testweise den thttpd-Server für die Fbox gebaut, und siehe da, dort läuft das AVM-WebIf auf den ersten Blick ohne Probleme.

Vielleicht hat ja jemand eine Idee, woran es mit dem busybox-httpd noch haken könnte.

Gruss, Nico
 
McNetic schrieb:
Leider funktioniert bei diesem das Zusammenspiel zwischen httpd und webcm nicht korrekt; die Webseiten laufen nicht.

Ich habe dann mal testweise den thttpd-Server für die Fbox gebaut, und siehe da, dort läuft das AVM-WebIf auf den ersten Blick ohne Probleme.

Vielleicht hat ja jemand eine Idee, woran es mit dem busybox-httpd noch haken könnte.
Versuch einmal, das /bin/env und /bin/pwd nach /usr/www/cgi-bin/ zu kopieren (Symlink auf /bin/busybox) und über httpd und über websrv aufzurufen. Vielleicht wird da ein Unterschied sichtbar.
 
Häng mal bitte Dein thttpd-Binary und eine kurze Anleitung, wie ich ihn starte, hier an den Thread, ich möchte gern was probieren, denn mit der Methode, Variablen explizit in einem Wrapper-Skript zu setzen, kam ich auch nicht weiter bislang.
 
Hallo,

ich wollte eigentlich erst posten, wenn das die Lösung spruchreif ist, aber bevor sich jetzt alle den Kopf zerbrechen mal kurz eine Zwischeninfo:

Olistudent hat herausgefunden, dass es nicht an den Umgebungsvariablen liegt, sondern an der Art des Aufrufs. Alle Webserver wechseln zur Ausführung eines CGIs in das Verzeichnis, in dem selbiges liegt. Der busybox-httpd ermittelt aber den kompletten Pfad zum CGI mittels realpath() und expandiert daher auch eventuelle Symlinks (wie in diesem Fall den von /usr/www/html/cgi-bin/webcm auf /usr/www/cgi-bin/webcm). Er wechselt daher nicht in den Pfad, wo der Symlink liegt, sondern eben in den, wo die tatsächliche Datei liegt. Im weiteren Verlauf findet das CGI dann natürlich seine Dateien nicht mehr, die ja relativ angegeben werden.

Schnellfix: Durch Kopieren des Binaries lässt sich das Problem beheben und das WebIf läuft.

Zum Test könnte man jetzt auch einen Wrapper schreiben, der das CGI wieder ins richtige Verzeichnis chdir()ed.

Da die anderen Webserver dieses Verhalten jedoch nicht zeigen, denke ich, die 'richtige' Lösung für das Problem ist ein Fix des Busybox-Httpd. Ich habe sowas schon fertig und werde es gleich mal testen, dann gibts mehr Infos.

Gruss, Nico
 
Weiß schon, daß Oliver da auch dran war gestern. Ich hatte ihm mein Wrapper-Skript geschickt, da ich aufhören mußte, bevor ich richtig mit dem Testen begonnen hatte (Besuch).

Zum Busybox-httpd-Patch, den Du gerade entwickelst: Ich werde ihn dann, wenn er gut aussieht, auch in die offizielle BB-Distribution hinein zu bringen versuchen. Hast Du vorsichtshalber mal geschaut, ob in 1.5.1 das Ganze evtl. schon bereinigt ist?
 
Ich dachte nicht, dass es so schnell geht :). Also, mit dem modifizierten Busybox-Httpd läuft das WebIf jetzt augenscheinlich, und zwar sowohl im Standalone-Modus als auch über inetd.

Einstellungen ändern ist kein Problem, aber ich habe jetzt noch keine komplizierteren Sachen wie ein Firmware-Update ausprobiert. Letzteres ist bestimmt noch etwas frickelig, das probier ich später mal aus.

Den BB-Patch habe ich mal angehängt. Die Funktion abspath() habe ich selbst geschrieben, mich dabei aber an vorhandenem orientiert. Bin schon sehr verwundert, dass sowas nicht in der libc drin ist - jede GNU-Software implementiert das selbst (gcc, make, emacs,...).

Edit: Ach ja, nein, in BB 1.5.1 ist die Situation noch die gleiche. Ist wohl nicht so häufig und auch ein Sicherheitsrisiko, mit Symlinks und CGIs rumzuhantieren (vor allem wenn potentiell nicht vertrauenswürdige Personen CGIs erstellen können bzw. Schreibzugriff auf die Webserver-Verzeichnisse haben). Aber das ist eine komplett andere Baustelle, denn momentan wird dem Symlink ja auch gefolgt, nur die Aufrufumgebung stimmt dann nicht mehr.

Gruss, Nico
 

Anhänge

  • busybox-realpath.patch.bz2
    1.1 KB · Aufrufe: 5
pwd.c ruft xgetcwd auf. Ich habe nicht genau geschaut, aber das sieht doch danach aus, als gäbe es das schon. Der Befehl pwd macht doch genau das, was Du brauchst. Kannst Du das auf diese Weise evtl. etwas vereinfachen und auf die selbst geschriebene Funktion verzichten?
 
Hm. Nein. xgetcwd() gibt ja nur das aktuelle working directory her.

Der busybox-httpd hat bisher den Pfad zum cgi (also bspws. den Teil der Url: "/cgi-bin/webcm") genommen, das leading / entfernt, und dann realpath() damit aufgerufen. realpath() fügt jetzt diesen Pfad an das cwd an, expandiert ihn (er kann z.B. ./ oder ../ enthalten), und löst dabei auch sämtliche enthaltenen Symlinks auf.

Der so erhaltene Pfad wird dann weiterverarbeitet (z.B. in die Env-Variable SCRIPT_FILENAME) und es wird in das Verzeichnis der in diesem Pfad bezeichneten Datei gewechselt. Diese Verhalten ist insofern falsch, als dass der httpd als Userspace-Anwendung sich um die FS-Spezifika wie Symlinks nicht kümmern sollte, sondern die Symlinks wie jede andere Datei auch behandeln sollte.

Was der httpd also braucht, ist eine Funktion abspath(), die das gleiche macht, wie realpath(), dabei aber eben die Symlinks *nicht* verfolgt. Und genau das macht meine Funktion. Wie gesagt, gcc und make haben z.B. auch solche Implementierungen. Die sind aber um einiges komplexer, da sie auch noch verschiedene OS-Spezialitäten berücksichtigen, was wir natürlich nicht müssen.

Gruss, Nico
 
xgetcwd expandiert Symlinks aber auch nicht.
 
Wenn ich Dich richtig verstanden habe, ist das Problem doch nicht der Pfad zum CGI-Skript, sondern das Arbeitsverzeichnis, wenn das Skript aufgerufen wird.
Würde es dann nicht reichen, in das angegebene Verzeichnis zu wechseln?
Also
Code:
networking/httpd.c:
   1090                 script = strrchr(realpath_buff, '/');
   1091                 if (!script)
   1092                         goto error_execing_cgi;
   1093                 *script = '\0';
   1094                 if (chdir(realpath_buff) == 0) {
->
   1090                 script = strrchr(purl, '/');
   1091                 if (!script)
   1092                         goto error_execing_cgi;
   1093                 *script = '\0';
   1094                 if (chdir(purl + 1) == 0) {
Damit ist das aktuelle Verzeichnis das, in dem sich das Skript oder der Link befindet.
 
kriegaex:
Ja, aber es macht doch was ganz anders? Es gibt mir das aktuelle Verzeichnis (also das, in dem der momentan ausgeführte Kontext läuft). Während die Funktionen realpath() und abspath() mir den absoluten Pfad zu einem übergebenen, potentiell (und in diesem Fall wohl immer) relativen Dateinamen gibt.

RalfFriedl:
Im Prinzip ist das richtig, das angesprochene Problem ist nur das Wechseln in das korrekte Verzeichnis. Daran hängt aber auch, dass die CGI-Umgebung korrekt initialisiert werden muss, und der BB-Httpd stellt da z.B. eine Variable SCRIPT_FILENAME zur Verfügung, die den kompletten Pfad zum CGI enthält. Dort wird halt momentan der realpath() eingetragen. Damit das Verhalten konsistent bleibt, muss der abspath() da hin.

Man könnte das natürlich weglassen, aber man weiss ja nicht, welche Scripts sich auf solche Besonderheiten verlassen (denn SCRIPT_FILENAME gehört wohl nicht zur CGI 1.1-Spezifikation).

Gruss, Nico
 
McNetic schrieb:
Im Prinzip ist das richtig, das angesprochene Problem ist nur das Wechseln in das korrekte Verzeichnis.
Das Verzeichnis, in dem sich das Script befindet, ist doch anscheinend das, was erwartet wird, und sollte daher funktionieren, ob es sich dabei um die Datei selbst oder einen Link handelt.
Daran hängt aber auch, dass die CGI-Umgebung korrekt initialisiert werden muss, und der BB-Httpd stellt da z.B. eine Variable SCRIPT_FILENAME zur Verfügung, die den kompletten Pfad zum CGI enthält. Dort wird halt momentan der realpath() eingetragen. Damit das Verhalten konsistent bleibt, muss der abspath() da hin.

Man könnte das natürlich weglassen, aber man weiss ja nicht, welche Scripts sich auf solche Besonderheiten verlassen (denn SCRIPT_FILENAME gehört wohl nicht zur CGI 1.1-Spezifikation).
Dann sollte sich auch kein CGI-Programm darauf verlassen. Wenn man andererseits SCRIPT_FILENAME aus den übergebenen Werten aufbaut, bekommt das CGI-Programm den logischen Pfadnamen übergeben und könnte bei Bedarf immer noch realpath() darauf anwenden. Insbesondere verweist jeder Name auf die gleiche Datei, ob mit oder ohne Link. Für die meisten Dateioperationen macht das keinen Unterschied.

Das einzige Problem ist doch anscheinend, daß BB-HTTPD im Moment
chdir (dirname (realpath (WWWROOT + SCRIPT_NAME)))
ausführt.
Wir bräuchten statt dessen
chdir (realpath (dirname (WWWROOT + SCRIPT_NAME)))
oder
chdir (dirname (WWWROOT + SCRIPT_NAME))
oder
chdir (WWWROOT + dirname (SCRIPT_NAME))
Die letzten drei sind aber identisch, weil chdir den Symlinks folgt, und für das aufgerufene Programm ist nicht mehr feststellbar, unter welchem Namen in das Verzeichnis gewechselt wurde.
Die einzige Frage ist also, ob das CGI-Programm in SCRIPT_FILENAME seinen eigenen realpath braucht. Ich gehe davon aus, daß dies nicht der Fall ist.
 
RalfFriedl schrieb:
Das Verzeichnis, in dem sich das Script befindet, ist doch anscheinend das, was erwartet wird, und sollte daher funktionieren, ob es sich dabei um die Datei selbst oder einen Link handelt.
Genau. Ist ja auch offenbar der Fall.

RalfFriedl schrieb:
chdir (dirname (WWWROOT + SCRIPT_NAME))
Die einzige Frage ist also, ob das CGI-Programm in SCRIPT_FILENAME seinen eigenen realpath braucht. Ich gehe davon aus, daß dies nicht der Fall ist.
Wir brauchen von Deinen Vorschlägen diesen. Was genau ein Script in SCRIPT_FILENAME erwartet, kann ich nicht sagen. Aus meiner Sicht wäre realpath() (also mit Auflösung von Symlinks) aber nicht korrekt, da Symlinks aus Anwendungssicht wie normale Dateien behandelt werden sollten. Und saubererweise schreibt man in solch eine Variable in meinen Augen eben einen absoluten Pfad, ohne eventuelle ../ oder ähnliches. Sonst könnte der BB-Httpd sich das realpath() auch direkt sparen. Deswegen sehe ich die Lösung mit (meinem|einem anderen) abspath() immer noch als die optimale an. Man könnte das aber auch die Upstream-BB-Autoren entscheiden lassen.

Gruss, Nico
 
Ich habe das jetzt nicht ausprobiert, aber der Patch sollte genau so funktionieren. Wir brauchen ja nur eine Hand voll Zeilen aus dem ganzen Patch.
 
hallöchen...
habe das jetzt nach besten wissen mal nachgebaut...
er hat anstandslos die patche durchgeführt, gemaked und geflashed...
aber inetd starten bringt leider nen fehler...
was habe ich falsch gemacht?
Code:
Starting inetd.../mod/etc/init.d/rc.inetd: /mod/etc/init.d/rc.inetd: 120: inetd: not found
failed.
inetd kann ich auch nirgends finden...
snief snief...
danke für eure mühen

p.s. sehe grad, das das was dazugekommen iss...werde gleich mal die busybox neu machen...danke für den wink
 
Zuletzt bearbeitet:
Holen Sie sich 3CX - völlig kostenlos!
Verbinden Sie Ihr Team und Ihre Kunden Telefonie Livechat Videokonferenzen

Gehostet oder selbst-verwaltet. Für bis zu 10 Nutzer dauerhaft kostenlos. Keine Kreditkartendetails erforderlich. Ohne Risiko testen.

3CX
Für diese E-Mail-Adresse besteht bereits ein 3CX-Konto. Sie werden zum Kundenportal weitergeleitet, wo Sie sich anmelden oder Ihr Passwort zurücksetzen können, falls Sie dieses vergessen haben.