| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240 |
- #include "furi-hal-spi.h"
- #include "furi-hal-resources.h"
- #include <stdbool.h>
- #include <assert.h>
- #include <stm32wbxx_ll_spi.h>
- #include <stm32wbxx_ll_utils.h>
- #include <stm32wbxx_ll_cortex.h>
- extern void Enable_SPI(SPI_TypeDef* spi);
- void furi_hal_spi_init() {
- for(size_t i = 0; i < FuriHalSpiDeviceIdMax; ++i) {
- hal_gpio_write(furi_hal_spi_devices[i].chip_select, true);
- hal_gpio_init(
- furi_hal_spi_devices[i].chip_select,
- GpioModeOutputPushPull,
- GpioPullNo,
- GpioSpeedVeryHigh);
- }
- hal_gpio_init_ex(
- &gpio_spi_r_miso,
- GpioModeAltFunctionPushPull,
- GpioPullNo,
- GpioSpeedVeryHigh,
- GpioAltFn5SPI1);
- hal_gpio_init_ex(
- &gpio_spi_r_mosi,
- GpioModeAltFunctionPushPull,
- GpioPullNo,
- GpioSpeedVeryHigh,
- GpioAltFn5SPI1);
- hal_gpio_init_ex(
- &gpio_spi_r_sck,
- GpioModeAltFunctionPushPull,
- GpioPullNo,
- GpioSpeedVeryHigh,
- GpioAltFn5SPI1);
- hal_gpio_init_ex(
- &gpio_spi_d_miso,
- GpioModeAltFunctionPushPull,
- GpioPullUp,
- GpioSpeedVeryHigh,
- GpioAltFn5SPI2);
- hal_gpio_init_ex(
- &gpio_spi_d_mosi,
- GpioModeAltFunctionPushPull,
- GpioPullUp,
- GpioSpeedVeryHigh,
- GpioAltFn5SPI2);
- hal_gpio_init_ex(
- &gpio_spi_d_sck,
- GpioModeAltFunctionPushPull,
- GpioPullUp,
- GpioSpeedVeryHigh,
- GpioAltFn5SPI2);
- }
- void furi_hal_spi_bus_lock(const FuriHalSpiBus* bus) {
- assert(bus);
- }
- void furi_hal_spi_bus_unlock(const FuriHalSpiBus* bus) {
- assert(bus);
- }
- void furi_hal_spi_bus_configure(const FuriHalSpiBus* bus, const LL_SPI_InitTypeDef* config) {
- assert(bus);
- LL_SPI_DeInit((SPI_TypeDef*)bus->spi);
- LL_SPI_Init((SPI_TypeDef*)bus->spi, (LL_SPI_InitTypeDef*)config);
- LL_SPI_SetRxFIFOThreshold((SPI_TypeDef*)bus->spi, LL_SPI_RX_FIFO_TH_QUARTER);
- LL_SPI_Enable((SPI_TypeDef*)bus->spi);
- }
- void furi_hal_spi_bus_end_txrx(const FuriHalSpiBus* bus, uint32_t timeout) {
- while(LL_SPI_GetTxFIFOLevel((SPI_TypeDef*)bus->spi) != LL_SPI_TX_FIFO_EMPTY)
- ;
- while(LL_SPI_IsActiveFlag_BSY((SPI_TypeDef*)bus->spi))
- ;
- while(LL_SPI_GetRxFIFOLevel((SPI_TypeDef*)bus->spi) != LL_SPI_RX_FIFO_EMPTY) {
- LL_SPI_ReceiveData8((SPI_TypeDef*)bus->spi);
- }
- }
- bool furi_hal_spi_bus_rx(const FuriHalSpiBus* bus, uint8_t* buffer, size_t size, uint32_t timeout) {
- assert(bus);
- assert(buffer);
- assert(size > 0);
- return furi_hal_spi_bus_trx(bus, buffer, buffer, size, timeout);
- }
- bool furi_hal_spi_bus_tx(const FuriHalSpiBus* bus, uint8_t* buffer, size_t size, uint32_t timeout) {
- assert(bus);
- assert(buffer);
- assert(size > 0);
- bool ret = true;
- while(size > 0) {
- if(LL_SPI_IsActiveFlag_TXE((SPI_TypeDef*)bus->spi)) {
- LL_SPI_TransmitData8((SPI_TypeDef*)bus->spi, *buffer);
- buffer++;
- size--;
- }
- }
- furi_hal_spi_bus_end_txrx(bus, timeout);
- LL_SPI_ClearFlag_OVR((SPI_TypeDef*)bus->spi);
- return ret;
- }
- bool furi_hal_spi_bus_trx(
- const FuriHalSpiBus* bus,
- uint8_t* tx_buffer,
- uint8_t* rx_buffer,
- size_t size,
- uint32_t timeout) {
- assert(bus);
- assert(tx_buffer);
- assert(rx_buffer);
- assert(size > 0);
- bool ret = true;
- size_t tx_size = size;
- bool tx_allowed = true;
- while(size > 0) {
- if(tx_size > 0 && LL_SPI_IsActiveFlag_TXE((SPI_TypeDef*)bus->spi) && tx_allowed) {
- LL_SPI_TransmitData8((SPI_TypeDef*)bus->spi, *tx_buffer);
- tx_buffer++;
- tx_size--;
- tx_allowed = false;
- }
- if(LL_SPI_IsActiveFlag_RXNE((SPI_TypeDef*)bus->spi)) {
- *rx_buffer = LL_SPI_ReceiveData8((SPI_TypeDef*)bus->spi);
- rx_buffer++;
- size--;
- tx_allowed = true;
- }
- }
- furi_hal_spi_bus_end_txrx(bus, timeout);
- return ret;
- }
- void furi_hal_spi_device_configure(const FuriHalSpiDevice* device) {
- assert(device);
- assert(device->config);
- furi_hal_spi_bus_configure(device->bus, device->config);
- }
- const FuriHalSpiDevice* furi_hal_spi_device_get(FuriHalSpiDeviceId device_id) {
- assert(device_id < FuriHalSpiDeviceIdMax);
- const FuriHalSpiDevice* device = &furi_hal_spi_devices[device_id];
- assert(device);
- furi_hal_spi_bus_lock(device->bus);
- furi_hal_spi_device_configure(device);
- return device;
- }
- void furi_hal_spi_device_return(const FuriHalSpiDevice* device) {
- furi_hal_spi_bus_unlock(device->bus);
- }
- bool furi_hal_spi_device_rx(
- const FuriHalSpiDevice* device,
- uint8_t* buffer,
- size_t size,
- uint32_t timeout) {
- assert(device);
- assert(buffer);
- assert(size > 0);
- if(device->chip_select) {
- hal_gpio_write(device->chip_select, false);
- }
- bool ret = furi_hal_spi_bus_rx(device->bus, buffer, size, timeout);
- if(device->chip_select) {
- hal_gpio_write(device->chip_select, true);
- }
- return ret;
- }
- bool furi_hal_spi_device_tx(
- const FuriHalSpiDevice* device,
- uint8_t* buffer,
- size_t size,
- uint32_t timeout) {
- assert(device);
- assert(buffer);
- assert(size > 0);
- if(device->chip_select) {
- hal_gpio_write(device->chip_select, false);
- }
- bool ret = furi_hal_spi_bus_tx(device->bus, buffer, size, timeout);
- if(device->chip_select) {
- hal_gpio_write(device->chip_select, true);
- }
- return ret;
- }
- bool furi_hal_spi_device_trx(
- const FuriHalSpiDevice* device,
- uint8_t* tx_buffer,
- uint8_t* rx_buffer,
- size_t size,
- uint32_t timeout) {
- assert(device);
- assert(tx_buffer);
- assert(rx_buffer);
- assert(size > 0);
- if(device->chip_select) {
- hal_gpio_write(device->chip_select, false);
- }
- bool ret = furi_hal_spi_bus_trx(device->bus, tx_buffer, rx_buffer, size, timeout);
- if(device->chip_select) {
- hal_gpio_write(device->chip_select, true);
- }
- return ret;
- }
|