SPI调试笔记

SPI调试笔记

root2011-01-09

实现了通过CPUSPI控制器来读写外部Flash,做一下笔记。

CPULPC2366,内置1SPI控制器,两个SSP控制器。

FlashAT45DB321,通过SPI接口读写,13 MHzMax Clock Frequency

 

CPU设置为SPI masterAT45DB321Slave,读写时钟都是由master发出的,在读AT45DB321的时候通过写CPUSPI数据寄存器来产生读时钟。

 

SPI master初始化代码:

 

void mSPI_Init(void)

{

       U8u8_dummy;

 

       PINSEL0&= ~(3U << 30);

       PINSEL0|= 3U << 30; // P0[15], SCK

       PINSEL1&= ~0xffU;          // P0[16-19],SSEL, MISO, MOSI, WP

       PINSEL1|= 0x3c;

 

       PIN_SET(P0,PIN_AT45_WP | PIN_AT45_CS);

       PIN_DIR(P0,PIN_AT45_WP | PIN_AT45_CS, OUT);

 

       S0SPCCR= 0x52;             // 分频时钟

       S0SPCR= (0 << 2) |           //bitEnable, 8bit

                      (0 << 3) |          // cpha

                   (0 << 4) |          // cpol

                   (1 << 5) |          //mstr = 1, 主模式

                   (0 << 6) |              // lsbf = 0, msb位在先

                   (0 << 7);          //禁止spi中断

       u8_dummy= S0SPSR;    // flush SPI Rx buffer

       u8_dummy= S0SPDR;

       u8_dummy= S0SPSR;

       u8_dummy= S0SPDR;

}

 

SPI master发送1byte数据:

static void mSPI_SendByte(U8 u8_dat)

{

      S0SPDR = u8_dat;

       while((S0SPSR & 0x80) == 0);  // spicontroller is busy when S0SPSR[7] == 0

       u8_dat= S0SPSR;

       u8_dat =S0SPDR;          // flush the Rx buffer,这个一定要读,否则后面调用读函//数的时候读出来的是0xff

}

SPI master接收1byte数据:

static U8 mSPI_RecvByte(void)

{

       U8u8_dat;

 

       S0SPDR= 0x00;          // wrtie dummy byte outto generate clock, then read data from miso

       while((S0SPSR & 0x80) == 0);  // spicontroller is busy when S0SPSR[7] == 0

       u8_dat= S0SPSR;

       u8_dat= S0SPDR;

 

       returnu8_dat;

}

 

AT45DB321状态寄存器的例子:

       mSPI1_Init();

       PIN_CLR(P0,PIN_AT45_CS);

       mSPI_SendByte(0xd7);

       u8_tmp= mSPI_RecvByte();

       PIN_SET(P0,PIN_AT45_CS);

 

通过LPC2366SSP1读写AT45DB321的代码

void mSPI1_Init(void)

{

       U8u8_i, u8_dat;

 

       SSP1CR1= 0x00;                      // disablessp controller before configuration

 

       PINSEL0&= ~(0x3ff << 10);

       PINSEL0|= 0x2a0 << 10;

 

       PIN_DIR(P0,PIN_AT45_WP | PIN_AT45_CS, OUT);

       PIN_SET(P0,PIN_AT45_WP | PIN_AT45_CS); 

      

       SSP1CR0= (7 << 0)    |     // 8bit

                      (0 << 4)   |   // ssp is configured to spi

                      (0 << 6)     |   // cpol

                      (0 << 7)   |   // cpha

                      (0x07 << 8);     // scr

       SSP1CPSR= 0x30;

       SSP1CR1= (0 << 0)           |  // noraml operation

                      (1 << 1)            |   // ssp enable

                      (0 << 2);               // spi ismaster

 

       for(u8_i = 8; u8_i > 0; u8_i--){

              u8_dat= SSP1DR;              // clear RxFIFO

       }

}

 

写数据:

void mSPI1_Send(const U8 *u8_buf, U32u32_len)

{

       U8u8_dat;

 

       if(u32_len == 0){

              return;

       }

      

       do{

              while( !(SSP1SR & 0x02) );// TxFIFO isfull when SSP1SR[1] is 0

              SSP1DR= *u8_buf++;

              while(SSP1SR & 0x10);     // Wait untilthe Busy bit is cleared

              u8_dat = SSP1DR;// flush RxFIFO,一定要读,要不然后面mSPI1_RecByte读回来//的是0xff

       }while (u32_len--);

}

 

读数据:

U8 mSPI1_RecvByte(void)

{

       U8u8_dat;

 

       SSP1DR= 0x00;   // wrtie dummy byte out togenerate clock, then read data from miso

       while(SSP1SR & 0x10);     // Wait untilthe Busy bit is cleared

       u8_dat= SSP1DR;

 

       returnu8_dat;

}

 

AT45DB321状态寄存器的例子

       mSPI1_Init();

       PIN_CLR(P0,PIN_AT45_CS);

       buf_w[0]= 0xd7;

       mSPI1_Send(buf_w,1);

       buf_r[0]= mSPI1_RecvByte();

       PIN_SET(P0,PIN_AT45_CS);

 

通过普GPIO仿SPI时序读写AT45DB321

/*====================================================================

**    函数名称 :    SPI_Wr

**  输入参数 :    dat1字节数据

**    输出参数 :    

**  影响变量 : 

**    函数描述 :    1字节到SPI总线

**  修改描述 :  root 2010-10-24

====================================================================*/

static void SPI_Wr(INT8U dat)

{

       INT8Ui;

 

       OS_ENTER_CRITICAL();   

       for(i = 0;i<8;i++){

              if((dat & 0x80)==0x80){

                     PIN_SET(P0,PIN_AT45_SI);

              }

              else{

                     PIN_CLR(P0,PIN_AT45_SI);

              }

              PIN_SET(P0,PIN_AT45_SCK);

              PIN_CLR(P0,PIN_AT45_SCK);

              dat<<= 1;

       }

       OS_EXIT_CRITICAL();

}

 

/*====================================================================

**    函数名称 :    SPI_Rd

**  输入参数 :    

**    输出参数 :    dat1字节数据

**  影响变量 : 

**    函数描述 :    1字节到SPI总线

**  修改描述 :  root 2010-10-24

====================================================================*/

static INT8U SPI_Rd(void)

{

       INT8Ui, dat;

 

       OS_ENTER_CRITICAL();   

       for(dat = 0, i = 0;i<8;i++){

              PIN_SET(P0,PIN_AT45_SCK);

              dat<<= 1;

              if(PIN_GET(P0, PIN_AT45_SO)){

                     dat|= 1; 

              }

              PIN_CLR(P0,PIN_AT45_SCK);

       }

       OS_EXIT_CRITICAL();

 

       returndat;

}

你可能感兴趣的:(SPI调试笔记)