Continue to Site

Welcome to our site!

Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

  • Welcome to our site! Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

Why i do not drive the 93C46?

Status
Not open for further replies.

jason540

New Member
i try to write a program to drive 93C46(SPI EEROM), but it do not read data(may be do not write).
i want to know which part do not work.

Thank very much


Main Program

#include <p18f4620.h>
#include <delays.h>

#pragma config OSC = HS // use High Speed crystal (20MHz) - not using PLL right now
#pragma config PWRT = ON //Power up timer is ON
#pragma config WDT = OFF // Watchdog timer is OFF
#pragma config LVP = ON // Low Voltage Programming ON
#pragma config BOREN = OFF //Brown out reset is OFF
#pragma config DEBUG = ON //Debug is ON


#define CS LATDbits.LATD0 //Chip Select Latch = RD4
#define SCL LATCbits.LATC6 //Clock Latch = RC1
#define SDO LATCbits.LATC5 //Data Out Latch = RC5
#define SDI PORTCbits.RC4 //Data In Port = RC4
#define ORG LATCbits.LATC7


#define CST TRISDbits.TRISD0 //Chip Select TRIS=TRISD4
#define SCLT TRISCbits.TRISC6 //Clock TRIS=TRISC1
#define SDOT TRISCbits.TRISC5 //Data Out TRIS =TRISC5
#define SDIT TRISCbits.TRISC4 //Data In TRIS = TRISC2
#define ORGT TRISCbits.TRISC7

unsigned char val_1=0;

void main(void);
void initSPI(void);
unsigned char ReadSPI(unsigned char address);
void WriteSPI(unsigned char address, unsigned char data);
unsigned char SPI_RByte(void);
void SPI_WByte(unsigned char data);
void SPI_address(unsigned char address);



void main (void)
{
// Make bit 7 the Port D (LED) output bit.
TRISDbits.TRISD7 = 0;

//SPI init
initSPI();

while (1) {
TRISDbits.TRISD7 = 0;
TRISDbits.TRISD6 = 0;

val_1=0; // reset value
WriteSPI(0x05,0xAA); //Set up MMA7455L operation mode by writing to hex addr 16, hex value 05 (2g, 4 wires)
val_1 = ReadSPI(0x05); // read value back from register and if expected value turn ON the LED
if(val_1==0xAA){LATDbits.LATD7 = 1;Delay10KTCYx(300);} // turn LED ON
else if(val_1!=0xAA) {LATDbits.LATD7 = 0;} // turn LED OFF

};

}// End of the main program




void initSPI(void){
SCLT = 0; //Set the SCL (CLOCK) pin to output,
SDOT = 0; //Set the SDO (DATA OUT) pin to output,
SDIT = 1; //Set the SDI (DATA IN) pin to input,
CST = 0; //Set the CS (Chip Select) pin to output,
ORGT = 0; //Set the ORG pin to output

CS = 0; //Set Chip Select Low
SDO = 0; //Set Serial Data Out Low
SCL = 0; //Set Serial Clock Low
ORG = 0;
}


void SPI_WByte(unsigned char data)
{

char x;
for(x=0;x<8;x++){ //Loop 8 bits
SCL = 0; //Clock Low
SDO = 0; //Data Low

if((data & 0x80) != 0) //Clear entire byte except bit 7 and check if byte is greater than 0
SDO = 1; //Set the Data Out to HIGH
Delay10TCY(); //Delay 5uS
SCL = 1; //Clock High

Delay10TCY(); //Delay 5uS
data <<= 1; //Shift data bit out to the right
}
}

void SPI_address(unsigned char address)
{
char x;
for(x=0;x<10;x++){ //Loop 10 bits 3-bit instruction, 7-bit address
SCL = 0; //Clock Low
SDO = 0; //Data Low

if((address & 0x200) != 0) //Clear entire byte except bit 9 and check if byte is greater than 0
SDO = 1; //Set the Data Out to HIGH
Delay10TCY(); //Delay 5uS
SCL = 1; //Clock High

Delay10TCY(); //Delay 5uS
address <<= 1; //Shift data bit out to the right
}
}

unsigned char SPI_RByte(void){
char x,data;
for(x=0;x<8;x++){ //Loop 8 bits 8-bit data
SCL = 0; //Clock Low

Delay10TCY(); //5uS delay
data <<= 1; //Shift 1 bit to the left
data &= 0xFE; //Clear BIT 0 from byte without touching the rest
if(SDI) //if the Serial Data In is HIGH do below if not then leave it 0
data |= 1; //OR in a 1 into out byte
Delay10TCY(); //delay 5uS
SCL = 1; //Clock High

}
return data; //return our data
}

void WriteSPI(unsigned char address, unsigned char data){

SCL = 1; //Clock High
CS = 0; //Chip Select Low = SPI Enable
address = address | 0x280; //b101xxxxxxx is write instruction
SPI_address(0b1001100000);
SPI_address(address); //Write our address
SPI_WByte(data); //Write our data
CS = 1; //Chip Select High

}

unsigned char ReadSPI(unsigned char address){
unsigned char tmp;
SCL = 1; //Clock High
CS = 0; //Chip Select Low
address = address | 0x300; //110xxxxxxx is read instruction
SPI_address(address); //Write our address to read from
tmp = SPI_RByte(); //Get the byte from the device
CS = 1; //Chip Select High
return tmp; //Return tmp
}
 
Have you allowed 6ms for the EEPROM to program? I cannot see this in your code. Once you write data to the memory, you have to implement a wait delay (i normally use 10ms) for hte internal program cycle to complete.

If I had one 'stock' answer to solve most E2 read/write problems, this would be it

let me know

Thanks
 
I don't see where you are sending an EWEN command.

Also, why aren't you using the hardware SPI unit?

Mike.
 
it is allow >6ms for the EEPROM to program?



i sending an EWEN instruction at void WriteSPI

void WriteSPI(unsigned char address, unsigned char data){

SCL = 1; //Clock High
CS = 0; //Chip Select Low = SPI Enable
address = address | 0x280; //0b101xxxxxxx is write instruction
SPI_address(0b1001100000); //0b10011xxxxx is a EWEN instruction
SPI_address(address); //Write our address
SPI_WByte(data); //Write our data
CS = 1; //Chip Select High
}
 
Status
Not open for further replies.

Latest threads

Back
Top