This source file includes following definitions.
- minix_put_inode
- minix_commit_super
- minix_write_super
- minix_put_super
- minix_remount
- minix_read_super
- minix_statfs
- block_bmap
- minix_bmap
- inode_getblk
- block_getblk
- minix_getblk
- minix_bread
- minix_read_inode
- minix_update_inode
- minix_write_inode
- minix_sync_inode
- init_module
- cleanup_module
1
2
3
4
5
6
7 #ifdef MODULE
8 #include <linux/module.h>
9 #include <linux/version.h>
10 #else
11 #define MOD_INC_USE_COUNT
12 #define MOD_DEC_USE_COUNT
13 #endif
14
15 #include <linux/sched.h>
16 #include <linux/minix_fs.h>
17 #include <linux/kernel.h>
18 #include <linux/mm.h>
19 #include <linux/string.h>
20 #include <linux/stat.h>
21 #include <linux/locks.h>
22
23 #include <asm/system.h>
24 #include <asm/segment.h>
25 #include <asm/bitops.h>
26
27 void minix_put_inode(struct inode *inode)
28 {
29 if (inode->i_nlink)
30 return;
31 inode->i_size = 0;
32 minix_truncate(inode);
33 minix_free_inode(inode);
34 }
35
36 static void minix_commit_super (struct super_block * sb,
37 struct minix_super_block * ms)
38 {
39 mark_buffer_dirty(sb->u.minix_sb.s_sbh, 1);
40 sb->s_dirt = 0;
41 }
42
43 void minix_write_super (struct super_block * sb)
44 {
45 struct minix_super_block * ms;
46
47 if (!(sb->s_flags & MS_RDONLY)) {
48 ms = sb->u.minix_sb.s_ms;
49
50 if (ms->s_state & MINIX_VALID_FS)
51 ms->s_state &= ~MINIX_VALID_FS;
52 minix_commit_super (sb, ms);
53 }
54 sb->s_dirt = 0;
55 }
56
57
58 void minix_put_super(struct super_block *sb)
59 {
60 int i;
61
62 lock_super(sb);
63 if (!(sb->s_flags & MS_RDONLY)) {
64 sb->u.minix_sb.s_ms->s_state = sb->u.minix_sb.s_mount_state;
65 mark_buffer_dirty(sb->u.minix_sb.s_sbh, 1);
66 }
67 sb->s_dev = 0;
68 for(i = 0 ; i < MINIX_I_MAP_SLOTS ; i++)
69 brelse(sb->u.minix_sb.s_imap[i]);
70 for(i = 0 ; i < MINIX_Z_MAP_SLOTS ; i++)
71 brelse(sb->u.minix_sb.s_zmap[i]);
72 brelse (sb->u.minix_sb.s_sbh);
73 unlock_super(sb);
74 MOD_DEC_USE_COUNT;
75 return;
76 }
77
78 static struct super_operations minix_sops = {
79 minix_read_inode,
80 NULL,
81 minix_write_inode,
82 minix_put_inode,
83 minix_put_super,
84 minix_write_super,
85 minix_statfs,
86 minix_remount
87 };
88
89 int minix_remount (struct super_block * sb, int * flags, char * data)
90 {
91 struct minix_super_block * ms;
92
93 ms = sb->u.minix_sb.s_ms;
94 if ((*flags & MS_RDONLY) == (sb->s_flags & MS_RDONLY))
95 return 0;
96 if (*flags & MS_RDONLY) {
97 if (ms->s_state & MINIX_VALID_FS ||
98 !(sb->u.minix_sb.s_mount_state & MINIX_VALID_FS))
99 return 0;
100
101 ms->s_state = sb->u.minix_sb.s_mount_state;
102 mark_buffer_dirty(sb->u.minix_sb.s_sbh, 1);
103 sb->s_dirt = 1;
104 minix_commit_super (sb, ms);
105 }
106 else {
107
108 sb->u.minix_sb.s_mount_state = ms->s_state;
109 ms->s_state &= ~MINIX_VALID_FS;
110 mark_buffer_dirty(sb->u.minix_sb.s_sbh, 1);
111 sb->s_dirt = 1;
112
113 if (!(sb->u.minix_sb.s_mount_state & MINIX_VALID_FS))
114 printk ("MINIX-fs warning: remounting unchecked fs, "
115 "running fsck is recommended.\n");
116 else if ((sb->u.minix_sb.s_mount_state & MINIX_ERROR_FS))
117 printk ("MINIX-fs warning: remounting fs with errors, "
118 "running fsck is recommended.\n");
119 }
120 return 0;
121 }
122
123
124 struct super_block *minix_read_super(struct super_block *s,void *data,
125 int silent)
126 {
127 struct buffer_head *bh;
128 struct minix_super_block *ms;
129 int i,dev=s->s_dev,block;
130
131 if (32 != sizeof (struct minix_inode))
132 panic("bad i-node size");
133 lock_super(s);
134 set_blocksize(dev, BLOCK_SIZE);
135 if (!(bh = bread(dev,1,BLOCK_SIZE))) {
136 s->s_dev=0;
137 unlock_super(s);
138 printk("MINIX-fs: unable to read superblock\n");
139 return NULL;
140 }
141 ms = (struct minix_super_block *) bh->b_data;
142 s->u.minix_sb.s_ms = ms;
143 s->u.minix_sb.s_sbh = bh;
144 s->u.minix_sb.s_mount_state = ms->s_state;
145 s->s_blocksize = 1024;
146 s->s_blocksize_bits = 10;
147 s->u.minix_sb.s_ninodes = ms->s_ninodes;
148 s->u.minix_sb.s_nzones = ms->s_nzones;
149 s->u.minix_sb.s_imap_blocks = ms->s_imap_blocks;
150 s->u.minix_sb.s_zmap_blocks = ms->s_zmap_blocks;
151 s->u.minix_sb.s_firstdatazone = ms->s_firstdatazone;
152 s->u.minix_sb.s_log_zone_size = ms->s_log_zone_size;
153 s->u.minix_sb.s_max_size = ms->s_max_size;
154 s->s_magic = ms->s_magic;
155 if (s->s_magic == MINIX_SUPER_MAGIC) {
156 s->u.minix_sb.s_dirsize = 16;
157 s->u.minix_sb.s_namelen = 14;
158 } else if (s->s_magic == MINIX_SUPER_MAGIC2) {
159 s->u.minix_sb.s_dirsize = 32;
160 s->u.minix_sb.s_namelen = 30;
161 } else {
162 s->s_dev = 0;
163 unlock_super(s);
164 brelse(bh);
165 if (!silent)
166 printk("VFS: Can't find a minix filesystem on dev 0x%04x.\n", dev);
167 return NULL;
168 }
169 for (i=0;i < MINIX_I_MAP_SLOTS;i++)
170 s->u.minix_sb.s_imap[i] = NULL;
171 for (i=0;i < MINIX_Z_MAP_SLOTS;i++)
172 s->u.minix_sb.s_zmap[i] = NULL;
173 block=2;
174 for (i=0 ; i < s->u.minix_sb.s_imap_blocks ; i++)
175 if ((s->u.minix_sb.s_imap[i]=bread(dev,block,BLOCK_SIZE)) != NULL)
176 block++;
177 else
178 break;
179 for (i=0 ; i < s->u.minix_sb.s_zmap_blocks ; i++)
180 if ((s->u.minix_sb.s_zmap[i]=bread(dev,block,BLOCK_SIZE)) != NULL)
181 block++;
182 else
183 break;
184 if (block != 2+s->u.minix_sb.s_imap_blocks+s->u.minix_sb.s_zmap_blocks) {
185 for(i=0;i<MINIX_I_MAP_SLOTS;i++)
186 brelse(s->u.minix_sb.s_imap[i]);
187 for(i=0;i<MINIX_Z_MAP_SLOTS;i++)
188 brelse(s->u.minix_sb.s_zmap[i]);
189 s->s_dev=0;
190 unlock_super(s);
191 brelse(bh);
192 printk("MINIX-fs: bad superblock or unable to read bitmaps\n");
193 return NULL;
194 }
195 set_bit(0,s->u.minix_sb.s_imap[0]->b_data);
196 set_bit(0,s->u.minix_sb.s_zmap[0]->b_data);
197 unlock_super(s);
198
199 s->s_dev = dev;
200 s->s_op = &minix_sops;
201 s->s_mounted = iget(s,MINIX_ROOT_INO);
202 if (!s->s_mounted) {
203 s->s_dev = 0;
204 brelse(bh);
205 printk("MINIX-fs: get root inode failed\n");
206 return NULL;
207 }
208 if (!(s->s_flags & MS_RDONLY)) {
209 ms->s_state &= ~MINIX_VALID_FS;
210 mark_buffer_dirty(bh, 1);
211 s->s_dirt = 1;
212 }
213 if (!(s->u.minix_sb.s_mount_state & MINIX_VALID_FS))
214 printk ("MINIX-fs: mounting unchecked file system, "
215 "running fsck is recommended.\n");
216 else if (s->u.minix_sb.s_mount_state & MINIX_ERROR_FS)
217 printk ("MINIX-fs: mounting file system with errors, "
218 "running fsck is recommended.\n");
219 MOD_INC_USE_COUNT;
220 return s;
221 }
222
223 void minix_statfs(struct super_block *sb, struct statfs *buf)
224 {
225 long tmp;
226
227 put_fs_long(MINIX_SUPER_MAGIC, &buf->f_type);
228 put_fs_long(1024, &buf->f_bsize);
229 tmp = sb->u.minix_sb.s_nzones - sb->u.minix_sb.s_firstdatazone;
230 tmp <<= sb->u.minix_sb.s_log_zone_size;
231 put_fs_long(tmp, &buf->f_blocks);
232 tmp = minix_count_free_blocks(sb);
233 put_fs_long(tmp, &buf->f_bfree);
234 put_fs_long(tmp, &buf->f_bavail);
235 put_fs_long(sb->u.minix_sb.s_ninodes, &buf->f_files);
236 put_fs_long(minix_count_free_inodes(sb), &buf->f_ffree);
237 put_fs_long(sb->u.minix_sb.s_namelen, &buf->f_namelen);
238
239 }
240
241 #define inode_bmap(inode,nr) ((inode)->u.minix_i.i_data[(nr)])
242
243 static int block_bmap(struct buffer_head * bh, int nr)
244 {
245 int tmp;
246
247 if (!bh)
248 return 0;
249 tmp = ((unsigned short *) bh->b_data)[nr];
250 brelse(bh);
251 return tmp;
252 }
253
254 int minix_bmap(struct inode * inode,int block)
255 {
256 int i;
257
258 if (block<0) {
259 printk("minix_bmap: block<0");
260 return 0;
261 }
262 if (block >= 7+512+512*512) {
263 printk("minix_bmap: block>big");
264 return 0;
265 }
266 if (block < 7)
267 return inode_bmap(inode,block);
268 block -= 7;
269 if (block < 512) {
270 i = inode_bmap(inode,7);
271 if (!i)
272 return 0;
273 return block_bmap(bread(inode->i_dev,i,BLOCK_SIZE),block);
274 }
275 block -= 512;
276 i = inode_bmap(inode,8);
277 if (!i)
278 return 0;
279 i = block_bmap(bread(inode->i_dev,i,BLOCK_SIZE),block>>9);
280 if (!i)
281 return 0;
282 return block_bmap(bread(inode->i_dev,i,BLOCK_SIZE),block & 511);
283 }
284
285 static struct buffer_head * inode_getblk(struct inode * inode, int nr, int create)
286 {
287 int tmp;
288 unsigned short *p;
289 struct buffer_head * result;
290
291 p = inode->u.minix_i.i_data + nr;
292 repeat:
293 tmp = *p;
294 if (tmp) {
295 result = getblk(inode->i_dev, tmp, BLOCK_SIZE);
296 if (tmp == *p)
297 return result;
298 brelse(result);
299 goto repeat;
300 }
301 if (!create)
302 return NULL;
303 tmp = minix_new_block(inode->i_sb);
304 if (!tmp)
305 return NULL;
306 result = getblk(inode->i_dev, tmp, BLOCK_SIZE);
307 if (*p) {
308 minix_free_block(inode->i_sb,tmp);
309 brelse(result);
310 goto repeat;
311 }
312 *p = tmp;
313 inode->i_ctime = CURRENT_TIME;
314 inode->i_dirt = 1;
315 return result;
316 }
317
318 static struct buffer_head * block_getblk(struct inode * inode,
319 struct buffer_head * bh, int nr, int create)
320 {
321 int tmp;
322 unsigned short *p;
323 struct buffer_head * result;
324
325 if (!bh)
326 return NULL;
327 if (!bh->b_uptodate) {
328 ll_rw_block(READ, 1, &bh);
329 wait_on_buffer(bh);
330 if (!bh->b_uptodate) {
331 brelse(bh);
332 return NULL;
333 }
334 }
335 p = nr + (unsigned short *) bh->b_data;
336 repeat:
337 tmp = *p;
338 if (tmp) {
339 result = getblk(bh->b_dev, tmp, BLOCK_SIZE);
340 if (tmp == *p) {
341 brelse(bh);
342 return result;
343 }
344 brelse(result);
345 goto repeat;
346 }
347 if (!create) {
348 brelse(bh);
349 return NULL;
350 }
351 tmp = minix_new_block(inode->i_sb);
352 if (!tmp) {
353 brelse(bh);
354 return NULL;
355 }
356 result = getblk(bh->b_dev, tmp, BLOCK_SIZE);
357 if (*p) {
358 minix_free_block(inode->i_sb,tmp);
359 brelse(result);
360 goto repeat;
361 }
362 *p = tmp;
363 mark_buffer_dirty(bh, 1);
364 brelse(bh);
365 return result;
366 }
367
368 struct buffer_head * minix_getblk(struct inode * inode, int block, int create)
369 {
370 struct buffer_head * bh;
371
372 if (block<0) {
373 printk("minix_getblk: block<0");
374 return NULL;
375 }
376 if (block >= 7+512+512*512) {
377 printk("minix_getblk: block>big");
378 return NULL;
379 }
380 if (block < 7)
381 return inode_getblk(inode,block,create);
382 block -= 7;
383 if (block < 512) {
384 bh = inode_getblk(inode,7,create);
385 return block_getblk(inode, bh, block, create);
386 }
387 block -= 512;
388 bh = inode_getblk(inode,8,create);
389 bh = block_getblk(inode, bh, block>>9, create);
390 return block_getblk(inode, bh, block & 511, create);
391 }
392
393 struct buffer_head * minix_bread(struct inode * inode, int block, int create)
394 {
395 struct buffer_head * bh;
396
397 bh = minix_getblk(inode,block,create);
398 if (!bh || bh->b_uptodate)
399 return bh;
400 ll_rw_block(READ, 1, &bh);
401 wait_on_buffer(bh);
402 if (bh->b_uptodate)
403 return bh;
404 brelse(bh);
405 return NULL;
406 }
407
408 void minix_read_inode(struct inode * inode)
409 {
410 struct buffer_head * bh;
411 struct minix_inode * raw_inode;
412 int block, ino;
413
414 ino = inode->i_ino;
415 inode->i_op = NULL;
416 inode->i_mode = 0;
417 if (!ino || ino >= inode->i_sb->u.minix_sb.s_ninodes) {
418 printk("Bad inode number on dev 0x%04x: %d is out of range\n",
419 inode->i_dev, ino);
420 return;
421 }
422 block = 2 + inode->i_sb->u.minix_sb.s_imap_blocks +
423 inode->i_sb->u.minix_sb.s_zmap_blocks +
424 (ino-1)/MINIX_INODES_PER_BLOCK;
425 if (!(bh=bread(inode->i_dev,block, BLOCK_SIZE))) {
426 printk("Major problem: unable to read inode from dev 0x%04x\n",
427 inode->i_dev);
428 return;
429 }
430 raw_inode = ((struct minix_inode *) bh->b_data) +
431 (ino-1)%MINIX_INODES_PER_BLOCK;
432 inode->i_mode = raw_inode->i_mode;
433 inode->i_uid = raw_inode->i_uid;
434 inode->i_gid = raw_inode->i_gid;
435 inode->i_nlink = raw_inode->i_nlinks;
436 inode->i_size = raw_inode->i_size;
437 inode->i_mtime = inode->i_atime = inode->i_ctime = raw_inode->i_time;
438 inode->i_blocks = inode->i_blksize = 0;
439 if (S_ISCHR(inode->i_mode) || S_ISBLK(inode->i_mode))
440 inode->i_rdev = raw_inode->i_zone[0];
441 else for (block = 0; block < 9; block++)
442 inode->u.minix_i.i_data[block] = raw_inode->i_zone[block];
443 brelse(bh);
444 if (S_ISREG(inode->i_mode))
445 inode->i_op = &minix_file_inode_operations;
446 else if (S_ISDIR(inode->i_mode))
447 inode->i_op = &minix_dir_inode_operations;
448 else if (S_ISLNK(inode->i_mode))
449 inode->i_op = &minix_symlink_inode_operations;
450 else if (S_ISCHR(inode->i_mode))
451 inode->i_op = &chrdev_inode_operations;
452 else if (S_ISBLK(inode->i_mode))
453 inode->i_op = &blkdev_inode_operations;
454 else if (S_ISFIFO(inode->i_mode))
455 init_fifo(inode);
456 }
457
458 static struct buffer_head * minix_update_inode(struct inode * inode)
459 {
460 struct buffer_head * bh;
461 struct minix_inode * raw_inode;
462 int ino, block;
463
464 ino = inode->i_ino;
465 if (!ino || ino >= inode->i_sb->u.minix_sb.s_ninodes) {
466 printk("Bad inode number on dev 0x%04x: %d is out of range\n",
467 inode->i_dev, ino);
468 inode->i_dirt = 0;
469 return 0;
470 }
471 block = 2 + inode->i_sb->u.minix_sb.s_imap_blocks + inode->i_sb->u.minix_sb.s_zmap_blocks +
472 (ino-1)/MINIX_INODES_PER_BLOCK;
473 if (!(bh=bread(inode->i_dev, block, BLOCK_SIZE))) {
474 printk("unable to read i-node block\n");
475 inode->i_dirt = 0;
476 return 0;
477 }
478 raw_inode = ((struct minix_inode *)bh->b_data) +
479 (ino-1)%MINIX_INODES_PER_BLOCK;
480 raw_inode->i_mode = inode->i_mode;
481 raw_inode->i_uid = inode->i_uid;
482 raw_inode->i_gid = inode->i_gid;
483 raw_inode->i_nlinks = inode->i_nlink;
484 raw_inode->i_size = inode->i_size;
485 raw_inode->i_time = inode->i_mtime;
486 if (S_ISCHR(inode->i_mode) || S_ISBLK(inode->i_mode))
487 raw_inode->i_zone[0] = inode->i_rdev;
488 else for (block = 0; block < 9; block++)
489 raw_inode->i_zone[block] = inode->u.minix_i.i_data[block];
490 inode->i_dirt=0;
491 mark_buffer_dirty(bh, 1);
492 return bh;
493 }
494
495 void minix_write_inode(struct inode * inode)
496 {
497 struct buffer_head *bh;
498 bh = minix_update_inode(inode);
499 brelse(bh);
500 }
501
502 int minix_sync_inode(struct inode * inode)
503 {
504 int err = 0;
505 struct buffer_head *bh;
506
507 bh = minix_update_inode(inode);
508 if (bh && bh->b_dirt)
509 {
510 ll_rw_block(WRITE, 1, &bh);
511 wait_on_buffer(bh);
512 if (bh->b_req && !bh->b_uptodate)
513 {
514 printk ("IO error syncing minix inode [%04x:%08lx]\n",
515 inode->i_dev, inode->i_ino);
516 err = -1;
517 }
518 }
519 else if (!bh)
520 err = -1;
521 brelse (bh);
522 return err;
523 }
524
525 #ifdef MODULE
526
527 char kernel_version[] = UTS_RELEASE;
528
529 static struct file_system_type minix_fs_type = {
530 minix_read_super, "minix", 1, NULL
531 };
532
533 int init_module(void)
534 {
535 register_filesystem(&minix_fs_type);
536 return 0;
537 }
538
539 void cleanup_module(void)
540 {
541 if (MOD_IN_USE)
542 printk("ne: device busy, remove delayed\n");
543 else
544 {
545 unregister_filesystem(&minix_fs_type);
546 }
547 }
548
549 #endif
550