| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496 |
- /* Copyright 2018 Canaan Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
- #ifndef _DRIVER_SPI_H
- #define _DRIVER_SPI_H
- #include <stddef.h>
- #include <stdint.h>
- #include "dmac.h"
- #ifdef __cplusplus
- extern "C" {
- #endif
- /* clang-format off */
- typedef struct _spi
- {
- /* SPI Control Register 0 (0x00)*/
- volatile uint32_t ctrlr0;
- /* SPI Control Register 1 (0x04)*/
- volatile uint32_t ctrlr1;
- /* SPI Enable Register (0x08)*/
- volatile uint32_t ssienr;
- /* SPI Microwire Control Register (0x0c)*/
- volatile uint32_t mwcr;
- /* SPI Slave Enable Register (0x10)*/
- volatile uint32_t ser;
- /* SPI Baud Rate Select (0x14)*/
- volatile uint32_t baudr;
- /* SPI Transmit FIFO Threshold Level (0x18)*/
- volatile uint32_t txftlr;
- /* SPI Receive FIFO Threshold Level (0x1c)*/
- volatile uint32_t rxftlr;
- /* SPI Transmit FIFO Level Register (0x20)*/
- volatile uint32_t txflr;
- /* SPI Receive FIFO Level Register (0x24)*/
- volatile uint32_t rxflr;
- /* SPI Status Register (0x28)*/
- volatile uint32_t sr;
- /* SPI Interrupt Mask Register (0x2c)*/
- volatile uint32_t imr;
- /* SPI Interrupt Status Register (0x30)*/
- volatile uint32_t isr;
- /* SPI Raw Interrupt Status Register (0x34)*/
- volatile uint32_t risr;
- /* SPI Transmit FIFO Overflow Interrupt Clear Register (0x38)*/
- volatile uint32_t txoicr;
- /* SPI Receive FIFO Overflow Interrupt Clear Register (0x3c)*/
- volatile uint32_t rxoicr;
- /* SPI Receive FIFO Underflow Interrupt Clear Register (0x40)*/
- volatile uint32_t rxuicr;
- /* SPI Multi-Master Interrupt Clear Register (0x44)*/
- volatile uint32_t msticr;
- /* SPI Interrupt Clear Register (0x48)*/
- volatile uint32_t icr;
- /* SPI DMA Control Register (0x4c)*/
- volatile uint32_t dmacr;
- /* SPI DMA Transmit Data Level (0x50)*/
- volatile uint32_t dmatdlr;
- /* SPI DMA Receive Data Level (0x54)*/
- volatile uint32_t dmardlr;
- /* SPI Identification Register (0x58)*/
- volatile uint32_t idr;
- /* SPI DWC_ssi component version (0x5c)*/
- volatile uint32_t ssic_version_id;
- /* SPI Data Register 0-36 (0x60 -- 0xec)*/
- volatile uint32_t dr[36];
- /* SPI RX Sample Delay Register (0xf0)*/
- volatile uint32_t rx_sample_delay;
- /* SPI SPI Control Register (0xf4)*/
- volatile uint32_t spi_ctrlr0;
- /* reserved (0xf8)*/
- volatile uint32_t resv;
- /* SPI XIP Mode bits (0xfc)*/
- volatile uint32_t xip_mode_bits;
- /* SPI XIP INCR transfer opcode (0x100)*/
- volatile uint32_t xip_incr_inst;
- /* SPI XIP WRAP transfer opcode (0x104)*/
- volatile uint32_t xip_wrap_inst;
- /* SPI XIP Control Register (0x108)*/
- volatile uint32_t xip_ctrl;
- /* SPI XIP Slave Enable Register (0x10c)*/
- volatile uint32_t xip_ser;
- /* SPI XIP Receive FIFO Overflow Interrupt Clear Register (0x110)*/
- volatile uint32_t xrxoicr;
- /* SPI XIP time out register for continuous transfers (0x114)*/
- volatile uint32_t xip_cnt_time_out;
- volatile uint32_t endian;
- } __attribute__((packed, aligned(4))) spi_t;
- /* clang-format on */
- typedef enum _spi_device_num
- {
- SPI_DEVICE_0,
- SPI_DEVICE_1,
- SPI_DEVICE_2,
- SPI_DEVICE_3,
- SPI_DEVICE_MAX,
- } spi_device_num_t;
- typedef enum _spi_work_mode
- {
- SPI_WORK_MODE_0,
- SPI_WORK_MODE_1,
- SPI_WORK_MODE_2,
- SPI_WORK_MODE_3,
- } spi_work_mode_t;
- typedef enum _spi_frame_format
- {
- SPI_FF_STANDARD,
- SPI_FF_DUAL,
- SPI_FF_QUAD,
- SPI_FF_OCTAL
- } spi_frame_format_t;
- typedef enum _spi_instruction_address_trans_mode
- {
- SPI_AITM_STANDARD,
- SPI_AITM_ADDR_STANDARD,
- SPI_AITM_AS_FRAME_FORMAT
- } spi_instruction_address_trans_mode_t;
- typedef enum _spi_transfer_mode
- {
- SPI_TMOD_TRANS_RECV,
- SPI_TMOD_TRANS,
- SPI_TMOD_RECV,
- SPI_TMOD_EEROM
- } spi_transfer_mode_t;
- typedef enum _spi_transfer_width
- {
- SPI_TRANS_CHAR = 0x1,
- SPI_TRANS_SHORT = 0x2,
- SPI_TRANS_INT = 0x4,
- } spi_transfer_width_t;
- typedef enum _spi_chip_select
- {
- SPI_CHIP_SELECT_0,
- SPI_CHIP_SELECT_1,
- SPI_CHIP_SELECT_2,
- SPI_CHIP_SELECT_3,
- SPI_CHIP_SELECT_MAX,
- } spi_chip_select_t;
- typedef enum
- {
- WRITE_CONFIG,
- READ_CONFIG,
- WRITE_DATA_BYTE,
- READ_DATA_BYTE,
- WRITE_DATA_BLOCK,
- READ_DATA_BLOCK,
- } spi_slave_command_e;
- typedef struct
- {
- uint8_t cmd;
- uint8_t err;
- uint32_t addr;
- uint32_t len;
- } spi_slave_command_t;
- typedef enum
- {
- IDLE,
- COMMAND,
- TRANSFER,
- } spi_slave_status_e;
- typedef int (*spi_slave_receive_callback_t)(void *ctx);
- typedef struct _spi_slave_instance
- {
- uint8_t int_pin;
- uint8_t ready_pin;
- dmac_channel_number_t dmac_channel;
- uint8_t dfs;
- uint8_t slv_oe;
- uint8_t work_mode;
- size_t data_bit_length;
- volatile spi_slave_status_e status;
- volatile spi_slave_command_t command;
- volatile uint8_t *config_ptr;
- uint32_t config_len;
- spi_slave_receive_callback_t callback;
- uint8_t is_dual;
- uint8_t mosi_pin;
- uint8_t miso_pin;
- } spi_slave_instance_t;
- typedef struct _spi_data_t
- {
- dmac_channel_number_t tx_channel;
- dmac_channel_number_t rx_channel;
- uint32_t *tx_buf;
- size_t tx_len;
- uint32_t *rx_buf;
- size_t rx_len;
- spi_transfer_mode_t transfer_mode;
- bool fill_mode;
- } spi_data_t;
- extern volatile spi_t *const spi[4];
- /**
- * @brief Set spi configuration
- *
- * @param[in] spi_num Spi bus number
- * @param[in] mode Spi mode
- * @param[in] frame_format Spi frame format
- * @param[in] data_bit_length Spi data bit length
- * @param[in] endian 0:little-endian 1:big-endian
- *
- * @return Void
- */
- void spi_init(spi_device_num_t spi_num, spi_work_mode_t work_mode, spi_frame_format_t frame_format,
- size_t data_bit_length, uint32_t endian);
- /**
- * @brief Set multiline configuration
- *
- * @param[in] spi_num Spi bus number
- * @param[in] instruction_length Instruction length
- * @param[in] address_length Address length
- * @param[in] wait_cycles Wait cycles
- * @param[in] instruction_address_trans_mode Spi transfer mode
- *
- */
- void spi_init_non_standard(spi_device_num_t spi_num, uint32_t instruction_length, uint32_t address_length,
- uint32_t wait_cycles, spi_instruction_address_trans_mode_t instruction_address_trans_mode);
- /**
- * @brief Spi send data
- *
- * @param[in] spi_num Spi bus number
- * @param[in] chip_select Spi chip select
- * @param[in] cmd_buff Spi command buffer point
- * @param[in] cmd_len Spi command length
- * @param[in] tx_buff Spi transmit buffer point
- * @param[in] tx_len Spi transmit buffer length
- *
- * @return Result
- * - 0 Success
- * - Other Fail
- */
- void spi_send_data_standard(spi_device_num_t spi_num, spi_chip_select_t chip_select, const uint8_t *cmd_buff,
- size_t cmd_len, const uint8_t *tx_buff, size_t tx_len);
- /**
- * @brief Spi receive data
- *
- * @param[in] spi_num Spi bus number
- * @param[in] chip_select Spi chip select
- * @param[in] cmd_buff Spi command buffer point
- * @param[in] cmd_len Spi command length
- * @param[in] rx_buff Spi receive buffer point
- * @param[in] rx_len Spi receive buffer length
- *
- * @return Result
- * - 0 Success
- * - Other Fail
- */
- void spi_receive_data_standard(spi_device_num_t spi_num, spi_chip_select_t chip_select, const uint8_t *cmd_buff,
- size_t cmd_len, uint8_t *rx_buff, size_t rx_len);
- /**
- * @brief Spi special receive data
- *
- * @param[in] spi_num Spi bus number
- * @param[in] chip_select Spi chip select
- * @param[in] cmd_buff Spi command buffer point
- * @param[in] cmd_len Spi command length
- * @param[in] rx_buff Spi receive buffer point
- * @param[in] rx_len Spi receive buffer length
- *
- * @return Result
- * - 0 Success
- * - Other Fail
- */
- void spi_receive_data_multiple(spi_device_num_t spi_num, spi_chip_select_t chip_select, const uint32_t *cmd_buff,
- size_t cmd_len, uint8_t *rx_buff, size_t rx_len);
- /**
- * @brief Spi special send data
- *
- * @param[in] spi_num Spi bus number
- * @param[in] chip_select Spi chip select
- * @param[in] cmd_buff Spi command buffer point
- * @param[in] cmd_len Spi command length
- * @param[in] tx_buff Spi transmit buffer point
- * @param[in] tx_len Spi transmit buffer length
- *
- * @return Result
- * - 0 Success
- * - Other Fail
- */
- void spi_send_data_multiple(spi_device_num_t spi_num, spi_chip_select_t chip_select, const uint32_t *cmd_buff,
- size_t cmd_len, const uint8_t *tx_buff, size_t tx_len);
- /**
- * @brief Spi send data by dma
- *
- * @param[in] channel_num Dmac channel number
- * @param[in] spi_num Spi bus number
- * @param[in] chip_select Spi chip select
- * @param[in] cmd_buff Spi command buffer point
- * @param[in] cmd_len Spi command length
- * @param[in] tx_buff Spi transmit buffer point
- * @param[in] tx_len Spi transmit buffer length
- *
- * @return Result
- * - 0 Success
- * - Other Fail
- */
- void spi_send_data_standard_dma(dmac_channel_number_t channel_num, spi_device_num_t spi_num,
- spi_chip_select_t chip_select,
- const uint8_t *cmd_buff, size_t cmd_len, const uint8_t *tx_buff, size_t tx_len);
- /**
- * @brief Spi receive data by dma
- *
- * @param[in] w_channel_num Dmac write channel number
- * @param[in] r_channel_num Dmac read channel number
- * @param[in] spi_num Spi bus number
- * @param[in] chip_select Spi chip select
- * @param[in] cmd_buff Spi command buffer point
- * @param[in] cmd_len Spi command length
- * @param[in] rx_buff Spi receive buffer point
- * @param[in] rx_len Spi receive buffer length
- *
- * @return Result
- * - 0 Success
- * - Other Fail
- */
- void spi_receive_data_standard_dma(dmac_channel_number_t dma_send_channel_num,
- dmac_channel_number_t dma_receive_channel_num,
- spi_device_num_t spi_num, spi_chip_select_t chip_select, const uint8_t *cmd_buff,
- size_t cmd_len, uint8_t *rx_buff, size_t rx_len);
- /**
- * @brief Spi special send data by dma
- *
- * @param[in] channel_num Dmac channel number
- * @param[in] spi_num Spi bus number
- * @param[in] chip_select Spi chip select
- * @param[in] cmd_buff Spi command buffer point
- * @param[in] cmd_len Spi command length
- * @param[in] tx_buff Spi transmit buffer point
- * @param[in] tx_len Spi transmit buffer length
- *
- * @return Result
- * - 0 Success
- * - Other Fail
- */
- void spi_send_data_multiple_dma(dmac_channel_number_t channel_num, spi_device_num_t spi_num,
- spi_chip_select_t chip_select,
- const uint32_t *cmd_buff, size_t cmd_len, const uint8_t *tx_buff, size_t tx_len);
- /**
- * @brief Spi special receive data by dma
- *
- * @param[in] dma_send_channel_num Dmac write channel number
- * @param[in] dma_receive_channel_num Dmac read channel number
- * @param[in] spi_num Spi bus number
- * @param[in] chip_select Spi chip select
- * @param[in] cmd_buff Spi command buffer point
- * @param[in] cmd_len Spi command length
- * @param[in] rx_buff Spi receive buffer point
- * @param[in] rx_len Spi receive buffer length
- *
- * @return Result
- * - 0 Success
- * - Other Fail
- */
- void spi_receive_data_multiple_dma(dmac_channel_number_t dma_send_channel_num,
- dmac_channel_number_t dma_receive_channel_num,
- spi_device_num_t spi_num, spi_chip_select_t chip_select, const uint32_t *cmd_buff,
- size_t cmd_len, uint8_t *rx_buff, size_t rx_len);
- /**
- * @brief Spi fill dma
- *
- * @param[in] channel_num Dmac channel number
- * @param[in] spi_num Spi bus number
- * @param[in] chip_select Spi chip select
- * @param[in] tx_buff Spi command buffer point
- * @param[in] tx_len Spi command length
- *
- * @return Result
- * - 0 Success
- * - Other Fail
- */
- void spi_fill_data_dma(dmac_channel_number_t channel_num, spi_device_num_t spi_num, spi_chip_select_t chip_select,
- const uint32_t *tx_buff, size_t tx_len);
- /**
- * @brief Spi normal send by dma
- *
- * @param[in] channel_num Dmac channel number
- * @param[in] spi_num Spi bus number
- * @param[in] chip_select Spi chip select
- * @param[in] tx_buff Spi transmit buffer point
- * @param[in] tx_len Spi transmit buffer length
- * @param[in] stw Spi transfer width
- *
- * @return Result
- * - 0 Success
- * - Other Fail
- */
- void spi_send_data_normal_dma(dmac_channel_number_t channel_num, spi_device_num_t spi_num,
- spi_chip_select_t chip_select,
- const void *tx_buff, size_t tx_len, spi_transfer_width_t spi_transfer_width);
- /**
- * @brief Spi normal send by dma
- *
- * @param[in] spi_num Spi bus number
- * @param[in] spi_clk Spi clock rate
- *
- * @return The real spi clock rate
- */
- uint32_t spi_set_clk_rate(spi_device_num_t spi_num, uint32_t spi_clk);
- /**
- * @brief Spi full duplex send receive data by dma
- *
- * @param[in] dma_send_channel_num Dmac write channel number
- * @param[in] dma_receive_channel_num Dmac read channel number
- * @param[in] spi_num Spi bus number
- * @param[in] chip_select Spi chip select
- * @param[in] tx_buf Spi send buffer
- * @param[in] tx_len Spi send buffer length
- * @param[in] rx_buf Spi receive buffer
- * @param[in] rx_len Spi receive buffer length
- *
- */
- void spi_dup_send_receive_data_dma(dmac_channel_number_t dma_send_channel_num,
- dmac_channel_number_t dma_receive_channel_num,
- spi_device_num_t spi_num, spi_chip_select_t chip_select,
- const uint8_t *tx_buf, size_t tx_len, uint8_t *rx_buf, size_t rx_len);
- /**
- * @brief Set spi slave configuration
- *
- * @param[in] int_pin SPI master starts sending data interrupt.
- * @param[in] ready_pin SPI slave ready.
- * @param[in] dmac_channel Dmac channel number for block.
- * @param[in] data_bit_length Spi data bit length
- * @param[in] data SPI slave device data buffer.
- * @param[in] len The length of SPI slave device data buffer.
- * @param[in] callback Callback of spi slave.
- *
- * @return Void
- */
- void spi_slave_config(uint8_t int_pin, uint8_t ready_pin, dmac_channel_number_t dmac_channel, size_t data_bit_length, uint8_t *data, uint32_t len, spi_slave_receive_callback_t callback);
- void spi_slave_dual_config(uint8_t int_pin,
- uint8_t ready_pin,
- uint8_t mosi_pin,
- uint8_t miso_pin,
- dmac_channel_number_t dmac_channel,
- size_t data_bit_length,
- uint8_t *data,
- uint32_t len,
- spi_slave_receive_callback_t callback);
- /**
- * @brief Spi handle transfer data operations
- *
- * @param[in] spi_num Spi bus number
- * @param[in] chip_select Spi chip select
- * @param[in] data Spi transfer data information
- * @param[in] cb Spi DMA callback
- *
- */
- void spi_handle_data_dma(spi_device_num_t spi_num, spi_chip_select_t chip_select, spi_data_t data, plic_interrupt_t *cb);
- #ifdef __cplusplus
- }
- #endif
- #endif /* _DRIVER_SPI_H */
|