Lines Matching +full:super +full:- +full:set
1 // SPDX-License-Identifier: GPL-2.0+
3 * the_nilfs.c - the_nilfs shared structure.
5 * Copyright (C) 2005-2008 Nippon Telegraph and Telephone Corporation.
14 #include <linux/backing-dev.h>
32 spin_lock(&nilfs->ns_last_segment_lock); in nilfs_set_last_segment()
33 nilfs->ns_last_pseg = start_blocknr; in nilfs_set_last_segment()
34 nilfs->ns_last_seq = seq; in nilfs_set_last_segment()
35 nilfs->ns_last_cno = cno; in nilfs_set_last_segment()
38 if (nilfs->ns_prev_seq == nilfs->ns_last_seq) in nilfs_set_last_segment()
43 nilfs->ns_prev_seq = nilfs->ns_last_seq; in nilfs_set_last_segment()
46 spin_unlock(&nilfs->ns_last_segment_lock); in nilfs_set_last_segment()
50 * alloc_nilfs - allocate a nilfs object
51 * @sb: super block instance
64 nilfs->ns_sb = sb; in alloc_nilfs()
65 nilfs->ns_bdev = sb->s_bdev; in alloc_nilfs()
66 atomic_set(&nilfs->ns_ndirtyblks, 0); in alloc_nilfs()
67 init_rwsem(&nilfs->ns_sem); in alloc_nilfs()
68 mutex_init(&nilfs->ns_snapshot_mount_mutex); in alloc_nilfs()
69 INIT_LIST_HEAD(&nilfs->ns_dirty_files); in alloc_nilfs()
70 INIT_LIST_HEAD(&nilfs->ns_gc_inodes); in alloc_nilfs()
71 spin_lock_init(&nilfs->ns_inode_lock); in alloc_nilfs()
72 spin_lock_init(&nilfs->ns_next_gen_lock); in alloc_nilfs()
73 spin_lock_init(&nilfs->ns_last_segment_lock); in alloc_nilfs()
74 nilfs->ns_cptree = RB_ROOT; in alloc_nilfs()
75 spin_lock_init(&nilfs->ns_cptree_lock); in alloc_nilfs()
76 init_rwsem(&nilfs->ns_segctor_sem); in alloc_nilfs()
77 nilfs->ns_sb_update_freq = NILFS_SB_FREQ; in alloc_nilfs()
83 * destroy_nilfs - destroy nilfs object
90 brelse(nilfs->ns_sbh[0]); in destroy_nilfs()
91 brelse(nilfs->ns_sbh[1]); in destroy_nilfs()
101 struct nilfs_super_block **sbp = nilfs->ns_sbp; in nilfs_load_super_root()
111 down_read(&nilfs->ns_sem); in nilfs_load_super_root()
112 dat_entry_size = le16_to_cpu(sbp[0]->s_dat_entry_size); in nilfs_load_super_root()
113 checkpoint_size = le16_to_cpu(sbp[0]->s_checkpoint_size); in nilfs_load_super_root()
114 segment_usage_size = le16_to_cpu(sbp[0]->s_segment_usage_size); in nilfs_load_super_root()
115 up_read(&nilfs->ns_sem); in nilfs_load_super_root()
117 inode_size = nilfs->ns_inode_size; in nilfs_load_super_root()
119 rawi = (void *)bh_sr->b_data + NILFS_SR_DAT_OFFSET(inode_size); in nilfs_load_super_root()
120 err = nilfs_dat_read(sb, dat_entry_size, rawi, &nilfs->ns_dat); in nilfs_load_super_root()
124 rawi = (void *)bh_sr->b_data + NILFS_SR_CPFILE_OFFSET(inode_size); in nilfs_load_super_root()
125 err = nilfs_cpfile_read(sb, checkpoint_size, rawi, &nilfs->ns_cpfile); in nilfs_load_super_root()
129 rawi = (void *)bh_sr->b_data + NILFS_SR_SUFILE_OFFSET(inode_size); in nilfs_load_super_root()
131 &nilfs->ns_sufile); in nilfs_load_super_root()
135 raw_sr = (struct nilfs_super_root *)bh_sr->b_data; in nilfs_load_super_root()
136 nilfs->ns_nongc_ctime = le64_to_cpu(raw_sr->sr_nongc_ctime); in nilfs_load_super_root()
143 iput(nilfs->ns_cpfile); in nilfs_load_super_root()
146 iput(nilfs->ns_dat); in nilfs_load_super_root()
153 INIT_LIST_HEAD(&ri->ri_used_segments); in nilfs_init_recovery_info()
158 nilfs_dispose_segment_list(&ri->ri_used_segments); in nilfs_clear_recovery_info()
162 * nilfs_store_log_cursor - load log cursor from a super block
164 * @sbp: buffer storing super block to be read
167 * containing a super root from a given super block, and initializes
176 nilfs->ns_last_pseg = le64_to_cpu(sbp->s_last_pseg); in nilfs_store_log_cursor()
177 nilfs->ns_last_cno = le64_to_cpu(sbp->s_last_cno); in nilfs_store_log_cursor()
178 nilfs->ns_last_seq = le64_to_cpu(sbp->s_last_seq); in nilfs_store_log_cursor()
180 nilfs->ns_prev_seq = nilfs->ns_last_seq; in nilfs_store_log_cursor()
181 nilfs->ns_seg_seq = nilfs->ns_last_seq; in nilfs_store_log_cursor()
182 nilfs->ns_segnum = in nilfs_store_log_cursor()
183 nilfs_get_segnum_of_block(nilfs, nilfs->ns_last_pseg); in nilfs_store_log_cursor()
184 nilfs->ns_cno = nilfs->ns_last_cno + 1; in nilfs_store_log_cursor()
185 if (nilfs->ns_segnum >= nilfs->ns_nsegments) { in nilfs_store_log_cursor()
186 nilfs_err(nilfs->ns_sb, in nilfs_store_log_cursor()
188 (unsigned long long)nilfs->ns_segnum, in nilfs_store_log_cursor()
189 nilfs->ns_nsegments); in nilfs_store_log_cursor()
190 ret = -EINVAL; in nilfs_store_log_cursor()
196 * nilfs_get_blocksize - get block size from raw superblock data
197 * @sb: super block instance
206 * large, -EINVAL is returned.
211 unsigned int shift_bits = le32_to_cpu(sbp->s_log_block_size); in nilfs_get_blocksize()
214 ilog2(NILFS_MAX_BLOCK_SIZE) - BLOCK_SIZE_BITS)) { in nilfs_get_blocksize()
217 return -EINVAL; in nilfs_get_blocksize()
224 * load_nilfs - load and recover the nilfs
226 * @sb: super block isntance used to recover past segment
228 * load_nilfs() searches and load the latest super root,
235 unsigned int s_flags = sb->s_flags; in load_nilfs()
236 int really_read_only = bdev_read_only(nilfs->ns_bdev); in load_nilfs()
254 struct nilfs_super_block **sbp = nilfs->ns_sbp; in load_nilfs()
257 if (err != -EINVAL) in load_nilfs()
262 "unable to fall back to spare super block"); in load_nilfs()
268 * restore super block with its spare and reconfigure in load_nilfs()
271 memcpy(sbp[0], sbp[1], nilfs->ns_sbsize); in load_nilfs()
272 nilfs->ns_crc_seed = le32_to_cpu(sbp[0]->s_crc_seed); in load_nilfs()
273 nilfs->ns_sbwtime = le64_to_cpu(sbp[0]->s_wtime); in load_nilfs()
275 /* verify consistency between two super blocks */ in load_nilfs()
280 if (blocksize != nilfs->ns_blocksize) { in load_nilfs()
282 "blocksize differs between two super blocks (%d != %d)", in load_nilfs()
283 blocksize, nilfs->ns_blocksize); in load_nilfs()
284 err = -EINVAL; in load_nilfs()
292 /* drop clean flag to allow roll-forward and recovery */ in load_nilfs()
293 nilfs->ns_mount_state &= ~NILFS_VALID_FS; in load_nilfs()
303 nilfs_err(sb, "error %d while loading super root", err); in load_nilfs()
319 "norecovery option specified, skipping roll-forward recovery"); in load_nilfs()
322 features = le64_to_cpu(nilfs->ns_sbp[0]->s_feature_compat_ro) & in load_nilfs()
328 err = -EROFS; in load_nilfs()
334 err = -EROFS; in load_nilfs()
337 sb->s_flags &= ~SB_RDONLY; in load_nilfs()
341 err = -EINVAL; in load_nilfs()
349 down_write(&nilfs->ns_sem); in load_nilfs()
350 nilfs->ns_mount_state |= NILFS_VALID_FS; /* set "clean" flag */ in load_nilfs()
352 up_write(&nilfs->ns_sem); in load_nilfs()
356 "error %d updating super block. recovery unfinished.", in load_nilfs()
364 sb->s_flags = s_flags; in load_nilfs()
368 nilfs_err(sb, "error %d while searching super root", err); in load_nilfs()
375 iput(nilfs->ns_cpfile); in load_nilfs()
376 iput(nilfs->ns_sufile); in load_nilfs()
377 iput(nilfs->ns_dat); in load_nilfs()
381 sb->s_flags = s_flags; in load_nilfs()
392 res = min_t(unsigned long long, res, (1ULL << max_bits) - 1); in nilfs_max_size()
397 * nilfs_nrsvsegs - calculate the number of reserved segments
404 DIV_ROUND_UP(nsegs * nilfs->ns_r_segments_percentage, in nilfs_nrsvsegs()
409 * nilfs_max_segment_count - calculate the maximum number of segments
416 do_div(max_count, nilfs->ns_blocks_per_segment); in nilfs_max_segment_count()
422 nilfs->ns_nsegments = nsegs; in nilfs_set_nsegments()
423 nilfs->ns_nrsvsegs = nilfs_nrsvsegs(nilfs, nsegs); in nilfs_set_nsegments()
431 if (le32_to_cpu(sbp->s_rev_level) < NILFS_MIN_SUPP_REV) { in nilfs_store_disk_layout()
432 nilfs_err(nilfs->ns_sb, in nilfs_store_disk_layout()
434 le32_to_cpu(sbp->s_rev_level), in nilfs_store_disk_layout()
435 le16_to_cpu(sbp->s_minor_rev_level), in nilfs_store_disk_layout()
437 return -EINVAL; in nilfs_store_disk_layout()
439 nilfs->ns_sbsize = le16_to_cpu(sbp->s_bytes); in nilfs_store_disk_layout()
440 if (nilfs->ns_sbsize > BLOCK_SIZE) in nilfs_store_disk_layout()
441 return -EINVAL; in nilfs_store_disk_layout()
443 nilfs->ns_inode_size = le16_to_cpu(sbp->s_inode_size); in nilfs_store_disk_layout()
444 if (nilfs->ns_inode_size > nilfs->ns_blocksize) { in nilfs_store_disk_layout()
445 nilfs_err(nilfs->ns_sb, "too large inode size: %d bytes", in nilfs_store_disk_layout()
446 nilfs->ns_inode_size); in nilfs_store_disk_layout()
447 return -EINVAL; in nilfs_store_disk_layout()
448 } else if (nilfs->ns_inode_size < NILFS_MIN_INODE_SIZE) { in nilfs_store_disk_layout()
449 nilfs_err(nilfs->ns_sb, "too small inode size: %d bytes", in nilfs_store_disk_layout()
450 nilfs->ns_inode_size); in nilfs_store_disk_layout()
451 return -EINVAL; in nilfs_store_disk_layout()
454 nilfs->ns_first_ino = le32_to_cpu(sbp->s_first_ino); in nilfs_store_disk_layout()
456 nilfs->ns_blocks_per_segment = le32_to_cpu(sbp->s_blocks_per_segment); in nilfs_store_disk_layout()
457 if (nilfs->ns_blocks_per_segment < NILFS_SEG_MIN_BLOCKS) { in nilfs_store_disk_layout()
458 nilfs_err(nilfs->ns_sb, "too short segment: %lu blocks", in nilfs_store_disk_layout()
459 nilfs->ns_blocks_per_segment); in nilfs_store_disk_layout()
460 return -EINVAL; in nilfs_store_disk_layout()
463 nilfs->ns_first_data_block = le64_to_cpu(sbp->s_first_data_block); in nilfs_store_disk_layout()
464 nilfs->ns_r_segments_percentage = in nilfs_store_disk_layout()
465 le32_to_cpu(sbp->s_r_segments_percentage); in nilfs_store_disk_layout()
466 if (nilfs->ns_r_segments_percentage < 1 || in nilfs_store_disk_layout()
467 nilfs->ns_r_segments_percentage > 99) { in nilfs_store_disk_layout()
468 nilfs_err(nilfs->ns_sb, in nilfs_store_disk_layout()
470 nilfs->ns_r_segments_percentage); in nilfs_store_disk_layout()
471 return -EINVAL; in nilfs_store_disk_layout()
474 nsegments = le64_to_cpu(sbp->s_nsegments); in nilfs_store_disk_layout()
476 nilfs_err(nilfs->ns_sb, in nilfs_store_disk_layout()
480 return -EINVAL; in nilfs_store_disk_layout()
483 nblocks = (u64)i_size_read(nilfs->ns_sb->s_bdev->bd_inode) >> in nilfs_store_disk_layout()
484 nilfs->ns_sb->s_blocksize_bits; in nilfs_store_disk_layout()
486 u64 min_block_count = nsegments * nilfs->ns_blocks_per_segment; in nilfs_store_disk_layout()
494 nilfs_err(nilfs->ns_sb, in nilfs_store_disk_layout()
498 return -EINVAL; in nilfs_store_disk_layout()
503 nilfs->ns_crc_seed = le32_to_cpu(sbp->s_crc_seed); in nilfs_store_disk_layout()
514 if (!sbp || le16_to_cpu(sbp->s_magic) != NILFS_SUPER_MAGIC) in nilfs_valid_sb()
516 bytes = le16_to_cpu(sbp->s_bytes); in nilfs_valid_sb()
519 crc = crc32_le(le32_to_cpu(sbp->s_crc_seed), (unsigned char *)sbp, in nilfs_valid_sb()
523 bytes - sumoff - 4); in nilfs_valid_sb()
524 return crc == le32_to_cpu(sbp->s_sum); in nilfs_valid_sb()
528 * nilfs_sb2_bad_offset - check the location of the second superblock
542 unsigned int shift_bits = le32_to_cpu(sbp->s_log_block_size); in nilfs_sb2_bad_offset()
543 u32 blocks_per_segment = le32_to_cpu(sbp->s_blocks_per_segment); in nilfs_sb2_bad_offset()
544 u64 nsegments = le64_to_cpu(sbp->s_nsegments); in nilfs_sb2_bad_offset()
548 shift_bits > ilog2(NILFS_MAX_BLOCK_SIZE) - BLOCK_SIZE_BITS) in nilfs_sb2_bad_offset()
561 if (nilfs->ns_sbp[i]) { in nilfs_release_super_block()
562 brelse(nilfs->ns_sbh[i]); in nilfs_release_super_block()
563 nilfs->ns_sbh[i] = NULL; in nilfs_release_super_block()
564 nilfs->ns_sbp[i] = NULL; in nilfs_release_super_block()
571 brelse(nilfs->ns_sbh[0]); in nilfs_fall_back_super_block()
572 nilfs->ns_sbh[0] = nilfs->ns_sbh[1]; in nilfs_fall_back_super_block()
573 nilfs->ns_sbp[0] = nilfs->ns_sbp[1]; in nilfs_fall_back_super_block()
574 nilfs->ns_sbh[1] = NULL; in nilfs_fall_back_super_block()
575 nilfs->ns_sbp[1] = NULL; in nilfs_fall_back_super_block()
580 struct buffer_head *tsbh = nilfs->ns_sbh[0]; in nilfs_swap_super_block()
581 struct nilfs_super_block *tsbp = nilfs->ns_sbp[0]; in nilfs_swap_super_block()
583 nilfs->ns_sbh[0] = nilfs->ns_sbh[1]; in nilfs_swap_super_block()
584 nilfs->ns_sbp[0] = nilfs->ns_sbp[1]; in nilfs_swap_super_block()
585 nilfs->ns_sbh[1] = tsbh; in nilfs_swap_super_block()
586 nilfs->ns_sbp[1] = tsbp; in nilfs_swap_super_block()
593 struct nilfs_super_block **sbp = nilfs->ns_sbp; in nilfs_load_super_block()
594 struct buffer_head **sbh = nilfs->ns_sbh; in nilfs_load_super_block()
595 u64 sb2off, devsize = nilfs->ns_bdev->bd_inode->i_size; in nilfs_load_super_block()
600 return -EINVAL; in nilfs_load_super_block()
611 return -EIO; in nilfs_load_super_block()
623 * Compare two super blocks and set 1 in swp if the secondary in nilfs_load_super_block()
624 * super block is valid and newer. Otherwise, set 0 in swp. in nilfs_load_super_block()
629 le64_to_cpu(sbp[1]->s_last_cno) > in nilfs_load_super_block()
630 le64_to_cpu(sbp[0]->s_last_cno)); in nilfs_load_super_block()
642 return -EINVAL; in nilfs_load_super_block()
652 nilfs->ns_sbwcount = 0; in nilfs_load_super_block()
653 nilfs->ns_sbwtime = le64_to_cpu(sbp[0]->s_wtime); in nilfs_load_super_block()
654 nilfs->ns_prot_seq = le64_to_cpu(sbp[valid[1] & !swp]->s_last_seq); in nilfs_load_super_block()
660 * init_nilfs - initialize a NILFS instance.
662 * @sb: super block
666 * reading the super block, getting disk layout information, initializing
678 down_write(&nilfs->ns_sem); in init_nilfs()
682 nilfs_err(sb, "unable to set blocksize"); in init_nilfs()
683 err = -EINVAL; in init_nilfs()
706 err = -EINVAL; in init_nilfs()
709 if (sb->s_blocksize != blocksize) { in init_nilfs()
710 int hw_blocksize = bdev_logical_block_size(sb->s_bdev); in init_nilfs()
714 "blocksize %d too small for device (sector-size = %d)", in init_nilfs()
716 err = -EINVAL; in init_nilfs()
722 err = -EINVAL; in init_nilfs()
734 nilfs->ns_blocksize_bits = sb->s_blocksize_bits; in init_nilfs()
735 nilfs->ns_blocksize = blocksize; in init_nilfs()
737 get_random_bytes(&nilfs->ns_next_generation, in init_nilfs()
738 sizeof(nilfs->ns_next_generation)); in init_nilfs()
744 sb->s_maxbytes = nilfs_max_size(sb->s_blocksize_bits); in init_nilfs()
746 nilfs->ns_mount_state = le16_to_cpu(sbp->s_state); in init_nilfs()
755 up_write(&nilfs->ns_sem); in init_nilfs()
772 sects_per_block = (1 << nilfs->ns_blocksize_bits) / in nilfs_discard_segments()
773 bdev_logical_block_size(nilfs->ns_bdev); in nilfs_discard_segments()
779 nblocks = seg_end - seg_start + 1; in nilfs_discard_segments()
781 nblocks += seg_end - seg_start + 1; in nilfs_discard_segments()
783 ret = blkdev_issue_discard(nilfs->ns_bdev, in nilfs_discard_segments()
793 ret = blkdev_issue_discard(nilfs->ns_bdev, in nilfs_discard_segments()
804 ncleansegs = nilfs_sufile_get_ncleansegs(nilfs->ns_sufile); in nilfs_count_free_blocks()
805 *nblocks = (sector_t)ncleansegs * nilfs->ns_blocks_per_segment; in nilfs_count_free_blocks()
813 ncleansegs = nilfs_sufile_get_ncleansegs(nilfs->ns_sufile); in nilfs_near_disk_full()
814 nincsegs = atomic_read(&nilfs->ns_ndirtyblks) / in nilfs_near_disk_full()
815 nilfs->ns_blocks_per_segment + 1; in nilfs_near_disk_full()
817 return ncleansegs <= nilfs->ns_nrsvsegs + nincsegs; in nilfs_near_disk_full()
825 spin_lock(&nilfs->ns_cptree_lock); in nilfs_lookup_root()
826 n = nilfs->ns_cptree.rb_node; in nilfs_lookup_root()
830 if (cno < root->cno) { in nilfs_lookup_root()
831 n = n->rb_left; in nilfs_lookup_root()
832 } else if (cno > root->cno) { in nilfs_lookup_root()
833 n = n->rb_right; in nilfs_lookup_root()
835 refcount_inc(&root->count); in nilfs_lookup_root()
836 spin_unlock(&nilfs->ns_cptree_lock); in nilfs_lookup_root()
840 spin_unlock(&nilfs->ns_cptree_lock); in nilfs_lookup_root()
860 spin_lock(&nilfs->ns_cptree_lock); in nilfs_find_or_create_root()
862 p = &nilfs->ns_cptree.rb_node; in nilfs_find_or_create_root()
869 if (cno < root->cno) { in nilfs_find_or_create_root()
870 p = &(*p)->rb_left; in nilfs_find_or_create_root()
871 } else if (cno > root->cno) { in nilfs_find_or_create_root()
872 p = &(*p)->rb_right; in nilfs_find_or_create_root()
874 refcount_inc(&root->count); in nilfs_find_or_create_root()
875 spin_unlock(&nilfs->ns_cptree_lock); in nilfs_find_or_create_root()
881 new->cno = cno; in nilfs_find_or_create_root()
882 new->ifile = NULL; in nilfs_find_or_create_root()
883 new->nilfs = nilfs; in nilfs_find_or_create_root()
884 refcount_set(&new->count, 1); in nilfs_find_or_create_root()
885 atomic64_set(&new->inodes_count, 0); in nilfs_find_or_create_root()
886 atomic64_set(&new->blocks_count, 0); in nilfs_find_or_create_root()
888 rb_link_node(&new->rb_node, parent, p); in nilfs_find_or_create_root()
889 rb_insert_color(&new->rb_node, &nilfs->ns_cptree); in nilfs_find_or_create_root()
891 spin_unlock(&nilfs->ns_cptree_lock); in nilfs_find_or_create_root()
904 struct the_nilfs *nilfs = root->nilfs; in nilfs_put_root()
906 if (refcount_dec_and_lock(&root->count, &nilfs->ns_cptree_lock)) { in nilfs_put_root()
907 rb_erase(&root->rb_node, &nilfs->ns_cptree); in nilfs_put_root()
908 spin_unlock(&nilfs->ns_cptree_lock); in nilfs_put_root()
911 iput(root->ifile); in nilfs_put_root()