Linux - SecurityThis forum is for all security related questions.
Questions, tips, system compromises, firewalls, etc. are all included here.
Notices
Welcome to LinuxQuestions.org, a friendly and active Linux Community.
You are currently viewing LQ as a guest. By joining our community you will have the ability to post topics, receive our newsletter, use the advanced search, subscribe to threads and access many other special features. Registration is quick, simple and absolutely free. Join our community today!
Note that registered members see fewer ads, and ContentLink is completely disabled once you log in.
If you have any problems with the registration process or your account login, please contact us. If you need to reset your password, click here.
Having a problem logging in? Please visit this page to clear all LQ-related cookies.
Get a virtual cloud desktop with the Linux distro that you want in less than five minutes with Shells! With over 10 pre-installed distros to choose from, the worry-free installation life is here! Whether you are a digital nomad or just looking for flexibility, Shells can put your Linux machine on the device that you want to use.
Exclusive for LQ members, get up to 45% off per month. Click here for more info.
mysqld Command-line Options
--chroot=path
Put mysqld daemon in chroot environment at startup. Recommended security measure. It somewhat limits LOAD DATA INFILE and SELECT ... INTO OUTFILE though.
I've installed the binary distribution of mysql and modified the safe_mysqld script a bit (added --chroot=/server/mysql) to it so it executes mysqld chrooted to /server/mysql.
Quote:
ps auxw | grep mysql
root 26123 0.0 0.1 3836 1088 pts/0 S 11:11 0:00 /bin/sh ./bin/safe_mysqld
mysql 26139 0.0 0.0 10524 992 pts/0 S 11:11 0:00 /server/mysql/binary/bin/mysqld --defaults-extra-file=/server/mysql/b
ls -al /proc/26139/
-r--r--r-- 1 root root 0 Nov 1 11:16 cmdline
lrwxrwxrwx 1 root root 0 Nov 1 11:16 cwd -> /server/mysql/databases
-r-------- 1 root root 0 Nov 1 11:16 environ
lrwxrwxrwx 1 root root 0 Nov 1 11:16 exe -> /server/mysql/binary/bin/mysqld
dr-x------ 2 root root 0 Nov 1 11:16 fd
-r--r--r-- 1 root root 0 Nov 1 11:16 maps
-rw------- 1 root root 0 Nov 1 11:16 mem
-r--r--r-- 1 root root 0 Nov 1 11:16 mounts
lrwxrwxrwx 1 root root 0 Nov 1 11:16 root -> /server/mysql
-r--r--r-- 1 root root 0 Nov 1 11:16 stat
-r--r--r-- 1 root root 0 Nov 1 11:16 statm
-r--r--r-- 1 root root 0 Nov 1 11:16 status
Looks like the proccess got chrooted to /server/mysql IMHO.
Then I moved the databases directory OUTSIDE of the chrooted area to /databases and created a symlink to it.
Quote:
ps auxw | grep mysql
root 26185 0.1 0.1 3836 1088 pts/0 S 11:18 0:00 /bin/sh ./bin/safe_mysqld
mysql 26198 0.1 0.0 10524 992 pts/0 S 11:18 0:00 /server/mysql/binary/bin/mysqld --defaults-extra-file=/server/mysql/b
ls -al /proc/26198/
-r--r--r-- 1 root root 0 Nov 1 11:20 cmdline
lrwxrwxrwx 1 root root 0 Nov 1 11:20 cwd -> /databases
-r-------- 1 root root 0 Nov 1 11:20 environ
lrwxrwxrwx 1 root root 0 Nov 1 11:20 exe -> /server/mysql/binary/bin/mysqld
dr-x------ 2 root root 0 Nov 1 11:20 fd
-r--r--r-- 1 root root 0 Nov 1 11:20 maps
-rw------- 1 root root 0 Nov 1 11:20 mem
-r--r--r-- 1 root root 0 Nov 1 11:20 mounts
lrwxrwxrwx 1 root root 0 Nov 1 11:20 root -> /server/mysql
-r--r--r-- 1 root root 0 Nov 1 11:20 stat
-r--r--r-- 1 root root 0 Nov 1 11:20 statm
-r--r--r-- 1 root root 0 Nov 1 11:20 status
Shouldn't I get an error in this case cause the databases are OUTSIDE of the chrooted environment and anything outside of the chrooted area should be NOT ACCESSABLE ... seems like the mysqld chrooting acts a bit weird in this case ...
I've set up a REALLY chrooted area based up on a MySQL binary distrubution and when I do the steps again I get the expected result:
Quote:
/binary/bin/mysqld: Can't change dir to '/databases/' (Errcode: 40)
And THIS is how things should be!
Last edited by markus1982; 11-01-2002 at 05:13 AM.
Yes, if a properly chrooted process has dropped all root privileges after the chdir/chroot you should have access problems accessing stuff outside the chroot. I don't want to solely rely on the apps own (in)capacities to chroot, so that's why I use the Grsecurity patches.
To be sure use lsof and see if no files outside the chroot are accessed, and run a strace on the mysql pids as well, then if you want to do another test, here's the explanation and code.
If all tests turn out OK, then it seems you finally pulled it off, congrats. I hope you will publish your efforts somewhere, or add to any existing chroot howto so other ppl may benefit from it.
Yes, if a properly chrooted process has dropped all root privileges after the chdir/chroot you should have access problems accessing stuff outside the chroot. I don't want to solely rely on the apps own (in)capacities to chroot, so that's why I use the Grsecurity patches.
Yep, I also use the grsecurity patches, waiting for kernel v2.4.20 stable and the release of grsecurity supporting it so I can use it again! Since in v2.4.19 DMA is messed up and in v2.4.20-pre6+ it works flawlessly
Quote:
To be sure use lsof and see if no files outside the chroot are accessed, and run a strace on the mysql pids as well, then if you want to do another test, here's the explanation and code.
I bet I need more review on strace - do you know any good documents about it?
lsof is also a good idea ... will look into that one now ...
Quote:
If all tests turn out OK, then it seems you finally pulled it off, congrats. I hope you will publish your efforts somewhere, or add to any existing chroot howto so other ppl may benefit from it.
I will post it in some thread at this forum ... might just post a script and a short explanaition how I came up with the stuff provided there!
Since in v2.4.19 DMA is messed up and in v2.4.20-pre6+ it works flawlessly
Fsckin' koala's in a bloodwood tree! That's what I've been having problems with like it's going out of style! :-[
Uhm, no, I read the man page and cooked up my own script to strace already running pids:
You need beep (you already got that :-]) and cryogenic (if you don't want to cp /proc entries manually).
8<--------------------------------------------
Code:
#!/bin/sh
if [ -z "$1" ]; then exit 0; fi
prog=$(basename "$1")
base_cryo=/tmp/cryo
pids=$(/sbin/pidof "$prog")
if [ -z "$pids" ]; then pids=$(/sbin/pidof -x "$prog"); fi
if [ -z "$pids" ]; then echo "Can't find pid for "$prog""; else
for pid in $pids; do
base_pid="$base_cryo"/"$prog"-strace-"$pid-$(date +%d%m%Y_%H%M)"
mkdir "$base_pid"
cryogenic -p "$pid" "$base_pid"
lsof -p "$pid" > "$base_pid"/lsof.log
strace -f -ff -F -v -v -v -v -v -v -o "$base_pid"/strace.log -p "$pid"
beep 760
echo "Done. Results for "$prog" ("$pid") are in "$base_pid""
done
fi
cryogenic requires linux/tasks.h - I did not find that file on the whole HDD! Well I've done the task manually then using portions of your script. Result is as of lsof.log for instance:
Quote:
COMMAND PID USER FD TYPE DEVICE SIZE NODE NAME
mysqld 18012 mysql cwd DIR 3,10 4096 966657 /server/mysql/database
s
mysqld 18012 mysql rtd DIR 3,10 4096 868353 /server/mysql
mysqld 18012 mysql txt REG 3,10 2053388 950288 /server/mysql/binary/b
in/mysqld
mysqld 18012 mysql 0u CHR 136,1 3 /dev/pts/1
mysqld 18012 mysql 1u CHR 136,1 3 /dev/pts/1
mysqld 18012 mysql 2u CHR 136,1 3 /dev/pts/1
mysqld 18012 mysql 3u IPv4 501462 TCP *:mysql (LISTEN)
mysqld 18012 mysql 4u unix 0xf7971c80 501464 /tmp/mysql.sock
mysqld 18012 mysql 5r FIFO 0,5 501466 pipe
mysqld 18012 mysql 6w FIFO 0,5 501466 pipe
And /proc/18012/
Quote:
dr-xr-xr-x 3 mysql mysql 0 Nov 1 18:20 .
dr-xr-xr-x 55 root root 0 Oct 31 14:28 ..
-r--r--r-- 1 root root 0 Nov 1 18:20 cmdline
lrwxrwxrwx 1 root root 0 Nov 1 18:20 cwd -> /server/mysql/databases
-r-------- 1 root root 0 Nov 1 18:20 environ
lrwxrwxrwx 1 root root 0 Nov 1 18:20 exe -> /server/mysql/binary/bin/mysqld
dr-x------ 2 root root 0 Nov 1 18:20 fd
-r--r--r-- 1 root root 0 Nov 1 18:20 maps
-rw------- 1 root root 0 Nov 1 18:20 mem
-r--r--r-- 1 root root 0 Nov 1 18:20 mounts
lrwxrwxrwx 1 root root 0 Nov 1 18:20 root -> /server/mysql
-r--r--r-- 1 root root 0 Nov 1 18:20 stat
-r--r--r-- 1 root root 0 Nov 1 18:20 statm
-r--r--r-- 1 root root 0 Nov 1 18:20 status
Looks like a successfully chrooted proccess in my eyes ...
How I ran mysqld: chroot /server/mysql /binary/bin/mysqld --user=mysql &
Sergei Golubchik of the MySQL Development team has just emailed me that the bug has been fixed. Anyways never rely on an application security ... this is just one example!
Well I have to thank the team for that bug though. It has been a good practice and example to demonstrate that chrooting on an application based level should NEVER be trusted.
Maybe this sounds a bit paranoid ... but you all know that I am so ;-P
I've written a tutorial setting up mysql incl. chroot (and details how to chroot it). This tutorial has been published at my website. You can go directly tutorial.
Distribution: OpenBSD 4.6, OS X 10.6.2, CentOS 4 & 5
Posts: 3,660
Rep:
You're absolutely correct, you should never trust an application to chroot itself, always rely on the OS for that. There's a simple reason, the OS will force the app to operate a certain way or not at all, but the application developers might fudge a little bit if they're lazy, or incomplete in their work. If you know the the OS chrooting works correctly (from past experience with other apps), then you know (with a pretty good degree of certainty) that it will work with any app.
Distribution: OpenBSD 4.6, OS X 10.6.2, CentOS 4 & 5
Posts: 3,660
Rep:
$ man chroot
Google: chroot +linux
etc...
Briefly, chroot is a mechanism to restrict processes from being able to access the full file system. The implication of not being chroot'd properly is that a process can potentially access files that it should not be allowed to.
LinuxQuestions.org is looking for people interested in writing
Editorials, Articles, Reviews, and more. If you'd like to contribute
content, let us know.