主题中讨论的其他器件:DAC70501
大家好!
我无法配置 SPI 3线模式、即简单地向 SPI 从器件发送3个字节。
已正确配置 GPIO:
SysCtrlRegs.PCLKCR0.bit.SPIAENCLK = 1; // SPI-A //-------------------------------------------------------------------------------------- // GPIO-16 - PIN FUNCTION = SPISIMO-A GpioCtrlRegs.GPAPUD.bit.GPIO16 = 0; // Enable pull-up on GPIO16 (SPISIMOA) GpioCtrlRegs.GPAQSEL2.bit.GPIO16 = 3; // Asynch input GPIO16 (SPISIMOA) GpioCtrlRegs.GPAMUX2.bit.GPIO16 = 1; // 0=GPIO, 1=SPISIMO-A, 2=Resv, 3=TZ2 //-------------------------------------------------------------------------------------- // GPIO-17 - PIN FUNCTION = SPISOMI-A (as GPIO not needed in 3-wire mode) GpioCtrlRegs.GPAMUX2.bit.GPIO17 = 0; // 0=GPIO, 1=SPISOMI-A, 2=Resv, 3=TZ3 GpioCtrlRegs.GPADIR.bit.GPIO17 = 1; // 1=OUTput, 0=INput GpioDataRegs.GPACLEAR.bit.GPIO17 = 1; // uncomment if --> Set Low initially //-------------------------------------------------------------------------------------- // GPIO-18 - PIN FUNCTION = SPICLK-A GpioCtrlRegs.GPAPUD.bit.GPIO18 = 0; // Enable pull-up on GPIO18 (SPICLKA) GpioCtrlRegs.GPAQSEL2.bit.GPIO18 = 3; // Asynch input GPIO18 (SPICLKA) GpioCtrlRegs.GPAMUX2.bit.GPIO18 = 1; // 0=GPIO, 1=SPICLK-A, 2=SCITX-A, 3=XCLKOUT //-------------------------------------------------------------------------------------- // GPIO-19 - PIN FUNCTION = SPISTE-A GpioCtrlRegs.GPAPUD.bit.GPIO19 = 0; // Enable pull-up on GPIO19 (SPISTEA) GpioCtrlRegs.GPAQSEL2.bit.GPIO19 = 3; // Asynch input GPIO19 (SPISTEA) GpioCtrlRegs.GPAMUX2.bit.GPIO19 = 1; // 0=GPIO, 1=SPISTE-A, 2=SCIRX-A, 3=ECAP1 //--------------------------------------------------------------------------------------
然后、我为 TX 用3个级别初始化 FIFO、我不需要 RX (也许是肯定的?):
void spi_fifo_init() { // Initialize SPI FIFO registers //SpiaRegs.SPIFFTX.all=0xE040; SpiaRegs.SPIFFTX.bit.SPIRST=1; //SPI FIFO can resume transmit or receive SpiaRegs.SPIFFTX.bit.SPIFFENA=1; //SPI FIFO enhancements are enabled SpiaRegs.SPIFFTX.bit.TXFFINTCLR =1; // Clear TXFIFO interrupt flag SpiaRegs.SPIFFTX.bit.TXFFIENA = 0; // TXFIFO interrupt disabled SpiaRegs.SPIFFTX.bit.TXFFIL =3; //3 levels for TXFIFO Interrupt (no needed) SpiaRegs.SPIFFTX.bit.TXFIFO =1; //Release transmit FIFO from reset. //SpiaRegs.SPIFFRX.all=0x2044; SpiaRegs.SPIFFRX.bit.RXFFOVFCLR = 1; // CLEAR OV rX flag SpiaRegs.SPIFFRX.bit.RXFFINTCLR =1; //b6 Clear SPIFFRX flag SpiaRegs.SPIFFRX.bit.RXFFIENA = 0; //b5 RXFIFO interrupt disabled SpiaRegs.SPIFFRX.bit.RXFFIL=0; //level bits for RXFIFO Interrupt (no needed) SpiaRegs.SPIFFRX.bit.RXFIFORESET = 1; //b13 Re-enable receive FIFO operation. SpiaRegs.SPIFFCT.all=0x0; //The next word in the TX FIFO buffer is transferred to //SPITXBUF immediately upon completion of transmission of the //previous word. }
然后 SPI 初始化:
void spi_init_DAC70501() { //SpiaRegs.SPICCR.all =0x000F; // Reset on, rising edge, 16-bit char bits //SpiaRegs.SPICTL.all =0x0006; // Enable master mode, normal phase, // enable talk, and SPI int disabled. SpiaRegs.SPICCR.bit.SPISWRESET = 0; //Reset SPI before configuration SpiaRegs.SPICCR.bit.CLKPOLARITY =1; //falling edge SpiaRegs.SPICCR.bit.SPICHAR =7; //8-bit char bits SpiaRegs.SPICTL.bit.MASTER_SLAVE=1; //Enable master mode SpiaRegs.SPICTL.bit.CLK_PHASE=1; // phase with delay SpiaRegs.SPICTL.bit.TALK = 1; // Enable Transmit path SpiaRegs.SPICTL.bit.OVERRUNINTENA = 0; //disbale overrun interruption SpiaRegs.SPICTL.bit.SPIINTENA = 0; ////disable SPIinterruption SpiaRegs.SPIBRR =127; // SPI Baud Rate=LSPCLK/(SPIBRR+1) LSPCLK=CPU_FREQ/4 // 15MHz/(127+1)=117kHz // 15MHz/(14+1)=1MHz SpiaRegs.SPIPRI.bit.TRIWIRE=1; //3-wire SPI mode enable //(The unused pin SPISOMI is free for GPIO) //SpiaRegs.SPICCR.all =0x009F; // Relinquish SPI from Reset SpiaRegs.SPICCR.bit.SPISWRESET = 1; // Relinquish SPI from Reset SpiaRegs.SPIPRI.bit.FREE = 1; // Set so breakpoints don't disturb xmission }
最后、这是我将 在主程序中定期调用的 TX 函数:
/********************************************************************** * Function: spi_xmit() * * Description: Transmit 16bit to SPIA using 3-Wire Mode Transmit * When the master transmits, it receives the data it * transmits (because SPISIMOx and SPISOMIx are connected * internally in 3-wire mode). Therefore, the junk data received * must be cleared from the receive buffer every time data is transmitted. **********************************************************************/ void spi_xmit(char a) { Uint16 data= (Uint16)(a<<8); Uint16 dummy; SpiaRegs.SPICTL.bit.TALK = 1; // Enable Transmit path SpiaRegs.SPITXBUF = data; // Master transmits data while(SpiaRegs.SPISTS.bit.INT_FLAG !=1) {} // Waits until data rx’d dummy = SpiaRegs.SPIRXBUF; // Clears junk data from itself SpiaRegs.SPITXBUF = data; // Master transmits data while(SpiaRegs.SPISTS.bit.INT_FLAG !=1) {} // Waits until data rx’d dummy = SpiaRegs.SPIRXBUF; // Clears junk data from itself SpiaRegs.SPITXBUF = data; // Master transmits data while(SpiaRegs.SPISTS.bit.INT_FLAG !=1) {} // Waits until data rx’d dummy = SpiaRegs.SPIRXBUF; // Clears junk data from itself }
我可以在示波器中检查第一个字节已发送、但之后通信会被阻止。
如果没有3线制模式或 FIFO、我就能够顺利发送2个字节(没有阻塞)。
我做错了什么? 通过 SPI 向外部从器件发送3个字节的正确方法是什么?
提前感谢。
此致