diff options
Diffstat (limited to 'fs/nilfs2/cpfile.c')
-rw-r--r-- | fs/nilfs2/cpfile.c | 38 |
1 files changed, 21 insertions, 17 deletions
diff --git a/fs/nilfs2/cpfile.c b/fs/nilfs2/cpfile.c index 218b34418508..e90b60dfced9 100644 --- a/fs/nilfs2/cpfile.c +++ b/fs/nilfs2/cpfile.c | |||
@@ -40,10 +40,7 @@ nilfs_cpfile_checkpoints_per_block(const struct inode *cpfile) | |||
40 | static unsigned long | 40 | static unsigned long |
41 | nilfs_cpfile_get_blkoff(const struct inode *cpfile, __u64 cno) | 41 | nilfs_cpfile_get_blkoff(const struct inode *cpfile, __u64 cno) |
42 | { | 42 | { |
43 | __u64 tcno; | 43 | __u64 tcno = cno + NILFS_MDT(cpfile)->mi_first_entry_offset - 1; |
44 | |||
45 | BUG_ON(cno == 0); /* checkpoint number 0 is invalid */ | ||
46 | tcno = cno + NILFS_MDT(cpfile)->mi_first_entry_offset - 1; | ||
47 | do_div(tcno, nilfs_cpfile_checkpoints_per_block(cpfile)); | 44 | do_div(tcno, nilfs_cpfile_checkpoints_per_block(cpfile)); |
48 | return (unsigned long)tcno; | 45 | return (unsigned long)tcno; |
49 | } | 46 | } |
@@ -96,7 +93,7 @@ nilfs_cpfile_block_sub_valid_checkpoints(const struct inode *cpfile, | |||
96 | struct nilfs_checkpoint *cp = kaddr + bh_offset(bh); | 93 | struct nilfs_checkpoint *cp = kaddr + bh_offset(bh); |
97 | unsigned int count; | 94 | unsigned int count; |
98 | 95 | ||
99 | BUG_ON(le32_to_cpu(cp->cp_checkpoints_count) < n); | 96 | WARN_ON(le32_to_cpu(cp->cp_checkpoints_count) < n); |
100 | count = le32_to_cpu(cp->cp_checkpoints_count) - n; | 97 | count = le32_to_cpu(cp->cp_checkpoints_count) - n; |
101 | cp->cp_checkpoints_count = cpu_to_le32(count); | 98 | cp->cp_checkpoints_count = cpu_to_le32(count); |
102 | return count; | 99 | return count; |
@@ -178,6 +175,8 @@ static inline int nilfs_cpfile_delete_checkpoint_block(struct inode *cpfile, | |||
178 | * %-ENOMEM - Insufficient amount of memory available. | 175 | * %-ENOMEM - Insufficient amount of memory available. |
179 | * | 176 | * |
180 | * %-ENOENT - No such checkpoint. | 177 | * %-ENOENT - No such checkpoint. |
178 | * | ||
179 | * %-EINVAL - invalid checkpoint. | ||
181 | */ | 180 | */ |
182 | int nilfs_cpfile_get_checkpoint(struct inode *cpfile, | 181 | int nilfs_cpfile_get_checkpoint(struct inode *cpfile, |
183 | __u64 cno, | 182 | __u64 cno, |
@@ -191,8 +190,9 @@ int nilfs_cpfile_get_checkpoint(struct inode *cpfile, | |||
191 | void *kaddr; | 190 | void *kaddr; |
192 | int ret; | 191 | int ret; |
193 | 192 | ||
194 | BUG_ON(cno < 1 || cno > nilfs_mdt_cno(cpfile) || | 193 | if (unlikely(cno < 1 || cno > nilfs_mdt_cno(cpfile) || |
195 | (cno < nilfs_mdt_cno(cpfile) && create)); | 194 | (cno < nilfs_mdt_cno(cpfile) && create))) |
195 | return -EINVAL; | ||
196 | 196 | ||
197 | down_write(&NILFS_MDT(cpfile)->mi_sem); | 197 | down_write(&NILFS_MDT(cpfile)->mi_sem); |
198 | 198 | ||
@@ -288,12 +288,11 @@ int nilfs_cpfile_delete_checkpoints(struct inode *cpfile, | |||
288 | unsigned long tnicps; | 288 | unsigned long tnicps; |
289 | int ret, ncps, nicps, count, i; | 289 | int ret, ncps, nicps, count, i; |
290 | 290 | ||
291 | if ((start == 0) || (start > end)) { | 291 | if (unlikely(start == 0 || start > end)) { |
292 | printk(KERN_CRIT "%s: start = %llu, end = %llu\n", | 292 | printk(KERN_ERR "%s: invalid range of checkpoint numbers: " |
293 | __func__, | 293 | "[%llu, %llu)\n", __func__, |
294 | (unsigned long long)start, | 294 | (unsigned long long)start, (unsigned long long)end); |
295 | (unsigned long long)end); | 295 | return -EINVAL; |
296 | BUG(); | ||
297 | } | 296 | } |
298 | 297 | ||
299 | /* cannot delete the latest checkpoint */ | 298 | /* cannot delete the latest checkpoint */ |
@@ -323,7 +322,7 @@ int nilfs_cpfile_delete_checkpoints(struct inode *cpfile, | |||
323 | cpfile, cno, cp_bh, kaddr); | 322 | cpfile, cno, cp_bh, kaddr); |
324 | nicps = 0; | 323 | nicps = 0; |
325 | for (i = 0; i < ncps; i++, cp = (void *)cp + cpsz) { | 324 | for (i = 0; i < ncps; i++, cp = (void *)cp + cpsz) { |
326 | BUG_ON(nilfs_checkpoint_snapshot(cp)); | 325 | WARN_ON(nilfs_checkpoint_snapshot(cp)); |
327 | if (!nilfs_checkpoint_invalid(cp)) { | 326 | if (!nilfs_checkpoint_invalid(cp)) { |
328 | nilfs_checkpoint_set_invalid(cp); | 327 | nilfs_checkpoint_set_invalid(cp); |
329 | nicps++; | 328 | nicps++; |
@@ -393,6 +392,8 @@ static ssize_t nilfs_cpfile_do_get_cpinfo(struct inode *cpfile, __u64 *cnop, | |||
393 | int n, ret; | 392 | int n, ret; |
394 | int ncps, i; | 393 | int ncps, i; |
395 | 394 | ||
395 | if (cno == 0) | ||
396 | return -ENOENT; /* checkpoint number 0 is invalid */ | ||
396 | down_read(&NILFS_MDT(cpfile)->mi_sem); | 397 | down_read(&NILFS_MDT(cpfile)->mi_sem); |
397 | 398 | ||
398 | for (n = 0; cno < cur_cno && n < nci; cno += ncps) { | 399 | for (n = 0; cno < cur_cno && n < nci; cno += ncps) { |
@@ -532,9 +533,6 @@ int nilfs_cpfile_delete_checkpoint(struct inode *cpfile, __u64 cno) | |||
532 | ssize_t nci; | 533 | ssize_t nci; |
533 | int ret; | 534 | int ret; |
534 | 535 | ||
535 | /* checkpoint number 0 is invalid */ | ||
536 | if (cno == 0) | ||
537 | return -ENOENT; | ||
538 | nci = nilfs_cpfile_do_get_cpinfo(cpfile, &tcno, &ci, 1); | 536 | nci = nilfs_cpfile_do_get_cpinfo(cpfile, &tcno, &ci, 1); |
539 | if (nci < 0) | 537 | if (nci < 0) |
540 | return nci; | 538 | return nci; |
@@ -582,6 +580,8 @@ static int nilfs_cpfile_set_snapshot(struct inode *cpfile, __u64 cno) | |||
582 | void *kaddr; | 580 | void *kaddr; |
583 | int ret; | 581 | int ret; |
584 | 582 | ||
583 | if (cno == 0) | ||
584 | return -ENOENT; /* checkpoint number 0 is invalid */ | ||
585 | down_write(&NILFS_MDT(cpfile)->mi_sem); | 585 | down_write(&NILFS_MDT(cpfile)->mi_sem); |
586 | 586 | ||
587 | ret = nilfs_cpfile_get_checkpoint_block(cpfile, cno, 0, &cp_bh); | 587 | ret = nilfs_cpfile_get_checkpoint_block(cpfile, cno, 0, &cp_bh); |
@@ -698,6 +698,8 @@ static int nilfs_cpfile_clear_snapshot(struct inode *cpfile, __u64 cno) | |||
698 | void *kaddr; | 698 | void *kaddr; |
699 | int ret; | 699 | int ret; |
700 | 700 | ||
701 | if (cno == 0) | ||
702 | return -ENOENT; /* checkpoint number 0 is invalid */ | ||
701 | down_write(&NILFS_MDT(cpfile)->mi_sem); | 703 | down_write(&NILFS_MDT(cpfile)->mi_sem); |
702 | 704 | ||
703 | ret = nilfs_cpfile_get_checkpoint_block(cpfile, cno, 0, &cp_bh); | 705 | ret = nilfs_cpfile_get_checkpoint_block(cpfile, cno, 0, &cp_bh); |
@@ -813,6 +815,8 @@ int nilfs_cpfile_is_snapshot(struct inode *cpfile, __u64 cno) | |||
813 | void *kaddr; | 815 | void *kaddr; |
814 | int ret; | 816 | int ret; |
815 | 817 | ||
818 | if (cno == 0) | ||
819 | return -ENOENT; /* checkpoint number 0 is invalid */ | ||
816 | down_read(&NILFS_MDT(cpfile)->mi_sem); | 820 | down_read(&NILFS_MDT(cpfile)->mi_sem); |
817 | 821 | ||
818 | ret = nilfs_cpfile_get_checkpoint_block(cpfile, cno, 0, &bh); | 822 | ret = nilfs_cpfile_get_checkpoint_block(cpfile, cno, 0, &bh); |