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

📄 main.c

📁 51读写硬盘的程序模块,编译完全通过,移植方面,实用.
💻 C
字号:
#include <reg51.h>
#include <absacc.h>
#define uchar unsigned char
#define uint  unsigned int
#define KEYPORT P1

#define LCDCOM  XBYTE[0x0008] //LCD命令寄存器
#define LCDDATA XBYTE[0x0009] //LCD数据寄存器

#define CDPA  XBYTE[0x0004]   //8255 PORT A, harddisk D0-D7
#define CDPB  XBYTE[0x0005]   //8255 PORT B, harddisk D8-D15
#define CDPC  XBYTE[0x0006]   //8255 PORT C,harddisk address
#define CDCOM XBYTE[0x0007]   //8255 命令寄存器

#define FILE0 0x00            //硬盘数据寄存器          
#define FILE1 0x01            //错误/特征寄存器
#define FILE2 0x02            //扇区数寄存器
#define FILE3 0x03            //扇区号寄存器
#define FILE4 0x04            //柱面号寄存器L
#define FILE5 0x05            //柱面号寄存器H
#define FILE6 0x06            //驱动器/磁头寄存器
#define FILE7 0x07            //状态/命令寄存器

static uchar code LCD1[16]= "TOPLOW DESIGN   ";
static uchar code LCD2[16]= "Copyright(C)2004";
static uchar code ERROR[16]="ERROR           ";
static uchar code PASS[16]= "PASS            ";

uchar buffer0,buffer1;
uchar buffer[16];
uchar STATUS;
      ///////////////////位设置///////////////////////////
sbit BFLAG=ACC^7;
sbit BSY=ACC^7;
sbit DRDY=ACC^6;
sbit DRQ=ACC^3;
sbit ERR=ACC^0;
sbit RESET=P3^5;
sbit READ=P3^0;
sbit WRITE=P3^1;
sbit ILT=ACC^0;
sbit INTRQ=P3^3;
/************************************************************
* D7   D6   D5   D4   D3   D2    D1   D0                    *
BSY  DRDY  DWF  DSC DRQ  CORR  IDX   ERR                   *
BSY:驱动器忙;                                             *
DRDY:驱动器准备好;                                        *
DWF:驱动器写失败;                                         *
DSC:寻道结束;                                              *
DRQ:请求服务,驱动器希望通过数据寄存器与CPU交换一字节数据;*
CORR:当可以纠正的读错误发生时,该位置1,数据传输将继续进行 *
IDX:收到综引信号;                                         *
ERR:命令执行出错。                                         *
*************************************************************/

/*******************************************************
*函数名称:void delay(uint time)                        *
*函数用途:延迟函数                                     *
********************************************************/    
void delay(uint time)
{
	uint i,j;
	for(i=0;i<time;i++)
	for(j=0;j<255;j++);
} 

/*******************************************************
*函数名称:void putch(unsigned char ch)                 *
*函数用途:串口发送程序                                 *
********************************************************/
void putch(unsigned char ch) 
{
	SBUF=ch;
	TI=0;
	while(!TI);
}

/*******************************************************
*函数名称:unsigned char getch(void)                    *
*函数用途:串口接收程序                                 *
********************************************************/
unsigned char getch(void) 
{
	uchar temp; 
	while(!RI);
	temp=SBUF;   
	RI=0;
	return(temp);
} 


/*******************************************************
*函数名称:void wait(void)                              *
*函数用途:LCD忙等待                                    *
********************************************************/  
void wait(void)
{
	do{ACC=LCDCOM;}
	while(BFLAG==1);
}

/*******************************************************
*函数名称:void IniLcd(void)                            *
*函数用途:LCD初始化函数                                *
********************************************************/  
void IniLcd(void)
{
	LCDCOM=0x38;
	wait();
	LCDCOM=0x08;
	wait();
	LCDCOM=0x01;
	wait();
	LCDCOM=0x06;
	wait();
	LCDCOM=0x0c;
	wait();
}  
/***********************************************************************
*函数名称:void LcdDis(uchar FL,uchar Lcd1[16],uchar SL,uchar Lcd2[16]) *
*函数用途:液晶显示函数                                                 *
************************************************************************/ 
void LcdDis(uchar FL,uchar Lcd1[16],uchar SL,uchar Lcd2[16])
{
	uchar k;

	LCDCOM=FL|0x80;
	wait();
	for(k=0;k<16;k++){
		LCDDATA=Lcd1[k];
		wait();
		}
	LCDCOM=SL|0xc0;
	wait();
	for(k=0;k<16;k++){
		LCDDATA=Lcd2[k];
		wait();
		}
}

/*******************************************************
*函数名称:void ReadReg(uchar ADD)                      *
*函数用途:读硬盘非数据寄存器内容,并将结果返回         *
********************************************************/
void ReadReg(uchar ADD)
{
	CDCOM=0x92;
	CDPC=ADD;
	READ=0;
	ACC=CDPA;
	STATUS=ACC;
	READ=1;
}

/*******************************************************
*函数名称:void WriteReg(uchar ADD,uchar DATA)          *
*函数用途:写硬盘非数据寄存器内容                       *
********************************************************/
void WriteReg(uchar ADD,uchar DATA)
{
	CDCOM=0x80;
	CDPC=ADD;
	WRITE=0;
	CDPA=DATA;
	WRITE=1;
}

/*******************************************************
*函数名称:void ReadData()                              *
*函数用途:读硬盘数据寄存器内容                         *
********************************************************/
void ReadData()
{
	CDCOM=0x92;
	CDPC=FILE0;
	READ=0;
	buffer0=CDPA;
	buffer1=CDPB;
	READ=1;
}

/*******************************************************
*函数名称:void WriteData(uchar Data0,uchar Data1)      *
*函数用途:写硬盘数据寄存器内容                         *
********************************************************/
void WriteData(uchar Data0,uchar Data1)
{
	CDCOM=0x80;
	CDPC=FILE0;
	WRITE=0;
	CDPA=Data0;
	CDPB=Data1;
	WRITE=1;
}

/*********************************************************
*函数名称:WriteCHS(uint cylinder,uchar head,uchar sector)*
*函数用途:写CHS信息(地址信息)                            *
**********************************************************/
WriteCHS(uchar head,uint cylinder,uchar sector)
{
	do{ReadReg(FILE7);}while(BSY);
	WriteReg(FILE6,0xe0&head);
	WriteReg(FILE5,cylinder>>8);    //high 2-bit cylinder
	WriteReg(FILE4,cylinder&0x00ff);//low 8-bit cylinder
	WriteReg(FILE3,sector); //start sector
	WriteReg(FILE2,0x01);   //sector counter
}
/*********************************************************
*函数名称:WriteCommand(command)                          *
*函数用途:写命令                                         *
**********************************************************/
WriteCommand(command)
{
	do{ReadReg(FILE7);}while(BSY);
	WriteReg(FILE7,command);
}
/**********************************************************
*函数名称:GetData()                                       *
*用途:将硬盘的返回数据读入BUFFER数组                      *
***********************************************************/
void GetData()
{
	uint i=512;
	do{ReadReg(FILE7);}while(BSY|!DRQ);
	if(ERR){
		LcdDis(0,ERROR,0,LCD2);
		putch(255);
		}
	while(i){ReadData();putch(buffer0);putch(buffer1);i-=2;}
}

/**********************************************************
*函数名称:void IniHard(void)                              *
*用途:初始化硬盘                                          *
***********************************************************/
void IniHard(void)
{
	do{
		WriteReg(FILE6,0xa0);
		ReadReg(FILE7); 
		}while(!DRDY|BSY);
	WriteReg(FILE6,0x20);
	WriteReg(FILE2,64);
	WriteReg(FILE7,0x91);
	do{ReadReg(FILE7);}while(BSY);
	WriteReg(FILE7,0x10);
	do{ReadReg(FILE7);}while(BSY); 
}  
/**********************************************************
*函数名称:void DriveID(void)                              *
*用途:读硬盘ID                                            *
***********************************************************/ 
void DriveID(void) 
{
	uint i=512;
	do{ReadReg(FILE7);}while(BSY);
	WriteReg(FILE7,0xec);
	do{ReadReg(FILE7);}while(BSY|!DRQ);
	while(i){ReadData();putch(buffer0);putch(buffer1);i-=2;}
}

/*******************************************************
*函数名称:主函数                                       *
*函数用途:                                             *
********************************************************/
void HardDiskControl(void)
{
	uint i;
	SCON=0x50;      /*方式1,串行口接收允许位*/
	TMOD=0x21;      /*定时器1用于串行通信波特率发生,定时器0用于REMOTE接收判断0,1时间*/
	PCON=0x80;      /*串行波特率加倍位*/
	TCON=0x51;      /*启动计数器0,计数器1*/
	EA=1;           /*中断允许*/
	EX0=0;          /*外部中断0不允许*/
	TH1=0xD0;
	TL1=0xD0;
	TI=1;

	RESET=0;
	delay(50);
	RESET=1;
	delay(255);

	IniHard();
      //DriveID();
	WriteCHS(0,0,0);
	WriteCommand(0x20);
	GetData();

	IniLcd();
	LcdDis(0,LCD1,0,LCD2);

	for(i=0;i<512;i++){
		putch(i);
		delay(255);
		}
	while(1);
}

void main(void){
	HardDiskControl();
	DriveID();
	WriteData(0X00,0X01);
	getch();
}

⌨️ 快捷键说明

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