xref: /netbsd-src/tests/fs/nullfs/t_basic.c (revision bbde328be4e75ea9ad02e9715ea13ca54b797ada)
1 /*	$NetBSD: t_basic.c,v 1.1 2010/03/30 01:02:47 pooka Exp $	*/
2 
3 #include <sys/types.h>
4 #include <sys/mount.h>
5 
6 #include <atf-c.h>
7 #include <err.h>
8 #include <errno.h>
9 #include <fcntl.h>
10 #include <stdio.h>
11 #include <unistd.h>
12 #include <string.h>
13 #include <stdlib.h>
14 
15 #include <rump/rump.h>
16 #include <rump/rump_syscalls.h>
17 
18 #include <miscfs/nullfs/null.h>
19 #include <fs/tmpfs/tmpfs_args.h>
20 
21 #define USE_ATF
22 #include "../../h_macros.h"
23 
24 #ifdef USE_ATF
25 ATF_TC(basic);
26 ATF_TC_HEAD(basic, tc)
27 {
28 	atf_tc_set_md_var(tc, "descr", "basic nullfs functionality");
29 }
30 #else
31 #define atf_tc_fail(...) errx(1, __VA_ARGS__)
32 #endif
33 
34 #define MSTR "magic bus"
35 
36 static void
37 xput_tfile(const char *path, const char *mstr)
38 {
39 	int fd;
40 
41 	fd = rump_sys_open(path, O_CREAT | O_RDWR, 0777);
42 	if (fd == -1)
43 		atf_tc_fail_errno("create %s", path);
44 	if (rump_sys_write(fd, MSTR, sizeof(MSTR)) != sizeof(MSTR))
45 		atf_tc_fail_errno("write to testfile");
46 	rump_sys_close(fd);
47 }
48 
49 static int
50 xread_tfile(const char *path, const char *mstr)
51 {
52 	char buf[128];
53 	int fd;
54 
55 	fd = rump_sys_open(path, O_RDONLY);
56 	if (fd == -1)
57 		return errno;
58 	if (rump_sys_read(fd, buf, sizeof(buf)) == -1)
59 		atf_tc_fail_errno("read tfile");
60 	rump_sys_close(fd);
61 	if (strcmp(buf, MSTR) == 0)
62 		return 0;
63 	return EPROGMISMATCH;
64 }
65 
66 #ifdef USE_ATF
67 ATF_TC_BODY(basic, tc)
68 #else
69 int main(int argc, char *argv[])
70 #endif
71 {
72 	struct null_args nargs;
73 	struct tmpfs_args targs;
74 	struct stat sb;
75 	int error;
76 
77 	rump_init();
78 	if (rump_sys_mkdir("/td1", 0777) == -1)
79 		atf_tc_fail_errno("mp1");
80 	if (rump_sys_mkdir("/td2", 0777) == -1)
81 		atf_tc_fail_errno("mp1");
82 
83 	/* use tmpfs because rumpfs doesn't support regular files */
84 	memset(&targs, 0, sizeof(targs));
85 	targs.ta_version = TMPFS_ARGS_VERSION;
86 	targs.ta_root_mode = 0777;
87 	if (rump_sys_mount(MOUNT_TMPFS, "/td1", 0, &targs, sizeof(targs)) == -1)
88 		atf_tc_fail_errno("could not mount tmpfs td1");
89 
90 	memset(&nargs, 0, sizeof(nargs));
91 	nargs.nulla_target = __UNCONST("/td1");
92 	if (rump_sys_mount(MOUNT_NULL, "/td2", 0, &nargs, sizeof(nargs)) == -1)
93 		atf_tc_fail_errno("could not mount nullfs");
94 
95 	/* test unnull -> null */
96 	xput_tfile("/td1/tensti", "jeppe");
97 	error = xread_tfile("/td2/tensti", "jeppe");
98 	if (error != 0)
99 		atf_tc_fail("null compare failed: %d (%s)",
100 		    error, strerror(error));
101 
102 	/* test null -> unnull */
103 	xput_tfile("/td2/kiekko", "keppi");
104 	error = xread_tfile("/td1/kiekko", "keppi");
105 	if (error != 0)
106 		atf_tc_fail("unnull compare failed: %d (%s)",
107 		    error, strerror(error));
108 
109 	/* test unnull -> null overwrite */
110 	xput_tfile("/td1/tensti", "se oolannin sota");
111 	error = xread_tfile("/td2/tensti", "se oolannin sota");
112 	if (error != 0)
113 		atf_tc_fail("unnull compare failed: %d (%s)",
114 		    error, strerror(error));
115 
116 	/* test that /td2 is unaffected in "real life" */
117 	if (rump_sys_unmount("/td2", 0) == -1)
118 		atf_tc_fail_errno("cannot unmount nullfs");
119 	if ((error = rump_sys_stat("/td2/tensti", &sb)) != -1
120 	    || errno != ENOENT) {
121 		atf_tc_fail("stat tensti should return ENOENT, got %d", error);
122 	}
123 	if ((error = rump_sys_stat("/td2/kiekko", &sb)) != -1
124 	    || errno != ENOENT) {
125 		atf_tc_fail("stat kiekko should return ENOENT, got %d", error);
126 	}
127 
128 	/* done */
129 }
130 
131 #ifdef USE_ATF
132 ATF_TP_ADD_TCS(tp)
133 {
134 	ATF_TP_ADD_TC(tp, basic);
135 	return 0; /*XXX?*/
136 }
137 #endif
138