Skip to content

Commit a9b3876

Browse files
committed
Pull ntfs3 updates from Konstantin Komarov: "Added: - support for FS_IOC_{GET,SET}FSLABEL ioctl - reject index allocation if $BITMAP is empty but blocks exist Fixed: - integer overflow in run_unpack() - resource leak bug in wnd_extend() Changed: - pretend $Extend records as regular files - stop using write_cache_pages" * tag 'ntfs3_for_6.18' of https://github.com/Paragon-Software-Group/linux-ntfs3: ntfs3: stop using write_cache_pages fs/ntfs3: reject index allocation if $BITMAP is empty but blocks exist fs/ntfs3: Fix a resource leak bug in wnd_extend() fs: ntfs3: Fix integer overflow in run_unpack() ntfs3: pretend $Extend records as regular files ntfs3: add FS_IOC_SETFSLABEL ioctl ntfs3: add FS_IOC_GETFSLABEL ioctl ntfs3: transition magic number to shared constant
2 parents 5cb08b6 + 7d46063 commit a9b3876

File tree

6 files changed

+50
-4
lines changed

6 files changed

+50
-4
lines changed

fs/ntfs3/bitmap.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1371,6 +1371,7 @@ int wnd_extend(struct wnd_bitmap *wnd, size_t new_bits)
13711371
mark_buffer_dirty(bh);
13721372
unlock_buffer(bh);
13731373
/* err = sync_dirty_buffer(bh); */
1374+
put_bh(bh);
13741375

13751376
b0 = 0;
13761377
bits -= op;

fs/ntfs3/file.c

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,30 @@ static int ntfs_ioctl_fitrim(struct ntfs_sb_info *sbi, unsigned long arg)
4949
return 0;
5050
}
5151

52+
static int ntfs_ioctl_get_volume_label(struct ntfs_sb_info *sbi, u8 __user *buf)
53+
{
54+
if (copy_to_user(buf, sbi->volume.label, FSLABEL_MAX))
55+
return -EFAULT;
56+
57+
return 0;
58+
}
59+
60+
static int ntfs_ioctl_set_volume_label(struct ntfs_sb_info *sbi, u8 __user *buf)
61+
{
62+
u8 user[FSLABEL_MAX] = {0};
63+
int len;
64+
65+
if (!capable(CAP_SYS_ADMIN))
66+
return -EPERM;
67+
68+
if (copy_from_user(user, buf, FSLABEL_MAX))
69+
return -EFAULT;
70+
71+
len = strnlen(user, FSLABEL_MAX);
72+
73+
return ntfs_set_label(sbi, user, len);
74+
}
75+
5276
/*
5377
* ntfs_ioctl - file_operations::unlocked_ioctl
5478
*/
@@ -64,6 +88,10 @@ long ntfs_ioctl(struct file *filp, u32 cmd, unsigned long arg)
6488
switch (cmd) {
6589
case FITRIM:
6690
return ntfs_ioctl_fitrim(sbi, arg);
91+
case FS_IOC_GETFSLABEL:
92+
return ntfs_ioctl_get_volume_label(sbi, (u8 __user *)arg);
93+
case FS_IOC_SETFSLABEL:
94+
return ntfs_ioctl_set_volume_label(sbi, (u8 __user *)arg);
6795
}
6896
return -ENOTTY; /* Inappropriate ioctl for device. */
6997
}

fs/ntfs3/index.c

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1508,6 +1508,16 @@ static int indx_add_allocate(struct ntfs_index *indx, struct ntfs_inode *ni,
15081508
bmp_size = bmp_size_v = le32_to_cpu(bmp->res.data_size);
15091509
}
15101510

1511+
/*
1512+
* Index blocks exist, but $BITMAP has zero valid bits.
1513+
* This implies an on-disk corruption and must be rejected.
1514+
*/
1515+
if (in->name == I30_NAME &&
1516+
unlikely(bmp_size_v == 0 && indx->alloc_run.count)) {
1517+
err = -EINVAL;
1518+
goto out1;
1519+
}
1520+
15111521
bit = bmp_size << 3;
15121522
}
15131523

fs/ntfs3/inode.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -471,6 +471,7 @@ static struct inode *ntfs_read_mft(struct inode *inode,
471471
fname->home.seq == cpu_to_le16(MFT_REC_EXTEND)) {
472472
/* Records in $Extend are not a files or general directories. */
473473
inode->i_op = &ntfs_file_inode_operations;
474+
mode = S_IFREG;
474475
} else {
475476
err = -EINVAL;
476477
goto out;

fs/ntfs3/ntfs_fs.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -280,7 +280,7 @@ struct ntfs_sb_info {
280280
__le16 flags; // Cached current VOLUME_INFO::flags, VOLUME_FLAG_DIRTY.
281281
u8 major_ver;
282282
u8 minor_ver;
283-
char label[256];
283+
char label[FSLABEL_MAX];
284284
bool real_dirty; // Real fs state.
285285
} volume;
286286

fs/ntfs3/run.c

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
#include <linux/blkdev.h>
1010
#include <linux/fs.h>
1111
#include <linux/log2.h>
12+
#include <linux/overflow.h>
1213

1314
#include "debug.h"
1415
#include "ntfs.h"
@@ -982,14 +983,18 @@ int run_unpack(struct runs_tree *run, struct ntfs_sb_info *sbi, CLST ino,
982983

983984
if (!dlcn)
984985
return -EINVAL;
985-
lcn = prev_lcn + dlcn;
986+
987+
if (check_add_overflow(prev_lcn, dlcn, &lcn))
988+
return -EINVAL;
986989
prev_lcn = lcn;
987990
} else {
988991
/* The size of 'dlcn' can't be > 8. */
989992
return -EINVAL;
990993
}
991994

992-
next_vcn = vcn64 + len;
995+
if (check_add_overflow(vcn64, len, &next_vcn))
996+
return -EINVAL;
997+
993998
/* Check boundary. */
994999
if (next_vcn > evcn + 1)
9951000
return -EINVAL;
@@ -1153,7 +1158,8 @@ int run_get_highest_vcn(CLST vcn, const u8 *run_buf, u64 *highest_vcn)
11531158
return -EINVAL;
11541159

11551160
run_buf += size_size + offset_size;
1156-
vcn64 += len;
1161+
if (check_add_overflow(vcn64, len, &vcn64))
1162+
return -EINVAL;
11571163

11581164
#ifndef CONFIG_NTFS3_64BIT_CLUSTER
11591165
if (vcn64 > 0x100000000ull)

0 commit comments

Comments
 (0)