diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2009-06-17 12:46:33 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2009-06-17 12:46:33 -0400 |
commit | b7c142dbf1e7422d0be7f7faa3f1163ad9da9788 (patch) | |
tree | 6e62c8654bb9c329f89246235062ac2a289960df /fs/ubifs/super.c | |
parent | 0bd8df908de2aefe312d05bd25cd3abc21a6d1da (diff) | |
parent | f2c5dbd7b7396457efc114f825acfdd4db4608f8 (diff) |
Merge branch 'linux-next' of git://git.infradead.org/ubifs-2.6
* 'linux-next' of git://git.infradead.org/ubifs-2.6:
UBIFS: start using hrtimers
hrtimer: export ktime_add_safe
UBIFS: do not forget to register BDI device
UBIFS: allow sync option in rootflags
UBIFS: remove dead code
UBIFS: use anonymous device
UBIFS: return proper error code if the compr is not present
UBIFS: return error if link and unlink race
UBIFS: reset no_space flag after inode deletion
Diffstat (limited to 'fs/ubifs/super.c')
-rw-r--r-- | fs/ubifs/super.c | 73 |
1 files changed, 48 insertions, 25 deletions
diff --git a/fs/ubifs/super.c b/fs/ubifs/super.c index 3260b73abe29..79fad43f3c57 100644 --- a/fs/ubifs/super.c +++ b/fs/ubifs/super.c | |||
@@ -361,6 +361,11 @@ static void ubifs_delete_inode(struct inode *inode) | |||
361 | out: | 361 | out: |
362 | if (ui->dirty) | 362 | if (ui->dirty) |
363 | ubifs_release_dirty_inode_budget(c, ui); | 363 | ubifs_release_dirty_inode_budget(c, ui); |
364 | else { | ||
365 | /* We've deleted something - clean the "no space" flags */ | ||
366 | c->nospace = c->nospace_rp = 0; | ||
367 | smp_wmb(); | ||
368 | } | ||
364 | clear_inode(inode); | 369 | clear_inode(inode); |
365 | } | 370 | } |
366 | 371 | ||
@@ -792,7 +797,7 @@ static int alloc_wbufs(struct ubifs_info *c) | |||
792 | * does not need to be synchronized by timer. | 797 | * does not need to be synchronized by timer. |
793 | */ | 798 | */ |
794 | c->jheads[GCHD].wbuf.dtype = UBI_LONGTERM; | 799 | c->jheads[GCHD].wbuf.dtype = UBI_LONGTERM; |
795 | c->jheads[GCHD].wbuf.timeout = 0; | 800 | c->jheads[GCHD].wbuf.softlimit = ktime_set(0, 0); |
796 | 801 | ||
797 | return 0; | 802 | return 0; |
798 | } | 803 | } |
@@ -933,6 +938,27 @@ static const match_table_t tokens = { | |||
933 | }; | 938 | }; |
934 | 939 | ||
935 | /** | 940 | /** |
941 | * parse_standard_option - parse a standard mount option. | ||
942 | * @option: the option to parse | ||
943 | * | ||
944 | * Normally, standard mount options like "sync" are passed to file-systems as | ||
945 | * flags. However, when a "rootflags=" kernel boot parameter is used, they may | ||
946 | * be present in the options string. This function tries to deal with this | ||
947 | * situation and parse standard options. Returns 0 if the option was not | ||
948 | * recognized, and the corresponding integer flag if it was. | ||
949 | * | ||
950 | * UBIFS is only interested in the "sync" option, so do not check for anything | ||
951 | * else. | ||
952 | */ | ||
953 | static int parse_standard_option(const char *option) | ||
954 | { | ||
955 | ubifs_msg("parse %s", option); | ||
956 | if (!strcmp(option, "sync")) | ||
957 | return MS_SYNCHRONOUS; | ||
958 | return 0; | ||
959 | } | ||
960 | |||
961 | /** | ||
936 | * ubifs_parse_options - parse mount parameters. | 962 | * ubifs_parse_options - parse mount parameters. |
937 | * @c: UBIFS file-system description object | 963 | * @c: UBIFS file-system description object |
938 | * @options: parameters to parse | 964 | * @options: parameters to parse |
@@ -1008,9 +1034,19 @@ static int ubifs_parse_options(struct ubifs_info *c, char *options, | |||
1008 | break; | 1034 | break; |
1009 | } | 1035 | } |
1010 | default: | 1036 | default: |
1011 | ubifs_err("unrecognized mount option \"%s\" " | 1037 | { |
1012 | "or missing value", p); | 1038 | unsigned long flag; |
1013 | return -EINVAL; | 1039 | struct super_block *sb = c->vfs_sb; |
1040 | |||
1041 | flag = parse_standard_option(p); | ||
1042 | if (!flag) { | ||
1043 | ubifs_err("unrecognized mount option \"%s\" " | ||
1044 | "or missing value", p); | ||
1045 | return -EINVAL; | ||
1046 | } | ||
1047 | sb->s_flags |= flag; | ||
1048 | break; | ||
1049 | } | ||
1014 | } | 1050 | } |
1015 | } | 1051 | } |
1016 | 1052 | ||
@@ -1180,6 +1216,7 @@ static int mount_ubifs(struct ubifs_info *c) | |||
1180 | if (!ubifs_compr_present(c->default_compr)) { | 1216 | if (!ubifs_compr_present(c->default_compr)) { |
1181 | ubifs_err("'compressor \"%s\" is not compiled in", | 1217 | ubifs_err("'compressor \"%s\" is not compiled in", |
1182 | ubifs_compr_name(c->default_compr)); | 1218 | ubifs_compr_name(c->default_compr)); |
1219 | err = -ENOTSUPP; | ||
1183 | goto out_free; | 1220 | goto out_free; |
1184 | } | 1221 | } |
1185 | 1222 | ||
@@ -1656,7 +1693,7 @@ static void ubifs_remount_ro(struct ubifs_info *c) | |||
1656 | 1693 | ||
1657 | for (i = 0; i < c->jhead_cnt; i++) { | 1694 | for (i = 0; i < c->jhead_cnt; i++) { |
1658 | ubifs_wbuf_sync(&c->jheads[i].wbuf); | 1695 | ubifs_wbuf_sync(&c->jheads[i].wbuf); |
1659 | del_timer_sync(&c->jheads[i].wbuf.timer); | 1696 | hrtimer_cancel(&c->jheads[i].wbuf.timer); |
1660 | } | 1697 | } |
1661 | 1698 | ||
1662 | c->mst_node->flags &= ~cpu_to_le32(UBIFS_MST_DIRTY); | 1699 | c->mst_node->flags &= ~cpu_to_le32(UBIFS_MST_DIRTY); |
@@ -1719,7 +1756,7 @@ static void ubifs_put_super(struct super_block *sb) | |||
1719 | if (c->jheads) | 1756 | if (c->jheads) |
1720 | for (i = 0; i < c->jhead_cnt; i++) { | 1757 | for (i = 0; i < c->jhead_cnt; i++) { |
1721 | ubifs_wbuf_sync(&c->jheads[i].wbuf); | 1758 | ubifs_wbuf_sync(&c->jheads[i].wbuf); |
1722 | del_timer_sync(&c->jheads[i].wbuf.timer); | 1759 | hrtimer_cancel(&c->jheads[i].wbuf.timer); |
1723 | } | 1760 | } |
1724 | 1761 | ||
1725 | /* | 1762 | /* |
@@ -1911,6 +1948,7 @@ static int ubifs_fill_super(struct super_block *sb, void *data, int silent) | |||
1911 | INIT_LIST_HEAD(&c->orph_list); | 1948 | INIT_LIST_HEAD(&c->orph_list); |
1912 | INIT_LIST_HEAD(&c->orph_new); | 1949 | INIT_LIST_HEAD(&c->orph_new); |
1913 | 1950 | ||
1951 | c->vfs_sb = sb; | ||
1914 | c->highest_inum = UBIFS_FIRST_INO; | 1952 | c->highest_inum = UBIFS_FIRST_INO; |
1915 | c->lhead_lnum = c->ltail_lnum = UBIFS_LOG_LNUM; | 1953 | c->lhead_lnum = c->ltail_lnum = UBIFS_LOG_LNUM; |
1916 | 1954 | ||
@@ -1945,13 +1983,10 @@ static int ubifs_fill_super(struct super_block *sb, void *data, int silent) | |||
1945 | if (err) | 1983 | if (err) |
1946 | goto out_bdi; | 1984 | goto out_bdi; |
1947 | 1985 | ||
1948 | c->vfs_sb = sb; | ||
1949 | |||
1950 | sb->s_fs_info = c; | 1986 | sb->s_fs_info = c; |
1951 | sb->s_magic = UBIFS_SUPER_MAGIC; | 1987 | sb->s_magic = UBIFS_SUPER_MAGIC; |
1952 | sb->s_blocksize = UBIFS_BLOCK_SIZE; | 1988 | sb->s_blocksize = UBIFS_BLOCK_SIZE; |
1953 | sb->s_blocksize_bits = UBIFS_BLOCK_SHIFT; | 1989 | sb->s_blocksize_bits = UBIFS_BLOCK_SHIFT; |
1954 | sb->s_dev = c->vi.cdev; | ||
1955 | sb->s_maxbytes = c->max_inode_sz = key_max_inode_size(c); | 1990 | sb->s_maxbytes = c->max_inode_sz = key_max_inode_size(c); |
1956 | if (c->max_inode_sz > MAX_LFS_FILESIZE) | 1991 | if (c->max_inode_sz > MAX_LFS_FILESIZE) |
1957 | sb->s_maxbytes = c->max_inode_sz = MAX_LFS_FILESIZE; | 1992 | sb->s_maxbytes = c->max_inode_sz = MAX_LFS_FILESIZE; |
@@ -1996,16 +2031,9 @@ out_free: | |||
1996 | static int sb_test(struct super_block *sb, void *data) | 2031 | static int sb_test(struct super_block *sb, void *data) |
1997 | { | 2032 | { |
1998 | dev_t *dev = data; | 2033 | dev_t *dev = data; |
2034 | struct ubifs_info *c = sb->s_fs_info; | ||
1999 | 2035 | ||
2000 | return sb->s_dev == *dev; | 2036 | return c->vi.cdev == *dev; |
2001 | } | ||
2002 | |||
2003 | static int sb_set(struct super_block *sb, void *data) | ||
2004 | { | ||
2005 | dev_t *dev = data; | ||
2006 | |||
2007 | sb->s_dev = *dev; | ||
2008 | return 0; | ||
2009 | } | 2037 | } |
2010 | 2038 | ||
2011 | static int ubifs_get_sb(struct file_system_type *fs_type, int flags, | 2039 | static int ubifs_get_sb(struct file_system_type *fs_type, int flags, |
@@ -2033,7 +2061,7 @@ static int ubifs_get_sb(struct file_system_type *fs_type, int flags, | |||
2033 | 2061 | ||
2034 | dbg_gen("opened ubi%d_%d", vi.ubi_num, vi.vol_id); | 2062 | dbg_gen("opened ubi%d_%d", vi.ubi_num, vi.vol_id); |
2035 | 2063 | ||
2036 | sb = sget(fs_type, &sb_test, &sb_set, &vi.cdev); | 2064 | sb = sget(fs_type, &sb_test, &set_anon_super, &vi.cdev); |
2037 | if (IS_ERR(sb)) { | 2065 | if (IS_ERR(sb)) { |
2038 | err = PTR_ERR(sb); | 2066 | err = PTR_ERR(sb); |
2039 | goto out_close; | 2067 | goto out_close; |
@@ -2073,16 +2101,11 @@ out_close: | |||
2073 | return err; | 2101 | return err; |
2074 | } | 2102 | } |
2075 | 2103 | ||
2076 | static void ubifs_kill_sb(struct super_block *sb) | ||
2077 | { | ||
2078 | generic_shutdown_super(sb); | ||
2079 | } | ||
2080 | |||
2081 | static struct file_system_type ubifs_fs_type = { | 2104 | static struct file_system_type ubifs_fs_type = { |
2082 | .name = "ubifs", | 2105 | .name = "ubifs", |
2083 | .owner = THIS_MODULE, | 2106 | .owner = THIS_MODULE, |
2084 | .get_sb = ubifs_get_sb, | 2107 | .get_sb = ubifs_get_sb, |
2085 | .kill_sb = ubifs_kill_sb | 2108 | .kill_sb = kill_anon_super, |
2086 | }; | 2109 | }; |
2087 | 2110 | ||
2088 | /* | 2111 | /* |