diff options
author | Justus Winter <4winter@informatik.uni-hamburg.de> | 2014-06-10 14:22:31 +0200 |
---|---|---|
committer | Justus Winter <4winter@informatik.uni-hamburg.de> | 2014-06-18 15:57:00 +0200 |
commit | 944cfdbe6cff4e8025a730228b48c1a21b4a2e33 (patch) | |
tree | 32accaee79c274514ead2fadd1a9975b2000fe8b | |
parent | 8821d8a213008eb723414c6c70de384830ea10d7 (diff) |
libdiskfs: add permission check to file_chflags
Only root is allowed to change the high 16 bits. The TODO entry says
otherwise, but that must be a mistake. For reference, see the glibc
sources, sysdeps/mach/hurd/bits/stat.h.
* libdiskfs/file-chflags.c (diskfs_S_file_chflags): Add permission
check.
* TODO (libdiskfs): Remove entry.
-rw-r--r-- | TODO | 2 | ||||
-rw-r--r-- | libdiskfs/file-chflags.c | 8 |
2 files changed, 8 insertions, 2 deletions
@@ -108,8 +108,6 @@ See `tasks', the exported task list. Rename the rest to libhurdutil or somesuch. ** libdiskfs -*** file_chflags does not do proper permission checking (non-root isn't - supposed to be able to change the low bits) *** Add the short-circuited-but-not-builtin translator startup code from dir-lookup to fsys_getroot. Compare and match carefully these two routines and then share common code. diff --git a/libdiskfs/file-chflags.c b/libdiskfs/file-chflags.c index 01dc495c..a29ff07c 100644 --- a/libdiskfs/file-chflags.c +++ b/libdiskfs/file-chflags.c @@ -23,8 +23,15 @@ kern_return_t diskfs_S_file_chflags (struct protid *cred, int flags) { +#define HI(X) ((X) & 0xffff0000u) CHANGE_NODE_FIELD (cred, ({ + /* Only root is allowed to change the high 16 + bits. */ + if ((HI (flags) != HI (np->dn_stat.st_flags)) + && ! idvec_contains (cred->user->uids, 0)) + return EPERM; + err = fshelp_isowner (&np->dn_stat, cred->user); if (!err) err = diskfs_validate_flags_change (np, flags); @@ -37,4 +44,5 @@ diskfs_S_file_chflags (struct protid *cred, diskfs_notice_filechange(np, FILE_CHANGED_META, 0, 0); })); +#undef HI } |