summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorpjd <pjd@FreeBSD.org>2013-03-02 09:58:47 +0000
committerpjd <pjd@FreeBSD.org>2013-03-02 09:58:47 +0000
commit73650b4f3af1f7c8b2448569209fcdff427c08db (patch)
treeed319d846a836186fac46278b94b45c60866038d
parentf77596bc521b671974f181500d0c32e3836d24ab (diff)
downloadFreeBSD-src-73650b4f3af1f7c8b2448569209fcdff427c08db.zip
FreeBSD-src-73650b4f3af1f7c8b2448569209fcdff427c08db.tar.gz
If the target file already exists, check for the CAP_UNLINKAT capabiity right
on the target directory descriptor, but only if this is renameat(2) and real target directory descriptor is given (not AT_FDCWD). Without this fix regular rename(2) fails if the target file already exists. Reported by: Michael Butler <imb@protected-networks.net> Reported by: Larry Rosenman <ler@lerctr.org> Sponsored by: The FreeBSD Foundation
-rw-r--r--sys/kern/vfs_syscalls.c17
1 files changed, 10 insertions, 7 deletions
diff --git a/sys/kern/vfs_syscalls.c b/sys/kern/vfs_syscalls.c
index 787399a..4c1d97c 100644
--- a/sys/kern/vfs_syscalls.c
+++ b/sys/kern/vfs_syscalls.c
@@ -3556,13 +3556,16 @@ kern_renameat(struct thread *td, int oldfd, char *old, int newfd, char *new,
goto out;
}
#ifdef CAPABILITIES
- /*
- * If the target already exists we require CAP_UNLINKAT
- * from 'newfd'.
- */
- error = cap_check(tond.ni_filecaps.fc_rights, CAP_UNLINKAT);
- if (error != 0)
- goto out;
+ if (newfd != AT_FDCWD) {
+ /*
+ * If the target already exists we require CAP_UNLINKAT
+ * from 'newfd'.
+ */
+ error = cap_check(tond.ni_filecaps.fc_rights,
+ CAP_UNLINKAT);
+ if (error != 0)
+ goto out;
+ }
#endif
}
if (fvp == tdvp) {
OpenPOWER on IntegriCloud