From 6d56251220954f4937c9fafbcdb427d4aa50d330 Mon Sep 17 00:00:00 2001 From: Sami Kerola Date: Fri, 2 Aug 2019 19:39:05 +0100 Subject: mountpoint: add --nofollow option The no follow option will allow user to distinct mount points from symbolic links pointing to them. Arguably this is pretty pedantic option, mounting a device or bind mount to a directory via symlink does not have or cause any issues. Addresses: https://github.com/karelzak/util-linux/issues/832 Signed-off-by: Sami Kerola --- sys-utils/mountpoint.1 | 7 ++++++- sys-utils/mountpoint.c | 19 ++++++++++++++++--- 2 files changed, 22 insertions(+), 4 deletions(-) (limited to 'sys-utils') diff --git a/sys-utils/mountpoint.1 b/sys-utils/mountpoint.1 index afc469ebc..6669b13eb 100644 --- a/sys-utils/mountpoint.1 +++ b/sys-utils/mountpoint.1 @@ -1,4 +1,4 @@ -.TH MOUNTPOINT 1 "July 2014" "util-linux" "User Commands" +.TH MOUNTPOINT 1 "August 2019" "util-linux" "User Commands" .SH NAME mountpoint \- see if a directory or file is a mountpoint .SH SYNOPSIS @@ -28,6 +28,11 @@ directory. .BR \-q , " \-\-quiet" Be quiet - don't print anything. .TP +.B "\-\-nofollow" +Do not follow symbolic link if it the last elemnt of the +.I directory +path. +.TP .BR \-x , " \-\-devno" Show the major/minor numbers of the given blockdevice on standard output. .TP diff --git a/sys-utils/mountpoint.c b/sys-utils/mountpoint.c index 985130cba..052440bd4 100644 --- a/sys-utils/mountpoint.c +++ b/sys-utils/mountpoint.c @@ -47,6 +47,7 @@ struct mountpoint_control { unsigned int dev_devno:1, fs_devno:1, + nofollow:1, quiet:1; }; @@ -123,6 +124,7 @@ static void __attribute__((__noreturn__)) usage(void) fputs(USAGE_OPTIONS, out); fputs(_(" -q, --quiet quiet mode - don't print anything\n" + " --nofollow do not follow symlink\n" " -d, --fs-devno print maj:min device number of the filesystem\n" " -x, --devno print maj:min device number of the block device\n"), out); fputs(USAGE_SEPARATOR, out); @@ -137,8 +139,13 @@ int main(int argc, char **argv) int c; struct mountpoint_control ctl = { NULL }; + enum { + OPT_NOFOLLOW = CHAR_MAX + 1 + }; + static const struct option longopts[] = { { "quiet", no_argument, NULL, 'q' }, + { "nofollow", no_argument, NULL, OPT_NOFOLLOW }, { "fs-devno", no_argument, NULL, 'd' }, { "devno", no_argument, NULL, 'x' }, { "help", no_argument, NULL, 'h' }, @@ -159,6 +166,9 @@ int main(int argc, char **argv) case 'q': ctl.quiet = 1; break; + case OPT_NOFOLLOW: + ctl.nofollow = 1; + break; case 'd': ctl.fs_devno = 1; break; @@ -179,17 +189,20 @@ int main(int argc, char **argv) warnx(_("bad usage")); errtryhelp(EXIT_FAILURE); } + if (ctl.nofollow && ctl.dev_devno) + errx(EXIT_FAILURE, _("%s and %s are mutually exclusive"), + "--devno", "--nofollow"); ctl.path = argv[optind]; - - if (stat(ctl.path, &ctl.st)) { + c = ctl.nofollow ? lstat(ctl.path, &ctl.st) : stat(ctl.path, &ctl.st); + if (c) { if (!ctl.quiet) err(EXIT_FAILURE, "%s", ctl.path); return EXIT_FAILURE; } if (ctl.dev_devno) return print_devno(&ctl) ? EXIT_FAILURE : EXIT_SUCCESS; - if (dir_to_device(&ctl)) { + if ((ctl.nofollow && S_ISLNK(ctl.st.st_mode)) || dir_to_device(&ctl)) { if (!ctl.quiet) printf(_("%s is not a mountpoint\n"), ctl.path); return EXIT_FAILURE; -- cgit v1.2.3-55-g7522