MCU control IIC protocol 24C512 chip EEPROM modular programming (continuous updates)

Label: Singlechip51 single chip microcomputerEEPROMIIC24c512
1110 people read comment(0) Collection Report
Classification:

Here I will write the STC12C5A60S2 MCU control EEPROM chip AT24C512 procedures to share, I hope you guys give is correct.

(added: the following code only need to modify the.H file containing the words "choice", can achieve the effect of reuse, the data for the T24C512 format, the time required is about 10s or so, to wait)

For the lcd2004 section, please refer toModular programming of 2004A LCD screen controlled by single chip microcomputer"Click to enter


Program only need to pay attention to the Chinese part of the notes

Test procedure:

/*################Start main.c################* /

<reg52.h> #include
<stdlib.h> #include
Common.h "#include"
Lcd2004.h "#include"
At24c512.h "#include"

Main void (void)
{

Lcd2004Init ();

/ / in order to show obvious effect, temporarily amended as the cursor is not displayed
Lcd2004WriteCommand (0x0c);

//AT24C512 chip 0 initialization, and display the first 20 characters (all '^')
At24c512Init (0 '^');
Lcd2004AddressWriteString (LCD2004_ROW0,0, "Init over First!");
For (i=0; i<20; i++)
{
Lcd2004AddressWriteByte (LCD2004_ROW1, I, at24c512RandomAddressReadByte (0, I, NULL);
		
}


1 //AT24C512 chip initialization, and display the first 20 characters (the "#")
At24c512Init (1,'#');
Lcd2004AddressWriteString (LCD2004_ROW2,0, "Init over Second!");
For (i=0; i<20; i++)
{
Lcd2004AddressWriteByte (LCD2004_ROW3, I, at24c512RandomAddressReadByte (1, I, NULL);
		
}


While (1);
	

}


/*################End main.c################* /

 

/*################At24c512.hStart################* /

__AT24C512_H__ #ifndef
__AT24C512_H__ #define

<reg52.h> #include
Common.h "#include"

Sbit at24c512_sclk_bit = P1^1; / * * / according to the choice of hardware
Sbit at24c512_sda_bit = P1^0; / * * / according to the choice of hardware

Number //Device
AT24C512_DEVICE0 #define 0
AT24C512_DEVICE1 #define 1
AT24C512_DEVICE2 #define 2
AT24C512_DEVICE3 #define 3
AT24C512_MIN_DEVICE_NUMBER AT24C512_DEVICE0 #define
AT24C512_MAX_DEVICE_NUMBER AT24C512_DEVICE3 #define


AT24C512_DEVICE_ADDRESS_BASE_VALUE 0xa0 #define

AT24C512_DEVICE_READ 0x01 #define
AT24C512_DEVICE_WRITE #define (0x01 & (~ (0x01<<0))

//page
AT24C512_MIN_PAGE_ADDRESS #define 0
#define AT24C512_MAX_PAGE_ADDRESS 511/*512 pgaes in total.
AT24C512_TOTAL_PAGE #define (AT24C512_MAX_PAGE_ADDRESS-AT24C512_MIN_PAGE_ADDRESS+1)

AT24C512_PAGE_LENGTH #define 128
One of the biggest changes / / length of a 128byte page
AT24C512_MAX_CHANGE_LENGTH_ON_BURST_MODE AT24C512_PAGE_LENGTH #define

Address //internal
AT24C512_MIN_INTERNAL_BYTE_ADDRESS #define 0
AT24C512_MAX_INNERNAL_BYTE_ADDRESS 65535/*65536 bytes in total*/ #define
AT24C512_TOTAL_BYTE #define (AT24C512_MAX_INNERNAL_BYTE_ADDRESS-AT24C512_MIN_INTERNAL_BYTE_ADDRESS+1)


//error
#define AT24C512_DEVICE_NUMBER_OVERFLOW -1 / * * / number overflow
#define AT24C512_INTERNAL_PAGE_ADDRESS_OVERFLOW -2 / * * / overflow page address


Device / bus initialization data formatting.
SB8 at24c512Init extern (deviceNumber UB8, dataCode UB8);

Address / / write byte data
SB8 at24c512AddressWriteByte extern (deviceNumber UB8, deviceInternalAddress UW16,
DataCode UB8);

Write page address / data
SB8 at24c512AddressWriteBurst extern (deviceNumber UB8,
PageNumber UW16,
UB8 *table const);

/ / current address read byte data
UB8 at24c512CurrentAddressReadByte extern (deviceNumber UB8, *errorFlag SB8);

Then the address / / read byte data
UB8 at24c512RandomAddressReadByte extern (deviceNumber UB8,
DeviceInternalAddress SB8, *errorFlag UW16);
/ / read sequence
SB8 at24c512SequentialRead extern (deviceNumber UB8,
DeviceInternalAddress UW16,
Table[] UB8, length UB8);


/ / internal data format
SB8 at24c512AllDataSetup extern (deviceNumber UB8, dataCode UB8);



/*__AT24C512_H__*/ #endif


 

/*################At24c512.hEnd################* /

 

/*################Start at24c512.c################* /

/***************************************************************************
Module: at24c512.c

Purpose: of AT24C512 module. Implementation

Version: 0.01 12:00 2014/02/03 (OK)

Complier:Keil 8051 complier V9.01 C

MCU: STC12C5A60S2


Author: Yangrui

Email: yangrui90s@163.com


Modification:
Desolate
08:12 2014/02/28
Reason:
1 delete is similar to
XXX (.., deviceInternalAddress UW16,..)
{
If (deviceInternalAddress < AT24C512_MIN_INTERNAL_BYTE_ADDRESS|| \
DeviceInternalAddress > AT24C512_MAX_INNERNAL_BYTE_ADDRESS >
{
-2 return;
}
}
Such code. The original intent of the code is to be called by the user when the input is more than AT24C512.
Address length 65536 (range 0~65535), but this is because the UW16 is the type of the
Short int unsigned type, so here's the judge is wrong, there is no sense, because the implicit
One type of conversion, simply to say, is that deviceInternalAddress will never be more than 65535,
For example, when the user calls deviceInternalAddress is 65537, because the data length overflow unsigned
The length of the int short type, so it will automatically intercept for (65537-65536) =1 (65536 start overflow).
So there is no work, can be deleted. This belongs to the category of C language.
Desolate

Desolate
20:30 2014/02/25
Reason:
1 modified at24c512AddressWriteBurst (...)
For (i=0; i<AT24C512_MAX_CHANGE_LENGTH; i++)
{
....
}

by
			
ChangeNumber = (strlen (table) > AT24C512_MAX_CHANGE_LENGTH)?
AT24C512_MAX_CHANGE_LENGTH: strlen (table);
	
For (i=0; i<changeNumber; i++)
{
...
}

Because the previous algorithm, the need to complete a page of the data, and sometimes may
Only need to write a few byte of the data, this time using the first algorithm, will be from
Table started the address after the 128 byte write AT24C512 central, so that it may be
Lead to an accident.

For the sake of safety, instead of second algorithms,


Desolate

Desolate
20:30 2014/02/25
Reason:
Function at24c02SequentialRead 1.Add (...)

Desolate

Desolate
23:44 2014/02/24
Reason:
1 modified at24c512AllDataSetup SB8 (deviceNumber UB8, dataCode UB8) core operation
I UW16;
For (i=0; AT24C512_MAX_INNERNAL_BYTE_ADDRESS i<=; i++)
{
At24c512AddressWriteByte (deviceNumber, I, dataCode);
}
			
For:
			
UB8 i;
Table[8] UB8;
For (i=0; i< 8; i++)
{
Table[i] = dataCode;
}

For (i=0; AT24C512_MAX_PAGE i<=; i++)
{
At24c512AddressWriteBurst (deviceNumber, I, table);
}

Use page write operations instead of byte write operations to the AT24C512 data format, faster,
Higher efficiency.
		
Desolate



***************************************************************************/

<reg52.h> #include
<string.h> #include
<intrins.h> #include
<stdlib.h> #include
Common.h "#include"
At24c512.h "#include"


/******************************************************
Function: delay10msForAt24c512
Input: N/A
Output: N/A
Return: N/A
Description: N/A
Note: internal data operation time for a read / write operation after AT24C512,
This period of time, is not to be able to operate on the AT24C512, so the
Miss this time with delay. Max 10ms (datasheet)
Frequency is 11.0592MHZ. crystal
******************************************************/
Void delay10msForAt24c512 static (void)
{
Char I unsigned, j;

_nop_ ();
_nop_ ();
I = 108;
J = 144;
Do
{
While (--j);
} while (--i);
}


/******************************************************
Function: at24c512StartSignal
Input: N/A
Output: N/A
Return: N/A
Description: start signal AT24C512
Note: N/A
******************************************************/
Void at24c512StartSignal static (void)
{
At24c512_sda_bit = HIGH_LEVEL;
//_nop_ ();
At24c512_sclk_bit = HIGH_LEVEL;
//_nop_ ();
At24c512_sda_bit = LOW_LEVEL;
//_nop_ ();
}

/******************************************************
Function: at24c512StopSignal
Input: N/A
Output: N/A
Return: N/A
Description: stop signal AT24C512
Note: N/A
******************************************************/
Void at24c512StopSignal static (void)
{
At24c512_sda_bit = LOW_LEVEL;
//_nop_ ();
At24c512_sclk_bit = HIGH_LEVEL;
//_nop_ ();
At24c512_sda_bit = HIGH_LEVEL;

/*AT24C512 self timed write cycle (5ms max).
Delay10msForAt24c512 ();
}

/******************************************************
Function: at24c512WriteByte
Input: data which is ready to write the to AT24C512
Output: N/A
Return: N/A
Description: N/A
Note: N/A
******************************************************/
Void at24c512WriteByte static (dataCode UB8)
{
I UB8;
Temp UB8 = dataCode;

For (i=0; i<8; i++)
{
At24c512_sclk_bit = LOW_LEVEL;
//_nop_ ();

/ / method
At24c512_sda_bit = (bit) (temp & (0x80>>i));

Two / / method
//temp <<= 1;
//at24c512_sda_bit = CY;

//_nop_ ();
At24c512_sclk_bit = HIGH_LEVEL;
//_nop_ ();
}
}

/******************************************************
Function: at24c512ReadByte
Input: N/A
Output: N/A
Return: byte-data which read from AT24C512 the
Description: N/A
Note: N/A
******************************************************/
UB8 at24c512ReadByte static (void)
{
I UB8;
DataCode UB8 = 0x00;

//Ready
On SDA pin /*Data may change during SCL low timer period*/
At24c512_sclk_bit = LOW_LEVEL;
//_nop_ ();
At24c512_sda_bit = HIGH_LEVEL;
//_nop_ ();

For (i=0; i<8; i++)
{
At24c512_sclk_bit = HIGH_LEVEL;
//_nop_ ();
DataCode<<= 1;
DataCode at24c512_sda_bit |=;
//_nop_ ();
At24c512_sclk_bit = LOW_LEVEL;
//_nop_ ();
}


DataCode return;
}

/******************************************************
Function: at24c512Acknowledge
Input: N/A
Output: N/A
Return: N/A
Description: AT24C512 receive a data from MCU When, write the data AT24C512
Internal address after, completed write AT24C512, send a zero to
MCU then, MCU can input data into to at24c512.
(the internally Once timed write cycle has started and
EEPROM inputs the are disabled until write finished.
Note: N/A
******************************************************/
Void at24c512Acknowledge static (void)
{
I=0 UB8;

At24c512_sclk_bit = LOW_LEVEL;
//_nop_ ();

At24c512_sclk_bit = HIGH_LEVEL;
//_nop_ ();

	
(while (at24c512_sda_bit) and (i<250))
{
I++; / / temporarily, see the specific debugging
}
At24c512_sclk_bit = LOW_LEVEL;
}

/******************************************************
Function: at24c512AddressWriteByte
Input: device number, internal address, data
Output: N/A
Return: 0 (OK)
-1 (device number overflow AT24C512)
-2 (device internal byte address overflow AT24C512)
Description: N/A
Note: N/A
******************************************************/
At24c512AddressWriteByte SB8 (deviceNumber UB8, deviceInternalAddress UW16,
DataCode UB8)
{
If (AT24C512_MIN_DEVICE_NUMBER|| < deviceNumber
DeviceNumber > AT24C512_MAX_DEVICE_NUMBER >
{
AT24C512_DEVICE_NUMBER_OVERFLOW return;
}

At24c512StartSignal ();
At24c512WriteByte (AT24C512_DEVICE_ADDRESS_BASE_VALUE.
(deviceNumber<<1) of the
AT24C512_DEVICE_WRITE);
At24c512Acknowledge ();

At24c512WriteByte ((deviceInternalAddress>>8) & 0xff); /*MSB*/
At24c512Acknowledge ();

0xff (deviceInternalAddress & at24c512WriteByte); /*LSB*/
At24c512Acknowledge ();

At24c512WriteByte (dataCode);
At24c512Acknowledge ();

At24c512StopSignal ();

Return 0;
}

/******************************************************
Function: at24c512AddressWriteBurst
Input: device number, page address, data pointer
Output: N/A
Return: 0 (Ok)
-1 (device number overflow AT24C512)
-3 (device internal page address overflow AT24C512)
Description: N/A
Note: N/A
******************************************************/
At24c512AddressWriteBurst SB8 (deviceNumber UB8, deviceInternalAddress UW16, UB8 *table const)
{
UB8 i;
ChangeLength UW16;

If (deviceNumber < AT24C512_MIN_DEVICE_NUMBER|| \
DeviceNumber > AT24C512_MAX_DEVICE_NUMBER >
{
AT24C512_DEVICE_NUMBER_OVERFLOW return;
}
At24c512StartSignal ();

At24c512WriteByte (AT24C512_DEVICE_ADDRESS_BASE_VALUE.
(deviceNumber<<1) of the
AT24C512_DEVICE_WRITE);
At24c512Acknowledge ();



At24c512WriteByte ((deviceInternalAddress) >>8 () & 0xff);
At24c512Acknowledge ();

At24c512WriteByte ((deviceInternalAddress) & 0xff);
At24c512Acknowledge ();
	
ChangeLength = (strlen (table) > AT24C512_MAX_CHANGE_LENGTH_ON_BURST_MODE)?
AT24C512_MAX_CHANGE_LENGTH_ON_BURST_MODE:strlen (table);
	
For (i=0; i<changeLength; i++)
{
At24c512WriteByte (*table);
At24c512Acknowledge ();
Table++;
}

At24c512StopSignal ();

Return 0;
}

/******************************************************
Function: at24c512AllDataSetup
Input: device number, formatted data
Output: N/A
Return: 0 (OK)
-1 (device number overflow AT24C512)
Description: N/A
Note: pay attention to page write operation "over Roll"
******************************************************/
At24c512AllDataSetup SB8 (deviceNumber UB8, dataCode UB8)
{
I UW16;
Table[AT24C512_MAX_CHANGE_LENGTH_ON_BURST_MODE] UB8;

If (deviceNumber < AT24C512_MIN_DEVICE_NUMBER|| \
DeviceNumber > AT24C512_MAX_DEVICE_NUMBER >
{
AT24C512_DEVICE_NUMBER_OVERFLOW return;
}
	
For (i=0; AT24C512_MAX_CHANGE_LENGTH_ON_BURST_MODE i<; i++)
{
Table[i] = dataCode;
}

For (i=0; AT24C512_MAX_PAGE_ADDRESS i<=; i++)
{
At24c512AddressWriteBurst (deviceNumber, I, table);
}
	
	
Return 0;
}

/******************************************************
Function: at24c512Init
Input: device number, formatted content
Output: N/A
Return: 0 (OK)
-1 (device number overflow AT24C512)
Description: AT24C512 internal data format, bus initialization
Note: after the test (combined with LCD screen), the entire initialization process is about 10s or so, the need to wait patiently
******************************************************/
At24c512Init SB8 (deviceNumber UB8, dataCode UB8)
{
If (AT24C512_MIN_DEVICE_NUMBER, deviceNumber < ||
DeviceNumber > AT24C512_MAX_DEVICE_NUMBER >
{
AT24C512_DEVICE_NUMBER_OVERFLOW return;
}
	
At24c512AllDataSetup (deviceNumber, dataCode);
	
At24c512_sclk_bit = HIGH_LEVEL;
At24c512_sda_bit = HIGH_LEVEL;

Return 0;
}

/******************************************************
Function: mcuAcknowledge
Input: N/A
Output: N/A
Return: N/A
Description: MCU receive a data word MCU send a zero to at24c512. when
Note: N/A
******************************************************/
Void mcuAcknowledge static (void)
{
At24c512_sclk_bit = LOW_LEVEL;
//_nop_ ();
At24c512_sda_bit = LOW_LEVEL;
//_nop_ ();
At24c512_sclk_bit = HIGH_LEVEL;
}

/******************************************************
Function: at24c512RandomAddressReadByteReady
Input: device number
Device internal address
Output: N/A
Return: N/A
Description: sequence read operation has two kinds of initialization method
1 is the same as the current address read operation preparation
2 the same as the immediately address read operation preparation stage
Here using the method two, so here is the package.
Respectively in at24c512RandomAddressReadByte (...)
And at24c512SequentialRead (...) in the call.
Note: N/A
******************************************************/
Void at24c512RandomAddressReadByteReady static (deviceNumber UB8,
DeviceInternalAddress UW16)
{
At24c512WriteByte (AT24C512_DEVICE_ADDRESS_BASE_VALUE.
(deviceNumber < 1)
AT24C512_DEVICE_WRITE);
At24c512Acknowledge ();
	

At24c512WriteByte ((deviceInternalAddress>>8) & 0xff);
At24c512Acknowledge ();

At24c512WriteByte (deviceInternalAddress & 0xff);
At24c512Acknowledge ();

At24c512StartSignal ();

At24c512WriteByte (AT24C512_DEVICE_ADDRESS_BASE_VALUE.
(deviceNumber < 1)
AT24C512_DEVICE_READ);
At24c512Acknowledge ();
}

/******************************************************
Function: at24c512RandomAddressReadByte
Input: device number, internal address
Output: N/A
Return: data from AT24C512 internal random adress. the
Description: N/A
Note: here for the user to call the wrong reserved interface *errorFlag, in the specific use, if the user
Determine their calls into the parameter deviceNumber to meet the 0~3, you can use the NULL, that is, the format:
At24c512RandomAddressReadByte (..,.., NULL);
******************************************************/
At24c512RandomAddressReadByte UB8 (deviceNumber UB8, deviceInternalAddress UW16, *errorFlag SB8)
{
DataCode UB8;
	
If (deviceNumber < AT24C512_MIN_DEVICE_NUMBER|| \
DeviceNumber > AT24C512_MAX_DEVICE_NUMBER >
{
		
*errorFlag = AT24C512_DEVICE_NUMBER_OVERFLOW;
//exit (0);
Return 0;
/ * here is not perfect, the judge is mainly to determine the mechanism for users to stay, because in a bus
The maximum number of allowed to be able to connect to the AT24C512 at the same time is 4, if more than, it can not be identified, the operation is also on the
Go wrong * /
}

At24c512StartSignal ();

At24c512RandomAddressReadByteReady (deviceNumber, deviceInternalAddress);
	
DataCode = at24c512ReadByte ();
	

At24c512StopSignal ();

DataCode return;
}

/******************************************************
Function: at24c512CurrentAddressReadByte
Input: device number
Output: N/A
Return: data from AT24C512 internal current address. the
Description: N/A
Note: here for the user to call the wrong reserved interface *errorFlag, in the specific use, if the user
Determine their calls into the parameter deviceNumber to meet the 0~3, you can use the NULL, that is, the format:
At24c512CurrentAddressReadByte (.., NULL);
******************************************************/
At24c512CurrentAddressReadByte UB8 (deviceNumber UB8, *errorFlag SB8)
{
DataCode UB8;
If (deviceNumber < AT24C512_MIN_DEVICE_NUMBER|| \
DeviceNumber > AT24C512_MAX_DEVICE_NUMBER >
{
*errorFlag = AT24C512_DEVICE_NUMBER_OVERFLOW;
//exit (0);
Return 0;
/ * here is not perfect, the judge is mainly to determine the mechanism for users to stay, because in a bus
The maximum number of allowed to be able to connect to the AT24C512 at the same time is 4, if more than, it can not be identified, the operation is also on the
Go wrong * /
}

At24c512StartSignal ();
	
/*------------------ preparation stage --------------------------*/

At24c512WriteByte (AT24C512_DEVICE_ADDRESS_BASE_VALUE.
(deviceNumber<<1.
AT24C512_DEVICE_READ);
At24c512Acknowledge ();
/*----------------------------------------------------*/
	
DataCode = at24c512ReadByte ();
	

At24c512StopSignal ();

DataCode return;
}

/******************************************************
Function: at24c512SequentialRead
Input: device number;
Device internal address (start address);
Data pointer
Read length
			 
Output: data pointer
Return: 0 (OK)
Description: sequence read
Note:
1 the last data do not have to host a reply, the other data transmission, the need to host the response.

2 sequence address read operation has two kinds of initialization method:
(1) the same as the current address read operation preparation stage
(2) the same as the immediately address read operation preparation stage

Second methods are adopted here, the first method is not flexible enough,
******************************************************/
At24c512SequentialRead SB8 (deviceNumber UB8, deviceInternalAddress UW16,
*table UB8, length UB8)
{
DataCode UB8;
	
If (deviceNumber < AT24C512_MIN_DEVICE_NUMBER|| \
DeviceNumber > AT24C512_MAX_DEVICE_NUMBER >
{
AT24C512_DEVICE_NUMBER_OVERFLOW return;
}

At24c512StartSignal ();

At24c512RandomAddressReadByteReady (deviceNumber, deviceInternalAddress);
	
While (--length)
{
*table = at24c512ReadByte ();
McuAcknowledge ();
Table++;
}
*table = at24c512ReadByte ();

At24c512StopSignal ();

DataCode return;
}


 

/*################End at24c512.c################* /

 

 

Supplement: common.h

__COMMON_H__ #ifndef
__COMMON_H__ #define

Unsigned char UB8 typedef;
Unsigned short int UW16 typedef;
Unsigned long UL32 typedef;

Char SB8 typedef;
Short int SW16 typedef;
Long SL32 typedef;
	
HIGH_LEVEL #define 1
LOW_LEVEL #define 0


/*__COMMON_H__*/ #endif



top
Three
step on
Zero

Reference knowledge base

Guess you're looking for
View comments
* the above user comments only represent their personal views, does not represent the views or position of the CSDN website
    personal data
    • Visit:42885 times
    • Integral:Eight hundred and four
    • Grade:
    • Rank:Thousands of miles away
    • Original:35
    • Reproduced:0
    • Translation:0
    • Comments:25
    Latest comments