25045操作標準子程序
# include
# include
# define uchar unsigned char
# define uint unsigned int
?sbit SO=P1^1;/*25045輸出*/
?sbit SI=P1^2;/*25045輸入*/
?sbit SCK=P1^3;/*25045時鐘*/
?sbit CS=P1^4;/*25045片選*/
?uchar code WREN_INST=0X06;
?/* Write enable latch instruction (WREN)*/
?uchar code WRDI_INST=0X04;
?/* Write disable latch instruction (WRDI)*/
?uchar code WRSR_INST=0X01;
?/* Write status register instruction (WRSR)*/
?uchar code RDSR_INST=0X05;
?/* Read status register instruction (RDSR)*/
?uchar code WRITE_INST=0X02;
?/* Write memory instruction (WRITE)*/
?/*寫入25045的先導字,應當為0000A010,其中的A為寫入25045的高位地址
?將此WRITE_INST和寫入高位地址相或后即為正確的寫先導字*/
?uchar code READ_INST=0X03;
?/* Read memory instruction (READ)*/
?/*讀出25045的先導字,應當為0000A011,其中的A為讀出25045的高位地址
?將此READ_INST和讀出高位地址相或后即為正確的讀先導字*/
?uint code BYTE_ADDR=0X55;
?/* Memory address for byte mode operations*/
?uchar code BYTE_DATA=0X11;
?/*Data byte for byte write operation*/
?uint? code PAGE_ADDR=0X1F;
?/* Memory address for page mode operations*/
?/*頁面寫入的其始地址*/
?uchar code PAGE_DATA1=0X22;
?/* 1st data byte for page write operation*/
?uchar code PAGE_DATA2=0X33;
?/* 2nd data byte for page write operation*/
?uchar code PAGE_DATA3=0X44;
?/* 3rd data byte for page write operation*/
?uchar code STATUS_REG=0X20;
?/* Status register,設置DOG時間設置為200毫秒,無寫保護*/
?/*這是狀態寄存器的值,他的意義在于第5,第4位為WDI1,WDI0代表DOG的時間,00為1.4秒,01為600毫秒,10為200毫秒,00為disabled
?第3位和第2位為BL1,BL0,是寫保護設置位,00為無保護,01為保護180-1FF,10為保護100-1FF,11為保護000-1FF.第1位為WEL,
?當他為1時代表已經"寫使能"設置了,現在可以寫了,只讀位.第0位為WIP,當他為1時代表正在進行寫操作,是只讀*/
?uchar code? MAX_POLL=0x99;
?/* Maximum number of polls*/
?/*最大寫過程時間,確定25045的最大的寫入過程的時間*/
?uchar code INIT_STATE=0x09;
?/* Initialization value for control ports*/
?uint code SLIC=0x30;
?/* Address location of SLIC*/
?void wren_cmd(void);/*寫使能子程序*/
?void wrdi_cmd(void);/*寫使能復位*/
?void wrsr_cmd(void);/*復位時間位和數據保護位寫入狀態寄存器*/
?uchar rdsr_cmd(void);/*讀狀態寄存器*/
?void byte_write(uchar aa,uint dd);/*字節寫入,aa為寫入的數據,dd為寫入的地址*/
?uchar byte_read(uint dd);/*字節讀出,dd為讀出的地址,返回讀出的數據*/
?void page_write(uchar aa1,uchar aa2,uchar aa3,uchar aa4,uint dd);/*頁寫入*/
?void sequ_read(void);/*連續讀出*/
?void rst_wdog(void);/*DOG復位*/
?void outbyt(uchar aa);/*輸出一個字節到25045中,不包括先導字等*/
?uchar inputbyt();/*由25045輸入一個字節,不包括先導字等額外的東西*/
?void wip_poll(void);/*檢查寫入過程是否結束*/
?
?
/*25045操作子程序集*/
/*;*******************************************************
*
;* Name: WREN_CMD
;* Description: Set write enable latch
;* Function: This routine sends the command to enable writes to the EEPROM memory array or
;* status register
;* Calls: outbyt
;* Input: None
;* Outputs: None
;* Register Usage: A
;*****************************************************
*/
/*寫使能子程序*/
void wren_cmd(void)
{
?uchar aa;
?SCK=0;/* Bring SCK low */
?CS=0;/* Bring /CS low */
?aa=WREN_INST;
?outbyt(aa);/* Send WREN instruction */
?SCK=0;/* Bring SCK low */
?CS=1;/* Bring /CS high */
}
/*;***********************************************************
*
;* Name: WRDI_CMD
;* Description: Reset write enable latch
;* Function: This routine sends the command to disable writes to the EEPROM memory array or
;* status register
;* Calls: outbyt
;* Input: None
;* Outputs: None
;* Register Usage: A
;***********************************************************
*/
/*寫使能復位子程序*/
void wrdi_cmd(void)
{
?uchar aa;
?SCK=0;/* Bring SCK low */
?CS=0;/* Bring /CS low */
?aa=WRDI_INST;
?outbyt(aa);/* Send WRDI instruction */
?SCK=0;/* Bring SCK low */
?CS=1;/* Bring /CS high */
}
/*;********************************************************
*
;* Name: WRSR_CMD
;* Description: Write Status Register
;* Function: This routine sends the command to write the WD0, WD1, BP0 and BP0 EEPROM
;* bits in the status register
;* Calls: outbyt, wip_poll
;* Input: None
;* Outputs: None
;* Register Usage: A
;********************************************
*/
/*寫狀態寄存器子程序*/
void wrsr_cmd(void)
{
?uchar aa;
?SCK=0;/* Bring SCK low */
?CS=0;/* Bring /CS low */
?aa=WRSR_INST;
?outbyt(aa) ;/* Send WRSR instruction */
?aa=STATUS_REG;
?outbyt(aa);/* Send status register */
?SCK=0;/* Bring SCK low */
?CS=1;/* Bring /CS high */
?wip_poll();/* Poll for completion of write cycle */
}
/*;*************************************************************
*
;* Name: RDSR_CMD
;* Description: Read Status Register
;* Function: This routine sends the command to read the status register
;* Calls: outbyt, inputbyt
;* Input: None
;* Outputs: A = status registerXicor Application Note AN21
;* Register Usage: A
;*******************************************************
*/
/*讀狀態寄存器,讀出的數據放入到aa中*/
uchar rdsr_cmd (void)
{
?uchar aa;
?SCK=0;
?CS=0;
?aa=RDSR_INST;
?outbyt(aa);
?aa=inputbyt();
?SCK=0;
?CS=1;
?return aa;
}
/*;*******************************************************
*
;* Name: BYTE_WRITE
;* Description: Single Byte Write
;* Function: This routine sends the command to write a single byte to the EEPROM memory
array
;* Calls: outbyt, wip_poll
;* Input: None
;* Outputs: None
;* Register Usage: A, B
;**********************************************************
*/
/*字節寫入,aa為寫入的數據,dd為寫入的地址,對于25045而言為000-1FF*/
void byte_write(aa,dd)
uchar aa;
uint dd;
{
?SCK=0;
?CS=0;
?outbyt((((uchar)(dd-0XFF))<<3)|WRITE_INST);/* Send WRITE instruction including MSB of address */
?/*將高位地址左移3位與寫入先導字相或,得到正確的先導字寫入25045*/
?outbyt((uchar)(dd));
?/*輸出低位地址到25045*/
?outbyt(aa);
?/*寫入數據到25045的對應單元*/
?SCK=0;
?CS=1;
?wip_poll();
?/*檢測是否寫完*/
}
/*;********************************************************
*
;* Name: BYTE_READ
;* Description: Single Byte Read
;* Function: This routine sends the command to read a single byte from the EEPROM memory
array
;* Calls: outbyt, inputbyt
;* Input: None
;* Outputs: A = read byte
;* Register Usage: A, BXicor Application Note AN21
;********************************************************
*/
/*字節讀出,其中dd為讀出的地址,返回的值為讀出的數據*/
uchar byte_read(dd)
uint dd;
{
?uchar cc;
?SCK=0;
?CS=0;
?outbyt((((uchar)(dd-0XFF))<<3)|READ_INST);/* Send READ_INST instruction including MSB of address */
?/*將高位地址左移3位與讀出先導字相或,得到正確的先導字寫入25045*/
?outbyt((uchar)(dd));
?/*輸出低位地址到25045*/
?cc=inputbyt();/*得到讀出的數據*/
?SCK=0;
?CS=1;
?return cc;
}
/*;**********************************************
*
;* Name: PAGE_WRITE
;* Description: Page Write
;* Function: This routine sends the command to write three consecutive bytes to the EEPROM
;* memory array using page mode
;* Calls: outbyt, wip_poll
;* Input: None
;* Outputs: None
;* Register Usage: A, B
;*****************************************************
*/
/*頁面寫入,其中aa1,aa2,aa3,aa4為需要寫入的4個數據(最大也就只能一次寫入4個字,dd為寫入的首地址*/
void page_write(aa1,aa2,aa3,aa4,dd)
uchar aa1,aa2,aa3,aa4;
uint dd;
{
?SCK=0;
?CS=0;
?outbyt((((uchar)(dd-0XFF))<<3)|WRITE_INST);/* Send WRITE instruction including MSB of address */
?/*將高位地址左移3位與寫入先導字相或,得到正確的先導字寫入25045*/
?outbyt((uchar)(dd));
?/*寫入低位地址到25045*/
?outbyt(aa1);
?/*寫入數據1到25045的對應單元*/
?outbyt(aa2);
?/*寫入數據2到25045的對應單元*/
?outbyt(aa3);
?/*寫入數據3到25045的對應單元*/
?outbyt(aa4);
?/*寫入數據4到25045的對應單元*/
?SCK=0;
?CS=1;
?wip_poll();
}
/*;********************************************
*
;* Name: SEQU_READ
;* Description: Sequential Read
;* Function: This routine sends the command to read three consecutive bytes from the EEPROM
;* memory array using sequential mode
;* Calls: outbyt, inputbyt
;* Input: None
;* Outputs: A = last byte read
;* Register Usage: A, B
;*********************************************************
*/
/*連續讀出,由于函數的返回值只能為1個,對于連續讀出的數據只能使用指針作為函數的返回值才能做到返回一系列的數組*/
/*sequ_read:*/
unsigned int *page_read(n,dd)
uchar n;/*n是希望讀出的數據的個數,n<=11*/
unsigned int dd;/*dd是讀出數據的首地址*/
{
?uchar i;
?uchar pp[10];
?unsigned int *pt=pp;
?SCK=0;
?CS=0;
?outbyt((((uchar)(dd-0XFF))<<3)|READ_INST);
?for (i=0;i
?? pp[i]=inputbyt();
?}
?return (pt);
}
/*調用的方法如下*/
/*unsigned int *p;*/
/*p=page_read(4,100);*/
/*a=*(p)*/?
/*b=*(p+1)*/
/*c=*(p+2)*/
/*d=*(p+3)*/
/*abcd中存放25045中由100地址開始的4個數據*/
?/* Send WRITE */
/*mov DPTR, #PAGE_ADDR ; Set address of 1st byte to be read
clr sck ; Bring SCK low
clr cs ; Bring /CS low
mov A, #READ_INST
mov B, DPH
mov C, B.0
mov ACC.3, C
lcall outbyt ; Send READ instruction with MSB of address
mov A, DPL
lcall outbyt ; Send low order address byte
lcall inputbyt ; Read 1st data byte
lcall inputbyt ; Read 2nd data byte
lcall inputbyt ; Read 3rd data byte
clr sck ; Bring SCK low
setb cs ; Bring /CS high
ret*/
/*;*******************************************************
*
;* Name: RST_WDOG
;* Description: Reset Watchdog Timer
;* Function: This routine resets the watchdog timer without sending a command
;* Calls: None
;* Input: None
;* Outputs: None
;* Register Usage: None
;***************************************************
*/
/*復位DOG*/
void rst_wdog (void)
{
?CS=0;
?CS=1;
}
/*;******************************************************
*
;* Name: WIP_POLL
;* Description: Write-In-Progress Polling
;* Function: This routine polls for completion of a nonvolatile write cycle by examining the
;* WIP bit of the status register
;* Calls: rdsr_cmdXicor Application Note AN21
;* Input: None
;* Outputs: None
;* Register Usage: R1, A
;**************************************************
*/
/*檢測寫入的過程是否結束*/
void wip_poll(void)
{
?uchar aa;
?uchar idata my_flag;
?for (aa=1;aa>MAX_POLL;aa++)
?{
? my_flag=rdsr_cmd();
? if ((my_flag&&0x01)==0) {aa=MAX_POLL;}/*判斷是否WIP=0,即判斷是否寫入過程已經結束,若結束就跳出,否則繼續等待直到達到最大記數值*/
?}
}
/*;*******************************************************
*
;* Name: OUTBYT
;* Description: Sends byte to EEPROM
;* Function: This routine shifts out a byte, starting with the MSB, to the EEPROM
;* Calls: None
;* Input: A = byte to be sent
;* Outputs: None
;* Register Usage: R0, A
;**********************************************************
*/
/*輸出一個數據到25045,此數據可能為地址,先導字,寫入的數據等*/
void outbyt(aa)
uchar aa;
{
?uchar my_flag1,i;
?for (i=0;i>7;i++)
?{
?? my_flag1=aa;
?? SCK=0;
?? SI=(my_flag1>>i);
?? SCK=1;
?}
?SI=0;/*使SI處于確定的狀態*/
}
/*;***************************************************
*
;* Name: INPUTBYT
;* Description: Recieves byte from EEPROM
;* Function: This routine recieves a byte, MSB first, from the EEPROM
;* Calls: None
;* Input: None
;* Outputs: A = recieved byte
;* Register Usage: R0, A
;*******************************************************
*/
/*得到一個數據,此數據可能為狀態寄存器數據,讀出的單元數據等*/
uchar inputbyt(void)
{
?uchar aa,my_flag;
?char i;
?for (i=7;i<0;i--)
?{
?? SCK=0;
?? my_flag=(uchar)(SO);
?? SCK=1;
?? aa=(aa||(my_flag<?? my_flag=0x00;
?}
?return aa;
}
評論
查看更多