checked in; - /hannes On Wed, Feb 25, 2004 at 12:03:30PM +0200, Pekka Savola wrote: | On Wed, 25 Feb 2004, Jefferson Ogata wrote: | > > This doesn't try to automatically create directories or whatever, but | > > relies on the compile time option (e.g. /var/empty) but is IMHO better | > > in some sense. | > | > > - if (initgroups(pw->pw_name, 0) != 0 || setgid(pw->pw_gid) != 0 || | > > + if (chroot_dir) { | > > + if (chroot(chroot_dir) != 0 || chdir (".") != 0) { | > | > No, you have to chdir to "/". Or better, do (chdir(chroot_dir) != 0 || | > chroot(".") != 0). | | Oops -- sorry for the typo! Obviously, that should be chdir("/") :) | | I was looking this after my another patch, to chroot/droproot ntp, and | didn't copy it appropriately. | | > There's one issue that occurred to me with chroot: on some | > platforms/configurations there may be a need for access to certain files outside | > the jail. If any get*byname() calls are being used, there may be a need for | > access to /etc/resolv.conf, /etc/protocols, etc. On IRIX, it's worse since all | > the get*by*() calls end up relying on access to /ns. So if -n isn't in force, | > chrooting might break some lookups. So that also argues for a commandline | > argument at least to switch it off. | | I would not enable tcpdump at compile time on such systems, so I don't | think this is a particularly nasty problem. | | -- | Pekka Savola "You each name yourselves king, yet the | Netcore Oy kingdom bleeds." | Systems. Networks. Security. -- George R.R. Martin: A Clash of Kings
| diff -ur -x configure tcpdump-2004.02.24/acconfig.h tcpdump-2004.02.23.new/acconfig.h | --- tcpdump-2004.02.24/acconfig.h Thu Jan 22 11:51:30 2004 | +++ tcpdump-2004.02.23.new/acconfig.h Wed Feb 25 09:04:41 2004 | @@ -129,3 +129,6 @@ | | /* define if should drop privileges by default */ | #undef WITH_USER | + | +/* define if should chroot when dropping privileges */ | +#undef WITH_CHROOT | diff -ur -x configure tcpdump-2004.02.24/configure.in tcpdump-2004.02.23.new/configure.in | --- tcpdump-2004.02.24/configure.in Sat Jan 31 07:26:51 2004 | +++ tcpdump-2004.02.23.new/configure.in Wed Feb 25 09:23:03 2004 | @@ -111,6 +111,15 @@ | AC_MSG_RESULT(no) | fi | | +AC_ARG_WITH(chroot, [ --with-chroot=DIRECTORY when dropping privileges, chroot to DIRECTORY]) | +AC_MSG_CHECKING([whether to chroot]) | +if test ! -z "$with_chroot" ; then | + AC_DEFINE_UNQUOTED(WITH_CHROOT, "$withval") | + AC_MSG_RESULT(to \"$withval\") | +else | + AC_MSG_RESULT(no) | +fi | + | AC_MSG_CHECKING([whether to enable ipv6]) | AC_ARG_ENABLE(ipv6, | [ --enable-ipv6 enable ipv6 (with ipv4) support | diff -ur -x configure tcpdump-2004.02.24/tcpdump.c tcpdump-2004.02.23.new/tcpdump.c | --- tcpdump-2004.02.24/tcpdump.c Tue Feb 24 10:12:18 2004 | +++ tcpdump-2004.02.23.new/tcpdump.c Wed Feb 25 09:56:25 2004 | @@ -129,7 +129,7 @@ | static void print_packet(u_char *, const struct pcap_pkthdr *, const u_char *); | static void dump_packet_and_trunc(u_char *, const struct pcap_pkthdr *, const u_char *); | static void dump_packet(u_char *, const struct pcap_pkthdr *, const u_char *); | -static void droproot(const char *); | +static void droproot(const char *, const char *); | | #ifdef SIGINFO | RETSIGTYPE requestinfo(int); | @@ -324,15 +324,26 @@ | #define U_FLAG | #endif | | -/* Drop root privileges */ | +/* Drop root privileges and chroot if necessary */ | static void | -droproot(const char *username) | +droproot(const char *username, const char *chroot_dir) | { | struct passwd *pw = NULL; | | + if (chroot_dir && !username) { | + fprintf(stderr, "Chroot without dropping root is insecure\n"); | + exit(1); | + } | + | pw = getpwnam(username); | if (pw) { | - if (initgroups(pw->pw_name, 0) != 0 || setgid(pw->pw_gid) != 0 || | + if (chroot_dir) { | + if (chroot(chroot_dir) != 0 || chdir ("/") != 0) { | + fprintf(stderr, "Couldn't chroot/chdir to '%.64s'\n", chroot_dir); | + exit(1); | + } | + } | + if (initgroups(pw->pw_name, pw->pw_gid) != 0 || setgid(pw->pw_gid) != 0 || | setuid(pw->pw_uid) != 0) { | fprintf(stderr, "Couldn't change to '%.32s' uid=%d gid=%d\n", username, | pw->pw_uid, pw->pw_gid); | @@ -386,6 +397,7 @@ | u_char *pcap_userdata; | char ebuf[PCAP_ERRBUF_SIZE]; | char *username = NULL; | + char *chroot_dir = NULL; | #ifdef HAVE_PCAP_FINDALLDEVS | pcap_if_t *devpointer; | int devnum; | @@ -704,6 +716,15 @@ | if (tflag > 0) | thiszone = gmt2local(0); | | +#ifdef WITH_CHROOT | + /* if run as root, prepare for chrooting */ | + if (getuid() == 0 || geteuid() == 0) { | + /* future extensibility for cmd-line arguments */ | + if (!chroot_dir) | + chroot_dir = WITH_CHROOT; | + } | +#endif | + | #ifdef WITH_USER | /* if run as root, prepare for dropping root privileges */ | if (getuid() == 0 || geteuid() == 0) { | @@ -885,9 +906,8 @@ | * We cannot do this earlier, because we want to be able to open | * the file (if done) for writing before giving up permissions. | */ | - if (username) { | - droproot(username); | - } | + if (username || chroot_dir) | + droproot(username, chroot_dir); | #endif /* WIN32 */ | #ifdef SIGINFO | (void)setsignal(SIGINFO, requestinfo); - This is the TCPDUMP workers list. It is archived at http://www.tcpdump.org/lists/workers/index.html To unsubscribe use mailto:[EMAIL PROTECTED]