亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频

? 歡迎來(lái)到蟲(chóng)蟲(chóng)下載站! | ?? 資源下載 ?? 資源專輯 ?? 關(guān)于我們
? 蟲(chóng)蟲(chóng)下載站

?? hd.c

?? LINUX1.0源代碼,代碼條理清晰
?? C
?? 第 1 頁(yè) / 共 2 頁(yè)
字號(hào):
#endif
		do_hd_request();
	}
	return;
}

static void recal_intr(void)
{
	if (win_result())
		bad_rw_intr();
	do_hd_request();
}

/*
 * This is another of the error-routines I don't know what to do with. The
 * best idea seems to just set reset, and start all over again.
 */
static void hd_times_out(void)
{
	DEVICE_INTR = NULL;
	sti();
	reset = 1;
	if (!CURRENT)
		return;
	printk(KERN_DEBUG "HD timeout\n");
	cli();
	if (++CURRENT->errors >= MAX_ERRORS) {
#ifdef DEBUG
		printk("hd : too many errors.\n");
#endif
		end_request(0);
	}

	do_hd_request();
}

/*
 * The driver has been modified to enable interrupts a bit more: in order to
 * do this we first (a) disable the timeout-interrupt and (b) clear the
 * device-interrupt. This way the interrupts won't mess with out code (the
 * worst that can happen is that an unexpected HD-interrupt comes in and
 * sets the "reset" variable and starts the timer)
 */
static void do_hd_request(void)
{
	unsigned int block,dev;
	unsigned int sec,head,cyl,track;
	unsigned int nsect;

	if (CURRENT && CURRENT->dev < 0) return;

	if (DEVICE_INTR)
		return;
repeat:
	timer_active &= ~(1<<HD_TIMER);
	sti();
	INIT_REQUEST;
	dev = MINOR(CURRENT->dev);
	block = CURRENT->sector;
	nsect = CURRENT->nr_sectors;
	if (dev >= (NR_HD<<6) || block >= hd[dev].nr_sects) {
#ifdef DEBUG
		printk("hd%d : attempted read for sector %d past end of device at sector %d.\n",
		   	block, hd[dev].nr_sects);
#endif
		end_request(0);
		goto repeat;
	}
	block += hd[dev].start_sect;
	dev >>= 6;
	sec = block % hd_info[dev].sect + 1;
	track = block / hd_info[dev].sect;
	head = track % hd_info[dev].head;
	cyl = track / hd_info[dev].head;
#ifdef DEBUG
	printk("hd%d : cyl = %d, head = %d, sector = %d, buffer = %08x\n",
		dev, cyl, head, sec, CURRENT->buffer);
#endif
	cli();
	if (reset) {
		int i;

		for (i=0; i < NR_HD; i++)
			recalibrate[i] = 1;
		reset_hd();
		sti();
		return;
	}
	if (recalibrate[dev]) {
		recalibrate[dev] = 0;
		hd_out(dev,hd_info[dev].sect,0,0,0,WIN_RESTORE,&recal_intr);
		if (reset)
			goto repeat;
		sti();
		return;
	}	
	if (CURRENT->cmd == WRITE) {
		hd_out(dev,nsect,sec,head,cyl,WIN_WRITE,&write_intr);
		if (reset)
			goto repeat;
		if (wait_DRQ()) {
			printk("HD: do_hd_request: no DRQ\n");
			bad_rw_intr();
			goto repeat;
		}
		outsw(HD_DATA,CURRENT->buffer,256);
		sti();
		return;
	}
	if (CURRENT->cmd == READ) {
		hd_out(dev,nsect,sec,head,cyl,WIN_READ,&read_intr);
		if (reset)
			goto repeat;
		sti();
		return;
	}
	panic("unknown hd-command");
}

static int hd_ioctl(struct inode * inode, struct file * file,
	unsigned int cmd, unsigned long arg)
{
	struct hd_geometry *loc = (struct hd_geometry *) arg;
	int dev, err;

	if (!inode)
		return -EINVAL;
	dev = MINOR(inode->i_rdev) >> 6;
	if (dev >= NR_HD)
		return -EINVAL;
	switch (cmd) {
		case HDIO_GETGEO:
			if (!loc)  return -EINVAL;
			err = verify_area(VERIFY_WRITE, loc, sizeof(*loc));
			if (err)
				return err;
			put_fs_byte(hd_info[dev].head,
				(char *) &loc->heads);
			put_fs_byte(hd_info[dev].sect,
				(char *) &loc->sectors);
			put_fs_word(hd_info[dev].cyl,
				(short *) &loc->cylinders);
			put_fs_long(hd[MINOR(inode->i_rdev)].start_sect,
				(long *) &loc->start);
			return 0;
         	case BLKGETSIZE:   /* Return device size */
			if (!arg)  return -EINVAL;
			err = verify_area(VERIFY_WRITE, (long *) arg, sizeof(long));
			if (err)
				return err;
			put_fs_long(hd[MINOR(inode->i_rdev)].nr_sects,
				(long *) arg);
			return 0;
		case BLKFLSBUF:
			if(!suser())  return -EACCES;
			if(!inode->i_rdev) return -EINVAL;
			fsync_dev(inode->i_rdev);
			invalidate_buffers(inode->i_rdev);
			return 0;

		case BLKRRPART: /* Re-read partition tables */
			return revalidate_hddisk(inode->i_rdev, 1);
		RO_IOCTLS(inode->i_rdev,arg);
		default:
			return -EINVAL;
	}
}

static int hd_open(struct inode * inode, struct file * filp)
{
	int target;
	target =  DEVICE_NR(MINOR(inode->i_rdev));

	while (busy[target])
		sleep_on(&busy_wait);
	access_count[target]++;
	return 0;
}

/*
 * Releasing a block device means we sync() it, so that it can safely
 * be forgotten about...
 */
static void hd_release(struct inode * inode, struct file * file)
{
        int target;
	sync_dev(inode->i_rdev);

	target =  DEVICE_NR(MINOR(inode->i_rdev));
	access_count[target]--;

}

static void hd_geninit(void);

static struct gendisk hd_gendisk = {
	MAJOR_NR,	/* Major number */	
	"hd",		/* Major name */
	6,		/* Bits to shift to get real from partition */
	1 << 6,		/* Number of partitions per real */
	MAX_HD,		/* maximum number of real */
	hd_geninit,	/* init function */
	hd,		/* hd struct */
	hd_sizes,	/* block sizes */
	0,		/* number */
	(void *) hd_info,	/* internal */
	NULL		/* next */
};
	
static void hd_interrupt(int unused)
{
	void (*handler)(void) = DEVICE_INTR;

	DEVICE_INTR = NULL;
	timer_active &= ~(1<<HD_TIMER);
	if (!handler)
		handler = unexpected_hd_interrupt;
	handler();
	sti();
}

/*
 * This is the harddisk IRQ description. The SA_INTERRUPT in sa_flags
 * means we run the IRQ-handler with interrupts disabled: this is bad for
 * interrupt latency, but anything else has led to problems on some
 * machines...
 *
 * We enable interrupts in some of the routines after making sure it's
 * safe.
 */
static struct sigaction hd_sigaction = {
	hd_interrupt,
	0,
	SA_INTERRUPT,
	NULL
};

static void hd_geninit(void)
{
	int drive, i;
	extern struct drive_info drive_info;
	unsigned char *BIOS = (unsigned char *) &drive_info;
	int cmos_disks;

	if (!NR_HD) {	   
		for (drive=0 ; drive<2 ; drive++) {
			hd_info[drive].cyl = *(unsigned short *) BIOS;
			hd_info[drive].head = *(2+BIOS);
			hd_info[drive].wpcom = *(unsigned short *) (5+BIOS);
			hd_info[drive].ctl = *(8+BIOS);
			hd_info[drive].lzone = *(unsigned short *) (12+BIOS);
			hd_info[drive].sect = *(14+BIOS);
			BIOS += 16;
		}

	/*
		We querry CMOS about hard disks : it could be that 
		we have a SCSI/ESDI/etc controller that is BIOS
		compatable with ST-506, and thus showing up in our
		BIOS table, but not register compatable, and therefore
		not present in CMOS.

		Furthurmore, we will assume that our ST-506 drives
		<if any> are the primary drives in the system, and 
		the ones reflected as drive 1 or 2.

		The first drive is stored in the high nibble of CMOS
		byte 0x12, the second in the low nibble.  This will be
		either a 4 bit drive type or 0xf indicating use byte 0x19 
		for an 8 bit type, drive 1, 0x1a for drive 2 in CMOS.

		Needless to say, a non-zero value means we have 
		an AT controller hard disk for that drive.

		
	*/

		if ((cmos_disks = CMOS_READ(0x12)) & 0xf0)
			if (cmos_disks & 0x0f)
				NR_HD = 2;
			else
				NR_HD = 1;
	}
	i = NR_HD;
	while (i-- > 0) {
		hd[i<<6].nr_sects = 0;
		if (hd_info[i].head > 16) {
			printk("hd.c: ST-506 interface disk with more than 16 heads detected,\n");
			printk("  probably due to non-standard sector translation. Giving up.\n");
			printk("  (disk %d: cyl=%d, sect=%d, head=%d)\n", i,
				hd_info[i].cyl,
				hd_info[i].sect,
				hd_info[i].head);
			if (i+1 == NR_HD)
				NR_HD--;
			continue;
		}
		hd[i<<6].nr_sects = hd_info[i].head*
				hd_info[i].sect*hd_info[i].cyl;
	}
	if (NR_HD) {
		if (irqaction(HD_IRQ,&hd_sigaction)) {
			printk("hd.c: unable to get IRQ%d for the harddisk driver\n",HD_IRQ);
			NR_HD = 0;
		}
	}
	hd_gendisk.nr_real = NR_HD;

	for(i=0;i<(MAX_HD << 6);i++) hd_blocksizes[i] = 1024;
	blksize_size[MAJOR_NR] = hd_blocksizes;
}

static struct file_operations hd_fops = {
	NULL,			/* lseek - default */
	block_read,		/* read - general block-dev read */
	block_write,		/* write - general block-dev write */
	NULL,			/* readdir - bad */
	NULL,			/* select */
	hd_ioctl,		/* ioctl */
	NULL,			/* mmap */
	hd_open,		/* open */
	hd_release,		/* release */
	block_fsync		/* fsync */
};

unsigned long hd_init(unsigned long mem_start, unsigned long mem_end)
{
	if (register_blkdev(MAJOR_NR,"hd",&hd_fops)) {
		printk("Unable to get major %d for harddisk\n",MAJOR_NR);
		return mem_start;
	}
	blk_dev[MAJOR_NR].request_fn = DEVICE_REQUEST;
	read_ahead[MAJOR_NR] = 8;		/* 8 sector (4kB) read-ahead */
	hd_gendisk.next = gendisk_head;
	gendisk_head = &hd_gendisk;
	timer_table[HD_TIMER].fn = hd_times_out;
	return mem_start;
}

#define DEVICE_BUSY busy[target]
#define USAGE access_count[target]
#define CAPACITY (hd_info[target].head*hd_info[target].sect*hd_info[target].cyl)
/* We assume that the the bios parameters do not change, so the disk capacity
   will not change */
#undef MAYBE_REINIT
#define GENDISK_STRUCT hd_gendisk

/*
 * This routine is called to flush all partitions and partition tables
 * for a changed scsi disk, and then re-read the new partition table.
 * If we are revalidating a disk because of a media change, then we
 * enter with usage == 0.  If we are using an ioctl, we automatically have
 * usage == 1 (we need an open channel to use an ioctl :-), so this
 * is our limit.
 */
static int revalidate_hddisk(int dev, int maxusage)
{
	int target, major;
	struct gendisk * gdev;
	int max_p;
	int start;
	int i;

	target =  DEVICE_NR(MINOR(dev));
	gdev = &GENDISK_STRUCT;

	cli();
	if (DEVICE_BUSY || USAGE > maxusage) {
		sti();
		return -EBUSY;
	};
	DEVICE_BUSY = 1;
	sti();

	max_p = gdev->max_p;
	start = target << gdev->minor_shift;
	major = MAJOR_NR << 8;

	for (i=max_p - 1; i >=0 ; i--) {
		sync_dev(major | start | i);
		invalidate_inodes(major | start | i);
		invalidate_buffers(major | start | i);
		gdev->part[start+i].start_sect = 0;
		gdev->part[start+i].nr_sects = 0;
	};

#ifdef MAYBE_REINIT
	MAYBE_REINIT;
#endif

	gdev->part[start].nr_sects = CAPACITY;
	resetup_one_dev(gdev, target);

	DEVICE_BUSY = 0;
	wake_up(&busy_wait);
	return 0;
}

?? 快捷鍵說(shuō)明

復(fù)制代碼 Ctrl + C
搜索代碼 Ctrl + F
全屏模式 F11
切換主題 Ctrl + Shift + D
顯示快捷鍵 ?
增大字號(hào) Ctrl + =
減小字號(hào) Ctrl + -
亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频
亚洲午夜视频在线观看| 欧美日韩成人一区二区| 国产成人一区在线| 精品亚洲成a人| 韩国成人精品a∨在线观看| 久久精品国产精品亚洲综合| 日韩av在线发布| 久久er99精品| 国产精品白丝jk白祙喷水网站| 国内久久婷婷综合| 国产一区二区精品久久| 国产99久久久国产精品免费看| 国产精品一品视频| 成人黄色a**站在线观看| 99热精品一区二区| 在线视频综合导航| 91精品国产色综合久久 | 国产欧美一区二区三区在线看蜜臀| 久久久久久麻豆| 国产精品日日摸夜夜摸av| 自拍偷拍亚洲综合| 亚洲综合在线免费观看| 亚洲v中文字幕| 国内国产精品久久| 波多野结衣中文一区| 一本久久a久久免费精品不卡| 欧美亚洲综合色| 精品少妇一区二区三区日产乱码 | 国产一区二区三区免费播放| 成人一道本在线| 在线亚洲欧美专区二区| 欧美一级夜夜爽| 国产欧美日韩一区二区三区在线观看| 国产精品久久久久一区二区三区| 亚洲自拍偷拍欧美| 精品一区二区国语对白| 91在线小视频| 制服.丝袜.亚洲.中文.综合| 久久天天做天天爱综合色| 亚洲三级小视频| 免费成人av资源网| 91亚洲精品久久久蜜桃| 91精品在线一区二区| 日本一区二区久久| 午夜欧美电影在线观看| 国产高清不卡一区| 欧美日韩你懂的| 国产亚洲精品aa午夜观看| 亚洲精品精品亚洲| 国产一区二区三区av电影| 91久久精品网| 久久久久免费观看| 午夜精品久久久久久久| 国产成人啪免费观看软件 | 国产精品久久久爽爽爽麻豆色哟哟| 亚洲国产sm捆绑调教视频| 国产高清一区日本| 欧美人牲a欧美精品| 中文av一区二区| 蜜臀av一区二区在线免费观看 | 日韩一区二区三区在线视频| 国产精品欧美久久久久一区二区 | 欧美色倩网站大全免费| 国产精品欧美一区喷水| 美女国产一区二区三区| 在线视频国内自拍亚洲视频| 国产亚洲va综合人人澡精品| 男女男精品网站| 欧美日韩精品专区| 亚洲色图色小说| 成人小视频在线观看| 欧美成人三级在线| 日韩国产欧美在线播放| 色88888久久久久久影院按摩| 久久久久久久久久久久电影| 日韩电影一区二区三区四区| 欧美亚一区二区| 亚洲欧洲av在线| 成人激情动漫在线观看| 久久久久久久久99精品| 精品一区二区三区免费毛片爱| 欧美酷刑日本凌虐凌虐| 一卡二卡三卡日韩欧美| 99久久婷婷国产综合精品电影| 国产日韩欧美a| 国产精品99久久久久久似苏梦涵| 精品女同一区二区| 美女在线观看视频一区二区| 337p亚洲精品色噜噜| 亚洲成人在线网站| 欧美日韩在线一区二区| 亚洲另类一区二区| 色欧美日韩亚洲| 亚洲日本电影在线| 91丨九色丨国产丨porny| 国产精品久久久一本精品| 成人福利在线看| 国产精品三级av| 99久久精品一区二区| 亚洲欧洲日本在线| 97精品电影院| 亚洲精品五月天| 在线亚洲高清视频| 香蕉影视欧美成人| 欧美日韩电影一区| 免费观看91视频大全| 日韩欧美国产一二三区| 激情五月播播久久久精品| 精品国产乱码久久久久久老虎| 精品一区二区三区视频 | 奇米影视在线99精品| 日韩欧美综合一区| 极品少妇一区二区| 国产欧美视频一区二区| www.亚洲精品| 亚洲一区二区三区影院| 欧美高清视频不卡网| 麻豆视频一区二区| 欧美精品一区男女天堂| 97国产一区二区| 亚洲一区二区三区三| 欧美精品在线观看播放| 久久国产免费看| 国产精品日日摸夜夜摸av| 色综合天天视频在线观看| 亚洲一二三区视频在线观看| 91麻豆精品国产91久久久使用方法| 蜜桃一区二区三区四区| 久久精品亚洲精品国产欧美kt∨| 9色porny自拍视频一区二区| 一区二区三区高清| 日韩欧美成人一区| 波多野结衣中文字幕一区| 亚洲午夜激情网页| 欧美v亚洲v综合ⅴ国产v| 成人aa视频在线观看| 亚洲午夜在线视频| 2021久久国产精品不只是精品| www.66久久| 日本亚洲一区二区| 中文字幕av免费专区久久| 欧美日韩精品欧美日韩精品一| 久久精品国产亚洲a| 亚洲欧洲综合另类在线| 91精品国产入口| 99久久精品费精品国产一区二区| 五月综合激情网| 国产清纯在线一区二区www| 欧美日韩一区三区| 国产成人精品亚洲午夜麻豆| 亚洲高清免费一级二级三级| 久久夜色精品一区| 欧美日韩在线播放三区| 国产99久久久精品| 日本视频免费一区| 国产精品国产三级国产aⅴ中文| 欧美人与禽zozo性伦| 成人av在线网| 美女视频黄免费的久久| 亚洲美女少妇撒尿| 久久午夜电影网| 欧美日韩亚州综合| av资源网一区| 久久99精品久久久久久| 亚洲午夜激情网站| 亚洲国产高清在线| 欧美变态tickling挠脚心| 91麻豆.com| 国产成人av一区二区三区在线| 日产国产欧美视频一区精品| 亚洲日本在线看| 国产欧美一区二区三区在线看蜜臀 | 亚洲妇熟xx妇色黄| 国产精品久久久久久久久免费桃花 | 欧美草草影院在线视频| 欧美亚日韩国产aⅴ精品中极品| 国产69精品久久777的优势| 美女精品一区二区| 亚洲国产wwwccc36天堂| 亚洲人成精品久久久久| 国产色91在线| 26uuuu精品一区二区| 日韩欧美一级二级三级| 欧美日韩精品二区第二页| 一本色道久久综合狠狠躁的推荐 | 欧美日韩国产另类不卡| 91浏览器入口在线观看| 国产宾馆实践打屁股91| 国产一区二区成人久久免费影院| 日韩av在线免费观看不卡| 亚洲国产精品久久久久婷婷884| 亚洲欧美一区二区视频| 日本一区免费视频| 国产亚洲欧美日韩日本| www欧美成人18+| 久久久久久久综合日本| 精品国产乱码久久久久久图片| 日韩一区二区三区免费看| 4438成人网| 3d成人h动漫网站入口|