diff options
author | Jason Wessel <jason.wessel@windriver.com> | 2014-01-23 08:32:41 -0600 |
---|---|---|
committer | Richard Purdie <richard.purdie@linuxfoundation.org> | 2014-01-28 00:52:35 +0000 |
commit | 162dd389301ce238b5003d6b4f6031256532508b (patch) | |
tree | 8100bf96362321edec26f099334102d3962c5bdd /meta | |
parent | b3bb9c770b17be4f7e1e424e0d0ec00ebe5bfb62 (diff) | |
download | poky-162dd389301ce238b5003d6b4f6031256532508b.tar.gz |
unfs3: Add a NFSv3 user mode server for use with runqemu
The user mode nfs server allows the use of runqemu without any root
privileges and may even be accelerated with kvm.
Example:
runqemu-extract-sdk tmp-eglibc/deploy/images/qemux86-64/core-image-minimal-qemux86-64.tar.bz2 rootfs
runqemu qemux86-64 `pwd`/rootfs nographic slirp kvm
[YOCTO #5639]
(From OE-Core rev: 24183f5ec9c71db936e75060387941463d30d962)
Signed-off-by: Jason Wessel <jason.wessel@windriver.com>
Signed-off-by: Saul Wold <sgw@linux.intel.com>
Signed-off-by: Richard Purdie <richard.purdie@linuxfoundation.org>
Diffstat (limited to 'meta')
10 files changed, 595 insertions, 0 deletions
diff --git a/meta/files/common-licenses/unfs3 b/meta/files/common-licenses/unfs3 new file mode 100644 index 0000000000..7f2b53f167 --- /dev/null +++ b/meta/files/common-licenses/unfs3 | |||
@@ -0,0 +1,24 @@ | |||
1 | UNFS3 user-space NFSv3 server | ||
2 | (C) 2003, Pascal Schmidt <unfs3-server@ewetel.net> | ||
3 | |||
4 | Redistribution and use in source and binary forms, with or without | ||
5 | modification, are permitted provided that the following conditions are met: | ||
6 | |||
7 | 1. Redistributions of source code must retain the above copyright notice, | ||
8 | this list of conditions and the following disclaimer. | ||
9 | 2. Redistributions in binary form must reproduce the above copyright notice, | ||
10 | this list of conditions and the following disclaimer in the documentation | ||
11 | and/or other materials provided with the distribution. | ||
12 | 3. The name of the author may not be used to endorse or promote products | ||
13 | derived from this software without specific prior written permission. | ||
14 | |||
15 | THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED | ||
16 | WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF | ||
17 | MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO | ||
18 | EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||
19 | SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, | ||
20 | PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; | ||
21 | OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, | ||
22 | WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR | ||
23 | OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF | ||
24 | ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
diff --git a/meta/recipes-devtools/unfs3/unfs3/alternate_rpc_ports.patch b/meta/recipes-devtools/unfs3/unfs3/alternate_rpc_ports.patch new file mode 100644 index 0000000000..029582ea1d --- /dev/null +++ b/meta/recipes-devtools/unfs3/unfs3/alternate_rpc_ports.patch | |||
@@ -0,0 +1,158 @@ | |||
1 | Add ability to specify rcp port numbers | ||
2 | |||
3 | In order to run more than one unfs server on a host system, you must | ||
4 | be able to specify alternate rpc port numbers. | ||
5 | |||
6 | Jason Wessel <jason.wessel@windriver.com> | ||
7 | |||
8 | Upstream-Status: Pending | ||
9 | |||
10 | --- | ||
11 | daemon.c | 44 +++++++++++++++++++++++++++++++------------- | ||
12 | mount.c | 4 ++-- | ||
13 | 2 files changed, 33 insertions(+), 15 deletions(-) | ||
14 | |||
15 | --- a/daemon.c | ||
16 | +++ b/daemon.c | ||
17 | @@ -78,6 +78,8 @@ int opt_testconfig = FALSE; | ||
18 | struct in_addr opt_bind_addr; | ||
19 | int opt_readable_executables = FALSE; | ||
20 | char *opt_pid_file = NULL; | ||
21 | +int nfs_prog = NFS3_PROGRAM; | ||
22 | +int mount_prog = MOUNTPROG; | ||
23 | |||
24 | /* Register with portmapper? */ | ||
25 | int opt_portmapper = TRUE; | ||
26 | @@ -206,7 +208,7 @@ static void parse_options(int argc, char | ||
27 | { | ||
28 | |||
29 | int opt = 0; | ||
30 | - char *optstring = "bcC:de:hl:m:n:prstTuwi:"; | ||
31 | + char *optstring = "bcC:de:hl:m:n:prstTuwi:x:y:"; | ||
32 | |||
33 | while (opt != -1) { | ||
34 | opt = getopt(argc, argv, optstring); | ||
35 | @@ -261,8 +263,24 @@ static void parse_options(int argc, char | ||
36 | printf | ||
37 | ("\t-r report unreadable executables as readable\n"); | ||
38 | printf("\t-T test exports file and exit\n"); | ||
39 | + printf("\t-x <port> alternate NFS RPC port\n"); | ||
40 | + printf("\t-y <port> alternate MOUNTD RPC port\n"); | ||
41 | exit(0); | ||
42 | break; | ||
43 | + case 'x': | ||
44 | + nfs_prog = strtol(optarg, NULL, 10); | ||
45 | + if (nfs_prog == 0) { | ||
46 | + fprintf(stderr, "Invalid NFS RPC port\n"); | ||
47 | + exit(1); | ||
48 | + } | ||
49 | + break; | ||
50 | + case 'y': | ||
51 | + mount_prog = strtol(optarg, NULL, 10); | ||
52 | + if (mount_prog == 0) { | ||
53 | + fprintf(stderr, "Invalid MOUNTD RPC port\n"); | ||
54 | + exit(1); | ||
55 | + } | ||
56 | + break; | ||
57 | case 'l': | ||
58 | opt_bind_addr.s_addr = inet_addr(optarg); | ||
59 | if (opt_bind_addr.s_addr == (unsigned) -1) { | ||
60 | @@ -347,12 +365,12 @@ void daemon_exit(int error) | ||
61 | #endif /* WIN32 */ | ||
62 | |||
63 | if (opt_portmapper) { | ||
64 | - svc_unregister(MOUNTPROG, MOUNTVERS1); | ||
65 | - svc_unregister(MOUNTPROG, MOUNTVERS3); | ||
66 | + svc_unregister(mount_prog, MOUNTVERS1); | ||
67 | + svc_unregister(mount_prog, MOUNTVERS3); | ||
68 | } | ||
69 | |||
70 | if (opt_portmapper) { | ||
71 | - svc_unregister(NFS3_PROGRAM, NFS_V3); | ||
72 | + svc_unregister(nfs_prog, NFS_V3); | ||
73 | } | ||
74 | |||
75 | if (error == SIGSEGV) | ||
76 | @@ -657,13 +675,13 @@ static void mountprog_3(struct svc_req * | ||
77 | static void register_nfs_service(SVCXPRT * udptransp, SVCXPRT * tcptransp) | ||
78 | { | ||
79 | if (opt_portmapper) { | ||
80 | - pmap_unset(NFS3_PROGRAM, NFS_V3); | ||
81 | + pmap_unset(nfs_prog, NFS_V3); | ||
82 | } | ||
83 | |||
84 | if (udptransp != NULL) { | ||
85 | /* Register NFS service for UDP */ | ||
86 | if (!svc_register | ||
87 | - (udptransp, NFS3_PROGRAM, NFS_V3, nfs3_program_3, | ||
88 | + (udptransp, nfs_prog, NFS_V3, nfs3_program_3, | ||
89 | opt_portmapper ? IPPROTO_UDP : 0)) { | ||
90 | fprintf(stderr, "%s\n", | ||
91 | "unable to register (NFS3_PROGRAM, NFS_V3, udp)."); | ||
92 | @@ -674,7 +692,7 @@ static void register_nfs_service(SVCXPRT | ||
93 | if (tcptransp != NULL) { | ||
94 | /* Register NFS service for TCP */ | ||
95 | if (!svc_register | ||
96 | - (tcptransp, NFS3_PROGRAM, NFS_V3, nfs3_program_3, | ||
97 | + (tcptransp, nfs_prog, NFS_V3, nfs3_program_3, | ||
98 | opt_portmapper ? IPPROTO_TCP : 0)) { | ||
99 | fprintf(stderr, "%s\n", | ||
100 | "unable to register (NFS3_PROGRAM, NFS_V3, tcp)."); | ||
101 | @@ -686,14 +704,14 @@ static void register_nfs_service(SVCXPRT | ||
102 | static void register_mount_service(SVCXPRT * udptransp, SVCXPRT * tcptransp) | ||
103 | { | ||
104 | if (opt_portmapper) { | ||
105 | - pmap_unset(MOUNTPROG, MOUNTVERS1); | ||
106 | - pmap_unset(MOUNTPROG, MOUNTVERS3); | ||
107 | + pmap_unset(mount_prog, MOUNTVERS1); | ||
108 | + pmap_unset(mount_prog, MOUNTVERS3); | ||
109 | } | ||
110 | |||
111 | if (udptransp != NULL) { | ||
112 | /* Register MOUNT service (v1) for UDP */ | ||
113 | if (!svc_register | ||
114 | - (udptransp, MOUNTPROG, MOUNTVERS1, mountprog_3, | ||
115 | + (udptransp, mount_prog, MOUNTVERS1, mountprog_3, | ||
116 | opt_portmapper ? IPPROTO_UDP : 0)) { | ||
117 | fprintf(stderr, "%s\n", | ||
118 | "unable to register (MOUNTPROG, MOUNTVERS1, udp)."); | ||
119 | @@ -702,7 +720,7 @@ static void register_mount_service(SVCXP | ||
120 | |||
121 | /* Register MOUNT service (v3) for UDP */ | ||
122 | if (!svc_register | ||
123 | - (udptransp, MOUNTPROG, MOUNTVERS3, mountprog_3, | ||
124 | + (udptransp, mount_prog, MOUNTVERS3, mountprog_3, | ||
125 | opt_portmapper ? IPPROTO_UDP : 0)) { | ||
126 | fprintf(stderr, "%s\n", | ||
127 | "unable to register (MOUNTPROG, MOUNTVERS3, udp)."); | ||
128 | @@ -713,7 +731,7 @@ static void register_mount_service(SVCXP | ||
129 | if (tcptransp != NULL) { | ||
130 | /* Register MOUNT service (v1) for TCP */ | ||
131 | if (!svc_register | ||
132 | - (tcptransp, MOUNTPROG, MOUNTVERS1, mountprog_3, | ||
133 | + (tcptransp, mount_prog, MOUNTVERS1, mountprog_3, | ||
134 | opt_portmapper ? IPPROTO_TCP : 0)) { | ||
135 | fprintf(stderr, "%s\n", | ||
136 | "unable to register (MOUNTPROG, MOUNTVERS1, tcp)."); | ||
137 | @@ -722,7 +740,7 @@ static void register_mount_service(SVCXP | ||
138 | |||
139 | /* Register MOUNT service (v3) for TCP */ | ||
140 | if (!svc_register | ||
141 | - (tcptransp, MOUNTPROG, MOUNTVERS3, mountprog_3, | ||
142 | + (tcptransp, mount_prog, MOUNTVERS3, mountprog_3, | ||
143 | opt_portmapper ? IPPROTO_TCP : 0)) { | ||
144 | fprintf(stderr, "%s\n", | ||
145 | "unable to register (MOUNTPROG, MOUNTVERS3, tcp)."); | ||
146 | --- a/mount.c | ||
147 | +++ b/mount.c | ||
148 | @@ -155,8 +155,8 @@ mountres3 *mountproc_mnt_3_svc(dirpath * | ||
149 | /* error out if not version 3 */ | ||
150 | if (rqstp->rq_vers != 3) { | ||
151 | logmsg(LOG_INFO, | ||
152 | - "%s attempted mount with unsupported protocol version", | ||
153 | - inet_ntoa(get_remote(rqstp))); | ||
154 | + "%s attempted mount with unsupported protocol version: %i", | ||
155 | + inet_ntoa(get_remote(rqstp)), rqstp->rq_vers); | ||
156 | result.fhs_status = MNT3ERR_INVAL; | ||
157 | return &result; | ||
158 | } | ||
diff --git a/meta/recipes-devtools/unfs3/unfs3/fix_compile_warning.patch b/meta/recipes-devtools/unfs3/unfs3/fix_compile_warning.patch new file mode 100644 index 0000000000..604824a230 --- /dev/null +++ b/meta/recipes-devtools/unfs3/unfs3/fix_compile_warning.patch | |||
@@ -0,0 +1,25 @@ | |||
1 | daemon.c: Check exit code of chdir() | ||
2 | |||
3 | Stop the compile warning and fix the code to act on a chdir() failure. | ||
4 | If this one does fail something is very, very wrong. | ||
5 | |||
6 | Signed-off-by: Jason Wessel <jason.wessel@windriver.com> | ||
7 | |||
8 | Upstream-Status: Pending | ||
9 | |||
10 | --- | ||
11 | daemon.c | 3 ++- | ||
12 | 1 file changed, 2 insertions(+), 1 deletion(-) | ||
13 | |||
14 | --- a/daemon.c | ||
15 | +++ b/daemon.c | ||
16 | @@ -964,7 +964,8 @@ int main(int argc, char **argv) | ||
17 | sigaction(SIGALRM, &act, NULL); | ||
18 | |||
19 | /* don't make directory we started in busy */ | ||
20 | - chdir("/"); | ||
21 | + if(chdir("/") < 0) | ||
22 | + daemon_exit(0); | ||
23 | |||
24 | /* detach from terminal */ | ||
25 | if (opt_detach) { | ||
diff --git a/meta/recipes-devtools/unfs3/unfs3/fix_pid_race_parent_writes_child_pid.patch b/meta/recipes-devtools/unfs3/unfs3/fix_pid_race_parent_writes_child_pid.patch new file mode 100644 index 0000000000..76d7555ea9 --- /dev/null +++ b/meta/recipes-devtools/unfs3/unfs3/fix_pid_race_parent_writes_child_pid.patch | |||
@@ -0,0 +1,61 @@ | |||
1 | daemon.c: Fix race window for writing of the pid file | ||
2 | |||
3 | The parent process should write the pid file such that the pid file | ||
4 | will can be checked immediately following exit of the fork from the | ||
5 | parent. | ||
6 | |||
7 | This allows external monitoring applications to watch the daemon | ||
8 | without having to add sleep calls to wait for the pid file be written | ||
9 | on a busy system. | ||
10 | |||
11 | Signed-off-by: Jason Wessel <jason.wessel@windriver.com> | ||
12 | |||
13 | Upstream-Status: Pending | ||
14 | |||
15 | --- | ||
16 | daemon.c | 12 +++++++++--- | ||
17 | 1 file changed, 9 insertions(+), 3 deletions(-) | ||
18 | |||
19 | --- a/daemon.c | ||
20 | +++ b/daemon.c | ||
21 | @@ -153,7 +153,7 @@ int get_socket_type(struct svc_req *rqst | ||
22 | /* | ||
23 | * write current pid to a file | ||
24 | */ | ||
25 | -static void create_pid_file(void) | ||
26 | +static void create_pid_file(int pid) | ||
27 | { | ||
28 | char buf[16]; | ||
29 | int fd, res, len; | ||
30 | @@ -175,7 +175,7 @@ static void create_pid_file(void) | ||
31 | } | ||
32 | #endif | ||
33 | |||
34 | - sprintf(buf, "%i\n", backend_getpid()); | ||
35 | + sprintf(buf, "%i\n", pid); | ||
36 | len = strlen(buf); | ||
37 | |||
38 | res = backend_pwrite(fd, buf, len, 0); | ||
39 | @@ -970,6 +970,10 @@ int main(int argc, char **argv) | ||
40 | fprintf(stderr, "could not fork into background\n"); | ||
41 | daemon_exit(0); | ||
42 | } | ||
43 | + if (pid) | ||
44 | + create_pid_file(pid); | ||
45 | + } else { | ||
46 | + create_pid_file(backend_getpid()); | ||
47 | } | ||
48 | #endif /* WIN32 */ | ||
49 | |||
50 | @@ -1006,8 +1010,10 @@ int main(int argc, char **argv) | ||
51 | /* no umask to not screw up create modes */ | ||
52 | umask(0); | ||
53 | |||
54 | +#ifdef WIN32 | ||
55 | /* create pid file if wanted */ | ||
56 | - create_pid_file(); | ||
57 | + create_pid_file(backend_getpid()); | ||
58 | +#endif | ||
59 | |||
60 | /* initialize internal stuff */ | ||
61 | fh_cache_init(); | ||
diff --git a/meta/recipes-devtools/unfs3/unfs3/fix_warnings.patch b/meta/recipes-devtools/unfs3/unfs3/fix_warnings.patch new file mode 100644 index 0000000000..ed61ea16fe --- /dev/null +++ b/meta/recipes-devtools/unfs3/unfs3/fix_warnings.patch | |||
@@ -0,0 +1,53 @@ | |||
1 | exports.*: fix warnings. | ||
2 | |||
3 | Fix these warnings: | ||
4 | lex.yy.c:1207: warning: 'yyunput' defined but not used | ||
5 | lex.yy.c:1248: warning: 'input' defined but not used | ||
6 | exports.y: In function 'set_hostname': | ||
7 | exports.y:334: warning: large integer implicitly truncated to unsigned type | ||
8 | exports.y: In function 'set_ipaddr': | ||
9 | exports.y:350: warning: large integer implicitly truncated to unsigned type | ||
10 | |||
11 | Signed-off-by: Jason Wessel <jason.wessel@windriver.com> | ||
12 | |||
13 | Upstream-Status: Pending | ||
14 | |||
15 | --- | ||
16 | Config/exports.l | 3 +++ | ||
17 | Config/exports.y | 6 ++++-- | ||
18 | 2 files changed, 7 insertions(+), 2 deletions(-) | ||
19 | |||
20 | --- a/Config/exports.l | ||
21 | +++ b/Config/exports.l | ||
22 | @@ -48,6 +48,9 @@ NETCOMP [0-9]{1,2} | ||
23 | NET {IP}"/"{NETCOMP} | ||
24 | OLDNET {IP}"/"{IP} | ||
25 | |||
26 | +%option nounput | ||
27 | +%option noinput | ||
28 | + | ||
29 | %% | ||
30 | |||
31 | ^{WHITE}*\n { /* eat empty line */ } | ||
32 | --- a/Config/exports.y | ||
33 | +++ b/Config/exports.y | ||
34 | @@ -331,7 +331,8 @@ static void set_hostname(const char *nam | ||
35 | if (ent) { | ||
36 | memcpy(&cur_host.addr, ent->h_addr_list[0], | ||
37 | sizeof(struct in_addr)); | ||
38 | - cur_host.mask.s_addr = ~0UL; | ||
39 | + cur_host.mask.s_addr = 0; | ||
40 | + cur_host.mask.s_addr = ~cur_host.mask.s_addr; | ||
41 | } else { | ||
42 | logmsg(LOG_CRIT, "could not resolve hostname '%s'", name); | ||
43 | e_error = TRUE; | ||
44 | @@ -347,7 +348,8 @@ static void set_ipaddr(const char *addr) | ||
45 | |||
46 | if (!inet_aton(addr, &cur_host.addr)) | ||
47 | e_error = TRUE; | ||
48 | - cur_host.mask.s_addr = ~0UL; | ||
49 | + cur_host.mask.s_addr = 0; | ||
50 | + cur_host.mask.s_addr = ~cur_host.mask.s_addr; | ||
51 | } | ||
52 | |||
53 | /* | ||
diff --git a/meta/recipes-devtools/unfs3/unfs3/relative_max_socket_path_len.patch b/meta/recipes-devtools/unfs3/unfs3/relative_max_socket_path_len.patch new file mode 100644 index 0000000000..17ad7b6feb --- /dev/null +++ b/meta/recipes-devtools/unfs3/unfs3/relative_max_socket_path_len.patch | |||
@@ -0,0 +1,74 @@ | |||
1 | nfs.c: Allow max sa.sun_path for a localdomain socket with the user nfs-server | ||
2 | |||
3 | There is a hard limit for the kernel of 108 characters for a | ||
4 | localdomain socket name. To avoid problems with the user nfs | ||
5 | server it should maximize the number of characters by using | ||
6 | a relative path on the server side. | ||
7 | |||
8 | Previously the nfs-server used the absolute path name passed to | ||
9 | the sa.sunpath arg for binding the socket and this has caused | ||
10 | problems for both the X server and UST binaries which make | ||
11 | heavy use of named sockets with long names. | ||
12 | |||
13 | Signed-off-by: Jason Wessel <jason.wessel@windriver.com> | ||
14 | |||
15 | Upstream-Status: Pending | ||
16 | |||
17 | --- | ||
18 | nfs.c | 29 +++++++++++++++++++++++++++-- | ||
19 | 1 file changed, 27 insertions(+), 2 deletions(-) | ||
20 | |||
21 | --- a/nfs.c | ||
22 | +++ b/nfs.c | ||
23 | @@ -672,6 +672,7 @@ SYMLINK3res *nfsproc3_symlink_3_svc(SYML | ||
24 | } | ||
25 | |||
26 | #ifndef WIN32 | ||
27 | +static char pathbuf_tmp[NFS_MAXPATHLEN + NFS_MAXNAMLEN + 1]; | ||
28 | |||
29 | /* | ||
30 | * create Unix socket | ||
31 | @@ -680,17 +681,41 @@ static int mksocket(const char *path, mo | ||
32 | { | ||
33 | int res, sock; | ||
34 | struct sockaddr_un addr; | ||
35 | + unsigned int len = strlen(path); | ||
36 | |||
37 | sock = socket(PF_UNIX, SOCK_STREAM, 0); | ||
38 | - addr.sun_family = AF_UNIX; | ||
39 | - strcpy(addr.sun_path, path); | ||
40 | res = sock; | ||
41 | if (res != -1) { | ||
42 | + addr.sun_family = AF_UNIX; | ||
43 | + if (len < sizeof(addr.sun_path) -1) { | ||
44 | + strcpy(addr.sun_path, path); | ||
45 | + } else { | ||
46 | + char *ptr; | ||
47 | + res = -1; | ||
48 | + if (len >= sizeof(path)) | ||
49 | + goto out; | ||
50 | + strcpy(pathbuf_tmp, path); | ||
51 | + ptr = strrchr(pathbuf_tmp,'/'); | ||
52 | + if (ptr) { | ||
53 | + *ptr = '\0'; | ||
54 | + ptr++; | ||
55 | + if (chdir(pathbuf_tmp)) | ||
56 | + goto out; | ||
57 | + } else { | ||
58 | + ptr = pathbuf_tmp; | ||
59 | + } | ||
60 | + if (strlen(ptr) >= sizeof(addr.sun_path)) | ||
61 | + goto out; | ||
62 | + strcpy(addr.sun_path, ptr); | ||
63 | + } | ||
64 | umask(~mode); | ||
65 | res = | ||
66 | bind(sock, (struct sockaddr *) &addr, | ||
67 | sizeof(addr.sun_family) + strlen(addr.sun_path)); | ||
68 | umask(0); | ||
69 | +out: | ||
70 | + if (chdir("/")) | ||
71 | + fprintf(stderr, "Internal failure to chdir /\n"); | ||
72 | close(sock); | ||
73 | } | ||
74 | return res; | ||
diff --git a/meta/recipes-devtools/unfs3/unfs3/rename_fh_cache.patch b/meta/recipes-devtools/unfs3/unfs3/rename_fh_cache.patch new file mode 100644 index 0000000000..37de8c3ca2 --- /dev/null +++ b/meta/recipes-devtools/unfs3/unfs3/rename_fh_cache.patch | |||
@@ -0,0 +1,64 @@ | |||
1 | From: Jason Wessel <jason.wessel@windriver.com> | ||
2 | Date: Sat, 23 Feb 2013 08:49:08 -0600 | ||
3 | Subject: [PATCH] fh_cache: fix statle nfs handle on rename problem | ||
4 | |||
5 | The following test case fails with modern linunx kernels which cache | ||
6 | the renamed inode. | ||
7 | |||
8 | % mkdir a;mkdir b;mv b a/;ls -l a | ||
9 | ls: a/b: Stale NFS file handle | ||
10 | |||
11 | The issue is that nfserver was not updating the fh_cache with the new | ||
12 | location of the inode, when it moves directories. | ||
13 | |||
14 | Signed-off-by: Jason Wessel <jason.wessel@windriver.com> | ||
15 | |||
16 | Upstream-Status: Pending | ||
17 | |||
18 | --- | ||
19 | fh_cache.c | 12 ++++++++++++ | ||
20 | fh_cache.h | 1 + | ||
21 | nfs.c | 2 ++ | ||
22 | 3 files changed, 15 insertions(+) | ||
23 | |||
24 | --- a/fh_cache.c | ||
25 | +++ b/fh_cache.c | ||
26 | @@ -199,6 +199,18 @@ static char *fh_cache_lookup(uint32 dev, | ||
27 | } | ||
28 | |||
29 | /* | ||
30 | + * update a fh inode cache for an operation like rename | ||
31 | + */ | ||
32 | +void fh_cache_update(nfs_fh3 fh, char *path) | ||
33 | +{ | ||
34 | + unfs3_fh_t *obj = (void *) fh.data.data_val; | ||
35 | + backend_statstruct buf; | ||
36 | + | ||
37 | + if (backend_lstat(path, &buf) != -1) { | ||
38 | + fh_cache_add(obj->dev, buf.st_ino, path); | ||
39 | + } | ||
40 | +} | ||
41 | +/* | ||
42 | * resolve a filename into a path | ||
43 | * cache-using wrapper for fh_decomp_raw | ||
44 | */ | ||
45 | --- a/fh_cache.h | ||
46 | +++ b/fh_cache.h | ||
47 | @@ -19,5 +19,6 @@ unfs3_fh_t fh_comp(const char *path, str | ||
48 | unfs3_fh_t *fh_comp_ptr(const char *path, struct svc_req *rqstp, int need_dir); | ||
49 | |||
50 | char *fh_cache_add(uint32 dev, uint64 ino, const char *path); | ||
51 | +void fh_cache_update(nfs_fh3 fh, char *path); | ||
52 | |||
53 | #endif | ||
54 | --- a/nfs.c | ||
55 | +++ b/nfs.c | ||
56 | @@ -876,6 +876,8 @@ RENAME3res *nfsproc3_rename_3_svc(RENAME | ||
57 | res = backend_rename(from_obj, to_obj); | ||
58 | if (res == -1) | ||
59 | result.status = rename_err(); | ||
60 | + /* Update the fh_cache with moved inode value */ | ||
61 | + fh_cache_update(argp->to.dir, to_obj); | ||
62 | } | ||
63 | } | ||
64 | |||
diff --git a/meta/recipes-devtools/unfs3/unfs3/tcp_no_delay.patch b/meta/recipes-devtools/unfs3/unfs3/tcp_no_delay.patch new file mode 100644 index 0000000000..bc78dee361 --- /dev/null +++ b/meta/recipes-devtools/unfs3/unfs3/tcp_no_delay.patch | |||
@@ -0,0 +1,56 @@ | |||
1 | daemon.c: Add option for tcp no delay | ||
2 | |||
3 | Allow the NFS tcp sockets to conditionally use TCP_NODELAY | ||
4 | |||
5 | Upstream-Status: Pending | ||
6 | |||
7 | --- | ||
8 | daemon.c | 9 ++++++++- | ||
9 | 1 file changed, 8 insertions(+), 1 deletion(-) | ||
10 | |||
11 | --- a/daemon.c | ||
12 | +++ b/daemon.c | ||
13 | @@ -17,6 +17,7 @@ | ||
14 | #ifndef WIN32 | ||
15 | #include <sys/socket.h> | ||
16 | #include <netinet/in.h> | ||
17 | +#include <netinet/tcp.h> | ||
18 | #include <arpa/inet.h> | ||
19 | #include <syslog.h> | ||
20 | #else /* WIN32 */ | ||
21 | @@ -75,6 +76,7 @@ unsigned int opt_mount_port = NFS_PORT; | ||
22 | int opt_singleuser = FALSE; | ||
23 | int opt_brute_force = FALSE; | ||
24 | int opt_testconfig = FALSE; | ||
25 | +int opt_tcp_nodelay = FALSE; | ||
26 | struct in_addr opt_bind_addr; | ||
27 | int opt_readable_executables = FALSE; | ||
28 | char *opt_pid_file = NULL; | ||
29 | @@ -208,7 +210,7 @@ static void parse_options(int argc, char | ||
30 | { | ||
31 | |||
32 | int opt = 0; | ||
33 | - char *optstring = "bcC:de:hl:m:n:prstTuwi:x:y:"; | ||
34 | + char *optstring = "bcC:de:hl:m:Nn:prstTuwi:x:y:"; | ||
35 | |||
36 | while (opt != -1) { | ||
37 | opt = getopt(argc, argv, optstring); | ||
38 | @@ -295,6 +297,9 @@ static void parse_options(int argc, char | ||
39 | exit(1); | ||
40 | } | ||
41 | break; | ||
42 | + case 'N': | ||
43 | + opt_tcp_nodelay = TRUE; | ||
44 | + break; | ||
45 | case 'n': | ||
46 | opt_nfs_port = strtol(optarg, NULL, 10); | ||
47 | if (opt_nfs_port == 0) { | ||
48 | @@ -802,6 +807,8 @@ static SVCXPRT *create_tcp_transport(uns | ||
49 | sin.sin_addr.s_addr = opt_bind_addr.s_addr; | ||
50 | sock = socket(PF_INET, SOCK_STREAM, 0); | ||
51 | setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, (const char *) &on, sizeof(on)); | ||
52 | + if (opt_tcp_nodelay) | ||
53 | + setsockopt(sock, IPPROTO_TCP, TCP_NODELAY, &on, sizeof(on)); | ||
54 | if (bind(sock, (struct sockaddr *) &sin, sizeof(struct sockaddr))) { | ||
55 | perror("bind"); | ||
56 | fprintf(stderr, "Couldn't bind to tcp port %d\n", port); | ||
diff --git a/meta/recipes-devtools/unfs3/unfs3/unfs3_parallel_build.patch b/meta/recipes-devtools/unfs3/unfs3/unfs3_parallel_build.patch new file mode 100644 index 0000000000..c7fe3d7c6b --- /dev/null +++ b/meta/recipes-devtools/unfs3/unfs3/unfs3_parallel_build.patch | |||
@@ -0,0 +1,36 @@ | |||
1 | Fix parallel build dependency issue | ||
2 | |||
3 | If building with make -j2 the lib.a will not get built in time. | ||
4 | |||
5 | Jason Wessel <jason.wessel@windriver.com> | ||
6 | |||
7 | Upstream-Status: Pending | ||
8 | |||
9 | --- | ||
10 | Config/Makefile.in | 2 ++ | ||
11 | Makefile.in | 3 ++- | ||
12 | 2 files changed, 4 insertions(+), 1 deletion(-) | ||
13 | |||
14 | --- a/Makefile.in | ||
15 | +++ b/Makefile.in | ||
16 | @@ -29,7 +29,8 @@ DESTDIR = | ||
17 | |||
18 | VPATH = $(srcdir) | ||
19 | |||
20 | -all: subdirs unfsd$(EXEEXT) | ||
21 | +all: subdirs | ||
22 | + $(MAKE) unfsd$(EXEEXT) | ||
23 | |||
24 | unfsd$(EXEEXT): $(OBJS) $(CONFOBJ) $(EXTRAOBJ) | ||
25 | $(CC) -o $@ $(OBJS) $(CONFOBJ) $(EXTRAOBJ) $(LDFLAGS) | ||
26 | --- a/Config/Makefile.in | ||
27 | +++ b/Config/Makefile.in | ||
28 | @@ -16,6 +16,8 @@ lib.a: $(OBJS) | ||
29 | $(AR) crs lib.a $(OBJS) | ||
30 | |||
31 | y.tab.h y.tab.c: $(srcdir)/exports.y | ||
32 | + | ||
33 | +y.tab.c: $(srcdir)/exports.y | ||
34 | $(YACC) -d $(srcdir)/exports.y | ||
35 | |||
36 | y.tab.o: y.tab.c $(srcdir)/exports.h $(top_srcdir)/nfs.h $(top_srcdir)/mount.h $(top_srcdir)/daemon.h | ||
diff --git a/meta/recipes-devtools/unfs3/unfs3_0.9.22.r490.bb b/meta/recipes-devtools/unfs3/unfs3_0.9.22.r490.bb new file mode 100644 index 0000000000..3d88b42733 --- /dev/null +++ b/meta/recipes-devtools/unfs3/unfs3_0.9.22.r490.bb | |||
@@ -0,0 +1,44 @@ | |||
1 | DESCRIPTION = "Userspace NFS server v3 protocol" | ||
2 | SECTION = "console/network" | ||
3 | LICENSE = "unfs3" | ||
4 | LIC_FILES_CHKSUM = "file://LICENSE;md5=9475885294e17c0cc0067820d042792e" | ||
5 | |||
6 | RDEPENDS_${PN} = "pseudo" | ||
7 | RDEPENDS_${PN}_class-native = "pseudo-native" | ||
8 | RDEPENDS_${PN}_class-nativesdk = "pseudo-nativesdk" | ||
9 | DEPENDS = "flex-native bison-native" | ||
10 | DEPENDS_class-nativesdk += "flex-nativesdk" | ||
11 | |||
12 | SRC_URI[md5sum] = "3687acc4ee992e536472365dd99712a7" | ||
13 | SRC_URI[sha256sum] = "274b43ada9c6eea1da26eb7010d72889c5278984ba0b50dff4e093057d4d64f8" | ||
14 | |||
15 | MOD_PV = "490" | ||
16 | S = "${WORKDIR}/trunk" | ||
17 | SRC_URI = "svn://svn.code.sf.net/p/unfs3/code;module=trunk;rev=${MOD_PV} \ | ||
18 | file://unfs3_parallel_build.patch \ | ||
19 | file://alternate_rpc_ports.patch \ | ||
20 | file://fix_pid_race_parent_writes_child_pid.patch \ | ||
21 | file://fix_compile_warning.patch \ | ||
22 | file://rename_fh_cache.patch \ | ||
23 | file://relative_max_socket_path_len.patch \ | ||
24 | file://fix_warnings.patch \ | ||
25 | file://tcp_no_delay.patch \ | ||
26 | " | ||
27 | BBCLASSEXTEND = "native nativesdk" | ||
28 | |||
29 | inherit autotools | ||
30 | |||
31 | # Turn off these header detects else the inode search | ||
32 | # will walk entire file systems and this is a real problem | ||
33 | # if you have 2 TB of files to walk in your file system | ||
34 | CACHED_CONFIGUREVARS = "ac_cv_header_mntent_h=no ac_cv_header_sys_mnttab_h=no" | ||
35 | |||
36 | # This recipe is intended for -native and -nativesdk builds only, | ||
37 | # not target installs: | ||
38 | python __anonymous () { | ||
39 | import re | ||
40 | |||
41 | pn = d.getVar("PN", True) | ||
42 | if not pn.endswith('-native') and not pn.startswith('nativesdk-'): | ||
43 | raise bb.parse.SkipPackage("unfs3 is intended for native/nativesdk builds only") | ||
44 | } | ||