aboutsummaryrefslogtreecommitdiffstats
path: root/fs/ufs
diff options
context:
space:
mode:
authorAndrea Bastoni <bastoni@cs.unc.edu>2010-05-30 19:16:45 -0400
committerAndrea Bastoni <bastoni@cs.unc.edu>2010-05-30 19:16:45 -0400
commitada47b5fe13d89735805b566185f4885f5a3f750 (patch)
tree644b88f8a71896307d71438e9b3af49126ffb22b /fs/ufs
parent43e98717ad40a4ae64545b5ba047c7b86aa44f4f (diff)
parent3280f21d43ee541f97f8cda5792150d2dbec20d5 (diff)
Merge branch 'wip-2.6.34' into old-private-masterarchived-private-master
Diffstat (limited to 'fs/ufs')
-rw-r--r--fs/ufs/balloc.c24
-rw-r--r--fs/ufs/dir.c14
-rw-r--r--fs/ufs/file.c3
-rw-r--r--fs/ufs/ialloc.c11
-rw-r--r--fs/ufs/inode.c9
-rw-r--r--fs/ufs/namei.c26
-rw-r--r--fs/ufs/super.c61
-rw-r--r--fs/ufs/truncate.c10
-rw-r--r--fs/ufs/ufs.h6
-rw-r--r--fs/ufs/ufs_fs.h15
10 files changed, 146 insertions, 33 deletions
diff --git a/fs/ufs/balloc.c b/fs/ufs/balloc.c
index 54c16ec95dff..5cfa4d85ccf2 100644
--- a/fs/ufs/balloc.c
+++ b/fs/ufs/balloc.c
@@ -85,7 +85,7 @@ void ufs_free_fragments(struct inode *inode, u64 fragment, unsigned count)
85 "bit already cleared for fragment %u", i); 85 "bit already cleared for fragment %u", i);
86 } 86 }
87 87
88 vfs_dq_free_block(inode, count); 88 dquot_free_block(inode, count);
89 89
90 90
91 fs32_add(sb, &ucg->cg_cs.cs_nffree, count); 91 fs32_add(sb, &ucg->cg_cs.cs_nffree, count);
@@ -195,7 +195,7 @@ do_more:
195 ubh_setblock(UCPI_UBH(ucpi), ucpi->c_freeoff, blkno); 195 ubh_setblock(UCPI_UBH(ucpi), ucpi->c_freeoff, blkno);
196 if ((UFS_SB(sb)->s_flags & UFS_CG_MASK) == UFS_CG_44BSD) 196 if ((UFS_SB(sb)->s_flags & UFS_CG_MASK) == UFS_CG_44BSD)
197 ufs_clusteracct (sb, ucpi, blkno, 1); 197 ufs_clusteracct (sb, ucpi, blkno, 1);
198 vfs_dq_free_block(inode, uspi->s_fpb); 198 dquot_free_block(inode, uspi->s_fpb);
199 199
200 fs32_add(sb, &ucg->cg_cs.cs_nbfree, 1); 200 fs32_add(sb, &ucg->cg_cs.cs_nbfree, 1);
201 uspi->cs_total.cs_nbfree++; 201 uspi->cs_total.cs_nbfree++;
@@ -511,6 +511,7 @@ static u64 ufs_add_fragments(struct inode *inode, u64 fragment,
511 struct ufs_cg_private_info * ucpi; 511 struct ufs_cg_private_info * ucpi;
512 struct ufs_cylinder_group * ucg; 512 struct ufs_cylinder_group * ucg;
513 unsigned cgno, fragno, fragoff, count, fragsize, i; 513 unsigned cgno, fragno, fragoff, count, fragsize, i;
514 int ret;
514 515
515 UFSD("ENTER, fragment %llu, oldcount %u, newcount %u\n", 516 UFSD("ENTER, fragment %llu, oldcount %u, newcount %u\n",
516 (unsigned long long)fragment, oldcount, newcount); 517 (unsigned long long)fragment, oldcount, newcount);
@@ -556,8 +557,9 @@ static u64 ufs_add_fragments(struct inode *inode, u64 fragment,
556 fs32_add(sb, &ucg->cg_frsum[fragsize - count], 1); 557 fs32_add(sb, &ucg->cg_frsum[fragsize - count], 1);
557 for (i = oldcount; i < newcount; i++) 558 for (i = oldcount; i < newcount; i++)
558 ubh_clrbit (UCPI_UBH(ucpi), ucpi->c_freeoff, fragno + i); 559 ubh_clrbit (UCPI_UBH(ucpi), ucpi->c_freeoff, fragno + i);
559 if (vfs_dq_alloc_block(inode, count)) { 560 ret = dquot_alloc_block(inode, count);
560 *err = -EDQUOT; 561 if (ret) {
562 *err = ret;
561 return 0; 563 return 0;
562 } 564 }
563 565
@@ -596,6 +598,7 @@ static u64 ufs_alloc_fragments(struct inode *inode, unsigned cgno,
596 struct ufs_cylinder_group * ucg; 598 struct ufs_cylinder_group * ucg;
597 unsigned oldcg, i, j, k, allocsize; 599 unsigned oldcg, i, j, k, allocsize;
598 u64 result; 600 u64 result;
601 int ret;
599 602
600 UFSD("ENTER, ino %lu, cgno %u, goal %llu, count %u\n", 603 UFSD("ENTER, ino %lu, cgno %u, goal %llu, count %u\n",
601 inode->i_ino, cgno, (unsigned long long)goal, count); 604 inode->i_ino, cgno, (unsigned long long)goal, count);
@@ -664,7 +667,7 @@ cg_found:
664 for (i = count; i < uspi->s_fpb; i++) 667 for (i = count; i < uspi->s_fpb; i++)
665 ubh_setbit (UCPI_UBH(ucpi), ucpi->c_freeoff, goal + i); 668 ubh_setbit (UCPI_UBH(ucpi), ucpi->c_freeoff, goal + i);
666 i = uspi->s_fpb - count; 669 i = uspi->s_fpb - count;
667 vfs_dq_free_block(inode, i); 670 dquot_free_block(inode, i);
668 671
669 fs32_add(sb, &ucg->cg_cs.cs_nffree, i); 672 fs32_add(sb, &ucg->cg_cs.cs_nffree, i);
670 uspi->cs_total.cs_nffree += i; 673 uspi->cs_total.cs_nffree += i;
@@ -676,8 +679,9 @@ cg_found:
676 result = ufs_bitmap_search (sb, ucpi, goal, allocsize); 679 result = ufs_bitmap_search (sb, ucpi, goal, allocsize);
677 if (result == INVBLOCK) 680 if (result == INVBLOCK)
678 return 0; 681 return 0;
679 if (vfs_dq_alloc_block(inode, count)) { 682 ret = dquot_alloc_block(inode, count);
680 *err = -EDQUOT; 683 if (ret) {
684 *err = ret;
681 return 0; 685 return 0;
682 } 686 }
683 for (i = 0; i < count; i++) 687 for (i = 0; i < count; i++)
@@ -714,6 +718,7 @@ static u64 ufs_alloccg_block(struct inode *inode,
714 struct ufs_super_block_first * usb1; 718 struct ufs_super_block_first * usb1;
715 struct ufs_cylinder_group * ucg; 719 struct ufs_cylinder_group * ucg;
716 u64 result, blkno; 720 u64 result, blkno;
721 int ret;
717 722
718 UFSD("ENTER, goal %llu\n", (unsigned long long)goal); 723 UFSD("ENTER, goal %llu\n", (unsigned long long)goal);
719 724
@@ -747,8 +752,9 @@ gotit:
747 ubh_clrblock (UCPI_UBH(ucpi), ucpi->c_freeoff, blkno); 752 ubh_clrblock (UCPI_UBH(ucpi), ucpi->c_freeoff, blkno);
748 if ((UFS_SB(sb)->s_flags & UFS_CG_MASK) == UFS_CG_44BSD) 753 if ((UFS_SB(sb)->s_flags & UFS_CG_MASK) == UFS_CG_44BSD)
749 ufs_clusteracct (sb, ucpi, blkno, -1); 754 ufs_clusteracct (sb, ucpi, blkno, -1);
750 if (vfs_dq_alloc_block(inode, uspi->s_fpb)) { 755 ret = dquot_alloc_block(inode, uspi->s_fpb);
751 *err = -EDQUOT; 756 if (ret) {
757 *err = ret;
752 return INVBLOCK; 758 return INVBLOCK;
753 } 759 }
754 760
diff --git a/fs/ufs/dir.c b/fs/ufs/dir.c
index 6f671f1ac271..317a0d444f6b 100644
--- a/fs/ufs/dir.c
+++ b/fs/ufs/dir.c
@@ -31,7 +31,7 @@
31 * len <= UFS_MAXNAMLEN and de != NULL are guaranteed by caller. 31 * len <= UFS_MAXNAMLEN and de != NULL are guaranteed by caller.
32 */ 32 */
33static inline int ufs_match(struct super_block *sb, int len, 33static inline int ufs_match(struct super_block *sb, int len,
34 const char * const name, struct ufs_dir_entry * de) 34 const unsigned char *name, struct ufs_dir_entry *de)
35{ 35{
36 if (len != ufs_get_de_namlen(sb, de)) 36 if (len != ufs_get_de_namlen(sb, de))
37 return 0; 37 return 0;
@@ -70,13 +70,13 @@ static inline unsigned long ufs_dir_pages(struct inode *inode)
70 return (inode->i_size+PAGE_CACHE_SIZE-1)>>PAGE_CACHE_SHIFT; 70 return (inode->i_size+PAGE_CACHE_SIZE-1)>>PAGE_CACHE_SHIFT;
71} 71}
72 72
73ino_t ufs_inode_by_name(struct inode *dir, struct dentry *dentry) 73ino_t ufs_inode_by_name(struct inode *dir, const struct qstr *qstr)
74{ 74{
75 ino_t res = 0; 75 ino_t res = 0;
76 struct ufs_dir_entry *de; 76 struct ufs_dir_entry *de;
77 struct page *page; 77 struct page *page;
78 78
79 de = ufs_find_entry(dir, dentry, &page); 79 de = ufs_find_entry(dir, qstr, &page);
80 if (de) { 80 if (de) {
81 res = fs32_to_cpu(dir->i_sb, de->d_ino); 81 res = fs32_to_cpu(dir->i_sb, de->d_ino);
82 ufs_put_page(page); 82 ufs_put_page(page);
@@ -249,12 +249,12 @@ struct ufs_dir_entry *ufs_dotdot(struct inode *dir, struct page **p)
249 * (as a parameter - res_dir). Page is returned mapped and unlocked. 249 * (as a parameter - res_dir). Page is returned mapped and unlocked.
250 * Entry is guaranteed to be valid. 250 * Entry is guaranteed to be valid.
251 */ 251 */
252struct ufs_dir_entry *ufs_find_entry(struct inode *dir, struct dentry *dentry, 252struct ufs_dir_entry *ufs_find_entry(struct inode *dir, const struct qstr *qstr,
253 struct page **res_page) 253 struct page **res_page)
254{ 254{
255 struct super_block *sb = dir->i_sb; 255 struct super_block *sb = dir->i_sb;
256 const char *name = dentry->d_name.name; 256 const unsigned char *name = qstr->name;
257 int namelen = dentry->d_name.len; 257 int namelen = qstr->len;
258 unsigned reclen = UFS_DIR_REC_LEN(namelen); 258 unsigned reclen = UFS_DIR_REC_LEN(namelen);
259 unsigned long start, n; 259 unsigned long start, n;
260 unsigned long npages = ufs_dir_pages(dir); 260 unsigned long npages = ufs_dir_pages(dir);
@@ -313,7 +313,7 @@ found:
313int ufs_add_link(struct dentry *dentry, struct inode *inode) 313int ufs_add_link(struct dentry *dentry, struct inode *inode)
314{ 314{
315 struct inode *dir = dentry->d_parent->d_inode; 315 struct inode *dir = dentry->d_parent->d_inode;
316 const char *name = dentry->d_name.name; 316 const unsigned char *name = dentry->d_name.name;
317 int namelen = dentry->d_name.len; 317 int namelen = dentry->d_name.len;
318 struct super_block *sb = dir->i_sb; 318 struct super_block *sb = dir->i_sb;
319 unsigned reclen = UFS_DIR_REC_LEN(namelen); 319 unsigned reclen = UFS_DIR_REC_LEN(namelen);
diff --git a/fs/ufs/file.c b/fs/ufs/file.c
index 73655c61240a..a8962cecde5b 100644
--- a/fs/ufs/file.c
+++ b/fs/ufs/file.c
@@ -24,6 +24,7 @@
24 */ 24 */
25 25
26#include <linux/fs.h> 26#include <linux/fs.h>
27#include <linux/quotaops.h>
27 28
28#include "ufs_fs.h" 29#include "ufs_fs.h"
29#include "ufs.h" 30#include "ufs.h"
@@ -40,7 +41,7 @@ const struct file_operations ufs_file_operations = {
40 .write = do_sync_write, 41 .write = do_sync_write,
41 .aio_write = generic_file_aio_write, 42 .aio_write = generic_file_aio_write,
42 .mmap = generic_file_mmap, 43 .mmap = generic_file_mmap,
43 .open = generic_file_open, 44 .open = dquot_file_open,
44 .fsync = simple_fsync, 45 .fsync = simple_fsync,
45 .splice_read = generic_file_splice_read, 46 .splice_read = generic_file_splice_read,
46}; 47};
diff --git a/fs/ufs/ialloc.c b/fs/ufs/ialloc.c
index 3527c00fef0d..230ecf608026 100644
--- a/fs/ufs/ialloc.c
+++ b/fs/ufs/ialloc.c
@@ -95,8 +95,8 @@ void ufs_free_inode (struct inode * inode)
95 95
96 is_directory = S_ISDIR(inode->i_mode); 96 is_directory = S_ISDIR(inode->i_mode);
97 97
98 vfs_dq_free_inode(inode); 98 dquot_free_inode(inode);
99 vfs_dq_drop(inode); 99 dquot_drop(inode);
100 100
101 clear_inode (inode); 101 clear_inode (inode);
102 102
@@ -355,9 +355,10 @@ cg_found:
355 355
356 unlock_super (sb); 356 unlock_super (sb);
357 357
358 if (vfs_dq_alloc_inode(inode)) { 358 dquot_initialize(inode);
359 vfs_dq_drop(inode); 359 err = dquot_alloc_inode(inode);
360 err = -EDQUOT; 360 if (err) {
361 dquot_drop(inode);
361 goto fail_without_unlock; 362 goto fail_without_unlock;
362 } 363 }
363 364
diff --git a/fs/ufs/inode.c b/fs/ufs/inode.c
index 7cf33379fd46..80b68c3702d1 100644
--- a/fs/ufs/inode.c
+++ b/fs/ufs/inode.c
@@ -36,6 +36,8 @@
36#include <linux/mm.h> 36#include <linux/mm.h>
37#include <linux/smp_lock.h> 37#include <linux/smp_lock.h>
38#include <linux/buffer_head.h> 38#include <linux/buffer_head.h>
39#include <linux/writeback.h>
40#include <linux/quotaops.h>
39 41
40#include "ufs_fs.h" 42#include "ufs_fs.h"
41#include "ufs.h" 43#include "ufs.h"
@@ -890,11 +892,11 @@ static int ufs_update_inode(struct inode * inode, int do_sync)
890 return 0; 892 return 0;
891} 893}
892 894
893int ufs_write_inode (struct inode * inode, int wait) 895int ufs_write_inode(struct inode *inode, struct writeback_control *wbc)
894{ 896{
895 int ret; 897 int ret;
896 lock_kernel(); 898 lock_kernel();
897 ret = ufs_update_inode (inode, wait); 899 ret = ufs_update_inode(inode, wbc->sync_mode == WB_SYNC_ALL);
898 unlock_kernel(); 900 unlock_kernel();
899 return ret; 901 return ret;
900} 902}
@@ -908,6 +910,9 @@ void ufs_delete_inode (struct inode * inode)
908{ 910{
909 loff_t old_i_size; 911 loff_t old_i_size;
910 912
913 if (!is_bad_inode(inode))
914 dquot_initialize(inode);
915
911 truncate_inode_pages(&inode->i_data, 0); 916 truncate_inode_pages(&inode->i_data, 0);
912 if (is_bad_inode(inode)) 917 if (is_bad_inode(inode))
913 goto no_delete; 918 goto no_delete;
diff --git a/fs/ufs/namei.c b/fs/ufs/namei.c
index 23119fe7ad62..118556243e7a 100644
--- a/fs/ufs/namei.c
+++ b/fs/ufs/namei.c
@@ -30,6 +30,7 @@
30#include <linux/time.h> 30#include <linux/time.h>
31#include <linux/fs.h> 31#include <linux/fs.h>
32#include <linux/smp_lock.h> 32#include <linux/smp_lock.h>
33#include <linux/quotaops.h>
33 34
34#include "ufs_fs.h" 35#include "ufs_fs.h"
35#include "ufs.h" 36#include "ufs.h"
@@ -56,7 +57,7 @@ static struct dentry *ufs_lookup(struct inode * dir, struct dentry *dentry, stru
56 return ERR_PTR(-ENAMETOOLONG); 57 return ERR_PTR(-ENAMETOOLONG);
57 58
58 lock_kernel(); 59 lock_kernel();
59 ino = ufs_inode_by_name(dir, dentry); 60 ino = ufs_inode_by_name(dir, &dentry->d_name);
60 if (ino) { 61 if (ino) {
61 inode = ufs_iget(dir->i_sb, ino); 62 inode = ufs_iget(dir->i_sb, ino);
62 if (IS_ERR(inode)) { 63 if (IS_ERR(inode)) {
@@ -84,6 +85,9 @@ static int ufs_create (struct inode * dir, struct dentry * dentry, int mode,
84 int err; 85 int err;
85 86
86 UFSD("BEGIN\n"); 87 UFSD("BEGIN\n");
88
89 dquot_initialize(dir);
90
87 inode = ufs_new_inode(dir, mode); 91 inode = ufs_new_inode(dir, mode);
88 err = PTR_ERR(inode); 92 err = PTR_ERR(inode);
89 93
@@ -107,6 +111,9 @@ static int ufs_mknod (struct inode * dir, struct dentry *dentry, int mode, dev_t
107 111
108 if (!old_valid_dev(rdev)) 112 if (!old_valid_dev(rdev))
109 return -EINVAL; 113 return -EINVAL;
114
115 dquot_initialize(dir);
116
110 inode = ufs_new_inode(dir, mode); 117 inode = ufs_new_inode(dir, mode);
111 err = PTR_ERR(inode); 118 err = PTR_ERR(inode);
112 if (!IS_ERR(inode)) { 119 if (!IS_ERR(inode)) {
@@ -131,6 +138,8 @@ static int ufs_symlink (struct inode * dir, struct dentry * dentry,
131 if (l > sb->s_blocksize) 138 if (l > sb->s_blocksize)
132 goto out_notlocked; 139 goto out_notlocked;
133 140
141 dquot_initialize(dir);
142
134 lock_kernel(); 143 lock_kernel();
135 inode = ufs_new_inode(dir, S_IFLNK | S_IRWXUGO); 144 inode = ufs_new_inode(dir, S_IFLNK | S_IRWXUGO);
136 err = PTR_ERR(inode); 145 err = PTR_ERR(inode);
@@ -176,6 +185,8 @@ static int ufs_link (struct dentry * old_dentry, struct inode * dir,
176 return -EMLINK; 185 return -EMLINK;
177 } 186 }
178 187
188 dquot_initialize(dir);
189
179 inode->i_ctime = CURRENT_TIME_SEC; 190 inode->i_ctime = CURRENT_TIME_SEC;
180 inode_inc_link_count(inode); 191 inode_inc_link_count(inode);
181 atomic_inc(&inode->i_count); 192 atomic_inc(&inode->i_count);
@@ -193,6 +204,8 @@ static int ufs_mkdir(struct inode * dir, struct dentry * dentry, int mode)
193 if (dir->i_nlink >= UFS_LINK_MAX) 204 if (dir->i_nlink >= UFS_LINK_MAX)
194 goto out; 205 goto out;
195 206
207 dquot_initialize(dir);
208
196 lock_kernel(); 209 lock_kernel();
197 inode_inc_link_count(dir); 210 inode_inc_link_count(dir);
198 211
@@ -237,7 +250,9 @@ static int ufs_unlink(struct inode *dir, struct dentry *dentry)
237 struct page *page; 250 struct page *page;
238 int err = -ENOENT; 251 int err = -ENOENT;
239 252
240 de = ufs_find_entry(dir, dentry, &page); 253 dquot_initialize(dir);
254
255 de = ufs_find_entry(dir, &dentry->d_name, &page);
241 if (!de) 256 if (!de)
242 goto out; 257 goto out;
243 258
@@ -281,7 +296,10 @@ static int ufs_rename(struct inode *old_dir, struct dentry *old_dentry,
281 struct ufs_dir_entry *old_de; 296 struct ufs_dir_entry *old_de;
282 int err = -ENOENT; 297 int err = -ENOENT;
283 298
284 old_de = ufs_find_entry(old_dir, old_dentry, &old_page); 299 dquot_initialize(old_dir);
300 dquot_initialize(new_dir);
301
302 old_de = ufs_find_entry(old_dir, &old_dentry->d_name, &old_page);
285 if (!old_de) 303 if (!old_de)
286 goto out; 304 goto out;
287 305
@@ -301,7 +319,7 @@ static int ufs_rename(struct inode *old_dir, struct dentry *old_dentry,
301 goto out_dir; 319 goto out_dir;
302 320
303 err = -ENOENT; 321 err = -ENOENT;
304 new_de = ufs_find_entry(new_dir, new_dentry, &new_page); 322 new_de = ufs_find_entry(new_dir, &new_dentry->d_name, &new_page);
305 if (!new_de) 323 if (!new_de)
306 goto out_dir; 324 goto out_dir;
307 inode_inc_link_count(old_inode); 325 inode_inc_link_count(old_inode);
diff --git a/fs/ufs/super.c b/fs/ufs/super.c
index 5faed7954d0a..14743d935a93 100644
--- a/fs/ufs/super.c
+++ b/fs/ufs/super.c
@@ -66,6 +66,7 @@
66 */ 66 */
67 67
68 68
69#include <linux/exportfs.h>
69#include <linux/module.h> 70#include <linux/module.h>
70#include <linux/bitops.h> 71#include <linux/bitops.h>
71 72
@@ -96,6 +97,56 @@
96#include "swab.h" 97#include "swab.h"
97#include "util.h" 98#include "util.h"
98 99
100static struct inode *ufs_nfs_get_inode(struct super_block *sb, u64 ino, u32 generation)
101{
102 struct ufs_sb_private_info *uspi = UFS_SB(sb)->s_uspi;
103 struct inode *inode;
104
105 if (ino < UFS_ROOTINO || ino > uspi->s_ncg * uspi->s_ipg)
106 return ERR_PTR(-ESTALE);
107
108 inode = ufs_iget(sb, ino);
109 if (IS_ERR(inode))
110 return ERR_CAST(inode);
111 if (generation && inode->i_generation != generation) {
112 iput(inode);
113 return ERR_PTR(-ESTALE);
114 }
115 return inode;
116}
117
118static struct dentry *ufs_fh_to_dentry(struct super_block *sb, struct fid *fid,
119 int fh_len, int fh_type)
120{
121 return generic_fh_to_dentry(sb, fid, fh_len, fh_type, ufs_nfs_get_inode);
122}
123
124static struct dentry *ufs_fh_to_parent(struct super_block *sb, struct fid *fid,
125 int fh_len, int fh_type)
126{
127 return generic_fh_to_parent(sb, fid, fh_len, fh_type, ufs_nfs_get_inode);
128}
129
130static struct dentry *ufs_get_parent(struct dentry *child)
131{
132 struct qstr dot_dot = {
133 .name = "..",
134 .len = 2,
135 };
136 ino_t ino;
137
138 ino = ufs_inode_by_name(child->d_inode, &dot_dot);
139 if (!ino)
140 return ERR_PTR(-ENOENT);
141 return d_obtain_alias(ufs_iget(child->d_inode->i_sb, ino));
142}
143
144static const struct export_operations ufs_export_ops = {
145 .fh_to_dentry = ufs_fh_to_dentry,
146 .fh_to_parent = ufs_fh_to_parent,
147 .get_parent = ufs_get_parent,
148};
149
99#ifdef CONFIG_UFS_DEBUG 150#ifdef CONFIG_UFS_DEBUG
100/* 151/*
101 * Print contents of ufs_super_block, useful for debugging 152 * Print contents of ufs_super_block, useful for debugging
@@ -965,6 +1016,9 @@ magic_found:
965 case UFS_FSSTABLE: 1016 case UFS_FSSTABLE:
966 UFSD("fs is stable\n"); 1017 UFSD("fs is stable\n");
967 break; 1018 break;
1019 case UFS_FSLOG:
1020 UFSD("fs is logging fs\n");
1021 break;
968 case UFS_FSOSF1: 1022 case UFS_FSOSF1:
969 UFSD("fs is DEC OSF/1\n"); 1023 UFSD("fs is DEC OSF/1\n");
970 break; 1024 break;
@@ -990,6 +1044,7 @@ magic_found:
990 * Read ufs_super_block into internal data structures 1044 * Read ufs_super_block into internal data structures
991 */ 1045 */
992 sb->s_op = &ufs_super_ops; 1046 sb->s_op = &ufs_super_ops;
1047 sb->s_export_op = &ufs_export_ops;
993 sb->dq_op = NULL; /***/ 1048 sb->dq_op = NULL; /***/
994 sb->s_magic = fs32_to_cpu(sb, usb3->fs_magic); 1049 sb->s_magic = fs32_to_cpu(sb, usb3->fs_magic);
995 1050
@@ -1380,6 +1435,11 @@ static void destroy_inodecache(void)
1380 kmem_cache_destroy(ufs_inode_cachep); 1435 kmem_cache_destroy(ufs_inode_cachep);
1381} 1436}
1382 1437
1438static void ufs_clear_inode(struct inode *inode)
1439{
1440 dquot_drop(inode);
1441}
1442
1383#ifdef CONFIG_QUOTA 1443#ifdef CONFIG_QUOTA
1384static ssize_t ufs_quota_read(struct super_block *, int, char *,size_t, loff_t); 1444static ssize_t ufs_quota_read(struct super_block *, int, char *,size_t, loff_t);
1385static ssize_t ufs_quota_write(struct super_block *, int, const char *, size_t, loff_t); 1445static ssize_t ufs_quota_write(struct super_block *, int, const char *, size_t, loff_t);
@@ -1390,6 +1450,7 @@ static const struct super_operations ufs_super_ops = {
1390 .destroy_inode = ufs_destroy_inode, 1450 .destroy_inode = ufs_destroy_inode,
1391 .write_inode = ufs_write_inode, 1451 .write_inode = ufs_write_inode,
1392 .delete_inode = ufs_delete_inode, 1452 .delete_inode = ufs_delete_inode,
1453 .clear_inode = ufs_clear_inode,
1393 .put_super = ufs_put_super, 1454 .put_super = ufs_put_super,
1394 .write_super = ufs_write_super, 1455 .write_super = ufs_write_super,
1395 .sync_fs = ufs_sync_fs, 1456 .sync_fs = ufs_sync_fs,
diff --git a/fs/ufs/truncate.c b/fs/ufs/truncate.c
index 41dd431ce228..d3b6270cb377 100644
--- a/fs/ufs/truncate.c
+++ b/fs/ufs/truncate.c
@@ -44,6 +44,7 @@
44#include <linux/buffer_head.h> 44#include <linux/buffer_head.h>
45#include <linux/blkdev.h> 45#include <linux/blkdev.h>
46#include <linux/sched.h> 46#include <linux/sched.h>
47#include <linux/quotaops.h>
47 48
48#include "ufs_fs.h" 49#include "ufs_fs.h"
49#include "ufs.h" 50#include "ufs.h"
@@ -517,9 +518,18 @@ static int ufs_setattr(struct dentry *dentry, struct iattr *attr)
517 if (error) 518 if (error)
518 return error; 519 return error;
519 520
521 if ((ia_valid & ATTR_UID && attr->ia_uid != inode->i_uid) ||
522 (ia_valid & ATTR_GID && attr->ia_gid != inode->i_gid)) {
523 error = dquot_transfer(inode, attr);
524 if (error)
525 return error;
526 }
520 if (ia_valid & ATTR_SIZE && 527 if (ia_valid & ATTR_SIZE &&
521 attr->ia_size != i_size_read(inode)) { 528 attr->ia_size != i_size_read(inode)) {
522 loff_t old_i_size = inode->i_size; 529 loff_t old_i_size = inode->i_size;
530
531 dquot_initialize(inode);
532
523 error = vmtruncate(inode, attr->ia_size); 533 error = vmtruncate(inode, attr->ia_size);
524 if (error) 534 if (error)
525 return error; 535 return error;
diff --git a/fs/ufs/ufs.h b/fs/ufs/ufs.h
index 644e77e13599..43f9f5d5670e 100644
--- a/fs/ufs/ufs.h
+++ b/fs/ufs/ufs.h
@@ -86,9 +86,9 @@ extern void ufs_put_cylinder (struct super_block *, unsigned);
86/* dir.c */ 86/* dir.c */
87extern const struct inode_operations ufs_dir_inode_operations; 87extern const struct inode_operations ufs_dir_inode_operations;
88extern int ufs_add_link (struct dentry *, struct inode *); 88extern int ufs_add_link (struct dentry *, struct inode *);
89extern ino_t ufs_inode_by_name(struct inode *, struct dentry *); 89extern ino_t ufs_inode_by_name(struct inode *, const struct qstr *);
90extern int ufs_make_empty(struct inode *, struct inode *); 90extern int ufs_make_empty(struct inode *, struct inode *);
91extern struct ufs_dir_entry *ufs_find_entry(struct inode *, struct dentry *, struct page **); 91extern struct ufs_dir_entry *ufs_find_entry(struct inode *, const struct qstr *, struct page **);
92extern int ufs_delete_entry(struct inode *, struct ufs_dir_entry *, struct page *); 92extern int ufs_delete_entry(struct inode *, struct ufs_dir_entry *, struct page *);
93extern int ufs_empty_dir (struct inode *); 93extern int ufs_empty_dir (struct inode *);
94extern struct ufs_dir_entry *ufs_dotdot(struct inode *, struct page **); 94extern struct ufs_dir_entry *ufs_dotdot(struct inode *, struct page **);
@@ -106,7 +106,7 @@ extern struct inode * ufs_new_inode (struct inode *, int);
106 106
107/* inode.c */ 107/* inode.c */
108extern struct inode *ufs_iget(struct super_block *, unsigned long); 108extern struct inode *ufs_iget(struct super_block *, unsigned long);
109extern int ufs_write_inode (struct inode *, int); 109extern int ufs_write_inode (struct inode *, struct writeback_control *);
110extern int ufs_sync_inode (struct inode *); 110extern int ufs_sync_inode (struct inode *);
111extern void ufs_delete_inode (struct inode *); 111extern void ufs_delete_inode (struct inode *);
112extern struct buffer_head * ufs_bread (struct inode *, unsigned, int, int *); 112extern struct buffer_head * ufs_bread (struct inode *, unsigned, int, int *);
diff --git a/fs/ufs/ufs_fs.h b/fs/ufs/ufs_fs.h
index 54bde1895a80..6943ec677c0b 100644
--- a/fs/ufs/ufs_fs.h
+++ b/fs/ufs/ufs_fs.h
@@ -138,6 +138,7 @@ typedef __u16 __bitwise __fs16;
138 138
139#define UFS_USEEFT ((__u16)65535) 139#define UFS_USEEFT ((__u16)65535)
140 140
141/* fs_clean values */
141#define UFS_FSOK 0x7c269d38 142#define UFS_FSOK 0x7c269d38
142#define UFS_FSACTIVE ((__s8)0x00) 143#define UFS_FSACTIVE ((__s8)0x00)
143#define UFS_FSCLEAN ((__s8)0x01) 144#define UFS_FSCLEAN ((__s8)0x01)
@@ -145,6 +146,11 @@ typedef __u16 __bitwise __fs16;
145#define UFS_FSOSF1 ((__s8)0x03) /* is this correct for DEC OSF/1? */ 146#define UFS_FSOSF1 ((__s8)0x03) /* is this correct for DEC OSF/1? */
146#define UFS_FSBAD ((__s8)0xff) 147#define UFS_FSBAD ((__s8)0xff)
147 148
149/* Solaris-specific fs_clean values */
150#define UFS_FSSUSPEND ((__s8)0xfe) /* temporarily suspended */
151#define UFS_FSLOG ((__s8)0xfd) /* logging fs */
152#define UFS_FSFIX ((__s8)0xfc) /* being repaired while mounted */
153
148/* From here to next blank line, s_flags for ufs_sb_info */ 154/* From here to next blank line, s_flags for ufs_sb_info */
149/* directory entry encoding */ 155/* directory entry encoding */
150#define UFS_DE_MASK 0x00000010 /* mask for the following */ 156#define UFS_DE_MASK 0x00000010 /* mask for the following */
@@ -227,11 +233,16 @@ typedef __u16 __bitwise __fs16;
227 */ 233 */
228#define ufs_cbtocylno(bno) \ 234#define ufs_cbtocylno(bno) \
229 ((bno) * uspi->s_nspf / uspi->s_spc) 235 ((bno) * uspi->s_nspf / uspi->s_spc)
230#define ufs_cbtorpos(bno) \ 236#define ufs_cbtorpos(bno) \
237 ((UFS_SB(sb)->s_flags & UFS_CG_SUN) ? \
238 (((((bno) * uspi->s_nspf % uspi->s_spc) % \
239 uspi->s_nsect) * \
240 uspi->s_nrpos) / uspi->s_nsect) \
241 : \
231 ((((bno) * uspi->s_nspf % uspi->s_spc / uspi->s_nsect \ 242 ((((bno) * uspi->s_nspf % uspi->s_spc / uspi->s_nsect \
232 * uspi->s_trackskew + (bno) * uspi->s_nspf % uspi->s_spc \ 243 * uspi->s_trackskew + (bno) * uspi->s_nspf % uspi->s_spc \
233 % uspi->s_nsect * uspi->s_interleave) % uspi->s_nsect \ 244 % uspi->s_nsect * uspi->s_interleave) % uspi->s_nsect \
234 * uspi->s_nrpos) / uspi->s_npsect) 245 * uspi->s_nrpos) / uspi->s_npsect))
235 246
236/* 247/*
237 * The following macros optimize certain frequently calculated 248 * The following macros optimize certain frequently calculated