blob: 11300301578aa4ac9f99fbf5f08cc3b1926ef58a [file] [log] [blame]
vapierd13d74b2006-02-11 07:24:00 +00001/*
2 * Copyright (c) Wipro Technologies Ltd, 2002. All Rights Reserved.
Cyril Hrubisc437b622014-08-14 11:01:33 +02003 * Copyright (c) 2014 Cyril Hrubis <chrubis@suse.cz>
vapierd13d74b2006-02-11 07:24:00 +00004 *
5 * This program is free software; you can redistribute it and/or modify it
6 * under the terms of version 2 of the GNU General Public License as
7 * published by the Free Software Foundation.
8 *
9 * This program is distributed in the hope that it would be useful, but
10 * WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
12 *
13 * You should have received a copy of the GNU General Public License along
Wanlong Gaofed96412012-10-24 10:10:29 +080014 * with this program; if not, write the Free Software Foundation, Inc.,
15 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
vapierd13d74b2006-02-11 07:24:00 +000016 *
vapierd13d74b2006-02-11 07:24:00 +000017 * AUTHOR : Nirmala Devi Dhanasekar <nirmala.devi@wipro.com>
subrata_modak4bb656a2009-02-26 12:02:09 +000018 *
vapierd13d74b2006-02-11 07:24:00 +000019 * DESCRIPTION
20 * Check for basic errors returned by umount(2) system call.
21 *
22 * Verify that umount(2) returns -1 and sets errno to
23 *
24 * 1) EBUSY if it cannot be umounted, because dir is still busy.
25 * 2) EFAULT if specialfile or device file points to invalid address space.
26 * 3) ENOENT if pathname was empty or has a nonexistent component.
subrata_modak4bb656a2009-02-26 12:02:09 +000027 * 4) EINVAL if specialfile or device is invalid or not a mount point.
vapierd13d74b2006-02-11 07:24:00 +000028 * 5) ENAMETOOLONG if pathname was longer than MAXPATHLEN.
vapierd13d74b2006-02-11 07:24:00 +000029 *****************************************************************************/
30
31#include <errno.h>
32#include <sys/mount.h>
33#include <sys/types.h>
34#include <sys/stat.h>
35#include <sys/fcntl.h>
36#include <pwd.h>
Cyril Hrubisc437b622014-08-14 11:01:33 +020037
vapierd13d74b2006-02-11 07:24:00 +000038#include "test.h"
Cyril Hrubisc437b622014-08-14 11:01:33 +020039#include "safe_macros.h"
vapierd13d74b2006-02-11 07:24:00 +000040
vapierd13d74b2006-02-11 07:24:00 +000041static void setup(void);
42static void cleanup(void);
43
Cyril Hrubisfdce7d52013-04-04 18:35:48 +020044char *TCID = "umount02";
vapierd13d74b2006-02-11 07:24:00 +000045
vapierd13d74b2006-02-11 07:24:00 +000046#define DIR_MODE S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH
47#define FILE_MODE S_IRWXU | S_IRWXG | S_IRWXO
Cyril Hrubisc437b622014-08-14 11:01:33 +020048#define MNTPOINT "mntpoint"
vapierd13d74b2006-02-11 07:24:00 +000049
Cyril Hrubisc437b622014-08-14 11:01:33 +020050static char long_path[PATH_MAX + 2];
51static int mount_flag;
subrata_modak56207ce2009-03-23 13:35:39 +000052static int fd;
Cyril Hrubisc437b622014-08-14 11:01:33 +020053
Cyril Hrubisbe070ad2014-08-14 11:06:05 +020054static const char *device;
vapierd13d74b2006-02-11 07:24:00 +000055
56static struct test_case_t {
Cyril Hrubisc437b622014-08-14 11:01:33 +020057 char *err_desc;
58 char *mntpoint;
59 int exp_errno;
60 char *exp_retval;
vapierd13d74b2006-02-11 07:24:00 +000061} testcases[] = {
Cyril Hrubisc437b622014-08-14 11:01:33 +020062 {"Already mounted/busy", MNTPOINT, EBUSY, "EBUSY"},
63 {"Invalid address space", NULL, EFAULT, "EFAULT"},
64 {"Directory not found", "nonexistent", ENOENT, "ENOENT"},
65 {"Invalid device", "./", EINVAL, "EINVAL"},
66 {"Pathname too long", long_path, ENAMETOOLONG, "ENAMETOOLONG"}
vapierd13d74b2006-02-11 07:24:00 +000067};
68
Cyril Hrubisc437b622014-08-14 11:01:33 +020069int TST_TOTAL = ARRAY_SIZE(testcases);
vapierd13d74b2006-02-11 07:24:00 +000070
subrata_modak56207ce2009-03-23 13:35:39 +000071int main(int ac, char **av)
vapierd13d74b2006-02-11 07:24:00 +000072{
Cyril Hrubis89af32a2012-10-24 16:39:11 +020073 int lc, i;
Cyril Hrubis0b9589f2014-05-27 17:40:33 +020074 const char *msg;
vapierd13d74b2006-02-11 07:24:00 +000075
Cyril Hrubisbe070ad2014-08-14 11:06:05 +020076 if ((msg = parse_opts(ac, av, NULL, NULL)))
vapierd13d74b2006-02-11 07:24:00 +000077 tst_brkm(TBROK, NULL, "OPTION PARSING ERROR - %s", msg);
vapierd13d74b2006-02-11 07:24:00 +000078
vapierd13d74b2006-02-11 07:24:00 +000079 setup();
80
vapierd13d74b2006-02-11 07:24:00 +000081 for (lc = 0; TEST_LOOPING(lc); lc++) {
Caspar Zhangd59a6592013-03-07 14:59:12 +080082 tst_count = 0;
vapierd13d74b2006-02-11 07:24:00 +000083
84 for (i = 0; i < TST_TOTAL; ++i) {
Cyril Hrubisc437b622014-08-14 11:01:33 +020085 TEST(umount(testcases[i].mntpoint));
vapierd13d74b2006-02-11 07:24:00 +000086
subrata_modak4bb656a2009-02-26 12:02:09 +000087 if ((TEST_RETURN == -1) &&
vapierd13d74b2006-02-11 07:24:00 +000088 (TEST_ERRNO == testcases[i].exp_errno)) {
89 tst_resm(TPASS, "umount(2) expected failure; "
subrata_modak56207ce2009-03-23 13:35:39 +000090 "Got errno - %s : %s",
Cyril Hrubisc437b622014-08-14 11:01:33 +020091 testcases[i].exp_retval,
vapierd13d74b2006-02-11 07:24:00 +000092 testcases[i].err_desc);
93 } else {
94 tst_resm(TFAIL, "umount(2) failed to produce "
subrata_modak56207ce2009-03-23 13:35:39 +000095 "expected error; %d, errno:%s got %d",
vapierd13d74b2006-02-11 07:24:00 +000096 testcases[i].exp_errno,
Cyril Hrubisc437b622014-08-14 11:01:33 +020097 testcases[i].exp_retval, TEST_ERRNO);
vapierd13d74b2006-02-11 07:24:00 +000098 }
Garrett Cooper2c282152010-12-16 00:55:50 -080099 }
100 }
vapierd13d74b2006-02-11 07:24:00 +0000101
vapierd13d74b2006-02-11 07:24:00 +0000102 cleanup();
Garrett Cooper53740502010-12-16 00:04:01 -0800103 tst_exit();
Garrett Cooper2c282152010-12-16 00:55:50 -0800104}
vapierd13d74b2006-02-11 07:24:00 +0000105
Cyril Hrubis7224b782013-08-08 18:03:54 +0200106static void setup(void)
vapierd13d74b2006-02-11 07:24:00 +0000107{
Cyril Hrubisbe070ad2014-08-14 11:06:05 +0200108 const char *fs_type;
109
vapierd13d74b2006-02-11 07:24:00 +0000110 tst_sig(FORK, DEF_HANDLER, cleanup);
111
Cyril Hrubis7224b782013-08-08 18:03:54 +0200112 tst_require_root(NULL);
vapierd13d74b2006-02-11 07:24:00 +0000113
vapierd13d74b2006-02-11 07:24:00 +0000114 tst_tmpdir();
115
Cyril Hrubisbe070ad2014-08-14 11:06:05 +0200116 fs_type = tst_dev_fs_type();
117 device = tst_acquire_device(cleanup);
118
119 if (!device)
120 tst_brkm(TCONF, cleanup, "Failed to obtain block device");
121
122 tst_mkfs(cleanup, device, fs_type, NULL);
123
Cyril Hrubisc437b622014-08-14 11:01:33 +0200124 memset(long_path, 'a', PATH_MAX + 1);
125
126 SAFE_MKDIR(cleanup, MNTPOINT, DIR_MODE);
127
Cyril Hrubisbe070ad2014-08-14 11:06:05 +0200128 if (mount(device, MNTPOINT, fs_type, 0, NULL))
Cyril Hrubisc437b622014-08-14 11:01:33 +0200129 tst_brkm(TBROK | TERRNO, cleanup, "mount() failed");
130 mount_flag = 1;
131
132 fd = SAFE_OPEN(cleanup, MNTPOINT "/file", O_CREAT | O_RDWR);
vapierd13d74b2006-02-11 07:24:00 +0000133
vapierd13d74b2006-02-11 07:24:00 +0000134 TEST_PAUSE;
Garrett Cooper2c282152010-12-16 00:55:50 -0800135}
vapierd13d74b2006-02-11 07:24:00 +0000136
Cyril Hrubis7224b782013-08-08 18:03:54 +0200137static void cleanup(void)
vapierd13d74b2006-02-11 07:24:00 +0000138{
Cyril Hrubisc437b622014-08-14 11:01:33 +0200139 if (fd > 0 && close(fd))
140 tst_resm(TWARN | TERRNO, "Failed to close file");
141
Cyril Hrubisc60a2302015-01-29 16:28:24 +0100142 if (mount_flag && tst_umount(MNTPOINT))
Cyril Hrubisc437b622014-08-14 11:01:33 +0200143 tst_resm(TWARN | TERRNO, "umount() failed");
144
Cyril Hrubisbe070ad2014-08-14 11:06:05 +0200145 if (device)
146 tst_release_device(NULL, device);
vapierd13d74b2006-02-11 07:24:00 +0000147
Cyril Hrubisbe070ad2014-08-14 11:06:05 +0200148 tst_rmdir();
Chris Dearmanec6edca2012-10-17 19:54:01 -0700149}