⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 super.c

📁 ARM 嵌入式 系统 设计与实例开发 实验教材 二源码
💻 C
📖 第 1 页 / 共 2 页
字号:
/* *  linux/fs/hpfs/super.c * *  Mikulas Patocka (mikulas@artax.karlin.mff.cuni.cz), 1998-1999 * *  mounting, unmounting, error handling */#include <linux/string.h>#include "hpfs_fn.h"#include <linux/module.h>#include <linux/init.h>/* Mark the filesystem dirty, so that chkdsk checks it when os/2 booted */static void mark_dirty(struct super_block *s){	if (s->s_hpfs_chkdsk && !(s->s_flags & MS_RDONLY)) {		struct buffer_head *bh;		struct hpfs_spare_block *sb;		if ((sb = hpfs_map_sector(s, 17, &bh, 0))) {			sb->dirty = 1;			sb->old_wrote = 0;			mark_buffer_dirty(bh);			brelse(bh);		}	}}/* Mark the filesystem clean (mark it dirty for chkdsk if chkdsk==2 or if there   were errors) */static void unmark_dirty(struct super_block *s){	struct buffer_head *bh;	struct hpfs_spare_block *sb;	if (s->s_flags & MS_RDONLY) return;	if ((sb = hpfs_map_sector(s, 17, &bh, 0))) {		sb->dirty = s->s_hpfs_chkdsk > 1 - s->s_hpfs_was_error;		sb->old_wrote = s->s_hpfs_chkdsk >= 2 && !s->s_hpfs_was_error;		mark_buffer_dirty(bh);		brelse(bh);	}}/* Filesystem error... */#define ERR_BUF_SIZE 1024void hpfs_error(struct super_block *s, char *m,...){	char *buf;	va_list l;	va_start(l, m);	if (!(buf = kmalloc(ERR_BUF_SIZE, GFP_KERNEL)))		printk("HPFS: No memory for error message '%s'\n",m);	else if (vsprintf(buf, m, l) >= ERR_BUF_SIZE)		printk("HPFS: Grrrr... Kernel memory corrupted ... going on, but it'll crash very soon :-(\n");	printk("HPFS: filesystem error: ");	if (buf) printk("%s", buf);	else printk("%s\n",m);	if (!s->s_hpfs_was_error) {		if (s->s_hpfs_err == 2) {			printk("; crashing the system because you wanted it\n");			mark_dirty(s);			panic("HPFS panic");		} else if (s->s_hpfs_err == 1) {			if (s->s_flags & MS_RDONLY) printk("; already mounted read-only\n");			else {				printk("; remounting read-only\n");				mark_dirty(s);				s->s_flags |= MS_RDONLY;			}		} else if (s->s_flags & MS_RDONLY) printk("; going on - but anything won't be destroyed because it's read-only\n");		else printk("; corrupted filesystem mounted read/write - your computer will explode within 20 seconds ... but you wanted it so!\n");	} else printk("\n");	if (buf) kfree(buf);	s->s_hpfs_was_error = 1;}/*  * A little trick to detect cycles in many hpfs structures and don't let the * kernel crash on corrupted filesystem. When first called, set c2 to 0. * * BTW. chkdsk doesn't detect cycles correctly. When I had 2 lost directories * nested each in other, chkdsk locked up happilly. */int hpfs_stop_cycles(struct super_block *s, int key, int *c1, int *c2,		char *msg){	if (*c2 && *c1 == key) {		hpfs_error(s, "cycle detected on key %08x in %s", key, msg);		return 1;	}	(*c2)++;	if (!((*c2 - 1) & *c2)) *c1 = key;	return 0;}void hpfs_put_super(struct super_block *s){	if (s->s_hpfs_cp_table) kfree(s->s_hpfs_cp_table);	if (s->s_hpfs_bmp_dir) kfree(s->s_hpfs_bmp_dir);	unmark_dirty(s);}unsigned hpfs_count_one_bitmap(struct super_block *s, secno secno){	struct quad_buffer_head qbh;	unsigned *bits;	unsigned i, count;	if (!(bits = hpfs_map_4sectors(s, secno, &qbh, 4))) return 0;	count = 0;	for (i = 0; i < 2048 / sizeof(unsigned); i++) {		unsigned b; 		if (!bits[i]) continue;		for (b = bits[i]; b; b>>=1) count += b & 1;	}	hpfs_brelse4(&qbh);	return count;}static unsigned count_bitmaps(struct super_block *s){	unsigned n, count, n_bands;	n_bands = (s->s_hpfs_fs_size + 0x3fff) >> 14;	count = 0;	for (n = 0; n < n_bands; n++)		count += hpfs_count_one_bitmap(s, s->s_hpfs_bmp_dir[n]);	return count;}int hpfs_statfs(struct super_block *s, struct statfs *buf){	/*if (s->s_hpfs_n_free == -1) {*/		s->s_hpfs_n_free = count_bitmaps(s);		s->s_hpfs_n_free_dnodes = hpfs_count_one_bitmap(s, s->s_hpfs_dmap);	/*}*/	buf->f_type = s->s_magic;	buf->f_bsize = 512;	buf->f_blocks = s->s_hpfs_fs_size;	buf->f_bfree = s->s_hpfs_n_free;	buf->f_bavail = s->s_hpfs_n_free;	buf->f_files = s->s_hpfs_dirband_size / 4;	buf->f_ffree = s->s_hpfs_n_free_dnodes;	buf->f_namelen = 254;	return 0;}/* Super operations */static struct super_operations hpfs_sops ={        read_inode:	hpfs_read_inode,	delete_inode:	hpfs_delete_inode,	put_super:	hpfs_put_super,	statfs:		hpfs_statfs,	remount_fs:	hpfs_remount_fs,};/* * A tiny parser for option strings, stolen from dosfs. * * Stolen again from read-only hpfs. */int parse_opts(char *opts, uid_t *uid, gid_t *gid, umode_t *umask,	       int *lowercase, int *conv, int *eas, int *chk, int *errs,	       int *chkdsk, int *timeshift){	char *p, *rhs;	if (!opts)		return 1;	/*printk("Parsing opts: '%s'\n",opts);*/	for (p = strtok(opts, ","); p != 0; p = strtok(0, ",")) {		if ((rhs = strchr(p, '=')) != 0)			*rhs++ = '\0';		if (!strcmp(p, "help")) return 2;		if (!strcmp(p, "uid")) {			if (!rhs || !*rhs)				return 0;			*uid = simple_strtoul(rhs, &rhs, 0);			if (*rhs)				return 0;		}		else if (!strcmp(p, "gid")) {			if (!rhs || !*rhs)				return 0;			*gid = simple_strtoul(rhs, &rhs, 0);			if (*rhs)				return 0;		}		else if (!strcmp(p, "umask")) {			if (!rhs || !*rhs)				return 0;			*umask = simple_strtoul(rhs, &rhs, 8);			if (*rhs)				return 0;		}		else if (!strcmp(p, "timeshift")) {			int m = 1;			if (!rhs || !*rhs)				return 0;			if (*rhs == '-') m = -1;			if (*rhs == '+' || *rhs == '-') rhs++;			*timeshift = simple_strtoul(rhs, &rhs, 0) * m;			if (*rhs)				return 0;		}		else if (!strcmp(p, "case")) {			if (!rhs || !*rhs)				return 0;			if (!strcmp(rhs, "lower"))				*lowercase = 1;			else if (!strcmp(rhs, "asis"))				*lowercase = 0;			else				return 0;		}		else if (!strcmp(p, "conv")) {			if (!rhs || !*rhs)				return 0;			if (!strcmp(rhs, "binary"))				*conv = CONV_BINARY;			else if (!strcmp(rhs, "text"))				*conv = CONV_TEXT;			else if (!strcmp(rhs, "auto"))				*conv = CONV_AUTO;			else				return 0;		}		else if (!strcmp(p, "check")) {			if (!rhs || !*rhs)				return 0;			if (!strcmp(rhs, "none"))				*chk = 0;			else if (!strcmp(rhs, "normal"))				*chk = 1;			else if (!strcmp(rhs, "strict"))				*chk = 2;			else				return 0;		}		else if (!strcmp(p, "errors")) {			if (!rhs || !*rhs)				return 0;			if (!strcmp(rhs, "continue"))				*errs = 0;			else if (!strcmp(rhs, "remount-ro"))				*errs = 1;			else if (!strcmp(rhs, "panic"))				*errs = 2;			else				return 0;		}		else if (!strcmp(p, "eas")) {			if (!rhs || !*rhs)				return 0;			if (!strcmp(rhs, "no"))				*eas = 0;			else if (!strcmp(rhs, "ro"))				*eas = 1;			else if (!strcmp(rhs, "rw"))				*eas = 2;			else				return 0;		}		else if (!strcmp(p, "chkdsk")) {			if (!rhs || !*rhs)				return 0;			if (!strcmp(rhs, "no"))				*chkdsk = 0;			else if (!strcmp(rhs, "errors"))				*chkdsk = 1;			else if (!strcmp(rhs, "always"))				*chkdsk = 2;			else				return 0;		}		else			return 0;	}	return 1;}static inline void hpfs_help(void){	printk("\n\HPFS filesystem options:\n\      help              do not mount and display this text\n\

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -