diff options
-rw-r--r-- | fs/fat/dir.c | 22 | ||||
-rw-r--r-- | include/uapi/linux/msdos_fs.h | 1 |
2 files changed, 20 insertions, 3 deletions
diff --git a/fs/fat/dir.c b/fs/fat/dir.c index cb0e9b10953..9feae8c2c61 100644 --- a/fs/fat/dir.c +++ b/fs/fat/dir.c @@ -783,6 +783,24 @@ static int fat_ioctl_volume_id(struct inode *dir) return sbi->vol_id; } +static long fat_dir_generic_ioctl(struct file *filp, unsigned int cmd, + unsigned long arg) +{ + struct inode *inode = file_inode(filp); + u32 id; + + switch (cmd) { + case VFAT_IOCTL_GET_VOLUME_ID_BROKEN: + return fat_ioctl_volume_id(inode); + case VFAT_IOCTL_GET_VOLUME_ID: + if (inode->i_ino != MSDOS_ROOT_INO) + return -EINVAL; + id = fat_ioctl_volume_id(inode); + return copy_to_user((u32 *)arg, &id, sizeof(id)); + } + return fat_generic_ioctl(filp, cmd, arg); +} + static long fat_dir_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) { @@ -799,10 +817,8 @@ static long fat_dir_ioctl(struct file *filp, unsigned int cmd, short_only = 0; both = 1; break; - case VFAT_IOCTL_GET_VOLUME_ID_BROKEN: - return fat_ioctl_volume_id(inode); default: - return fat_generic_ioctl(filp, cmd, arg); + return fat_dir_generic_ioctl(filp, cmd, arg); } if (!access_ok(VERIFY_WRITE, d1, sizeof(struct __fat_dirent[2]))) diff --git a/include/uapi/linux/msdos_fs.h b/include/uapi/linux/msdos_fs.h index fddfc61418d..b322512e2b2 100644 --- a/include/uapi/linux/msdos_fs.h +++ b/include/uapi/linux/msdos_fs.h @@ -105,6 +105,7 @@ struct __fat_dirent { #define FAT_IOCTL_GET_ATTRIBUTES _IOR('r', 0x10, __u32) #define FAT_IOCTL_SET_ATTRIBUTES _IOW('r', 0x11, __u32) #define VFAT_IOCTL_GET_VOLUME_ID_BROKEN _IOR('r', 0x12, __u32) +#define VFAT_IOCTL_GET_VOLUME_ID _IOR('r', 0x13, __u32) struct fat_boot_sector { __u8 ignored[3]; /* Boot strap short or near jump */ |