1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24#ifndef _THE_NILFS_H
25#define _THE_NILFS_H
26
27#include <linux/types.h>
28#include <linux/buffer_head.h>
29#include <linux/fs.h>
30#include <linux/blkdev.h>
31#include <linux/backing-dev.h>
32#include "sb.h"
33
34
35enum {
36 THE_NILFS_INIT = 0,
37 THE_NILFS_LOADED,
38
39 THE_NILFS_DISCONTINUED,
40 THE_NILFS_GC_RUNNING,
41};
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92struct the_nilfs {
93 unsigned long ns_flags;
94 atomic_t ns_count;
95 struct list_head ns_list;
96
97 struct block_device *ns_bdev;
98 struct backing_dev_info *ns_bdi;
99 struct nilfs_sb_info *ns_writer;
100 struct rw_semaphore ns_sem;
101 struct rw_semaphore ns_super_sem;
102 struct mutex ns_mount_mutex;
103 struct rw_semaphore ns_writer_sem;
104
105
106
107
108 struct nilfs_sb_info *ns_current;
109 struct list_head ns_supers;
110
111
112
113
114
115
116
117
118 struct buffer_head *ns_sbh[2];
119 struct nilfs_super_block *ns_sbp[2];
120 time_t ns_sbwtime[2];
121 unsigned ns_sbsize;
122 unsigned ns_mount_state;
123
124
125
126
127
128
129
130
131 u64 ns_seg_seq;
132 __u64 ns_segnum;
133 __u64 ns_nextnum;
134 unsigned long ns_pseg_offset;
135 __u64 ns_cno;
136 time_t ns_ctime;
137 time_t ns_nongc_ctime;
138 atomic_t ns_ndirtyblks;
139
140
141
142
143
144
145 spinlock_t ns_last_segment_lock;
146 sector_t ns_last_pseg;
147 u64 ns_last_seq;
148 __u64 ns_last_cno;
149 u64 ns_prot_seq;
150 unsigned long ns_free_segments_count;
151
152 struct rw_semaphore ns_segctor_sem;
153
154
155
156
157
158 struct inode *ns_dat;
159 struct inode *ns_cpfile;
160 struct inode *ns_sufile;
161 struct inode *ns_gc_dat;
162
163
164 struct list_head ns_gc_inodes;
165 struct hlist_head *ns_gc_inodes_h;
166
167
168 unsigned int ns_blocksize_bits;
169 unsigned long ns_nsegments;
170 unsigned long ns_blocks_per_segment;
171 unsigned long ns_r_segments_percentage;
172 unsigned long ns_nrsvsegs;
173 unsigned long ns_first_data_block;
174 int ns_inode_size;
175 int ns_first_ino;
176 u32 ns_crc_seed;
177};
178
179#define NILFS_GCINODE_HASH_BITS 8
180#define NILFS_GCINODE_HASH_SIZE (1<<NILFS_GCINODE_HASH_BITS)
181
182#define THE_NILFS_FNS(bit, name) \
183static inline void set_nilfs_##name(struct the_nilfs *nilfs) \
184{ \
185 set_bit(THE_NILFS_##bit, &(nilfs)->ns_flags); \
186} \
187static inline void clear_nilfs_##name(struct the_nilfs *nilfs) \
188{ \
189 clear_bit(THE_NILFS_##bit, &(nilfs)->ns_flags); \
190} \
191static inline int nilfs_##name(struct the_nilfs *nilfs) \
192{ \
193 return test_bit(THE_NILFS_##bit, &(nilfs)->ns_flags); \
194}
195
196THE_NILFS_FNS(INIT, init)
197THE_NILFS_FNS(LOADED, loaded)
198THE_NILFS_FNS(DISCONTINUED, discontinued)
199THE_NILFS_FNS(GC_RUNNING, gc_running)
200
201
202#define NILFS_SB_FREQ 10
203#define NILFS_ALTSB_FREQ 60
204
205static inline int nilfs_sb_need_update(struct the_nilfs *nilfs)
206{
207 u64 t = get_seconds();
208 return t < nilfs->ns_sbwtime[0] ||
209 t > nilfs->ns_sbwtime[0] + NILFS_SB_FREQ;
210}
211
212static inline int nilfs_altsb_need_update(struct the_nilfs *nilfs)
213{
214 u64 t = get_seconds();
215 struct nilfs_super_block **sbp = nilfs->ns_sbp;
216 return sbp[1] && t > nilfs->ns_sbwtime[1] + NILFS_ALTSB_FREQ;
217}
218
219void nilfs_set_last_segment(struct the_nilfs *, sector_t, u64, __u64);
220struct the_nilfs *find_or_create_nilfs(struct block_device *);
221void put_nilfs(struct the_nilfs *);
222int init_nilfs(struct the_nilfs *, struct nilfs_sb_info *, char *);
223int load_nilfs(struct the_nilfs *, struct nilfs_sb_info *);
224int nilfs_count_free_blocks(struct the_nilfs *, sector_t *);
225struct nilfs_sb_info *nilfs_find_sbinfo(struct the_nilfs *, int, __u64);
226int nilfs_checkpoint_is_mounted(struct the_nilfs *, __u64, int);
227int nilfs_near_disk_full(struct the_nilfs *);
228void nilfs_fall_back_super_block(struct the_nilfs *);
229void nilfs_swap_super_block(struct the_nilfs *);
230
231
232static inline void get_nilfs(struct the_nilfs *nilfs)
233{
234
235 atomic_inc(&nilfs->ns_count);
236}
237
238static inline void
239nilfs_attach_writer(struct the_nilfs *nilfs, struct nilfs_sb_info *sbi)
240{
241 down_write(&nilfs->ns_writer_sem);
242 nilfs->ns_writer = sbi;
243 up_write(&nilfs->ns_writer_sem);
244}
245
246static inline void
247nilfs_detach_writer(struct the_nilfs *nilfs, struct nilfs_sb_info *sbi)
248{
249 down_write(&nilfs->ns_writer_sem);
250 if (sbi == nilfs->ns_writer)
251 nilfs->ns_writer = NULL;
252 up_write(&nilfs->ns_writer_sem);
253}
254
255static inline void nilfs_put_sbinfo(struct nilfs_sb_info *sbi)
256{
257 if (atomic_dec_and_test(&sbi->s_count))
258 kfree(sbi);
259}
260
261static inline void
262nilfs_get_segment_range(struct the_nilfs *nilfs, __u64 segnum,
263 sector_t *seg_start, sector_t *seg_end)
264{
265 *seg_start = (sector_t)nilfs->ns_blocks_per_segment * segnum;
266 *seg_end = *seg_start + nilfs->ns_blocks_per_segment - 1;
267 if (segnum == 0)
268 *seg_start = nilfs->ns_first_data_block;
269}
270
271static inline sector_t
272nilfs_get_segment_start_blocknr(struct the_nilfs *nilfs, __u64 segnum)
273{
274 return (segnum == 0) ? nilfs->ns_first_data_block :
275 (sector_t)nilfs->ns_blocks_per_segment * segnum;
276}
277
278static inline __u64
279nilfs_get_segnum_of_block(struct the_nilfs *nilfs, sector_t blocknr)
280{
281 sector_t segnum = blocknr;
282
283 sector_div(segnum, nilfs->ns_blocks_per_segment);
284 return segnum;
285}
286
287static inline void
288nilfs_terminate_segment(struct the_nilfs *nilfs, sector_t seg_start,
289 sector_t seg_end)
290{
291
292 nilfs->ns_pseg_offset = seg_end - seg_start + 1;
293}
294
295static inline void nilfs_shift_to_next_segment(struct the_nilfs *nilfs)
296{
297
298 nilfs->ns_segnum = nilfs->ns_nextnum;
299 nilfs->ns_pseg_offset = 0;
300 nilfs->ns_seg_seq++;
301}
302
303static inline __u64 nilfs_last_cno(struct the_nilfs *nilfs)
304{
305 __u64 cno;
306
307 spin_lock(&nilfs->ns_last_segment_lock);
308 cno = nilfs->ns_last_cno;
309 spin_unlock(&nilfs->ns_last_segment_lock);
310 return cno;
311}
312
313static inline int nilfs_segment_is_active(struct the_nilfs *nilfs, __u64 n)
314{
315 return n == nilfs->ns_segnum || n == nilfs->ns_nextnum;
316}
317
318#endif
319