Sign Up
Log In
Log In
or
Sign Up
Places
All Projects
Status Monitor
Collapse sidebar
SUSE:SLE-12-SP2:Update
qemu-linux-user
0177-9pfs-local-rename-use-renameat.patch
Overview
Repositories
Revisions
Requests
Users
Attributes
Meta
File 0177-9pfs-local-rename-use-renameat.patch of Package qemu-linux-user
From: Greg Kurz <groug@kaod.org> Date: Sun, 26 Feb 2017 23:44:03 +0100 Subject: 9pfs: local: rename: use renameat The local_rename() callback is vulnerable to symlink attacks because it uses rename() which follows symbolic links in all path elements but the rightmost one. This patch simply transforms local_rename() into a wrapper around local_renameat() which is symlink-attack safe. This partly fixes CVE-2016-9602. Signed-off-by: Greg Kurz <groug@kaod.org> Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com> (cherry picked from commit d2767edec582558f1e6c52e1dd9370d62e2b30fc) [BR: Fix and/or infrastructure for BSC#1020427 CVE-2016-9602] Signed-off-by: Bruce Rogers <brogers@suse.com> --- hw/9pfs/9p-local.c | 57 ++++++++++++++++++++++------------------------ 1 file changed, 27 insertions(+), 30 deletions(-) diff --git a/hw/9pfs/9p-local.c b/hw/9pfs/9p-local.c index 8e58111129a77044218e2c9709ba..7b1f234156fb80028ba39e66167f 100644 --- a/hw/9pfs/9p-local.c +++ b/hw/9pfs/9p-local.c @@ -963,36 +963,6 @@ static int local_truncate(FsContext *ctx, V9fsPath *fs_path, off_t size) return ret; } -static int local_rename(FsContext *ctx, const char *oldpath, - const char *newpath) -{ - int err; - char *buffer, *buffer1; - - if (ctx->export_flags & V9FS_SM_MAPPED_FILE) { - err = local_create_mapped_attr_dir(ctx, newpath); - if (err < 0) { - return err; - } - /* rename the .virtfs_metadata files */ - buffer = local_mapped_attr_path(ctx, oldpath); - buffer1 = local_mapped_attr_path(ctx, newpath); - err = rename(buffer, buffer1); - g_free(buffer); - g_free(buffer1); - if (err < 0 && errno != ENOENT) { - return err; - } - } - - buffer = rpath(ctx, oldpath); - buffer1 = rpath(ctx, newpath); - err = rename(buffer, buffer1); - g_free(buffer); - g_free(buffer1); - return err; -} - static int local_chown(FsContext *fs_ctx, V9fsPath *fs_path, FsCred *credp) { char *buffer; @@ -1256,6 +1226,33 @@ out: return ret; } +static void v9fs_path_init_dirname(V9fsPath *path, const char *str) +{ + path->data = g_path_get_dirname(str); + path->size = strlen(path->data) + 1; +} + +static int local_rename(FsContext *ctx, const char *oldpath, + const char *newpath) +{ + int err; + char *oname = g_path_get_basename(oldpath); + char *nname = g_path_get_basename(newpath); + V9fsPath olddir, newdir; + + v9fs_path_init_dirname(&olddir, oldpath); + v9fs_path_init_dirname(&newdir, newpath); + + err = local_renameat(ctx, &olddir, oname, &newdir, nname); + + v9fs_path_free(&newdir); + v9fs_path_free(&olddir); + g_free(nname); + g_free(oname); + + return err; +} + static int local_unlinkat(FsContext *ctx, V9fsPath *dir, const char *name, int flags) {
Locations
Projects
Search
Status Monitor
Help
OpenBuildService.org
Documentation
API Documentation
Code of Conduct
Contact
Support
@OBShq
Terms
openSUSE Build Service is sponsored by
The Open Build Service is an
openSUSE project
.
Sign Up
Log In
Places
Places
All Projects
Status Monitor