@@ -4,7 +4,7 @@ xfs_scrub \- check and repair the contents of a mounted XFS filesystem
.SH SYNOPSIS
.B xfs_scrub
[
-.B \-abCemnTvx
+.B \-abCeMmnTvx
]
.I mount-point
.br
@@ -79,6 +79,13 @@ behavior.
.B \-k
Do not call TRIM on the free space.
.TP
+.BI \-M " real-mount-point"
+Open the this path for issuing scrub system calls to the kernel.
+The positional
+.I mount-point
+parameter will be used for displaying informational messages and logging.
+This parameter exists to enable process sandboxing for service mode.
+.TP
.BI \-m " file"
Search this file for mounted filesystems instead of /etc/mtab.
.TP
@@ -146,7 +146,7 @@ phase1_func(
* CAP_SYS_ADMIN, which we probably need to do anything fancy
* with the (XFS driver) kernel.
*/
- error = -xfd_open(&ctx->mnt, ctx->mntpoint,
+ error = -xfd_open(&ctx->mnt, ctx->actual_mntpoint,
O_RDONLY | O_NOATIME | O_DIRECTORY);
if (error) {
if (error == EPERM)
@@ -199,7 +199,7 @@ _("Not an XFS filesystem."));
return error;
}
- error = path_to_fshandle(ctx->mntpoint, &ctx->fshandle,
+ error = path_to_fshandle(ctx->actual_mntpoint, &ctx->fshandle,
&ctx->fshandle_len);
if (error) {
str_errno(ctx, _("getting fshandle"));
@@ -249,7 +249,7 @@ scan_fs_tree(
goto out_cond;
}
- ret = queue_subdir(ctx, &sft, &wq, ctx->mntpoint, true);
+ ret = queue_subdir(ctx, &sft, &wq, ctx->actual_mntpoint, true);
if (ret) {
str_liberror(ctx, ret, _("queueing directory scan"));
goto out_wq;
@@ -725,7 +725,7 @@ main(
pthread_mutex_init(&ctx.lock, NULL);
ctx.mode = SCRUB_MODE_REPAIR;
ctx.error_action = ERRORS_CONTINUE;
- while ((c = getopt(argc, argv, "a:bC:de:km:no:TvxV")) != EOF) {
+ while ((c = getopt(argc, argv, "a:bC:de:kM:m:no:TvxV")) != EOF) {
switch (c) {
case 'a':
ctx.max_errors = cvt_u64(optarg, 10);
@@ -769,6 +769,9 @@ main(
case 'k':
want_fstrim = false;
break;
+ case 'M':
+ ctx.actual_mntpoint = optarg;
+ break;
case 'm':
mtab = optarg;
break;
@@ -823,6 +826,8 @@ main(
usage();
ctx.mntpoint = argv[optind];
+ if (!ctx.actual_mntpoint)
+ ctx.actual_mntpoint = ctx.mntpoint;
stdout_isatty = isatty(STDOUT_FILENO);
stderr_isatty = isatty(STDERR_FILENO);
@@ -840,7 +845,7 @@ main(
return SCRUB_RET_OPERROR;
/* Find the mount record for the passed-in argument. */
- if (stat(argv[optind], &ctx.mnt_sb) < 0) {
+ if (stat(ctx.actual_mntpoint, &ctx.mnt_sb) < 0) {
fprintf(stderr,
_("%s: could not stat: %s: %s\n"),
progname, argv[optind], strerror(errno));
@@ -863,7 +868,7 @@ main(
}
fs_table_initialise(0, NULL, 0, NULL);
- fsp = fs_table_lookup_mount(ctx.mntpoint);
+ fsp = fs_table_lookup_mount(ctx.actual_mntpoint);
if (!fsp) {
fprintf(stderr, _("%s: Not a XFS mount point.\n"),
ctx.mntpoint);
@@ -38,9 +38,12 @@ enum error_action {
struct scrub_ctx {
/* Immutable scrub state. */
- /* Strings we need for presentation */
+ /* Mountpoint we use for presentation */
char *mntpoint;
+ /* Actual VFS path to the filesystem */
+ char *actual_mntpoint;
+
/* Mountpoint info */
struct stat mnt_sb;
struct statvfs mnt_sv;