• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright (C) 2022 Beken Corporation
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 //     http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 
15 #pragma once
16 
17 #include <soc/soc.h>
18 #include "hal_port.h"
19 #include <driver/hal/hal_gpio_types.h>
20 #include "spi_hw.h"
21 #include <driver/hal/hal_spi_types.h>
22 
23 #ifdef __cplusplus
24 extern "C" {
25 #endif
26 
27 #define SPI_LL_REG_BASE(_spi_unit_id)    (SOC_SPI_REG_BASE + _spi_unit_id * 0x1060000)
28 
29 /*
30  *  config GPIO44~GPIO47 for SPI0
31  */
32 #define SPI0_LL_SCK_PIN     GPIO_44
33 #define SPI0_LL_CSN_PIN     GPIO_45
34 #define SPI0_LL_MOSI_PIN    GPIO_46
35 #define SPI0_LL_MISO_PIN    GPIO_47
36 
37 //TODO init more
spi_ll_init(spi_hw_t * hw)38 static inline void spi_ll_init(spi_hw_t *hw)
39 {
40 	hw->ctrl.tx_fifo_int_level = 0;
41 	hw->ctrl.rx_fifo_int_level = 2;
42 }
43 
spi_ll_enable(spi_hw_t * hw)44 static inline void spi_ll_enable(spi_hw_t *hw)
45 {
46 	hw->ctrl.enable = 1;
47 }
48 
spi_ll_disable(spi_hw_t * hw)49 static inline void spi_ll_disable(spi_hw_t *hw)
50 {
51 	hw->ctrl.enable = 0;
52 }
53 
spi_ll_set_tx_fifo_int_level(spi_hw_t * hw,spi_fifo_int_level level)54 static inline void spi_ll_set_tx_fifo_int_level(spi_hw_t *hw, spi_fifo_int_level level)
55 {
56 	hw->ctrl.tx_fifo_int_level = level;
57 }
58 
spi_ll_set_rx_fifo_int_level(spi_hw_t * hw,spi_fifo_int_level level)59 static inline void spi_ll_set_rx_fifo_int_level(spi_hw_t *hw, spi_fifo_int_level level)
60 {
61 	hw->ctrl.rx_fifo_int_level = level;
62 }
63 
spi_ll_get_tx_fifo_int_level(spi_hw_t * hw)64 static inline uint32_t spi_ll_get_tx_fifo_int_level(spi_hw_t *hw)
65 {
66 	switch (hw->ctrl.tx_fifo_int_level) {
67 	case SPI_FIFO_INT_LEVEL_1:
68 		return 1;
69 	case SPI_FIFO_INT_LEVEL_16:
70 		return 16;
71 	case SPI_FIFO_INT_LEVEL_32:
72 		return 32;
73 	case SPI_FIFO_INT_LEVEL_48:
74 	default:
75 		return 48;
76 	}
77 }
78 
spi_ll_get_rx_fifo_int_level(spi_hw_t * hw)79 static inline uint32_t spi_ll_get_rx_fifo_int_level(spi_hw_t *hw)
80 {
81 	switch (hw->ctrl.rx_fifo_int_level) {
82 	case SPI_FIFO_INT_LEVEL_1:
83 		return 1;
84 	case SPI_FIFO_INT_LEVEL_16:
85 		return 16;
86 	case SPI_FIFO_INT_LEVEL_32:
87 		return 32;
88 	case SPI_FIFO_INT_LEVEL_48:
89 	default:
90 		return 48;
91 	}
92 }
93 
spi_ll_enable_tx_underflow_int(spi_hw_t * hw)94 static inline void spi_ll_enable_tx_underflow_int(spi_hw_t *hw)
95 {
96 	hw->ctrl.tx_udf_int_en = 1;
97 }
98 
spi_ll_disable_tx_underflow_int(spi_hw_t * hw)99 static inline void spi_ll_disable_tx_underflow_int(spi_hw_t *hw)
100 {
101 	hw->ctrl.tx_udf_int_en = 0;
102 }
103 
spi_ll_enable_rx_overflow_int(spi_hw_t * hw)104 static inline void spi_ll_enable_rx_overflow_int(spi_hw_t *hw)
105 {
106 	hw->ctrl.rx_ovf_int_en = 1;
107 }
108 
spi_ll_disable_rx_overflow_int(spi_hw_t * hw)109 static inline void spi_ll_disable_rx_overflow_int(spi_hw_t *hw)
110 {
111 	hw->ctrl.rx_ovf_int_en = 0;
112 }
113 
spi_ll_enable_tx_fifo_int(spi_hw_t * hw)114 static inline void spi_ll_enable_tx_fifo_int(spi_hw_t *hw)
115 {
116 	hw->ctrl.tx_fifo_int_en = 1;
117 }
118 
spi_ll_disable_tx_fifo_int(spi_hw_t * hw)119 static inline void spi_ll_disable_tx_fifo_int(spi_hw_t *hw)
120 {
121 	hw->ctrl.tx_fifo_int_en = 0;
122 }
123 
spi_ll_enable_rx_fifo_int(spi_hw_t * hw)124 static inline void spi_ll_enable_rx_fifo_int(spi_hw_t *hw)
125 {
126 	hw->ctrl.rx_fifo_int_en = 1;
127 }
128 
spi_ll_disable_rx_fifo_int(spi_hw_t * hw)129 static inline void spi_ll_disable_rx_fifo_int(spi_hw_t *hw)
130 {
131 	hw->ctrl.rx_fifo_int_en = 0;
132 }
133 
spi_ll_set_clk_div(spi_hw_t * hw,uint32_t clk_div)134 static inline void spi_ll_set_clk_div(spi_hw_t *hw, uint32_t clk_div)
135 {
136 	hw->ctrl.clk_rate = clk_div & SPI_F_CLK_DIV_M;
137 }
138 
spi_ll_enable_slave_release_int(spi_hw_t * hw)139 static inline void spi_ll_enable_slave_release_int(spi_hw_t *hw)
140 {
141 	hw->ctrl.slave_release_int_en = 1;
142 }
143 
spi_ll_disable_slave_release_int(spi_hw_t * hw)144 static inline void spi_ll_disable_slave_release_int(spi_hw_t *hw)
145 {
146 	hw->ctrl.slave_release_int_en = 0;
147 }
148 
spi_ll_set_wire_mode(spi_hw_t * hw,spi_wire_mode_t wire_mode)149 static inline void spi_ll_set_wire_mode(spi_hw_t *hw, spi_wire_mode_t wire_mode)
150 {
151 	hw->ctrl.wire3_en = wire_mode;
152 }
153 
spi_ll_set_bit_width(spi_hw_t * hw,spi_bit_width_t bit_width)154 static inline void spi_ll_set_bit_width(spi_hw_t *hw, spi_bit_width_t bit_width)
155 {
156 	hw->ctrl.bit_width = bit_width;
157 }
158 
spi_ll_set_first_bit(spi_hw_t * hw,spi_bit_order_t first_bit)159 static inline void spi_ll_set_first_bit(spi_hw_t *hw, spi_bit_order_t first_bit)
160 {
161 	hw->ctrl.lsb_first_en = first_bit;
162 }
163 
spi_ll_set_cpol(spi_hw_t * hw,spi_polarity_t cpol)164 static inline void spi_ll_set_cpol(spi_hw_t *hw, spi_polarity_t cpol)
165 {
166 	hw->ctrl.cpol = cpol;
167 }
168 
spi_ll_set_cpha(spi_hw_t * hw,spi_phase_t cpha)169 static inline void spi_ll_set_cpha(spi_hw_t *hw, spi_phase_t cpha)
170 {
171 	hw->ctrl.cpha = cpha;
172 }
173 
spi_ll_set_role(spi_hw_t * hw,spi_role_t role)174 static inline void spi_ll_set_role(spi_hw_t *hw, spi_role_t role)
175 {
176 	hw->ctrl.master_en = role;
177 }
178 
spi_ll_set_role_master(spi_hw_t * hw)179 static inline void spi_ll_set_role_master(spi_hw_t *hw)
180 {
181 	hw->ctrl.master_en = 1;
182 }
183 
spi_ll_set_role_slave(spi_hw_t * hw)184 static inline void spi_ll_set_role_slave(spi_hw_t *hw)
185 {
186 	hw->ctrl.master_en = 0;
187 }
188 
spi_ll_is_role_master(spi_hw_t * hw)189 static inline bool spi_ll_is_role_master(spi_hw_t *hw)
190 {
191 	return !!(hw->ctrl.master_en);
192 }
193 
spi_ll_is_role_slave(spi_hw_t * hw)194 static inline bool spi_ll_is_role_slave(spi_hw_t *hw)
195 {
196 	return !(hw->ctrl.master_en);
197 }
198 
spi_ll_enable_tx(spi_hw_t * hw)199 static inline void spi_ll_enable_tx(spi_hw_t *hw)
200 {
201 	hw->cfg.tx_en = 1;
202 }
203 
spi_ll_disable_tx(spi_hw_t * hw)204 static inline void spi_ll_disable_tx(spi_hw_t *hw)
205 {
206 	hw->cfg.tx_en = 0;
207 }
208 
spi_ll_enable_rx(spi_hw_t * hw)209 static inline void spi_ll_enable_rx(spi_hw_t *hw)
210 {
211 	hw->cfg.rx_en = 1;
212 }
213 
spi_ll_disable_rx(spi_hw_t * hw)214 static inline void spi_ll_disable_rx(spi_hw_t *hw)
215 {
216 	hw->cfg.rx_en = 0;
217 }
218 
spi_ll_enable_tx_finish_int(spi_hw_t * hw)219 static inline void spi_ll_enable_tx_finish_int(spi_hw_t *hw)
220 {
221 	hw->cfg.tx_finish_int_en = 1;
222 }
223 
spi_ll_disable_tx_finish_int(spi_hw_t * hw)224 static inline void spi_ll_disable_tx_finish_int(spi_hw_t *hw)
225 {
226 	hw->cfg.tx_finish_int_en = 0;
227 }
228 
spi_ll_enable_rx_finish_int(spi_hw_t * hw)229 static inline void spi_ll_enable_rx_finish_int(spi_hw_t *hw)
230 {
231 	hw->cfg.rx_finish_int_en = 1;
232 }
233 
spi_ll_disable_rx_finish_int(spi_hw_t * hw)234 static inline void spi_ll_disable_rx_finish_int(spi_hw_t *hw)
235 {
236 	hw->cfg.rx_finish_int_en = 0;
237 }
238 
spi_ll_set_tx_trans_len(spi_hw_t * hw,uint32_t len)239 static inline void spi_ll_set_tx_trans_len(spi_hw_t *hw, uint32_t len)
240 {
241 	if (hw->ctrl.bit_width == SPI_BIT_WIDTH_16BITS) {
242 		len = len / 2;
243 	}
244 	hw->cfg.tx_trans_len = len & SPI_F_TX_TRANS_LEN_M;
245 }
246 
spi_ll_set_rx_trans_len(spi_hw_t * hw,uint32_t len)247 static inline void spi_ll_set_rx_trans_len(spi_hw_t *hw, uint32_t len)
248 {
249 	if (hw->ctrl.bit_width == SPI_BIT_WIDTH_16BITS) {
250 		len = len / 2;
251 	}
252 	hw->cfg.rx_trans_len = len & SPI_F_RX_TRANS_LEN_M;
253 }
254 
spi_ll_clear_int_status(spi_hw_t * hw)255 static inline void spi_ll_clear_int_status(spi_hw_t *hw)
256 {
257 	hw->int_status.tx_fifo_int = 1;
258 	hw->int_status.rx_fifo_int = 1;
259 	hw->int_status.slave_release_int = 1;
260 	hw->int_status.tx_underflow_int = 1;
261 	hw->int_status.rx_overflow_int = 1;
262 }
263 
spi_ll_clear_slave_release_int_status(spi_hw_t * hw)264 static inline void spi_ll_clear_slave_release_int_status(spi_hw_t *hw)
265 {
266 	hw->int_status.slave_release_int = 1;
267 }
268 
spi_ll_reset_slave_release_int_status_to_default(spi_hw_t * hw)269 static inline void spi_ll_reset_slave_release_int_status_to_default(spi_hw_t *hw)
270 {
271 	hw->int_status.slave_release_int = 0;
272 }
273 
spi_ll_clear_tx_underflow_int_status(spi_hw_t * hw)274 static inline void spi_ll_clear_tx_underflow_int_status(spi_hw_t *hw)
275 {
276 	hw->int_status.tx_underflow_int = 1;
277 }
278 
spi_ll_clear_rx_overflow_int_status(spi_hw_t * hw)279 static inline void spi_ll_clear_rx_overflow_int_status(spi_hw_t *hw)
280 {
281 	hw->int_status.rx_overflow_int = 1;
282 }
283 
spi_ll_get_interrupt_status(spi_hw_t * hw)284 static inline uint32_t spi_ll_get_interrupt_status(spi_hw_t *hw)
285 {
286 	return hw->int_status.v;
287 }
288 
spi_ll_clear_interrupt_status(spi_hw_t * hw,uint32_t status)289 static inline void spi_ll_clear_interrupt_status(spi_hw_t *hw, uint32_t status)
290 {
291 	hw->int_status.v = status;
292 }
293 
spi_ll_is_tx_fifo_wr_ready(spi_hw_t * hw)294 static inline bool spi_ll_is_tx_fifo_wr_ready(spi_hw_t *hw)
295 {
296 	return !!(hw->int_status.tx_fifo_wr_ready);
297 }
298 
spi_ll_is_rx_fifo_rd_ready(spi_hw_t * hw)299 static inline bool spi_ll_is_rx_fifo_rd_ready(spi_hw_t *hw)
300 {
301 	return !!(hw->int_status.rx_fifo_rd_ready);
302 }
303 
spi_ll_is_tx_fifo_int_triggered(spi_hw_t * hw)304 static inline bool spi_ll_is_tx_fifo_int_triggered(spi_hw_t *hw)
305 {
306 	return !!(hw->int_status.tx_fifo_int);
307 }
308 
spi_ll_is_rx_fifo_int_triggered(spi_hw_t * hw)309 static inline bool spi_ll_is_rx_fifo_int_triggered(spi_hw_t *hw)
310 {
311 	return !!(hw->int_status.rx_fifo_int);
312 }
313 
spi_ll_is_tx_fifo_int_triggered_with_status(spi_hw_t * hw,uint32_t status)314 static inline bool spi_ll_is_tx_fifo_int_triggered_with_status(spi_hw_t *hw, uint32_t status)
315 {
316 	return !!(status & BIT(8));
317 }
318 
spi_ll_is_rx_fifo_int_triggered_with_status(spi_hw_t * hw,uint32_t status)319 static inline bool spi_ll_is_rx_fifo_int_triggered_with_status(spi_hw_t *hw, uint32_t status)
320 {
321 	return !!(status & BIT(9));
322 }
323 
spi_ll_is_slave_release_int_triggered(spi_hw_t * hw,uint32_t status)324 static inline bool spi_ll_is_slave_release_int_triggered(spi_hw_t *hw, uint32_t status)
325 {
326 	return !!(status & BIT(10));
327 }
328 
spi_ll_is_tx_finish_int_triggered(spi_hw_t * hw,uint32_t status)329 static inline bool spi_ll_is_tx_finish_int_triggered(spi_hw_t *hw, uint32_t status)
330 {
331 	return !!(status & BIT(13));
332 }
333 
spi_ll_is_rx_finish_int_triggered(spi_hw_t * hw,uint32_t status)334 static inline bool spi_ll_is_rx_finish_int_triggered(spi_hw_t *hw, uint32_t status)
335 {
336 	return !!(status & BIT(14));
337 }
338 
spi_ll_is_rx_overflow_int_triggered(spi_hw_t * hw,uint32_t status)339 static inline bool spi_ll_is_rx_overflow_int_triggered(spi_hw_t *hw, uint32_t status)
340 {
341 	return !!(status & BIT(12));
342 }
343 
spi_ll_is_tx_underflow_int_triggered(spi_hw_t * hw,uint32_t status)344 static inline bool spi_ll_is_tx_underflow_int_triggered(spi_hw_t *hw, uint32_t status)
345 {
346 	return !!(status & BIT(11));
347 }
348 
spi_ll_clear_tx_finish_int_status(spi_hw_t * hw)349 static inline void spi_ll_clear_tx_finish_int_status(spi_hw_t *hw)
350 {
351 	hw->int_status.tx_finish_int = 1;
352 }
353 
spi_ll_clear_rx_finish_int_status(spi_hw_t * hw)354 static inline void spi_ll_clear_rx_finish_int_status(spi_hw_t *hw)
355 {
356 	hw->int_status.rx_finish_int = 1;
357 }
358 
spi_ll_clear_tx_fifo_int_status(spi_hw_t * hw)359 static inline void spi_ll_clear_tx_fifo_int_status(spi_hw_t *hw)
360 {
361 	hw->int_status.tx_fifo_int = 1;
362 }
363 
spi_ll_clear_rx_fifo_int_status(spi_hw_t * hw)364 static inline void spi_ll_clear_rx_fifo_int_status(spi_hw_t *hw)
365 {
366 	hw->int_status.rx_fifo_int = 1;
367 }
368 
spi_ll_clear_tx_fifo(spi_hw_t * hw)369 static inline void spi_ll_clear_tx_fifo(spi_hw_t *hw)
370 {
371 	hw->int_status.tx_fifo_clr = 1;
372 }
373 
spi_ll_clear_rx_fifo(spi_hw_t * hw)374 static inline void spi_ll_clear_rx_fifo(spi_hw_t *hw)
375 {
376 	hw->int_status.rx_fifo_clr = 1;
377 }
378 
spi_ll_write_byte(spi_hw_t * hw,uint32_t data)379 static inline void spi_ll_write_byte(spi_hw_t *hw, uint32_t data)
380 {
381 	hw->data.fifo_data = data;
382 }
383 
spi_ll_read_byte(spi_hw_t * hw)384 static inline uint32_t spi_ll_read_byte(spi_hw_t *hw)
385 {
386 	return hw->data.fifo_data;
387 }
388 
389 #ifdef __cplusplus
390 }
391 #endif
392 
393