diff options
Diffstat (limited to 'fs/hugetlbfs/inode.c')
-rw-r--r-- | fs/hugetlbfs/inode.c | 49 |
1 files changed, 15 insertions, 34 deletions
diff --git a/fs/hugetlbfs/inode.c b/fs/hugetlbfs/inode.c index cb88dac8ccaa..87a1258953b8 100644 --- a/fs/hugetlbfs/inode.c +++ b/fs/hugetlbfs/inode.c | |||
@@ -31,12 +31,10 @@ | |||
31 | #include <linux/statfs.h> | 31 | #include <linux/statfs.h> |
32 | #include <linux/security.h> | 32 | #include <linux/security.h> |
33 | #include <linux/ima.h> | 33 | #include <linux/ima.h> |
34 | #include <linux/magic.h> | ||
34 | 35 | ||
35 | #include <asm/uaccess.h> | 36 | #include <asm/uaccess.h> |
36 | 37 | ||
37 | /* some random number */ | ||
38 | #define HUGETLBFS_MAGIC 0x958458f6 | ||
39 | |||
40 | static const struct super_operations hugetlbfs_ops; | 38 | static const struct super_operations hugetlbfs_ops; |
41 | static const struct address_space_operations hugetlbfs_aops; | 39 | static const struct address_space_operations hugetlbfs_aops; |
42 | const struct file_operations hugetlbfs_file_operations; | 40 | const struct file_operations hugetlbfs_file_operations; |
@@ -44,6 +42,7 @@ static const struct inode_operations hugetlbfs_dir_inode_operations; | |||
44 | static const struct inode_operations hugetlbfs_inode_operations; | 42 | static const struct inode_operations hugetlbfs_inode_operations; |
45 | 43 | ||
46 | static struct backing_dev_info hugetlbfs_backing_dev_info = { | 44 | static struct backing_dev_info hugetlbfs_backing_dev_info = { |
45 | .name = "hugetlbfs", | ||
47 | .ra_pages = 0, /* No readahead */ | 46 | .ra_pages = 0, /* No readahead */ |
48 | .capabilities = BDI_CAP_NO_ACCT_AND_WRITEBACK, | 47 | .capabilities = BDI_CAP_NO_ACCT_AND_WRITEBACK, |
49 | }; | 48 | }; |
@@ -381,36 +380,11 @@ static void hugetlbfs_delete_inode(struct inode *inode) | |||
381 | 380 | ||
382 | static void hugetlbfs_forget_inode(struct inode *inode) __releases(inode_lock) | 381 | static void hugetlbfs_forget_inode(struct inode *inode) __releases(inode_lock) |
383 | { | 382 | { |
384 | struct super_block *sb = inode->i_sb; | 383 | if (generic_detach_inode(inode)) { |
385 | 384 | truncate_hugepages(inode, 0); | |
386 | if (!hlist_unhashed(&inode->i_hash)) { | 385 | clear_inode(inode); |
387 | if (!(inode->i_state & (I_DIRTY|I_SYNC))) | 386 | destroy_inode(inode); |
388 | list_move(&inode->i_list, &inode_unused); | ||
389 | inodes_stat.nr_unused++; | ||
390 | if (!sb || (sb->s_flags & MS_ACTIVE)) { | ||
391 | spin_unlock(&inode_lock); | ||
392 | return; | ||
393 | } | ||
394 | inode->i_state |= I_WILL_FREE; | ||
395 | spin_unlock(&inode_lock); | ||
396 | /* | ||
397 | * write_inode_now is a noop as we set BDI_CAP_NO_WRITEBACK | ||
398 | * in our backing_dev_info. | ||
399 | */ | ||
400 | write_inode_now(inode, 1); | ||
401 | spin_lock(&inode_lock); | ||
402 | inode->i_state &= ~I_WILL_FREE; | ||
403 | inodes_stat.nr_unused--; | ||
404 | hlist_del_init(&inode->i_hash); | ||
405 | } | 387 | } |
406 | list_del_init(&inode->i_list); | ||
407 | list_del_init(&inode->i_sb_list); | ||
408 | inode->i_state |= I_FREEING; | ||
409 | inodes_stat.nr_inodes--; | ||
410 | spin_unlock(&inode_lock); | ||
411 | truncate_hugepages(inode, 0); | ||
412 | clear_inode(inode); | ||
413 | destroy_inode(inode); | ||
414 | } | 388 | } |
415 | 389 | ||
416 | static void hugetlbfs_drop_inode(struct inode *inode) | 390 | static void hugetlbfs_drop_inode(struct inode *inode) |
@@ -506,6 +480,13 @@ static struct inode *hugetlbfs_get_inode(struct super_block *sb, uid_t uid, | |||
506 | inode->i_atime = inode->i_mtime = inode->i_ctime = CURRENT_TIME; | 480 | inode->i_atime = inode->i_mtime = inode->i_ctime = CURRENT_TIME; |
507 | INIT_LIST_HEAD(&inode->i_mapping->private_list); | 481 | INIT_LIST_HEAD(&inode->i_mapping->private_list); |
508 | info = HUGETLBFS_I(inode); | 482 | info = HUGETLBFS_I(inode); |
483 | /* | ||
484 | * The policy is initialized here even if we are creating a | ||
485 | * private inode because initialization simply creates an | ||
486 | * an empty rb tree and calls spin_lock_init(), later when we | ||
487 | * call mpol_free_shared_policy() it will just return because | ||
488 | * the rb tree will still be empty. | ||
489 | */ | ||
509 | mpol_shared_policy_init(&info->policy, NULL); | 490 | mpol_shared_policy_init(&info->policy, NULL); |
510 | switch (mode & S_IFMT) { | 491 | switch (mode & S_IFMT) { |
511 | default: | 492 | default: |
@@ -936,7 +917,7 @@ static int can_do_hugetlb_shm(void) | |||
936 | } | 917 | } |
937 | 918 | ||
938 | struct file *hugetlb_file_setup(const char *name, size_t size, int acctflag, | 919 | struct file *hugetlb_file_setup(const char *name, size_t size, int acctflag, |
939 | struct user_struct **user) | 920 | struct user_struct **user, int creat_flags) |
940 | { | 921 | { |
941 | int error = -ENOMEM; | 922 | int error = -ENOMEM; |
942 | struct file *file; | 923 | struct file *file; |
@@ -948,7 +929,7 @@ struct file *hugetlb_file_setup(const char *name, size_t size, int acctflag, | |||
948 | if (!hugetlbfs_vfsmount) | 929 | if (!hugetlbfs_vfsmount) |
949 | return ERR_PTR(-ENOENT); | 930 | return ERR_PTR(-ENOENT); |
950 | 931 | ||
951 | if (!can_do_hugetlb_shm()) { | 932 | if (creat_flags == HUGETLB_SHMFS_INODE && !can_do_hugetlb_shm()) { |
952 | *user = current_user(); | 933 | *user = current_user(); |
953 | if (user_shm_lock(size, *user)) { | 934 | if (user_shm_lock(size, *user)) { |
954 | WARN_ONCE(1, | 935 | WARN_ONCE(1, |