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

📄 ide.c

📁 1. 8623L平台
💻 C
📖 第 1 页 / 共 2 页
字号:
	return 0;}int ide_select_drive(int drive){	unsigned short select = g_ideinfo[drive].select.all;	unsigned int status;	OUT_BYTE(drive, select, IDE_SELECT_REG);	if (ide_wait_stat(drive, BUSY_STAT, 0, 1))		return 1;	if ((IN_BYTE(drive, IDE_SELECT_REG) & 0xff) != select) 		return 1;		status = IN_BYTE(drive, IDE_STATUS_REG);	return (status & READY_STAT) ? 0 : 1;}void ide_input_data(int drive, unsigned int *buf, unsigned int wcount){	unsigned short *ptr = (unsigned short *) buf;	// read data	while (wcount-- > 0) {		*ptr++ = IN_WORD(drive, IDE_DATA_REG);		*ptr++ = IN_WORD(drive, IDE_DATA_REG);	}}void ide_output_data(int drive, unsigned int *buf, unsigned int wcount){	unsigned short *ptr = (unsigned short *) buf;	// write data	while (wcount-- > 0) {		OUT_WORD(drive, *ptr++, IDE_DATA_REG);		OUT_WORD(drive, *ptr++, IDE_DATA_REG);	}}void ide_fixstring(unsigned char *s, const int bytecount, const int byteswap){	unsigned char *p = s, *end = &s[bytecount & ~1]; /* bytecount must be even */	if (byteswap) {		/* convert from big-endian to host unsigned char order */		for (p = end ; p != s;) {			unsigned short *pp = (unsigned short *) (p -= 2);			*pp = ntohs(*pp);		}	}	/* strip leading blanks */	while (s != end && *s == ' ')		++s;	/* compress internal blanks and strip trailing blanks */	while (s != end && *s) {		if (*s++ != ' ' || (s != end && *s && *s != ' '))			*p++ = *(s-1);	}	/* wipe out trailing garbage */	while (p != end)		*p++ = '\0';}//// IDE Identify//static int ide_identify_cmd(int cmd, int drive, struct hd_driveid *pid);ide_info_t *ide_identify(int drive){	ide_info_t *pideinfo = g_ideinfo + drive;	struct hd_driveid *pid = &pideinfo->id;	pideinfo->type = IDE_NONE;			if (ide_identify_cmd(WIN_IDENTIFY, drive, pid) == 0) {		pideinfo->type = IDE_ATA;		pideinfo->cyls = pid->cyls;		pideinfo->heads = pid->heads;		pideinfo->sectors = pid->sectors;		// C/H/S = 16383/16/63 : LBA		if (pid->cyls == 16383 && pid->heads == 16 && pid->sectors == 63) {			pideinfo->lba = 1;			pideinfo->nsectors = pid->lba_capacity;			pideinfo->select.b.lba = 1;			pideinfo->heads = 255;			pideinfo->sectors = 63;			pideinfo->cyls = pideinfo->nsectors / (255 * 63);		} else {			pideinfo->lba = 0;			pideinfo->nsectors = pid->cyls * pid->heads * pid->sectors;			pideinfo->select.b.lba = 0;		}		pideinfo->cap_dma = (pideinfo->id.capability & 1) ? 1 : 0;		pideinfo->cap_udma = (pideinfo->id.field_valid & 0x04) ? 1 : 0;		pideinfo->size = pideinfo->nsectors >> 11;	} else if (ide_identify_cmd(WIN_PIDENTIFY, drive, pid) == 0) {		pideinfo->type = IDE_ATAPI;	}	return pideinfo;}int ide_identify_cmd(int cmd, int drive, struct hd_driveid *pid){	if (ide_command(cmd, drive, 0, 0, 0, 0, 0, pid, SECTOR_WORDS) == 0) {		ide_fixstring(pid->model, sizeof(pid->model), 1);		ide_fixstring(pid->fw_rev, sizeof(pid->fw_rev), 1);		ide_fixstring(pid->serial_no, sizeof(pid->serial_no), 1);		return 0;	} else		return 1;}//// Other commands//int ide_set_drive_speed(int drive, int speed){	return ide_command(WIN_SETFEATURES, drive, SETFEATURES_XFER, 0, 0, 0, speed, NULL, 0);}//// IDE read/write//static int ide_chs_rw(int read, int dma, int drive, unsigned int block, unsigned char *buf, int nsector);static int ide_lbs_28_rw(int read, int dma, int drive, unsigned int block, unsigned char *buf, int nsector);int ide_rw_sector(int read, int dma, int drive, int cyl, int head, int sector, unsigned char *buf){	return ide_command(read ? (dma ? WIN_READDMA : WIN_READ) : (dma ? WIN_WRITEDMA : WIN_WRITE), 		drive, 0, cyl, head, sector, 1, buf, SECTOR_SIZE);}#define SECTOR_CHUNKS	8int ide_rw_block(int read, int dma, int drive, int block, unsigned char *buf, int nsector){	ide_info_t *pideinfo = g_ideinfo + drive;	int nsector_transfer;	if (pideinfo->type == IDE_NONE) 		return 1;	while (nsector > 0) {		nsector_transfer = (nsector >= SECTOR_CHUNKS) ? SECTOR_CHUNKS : nsector;		if (pideinfo->lba) {			if (ide_lbs_28_rw(read, dma, drive, block, buf, nsector_transfer))				return 1;		} else {			if (ide_chs_rw(read, dma, drive, block, buf, nsector_transfer))				return 1;		}				block += nsector_transfer;		nsector -= nsector_transfer;		buf += SECTOR_SIZE * nsector_transfer;	}		return 0;}int ide_chs_rw(int read, int dma, int drive, unsigned int block, unsigned char *buf, int nsector){	ide_info_t *pideinfo = g_ideinfo + drive;	unsigned int track, sector, head, cyl;   		track = block / pideinfo->sectors;	sector = block % pideinfo->sectors + 1;	cyl = track / pideinfo->heads;	head = track % pideinfo->heads;	return ide_command(read ? (dma ? WIN_READDMA : WIN_READ) : (dma ? WIN_WRITEDMA : WIN_WRITE), 		drive, 0, cyl, head, sector, nsector, buf, SECTOR_SIZE * nsector);}int ide_lbs_28_rw(int read, int dma, int drive, unsigned int block, unsigned char *buf, int nsector){	int head, cyl, sector;		sector = block & 0xff;	cyl = (block >> 8) & 0xffff;	head = (block >> 24) & 0xff;		return ide_command(read ? (dma ? WIN_READDMA : WIN_READ) : (dma ? WIN_WRITEDMA : WIN_WRITE), 		drive, 0, cyl, head, sector, nsector, buf, SECTOR_SIZE * nsector);}//// partition table translation//#define MSDOS_LABEL_MAGIC1	0x55#define MSDOS_LABEL_MAGIC2	0xAAstruct partition {	unsigned char boot_ind;		/* 0x80 - active */	unsigned char head;			/* starting head */	unsigned char sector;		/* starting sector */	unsigned char cyl;			/* starting cylinder */	unsigned char sys_ind;		/* What partition type */	unsigned char end_head;		/* end head */	unsigned char end_sector;	/* end sector */	unsigned char end_cyl;		/* end cylinder */	unsigned int start_sect;	/* starting sector counting from 0 */	unsigned int nr_sects;		/* nr of sectors in partition */} __attribute__((packed));static int msdos_magic_present(unsigned char *p){	return (p[0] == MSDOS_LABEL_MAGIC1 && p[1] == MSDOS_LABEL_MAGIC2);}int ide_read_partition(int drive, int *sectors, int showlist){	int i, npart = 0;	unsigned char buf[SECTOR_SIZE];	struct partition *part;	int sector_start, cyl_start, sector_end, cyl_end;		if (ide_rw_block(1, 0, drive, 0, buf, 1))		return 0;	if (!msdos_magic_present(buf + 510)) {		printk("Invalid partition table\n");		return 0;	}		part = (struct partition *) (buf + 0x1be);		if (showlist)		printk("# : A TYPE [  CYL / HEAD / SEC -  CYL / HEAD / SEC ] (#SECT)\n");	for (i = 0; i < 4; ++i) {		if (part[i].nr_sects > 0) {			if (sectors)				sectors[i] = part[i].start_sect;			++npart;			if (showlist) {				sector_start = part[i].sector & 0x3f;				cyl_start = ((part[i].sector & 0xc0) << 2) + part[i].cyl;				sector_end = part[i].end_sector & 0x3f;				cyl_end = ((part[i].end_sector & 0xc0) << 2) + part[i].end_cyl;				printk("%d : %c  %02x  [ %4d / %4d / %3d - %4d / %4d / %3d ] (%d, %d = %dMB)\n",					i, part[i].boot_ind & 0x80 ? 'A' : ' ', part[i].sys_ind, 					cyl_start, part[i].head, sector_start,					cyl_end, part[i].end_head, sector_end,					part[i].start_sect, part[i].nr_sects, part[i].nr_sects >> 11);			}		} else {			if (sectors)				sectors[i] = -1;		}	}		return npart;}int ide_rw_block_partition(int read, int dma, int drive, int partition, int block, unsigned char *buf, int nsector){	int npart, part[MAX_PARTITIONS];		if ((npart = ide_read_partition(drive, part, 0)) < 0)		return 1;	if (partition < 0 || partition >= npart || part[partition] < 0)		return 2;		if (dma)		return 1; // return ide_rw_dma_block(read, drive, part[partition] + block, buf, nsector);	else		return ide_rw_block(read, 0, drive, part[partition] + block, buf, nsector);}//// kernel image or filesystem in IDE device//int ide_probe_image(int drive, int *ppart, void *pinfo) {	int i, npart, part[MAX_PARTITIONS];	int type;		if ((npart = ide_read_partition(drive, part, 0)) < 0)		return IMAGE_TYPE_NONE;	for (i = 0; i < npart; ++i) {		if ((type = ide_check_image(drive, i, pinfo)) != IMAGE_TYPE_NONE) {			*ppart = i;			return type;		}	}	return IMAGE_TYPE_NONE;}int ide_check_image(int drive, int part, void *pinfo) {	image_infoblock_t info;	if (ide_rw_block_partition(1, 0, drive, part, 0, (unsigned char *) &info, 1))		return IMAGE_TYPE_NONE;	if (pinfo)		memcpy(pinfo, &info, sizeof info);	if (strcmp(info.u.signature, IMAGE_SIGNATURE) != 0)		return IMAGE_TYPE_NONE;	if (strcmp(info.u.id, IMAGE_ID_KERNEL) == 0) 		return IMAGE_TYPE_KERNEL;	else if (strcmp(info.u.id, IMAGE_ID_ROMFS) == 0)		return IMAGE_TYPE_ROMFS;	else		return IMAGE_TYPE_NONE;}int ide_read_image(int type, int drive, int part, unsigned char *buf){	image_infoblock_t info;	int foundtype = ide_check_image(drive, part, &info);	if (type != IMAGE_TYPE_NONE && type != foundtype)		return 1;	return (ide_rw_block_partition(1, 0, drive, part, 1, buf, (info.u.len + SECTOR_SIZE - 1) / SECTOR_SIZE)) ? 1 : 0;}int ide_write_image(int type, int drive, int part, unsigned char *buf, int len){	image_infoblock_t info;	memset(&info, 0, sizeof info);		strcpy(info.u.signature, IMAGE_SIGNATURE);	if (type == IMAGE_TYPE_KERNEL)		strcpy(info.u.id, IMAGE_ID_KERNEL);	else if (type == IMAGE_TYPE_ROMFS)		strcpy(info.u.id, IMAGE_ID_ROMFS);	else		return 1;	info.u.major = 1;	info.u.minor = 0;	info.u.len = len;	if (ide_rw_block_partition(0, 0, drive, part, 0, (unsigned char *) &info, 1))		return 1;	return (ide_rw_block_partition(0, 0, drive, part, 1, buf, (info.u.len + SECTOR_SIZE - 1) / SECTOR_SIZE)) ? 1 : 0;}

⌨️ 快捷键说明

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