hc
2024-12-19 9370bb92b2d16684ee45cf24e879c93c509162da
kernel/fs/ntfs/inode.c
....@@ -1,22 +1,8 @@
1
+// SPDX-License-Identifier: GPL-2.0-or-later
12 /**
23 * inode.c - NTFS kernel inode handling.
34 *
45 * Copyright (c) 2001-2014 Anton Altaparmakov and Tuxera Inc.
5
- *
6
- * This program/include file is free software; you can redistribute it and/or
7
- * modify it under the terms of the GNU General Public License as published
8
- * by the Free Software Foundation; either version 2 of the License, or
9
- * (at your option) any later version.
10
- *
11
- * This program/include file is distributed in the hope that it will be
12
- * useful, but WITHOUT ANY WARRANTY; without even the implied warranty
13
- * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
- * GNU General Public License for more details.
15
- *
16
- * You should have received a copy of the GNU General Public License
17
- * along with this program (in the main directory of the Linux-NTFS
18
- * distribution in the file COPYING); if not, write to the Free Software
19
- * Foundation,Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
206 */
217
228 #include <linux/buffer_head.h>
....@@ -44,10 +30,10 @@
4430 /**
4531 * ntfs_test_inode - compare two (possibly fake) inodes for equality
4632 * @vi: vfs inode which to test
47
- * @na: ntfs attribute which is being tested with
33
+ * @data: data which is being tested with
4834 *
4935 * Compare the ntfs attribute embedded in the ntfs specific part of the vfs
50
- * inode @vi for equality with the ntfs attribute @na.
36
+ * inode @vi for equality with the ntfs attribute @data.
5137 *
5238 * If searching for the normal file/directory inode, set @na->type to AT_UNUSED.
5339 * @na->name and @na->name_len are then ignored.
....@@ -57,8 +43,9 @@
5743 * NOTE: This function runs with the inode_hash_lock spin lock held so it is not
5844 * allowed to sleep.
5945 */
60
-int ntfs_test_inode(struct inode *vi, ntfs_attr *na)
46
+int ntfs_test_inode(struct inode *vi, void *data)
6147 {
48
+ ntfs_attr *na = (ntfs_attr *)data;
6249 ntfs_inode *ni;
6350
6451 if (vi->i_ino != na->mft_no)
....@@ -86,9 +73,9 @@
8673 /**
8774 * ntfs_init_locked_inode - initialize an inode
8875 * @vi: vfs inode to initialize
89
- * @na: ntfs attribute which to initialize @vi to
76
+ * @data: data which to initialize @vi to
9077 *
91
- * Initialize the vfs inode @vi with the values from the ntfs attribute @na in
78
+ * Initialize the vfs inode @vi with the values from the ntfs attribute @data in
9279 * order to enable ntfs_test_inode() to do its work.
9380 *
9481 * If initializing the normal file/directory inode, set @na->type to AT_UNUSED.
....@@ -101,8 +88,9 @@
10188 * NOTE: This function runs with the inode->i_lock spin lock held so it is not
10289 * allowed to sleep. (Hence the GFP_ATOMIC allocation.)
10390 */
104
-static int ntfs_init_locked_inode(struct inode *vi, ntfs_attr *na)
91
+static int ntfs_init_locked_inode(struct inode *vi, void *data)
10592 {
93
+ ntfs_attr *na = (ntfs_attr *)data;
10694 ntfs_inode *ni = NTFS_I(vi);
10795
10896 vi->i_ino = na->mft_no;
....@@ -145,7 +133,6 @@
145133 return 0;
146134 }
147135
148
-typedef int (*set_t)(struct inode *, void *);
149136 static int ntfs_read_locked_inode(struct inode *vi);
150137 static int ntfs_read_locked_attr_inode(struct inode *base_vi, struct inode *vi);
151138 static int ntfs_read_locked_index_inode(struct inode *base_vi,
....@@ -178,8 +165,8 @@
178165 na.name = NULL;
179166 na.name_len = 0;
180167
181
- vi = iget5_locked(sb, mft_no, (test_t)ntfs_test_inode,
182
- (set_t)ntfs_init_locked_inode, &na);
168
+ vi = iget5_locked(sb, mft_no, ntfs_test_inode,
169
+ ntfs_init_locked_inode, &na);
183170 if (unlikely(!vi))
184171 return ERR_PTR(-ENOMEM);
185172
....@@ -239,8 +226,8 @@
239226 na.name = name;
240227 na.name_len = name_len;
241228
242
- vi = iget5_locked(base_vi->i_sb, na.mft_no, (test_t)ntfs_test_inode,
243
- (set_t)ntfs_init_locked_inode, &na);
229
+ vi = iget5_locked(base_vi->i_sb, na.mft_no, ntfs_test_inode,
230
+ ntfs_init_locked_inode, &na);
244231 if (unlikely(!vi))
245232 return ERR_PTR(-ENOMEM);
246233
....@@ -294,8 +281,8 @@
294281 na.name = name;
295282 na.name_len = name_len;
296283
297
- vi = iget5_locked(base_vi->i_sb, na.mft_no, (test_t)ntfs_test_inode,
298
- (set_t)ntfs_init_locked_inode, &na);
284
+ vi = iget5_locked(base_vi->i_sb, na.mft_no, ntfs_test_inode,
285
+ ntfs_init_locked_inode, &na);
299286 if (unlikely(!vi))
300287 return ERR_PTR(-ENOMEM);
301288
....@@ -332,21 +319,9 @@
332319 return NULL;
333320 }
334321
335
-static void ntfs_i_callback(struct rcu_head *head)
322
+void ntfs_free_big_inode(struct inode *inode)
336323 {
337
- struct inode *inode = container_of(head, struct inode, i_rcu);
338324 kmem_cache_free(ntfs_big_inode_cache, NTFS_I(inode));
339
-}
340
-
341
-void ntfs_destroy_big_inode(struct inode *inode)
342
-{
343
- ntfs_inode *ni = NTFS_I(inode);
344
-
345
- ntfs_debug("Entering.");
346
- BUG_ON(ni->page);
347
- if (!atomic_dec_and_test(&ni->count))
348
- BUG();
349
- call_rcu(&inode->i_rcu, ntfs_i_callback);
350325 }
351326
352327 static inline ntfs_inode *ntfs_alloc_extent_inode(void)
....@@ -1854,6 +1829,13 @@
18541829 goto err_out;
18551830 }
18561831
1832
+ /* Sanity check offset to the first attribute */
1833
+ if (le16_to_cpu(m->attrs_offset) >= le32_to_cpu(m->bytes_allocated)) {
1834
+ ntfs_error(sb, "Incorrect mft offset to the first attribute %u in superblock.",
1835
+ le16_to_cpu(m->attrs_offset));
1836
+ goto err_out;
1837
+ }
1838
+
18571839 /* Need this to sanity check attribute list references to $MFT. */
18581840 vi->i_generation = ni->seq_no = le16_to_cpu(m->sequence_number);
18591841
....@@ -1906,6 +1888,10 @@
19061888 }
19071889 /* Now allocate memory for the attribute list. */
19081890 ni->attr_list_size = (u32)ntfs_attr_size(a);
1891
+ if (!ni->attr_list_size) {
1892
+ ntfs_error(sb, "Attr_list_size is zero");
1893
+ goto put_err_out;
1894
+ }
19091895 ni->attr_list = ntfs_malloc_nofs(ni->attr_list_size);
19101896 if (!ni->attr_list) {
19111897 ntfs_error(sb, "Not enough memory to allocate buffer "
....@@ -2299,6 +2285,9 @@
22992285 ni->ext.base_ntfs_ino = NULL;
23002286 }
23012287 }
2288
+ BUG_ON(ni->page);
2289
+ if (!atomic_dec_and_test(&ni->count))
2290
+ BUG();
23022291 return;
23032292 }
23042293
....@@ -2935,14 +2924,11 @@
29352924 }
29362925 }
29372926 if (ia_valid & ATTR_ATIME)
2938
- vi->i_atime = timespec64_trunc(attr->ia_atime,
2939
- vi->i_sb->s_time_gran);
2927
+ vi->i_atime = attr->ia_atime;
29402928 if (ia_valid & ATTR_MTIME)
2941
- vi->i_mtime = timespec64_trunc(attr->ia_mtime,
2942
- vi->i_sb->s_time_gran);
2929
+ vi->i_mtime = attr->ia_mtime;
29432930 if (ia_valid & ATTR_CTIME)
2944
- vi->i_ctime = timespec64_trunc(attr->ia_ctime,
2945
- vi->i_sb->s_time_gran);
2931
+ vi->i_ctime = attr->ia_ctime;
29462932 mark_inode_dirty(vi);
29472933 out:
29482934 return err;