From: Thomas Veerman Date: Fri, 8 Mar 2013 14:17:13 +0000 (+0000) Subject: UDS: terminate canonical path string X-Git-Tag: v3.3.0~1096 X-Git-Url: http://zhaoyanbai.com/repos/%22http:/www.isc.org/icons/mdoc.3.txt?a=commitdiff_plain;h=76ddef10daacc4ff06e1afee29e2945b621cef5b;p=minix.git UDS: terminate canonical path string When you provided a string with junk after the terminating nul to a UNIX domain socket and used bind(2), the canonical path function would not properly terminate the new string. This caused VFS to return ENAMETOOLONG on an otherwise valid path name. Test case is added to test56. Change-Id: I883b6be23d9e4ea13c3cee28cbb3726343df037f --- diff --git a/servers/vfs/path.c b/servers/vfs/path.c index 242fe3eb8..6c0d2bbdf 100644 --- a/servers/vfs/path.c +++ b/servers/vfs/path.c @@ -760,14 +760,14 @@ struct fproc *rfp; } /* now we have to retrieve the name of the parent directory */ - if (get_name(parent_dir, dir_vp, component) != OK) { + if ((r = get_name(parent_dir, dir_vp, component)) != OK) { unlock_vnode(parent_dir); unlock_vmnt(parent_vmp); unlock_vnode(dir_vp); unlock_vmnt(dir_vmp); put_vnode(parent_dir); put_vnode(dir_vp); - return(ENOENT); + return(r); } len += strlen(component) + 1; @@ -809,7 +809,7 @@ struct fproc *rfp; /* add the leading slash */ len = strlen(orig_path); if (strlen(orig_path) >= PATH_MAX) return(ENAMETOOLONG); - memmove(orig_path+1, orig_path, len); + memmove(orig_path+1, orig_path, len + 1 /* include terminating nul */); orig_path[0] = '/'; /* remove trailing slash if there is any */ diff --git a/test/test56.c b/test/test56.c index 13751d515..eb3b0f33a 100644 --- a/test/test56.c +++ b/test/test56.c @@ -567,6 +567,21 @@ void test_bind(void) UNLINK(TEST_SYM_A); UNLINK(TEST_SYM_B); + /* Test bind with garbage in sockaddr_un */ + memset(&addr, '?', sizeof(struct sockaddr_un)); + addr.sun_family = AF_UNIX; + addr.sun_path[0] = 'f'; + addr.sun_path[1] = 'o'; + addr.sun_path[2] = 'o'; + addr.sun_path[3] = '\0'; + SOCKET(sd, PF_UNIX, SOCK_STREAM, 0); + rc = bind(sd, (struct sockaddr *) &addr, strlen(addr.sun_path) + 1); + if (rc == -1) { + test_fail("bind() should have worked"); + } + CLOSE(sd); + UNLINK(TEST_SUN_PATH); + debug("leaving test_bind()"); }