Other Parts Discussed in Thread: C2000WARE, DRV8311, DRV8376, DRV8316
Tool/software:
Hello,
I've been working on this for sometime and I'm really stuck so any help would be appreciated!
I have code that can communicate with a DRV device with a SPI frame of 16 bits, I'm trying to change this code so that I can communicate with another DRV device that has a SPI frame of 24 bits.
Here is the current code I have followed by the SPI frame I am trying to convert to:
void Config_evm_spi(void) { //Pin Config EALLOW; // SPI_MOSI GPIO_SetupPinOptions(16, GPIO_INPUT, GPIO_ASYNC | GPIO_PULLUP); // SPI_MISO GPIO_SetupPinOptions(17, GPIO_INPUT, GPIO_ASYNC | GPIO_PULLUP); // SPI_CS GPIO_SetupPinOptions(56, GPIO_INPUT, GPIO_ASYNC | GPIO_PULLUP); // SPI_CLK GPIO_SetupPinOptions(57, GPIO_INPUT, GPIO_ASYNC | GPIO_PULLUP); GPIO_SetupPinMux(16, GPIO_MUX_CPU1, 1); GPIO_SetupPinMux(17, GPIO_MUX_CPU1, 1); GPIO_SetupPinMux(56, GPIO_MUX_CPU1, 1); GPIO_SetupPinMux(57, GPIO_MUX_CPU1, 1); EDIS; EALLOW; ClkCfgRegs.LOSPCP.all = 0; EDIS; // Initialize SPI FIFO registers SpiaRegs.SPIFFTX.all=0xE040; SpiaRegs.SPIFFRX.all=0x2044; SpiaRegs.SPIFFCT.all=0x0; //SPI Settings SpiaRegs.SPICCR.bit.SPISWRESET = 0; //SPI Reset On SpiaRegs.SPICCR.bit.CLKPOLARITY = 0; //SCLK Active High SpiaRegs.SPICCR.bit.SPICHAR = 0xF; //16-bit SPI char SpiaRegs.SPICCR.bit.SPILBK = 0; SpiaRegs.SPICTL.bit.OVERRUNINTENA = 0; //No overrun interrupt SpiaRegs.SPICTL.bit.CLK_PHASE = 0; //Phase 0 SpiaRegs.SPICTL.bit.MASTER_SLAVE = 1; //Master mode SpiaRegs.SPICTL.bit.TALK = 1; //nSCS enabled SpiaRegs.SPICTL.bit.SPIINTENA = 0; //TX/RX Interrupt Disabled SpiaRegs.SPIBRR.bit.SPI_BIT_RATE = ((25000000 / 1000000) - 1); //Set baud rate to 1MHz SpiaRegs.SPIPRI.bit.FREE = 1; //Set so breakpoints don't disturb transmission SpiaRegs.SPICCR.bit.SPISWRESET = 1; //Exit SPI reset } Uint16 spi_xmit(Uint16 spiFrame) { SpiaRegs.SPITXBUF=spiFrame; //Wait for RX flag to indicate SPI frame completion while(SpiaRegs.SPIFFRX.bit.RXFFST != 1) { } return SpiaRegs.SPIRXBUF; } Uint16 spi_read(Uint16 addr) { Uint16 commandword = 0; uint16_t p_addr = addr; uint16_t p_data = 0; uint16_t calc = ((p_addr << 9) & 0x7E00) | (p_data & 0x00FF); uint16_t parity = 0; while(calc) { parity ^= (calc & 1); calc >>= 1; } commandword = (0x8000 | (addr << 9) | (parity << 8)); return spi_xmit(commandword); } Uint16 spi_write(Uint16 addr, Uint16 data) { Uint16 commandword = 0; uint16_t p_addr = addr; uint16_t p_data = data; uint16_t calc = ((p_addr << 9) & 0x7E00) | (p_data & 0x00FF); uint16_t parity = 0; while(calc) { parity ^= (calc & 1); calc >>= 1; } commandword = ((addr << 9) | (parity << 8) | data); return spi_xmit(commandword); }
I'm mostly concerned about the spi_read function for the time being, I feel like if I can get that to work I'd be able to figure out spi_write
Here is my attempt that's not working :
void Config_evm_spi(void) { //Pin Config EALLOW; // SPI_MOSI GPIO_SetupPinOptions(16, GPIO_INPUT, GPIO_ASYNC | GPIO_PULLUP); // SPI_MISO GPIO_SetupPinOptions(17, GPIO_INPUT, GPIO_ASYNC | GPIO_PULLUP); // SPI_CS GPIO_SetupPinOptions(56, GPIO_INPUT, GPIO_ASYNC | GPIO_PULLUP); // SPI_CLK GPIO_SetupPinOptions(57, GPIO_INPUT, GPIO_ASYNC | GPIO_PULLUP); GPIO_SetupPinMux(16, GPIO_MUX_CPU1, 1); GPIO_SetupPinMux(17, GPIO_MUX_CPU1, 1); GPIO_SetupPinMux(56, GPIO_MUX_CPU1, 1); GPIO_SetupPinMux(57, GPIO_MUX_CPU1, 1); EDIS; EALLOW; ClkCfgRegs.LOSPCP.all = 0; EDIS; // Initialize SPI FIFO registers SpiaRegs.SPIFFTX.all = 0xE040; SpiaRegs.SPIFFRX.all = 0x2044; SpiaRegs.SPIFFCT.all = 0x0; //SPI Settings SpiaRegs.SPICCR.bit.SPISWRESET = 0; //SPI Reset On SpiaRegs.SPICCR.bit.CLKPOLARITY = 0; //SCLK Active High SpiaRegs.SPICCR.bit.SPICHAR = 0xF; //16-bit SPI char SpiaRegs.SPICCR.bit.SPILBK = 0; SpiaRegs.SPICTL.bit.OVERRUNINTENA = 0; //No overrun interrupt SpiaRegs.SPICTL.bit.CLK_PHASE = 0; //Phase 0 SpiaRegs.SPICTL.bit.MASTER_SLAVE = 1; //Master mode SpiaRegs.SPICTL.bit.TALK = 1; //nSCS enabled SpiaRegs.SPICTL.bit.SPIINTENA = 0; //TX/RX Interrupt Disabled SpiaRegs.SPIBRR.bit.SPI_BIT_RATE = ((25000000 / 1000000) - 1); //Set baud rate to 1MHz SpiaRegs.SPIPRI.bit.FREE = 1; //Set so breakpoints don't disturb transmission SpiaRegs.SPICCR.bit.SPISWRESET = 1; //Exit SPI reset } Uint32 tspi_xmit(Uint32 spiFrame) { SpiaRegs.SPITXBUF = spiFrame; //Wait for RX flag to indicate SPI frame completion while(SpiaRegs.SPIFFRX.bit.RXFFST != 1) { } return SpiaRegs.SPIRXBUF; } Uint32 tspi_read(Uint16 id, Uint16 addr) { Uint32 commandword = 0; Uint16 data = 0; // No data to read Uint16 p_addr = addr & 0x3F; // Ensure address is 6 bits (0-63) // Construct the command word commandword = (data & 0x7FFF) | (1 << 16) | (p_addr << 17); // 1 for read // Calculate even parity for bits 0-15 and bits 16-23 Uint16 parity0 = 0, parity1 = 0; int i; for (i = 0; i < 16; i++) { parity0 ^= (commandword >> i) & 1; } for (i = 16; i < 24; i++) { parity1 ^= (commandword >> i) & 1; } // Set the parity bits commandword |= (parity0 << 15) | (parity1 << 23); return tspi_xmit(commandword); } Uint32 tspi_write(Uint16 id, Uint16 addr, Uint16 data) { Uint32 commandword = 0; Uint16 p_addr = addr & 0x3F; // Ensure address is 6 bits (0-63) // Construct the command word commandword = (data & 0x7FFF) | (0 << 16) | (p_addr << 17); // 0 for write // Calculate even parity for bits 0-15 and bits 16-23 Uint16 parity0 = 0, parity1 = 0; int i; for (i = 0; i < 16; i++) { parity0 ^= (commandword >> i) & 1; } for (i = 16; i < 24; i++) { parity1 ^= (commandword >> i) & 1; } // Set the parity bits commandword |= (parity0 << 15) | (parity1 << 23); return tspi_xmit(commandword); }
Thank you!
Yara