1 /*
2  * Copyright (C) 2017-2019 Alibaba Group Holding Limited
3  */
4 
5 /******************************************************************************
6  * @file     drv_spu_spi.h
7  * @brief    header file for spi driver
8  * @version  V1.0
9  * @date     02. June 2017
10  * @model    spu_spi
11  ******************************************************************************/
12 
13 #ifndef _DRV_SPU_SPI_H_
14 #define _DRV_SPU_SPI_H_
15 
16 
17 #include <stdint.h>
18 #include <drv/common.h>
19 #ifdef CONFIG_SPI_DMA
20 #include <drv/dmac.h>
21 #endif
22 #ifdef __cplusplus
23 extern "C" {
24 #endif
25 
26 /// definition for spi handle.
27 typedef void *spi_handle_t;
28 
29 /****** SPI specific error codes *****/
30 typedef enum {
31     SPI_ERROR_MODE  = (DRV_ERROR_SPECIFIC + 1),     ///< Specified Mode not supported
32     SPI_ERROR_FRAME_FORMAT,                       ///< Specified Frame Format not supported
33     SPI_ERROR_DATA_BITS,                          ///< Specified number of Data bits not supported
34     SPI_ERROR_BIT_ORDER,                          ///< Specified Bit order not supported
35     SPI_ERROR_SS_MODE                             ///< Specified Slave Select Mode not supported
36 } spi_error_e;
37 
38 /*----- SPI Control Codes: Mode -----*/
39 typedef enum {
40     SPI_MODE_INACTIVE = 0,       ///< SPI Inactive
41     SPI_MODE_MASTER,             ///< SPI Master (Output on MOSI, Input on MISO); arg = Bus Speed in bps
42     SPI_MODE_SLAVE,              ///< SPI Slave  (Output on MISO, Input on MOSI)
43     SPI_MODE_MASTER_SIMPLEX,     ///< SPI Master (Output/Input on MOSI); arg = Bus Speed in bps
44     SPI_MODE_SLAVE_SIMPLEX       ///< SPI Slave  (Output/Input on MISO)
45 } spi_mode_e;
46 
47 /*----- SPI Control Codes: Mode Parameters: Frame Format -----*/
48 typedef enum {
49     SPI_FORMAT_CPOL0_CPHA0 = 0, ///< Clock Polarity 0, Clock Phase 0
50     SPI_FORMAT_CPOL0_CPHA1,     ///< Clock Polarity 0, Clock Phase 1
51     SPI_FORMAT_CPOL1_CPHA0,     ///< Clock Polarity 1, Clock Phase 0
52     SPI_FORMAT_CPOL1_CPHA1,     ///< Clock Polarity 1, Clock Phase 1
53 } spi_format_e;
54 
55 /*----- SPI Control Codes: Mode Parameters: Bit Order -----*/
56 typedef enum {
57     SPI_ORDER_MSB2LSB = 0,  ///< SPI Bit order from MSB to LSB
58     SPI_ORDER_LSB2MSB       ///< SPI Bit order from LSB to MSB
59 } spi_bit_order_e;
60 
61 /*----- SPI Control Codes: Mode Parameters: Data Width in bits -----*/
62 #define SPI_DATAWIDTH_MAX 32         /* 1 ~ 32 bit*/
63 
64 /*----- SPI Control Codes: Mode Parameters: Slave Select Mode -----*/
65 typedef enum {
66     /*options for SPI_MODE_MASTER/SPI_MODE_MASTER_SIMPLEX */
67     SPI_SS_MASTER_UNUSED = 0,        ///< SPI Slave Select when Master: Not used.SS line is not controlled by master, For example,SS line connected to a fixed low level
68     SPI_SS_MASTER_SW,               ///< SPI Slave Select when Master: Software controlled. SS line is configured by software
69     SPI_SS_MASTER_HW_OUTPUT,         ///< SPI Slave Select when Master: Hardware controlled Output.SS line is activated or deactivated automatically by hardware
70     SPI_SS_MASTER_HW_INPUT,          ///< SPI Slave Select when Master: Hardware monitored Input.Used in multi-master configuration where a master does not drive the Slave Select when driving the bus, but rather monitors it
71     /*options for SPI_MODE_SLAVE/SPI_MODE_SLAVE_SIMPLEX */
72     SPI_SS_SLAVE_HW,                 ///< SPI Slave Select when Slave: Hardware monitored.Hardware monitors the Slave Select line and accepts transfers only when the line is active
73     SPI_SS_SLAVE_SW                  ///< SPI Slave Select when Slave: Software controlled.Used only when the Slave Select line is not used. Software controls if the slave is responding or not(enables or disables transfers)
74 } spi_ss_mode_e;
75 
76 /****** SPI Slave Select Signal definitions *****/
77 typedef enum {
78     SPI_SS_INACTIVE = 0,        ///< SPI Slave Select Signal/line Inactive
79     SPI_SS_ACTIVE               ///< SPI Slave Select Signal/line Active
80 } spi_ss_stat_e;
81 
82 /**
83 \brief SPI Status
84 */
85 typedef struct {
86     uint32_t busy       : 1;              ///< Transmitter/Receiver busy flag
87     uint32_t data_lost  : 1;              ///< Data lost: Receive overflow / Transmit underflow (cleared on start of transfer operation)
88     uint32_t mode_fault : 1;              ///< Mode fault detected; optional (cleared on start of transfer operation)
89 } spi_status_t;
90 
91 /****** SPI Event *****/
92 typedef enum {
93     SPI_EVENT_TRANSFER_COMPLETE = 0,   ///< Data Transfer completed. Occurs after call to drv_spu_spi_send, drv_spu_spi_receive, or drv_spu_spi_transfer to indicate that all the data has been transferred. The driver is ready for the next transfer operation
94     SPI_EVENT_TX_COMPLETE,              ///< Data Transfer completed. Occurs after call to drv_spu_spi_send, drv_spu_spi_receive, or drv_spu_spi_transfer to indicate that all the data has been transferred. The driver is ready for the next transfer operation
95     SPI_EVENT_RX_COMPLETE,              ///< Data Transfer completed. Occurs after call to drv_spu_spi_send, drv_spu_spi_receive, or drv_spu_spi_transfer to indicate that all the data has been transferred. The driver is ready for the next transfer operation
96     SPI_EVENT_DATA_LOST,               ///< Data lost: Receive overflow / Transmit underflow. Occurs in slave mode when data is requested/sent by master but send/receive/transfer operation has not been started and indicates that data is lost. Occurs also in master mode when driver cannot transfer data fast enough.
97     SPI_EVENT_MODE_FAULT               ///< Master Mode Fault (SS deactivated when Master).Occurs in master mode when Slave Select is deactivated and indicates Master Mode Fault. The driver is ready for the next transfer operation.
98 } spi_event_e;
99 
100 typedef void (*spi_event_cb_t)(int32_t idx, spi_event_e event);  ///< Pointer to \ref spi_event_cb_t : SPI Event call back.
101 
102 /**
103 \brief SPI Driver Capabilities.
104 */
105 typedef struct {
106     uint32_t simplex          : 1;        ///< supports Simplex Mode (Master and Slave)
107     uint32_t ti_ssi           : 1;        ///< supports TI Synchronous Serial Interface
108     uint32_t microwire        : 1;        ///< supports Microwire Interface
109     uint32_t event_mode_fault : 1;        ///< Signal Mode Fault event: \ref spi_event_e
110 } spi_capabilities_t;
111 
112 /**
113   \brief       Initialize SPI Interface. 1. Initializes the resources needed for the SPI interface 2.registers event callback function
114   \param[in]   idx spi index
115   \param[in]   cb_event  event callback function \ref spi_event_cb_t
116   \param[in]   cb_arg    argument for call back function
117   \return      return spi handle if success
118 */
119 spi_handle_t drv_spu_spi_initialize(int32_t idx, spi_event_cb_t cb_event);
120 
121 /**
122   \brief       De-initialize SPI Interface. stops operation and releases the software resources used by the interface
123   \param[in]   handle spi handle to operate.
124   \return      error code
125 */
126 int32_t drv_spu_spi_uninitialize(spi_handle_t handle);
127 
128 /**
129   \brief       Get driver capabilities.
130   \param[in]   idx spi index
131   \return      \ref spi_capabilities_t
132 */
133 spi_capabilities_t drv_spu_spi_get_capabilities(int32_t idx);
134 
135 /**
136   \brief       config spi mode.
137   \param[in]   handle spi handle to operate.
138   \param[in]   baud      spi baud rate. if negative, then this attribute not changed
139   \param[in]   mode      \ref spi_mode_e . if negative, then this attribute not changed
140   \param[in]   format    \ref spi_format_e . if negative, then this attribute not changed
141   \param[in]   order     \ref spi_bit_order_e . if negative, then this attribute not changed
142   \param[in]   ss_mode   \ref spi_ss_mode_e . if negative, then this attribute not changed
143   \param[in]   bit_width spi data bitwidth: (1 ~ SPI_DATAWIDTH_MAX) . if negative, then this attribute not changed
144   \return      error code
145 */
146 int32_t drv_spu_spi_config(spi_handle_t handle,
147                            int32_t          baud,
148                            spi_mode_e       mode,
149                            spi_format_e     format,
150                            spi_bit_order_e  order,
151                            spi_ss_mode_e    ss_mode,
152                            int32_t        bit_width);
153 
154 
155 /**
156 \brief         sending data to SPI transmitter,(received data is ignored).
157                if non-blocking mode, this function only starts the sending,
158                \ref spi_event_e is signaled when operation completes or error happens.
159                \ref drv_spu_spi_get_status can get operation status.
160                if blocking mode, this function returns after operation completes or error happens.
161   \param[in]   handle spi handle to operate.
162   \param[in]   data  Pointer to buffer with data to send to SPI transmitter. data_type is : uint8_t for 1..8 data bits, uint16_t for 9..16 data bits,uint32_t for 17..32 data bits,
163   \param[in]   num   Number of data items to send.
164   \return      error code
165 */
166 int32_t drv_spu_spi_send(spi_handle_t handle, const void *data, uint32_t num);
167 
168 /**
169   \brief       receiving data from SPI receiver. if non-blocking mode, this function only starts the receiving,
170                \ref spi_event_e is signaled when operation completes or error happens.
171                \ref drv_spu_spi_get_status can get operation status.
172                if blocking mode, this function returns after operation completes or error happens.
173   \param[in]   handle spi handle to operate.
174   \param[out]  data  Pointer to buffer for data to receive from SPI receiver
175   \param[in]   num   Number of data items to receive
176   \return      error code
177 */
178 int32_t drv_spu_spi_receive(spi_handle_t handle, void *data, uint32_t num);
179 
180 /**
181   \brief       sending/receiving data to/from SPI transmitter/receiver.
182                if non-blocking mode, this function only starts the transfer,
183                \ref spi_event_e is signaled when operation completes or error happens.
184                \ref drv_spu_spi_get_status can get operation status.
185                if blocking mode, this function returns after operation completes or error happens.
186   \param[in]   handle spi handle to operate.
187   \param[in]   data_out  Pointer to buffer with data to send to SPI transmitter
188   \param[out]  data_in   Pointer to buffer for data to receive from SPI receiver
189   \param[in]   num_out      Number of data items to send
190   \param[in]   num_in       Number of data items to receive
191   \return      error code
192 */
193 int32_t drv_spu_spi_transfer(spi_handle_t handle, const void *data_out, void *data_in, uint32_t num_out, uint32_t num_in);
194 
195 /**
196   \brief       abort spi transfer.
197   \param[in]   handle spi handle to operate.
198   \return      error code
199 */
200 int32_t drv_spu_spi_abort_transfer(spi_handle_t handle);
201 
202 /**
203   \brief       Get SPI status.
204   \param[in]   handle spi handle to operate.
205   \return      SPI status \ref spi_status_t
206 */
207 spi_status_t drv_spu_spi_get_status(spi_handle_t handle);
208 
209 /**
210   \brief       config the SPI mode.
211   \param[in]   handle   spi handle
212   \param[in]   mode     spi mode. \ref spi_mode_e
213   \return      error code
214 */
215 int32_t drv_spu_spi_config_mode(spi_handle_t handle, spi_mode_e  mode);
216 
217 /**
218   \brief       config the SPI block mode.
219   \param[in]   handle   spi handle
220   \param[in]   flag 1 - enbale the block mode. 0 - disable the block mode
221   \return      error code
222 */
223 int32_t drv_spu_spi_config_block_mode(spi_handle_t handle, int32_t flag);
224 
225 /**
226   \brief       Set the SPI baudrate.
227   \param[in]   handle   spi handle
228   \param[in]   baud     spi baud rate
229   \return      error code
230 */
231 int32_t drv_spu_spi_config_baudrate(spi_handle_t handle, uint32_t baud);
232 
233 /**
234   \brief       config the SPI bit order.
235   \param[in]   handle   spi handle
236   \param[in]   order    spi bit order.\ref spi_bit_order_e
237   \return      error code
238 */
239 int32_t drv_spu_spi_config_bit_order(spi_handle_t handle, spi_bit_order_e order);
240 
241 /**
242   \brief       Set the SPI datawidth.
243   \param[in]   handle     spi handle
244   \param[in]   datawidth  date frame size in bits
245   \return      error code
246 */
247 int32_t drv_spu_spi_config_datawidth(spi_handle_t handle, uint32_t datawidth);
248 
249 /**
250   \brief       config the SPI format.
251   \param[in]   handle   spi handle
252   \param[in]   format   spi format. \ref spi_format_e
253   \return      error code
254 */
255 int32_t drv_spu_spi_config_format(spi_handle_t handle, spi_format_e format);
256 
257 /**
258   \brief       config the SPI slave select mode.
259   \param[in]   handle   spi handle
260   \param[in]   ss_mode  spi slave select mode. \ref spi_ss_mode_e
261   \return      error code
262 */
263 int32_t drv_spu_spi_config_ss_mode(spi_handle_t handle, spi_ss_mode_e ss_mode);
264 
265 /**
266   \brief       Get the number of the currently transferred.
267   \param[in]   handle  spi handle to operate.
268   \return      the number of the currently transferred data items
269 */
270 uint32_t drv_spu_spi_get_data_count(spi_handle_t handle);
271 
272 /**
273   \brief       control spi power.
274   \param[in]   handle  spi handle to operate.
275   \param[in]   state   power state.\ref drv_spu_power_stat_e.
276   \return      error code
277 */
278 int32_t drv_spu_spi_power_control(spi_handle_t handle, csi_power_stat_e state);
279 
280 /**
281   \brief       Control the Slave Select signal (SS).
282   \param[in]   handle  spi handle to operate.
283   \param[in]   stat    SS state. \ref spi_ss_stat_e.
284   \return      error code
285 */
286 int32_t drv_spu_spi_ss_control(spi_handle_t handle, spi_ss_stat_e stat);
287 
288 
289 #ifdef __cplusplus
290 }
291 #endif
292 
293 #endif /* _DRV_SPU_SPI_H_ */
294