summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorPádraig Brady <P@draigBrady.com>2014-05-18 17:20:06 +0100
committerPádraig Brady <P@draigBrady.com>2014-05-21 11:18:27 +0100
commit0c4729516baa2fbefb0af66c38f434b1f7519078 (patch)
tree53401704e3202224cac326298cff134180d65f1e /src
parentaa1a72706bb9581fc08c63efc3bc03b908407124 (diff)
downloadcoreutils-0c4729516baa2fbefb0af66c38f434b1f7519078.tar.xz
chroot: make changing root check more robust
* src/chroot.c (is_root): A new helper function to determine if the passed argument is the root directory based on inode comparison. (main): Use the new helper rather than comparing strings. * tests/misc/chroot-fail.sh: Add cases for alternative root paths.
Diffstat (limited to 'src')
-rw-r--r--src/chroot.c19
1 files changed, 18 insertions, 1 deletions
diff --git a/src/chroot.c b/src/chroot.c
index 0ded25dec..a623f883a 100644
--- a/src/chroot.c
+++ b/src/chroot.c
@@ -28,6 +28,7 @@
#include "ignore-value.h"
#include "mgetgroups.h"
#include "quote.h"
+#include "root-dev-ino.h"
#include "userspec.h"
#include "xstrtol.h"
@@ -158,6 +159,22 @@ parse_additional_groups (char const *groups, GETGROUPS_T **pgids,
return ret;
}
+static bool
+is_root (const char* dir)
+{
+ struct dev_ino root_ino;
+ if (! get_root_dev_ino (&root_ino))
+ error (EXIT_CANCELED, errno, _("failed to get attributes of %s"),
+ quote ("/"));
+
+ struct stat arg_st;
+ if (stat (dir, &arg_st) == -1)
+ error (EXIT_CANCELED, errno, _("failed to get attributes of %s"),
+ quote (dir));
+
+ return SAME_INODE (root_ino, arg_st);
+}
+
void
usage (int status)
{
@@ -253,7 +270,7 @@ main (int argc, char **argv)
/* Only do chroot specific actions if actually changing root.
The main difference here is that we don't change working dir. */
- if (! STREQ (argv[optind], "/"))
+ if (! is_root (argv[optind]))
{
/* We have to look up users and groups twice.
- First, outside the chroot to load potentially necessary passwd/group