You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
220 lines
5.4 KiB
220 lines
5.4 KiB
#include "spi.h"
|
|
|
|
// generic implementation of spi channel class
|
|
|
|
void spiInitMaster(
|
|
spiCH_t spi_hw_ch,
|
|
spi_clkPol_t clockPolarity,
|
|
spi_phase_t phase,
|
|
spi_framef_t frameFormat,
|
|
spi_comMode_t comMode,
|
|
uint32_t prescaler,
|
|
pinNo_t clkPin,
|
|
uint16_t altFuncClkPin,
|
|
pinNo_t MOSIPin,
|
|
uint16_t altFuncMOSIPin,
|
|
pinNo_t MISOPin,
|
|
uint16_t altFuncMISOPin)
|
|
{
|
|
// GPIO setup
|
|
pinInit(clkPin);
|
|
pinInit(MOSIPin);
|
|
pinInit(MISOPin);
|
|
pinConfig(clkPin, alternate, pushPull, output, veryFast);
|
|
pinConfig(MISOPin, alternate, floating, input , veryFast);
|
|
pinConfig(MOSIPin, alternate, pushPull, output, veryFast);
|
|
pinSetAlternate(clkPin, altFuncClkPin);
|
|
pinSetAlternate(MOSIPin, altFuncMOSIPin);
|
|
pinSetAlternate(MISOPin, altFuncMISOPin);
|
|
|
|
// SPI setup
|
|
spiEnableBus(spi_hw_ch);
|
|
spiSetPolarity(spi_hw_ch,clockPolarity);
|
|
spiSetPhase(spi_hw_ch,phase);
|
|
spiSetMode(spi_hw_ch, SPI_MASTER);
|
|
spiSetClockPrescaler(spi_hw_ch, prescaler);
|
|
spiSetFrameFormat(spi_hw_ch,frameFormat);
|
|
spiSetSoftwareSlaveManagement(spi_hw_ch,1);
|
|
spiSetInternalSlaveSelect(spi_hw_ch,0);
|
|
spiSetComMode(spi_hw_ch, comMode);
|
|
spiSetClockPrescaler(spi_hw_ch, prescaler);
|
|
spiSetBitFrameLength(spi_hw_ch, SPI_FRAME_LENGTH_8BIT);
|
|
}
|
|
|
|
void spiSetupCH(spi_ch_t *ch, spiCH_t spi_hw_ch, pinNo_t chipselectPin)
|
|
{
|
|
ch->pin = chipselectPin;
|
|
ch->spi = spi_hw_ch;
|
|
pinWrite(chipselectPin, 0);
|
|
}
|
|
|
|
uint8_t spiReadReg(spi_ch_t *spi_ch, uint8_t reg_address) {
|
|
uint8_t buf;
|
|
|
|
// select target device
|
|
pinWrite(spi_ch->pin,0);
|
|
|
|
// send address of target register
|
|
spiTrx8BitPolling(spi_ch->spi, reg_address);
|
|
|
|
// read from target register
|
|
buf = spiTrx8BitPolling(spi_ch->spi,0x00);
|
|
|
|
// release target device
|
|
pinWrite(spi_ch->pin,1);
|
|
|
|
return buf;
|
|
}
|
|
|
|
void spiAutoReadBlock(spi_ch_t *spi_ch,
|
|
uint8_t start_address,
|
|
uint8_t* buffer,
|
|
uint8_t buf_len) {
|
|
uint8_t i = 0;
|
|
|
|
// select target device
|
|
pinWrite(spi_ch->pin,0);
|
|
|
|
// send address of starting register
|
|
spiTrx8BitPolling(spi_ch->spi, start_address);
|
|
|
|
// read block from device
|
|
for(;i < buf_len;i++) {
|
|
buffer[i] = spiTrx8BitPolling(spi_ch->spi, 0x00);
|
|
}
|
|
|
|
// release target device
|
|
pinWrite(spi_ch->pin,1);
|
|
}
|
|
|
|
void spiWriteReg(spi_ch_t *spi_ch,
|
|
uint8_t reg_address,
|
|
uint8_t data) {
|
|
// select target device
|
|
pinWrite(spi_ch->pin,0);
|
|
|
|
// send address of target register
|
|
spiTrx8BitPolling(spi_ch->spi, reg_address);
|
|
|
|
// write to target register
|
|
spiTrx8BitPolling(spi_ch->spi, data);
|
|
|
|
// release target device
|
|
pinWrite(spi_ch->pin,1);
|
|
}
|
|
|
|
void spiWriteBlock(spi_ch_t *spi_ch,
|
|
uint8_t start_address,
|
|
const uint8_t *data,
|
|
uint8_t data_len) {
|
|
uint8_t i = 0;
|
|
|
|
// select target device
|
|
pinWrite(spi_ch->pin,0);
|
|
|
|
// send address of starting register
|
|
spiTrx8BitPolling(spi_ch->spi, start_address);
|
|
|
|
// read block from device
|
|
for(;i < data_len;i++) {
|
|
spiTrx8BitPolling(spi_ch->spi, data[i]);
|
|
}
|
|
|
|
// release target device
|
|
pinWrite(spi_ch->pin,1);
|
|
}
|
|
|
|
void spiWrite8bit(spi_ch_t *spi_ch,
|
|
uint8_t bits)
|
|
{
|
|
pinWrite(spi_ch->pin,0);
|
|
spiTrx8BitPolling(spi_ch->spi,bits);
|
|
pinWrite(spi_ch->pin,1);
|
|
}
|
|
|
|
uint8_t spiReadWrite8bit(spi_ch_t *spi_ch,
|
|
uint8_t bits)
|
|
{
|
|
uint8_t buf;
|
|
pinWrite(spi_ch->pin,0);
|
|
buf = spiTrx8BitPolling(spi_ch->spi,bits);
|
|
pinWrite(spi_ch->pin,1);
|
|
return buf;
|
|
}
|
|
|
|
void spiWrite16bit(spi_ch_t *spi_ch,
|
|
uint16_t bits)
|
|
{
|
|
pinWrite(spi_ch->pin,0);
|
|
if(spiGetFrameFormat(spi_ch->spi) == SPI_MSB_FIRST) {
|
|
spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 8));
|
|
spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits));
|
|
} else {
|
|
spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits));
|
|
spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 8));
|
|
}
|
|
pinWrite(spi_ch->pin,1);
|
|
}
|
|
|
|
uint16_t spiReadWrite16bit(spi_ch_t *spi_ch,
|
|
uint16_t bits)
|
|
{
|
|
uint16_t buf;
|
|
|
|
pinWrite(spi_ch->pin,0);
|
|
if(spiGetFrameFormat(spi_ch->spi) == SPI_LSB_FIRST) {
|
|
buf = spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 8)) << 8;
|
|
buf |= spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits));
|
|
} else {
|
|
buf = spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits));
|
|
buf |= spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 8)) << 8;
|
|
}
|
|
pinWrite(spi_ch->pin,1);
|
|
|
|
return buf;
|
|
}
|
|
|
|
void spiWrite32bit(spi_ch_t *spi_ch,
|
|
uint32_t bits)
|
|
{
|
|
pinWrite(spi_ch->pin,0);
|
|
|
|
if(spiGetFrameFormat(spi_ch->spi) == SPI_LSB_FIRST) {
|
|
spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 24));
|
|
spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 16));
|
|
spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 8));
|
|
spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits));
|
|
} else {
|
|
spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits));
|
|
spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 8));
|
|
spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 16));
|
|
spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 24));
|
|
}
|
|
pinWrite(spi_ch->pin,1);
|
|
}
|
|
|
|
uint32_t spiReadWrite32bit(spi_ch_t *spi_ch,
|
|
uint8_t bits)
|
|
{
|
|
uint32_t buf;
|
|
|
|
pinWrite(spi_ch->pin,0);
|
|
if(spiGetFrameFormat(spi_ch->spi) == SPI_LSB_FIRST) {
|
|
buf = spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 24)) << 24;
|
|
buf |= spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 16)) << 16;
|
|
buf |= spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 8)) << 8;
|
|
buf |= spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits));
|
|
} else {
|
|
buf = spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits));
|
|
buf |= spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 8)) >> 8;
|
|
buf |= spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 16)) >> 16;
|
|
buf |= spiTrx8BitPolling(spi_ch->spi,(uint8_t)(bits >> 24)) >> 24;
|
|
}
|
|
pinWrite(spi_ch->pin,1);
|
|
|
|
return buf;
|
|
}
|
|
|
|
|
|
|