-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
We introduce a module parameter that enforces a umask on /dev/zfs. It was originally meant to be set only at module load time, but some difficulties with `modprobe zfs zfsdev_umask=777` in local testing lead me to allow its owner (default root) to change it at runtime. This should ease the transition for those that rely on this behavior, provided that we state in the release notes that future releases are expected to remove the ability to modify it at runtime. When the cause of that modprobe command failing to set the module is found, we can tighten the permissions for a future release. Closes openzfs#4100 Signed-off-by: Richard Yao <[email protected]>
- Loading branch information
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -195,6 +195,9 @@ | |
kmutex_t zfsdev_state_lock; | ||
zfsdev_state_t *zfsdev_state_list; | ||
|
||
/* The bits are stored in decimal format, not octal */ | ||
int zfsdev_umask = 77; | ||
This comment has been minimized.
Sorry, something went wrong.
This comment has been minimized.
Sorry, something went wrong.
behlendorf
|
||
|
||
extern void zfs_init(void); | ||
extern void zfs_fini(void); | ||
|
||
|
@@ -5776,6 +5779,29 @@ zfsdev_release(struct inode *ino, struct file *filp) | |
return (-error); | ||
} | ||
|
||
boolean_t | ||
zfsdev_fail_cred_check(struct file *filp) | ||
This comment has been minimized.
Sorry, something went wrong.
This comment has been minimized.
Sorry, something went wrong. |
||
{ | ||
umode_t umode = filp->f_inode->i_mode; | ||
This comment has been minimized.
Sorry, something went wrong.
behlendorf
|
||
|
||
if (!(filp->f_mode & (FMODE_WRITE|FMODE_READ))) | ||
return (B_TRUE); | ||
|
||
/* Check other credential */ | ||
if (((~zfsdev_umask & umode) & 8) >= 6) | ||
return (B_FALSE); | ||
This comment has been minimized.
Sorry, something went wrong.
behlendorf
|
||
|
||
/* Check group credential */ | ||
if (((~(zfsdev_umask / 10) & (umode >> 4)) & 8) >= 6) | ||
return (B_FALSE); | ||
|
||
/* Check user credential */ | ||
if (((~(zfsdev_umask / 100) & (umode >> 8)) & 8) >= 6) | ||
return (B_FALSE); | ||
|
||
return (B_TRUE); | ||
} | ||
|
||
static long | ||
zfsdev_ioctl(struct file *filp, unsigned cmd, unsigned long arg) | ||
{ | ||
|
@@ -5787,6 +5813,9 @@ zfsdev_ioctl(struct file *filp, unsigned cmd, unsigned long arg) | |
nvlist_t *innvl = NULL; | ||
fstrans_cookie_t cookie; | ||
|
||
if (zfsdev_fail_cred_check(filp)) | ||
This comment has been minimized.
Sorry, something went wrong.
behlendorf
|
||
return (-SET_ERROR(EPERM)); | ||
|
||
vecnum = cmd - ZFS_IOC_FIRST; | ||
if (vecnum >= sizeof (zfs_ioc_vec) / sizeof (zfs_ioc_vec[0])) | ||
return (-SET_ERROR(EINVAL)); | ||
|
@@ -6075,6 +6104,9 @@ _fini(void) | |
module_init(_init); | ||
module_exit(_fini); | ||
|
||
module_param(zfsdev_umask, int, 0644); | ||
MODULE_PARM_DESC(zfsdev_umask, "/dev/zfs umask"); | ||
This comment has been minimized.
Sorry, something went wrong.
behlendorf
|
||
|
||
MODULE_DESCRIPTION("ZFS"); | ||
MODULE_AUTHOR(ZFS_META_AUTHOR); | ||
MODULE_LICENSE(ZFS_META_LICENSE); | ||
|
I'd suggest using octal here, I think it's what users will expect when working with a umask. The kernel helpers should understand octal so I don't expect any problems, but I haven't verified this.