# Jailkit und mysqld.sock FIX***



## Rafael.K (17. Aug. 2011)

Hallo,

Ich wollte MySql + MySqlDump für Jailuser freigeben, dafür habe ich beide Anwendungen in "Jailkit chrooted Anwendungen" eingetragen und neue Jails erstellt.
Es hat alles einwandfrei funktioniert, allerdings nur bis zu ersten Neustart des Systems/MySql-Daemons. So habe ich mich auf die Suche nach Fehler im System begeben, konnte aber nichts feststellen. Nach einem Neustart kommt immer ein Fehler bei Jail-Benutzer etwa : "Kann nicht über Sockel mysqld.sock Verbindung herstellen…."

Das, was unten aufgeführt ist, ist zu Information, wie ich auf die Lösung gekommen bin. Und zweckt in erster Linie der Hilfe bei Fehlersuche in meinem Skript. Falls ich etwas FALSCHES wiedergegeben oder von sich geschrieben habe, dann liegt es an meine geringe Kenntnisse in Linux/Unix-Systemen oder Informationquellen, die ich genutzt habe. Berichtigt es bitte um Kettenreaktion der falschen Beiträge zu stoppen, denn die Suchmaschinen liefern *auch* Schrott, wobei dieses Thread beides sein kann. 


Quellen: " Jailkit - chroot jail utilities " , " http://www.howtoforge.*/forum/ " , "  gidf, wie immer nützliche in Lesezeichen nich angelegt !!!"

Jailkit-Doku --> jk_cp und jk_init tun fast das gleiche(s. Doku) "-k": "Try to create hardlinks instead of copying the files. If linking fails it falls back to copying.." 
Ich habe also gedacht, dass jailkit selbst erkennt welche Sockel er für MySql mitkopiert(bzw. ein Link erstellt) und gegebenenfalls überwacht, weil im CHROOTs war diese immer zu finden. Dann habe ich in einem anderen englischen Forum gleiches Problem gefunden und festgestellt, dass es nicht der Fall ist und diese Problem noch nicht gelöst ist, und Jailkit kann nicht mit Unix-Sockets(Ausnahme: jk_socketd für LOG Socket) umgehen. 
Eine weitere Suche hat ergeben, dass die Sockets keine gewöhnliche Dateien sind und werden erst erstellt, wenn daemon gestartet wird, und sollten nicht als Dateien, sondern als Geräte angesehen/behandelt werden. 

Erste positive ergebniss der Suche in "ISPConfig 3 Source" war die Datei "/usr/local/ispconfig/server/scripts/create_jailkit_chroot.sh" : 

```
####################################################################################
…
# mysql needs the socket in the chrooted environment
mkdir $CHROOT_HOMEDIR/var
mkdir $CHROOT_HOMEDIR/var/run
mkdir $CHROOT_HOMEDIR/var/run/mysqld

# ln /var/run/mysqld/mysqld.sock $CHROOT_HOMEDIR/var/run/mysqld/mysqld.sock
if [ -e "/var/run/mysqld/mysqld.sock" ]
then
  ln /var/run/mysqld/mysqld.sock $CHROOT_HOMEDIR/var/run/mysqld/mysqld.sock
fi
…
#################################################################################
```
zu beachten ist, dass hier ein Hardlink in CHROOT von echten MySQL-Socket erstellt wird, und wie oben beschrieben: "… Sockets … werden erst erstellt, wenn daemon gestartet wird … " . Und wenn die immerwieder neu erstellt werden, dann sind die immer unterschiedlich(also Infos und Adressen wo diese in liegen) und Hardlink zeigt irgendwo-hin nur nicht auf den neuen mysqld.sock.


Und so habe ich mich entschlossen etwas für Lösung dieses Problems zu unternehmen. 

*Folgendes war Ziel:*
1. alle CHROOTs finden.(kein Problem mit MySQL-Abfrage)
2. Jedes neustart des MySql-Servers muss neue Socket bei CHROOTs bereitstellen.
3. Muss automatisch Funktionieren. Und nicht Lastig sein, möglichst ohne extra DAEMON dafür.

*Und das ist dabei  rausgekommen:*
1. Geht auch ohne MySQL-Abfrage. Mit kleiner INJEKTION in /etc/init.d/mysql
2. OHNE Extra-DAEMON
3. fix-skript für bestehende CHROOTs
4. kleines Update-Skript für Zufügen neuen Anwendungen in "Jailkit chrooted Anwendungen" für alle CHROOTs. _"Könnte in eine der neuen Versionen von ISPCONFIG3 fließen, weil minestens 2 Threads für diese Problem hier gesehen."_

*Weiter geht es mit HowTo: - fix-Jailkit-mysqld.sock.*
_*Wie immer . . . alles ohne Gewähr, testet es auf eigene Gefahr.*_

als erstes ladet jk-mysql.sock-fix.zip Archiv [für Könner *.txt] aus Anhang herunter und schiebt enthaltene Dateien in Verzeichnis "/usr/local/ispconfig/server/scripts/" 

dann benennt folgende Dateien um: 
"create_jailkit_chroot.sh" => z.B "create_jailkit_chroot.sh.Original"

"create_jailkit_chroot.sh.fix" => "create_jailkit_chroot.sh"

und setzt Rechte der Dateien "create_jailkit_chroot.sh" und "jailkit_mysql_sock_fix.sh".

```
chown ispconfig:ispconfig create_jailkit_chroot.sh jailkit_mysql_sock_fix.sh
cmod 751  create_jailkit_chroot.sh jailkit_mysql_sock_fix.sh
```
jetzt wird die "/etc/init.d/mysql" angepasst.

_*ACHTUNG !!! Sehr aufmerksam!!! Die richtige Zeile finden!!! ACHTUNG*_

1. beim CASE-Verzweigung für 'start' bei ca Zeile 122

```
. . .
            # Now start mysqlcheck or whatever the admin wants.
            output=$(/etc/mysql/debian-start)
            [ -n "$output" ] && log_action_msg "$output" # <-- ca Zeile 121
#######################################################################################
# Jailkit-mysqld.sock Problem
        ./usr/local/ispconfig/server/scripts/jailkit_mysql_sock_fix.sh "mountAll"
#######################################################################################
        else
            log_end_msg 1
        log_failure_msg "Please take a look at the syslog"
        fi
    fi
. . .
```
2. beim CASE-Verzweigung für 'stop' gleich nach Kommentaren 

```
. . .
    # * As a passwordless mysqladmin (e.g. via ~/.my.cnf) must be possible
    # at least for cron, we can rely on it here, too. (although we have 
    # to specify it explicit as e.g. sudo environments points to the normal
    # users home and not /root)
#######################################################################################
# Jailkit-mysqld.sock Problem
        ./usr/local/ispconfig/server/scripts/jailkit_mysql_sock_fix.sh "umountAll" 
#######################################################################################
    log_daemon_msg "Stopping MySQL database server" "mysqld"
    if ! mysqld_status check_dead nowarn; then
. . .
```
_*ACHTUNG !!! Sehr wichtig!!! ACHTUNG*_
_Wenn web-Ordner von normalen Installation abweichen, dann in "jailkit_mysql_sock_fix.sh" reinschauen und jails="/var/www/clients/client*/web*/bin" anpassen._

jetzt werden Bestehende Jail-CHROOTs gefixt (alte Hardlinks löschen -> einfache "Datei/je CHROOT" mit touch erstellen -> mysqld.sock auf diese mounten)

```
/./usr/local/ispconfig/server/scripts/jailkit_mysql_sock_fix.sh -fixAll
```
*und nun FFF. Ab jetz wird MySql auch für Jails für immer zugänglich sein.** 
*


----------



## Till (17. Aug. 2011)

Danke für den Fix!


----------



## celocore (19. Aug. 2011)

Hi,

ich habe meine "Jailkit chrooted Anwendungen" um /usr/bin/mysql und /usr/bin/mysqldump erweitert. Es steht auch korrekt in der server-Tabelle der ispc-DB drin, aber irgendwie 
werden die Binaries nicht mit kopiert beim Anlegen der chroot-Umgebung 
Habt Ihr vielleicht eine Idee woran das liegen kann?


----------



## Rafael.K (19. Aug. 2011)

Wenn es um bestehende CHROOTs geht dann führe bitte mal folgendes aus:

```
./jailkit_mysql_sock_fix.sh -updateAll '/usr/bin/mysql /usr/bin/mysqldump'
./jailkit_mysql_sock_fix.sh -fixAll
```
beachte dabei, wenn die web-Ordner von Standartinstallation abweichen, die Zeilel in jailkit_mysql_sock_fix.sh :

```
...
# Costomize only if "System" -> "Server Config" -> "Web" -> "Website path" in ISPc-UI modified.
jails="/var/www/clients/client*/web*/bin" #finds all ISPCONFIGs CHROOTs !-> some Jailkits file schould be includet in String, for example "*/bin"!!! 
###
...
```
PS: Dieses Thread ist nur ein FIX für mysqld.sock und nicht für JAILKIT-Funktionen allgemein. jailkit_mysql_sock_fix.sh Skript ist noch nicht in PHP-Code integriert und somit nicht die Bestehende CHROOTs beim Einfügen in "Jailkit chrooted Anwendungen" updaten kann. Dafür muss du wie oben beschrieben optionen "-updateAll" und "-fixAll" selbst ausführen.


----------



## celocore (19. Aug. 2011)

Hallo Rafael,

soweit, so klar. Aber bei mir befinden bei neu angelegten chroots die MySQL-Binaries gar nicht erst in der chroot-Umgebung. Das ist das, was mich im Moment stutzen läßt.


----------



## Rafael.K (19. Aug. 2011)

Wenn Jailkit richtig installiert und konfiguriert ist sollte es keine Probleme geben. wenn nicht dann kannst du das hier versuchen.

bzw:
Debugging in der Datei "/usr/local/ispconfig/server/scripts/create_jailkit_programs.sh" erstellen. Dazu muss man diese Datei
anpassen: 
also Kommentar bei "jk_cp -k ........" setzen und "echo -e "` ...... " Zeile einfügen
etwa so :

```
...
#jk_cp -k $CHROOT_HOMEDIR $CHROOT_APP_PROGRAMS
fehler=`jk_cp 2>&1 -k $CHROOT_HOMEDIR $CHROOT_APP_PROGRAMS`

echo -e "`date +%d.%m.%y-%R:%S` : `basename $0`  -------------------------------------\n uebergeben : \t CHROOT_HOMEDIR =  $1 \n\t\t CHROOT_APP_SECTIONS = $2 \n\n Fehler: \t$fehler" >>  "/var/www/create_jailkit_programs.sh.log"
```
dann in Datei "/var/www/create_jailkit_programs.sh.log" nachschauen ob es wirklich an Skript übergegeben wird
und "Fehler: .... " beachten.

PS: "/var/www/create_jailkit_programs.sh.log" gegebenenfalls anpassen.

und poste bitte Inhalt der "/var/www/create_jailkit_programs.sh.log" Datei.


----------



## celocore (30. Mai 2012)

Moin zusammen,

ich krame diesen Thread nochmal raus, weil ich an dem ln gescheitert bin. Aufgrund von Änderungen (zumindest bei ubuntu) im Dateisystem, führt ein ln jetzt unweigerlich zum Fehler *Invalid cross-device link*. Ursache dafür ist, dass /var/run seit mind. 8.04 LTS eine eigenständige Partition ist.

Ein Workaround der funktioniert ist das Verzeichnis /var/run/mysqld mittels mount -o bind in das chrooted-Home-Dir/var/run/mysqld einzulinken.


----------



## Rafael.K (31. Mai 2012)

Das ist richtig, meine Shell-Skripte "mounten" den "mysqld"-Socket in alle "Jails" für alle WEBs automatisch und machen es erneut wenn Mysql neugestrtet wird.


----------



## celocore (31. Mai 2012)

Dadurch, dass das Verzeichnis gemountet wird ist es eigentlich nicht erforderlich, den Mount nach Restart des MySQL-Servers zu erneuern. Zumindest brauchte ich das bisher nicht.


----------



## Rafael.K (4. Juni 2012)

Zitat von celocore:


> Dadurch, dass das Verzeichnis gemountet wird ist es eigentlich nicht erforderlich, den Mount nach Restart des MySQL-Servers zu erneuern. Zumindest brauchte ich das bisher nicht.


 *Ja, das ist richtig.*

Im Shellskript habe ich die "mysqld.sock"-Datei direkt gemountet, weil ich nicht weiß wie sich Jailkit dabei verhällt, in gemountete Verzeichnisse reinzuschauen(Vielleicht ist es ein Risiko?!?!). 
Deswegen habe ich die Geschichte mit REMOUNT gemacht. *Also ich wollte einfach sicher gehen, dass niemand aus dem Jail entkommen kann. *

*Wenn man sich sicher ist, dass es sicher ist, ist es durchaus sinnvoller einmalig das Verzeichnis "/var/run/mysqld" zu mounten.*


----------



## mattula (24. Apr. 2013)

Zitat von Till:


> Danke für den Fix!


Hi Till,

wird der Fix in ISPConfig integriert werden?
Oder hast du eine andere Lösung?

Ich überlege grade, ob ich das auf die hier genante Art und Weise realisieren will, mit bind Mounts in die Chroot.

Grüße,
Matthias


----------



## Till (24. Apr. 2013)

Ich verwende sowohl mysql aus auch mysqldump in Jails ohne ein Socket zu benötigen, denn beide Befehle funktionieren genauso über http Connections zu localhost.


----------



## mattula (24. Apr. 2013)

Zitat von Till:


> Ich verwende sowohl mysql aus auch mysqldump in Jails ohne ein Socket zu benötigen, denn beide Befehle funktionieren genauso über http Connections zu localhost.


Das dachte  ich auch, bzw. bedingt stimmt das.

Der mysql Client scheint bei Benutzung des  Wortes "localhost" den Socket verwenden zu wollen:


```
web104@webhost:~$ mysql -hlocalhost   
ERROR 2002 (HY000): Can't connect to local MySQL server through socket '/var/run/mysqld/mysqld.sock' (111)
```
Wenn ich die IP nehme, geht es:


```
web104@webhost:~$ mysql -h127.0.0.1 
ERROR 1045 (28000): Access denied for user 'web104'@'localhost' (using password: NO)
```
Ich hab nur ne Weile gebraucht das herauszufinden, weil in den neueren Chroots der Socket /var/run/mysqld/mysqld.sock noch aktuell war und somit auch der "localhost" Aufruf funktioniert hat. Auch wenn ich den Socket ganz aus der Chroot lösche, versucht mysql -hlocalhost nur den Socket Zugriff. Dieses Verhalten wird auch im MySQL Reference Manual so beschrieben. Soll also so sein. Helfen tut nur die Angabe des Protokolls exlizit:


```
mysql --protocol=TCP -hlocalhost
```
Damit funktioniert auch localhost ohne Socket.

Darum die Überlegung doch den Socket zur Verfügung zu stellen.
Das ist imho einfacher, als zig Kunden erklären zu müssen, was sie falsch machen, wie sie es richtig machen und warum es bis zu einem bestimmten Zeitpunkt oder bei neu angeleghten Chroots noch funktioniert hat.

Verwirrend ist nämlich, dass per /usr/local/ispconfig/server/scripts/create_jailkit_chroot.sh nachwievor ein Hardlink auf /var/run/mysqld/mysqld.sock in der Chroot angelegt wird.

Der Hardlink funktioniert aber nicht mehr, sobald der MySQL Server neu gestartet wurde. (Ab Debian Wheezy bzw, neueren Ubuntu laesst sich gar kein Hardlink mehr anlegen, da dort /run als tmpfs gemountet ist = invalid cross device.)

Mein Vorschlag wäre dann, den Socket entweder ganz weg zu lassen, um keine Verwirrung zu stiften, oder per bind mount sauber einzubinden. Mit den Logs macht ISPConfig das ja auch schon so.

Alternativ wäre auch eine kleine mysql Config in der Chroot hilfreich:

/path/to/chroot/etc/mysql/my.cnf

```
[client]
port            = 3306
protocol        = TCP
host            = 127.0.0.1
```
Damit benutzt der mysql client auch ohne Angabe von Parametern per Default den localhost per TCP. Ob der protocol Parameter auch bei Aufrufen aus PHP heraus greift, habe ich noch nicht getestet.

Matthias


----------



## Till (24. Apr. 2013)

Ich denke die Variante mit der zusätzlichen my.cnf im jail sowie weglassen des Socket wäre die sauberste Lösung.


----------



## mattula (24. Apr. 2013)

Zitat von Till:


> Ich denke die Variante mit der zusätzlichen my.cnf im jail sowie weglassen des Socket wäre die sauberste Lösung.


OK, habe jetzt aber noch einen Stolperstein gefunden:

Wenn ich ein jk_update aufrufe wird die von mir vorher manuell hinein kopierte /etc/mysql/my.cnf durch die Version aus der echten root ersetzt:


```
root@webhost:# chroot=/path/to/chroot/webXX
root@webhost:# jk_update -j $chroot /bin /usr /lib /etc /opt /var
removing outdated file /var/www/clients/client2/web104/etc/mysql/my.cnf
Copying /etc/mysql/my.cnf to /var/www/clients/client2/web104/etc/mysql/my.cnf
```
Es ist nirgends konfiguriert, dass die my.cnf in die Jail soll. D.h. das jk_update scheint da ein wenig eigenmächtig "intelligent" zu handeln.

Hm ... blödes Verhalten.

Matthias


----------



## Rafael.K (24. Apr. 2013)

Hallo mattula

laut Jailkit - chroot jail utilities können die gewünschte Dateien bei *jk_update* übersprungen werden indem ein Schalter *-s* vor einer Datei im Befehl gesetzt werden kann. 

Es geht aber auch mit einer Konfigurationdatei für den Jail :
...
[/home/otherjail] skips = /usr/share/firefox, /usr/bin/firefox, /usr/lib/firefox...


----------



## Rafael.K (24. Apr. 2013)

Und ich habe vergessen zu erwähnen, dass Dein lösung gefeällt mir sehr gut und es ist definitiv besser als noch ein Skript im Programmablauf zu benutzen und ich werde es definitif auch so(custom my.ini für Jail, allerdings erst nach ***) machen. Was PHP auf der Seite des Webs angeht: Es kriegt von der änderung nichts mit. Was aber PHP-CLI angeht, kann ich erst nach dem *"Test mit Doctrine 2"**** sagen.


----------

