1 /*
2 * SPDX-FileCopyrightText: 2016 STMicroelectronics
3 * SPDX-FileCopyrightText: 2019-2025 SiFli Technologies(Nanjing) Co., Ltd
4 *
5 * SPDX-License-Identifier: BSD-3-Clause AND Apache-2.0
6 */
7
8 /* Includes ------------------------------------------------------------------*/
9 #include "bf0_hal.h"
10
11 /** @addtogroup BF0_HAL_Driver
12 * @{
13 */
14
15 #ifdef HAL_DSI_MODULE_ENABLED
16 #include "bf0_hal_dsi.h"
17
18 /** @addtogroup DSI
19 * @{
20 */
21
22 /* Private types -------------------------------------------------------------*/
23 /* Private defines -----------------------------------------------------------*/
24 /** @addtogroup DSI_Private_Constants
25 * @{
26 */
27 #define DSI_TIMEOUT_VALUE ((uint32_t)1000U) /* 1s */
28
29 #define DSI_ERROR_ACK_MASK (DSI_HOST_INT_MASK1_SOT | DSI_HOST_INT_MASK1_SOT_SYNC | DSI_HOST_INT_MASK1_EOT_SYNC | DSI_HOST_INT_MASK1_ESC_ENTRY_CMD | \
30 DSI_HOST_INT_MASK1_LPTX_SYNC | DSI_HOST_INT_MASK1_PERI_TIMEOUT | DSI_HOST_INT_MASK1_FALSE_CTRL | DSI_HOST_INT_MASK1_RSVD_INFO0 | \
31 DSI_HOST_INT_MASK1_SINGLE_ECC | DSI_HOST_INT_MASK1_MULTI_ECC | DSI_HOST_INT_MASK1_LONG_PKT_CHKSUM | DSI_HOST_INT_MASK1_UNDEF_DTYPE | \
32 DSI_HOST_INT_MASK1_INVALID_VCID | DSI_HOST_INT_MASK1_INVALID_TRANS_LEN | DSI_HOST_INT_MASK1_RSVD_INFO1 | DSI_HOST_INT_MASK1_DSI_PROTOCOL_VIO)
33 #define DSI_ERROR_PHY_MASK (DSI_HOST_INT_MASK1_D0_ERRESC | DSI_HOST_INT_MASK1_D0_ERRSYNCESC | DSI_HOST_INT_MASK1_D0_ERRCTRL | DSI_HOST_INT_MASK1_D0_LP0_CONT | DSI_HOST_INT_MASK1_D0_LP1_CONT)
34 #define DSI_ERROR_TX_MASK DSI_HOST_INT_MASK2_HSTX_TIMEOUT
35 #define DSI_ERROR_RX_MASK DSI_HOST_INT_MASK2_LPRX_TIMEOUT
36 #define DSI_ERROR_ECC_MASK (DSI_HOST_INT_MASK2_ECC_SINGLE | DSI_HOST_INT_MASK2_ECC_MULTI)
37 #define DSI_ERROR_CRC_MASK DSI_HOST_INT_MASK2_CRC
38 #define DSI_ERROR_PSE_MASK DSI_HOST_INT_MASK2_PACKET_SIZE
39 #define DSI_ERROR_EOT_MASK DSI_HOST_INT_MASK2_EOTP
40 #define DSI_ERROR_OVF_MASK (DSI_HOST_INT_MASK2_DBI_CMD_WR|DSI_HOST_INT_MASK2_DBI_PAYLOAD_WR|DSI_HOST_INT_MASK2_DBI_PAYLOAD_RD|DSI_HOST_INT_MASK2_DBI_PAYLOAD_RCV|DSI_HOST_INT_MASK2_DBI_INVALID_CMD)
41
42
43 #define DSI_ERROR_GEN_MASK (DSI_HOST_INT_MASK2_COM_CMD_WR | DSI_HOST_INT_MASK2_COM_PAYLOAD_WR | DSI_HOST_INT_MASK2_COM_PAYLOAD_SEND | DSI_HOST_INT_MASK2_COM_PAYLOAD_RD | DSI_HOST_INT_MASK2_COM_PAYLOAD_RCV)
44
45
46
47 #define DSI_LOG_D(...) //HAL_DBG_printf(__VA_ARGS__)
48 #define DSI_LOG_E(...) HAL_DBG_printf(__VA_ARGS__)
49
50 #define SHOW_BTA_LOG //For debug purpose
51
52 /**
53 * @}
54 */
55
56 typedef struct Freq2DLLMap
57 {
58 uint32_t freq;
59 uint8_t in_div2;
60 uint16_t stg;
61 uint8_t out_div2;
62
63 } *Freq2DLLMap_t;
64
65 #ifdef SF32LB55X
66 static const struct Freq2DLLMap DSI_Freq_DLL_map[] =
67 {
68 {DSI_FREQ_96Mbps, 1, 7, 0},
69 {DSI_FREQ_144Mbps, 1, 6, 0},
70 {DSI_FREQ_168Mbps, 1, 5, 0},
71 {DSI_FREQ_192Mbps, 1, 4, 0},
72 {DSI_FREQ_240Mbps, 1, 3, 0},
73 {DSI_FREQ_288Mbps, 1, 2, 0},
74 {DSI_FREQ_336Mbps, 1, 1, 0},
75 {DSI_FREQ_384Mbps, 1, 0, 0},
76 {DSI_FREQ_480Mbps, 0, 3, 0},
77 {DSI_FREQ_528Mbps, 0, 10, 0}
78 };
79
80 #else
81
82 static const struct Freq2DLLMap DSI_Freq_DLL_map[] =
83 {
84
85 {DSI_FREQ_96Mbps, 1, 3, 0},
86 {DSI_FREQ_144Mbps, 1, 5, 0},
87 {DSI_FREQ_168Mbps, 1, 6, 0},
88 {DSI_FREQ_192Mbps, 1, 7, 0},
89 {DSI_FREQ_240Mbps, 1, 9, 0},
90 {DSI_FREQ_288Mbps, 1, 11, 0},
91 {DSI_FREQ_336Mbps, 1, 13, 0},
92 {DSI_FREQ_384Mbps, 1, 15, 0},
93 {DSI_FREQ_480Mbps, 0, 9, 0},
94 {DSI_FREQ_528Mbps, 0, 10, 0}
95 };
96
97 #endif /* SF32LB55X */
98
99 typedef struct Freq2PhyCfgMap
100 {
101 uint32_t freq;
102 uint32_t ck_phase_sel; /*CK_LANE_CFG0*/
103 uint32_t ck_lpx_cnt;
104 uint32_t ck_prep_cnt;
105 uint32_t ck_zero_cnt;
106
107 uint32_t ck_pre_cnt; /*CK_LANE_CFG1*/
108 uint32_t ck_post_cnt;
109 uint32_t ck_trail_cnt;
110 uint32_t ck_hs_exit_cnt;
111
112 uint32_t ck_wakeup_cnt; /*CK_LANE_CFG2*/
113
114 uint32_t dx_lpx_cnt; /*D_LANE0_CFG0*/
115 uint32_t dx_hs_prep_cnt;
116 uint32_t dx_hs_zero_cnt;
117 uint32_t dx_hs_trail_cnt;
118
119
120 uint32_t dx_tasure_cnt; /*D_LANE0_CFG1*/
121 uint32_t dx_taget_cnt;
122 uint32_t dx_tago_cnt;
123 uint32_t dx_wakeup_cnt;
124 } *Freq2PhyCfgMap_t;
125
126 static const struct Freq2PhyCfgMap DSI_Freq_PHY_Cfg_map[] =
127 {
128 /* freq CK_LANE_CFG0 CK_LANE_CFG1 CK_LANE_CFG2 D_LANE0_CFG0 D_LANE0_CFG1 */
129 {DSI_FREQ_240Mbps, 0, 15, 15, 89, 7, 72, 19, 33, 20, 1, 2, 4, 2, 0, 4, 3, 20},
130 {DSI_FREQ_288Mbps, 0, 15, 15, 89, 7, 72, 19, 33, 20, 1, 2, 4, 2, 0, 4, 3, 20},
131 {DSI_FREQ_336Mbps, 2, 23, 23, 100, 23, 75, 21, 36, 30, 2, 2, 6, 3, 0, 4, 3, 20},
132 {DSI_FREQ_384Mbps, 0, 23, 23, 115, 23, 78, 26, 44, 40, 2, 3, 7, 3, 0, 4, 3, 20},
133 {DSI_FREQ_480Mbps, 0, 31, 31, 119, 23, 82, 30, 50, 50, 3, 3, 7, 5, 0, 4, 3, 20},
134 {DSI_FREQ_528Mbps, 2, 23, 23, 134, 23, 80, 28, 47, 40, 3, 3, 7, 4, 0, 4, 3, 20}
135 };
136
137 /* Private variables ---------------------------------------------------------*/
138 static uint8_t force_enable_err_report = 0; //Force enable DSI acknowledge
139
140 /* Private constants ---------------------------------------------------------*/
141 /* Private macros ------------------------------------------------------------*/
142 /* Private function prototypes -----------------------------------------------*/
143 static void DSI_ConfigPacketHeader(DSI_HOST_TypeDef *DSIx, uint32_t ChannelID, uint32_t DataType, uint32_t Data0, uint32_t Data1);
144
145 /* Private functions ---------------------------------------------------------*/
146 /**
147 * @brief Generic DSI packet header configuration
148 * @param DSIx Pointer to DSI register base
149 * @param ChannelID Virtual channel ID of the header packet
150 * @param DataType Packet data type of the header packet
151 * This parameter can be any value of :
152 * @ref DSI_SHORT_WRITE_PKT_Data_Type
153 * or @ref DSI_LONG_WRITE_PKT_Data_Type
154 * or @ref DSI_SHORT_READ_PKT_Data_Type
155 * or DSI_MAX_RETURN_PKT_SIZE
156 * @param Data0 Word count LSB
157 * @param Data1 Word count MSB
158 * @retval None
159 */
DSI_ConfigPacketHeader(DSI_HOST_TypeDef * DSIx,uint32_t ChannelID,uint32_t DataType,uint32_t Data0,uint32_t Data1)160 static void DSI_ConfigPacketHeader(DSI_HOST_TypeDef *DSIx,
161 uint32_t ChannelID,
162 uint32_t DataType,
163 uint32_t Data0,
164 uint32_t Data1)
165 {
166 /* Update the DSI packet header with new information */
167 DSIx->COM_INTF = (DataType | (ChannelID << DSI_HOST_COM_INTF_VID_Pos) | (Data0 << DSI_HOST_COM_INTF_LOW_DATA_Pos) | (Data1 << DSI_HOST_COM_INTF_HIGH_DATA_Pos));
168 }
169
170 /* Exported functions --------------------------------------------------------*/
171 /** @addtogroup DSI_Exported_Functions
172 * @{
173 */
174
175 /** @defgroup DSI_Group1 Initialization and Configuration functions
176 * @brief Initialization and Configuration functions
177 *
178 @verbatim
179 ===============================================================================
180 ##### Initialization and Configuration functions #####
181 ===============================================================================
182 [..] This section provides functions allowing to:
183 (+) Initialize and configure the DSI
184 (+) De-initialize the DSI
185
186 @endverbatim
187 * @{
188 */
189
190
GetDLLMap(uint32_t freq)191 static Freq2DLLMap_t GetDLLMap(uint32_t freq)
192 {
193 for (uint32_t i = 0; i < (sizeof(DSI_Freq_DLL_map) / sizeof(DSI_Freq_DLL_map[0])); i++)
194 {
195 if (freq == DSI_Freq_DLL_map[i].freq)
196 {
197 return (Freq2DLLMap_t)&DSI_Freq_DLL_map[i];
198 }
199 }
200
201 return NULL;
202 }
203
GetPHYCfgMap(uint32_t freq)204 static Freq2PhyCfgMap_t GetPHYCfgMap(uint32_t freq)
205 {
206 for (uint32_t i = 0; i < (sizeof(DSI_Freq_PHY_Cfg_map) / sizeof(DSI_Freq_PHY_Cfg_map[0])); i++)
207 {
208 if (freq == DSI_Freq_PHY_Cfg_map[i].freq)
209 {
210 return (Freq2PhyCfgMap_t)&DSI_Freq_PHY_Cfg_map[i];
211 }
212 }
213
214 return NULL;
215 }
216
217 /**
218 * @brief Initializes the DSI according to the specified
219 * parameters in the DSI_InitTypeDef and create the associated handle.
220 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
221 * the configuration information for the DSI.
222 * @retval HAL status
223 */
HAL_DSI_Init(DSI_HandleTypeDef * hdsi)224 HAL_StatusTypeDef HAL_DSI_Init(DSI_HandleTypeDef *hdsi)
225 {
226 uint32_t tickstart;
227 uint32_t unitIntervalx4;
228 uint32_t tempIDF;
229
230 /* Check the DSI handle allocation */
231 if (hdsi == NULL)
232 {
233 return HAL_ERROR;
234 }
235
236 /* Check function parameters */
237 //HAL_ASSERT(IS_DSI_PLL_NDIV(DLLInit->PLLNDIV));
238 //HAL_ASSERT(IS_DSI_PLL_IDF(DLLInit->PLLIDF));
239 //HAL_ASSERT(IS_DSI_PLL_ODF(DLLInit->PLLODF));
240 HAL_ASSERT(IS_DSI_AUTO_CLKLANE_CONTROL(hdsi->Init.AutomaticClockLaneControl));
241 HAL_ASSERT(IS_DSI_NUMBER_OF_LANES(hdsi->Init.NumberOfLanes));
242
243 HAL_RCC_EnableModule(RCC_MOD_DSIHOST);
244 HAL_RCC_EnableModule(RCC_MOD_DSIPHY);
245 HAL_RCC_ResetModule(RCC_MOD_DSIHOST);
246 HAL_RCC_ResetModule(RCC_MOD_DSIPHY);
247
248 if (hdsi->State == HAL_DSI_STATE_RESET)
249 {
250 /* Initialize the low level hardware */
251 HAL_DSI_MspInit(hdsi);
252 }
253
254 /* Change DSI peripheral state */
255 hdsi->State = HAL_DSI_STATE_BUSY;
256
257
258 /*************************** Set the PHY parameters ***************************/
259
260 /* Clock lane configuration */
261 hdsi->Instance->PHY_CTRL &= ~(DSI_HOST_PHY_CTRL_CKLANE_HSTXREQ | DSI_HOST_PHY_CTRL_CKLANE_AUTO_CTRL);
262 hdsi->Instance->PHY_CTRL |= (DSI_HOST_PHY_CTRL_CKLANE_HSTXREQ | hdsi->Init.AutomaticClockLaneControl);
263
264 /* Configure the number of active data lanes */
265 hdsi->Instance->PHY_CFG1 &= ~DSI_HOST_PHY_CFG1_NUM_ACT_LANE;
266 hdsi->Instance->PHY_CFG1 |= hdsi->Init.NumberOfLanes << DSI_HOST_PHY_CFG1_NUM_ACT_LANE_Pos;
267
268
269 /************************ Set the DSI clock parameters ************************/
270
271 {
272 /* Set the TX escape clock division factor */
273 hdsi->Instance->CTRL &= ~DSI_HOST_CTRL_ESC_DIV;
274 hdsi->Instance->CTRL |= (hdsi->Init.TXEscapeCkdiv << DSI_HOST_CTRL_ESC_DIV_Pos); //escape clk = dsi_phy_clk / 2(DDR) / 8 / ESC_DIV
275 }
276 #ifdef DSI_FIX_ME //PHY timing
277 /* Calculate the bit period in high-speed mode in unit of 0.25 ns (UIX4) */
278 /* The equation is : UIX4 = IntegerPart( (1000/F_PHY_Mhz) * 4 ) */
279 /* Where : F_PHY_Mhz = (NDIV * HSE_Mhz) / (IDF * ODF) */
280 tempIDF = (DLLInit->PLLIDF > 0U) ? DLLInit->PLLIDF : 1U;
281 unitIntervalx4 = (4000000U * tempIDF * (1U << DLLInit->PLLODF)) / ((HSE_VALUE / 1000U) * DLLInit->PLLNDIV);
282
283 /* Set the bit period in high-speed mode */
284 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_UIX4;
285 hdsi->Instance->WPCR[0U] |= unitIntervalx4;
286
287 #else
288
289 /* Enable the DSI host */
290 //__HAL_DSI_ENABLE(hdsi);
291
292 /* D-PHY clock and digital enable*/
293 hdsi->Instance->PHY_CTRL |= (DSI_HOST_PHY_CTRL_CKLANE_ENABLE | DSI_HOST_PHY_CTRL_PHY_RSTN | DSI_HOST_PHY_CTRL_PLL_EN | DSI_HOST_PHY_CTRL_PHY_PD_N);
294
295 /**************** Turn on the regulator and enable the DSI PLL ****************/
296
297 /* Enable the analog power */
298 __HAL_DSI_ANA_ENABLE(hdsi);
299
300 /* wait for 100 us*/
301 HAL_Delay_us(100U);
302
303 #if 1
304 /*start calib */
305 hdsi->PHY_Instance->BIAS_CAL |= DSI_PHY_BIAS_CAL_AUTO_CLK_DIV_Msk;
306 hdsi->PHY_Instance->BIAS_CAL |= DSI_PHY_BIAS_CAL_START;
307 uint32_t start_tick = HAL_GetTick();
308 do
309 {
310 if (hdsi->PHY_Instance->BIAS_CAL & DSI_PHY_BIAS_CAL_DONE) break;
311 }
312 while (HAL_GetTick() - start_tick < 100);
313 HAL_ASSERT(hdsi->PHY_Instance->BIAS_CAL & DSI_PHY_BIAS_CAL_DONE);
314 #else
315 hdsi->PHY_Instance->BIAS_CAL &= ~DSI_PHY_BIAS_CAL_RSET_MANUAL_Msk;
316 hdsi->PHY_Instance->BIAS_CAL |= DSI_PHY_BIAS_CAL_RCAL_EN_MANUAL | (0x3 << DSI_PHY_BIAS_CAL_RSET_MANUAL_Pos);
317 #endif
318
319
320
321 // phy power control
322 hdsi->PHY_Instance->CK_LANE_CTRL = (1 << DSI_PHY_CK_LANE_CTRL_HSTXPON_Pos) |
323 (1 << DSI_PHY_CK_LANE_CTRL_LPTXPON_Pos) |
324 (0 << DSI_PHY_CK_LANE_CTRL_LPRXPONLP_Pos) |
325 (0 << DSI_PHY_CK_LANE_CTRL_LPRXPONULP_Pos) |
326 (0 << DSI_PHY_CK_LANE_CTRL_LPRXPONCD_Pos) |
327 (1 << DSI_PHY_CK_LANE_CTRL_BIASPON_Pos);
328
329 hdsi->PHY_Instance->D_LANE0_CTRL = (1 << DSI_PHY_D_LANE0_CTRL_HSTXPON_Pos) |
330 (1 << DSI_PHY_D_LANE0_CTRL_LPTXPON_Pos) |
331 (1 << DSI_PHY_D_LANE0_CTRL_LPRXPONLP_Pos) |
332 (0 << DSI_PHY_D_LANE0_CTRL_LPRXPONULP_Pos) |
333 (0 << DSI_PHY_D_LANE0_CTRL_LPRXPONCD_Pos) |
334 (1 << DSI_PHY_D_LANE0_CTRL_BIASPON_Pos) |
335 (1 << DSI_PHY_D_LANE0_CTRL_LPTXPU_BYPASS_Pos) |
336 (0 << DSI_PHY_D_LANE0_CTRL_LPTXPU_SET_Pos);
337
338
339
340 if (DSI_TWO_DATA_LANES == hdsi->Init.NumberOfLanes)
341 {
342 hdsi->PHY_Instance->D_LANE1_CTRL = hdsi->PHY_Instance->D_LANE0_CTRL;
343 }
344
345 #endif
346
347 /****************************** Error management *****************************/
348
349 /* Disable all error interrupts and reset the Error Mask */
350 hdsi->Instance->INT_MASK1 = 0U;
351 hdsi->Instance->INT_MASK2 = 0U;
352 hdsi->ErrorMsk = 0U;
353
354 /* Initialise the error code */
355 hdsi->ErrorCode = HAL_DSI_ERROR_NONE;
356
357 /* Initialize the DSI state*/
358 hdsi->State = HAL_DSI_STATE_READY;
359
360 return HAL_OK;
361 }
362
363
364
365 /**
366 * @brief De-initializes the DSI peripheral registers to their default reset
367 * values.
368 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
369 * the configuration information for the DSI.
370 * @retval HAL status
371 */
HAL_DSI_DeInit(DSI_HandleTypeDef * hdsi)372 HAL_StatusTypeDef HAL_DSI_DeInit(DSI_HandleTypeDef *hdsi)
373 {
374 /* Check the DSI handle allocation */
375 if (hdsi == NULL)
376 {
377 return HAL_ERROR;
378 }
379
380 /* Change DSI peripheral state */
381 hdsi->State = HAL_DSI_STATE_BUSY;
382
383 /* Disable the DSI PHY */
384 __HAL_DSI_PHY_DISABLE(hdsi);
385
386 /* Disable the DSI host */
387 __HAL_DSI_DISABLE(hdsi);
388
389 /* D-PHY clock and digital disable */
390 hdsi->Instance->PHY_CTRL &= ~(DSI_HOST_PHY_CTRL_CKLANE_ENABLE /* | DSI_HOST_PHY_CTRL_PHY_RSTN*/);
391
392 /* Turn off the DSI PLL */
393 __HAL_DSI_PLL_DISABLE(hdsi);
394
395 /* Disable the analog power */
396 __HAL_DSI_ANA_DISABLE(hdsi);
397
398 /* DeInit the low level hardware */
399 HAL_DSI_MspDeInit(hdsi);
400
401 /* Initialise the error code */
402 hdsi->ErrorCode = HAL_DSI_ERROR_NONE;
403
404 /* Initialize the DSI state*/
405 hdsi->State = HAL_DSI_STATE_RESET;
406
407 /* Release Lock */
408 __HAL_UNLOCK(hdsi);
409
410 return HAL_OK;
411 }
412
413 /**
414 * @brief Enable the error monitor flags
415 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
416 * the configuration information for the DSI.
417 * @param ActiveErrors indicates which error interrupts will be enabled.
418 * This parameter can be any combination of @ref DSI_Error_Data_Type.
419 * @retval HAL status
420 */
HAL_DSI_ConfigErrorMonitor(DSI_HandleTypeDef * hdsi,uint32_t ActiveErrors)421 HAL_StatusTypeDef HAL_DSI_ConfigErrorMonitor(DSI_HandleTypeDef *hdsi, uint32_t ActiveErrors)
422 {
423 /* Process locked */
424 __HAL_LOCK(hdsi);
425
426 hdsi->Instance->INT_MASK1 = 0U;
427 hdsi->Instance->INT_MASK2 = 0U;
428
429 /* Store active errors to the handle */
430 hdsi->ErrorMsk = ActiveErrors;
431
432 if ((ActiveErrors & HAL_DSI_ERROR_ACK) != RESET)
433 {
434 /* Enable the interrupt generation on selected errors */
435 hdsi->Instance->INT_MASK1 |= DSI_ERROR_ACK_MASK;
436 }
437
438 if ((ActiveErrors & HAL_DSI_ERROR_PHY) != RESET)
439 {
440 /* Enable the interrupt generation on selected errors */
441 hdsi->Instance->INT_MASK1 |= DSI_ERROR_PHY_MASK;
442 }
443
444 if ((ActiveErrors & HAL_DSI_ERROR_TX) != RESET)
445 {
446 /* Enable the interrupt generation on selected errors */
447 hdsi->Instance->INT_MASK2 |= DSI_ERROR_TX_MASK;
448 }
449
450 if ((ActiveErrors & HAL_DSI_ERROR_RX) != RESET)
451 {
452 /* Enable the interrupt generation on selected errors */
453 hdsi->Instance->INT_MASK2 |= DSI_ERROR_RX_MASK;
454 }
455
456 if ((ActiveErrors & HAL_DSI_ERROR_ECC) != RESET)
457 {
458 /* Enable the interrupt generation on selected errors */
459 hdsi->Instance->INT_MASK2 |= DSI_ERROR_ECC_MASK;
460 }
461
462 if ((ActiveErrors & HAL_DSI_ERROR_CRC) != RESET)
463 {
464 /* Enable the interrupt generation on selected errors */
465 hdsi->Instance->INT_MASK2 |= DSI_ERROR_CRC_MASK;
466 }
467
468 if ((ActiveErrors & HAL_DSI_ERROR_PSE) != RESET)
469 {
470 /* Enable the interrupt generation on selected errors */
471 hdsi->Instance->INT_MASK2 |= DSI_ERROR_PSE_MASK;
472 }
473
474 if ((ActiveErrors & HAL_DSI_ERROR_EOT) != RESET)
475 {
476 /* Enable the interrupt generation on selected errors */
477 hdsi->Instance->INT_MASK2 |= DSI_ERROR_EOT_MASK;
478 }
479
480 if ((ActiveErrors & HAL_DSI_ERROR_OVF) != RESET)
481 {
482 /* Enable the interrupt generation on selected errors */
483 hdsi->Instance->INT_MASK2 |= DSI_ERROR_OVF_MASK;
484 }
485
486 if ((ActiveErrors & HAL_DSI_ERROR_GEN) != RESET)
487 {
488 /* Enable the interrupt generation on selected errors */
489 hdsi->Instance->INT_MASK2 |= DSI_ERROR_GEN_MASK;
490 }
491
492 /* Process Unlocked */
493 __HAL_UNLOCK(hdsi);
494
495 return HAL_OK;
496 }
497
498 /**
499 * @brief Initializes the DSI MSP.
500 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
501 * the configuration information for the DSI.
502 * @retval None
503 */
HAL_DSI_MspInit(DSI_HandleTypeDef * hdsi)504 __weak void HAL_DSI_MspInit(DSI_HandleTypeDef *hdsi)
505 {
506 /* Prevent unused argument(s) compilation warning */
507 UNUSED(hdsi);
508 /* NOTE : This function Should not be modified, when the callback is needed,
509 the HAL_DSI_MspInit could be implemented in the user file
510 */
511 }
512
513 /**
514 * @brief De-initializes the DSI MSP.
515 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
516 * the configuration information for the DSI.
517 * @retval None
518 */
HAL_DSI_MspDeInit(DSI_HandleTypeDef * hdsi)519 __weak void HAL_DSI_MspDeInit(DSI_HandleTypeDef *hdsi)
520 {
521 /* Prevent unused argument(s) compilation warning */
522 UNUSED(hdsi);
523 /* NOTE : This function Should not be modified, when the callback is needed,
524 the HAL_DSI_MspDeInit could be implemented in the user file
525 */
526 }
527
528 /**
529 * @}
530 */
531
532 /** @defgroup DSI_Group2 IO operation functions
533 * @brief IO operation functions
534 *
535 @verbatim
536 ===============================================================================
537 ##### IO operation functions #####
538 ===============================================================================
539 [..] This section provides function allowing to:
540 (+) Handle DSI interrupt request
541
542 @endverbatim
543 * @{
544 */
545 /**
546 * @brief Handles DSI interrupt request.
547 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
548 * the configuration information for the DSI.
549 * @retval HAL status
550 */
551 uint32_t prev_IntStatus1 = 0;
552 uint32_t IntStatus1_cnt = 0;
553 extern void rt_kprintf(const char *fmt, ...);
554
HAL_DSI_IRQHandler(DSI_HandleTypeDef * hdsi)555 void HAL_DSI_IRQHandler(DSI_HandleTypeDef *hdsi)
556 {
557 uint32_t IntStatus1, IntStatus2;
558
559
560 #if 0
561 /* Tearing Effect Interrupt management ***************************************/
562 if (__HAL_DSI_GET_FLAG(hdsi, DSI_FLAG_TE) != RESET)
563 {
564 if (__HAL_DSI_GET_IT_SOURCE(hdsi, DSI_IT_TE) != RESET)
565 {
566 /* Clear the Tearing Effect Interrupt Flag */
567 __HAL_DSI_CLEAR_FLAG(hdsi, DSI_FLAG_TE);
568
569 /* Tearing Effect Callback */
570 HAL_DSI_TearingEffectCallback(hdsi);
571 }
572 }
573
574 /* End of Refresh Interrupt management ***************************************/
575 if (__HAL_DSI_GET_FLAG(hdsi, DSI_FLAG_ER) != RESET)
576 {
577 if (__HAL_DSI_GET_IT_SOURCE(hdsi, DSI_IT_ER) != RESET)
578 {
579 /* Clear the End of Refresh Interrupt Flag */
580 __HAL_DSI_CLEAR_FLAG(hdsi, DSI_FLAG_ER);
581
582 /* End of Refresh Callback */
583 HAL_DSI_EndOfRefreshCallback(hdsi);
584 }
585 }
586 #endif
587
588
589 /* Error Interrupts management ***********************************************/
590 if (hdsi->ErrorMsk != 0U)
591 {
592 IntStatus1 = hdsi->Instance->INT_STAT1;
593 IntStatus1 &= hdsi->Instance->INT_MASK1;
594 IntStatus2 = hdsi->Instance->INT_STAT2;
595 IntStatus2 &= hdsi->Instance->INT_MASK2;
596
597
598 #if 0
599 if ((prev_IntStatus1 != IntStatus1) || (IntStatus1_cnt > 100000))
600 {
601
602 rt_kprintf("\nHAL_DSI_IRQHandler ist0=0x%x, ist1=0x%x\n", IntStatus1, IntStatus2);
603 IntStatus1_cnt = 1;
604 prev_IntStatus1 = IntStatus1;
605 }
606 else
607 {
608 IntStatus1_cnt++;
609 }
610 #endif /* 0 */
611
612 if ((IntStatus1 & DSI_ERROR_ACK_MASK) != RESET)
613 {
614 hdsi->ErrorCode |= HAL_DSI_ERROR_ACK;
615 DSI_LOG_E("HAL_DSI_ERROR_ACK");
616 }
617
618 if ((IntStatus1 & DSI_ERROR_PHY_MASK) != RESET)
619 {
620 hdsi->ErrorCode |= HAL_DSI_ERROR_PHY;
621 DSI_LOG_E("HAL_DSI_ERROR_PHY");
622 }
623
624 if ((IntStatus2 & DSI_ERROR_TX_MASK) != RESET)
625 {
626 hdsi->ErrorCode |= HAL_DSI_ERROR_TX;
627 DSI_LOG_E("HAL_DSI_ERROR_TX");
628 }
629
630 if ((IntStatus2 & DSI_ERROR_RX_MASK) != RESET)
631 {
632 hdsi->ErrorCode |= HAL_DSI_ERROR_RX;
633 DSI_LOG_E("HAL_DSI_ERROR_RX");
634 }
635
636 if ((IntStatus2 & DSI_ERROR_ECC_MASK) != RESET)
637 {
638 hdsi->ErrorCode |= HAL_DSI_ERROR_ECC;
639 DSI_LOG_E("HAL_DSI_ERROR_ECC");
640 }
641
642 if ((IntStatus2 & DSI_ERROR_CRC_MASK) != RESET)
643 {
644 hdsi->ErrorCode |= HAL_DSI_ERROR_CRC;
645 DSI_LOG_E("HAL_DSI_ERROR_CRC");
646 }
647
648 if ((IntStatus2 & DSI_ERROR_PSE_MASK) != RESET)
649 {
650 hdsi->ErrorCode |= HAL_DSI_ERROR_PSE;
651 DSI_LOG_E("HAL_DSI_ERROR_PSE");
652 }
653
654 if ((IntStatus2 & DSI_ERROR_EOT_MASK) != RESET)
655 {
656 hdsi->ErrorCode |= HAL_DSI_ERROR_EOT;
657 DSI_LOG_E("HAL_DSI_ERROR_EOT");
658 }
659
660 if ((IntStatus2 & DSI_ERROR_OVF_MASK) != RESET)
661 {
662 hdsi->ErrorCode |= HAL_DSI_ERROR_OVF;
663 DSI_LOG_E("HAL_DSI_ERROR_OVF");
664 }
665
666 if ((IntStatus2 & DSI_ERROR_GEN_MASK) != RESET)
667 {
668 hdsi->ErrorCode |= HAL_DSI_ERROR_GEN;
669 DSI_LOG_E("HAL_DSI_ERROR_GEN");
670 }
671
672 /* Check only selected errors */
673 if (hdsi->ErrorCode != HAL_DSI_ERROR_NONE)
674 {
675 DSI_LOG_E("IntStatus1 =%x, IntStatus2 = %x", IntStatus1, IntStatus2);
676
677 /* DSI error interrupt user callback */
678 HAL_DSI_ErrorCallback(hdsi);
679 }
680 }
681 }
682
683
684
685 /**
686 * @brief Tearing Effect DSI callback.
687 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
688 * the configuration information for the DSI.
689 * @retval None
690 */
HAL_DSI_TearingEffectCallback(DSI_HandleTypeDef * hdsi)691 __weak void HAL_DSI_TearingEffectCallback(DSI_HandleTypeDef *hdsi)
692 {
693 /* Prevent unused argument(s) compilation warning */
694 UNUSED(hdsi);
695 /* NOTE : This function Should not be modified, when the callback is needed,
696 the HAL_DSI_TearingEffectCallback could be implemented in the user file
697 */
698 }
699
700 /**
701 * @brief End of Refresh DSI callback.
702 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
703 * the configuration information for the DSI.
704 * @retval None
705 */
HAL_DSI_EndOfRefreshCallback(DSI_HandleTypeDef * hdsi)706 __weak void HAL_DSI_EndOfRefreshCallback(DSI_HandleTypeDef *hdsi)
707 {
708 /* Prevent unused argument(s) compilation warning */
709 UNUSED(hdsi);
710 /* NOTE : This function Should not be modified, when the callback is needed,
711 the HAL_DSI_EndOfRefreshCallback could be implemented in the user file
712 */
713 }
714
715 /**
716 * @brief Operation Error DSI callback.
717 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
718 * the configuration information for the DSI.
719 * @retval None
720 */
HAL_DSI_ErrorCallback(DSI_HandleTypeDef * hdsi)721 __weak void HAL_DSI_ErrorCallback(DSI_HandleTypeDef *hdsi)
722 {
723 /* Prevent unused argument(s) compilation warning */
724 UNUSED(hdsi);
725 /* NOTE : This function Should not be modified, when the callback is needed,
726 the HAL_DSI_ErrorCallback could be implemented in the user file
727 */
728 }
729
730 /**
731 * @}
732 */
733
734 /** @defgroup DSI_Group3 Peripheral Control functions
735 * @brief Peripheral Control functions
736 *
737 @verbatim
738 ===============================================================================
739 ##### Peripheral Control functions #####
740 ===============================================================================
741 [..] This section provides functions allowing to:
742 (+) Configure the Generic interface read-back Virtual Channel ID
743 (+) Select video mode and configure the corresponding parameters
744 (+) Configure command transmission mode: High-speed or Low-power
745 (+) Configure the flow control
746 (+) Configure the DSI PHY timer
747 (+) Configure the DSI HOST timeout
748 (+) Configure the DSI HOST timeout
749 (+) Start/Stop the DSI module
750 (+) Refresh the display in command mode
751 (+) Controls the display color mode in Video mode
752 (+) Control the display shutdown in Video mode
753 (+) write short DCS or short Generic command
754 (+) write long DCS or long Generic command
755 (+) Read command (DCS or generic)
756 (+) Enter/Exit the Ultra Low Power Mode on data only (D-PHY PLL running)
757 (+) Enter/Exit the Ultra Low Power Mode on data only and clock (D-PHY PLL turned off)
758 (+) Start/Stop test pattern generation
759 (+) Slew-Rate And Delay Tuning
760 (+) Low-Power Reception Filter Tuning
761 (+) Activate an additional current path on all lanes to meet the SDDTx parameter
762 (+) Custom lane pins configuration
763 (+) Set custom timing for the PHY
764 (+) Force the Clock/Data Lane in TX Stop Mode
765 (+) Force LP Receiver in Low-Power Mode
766 (+) Force Data Lanes in RX Mode after a BTA
767 (+) Enable a pull-down on the lanes to prevent from floating states when unused
768 (+) Switch off the contention detection on data lanes
769
770 @endverbatim
771 * @{
772 */
773
774 /**
775 * @brief Configure the Generic interface read-back Virtual Channel ID.
776 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
777 * the configuration information for the DSI.
778 * @param VirtualChannelID Virtual channel ID
779 * @retval HAL status
780 */
HAL_DSI_SetGenericVCID(DSI_HandleTypeDef * hdsi,uint32_t VirtualChannelID)781 HAL_StatusTypeDef HAL_DSI_SetGenericVCID(DSI_HandleTypeDef *hdsi, uint32_t VirtualChannelID)
782 {
783 /* Process locked */
784 __HAL_LOCK(hdsi);
785
786 /* Update the GVCID register */
787 hdsi->Instance->COM_CFG &= ~DSI_HOST_COM_CFG_VID;
788 hdsi->Instance->COM_CFG |= VirtualChannelID;
789
790 /* Process unlocked */
791 __HAL_UNLOCK(hdsi);
792
793 return HAL_OK;
794 }
795
796
797 /**
798 * @brief Select video mode and configure the corresponding parameters
799 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
800 * the configuration information for the DSI.
801 * @param VidCfg pointer to a DSI_VidCfgTypeDef structure that contains
802 * the DSI video mode configuration parameters
803 * @retval HAL status
804 */
HAL_DSI_ConfigVideoMode(DSI_HandleTypeDef * hdsi,DSI_VidCfgTypeDef * VidCfg)805 HAL_StatusTypeDef HAL_DSI_ConfigVideoMode(DSI_HandleTypeDef *hdsi, DSI_VidCfgTypeDef *VidCfg)
806 {
807 /* Process locked */
808 __HAL_LOCK(hdsi);
809
810
811 #ifdef SF32LB58X
812
813 uint32_t cf;
814
815 if (DSI_RGB888 == VidCfg->ColorCoding)
816 cf = 5;
817 else if (DSI_RGB666 == VidCfg->ColorCoding)
818 cf = 3;
819 else if (DSI_RGB565 == VidCfg->ColorCoding)
820 cf = 0;
821 else
822 {
823 HAL_ASSERT(0); //Unknown format
824 }
825
826
827 hwp_dsi_host->DPI_CFG1 = (0 << DSI_HOST_DPI_CFG1_VID_Pos) |
828 (cf << DSI_HOST_DPI_CFG1_FORMAT_Pos) |
829 (0 << DSI_HOST_DPI_CFG1_LOOSE_EN_Pos) |
830 (0 << DSI_HOST_DPI_CFG1_D_EN_POL_Pos) |
831 (0 << DSI_HOST_DPI_CFG1_VSYNC_POL_Pos) |
832 (0 << DSI_HOST_DPI_CFG1_HSYNC_POL_Pos) |
833 (0 << DSI_HOST_DPI_CFG1_SHUTDOWN_POL_Pos) |
834 (0 << DSI_HOST_DPI_CFG1_COLORM_POL_Pos);
835 hwp_dsi_host->DPI_CFG2 = (0 << DSI_HOST_DPI_CFG2_INVACT_Pos) |
836 (0 << DSI_HOST_DPI_CFG2_OUTVACT_Pos);
837
838
839
840
841 hwp_dsi_host->VMODE_CFG1 = (VidCfg->Mode << DSI_HOST_VMODE_CFG1_VMODE_TYPE_Pos) | // 0: burst mode
842 (1 << DSI_HOST_VMODE_CFG1_LPVSA_EN_Pos) | // enable LP mode for VSA
843 (1 << DSI_HOST_VMODE_CFG1_LPVBP_EN_Pos) | // enable LP mode for VBP
844 (1 << DSI_HOST_VMODE_CFG1_LPVFP_EN_Pos) | // enable LP mode for VFP
845 (1 << DSI_HOST_VMODE_CFG1_LPVACT_EN_Pos) | // enable LP mode for VACT
846 (0 << DSI_HOST_VMODE_CFG1_LPHBP_EN_Pos) | // enable LP mode for HBP
847 (0 << DSI_HOST_VMODE_CFG1_LPHFP_EN_Pos) | // enable LP mode for HFP
848 (0 << DSI_HOST_VMODE_CFG1_BTA_ACK_EN_Pos) | // no ack at end of frame
849 (1 << DSI_HOST_VMODE_CFG1_LPCMD_EN_Pos) | // no command transmission in LP mode
850 (0 << DSI_HOST_VMODE_CFG1_VPG_EN_Pos) | // disable video pattern generation
851 (0 << DSI_HOST_VMODE_CFG1_VPG_MODE_Pos) | // no vpg mode
852 (0 << DSI_HOST_VMODE_CFG1_VPG_ORIENTATION_Pos) | // no vpg mode
853 (VidCfg->PacketSize << DSI_HOST_VMODE_CFG1_PKT_SIZE_Pos); // number of pixels per line in single video packet
854
855
856
857 HAL_ASSERT(VidCfg->NullPacketSize <= (DSI_HOST_VMODE_CFG2_NULL_SIZE_Msk >> DSI_HOST_VMODE_CFG2_NULL_SIZE_Pos));
858 hwp_dsi_host->VMODE_CFG2 = (VidCfg->NumberOfChunks << DSI_HOST_VMODE_CFG2_NUM_CHUNKS_Pos) | // video line is transimitted in single packet
859 (VidCfg->NullPacketSize << DSI_HOST_VMODE_CFG2_NULL_SIZE_Pos); // no null packet
860 hwp_dsi_host->VTIMER1 = (VidCfg->HorizontalSyncActive << DSI_HOST_VTIMER1_HSA_Pos) | // HSA cycles
861 (VidCfg->HorizontalBackPorch << DSI_HOST_VTIMER1_HBP_Pos); // HBP cycles
862 hwp_dsi_host->VTIMER2 = (VidCfg->HorizontalLine << DSI_HOST_VTIMER2_HLINE_Pos) | // HLINE cycles // HSA+HBP+HACT+HFP period
863 (VidCfg->VerticalSyncActive << DSI_HOST_VTIMER2_VSA_Pos); // VSA lines
864 hwp_dsi_host->VTIMER3 = (VidCfg->VerticalBackPorch << DSI_HOST_VTIMER3_VBP_Pos) | // VBP lines
865 (VidCfg->VerticalFrontPorch << DSI_HOST_VTIMER3_VFP_Pos); // VFP lines
866 hwp_dsi_host->VTIMER4 = (VidCfg->VerticalActive << DSI_HOST_VTIMER4_VACT_Pos); // VACT lines
867
868
869
870 /*******
871 Generate test pattern
872 *****************/
873 hwp_dsi_host->VMODE_CFG1 |= (0 << DSI_HOST_VMODE_CFG1_VPG_EN_Pos) | // Enable video pattern generation
874 (0 << DSI_HOST_VMODE_CFG1_VPG_MODE_Pos) | // 0: color bar, 1: ber pattern
875 (0 << DSI_HOST_VMODE_CFG1_VPG_ORIENTATION_Pos); // color bar orientation, 0: vertical 1: horizontal
876
877
878 #endif /* SF32LB58X */
879
880 /* Process unlocked */
881 __HAL_UNLOCK(hdsi);
882
883 return HAL_OK;
884 }
885
886 /**
887 * @brief Select adapted command mode and configure the corresponding parameters
888 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
889 * the configuration information for the DSI.
890 * @param CmdCfg pointer to a DSI_CmdCfgTypeDef structure that contains
891 * the DSI command mode configuration parameters
892 * @retval HAL status
893 */
HAL_DSI_ConfigAdaptedCommandMode(DSI_HandleTypeDef * hdsi,DSI_CmdCfgTypeDef * CmdCfg)894 HAL_StatusTypeDef HAL_DSI_ConfigAdaptedCommandMode(DSI_HandleTypeDef *hdsi, DSI_CmdCfgTypeDef *CmdCfg)
895 {
896 /* Process locked */
897 __HAL_LOCK(hdsi);
898
899 /* Check the parameters */
900 HAL_ASSERT(IS_DSI_COLOR_CODING(CmdCfg->ColorCoding));
901 //HAL_ASSERT(IS_DSI_TE_SOURCE(CmdCfg->TearingEffectSource));
902 //HAL_ASSERT(IS_DSI_TE_POLARITY(CmdCfg->TearingEffectPolarity));
903 //HAL_ASSERT(IS_DSI_AUTOMATIC_REFRESH(CmdCfg->AutomaticRefresh));
904 //HAL_ASSERT(IS_DSI_VS_POLARITY(CmdCfg->VSyncPol));
905 HAL_ASSERT(IS_DSI_TE_ACK_REQUEST(CmdCfg->TEAcknowledgeRequest));
906 //HAL_ASSERT(IS_DSI_DE_POLARITY(CmdCfg->DEPolarity));
907 //HAL_ASSERT(IS_DSI_VSYNC_POLARITY(CmdCfg->VSPolarity));
908 //HAL_ASSERT(IS_DSI_HSYNC_POLARITY(CmdCfg->HSPolarity));
909
910 /* Select command mode by setting CMDM and DSIM bits */
911 hdsi->Instance->MODE_CFG |= DSI_HOST_MODE_CFG_CMD_VIDEO_SEL;
912 #if 0//def DSI_FIX_ME LCDC config
913
914 hdsi->Instance->WCFGR &= ~DSI_WCFGR_DSIM;
915 hdsi->Instance->WCFGR |= DSI_WCFGR_DSIM;
916 #endif
917
918 /* Select the virtual channel for the LTDC interface traffic */
919 hdsi->Instance->DBI_CFG1 &= ~DSI_HOST_DBI_CFG1_VID;
920 hdsi->Instance->DBI_CFG1 |= CmdCfg->VirtualChannelID;
921 #ifndef SF32LB55X
922 hdsi->Instance->DCOM_INTF_CFG3 &= ~DSI_HOST_DCOM_INTF_CFG3_ID_Msk;
923 hdsi->Instance->DCOM_INTF_CFG3 |= CmdCfg->VirtualChannelID << DSI_HOST_DCOM_INTF_CFG3_ID_Pos;
924 #endif /* !SF32LB55X */
925
926
927
928 hdsi->Instance->DBI_CFG1 &= ~(DSI_HOST_DBI_CFG1_IFORMAT_Msk | DSI_HOST_DBI_CFG1_OFORMAT_Msk | DSI_HOST_DBI_CFG1_LUT_SIZE_Msk);
929 #ifndef SF32LB55X
930 hdsi->Instance->DCOM_INTF_CFG3 &= ~DSI_HOST_DCOM_INTF_CFG3_I_FORMAT_Msk;
931 #endif /* SF32LB55X */
932 if (DSI_RGB888 == CmdCfg->ColorCoding)
933 {
934 hdsi->Instance->DBI_CFG1 |= (11 << DSI_HOST_DBI_CFG1_IFORMAT_Pos) | // DBI input format 16-bit 24bpp option 1
935 (11 << DSI_HOST_DBI_CFG1_OFORMAT_Pos) | // DBI output format 16-bit 24bpp option 1
936 (0 << DSI_HOST_DBI_CFG1_LUT_SIZE_Pos); // 16-bit color display
937 #ifndef SF32LB55X
938 hdsi->Instance->DCOM_INTF_CFG3 |= 1 << DSI_HOST_DCOM_INTF_CFG3_I_FORMAT_Pos;
939 #endif /* SF32LB55X */
940 }
941 else if (DSI_RGB565 == CmdCfg->ColorCoding)
942 {
943 hdsi->Instance->DBI_CFG1 |= (8 << DSI_HOST_DBI_CFG1_IFORMAT_Pos) | // DBI input format 16-bit 16bpp option 1
944 (8 << DSI_HOST_DBI_CFG1_OFORMAT_Pos) | // DBI output format 16-bit 16bpp option 1
945 (0 << DSI_HOST_DBI_CFG1_LUT_SIZE_Pos); // 16-bit color display
946 #ifndef SF32LB55X
947 hdsi->Instance->DCOM_INTF_CFG3 |= 0 << DSI_HOST_DCOM_INTF_CFG3_I_FORMAT_Pos;
948 #endif /* SF32LB55X */
949
950 }
951 else
952 {
953 HAL_ASSERT(0); //fix me
954 }
955
956 #ifndef SF32LB55X
957 hdsi->Instance->DCOM_INTF_CFG3 &= ~DSI_HOST_DCOM_INTF_CFG3_DATA_TYPE_Msk;
958 hdsi->Instance->DCOM_INTF_CFG3 |= DSI_DCS_LONG_PKT_WRITE << DSI_HOST_DCOM_INTF_CFG3_DATA_TYPE_Pos;
959 #endif /* !SF32LB55X */
960
961 hdsi->Instance->DBI_CFG1 &= ~DSI_HOST_DBI_CFG1_PARTITIONING_EN_Msk; //// disable partitioning, 0 - use automatic partitioning
962
963 hdsi->Instance->DBI_CFG1 |= (1 << 15); // wr_cont_mode
964
965 //Set default write command size
966 hdsi->Instance->DBI_CFG2 &= ~DSI_HOST_DBI_CFG2_WR_SIZE_Msk;
967 hdsi->Instance->DBI_CFG2 |= (CmdCfg->CommandSize << DSI_HOST_DBI_CFG2_WR_SIZE_Pos);
968
969
970 //Allowed command size
971 hdsi->Instance->DBI_CFG2 &= ~DSI_HOST_DBI_CFG2_ALLOWED_SIZE_Msk;
972 //if (DSI_TWO_DATA_LANES == hdsi->Init.NumberOfLanes)
973
974 hdsi->Instance->DBI_CFG2 |= (163 << DSI_HOST_DBI_CFG2_ALLOWED_SIZE_Pos);
975
976 //else
977 // hdsi->Instance->DBI_CFG2 |= (120 << DSI_HOST_DBI_CFG2_ALLOWED_SIZE_Pos);
978
979
980 /* Configure the tearing effect acknowledge request */
981 hdsi->Instance->CMODE_CFG &= ~DSI_HOST_CMODE_CFG_FMARK_EN;
982 if (DSI_TE_DSILINK == CmdCfg->TearingEffectSource) hdsi->Instance->CMODE_CFG |= CmdCfg->TEAcknowledgeRequest;
983
984 /* Enable the Tearing Effect interrupt */
985 __HAL_DSI_ENABLE_IT(hdsi, DSI_IT_TE);
986
987 /* Enable the End of Refresh interrupt */
988 __HAL_DSI_ENABLE_IT(hdsi, DSI_IT_ER);
989
990 /* Process unlocked */
991 __HAL_UNLOCK(hdsi);
992
993 return HAL_OK;
994 }
995
996 /**
997 * @brief Configure command transmission mode: High-speed or Low-power
998 * and enable/disable acknowledge request after packet transmission
999 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1000 * the configuration information for the DSI.
1001 * @param LPCmd pointer to a DSI_LPCmdTypeDef structure that contains
1002 * the DSI command transmission mode configuration parameters
1003 * @retval HAL status
1004 */
HAL_DSI_ConfigCommand(DSI_HandleTypeDef * hdsi,DSI_LPCmdTypeDef * LPCmd)1005 HAL_StatusTypeDef HAL_DSI_ConfigCommand(DSI_HandleTypeDef *hdsi, DSI_LPCmdTypeDef *LPCmd)
1006 {
1007 /* Process locked */
1008 __HAL_LOCK(hdsi);
1009
1010 HAL_ASSERT(IS_DSI_LP_GSW0P(LPCmd->LPGenShortWriteNoP));
1011 HAL_ASSERT(IS_DSI_LP_GSW1P(LPCmd->LPGenShortWriteOneP));
1012 HAL_ASSERT(IS_DSI_LP_GSW2P(LPCmd->LPGenShortWriteTwoP));
1013 HAL_ASSERT(IS_DSI_LP_GSR0P(LPCmd->LPGenShortReadNoP));
1014 HAL_ASSERT(IS_DSI_LP_GSR1P(LPCmd->LPGenShortReadOneP));
1015 HAL_ASSERT(IS_DSI_LP_GSR2P(LPCmd->LPGenShortReadTwoP));
1016 HAL_ASSERT(IS_DSI_LP_GLW(LPCmd->LPGenLongWrite));
1017 HAL_ASSERT(IS_DSI_LP_DSW0P(LPCmd->LPDcsShortWriteNoP));
1018 HAL_ASSERT(IS_DSI_LP_DSW1P(LPCmd->LPDcsShortWriteOneP));
1019 HAL_ASSERT(IS_DSI_LP_DSR0P(LPCmd->LPDcsShortReadNoP));
1020 HAL_ASSERT(IS_DSI_LP_DLW(LPCmd->LPDcsLongWrite));
1021 HAL_ASSERT(IS_DSI_LP_MRDP(LPCmd->LPMaxReadPacket));
1022 HAL_ASSERT(IS_DSI_ACK_REQUEST(LPCmd->AcknowledgeRequest));
1023
1024 /* Select High-speed or Low-power for command transmission */
1025 hdsi->Instance->CMODE_CFG &= ~(DSI_HOST_CMODE_CFG_COM_SHORT_WR0 | \
1026 DSI_HOST_CMODE_CFG_COM_SHORT_WR1 | \
1027 DSI_HOST_CMODE_CFG_COM_SHORT_WR2 | \
1028 DSI_HOST_CMODE_CFG_COM_SHORT_RD0 | \
1029 DSI_HOST_CMODE_CFG_COM_SHORT_RD1 | \
1030 DSI_HOST_CMODE_CFG_COM_SHORT_RD2 | \
1031 DSI_HOST_CMODE_CFG_COM_LONG_WR | \
1032 DSI_HOST_CMODE_CFG_SHORT_WR0 | \
1033 DSI_HOST_CMODE_CFG_SHORT_WR1 | \
1034 DSI_HOST_CMODE_CFG_SHORT_RD0 | \
1035 DSI_HOST_CMODE_CFG_LONG_WR | \
1036 DSI_HOST_CMODE_CFG_MAX_RD_SIZE);
1037 hdsi->Instance->CMODE_CFG |= (LPCmd->LPGenShortWriteNoP | \
1038 LPCmd->LPGenShortWriteOneP | \
1039 LPCmd->LPGenShortWriteTwoP | \
1040 LPCmd->LPGenShortReadNoP | \
1041 LPCmd->LPGenShortReadOneP | \
1042 LPCmd->LPGenShortReadTwoP | \
1043 LPCmd->LPGenLongWrite | \
1044 LPCmd->LPDcsShortWriteNoP | \
1045 LPCmd->LPDcsShortWriteOneP | \
1046 LPCmd->LPDcsShortReadNoP | \
1047 LPCmd->LPDcsLongWrite | \
1048 LPCmd->LPMaxReadPacket);
1049
1050 /* Configure the acknowledge request after each packet transmission */
1051 hdsi->Instance->CMODE_CFG &= ~DSI_HOST_CMODE_CFG_ACK_REQ_EN_Msk;
1052
1053 if (force_enable_err_report)
1054 hdsi->Instance->CMODE_CFG |= DSI_ACKNOWLEDGE_ENABLE;
1055 else
1056 hdsi->Instance->CMODE_CFG |= LPCmd->AcknowledgeRequest;
1057
1058 /* Process unlocked */
1059 __HAL_UNLOCK(hdsi);
1060
1061 return HAL_OK;
1062 }
1063
1064 /**
1065 * @brief Force acknowledge enable for testcase
1066 * @param hdsi -
1067 * @return
1068 */
HAL_DSI_ForceEnableAck(void)1069 void HAL_DSI_ForceEnableAck(void)
1070 {
1071 force_enable_err_report = 1;
1072 }
1073
1074
1075 /**
1076 * @brief Force acknowledge enable for testcase
1077 * @param hdsi -
1078 * @return
1079 */
HAL_DSI_ISForceEnableAck(void)1080 uint8_t HAL_DSI_ISForceEnableAck(void)
1081 {
1082 return force_enable_err_report;
1083 }
1084
1085 /**
1086 * @brief Configure the flow control parameters
1087 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1088 * the configuration information for the DSI.
1089 * @param FlowControl flow control feature(s) to be enabled.
1090 * This parameter can be any combination of @ref DSI_FlowControl.
1091 * @retval HAL status
1092 */
HAL_DSI_ConfigFlowControl(DSI_HandleTypeDef * hdsi,uint32_t FlowControl)1093 HAL_StatusTypeDef HAL_DSI_ConfigFlowControl(DSI_HandleTypeDef *hdsi, uint32_t FlowControl)
1094 {
1095 /* Process locked */
1096 __HAL_LOCK(hdsi);
1097
1098 /* Check the parameters */
1099 HAL_ASSERT(IS_DSI_FLOW_CONTROL(FlowControl));
1100
1101 /* Set the DSI Host Protocol Configuration Register */
1102 hdsi->Instance->PKT_CFG &= ~DSI_FLOW_CONTROL_ALL;
1103 hdsi->Instance->PKT_CFG |= FlowControl;
1104
1105 /* Process unlocked */
1106 __HAL_UNLOCK(hdsi);
1107
1108 return HAL_OK;
1109 }
1110
1111 /**
1112 * @brief Configure the DSI PHY timer parameters
1113 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1114 * the configuration information for the DSI.
1115 * @param PhyTimers DSI_PHY_TimerTypeDef structure that contains
1116 * the DSI PHY timing parameters
1117 * @retval HAL status
1118 */
HAL_DSI_ConfigPhyTimer(DSI_HandleTypeDef * hdsi,DSI_PHY_TimerTypeDef * PhyTimers)1119 HAL_StatusTypeDef HAL_DSI_ConfigPhyTimer(DSI_HandleTypeDef *hdsi, DSI_PHY_TimerTypeDef *PhyTimers)
1120 {
1121 uint32_t maxTime;
1122 /* Process locked */
1123 __HAL_LOCK(hdsi);
1124
1125 maxTime = (PhyTimers->ClockLaneLP2HSTime > PhyTimers->ClockLaneHS2LPTime) ? PhyTimers->ClockLaneLP2HSTime : PhyTimers->ClockLaneHS2LPTime;
1126
1127 /* Clock lane timer configuration */
1128
1129 /* In Automatic Clock Lane control mode, the DSI Host can turn off the clock lane between two
1130 High-Speed transmission.
1131 To do so, the DSI Host calculates the time required for the clock lane to change from HighSpeed
1132 to Low-Power and from Low-Power to High-Speed.
1133 This timings are configured by the HS2LP_TIME and LP2HS_TIME in the DSI Host Clock Lane Timer Configuration Register (DSI_CLTCR).
1134 But the DSI Host is not calculating LP2HS_TIME + HS2LP_TIME but 2 x HS2LP_TIME.
1135
1136 Workaround : Configure HS2LP_TIME and LP2HS_TIME with the same value being the max of HS2LP_TIME or LP2HS_TIME.
1137 */
1138 hdsi->Instance->PHY_CFG1 &= ~(DSI_HOST_PHY_CFG1_CKLP2HS_TIMER | DSI_HOST_PHY_CFG1_CKHS2LP_TIMER);
1139 hdsi->Instance->PHY_CFG1 |= ((maxTime << DSI_HOST_PHY_CFG1_CKLP2HS_TIMER_Pos) | ((maxTime) << DSI_HOST_PHY_CFG1_CKHS2LP_TIMER_Pos));
1140
1141 /* Data lane timer configuration */
1142 hdsi->Instance->PHY_CFG2 &= ~(DSI_HOST_PHY_CFG2_MAX_RD_TIMER | DSI_HOST_PHY_CFG2_DATALP2HS_TIMER | DSI_HOST_PHY_CFG2_DATAHS2LP_TIMER);
1143 hdsi->Instance->PHY_CFG2 |= ((PhyTimers->DataLaneMaxReadTime << DSI_HOST_PHY_CFG2_MAX_RD_TIMER_Pos) | ((PhyTimers->DataLaneLP2HSTime) << DSI_HOST_PHY_CFG2_DATALP2HS_TIMER_Pos) | ((PhyTimers->DataLaneHS2LPTime) << DSI_HOST_PHY_CFG2_DATAHS2LP_TIMER_Pos));
1144
1145 /* Configure the wait period to request HS transmission after a stop state */
1146 hdsi->Instance->PHY_CFG1 &= ~DSI_HOST_PHY_CFG1_WAIT_TIMER;
1147 hdsi->Instance->PHY_CFG1 |= ((PhyTimers->StopWaitTime) << DSI_HOST_PHY_CFG1_WAIT_TIMER_Pos);
1148
1149 /* Process unlocked */
1150 __HAL_UNLOCK(hdsi);
1151
1152 return HAL_OK;
1153 }
1154
1155 /**
1156 * @brief Configure the DSI HOST timeout parameters
1157 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1158 * the configuration information for the DSI.
1159 * @param HostTimeouts DSI_HOST_TimeoutTypeDef structure that contains
1160 * the DSI host timeout parameters
1161 * @retval HAL status
1162 */
HAL_DSI_ConfigHostTimeouts(DSI_HandleTypeDef * hdsi,DSI_HOST_TimeoutTypeDef * HostTimeouts)1163 HAL_StatusTypeDef HAL_DSI_ConfigHostTimeouts(DSI_HandleTypeDef *hdsi, DSI_HOST_TimeoutTypeDef *HostTimeouts)
1164 {
1165 /* Process locked */
1166 __HAL_LOCK(hdsi);
1167
1168 /* Set the timeout clock division factor */
1169 hdsi->Instance->CTRL &= ~DSI_HOST_CTRL_TIMEOUT_DIV;
1170 hdsi->Instance->CTRL |= ((HostTimeouts->TimeoutCkdiv) << DSI_HOST_CTRL_TIMEOUT_DIV_Pos); //timeout clk = dsi_phy_clk / 2(DDR) / 8 / TO_DIV
1171
1172 /* High-speed transmission timeout */
1173 hdsi->Instance->ST_CNT_CFG1 &= ~DSI_HOST_ST_CNT_CFG1_HSTX_TIMEOUT;
1174 hdsi->Instance->ST_CNT_CFG1 |= ((HostTimeouts->HighSpeedTransmissionTimeout) << DSI_HOST_ST_CNT_CFG1_HSTX_TIMEOUT_Pos);
1175
1176 /* Low-power reception timeout */
1177 hdsi->Instance->ST_CNT_CFG1 &= ~DSI_HOST_ST_CNT_CFG1_LPRX_TIMEOUT;
1178 hdsi->Instance->ST_CNT_CFG1 |= HostTimeouts->LowPowerReceptionTimeout << DSI_HOST_ST_CNT_CFG1_LPRX_TIMEOUT_Pos;
1179
1180 /* High-speed read timeout */
1181 hdsi->Instance->ST_CNT_CFG2 &= ~DSI_HOST_ST_CNT_CFG2_HSRD_TIMEOUT;
1182 hdsi->Instance->ST_CNT_CFG2 |= HostTimeouts->HighSpeedReadTimeout << DSI_HOST_ST_CNT_CFG2_HSRD_TIMEOUT_Pos;
1183
1184 /* Low-power read timeout */
1185 hdsi->Instance->ST_CNT_CFG2 &= ~DSI_HOST_ST_CNT_CFG2_LPRD_TIMEOUT;
1186 hdsi->Instance->ST_CNT_CFG2 |= HostTimeouts->LowPowerReadTimeout << DSI_HOST_ST_CNT_CFG2_LPRD_TIMEOUT_Pos;
1187
1188 /* High-speed write timeout */
1189 hdsi->Instance->ST_CNT_CFG3 &= ~DSI_HOST_ST_CNT_CFG3_HSWR_TIMEOUT;
1190 hdsi->Instance->ST_CNT_CFG3 |= HostTimeouts->HighSpeedWriteTimeout << DSI_HOST_ST_CNT_CFG3_HSWR_TIMEOUT_Pos;
1191
1192 /* Low-speed write timeout */
1193 hdsi->Instance->ST_CNT_CFG3 &= ~DSI_HOST_ST_CNT_CFG3_LPWR_TIMEOUT;
1194 hdsi->Instance->ST_CNT_CFG3 |= HostTimeouts->LowPowerWriteTimeout << DSI_HOST_ST_CNT_CFG3_LPWR_TIMEOUT_Pos;
1195
1196 /* BTA timeout */
1197 hdsi->Instance->ST_CNT_CFG4 &= ~DSI_HOST_ST_CNT_CFG4_BTA_TIMEOUT;
1198 hdsi->Instance->ST_CNT_CFG4 |= HostTimeouts->BTATimeout << DSI_HOST_ST_CNT_CFG4_BTA_TIMEOUT_Pos;
1199
1200 /* Process unlocked */
1201 __HAL_UNLOCK(hdsi);
1202
1203 return HAL_OK;
1204 }
1205
1206
1207 /**
1208 * @brief Configure the DSI PHY frequency.
1209 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1210 * the configuration information for the DSI.
1211 * @param freq DSI frequency.
1212 * @retval HAL status
1213 */
HAL_DSI_ConfigPhyFreq(DSI_HandleTypeDef * hdsi,uint32_t freq)1214 HAL_StatusTypeDef HAL_DSI_ConfigPhyFreq(DSI_HandleTypeDef *hdsi, uint32_t freq)
1215 {
1216 uint32_t tickstart;
1217 uint32_t unitIntervalx4;
1218 uint32_t tempIDF;
1219
1220 /* Check the DSI handle allocation */
1221 if (hdsi == NULL)
1222 {
1223 return HAL_ERROR;
1224 }
1225
1226 /* Change DSI peripheral state */
1227 hdsi->State = HAL_DSI_STATE_BUSY;
1228
1229 /* Disable the DSI PLL */
1230 __HAL_DSI_PLL_DISABLE(hdsi);
1231
1232 Freq2PhyCfgMap_t p_phy_cfg = GetPHYCfgMap(freq);
1233 HAL_ASSERT(p_phy_cfg != NULL);
1234
1235 // setup phy timing parameter
1236 hdsi->PHY_Instance->CK_LANE_CFG0 = (p_phy_cfg->ck_phase_sel << DSI_PHY_CK_LANE_CFG0_PHASE_SEL_Pos) |
1237 (p_phy_cfg->ck_lpx_cnt << DSI_PHY_CK_LANE_CFG0_TLPX_CNT_Pos) |
1238 (p_phy_cfg->ck_prep_cnt << DSI_PHY_CK_LANE_CFG0_TCLKPREP_CNT_Pos) |
1239 (p_phy_cfg->ck_zero_cnt << DSI_PHY_CK_LANE_CFG0_TCLKZERO_CNT_Pos);
1240 hdsi->PHY_Instance->CK_LANE_CFG1 = (p_phy_cfg->ck_pre_cnt << DSI_PHY_CK_LANE_CFG1_TCLKPRE_CNT_Pos) |
1241 (p_phy_cfg->ck_post_cnt << DSI_PHY_CK_LANE_CFG1_TCLKPOST_CNT_Pos) |
1242 (p_phy_cfg->ck_trail_cnt << DSI_PHY_CK_LANE_CFG1_TCLKTRAIL_CNT_Pos) |
1243 (p_phy_cfg->ck_hs_exit_cnt << DSI_PHY_CK_LANE_CFG1_THSEXIT_CNT_Pos);
1244 hdsi->PHY_Instance->CK_LANE_CFG2 = (p_phy_cfg->ck_wakeup_cnt << DSI_PHY_CK_LANE_CFG2_TWAKEUP_CNT_Pos);
1245 hdsi->PHY_Instance->D_LANE0_CFG0 = (p_phy_cfg->dx_lpx_cnt << DSI_PHY_D_LANE0_CFG0_TLPX_CNT_Pos) |
1246 (p_phy_cfg->dx_hs_prep_cnt << DSI_PHY_D_LANE0_CFG0_THSPREP_CNT_Pos) |
1247 (p_phy_cfg->dx_hs_zero_cnt << DSI_PHY_D_LANE0_CFG0_THSZERO_CNT_Pos) |
1248 (p_phy_cfg->dx_hs_trail_cnt << DSI_PHY_D_LANE0_CFG0_THSTRAIL_CNT_Pos);
1249 hdsi->PHY_Instance->D_LANE0_CFG1 = (p_phy_cfg->dx_tasure_cnt << DSI_PHY_D_LANE0_CFG1_TTASURE_CNT_Pos) |
1250 (p_phy_cfg->dx_taget_cnt << DSI_PHY_D_LANE0_CFG1_TTAGET_CNT_Pos) |
1251 (p_phy_cfg->dx_tago_cnt << DSI_PHY_D_LANE0_CFG1_TTAGO_CNT_Pos) |
1252 (p_phy_cfg->dx_wakeup_cnt << DSI_PHY_D_LANE0_CFG1_TWAKEUP_CNT_Pos);
1253
1254
1255
1256 //D_LANE1 use same config as D_LANE0
1257 if (DSI_TWO_DATA_LANES == hdsi->Init.NumberOfLanes)
1258 {
1259 hdsi->PHY_Instance->D_LANE1_CFG0 = hdsi->PHY_Instance->D_LANE0_CFG0;
1260 hdsi->PHY_Instance->D_LANE1_CFG1 = hdsi->PHY_Instance->D_LANE0_CFG1;
1261 }
1262
1263
1264 /* Set the PLL division factors */
1265 Freq2DLLMap_t dll = GetDLLMap(freq);
1266 HAL_ASSERT(dll != NULL);
1267 hdsi->PHY_Instance->DLL_CFG &= ~(DSI_PHY_DLL_CFG_DLL0_IN_DIV2_EN |
1268 DSI_PHY_DLL_CFG_DLL0_STG |
1269 DSI_PHY_DLL_CFG_DLL0_OUT_DIV2_EN |
1270 DSI_PHY_DLL_CFG_DLL0_48M_EN);
1271 hdsi->PHY_Instance->DLL_CFG |= ((dll->stg) << DSI_PHY_DLL_CFG_DLL0_STG_Pos);
1272 if (1 == dll->in_div2)
1273 {
1274 hdsi->PHY_Instance->DLL_CFG |= DSI_PHY_DLL_CFG_DLL0_IN_DIV2_EN;
1275 }
1276 if (1 == dll->out_div2)
1277 {
1278 hdsi->PHY_Instance->DLL_CFG |= DSI_PHY_DLL_CFG_DLL0_OUT_DIV2_EN;
1279 }
1280
1281
1282 if (DSI_FREQ_528Mbps == freq)
1283 {
1284
1285 MODIFY_REG(hdsi->PHY_Instance->BIAS_CTRL, DSI_PHY_BIAS_CTRL_BIAS_PROG_Msk,
1286 0x659B << DSI_PHY_BIAS_CTRL_BIAS_PROG_Pos);
1287
1288 MODIFY_REG(hdsi->PHY_Instance->BIAS_CAL, DSI_PHY_BIAS_CAL_RSET_MANUAL_Msk | DSI_PHY_BIAS_CAL_MODE_Msk,
1289 (7 << DSI_PHY_BIAS_CAL_RSET_MANUAL_Pos) | (1 << DSI_PHY_BIAS_CAL_MODE_Pos));
1290
1291 }
1292
1293
1294 /* Enable the DSI PLL */
1295 __HAL_DSI_PLL_ENABLE(hdsi);
1296
1297 /* PLL ready need 10~20us, wait for 50 us*/
1298 HAL_Delay_us(50U);
1299
1300
1301
1302
1303 /* Initialize the DSI state*/
1304 hdsi->State = HAL_DSI_STATE_READY;
1305
1306 return HAL_OK;
1307 }
1308
1309 /**
1310 * @brief Start the DSI module
1311 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1312 * the configuration information for the DSI.
1313 * @retval HAL status
1314 */
HAL_DSI_Start(DSI_HandleTypeDef * hdsi)1315 HAL_StatusTypeDef HAL_DSI_Start(DSI_HandleTypeDef *hdsi)
1316 {
1317 /* Process locked */
1318 __HAL_LOCK(hdsi);
1319
1320 /* Enable the DSI host */
1321 __HAL_DSI_ENABLE(hdsi);
1322
1323 hdsi->PHY_Instance->PHY_CFG &= ~DSI_PHY_PHY_CFG_INIT_CNT_Msk;
1324 hdsi->PHY_Instance->PHY_CFG |= (100 << DSI_PHY_PHY_CFG_INIT_CNT_Pos);
1325
1326 /* Enable the DSI PHY */
1327 __HAL_DSI_PHY_ENABLE(hdsi);
1328
1329 /* Process unlocked */
1330 __HAL_UNLOCK(hdsi);
1331
1332 return HAL_OK;
1333 }
1334
1335
1336 #if 0
1337
1338 /**
1339 * @brief Start the DSI module and keep on ULPM mode
1340 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1341 * the configuration information for the DSI.
1342 * @retval HAL status
1343 */
1344 HAL_StatusTypeDef HAL_DSI_Start_ULPM(DSI_HandleTypeDef *hdsi)
1345 {
1346 /* Process locked */
1347 __HAL_LOCK(hdsi);
1348
1349
1350 /*1. Bypas all output lanes of DSI-PHY*/
1351 {
1352 //hdsi->PHY_Instance->PHY_CFG |= DSI_PHY_PHY_CFG_RESETN;
1353
1354 hdsi->PHY_Instance->CK_LANE_CTRL |= DSI_PHY_CK_LANE_CTRL_LPTXENA_BYPASS
1355 | DSI_PHY_CK_LANE_CTRL_LPTXENA_SET
1356 | DSI_PHY_CK_LANE_CTRL_LPTXDIN_BYPASS;
1357
1358 hdsi->PHY_Instance->CK_LANE_CTRL &= ~DSI_PHY_CK_LANE_CTRL_LPTXDIN_SET;
1359
1360
1361
1362 hdsi->PHY_Instance->D_LANE0_CTRL |= DSI_PHY_D_LANE0_CTRL_LPTXENA_BYPASS
1363 | DSI_PHY_D_LANE0_CTRL_LPTXENA_SET
1364 | DSI_PHY_D_LANE0_CTRL_LPTXDIN_BYPASS;
1365
1366 hdsi->PHY_Instance->D_LANE0_CTRL &= ~DSI_PHY_D_LANE0_CTRL_LPTXDIN_SET;
1367
1368
1369 if (DSI_TWO_DATA_LANES == hdsi->Init.NumberOfLanes)
1370 {
1371 hdsi->PHY_Instance->D_LANE1_CTRL = hdsi->PHY_Instance->D_LANE0_CTRL;
1372 }
1373 }
1374
1375
1376 /* 2. Enable the DSI host & PHY*/
1377 {
1378 __HAL_DSI_ENABLE(hdsi);
1379
1380 hdsi->PHY_Instance->PHY_CFG &= ~DSI_PHY_PHY_CFG_INIT_CNT_Msk;
1381 hdsi->PHY_Instance->PHY_CFG |= (100 << DSI_PHY_PHY_CFG_INIT_CNT_Pos);
1382 /* Enable the DSI PHY */
1383 __HAL_DSI_PHY_ENABLE(hdsi);
1384
1385 //hdsi->PHY_Instance->PHY_CFG |= DSI_PHY_PHY_CFG_ENABLE;
1386 }
1387
1388 /*3. Enter ULPM, and it will not output to bus*/
1389 {
1390 hdsi->Instance->PHY_CTRL &= ~(DSI_HOST_PHY_CTRL_CKLANE_AUTO_CTRL | DSI_HOST_PHY_CTRL_CKLANE_HSTXREQ);
1391 /* ULPS Request on Clock and Data Lanes */
1392 hdsi->Instance->PHY_CTRL |= (DSI_HOST_PHY_CTRL_CKLANE_REQULPS | DSI_HOST_PHY_CTRL_DLANE_REQULPS);
1393
1394 HAL_Delay(1);
1395
1396 //hdsi->Instance->PHY_CTRL &= ~(DSI_HOST_PHY_CTRL_CKLANE_REQULPS | DSI_HOST_PHY_CTRL_DLANE_REQULPS);
1397 hdsi->Instance->PHY_CTRL |= hdsi->Init.AutomaticClockLaneControl; //Revert clk lane setting
1398 //hdsi->Instance->PHY_CTRL |= (DSI_HOST_PHY_CTRL_CKLANE_HSTXREQ | hdsi->Init.AutomaticClockLaneControl);
1399
1400 HAL_Delay(1);
1401 //__asm("B .");
1402 }
1403
1404 /*4. disable bypass*/
1405 {
1406 hdsi->PHY_Instance->CK_LANE_CTRL &= ~(DSI_PHY_CK_LANE_CTRL_LPTXENA_BYPASS | DSI_PHY_CK_LANE_CTRL_LPTXDIN_BYPASS);
1407 hdsi->PHY_Instance->D_LANE0_CTRL &= ~(DSI_PHY_D_LANE0_CTRL_LPTXENA_BYPASS | DSI_PHY_D_LANE0_CTRL_LPTXDIN_BYPASS);
1408 hdsi->PHY_Instance->D_LANE1_CTRL &= ~(DSI_PHY_D_LANE1_CTRL_LPTXENA_BYPASS | DSI_PHY_D_LANE1_CTRL_LPTXDIN_BYPASS);
1409 }
1410
1411 /* Process unlocked */
1412 __HAL_UNLOCK(hdsi);
1413
1414 return HAL_OK;
1415 }
1416 #endif /* 0 */
1417
HAL_DSI_bypass_output(DSI_HandleTypeDef * hdsi,bool bypass)1418 HAL_StatusTypeDef HAL_DSI_bypass_output(DSI_HandleTypeDef *hdsi, bool bypass)
1419 {
1420 __IO uint32_t tmpreg;
1421
1422 /* Process locked */
1423 __HAL_LOCK(hdsi);
1424
1425 if (bypass)
1426 {
1427 hdsi->PHY_Instance->CK_LANE_CTRL |= DSI_PHY_CK_LANE_CTRL_LPTXENA_BYPASS
1428 | DSI_PHY_CK_LANE_CTRL_LPTXENA_SET
1429 | DSI_PHY_CK_LANE_CTRL_LPTXDIN_BYPASS;
1430
1431 hdsi->PHY_Instance->CK_LANE_CTRL &= ~DSI_PHY_CK_LANE_CTRL_LPTXDIN_SET;
1432
1433 tmpreg = hdsi->PHY_Instance->CK_LANE_CTRL;
1434
1435 hdsi->PHY_Instance->D_LANE0_CTRL |= DSI_PHY_D_LANE0_CTRL_LPTXENA_BYPASS
1436 | DSI_PHY_D_LANE0_CTRL_LPTXENA_SET
1437 | DSI_PHY_D_LANE0_CTRL_LPTXDIN_BYPASS;
1438
1439 hdsi->PHY_Instance->D_LANE0_CTRL &= ~DSI_PHY_D_LANE0_CTRL_LPTXDIN_SET;
1440
1441 tmpreg = hdsi->PHY_Instance->D_LANE0_CTRL;
1442 if (DSI_TWO_DATA_LANES == hdsi->Init.NumberOfLanes)
1443 {
1444 hdsi->PHY_Instance->D_LANE1_CTRL = hdsi->PHY_Instance->D_LANE0_CTRL;
1445 tmpreg = hdsi->PHY_Instance->D_LANE1_CTRL;
1446 }
1447
1448 }
1449 else
1450 {
1451 hdsi->PHY_Instance->CK_LANE_CTRL &= ~(DSI_PHY_CK_LANE_CTRL_LPTXENA_BYPASS | DSI_PHY_CK_LANE_CTRL_LPTXDIN_BYPASS);
1452 tmpreg = hdsi->PHY_Instance->CK_LANE_CTRL;
1453
1454 hdsi->PHY_Instance->D_LANE0_CTRL &= ~(DSI_PHY_D_LANE0_CTRL_LPTXENA_BYPASS | DSI_PHY_D_LANE0_CTRL_LPTXDIN_BYPASS);
1455 tmpreg = hdsi->PHY_Instance->D_LANE0_CTRL;
1456
1457 if (DSI_TWO_DATA_LANES == hdsi->Init.NumberOfLanes)
1458 {
1459 hdsi->PHY_Instance->D_LANE1_CTRL = hdsi->PHY_Instance->D_LANE0_CTRL;
1460 tmpreg = hdsi->PHY_Instance->D_LANE1_CTRL;
1461 }
1462 }
1463
1464
1465 /* Process unlocked */
1466 __HAL_UNLOCK(hdsi);
1467
1468 return HAL_OK;
1469
1470 }
1471
1472 /**
1473 * @brief Stop the DSI module
1474 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1475 * the configuration information for the DSI.
1476 * @retval HAL status
1477 */
HAL_DSI_Stop(DSI_HandleTypeDef * hdsi)1478 HAL_StatusTypeDef HAL_DSI_Stop(DSI_HandleTypeDef *hdsi)
1479 {
1480 /* Process locked */
1481 __HAL_LOCK(hdsi);
1482
1483 /* Disable the DSI host */
1484 __HAL_DSI_DISABLE(hdsi);
1485
1486 /* Disable the DSI PHY */
1487 __HAL_DSI_PHY_DISABLE(hdsi);
1488
1489 /* Process unlocked */
1490 __HAL_UNLOCK(hdsi);
1491
1492 return HAL_OK;
1493 }
1494 #ifdef DSI_FIX_ME
1495 /**
1496 * @brief Refresh the display in command mode
1497 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1498 * the configuration information for the DSI.
1499 * @retval HAL status
1500 */
HAL_DSI_Refresh(DSI_HandleTypeDef * hdsi)1501 HAL_StatusTypeDef HAL_DSI_Refresh(DSI_HandleTypeDef *hdsi)
1502 {
1503 /* Process locked */
1504 __HAL_LOCK(hdsi);
1505
1506 /* Update the display */
1507 hdsi->Instance->WCR |= DSI_WCR_LTDCEN;
1508
1509 /* Process unlocked */
1510 __HAL_UNLOCK(hdsi);
1511
1512 return HAL_OK;
1513 }
1514
1515
1516 /**
1517 * @brief Controls the display color mode in Video mode
1518 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1519 * the configuration information for the DSI.
1520 * @param ColorMode Color mode (full or 8-colors).
1521 * This parameter can be any value of @ref DSI_Color_Mode
1522 * @retval HAL status
1523 */
HAL_DSI_ColorMode(DSI_HandleTypeDef * hdsi,uint32_t ColorMode)1524 HAL_StatusTypeDef HAL_DSI_ColorMode(DSI_HandleTypeDef *hdsi, uint32_t ColorMode)
1525 {
1526 /* Process locked */
1527 __HAL_LOCK(hdsi);
1528
1529 /* Check the parameters */
1530 HAL_ASSERT(IS_DSI_COLOR_MODE(ColorMode));
1531
1532 /* Update the display color mode */
1533 hdsi->Instance->WCR &= ~DSI_WCR_COLM;
1534 hdsi->Instance->WCR |= ColorMode;
1535
1536 /* Process unlocked */
1537 __HAL_UNLOCK(hdsi);
1538
1539 return HAL_OK;
1540 }
1541
1542 /**
1543 * @brief Control the display shutdown in Video mode
1544 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1545 * the configuration information for the DSI.
1546 * @param Shutdown Shut-down (Display-ON or Display-OFF).
1547 * This parameter can be any value of @ref DSI_ShutDown
1548 * @retval HAL status
1549 */
HAL_DSI_Shutdown(DSI_HandleTypeDef * hdsi,uint32_t Shutdown)1550 HAL_StatusTypeDef HAL_DSI_Shutdown(DSI_HandleTypeDef *hdsi, uint32_t Shutdown)
1551 {
1552 /* Process locked */
1553 __HAL_LOCK(hdsi);
1554
1555 /* Check the parameters */
1556 HAL_ASSERT(IS_DSI_SHUT_DOWN(Shutdown));
1557
1558 /* Update the display Shutdown */
1559 hdsi->Instance->WCR &= ~DSI_WCR_SHTDN;
1560 hdsi->Instance->WCR |= Shutdown;
1561
1562 /* Process unlocked */
1563 __HAL_UNLOCK(hdsi);
1564
1565 return HAL_OK;
1566 }
1567 #endif
1568
HAL_DSI_SetPaticalSend(DSI_HandleTypeDef * hdsi,uint32_t write_size)1569 HAL_StatusTypeDef HAL_DSI_SetPaticalSend(DSI_HandleTypeDef *hdsi,
1570 uint32_t write_size)
1571 {
1572 /* Process locked */
1573 __HAL_LOCK(hdsi);
1574
1575
1576 //Write command size
1577 hdsi->Instance->DBI_CFG2 &= ~DSI_HOST_DBI_CFG2_WR_SIZE_Msk;
1578 hdsi->Instance->DBI_CFG2 |= (write_size << DSI_HOST_DBI_CFG2_WR_SIZE_Pos);
1579
1580 /* Process unlocked */
1581 __HAL_UNLOCK(hdsi);
1582
1583 return HAL_OK;
1584
1585 }
1586
1587
1588 #ifndef SF32LB55X
HAL_DSI_DirectSend(DSI_HandleTypeDef * hdsi,uint32_t write_size)1589 HAL_StatusTypeDef HAL_DSI_DirectSend(DSI_HandleTypeDef *hdsi,
1590 uint32_t write_size)
1591 {
1592 /* Process locked */
1593 __HAL_LOCK(hdsi);
1594
1595
1596 hdsi->Instance->DCOM_INTF_CFG1 = (10 << DSI_HOST_DCOM_INTF_CFG1_WAIT_CYCLE_Pos) | //Hpsys clcyes
1597 (210 << DSI_HOST_DCOM_INTF_CFG1_PKT_SIZE_Pos); //Must <=512, large pkt size may enter LP mode
1598
1599 hdsi->Instance->DCOM_INTF_CFG2 = ((write_size) << DSI_HOST_DCOM_INTF_CFG2_TOTAL_SIZE_Pos);
1600
1601 // enable direct interface
1602 hdsi->Instance->DCOM_INTF_CTRL = (1 << DSI_HOST_DCOM_INTF_CTRL_START_Pos) |
1603 (0 << DSI_HOST_DCOM_INTF_CTRL_SW_RESET_Pos);
1604
1605
1606 /* Process unlocked */
1607 __HAL_UNLOCK(hdsi);
1608
1609 return HAL_OK;
1610
1611 }
1612
1613
1614 #endif /* !SF32LB55X */
1615
1616 /**
1617 * @brief write short DCS or short Generic command
1618 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1619 * the configuration information for the DSI.
1620 * @param ChannelID Virtual channel ID.
1621 * @param Mode DSI short packet data type.
1622 * This parameter can be any value of @ref DSI_SHORT_WRITE_PKT_Data_Type.
1623 * @param Param1 DSC command or first generic parameter.
1624 * This parameter can be any value of @ref DSI_DCS_Command or a
1625 * generic command code.
1626 * @param Param2 DSC parameter or second generic parameter.
1627 * @retval HAL status
1628 */
HAL_DSI_ShortWrite(DSI_HandleTypeDef * hdsi,uint32_t ChannelID,uint32_t Mode,uint32_t Param1,uint32_t Param2)1629 HAL_StatusTypeDef HAL_DSI_ShortWrite(DSI_HandleTypeDef *hdsi,
1630 uint32_t ChannelID,
1631 uint32_t Mode,
1632 uint32_t Param1,
1633 uint32_t Param2)
1634 {
1635 uint32_t tickstart;
1636
1637 /* Process locked */
1638 __HAL_LOCK(hdsi);
1639
1640 /* Check the parameters */
1641 HAL_ASSERT(IS_DSI_SHORT_WRITE_PACKET_TYPE(Mode));
1642 DSI_LOG_D("HAL_DSI_ShortWrite INT_STAT2=%x\n", hdsi->Instance->INT_STAT2);
1643 DSI_LOG_D("PHY_STAT %x\n", hdsi->Instance->PHY_STAT);
1644
1645 /* Get tick */
1646 tickstart = HAL_GetTick();
1647
1648 /* Wait for Command FIFO Empty */
1649 while ((hdsi->Instance->CMD_PKT_STAT & DSI_HOST_CMD_PKT_STAT_COM_CMD_EMPTY) == 0U)
1650 {
1651 /* Check for the Timeout */
1652 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
1653 {
1654
1655 DSI_LOG_D("HAL_DSI_ShortWrite time out, cur=%d, %d\n", HAL_GetTick(), tickstart);
1656
1657 /* Process Unlocked */
1658 __HAL_UNLOCK(hdsi);
1659
1660 return HAL_TIMEOUT;
1661 }
1662 }
1663
1664 DSI_LOG_D("HAL_DSI_ShortWrite %x, %x\n", Param1, Param2);
1665
1666 /* Configure the packet to send a short DCS command with 0 or 1 parameter */
1667 DSI_ConfigPacketHeader(hdsi->Instance,
1668 ChannelID,
1669 Mode,
1670 Param1,
1671 Param2);
1672
1673 /* Process unlocked */
1674 __HAL_UNLOCK(hdsi);
1675
1676 return HAL_OK;
1677 }
1678
1679 /**
1680 * @brief write long DCS or long Generic command
1681 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1682 * the configuration information for the DSI.
1683 * @param ChannelID Virtual channel ID.
1684 * @param Mode DSI long packet data type.
1685 * This parameter can be any value of @ref DSI_LONG_WRITE_PKT_Data_Type.
1686 * @param NbParams Number of parameters.
1687 * @param Param1 DSC command or first generic parameter.
1688 * This parameter can be any value of @ref DSI_DCS_Command or a
1689 * generic command code
1690 * @param ParametersTable Pointer to parameter values table.
1691 * @retval HAL status
1692 */
HAL_DSI_LongWrite(DSI_HandleTypeDef * hdsi,uint32_t ChannelID,uint32_t Mode,uint32_t NbParams,uint32_t Param1,uint8_t * ParametersTable)1693 HAL_StatusTypeDef HAL_DSI_LongWrite(DSI_HandleTypeDef *hdsi,
1694 uint32_t ChannelID,
1695 uint32_t Mode,
1696 uint32_t NbParams,
1697 uint32_t Param1,
1698 uint8_t *ParametersTable)
1699 {
1700 uint32_t uicounter, nbBytes, count;
1701 uint32_t tickstart;
1702 uint32_t fifoword;
1703 uint8_t *pparams = ParametersTable;
1704
1705 /* Process locked */
1706 __HAL_LOCK(hdsi);
1707
1708 /* Check the parameters */
1709 HAL_ASSERT(IS_DSI_LONG_WRITE_PACKET_TYPE(Mode));
1710 DSI_LOG_D("HAL_DSI_LongWrite INT_STAT2=%x\n", hdsi->Instance->INT_STAT2);
1711 DSI_LOG_D("PHY_STAT %x\n", hdsi->Instance->PHY_STAT);
1712
1713 /* Get tick */
1714 tickstart = HAL_GetTick();
1715
1716 /* Wait for Command FIFO Empty */
1717 while ((hdsi->Instance->CMD_PKT_STAT & DSI_HOST_CMD_PKT_STAT_COM_CMD_EMPTY) == RESET)
1718 {
1719 /* Check for the Timeout */
1720 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
1721 {
1722 /* Process Unlocked */
1723 __HAL_UNLOCK(hdsi);
1724
1725 return HAL_TIMEOUT;
1726 }
1727 }
1728
1729 DSI_LOG_D("HAL_DSI_LongWrite %x\n", Param1);
1730
1731 /* Set the DCS code on payload byte 1, and the other parameters on the write FIFO command*/
1732 fifoword = Param1;
1733 nbBytes = (NbParams < 3U) ? NbParams : 3U;
1734
1735 for (count = 0U; count < nbBytes; count++)
1736 {
1737 fifoword |= (((uint32_t)(*(pparams + count))) << (8U + (8U * count)));
1738 }
1739 hdsi->Instance->COM_PLD = fifoword;
1740
1741 uicounter = NbParams - nbBytes;
1742 pparams += nbBytes;
1743 /* Set the Next parameters on the write FIFO command*/
1744 while (uicounter != 0U)
1745 {
1746 nbBytes = (uicounter < 4U) ? uicounter : 4U;
1747 fifoword = 0U;
1748 for (count = 0U; count < nbBytes; count++)
1749 {
1750 fifoword |= (((uint32_t)(*(pparams + count))) << (8U * count));
1751 }
1752 hdsi->Instance->COM_PLD = fifoword;
1753
1754 uicounter -= nbBytes;
1755 pparams += nbBytes;
1756 }
1757
1758 /* Configure the packet to send a long DCS command */
1759 DSI_ConfigPacketHeader(hdsi->Instance,
1760 ChannelID,
1761 Mode,
1762 ((NbParams + 1U) & 0x00FFU),
1763 (((NbParams + 1U) & 0xFF00U) >> 8U));
1764
1765 /* Process unlocked */
1766 __HAL_UNLOCK(hdsi);
1767
1768 return HAL_OK;
1769 }
1770
1771 /**
1772 * @brief Read command (DCS or generic)
1773 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
1774 * the configuration information for the DSI.
1775 * @param ChannelNbr Virtual channel ID
1776 * @param Array pointer to a buffer to store the payload of a read back operation.
1777 * @param Size Data size to be read (in byte).
1778 * @param Mode DSI read packet data type.
1779 * This parameter can be any value of @ref DSI_SHORT_READ_PKT_Data_Type.
1780 * @param DCSCmd DCS get/read command.
1781 * @param ParametersTable Pointer to parameter values table.
1782 * @retval HAL status
1783 */
HAL_DSI_Read(DSI_HandleTypeDef * hdsi,uint32_t ChannelNbr,uint8_t * Array,uint32_t Size,uint32_t Mode,uint32_t DCSCmd,uint8_t * ParametersTable)1784 HAL_StatusTypeDef HAL_DSI_Read(DSI_HandleTypeDef *hdsi,
1785 uint32_t ChannelNbr,
1786 uint8_t *Array,
1787 uint32_t Size,
1788 uint32_t Mode,
1789 uint32_t DCSCmd,
1790 uint8_t *ParametersTable)
1791 {
1792 uint32_t tickstart;
1793 uint8_t *pdata = Array;
1794 uint32_t tmp, datasize = Size;
1795
1796 /* Process locked */
1797 __HAL_LOCK(hdsi);
1798
1799 /* Check the parameters */
1800 HAL_ASSERT(IS_DSI_READ_PACKET_TYPE(Mode));
1801
1802 if (Size > 64)
1803 {
1804 return HAL_ERROR;
1805 }
1806
1807 DSI_LOG_D("HAL_DSI_Readx start SIZE=%d\n", datasize);
1808 DSI_LOG_D("HAL_DSI_Read INT_STAT2=%x\n", hdsi->Instance->INT_STAT2);
1809 if (datasize > 2U)
1810 {
1811 /* set max return packet size */
1812 /* Get tick */
1813 tickstart = HAL_GetTick();
1814
1815 /* Wait for Command FIFO Empty */
1816 while ((hdsi->Instance->CMD_PKT_STAT & DSI_HOST_CMD_PKT_STAT_COM_CMD_EMPTY) == 0U)
1817 {
1818 /* Check for the Timeout */
1819 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
1820 {
1821
1822 DSI_LOG_D("HAL_DSI_ShortWrite time out, cur=%d, %d\n", HAL_GetTick(), tickstart);
1823
1824 /* Process Unlocked */
1825 __HAL_UNLOCK(hdsi);
1826
1827 return HAL_TIMEOUT;
1828 }
1829 }
1830
1831 /* Configure the packet to send a short DCS command with 0 or 1 parameter */
1832 DSI_ConfigPacketHeader(hdsi->Instance,
1833 ChannelNbr,
1834 DSI_MAX_RETURN_PKT_SIZE,
1835 ((datasize) & 0xFFU),
1836 (((datasize) >> 8U) & 0xFFU));
1837 }
1838
1839 DSI_LOG_D("HAL_DSI_Read Mode=%x, cmd=%x\n", Mode, DCSCmd);
1840 DSI_LOG_D("HAL_DSI_Read INT_STAT2=%x\n", hdsi->Instance->INT_STAT2);
1841 DSI_LOG_D("HAL_DSI_Read CMODE_CFG=%x\n", hdsi->Instance->CMODE_CFG);
1842
1843
1844 /* Get tick */
1845 tickstart = HAL_GetTick();
1846
1847 /* Wait for Command FIFO Empty */
1848 while ((hdsi->Instance->CMD_PKT_STAT & DSI_HOST_CMD_PKT_STAT_COM_CMD_EMPTY) == 0U)
1849 {
1850 /* Check for the Timeout */
1851 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
1852 {
1853
1854 DSI_LOG_D("HAL_DSI_ShortWrite time out, cur=%d, %d\n", HAL_GetTick(), tickstart);
1855
1856 /* Process Unlocked */
1857 __HAL_UNLOCK(hdsi);
1858
1859 return HAL_TIMEOUT;
1860 }
1861 }
1862
1863 /* Configure the packet to read command */
1864 if (Mode == DSI_DCS_SHORT_PKT_READ)
1865 {
1866 DSI_ConfigPacketHeader(hdsi->Instance, ChannelNbr, Mode, DCSCmd, 0U);
1867 }
1868 else if (Mode == DSI_GEN_SHORT_PKT_READ_P0)
1869 {
1870 DSI_ConfigPacketHeader(hdsi->Instance, ChannelNbr, Mode, 0U, 0U);
1871 }
1872 else if (Mode == DSI_GEN_SHORT_PKT_READ_P1)
1873 {
1874 DSI_ConfigPacketHeader(hdsi->Instance, ChannelNbr, Mode, ParametersTable[0U], 0U);
1875 }
1876 else if (Mode == DSI_GEN_SHORT_PKT_READ_P2)
1877 {
1878 DSI_ConfigPacketHeader(hdsi->Instance, ChannelNbr, Mode, ParametersTable[0U], ParametersTable[1U]);
1879 }
1880 else
1881 {
1882 /* Process Unlocked */
1883 __HAL_UNLOCK(hdsi);
1884
1885 return HAL_ERROR;
1886 }
1887
1888
1889 #ifdef SHOW_BTA_LOG
1890 {
1891 /* Get tick */
1892 tickstart = HAL_GetTick();
1893 // enter receive mode
1894 uint32_t rdata = (hdsi->Instance->PHY_STAT & DSI_HOST_PHY_STAT_DIR_Msk);
1895 while (rdata == (0 << DSI_HOST_PHY_STAT_DIR_Pos))
1896 {
1897 rdata = (hdsi->Instance->PHY_STAT & DSI_HOST_PHY_STAT_DIR_Msk);
1898 /* Check for the Timeout */
1899 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
1900 {
1901 /* Process Unlocked */
1902 __HAL_UNLOCK(hdsi);
1903
1904 return HAL_TIMEOUT;
1905 }
1906 }
1907
1908 DSI_LOG_D("enter receive mode\n");
1909 /* Get tick */
1910 tickstart = HAL_GetTick();
1911
1912 // enter transmitt mode
1913 rdata = (hdsi->Instance->PHY_STAT & DSI_HOST_PHY_STAT_DIR_Msk);
1914 while (rdata == (1 << DSI_HOST_PHY_STAT_DIR_Pos))
1915 {
1916 rdata = (hdsi->Instance->PHY_STAT & DSI_HOST_PHY_STAT_DIR_Msk);
1917 /* Check for the Timeout */
1918 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
1919 {
1920 /* Process Unlocked */
1921 __HAL_UNLOCK(hdsi);
1922
1923 return HAL_TIMEOUT;
1924 }
1925 }
1926
1927 DSI_LOG_D("enter transmit mode\n");
1928 }
1929 #endif
1930
1931 DSI_LOG_D("HAL_DSI_Read CMD_PKT_STAT=%x\n", hdsi->Instance->CMD_PKT_STAT);
1932
1933 /* Get tick */
1934 tickstart = HAL_GetTick();
1935
1936 /* Check that the payload read FIFO is not empty and transmit is finish*/
1937 while (((hdsi->Instance->CMD_PKT_STAT & DSI_HOST_CMD_PKT_STAT_COM_RDPLD_EMPTY) == DSI_HOST_CMD_PKT_STAT_COM_RDPLD_EMPTY)
1938 || ((1 << DSI_HOST_PHY_STAT_DIR_Pos) == (hdsi->Instance->PHY_STAT & DSI_HOST_PHY_STAT_DIR_Msk))
1939 )
1940 {
1941 /* Check for the Timeout */
1942 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
1943 {
1944 DSI_LOG_D("TIMEOUT CMD_PKT_STAT=%x, PHY_STAT=%x\n", hdsi->Instance->CMD_PKT_STAT, hdsi->Instance->PHY_STAT);
1945 /* Process Unlocked */
1946 __HAL_UNLOCK(hdsi);
1947
1948 return HAL_TIMEOUT;
1949 }
1950 }
1951
1952
1953 /* Read payload after transmit done. */
1954 do
1955 {
1956 tmp = hdsi->Instance->COM_PLD;
1957 for (uint8_t i = 0; (i < 4) && (datasize > 0); i++)
1958 {
1959 *pdata = (uint8_t)((tmp >> (i * 8)) & 0xff);
1960 DSI_LOG_D("HAL_DSI_Read byte=%x\n", *pdata);
1961 pdata++;
1962 datasize--;
1963 }
1964
1965 }
1966 while (datasize > 0);
1967
1968
1969 #ifdef SHOW_BTA_LOG
1970 /* Get tick */
1971 tickstart = HAL_GetTick();
1972
1973 /* Get the remaining bytes if any */
1974 while (((int)(datasize)) > 0)
1975 {
1976 if ((hdsi->Instance->CMD_PKT_STAT & DSI_HOST_CMD_PKT_STAT_COM_RDPLD_EMPTY) == 0U)
1977 {
1978 *((uint32_t *)pdata) = (hdsi->Instance->COM_PLD);
1979 DSI_LOG_D("HAL_DSI_Read remaining byte=%x\n", *((uint32_t *)pdata));
1980 datasize -= 4U;
1981 pdata += 4U;
1982 }
1983
1984 /* Check for the Timeout */
1985 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
1986 {
1987 /* Process Unlocked */
1988 __HAL_UNLOCK(hdsi);
1989
1990 return HAL_TIMEOUT;
1991 }
1992 }
1993 #endif
1994 /* Process unlocked */
1995 __HAL_UNLOCK(hdsi);
1996 DSI_LOG_D("HAL_DSI_Read end\n");
1997
1998 return HAL_OK;
1999 }
2000
2001 /**
2002 * @brief Enter the ULPM (Ultra Low Power Mode) with the D-PHY PLL running
2003 * (only data lanes are in ULPM)
2004 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2005 * the configuration information for the DSI.
2006 * @retval HAL status
2007 */
HAL_DSI_EnterULPMData(DSI_HandleTypeDef * hdsi)2008 HAL_StatusTypeDef HAL_DSI_EnterULPMData(DSI_HandleTypeDef *hdsi)
2009 {
2010 uint32_t tickstart;
2011
2012 /* Process locked */
2013 __HAL_LOCK(hdsi);
2014
2015 /* ULPS Request on Data Lanes */
2016 hdsi->Instance->PHY_CTRL |= DSI_HOST_PHY_CTRL_DLANE_REQULPS;
2017
2018 /* Get tick */
2019 tickstart = HAL_GetTick();
2020
2021 /* Wait until the D-PHY active lanes enter into ULPM */
2022 if ((hdsi->Instance->PHY_CFG1 & DSI_HOST_PHY_CFG1_NUM_ACT_LANE) == DSI_ONE_DATA_LANE)
2023 {
2024 while ((hdsi->Instance->PHY_STAT & DSI_HOST_PHY_STAT_DLANE0_ULPS_N) != RESET)
2025 {
2026 /* Check for the Timeout */
2027 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
2028 {
2029 /* Process Unlocked */
2030 __HAL_UNLOCK(hdsi);
2031
2032 return HAL_TIMEOUT;
2033 }
2034 }
2035 }
2036 else if ((hdsi->Instance->PHY_CFG1 & DSI_HOST_PHY_CFG1_NUM_ACT_LANE) == DSI_TWO_DATA_LANES)
2037 {
2038 while ((hdsi->Instance->PHY_STAT & (DSI_HOST_PHY_STAT_DLANE0_ULPS_N | DSI_HOST_PHY_STAT_DLANE1_ULPS_N)) != RESET)
2039 {
2040 /* Check for the Timeout */
2041 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
2042 {
2043 /* Process Unlocked */
2044 __HAL_UNLOCK(hdsi);
2045
2046 return HAL_TIMEOUT;
2047 }
2048 }
2049 }
2050 else
2051 {
2052 /* Process unlocked */
2053 __HAL_UNLOCK(hdsi);
2054
2055 return HAL_ERROR;
2056 }
2057
2058 /* Process unlocked */
2059 __HAL_UNLOCK(hdsi);
2060
2061 return HAL_OK;
2062 }
2063
2064 /**
2065 * @brief Exit the ULPM (Ultra Low Power Mode) with the D-PHY PLL running
2066 * (only data lanes are in ULPM)
2067 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2068 * the configuration information for the DSI.
2069 * @retval HAL status
2070 */
HAL_DSI_ExitULPMData(DSI_HandleTypeDef * hdsi)2071 HAL_StatusTypeDef HAL_DSI_ExitULPMData(DSI_HandleTypeDef *hdsi)
2072 {
2073 uint32_t tickstart;
2074
2075 /* Process locked */
2076 __HAL_LOCK(hdsi);
2077
2078 /* Exit ULPS on Data Lanes */
2079 hdsi->Instance->PHY_CTRL |= DSI_HOST_PHY_CTRL_DLANE_EXITULPS;
2080
2081 /* Get tick */
2082 tickstart = HAL_GetTick();
2083
2084 /* Wait until all active lanes exit ULPM */
2085 if ((hdsi->Instance->PHY_CFG1 & DSI_HOST_PHY_CFG1_NUM_ACT_LANE) == DSI_ONE_DATA_LANE)
2086 {
2087 while ((hdsi->Instance->PHY_STAT & DSI_HOST_PHY_STAT_DLANE0_ULPS_N) != DSI_HOST_PHY_STAT_DLANE0_ULPS_N)
2088 {
2089 /* Check for the Timeout */
2090 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
2091 {
2092 /* Process Unlocked */
2093 __HAL_UNLOCK(hdsi);
2094
2095 return HAL_TIMEOUT;
2096 }
2097 }
2098 }
2099 else if ((hdsi->Instance->PHY_CFG1 & DSI_HOST_PHY_CFG1_NUM_ACT_LANE) == DSI_TWO_DATA_LANES)
2100 {
2101 while ((hdsi->Instance->PHY_STAT & (DSI_HOST_PHY_STAT_DLANE0_ULPS_N | DSI_HOST_PHY_STAT_DLANE1_ULPS_N)) != (DSI_HOST_PHY_STAT_DLANE0_ULPS_N | DSI_HOST_PHY_STAT_DLANE1_ULPS_N))
2102 {
2103 /* Check for the Timeout */
2104 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
2105 {
2106 /* Process Unlocked */
2107 __HAL_UNLOCK(hdsi);
2108
2109 return HAL_TIMEOUT;
2110 }
2111 }
2112 }
2113 else
2114 {
2115 /* Process unlocked */
2116 __HAL_UNLOCK(hdsi);
2117
2118 return HAL_ERROR;
2119 }
2120
2121 /* wait for 1 ms*/
2122 HAL_Delay(1U);
2123
2124 /* De-assert the ULPM requests and the ULPM exit bits */
2125 hdsi->Instance->PHY_CTRL &= ~(DSI_HOST_PHY_CTRL_DLANE_REQULPS | DSI_HOST_PHY_CTRL_DLANE_EXITULPS | DSI_HOST_PHY_CTRL_CKLANE_REQULPS | DSI_HOST_PHY_CTRL_CKLANE_EXITULPS);
2126
2127 /* Process unlocked */
2128 __HAL_UNLOCK(hdsi);
2129
2130 return HAL_OK;
2131 }
2132
2133 /**
2134 * @brief Enter the ULPM (Ultra Low Power Mode) with the D-PHY PLL turned off
2135 * (both data and clock lanes are in ULPM)
2136 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2137 * the configuration information for the DSI.
2138 * @retval HAL status
2139 */
HAL_DSI_EnterULPM(DSI_HandleTypeDef * hdsi)2140 HAL_StatusTypeDef HAL_DSI_EnterULPM(DSI_HandleTypeDef *hdsi)
2141 {
2142 uint32_t tickstart;
2143 HAL_StatusTypeDef ret_v = HAL_OK;
2144
2145 if (HAL_DSI_IS_VIDEO_MODE(hdsi)) return HAL_OK;
2146
2147 DSI_LOG_D("HAL_DSI_EnterULPM \n");
2148 /* Process locked */
2149 __HAL_LOCK(hdsi);
2150
2151 /* Clock lane configuration: no more HS request */
2152 hdsi->Instance->PHY_CTRL &= ~DSI_HOST_PHY_CTRL_CKLANE_HSTXREQ;
2153
2154 /* Use system PLL as byte lane clock source before stopping DSIPHY clock source */
2155 //__HAL_RCC_DSI_CONFIG(RCC_DSICLKSOURCE_PLLR);
2156 //hdsi->Instance->PHY_CTRL &= ~(DSI_HOST_PHY_CTRL_CKLANE_AUTO_CTRL);
2157 HAL_ASSERT(DSI_HOST_PHY_CTRL_CKLANE_AUTO_CTRL == (hdsi->Instance->PHY_CTRL & DSI_HOST_PHY_CTRL_CKLANE_AUTO_CTRL)); //Make sure CLK lane not during HS mode
2158
2159 hdsi->Instance->PHY_CTRL &= ~(DSI_HOST_PHY_CTRL_CKLANE_AUTO_CTRL);
2160
2161 /* Get tick */
2162 tickstart = HAL_GetTick();
2163
2164 /*Wait clock lane enter LP mode*/
2165 while (!__HAL_DSI_IS_CKLANE_STOP(hdsi))
2166 {
2167 /* Check for the Timeout */
2168 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
2169 {
2170 ret_v = HAL_TIMEOUT;
2171 goto _ERR_HANDLE;
2172 }
2173 }
2174
2175 /* ULPS Request on Clock and Data Lanes */
2176 hdsi->Instance->PHY_CTRL |= (DSI_HOST_PHY_CTRL_CKLANE_REQULPS | DSI_HOST_PHY_CTRL_DLANE_REQULPS);
2177
2178
2179 /* Wait until all active lanes exit ULPM */
2180 if ((hdsi->Instance->PHY_CFG1 & DSI_HOST_PHY_CFG1_NUM_ACT_LANE) == DSI_ONE_DATA_LANE)
2181 {
2182 while ((hdsi->Instance->PHY_STAT & (DSI_HOST_PHY_STAT_DLANE0_ULPS_N | DSI_HOST_PHY_STAT_CKLANE_ULPS_N)) != RESET)
2183 {
2184 /* Check for the Timeout */
2185 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
2186 {
2187 ret_v = HAL_TIMEOUT;
2188 goto _ERR_HANDLE;
2189 }
2190 }
2191 }
2192 else if ((hdsi->Instance->PHY_CFG1 & DSI_HOST_PHY_CFG1_NUM_ACT_LANE) == DSI_TWO_DATA_LANES)
2193 {
2194 while ((hdsi->Instance->PHY_STAT & (DSI_HOST_PHY_STAT_DLANE0_ULPS_N | DSI_HOST_PHY_STAT_DLANE1_ULPS_N | DSI_HOST_PHY_STAT_CKLANE_ULPS_N)) != RESET)
2195 {
2196 /* Check for the Timeout */
2197 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
2198 {
2199 ret_v = HAL_TIMEOUT;
2200 goto _ERR_HANDLE;
2201 }
2202 }
2203 }
2204 else
2205 {
2206 ret_v = HAL_ERROR;
2207 goto _ERR_HANDLE;
2208 }
2209
2210 /* Turn off the DSI PLL */
2211 __HAL_DSI_PLL_DISABLE(hdsi);
2212
2213 _ERR_HANDLE:
2214 /* Process unlocked */
2215 __HAL_UNLOCK(hdsi);
2216
2217 DSI_LOG_D("HAL_DSI_EnterULPM done.\n");
2218
2219 return ret_v;
2220 }
2221
2222 /**
2223 * @brief Exit the ULPM (Ultra Low Power Mode) with the D-PHY PLL turned off
2224 * (both data and clock lanes are in ULPM)
2225 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2226 * the configuration information for the DSI.
2227 * @retval HAL status
2228 */
HAL_DSI_ExitULPM(DSI_HandleTypeDef * hdsi)2229 HAL_StatusTypeDef HAL_DSI_ExitULPM(DSI_HandleTypeDef *hdsi)
2230 {
2231 uint32_t tickstart;
2232
2233 if (HAL_DSI_IS_VIDEO_MODE(hdsi)) return HAL_OK;
2234
2235 DSI_LOG_D("HAL_DSI_ExitULPM \n");
2236
2237 /* Process locked */
2238 __HAL_LOCK(hdsi);
2239
2240 /* Turn on the DSI PLL */
2241 __HAL_DSI_PLL_ENABLE(hdsi);
2242
2243 /* PLL ready need 10~20us, wait for 50 us*/
2244 HAL_Delay_us(50U);
2245
2246
2247 /* Exit ULPS on Clock and Data Lanes */
2248 hdsi->Instance->PHY_CTRL |= (DSI_HOST_PHY_CTRL_CKLANE_EXITULPS | DSI_HOST_PHY_CTRL_DLANE_EXITULPS);
2249
2250 /* Get tick */
2251 tickstart = HAL_GetTick();
2252
2253 /* Wait until all active lanes exit ULPM */
2254 if ((hdsi->Instance->PHY_CFG1 & DSI_HOST_PHY_CFG1_NUM_ACT_LANE) == DSI_ONE_DATA_LANE)
2255 {
2256 while ((hdsi->Instance->PHY_STAT & (DSI_HOST_PHY_STAT_DLANE0_ULPS_N | DSI_HOST_PHY_STAT_CKLANE_ULPS_N)) != (DSI_HOST_PHY_STAT_DLANE0_ULPS_N | DSI_HOST_PHY_STAT_CKLANE_ULPS_N))
2257 {
2258 /* Check for the Timeout */
2259 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
2260 {
2261 /* Process Unlocked */
2262 __HAL_UNLOCK(hdsi);
2263
2264 return HAL_TIMEOUT;
2265 }
2266 }
2267 }
2268 else if ((hdsi->Instance->PHY_CFG1 & DSI_HOST_PHY_CFG1_NUM_ACT_LANE) == DSI_TWO_DATA_LANES)
2269 {
2270 while ((hdsi->Instance->PHY_STAT & (DSI_HOST_PHY_STAT_DLANE0_ULPS_N | DSI_HOST_PHY_STAT_DLANE1_ULPS_N | DSI_HOST_PHY_STAT_CKLANE_ULPS_N)) != (DSI_HOST_PHY_STAT_DLANE0_ULPS_N | DSI_HOST_PHY_STAT_DLANE1_ULPS_N | DSI_HOST_PHY_STAT_CKLANE_ULPS_N))
2271 {
2272 /* Check for the Timeout */
2273 if ((HAL_GetTick() - tickstart) > DSI_TIMEOUT_VALUE)
2274 {
2275 /* Process Unlocked */
2276 __HAL_UNLOCK(hdsi);
2277
2278 return HAL_TIMEOUT;
2279 }
2280 }
2281 }
2282 else
2283 {
2284 /* Process unlocked */
2285 __HAL_UNLOCK(hdsi);
2286
2287 return HAL_ERROR;
2288 }
2289
2290 /* wait for 1 ms */
2291 HAL_Delay_us(50U);
2292
2293 /* De-assert the ULPM requests and the ULPM exit bits */
2294 hdsi->Instance->PHY_CTRL &= ~(DSI_HOST_PHY_CTRL_DLANE_REQULPS | DSI_HOST_PHY_CTRL_DLANE_EXITULPS | DSI_HOST_PHY_CTRL_CKLANE_REQULPS | DSI_HOST_PHY_CTRL_CKLANE_EXITULPS);
2295
2296 /* Switch the lanbyteclock source in the RCC from system PLL to D-PHY */
2297 //__HAL_RCC_DSI_CONFIG(RCC_DSICLKSOURCE_DSIPHY);
2298
2299 /* Restore clock lane configuration to HS */
2300 //hdsi->Instance->PHY_CTRL |= DSI_HOST_PHY_CTRL_CKLANE_HSTXREQ;
2301
2302 hdsi->Instance->PHY_CTRL |= DSI_HOST_PHY_CTRL_CKLANE_HSTXREQ | hdsi->Init.AutomaticClockLaneControl; //Revert clk lane setting
2303 //HAL_Delay_us(50U);
2304
2305 /* Process unlocked */
2306 __HAL_UNLOCK(hdsi);
2307
2308 DSI_LOG_D("HAL_DSI_ExitULPM done.\n");
2309
2310 return HAL_OK;
2311 }
2312
2313
HAL_DSI_EnterHSM(DSI_HandleTypeDef * hdsi)2314 HAL_StatusTypeDef HAL_DSI_EnterHSM(DSI_HandleTypeDef *hdsi)
2315 {
2316
2317 return HAL_OK;
2318 }
2319
2320
HAL_DSI_ExitHSM(DSI_HandleTypeDef * hdsi)2321 HAL_StatusTypeDef HAL_DSI_ExitHSM(DSI_HandleTypeDef *hdsi)
2322 {
2323 return HAL_OK;
2324 }
2325
HAL_DSI_EnterCKLaneHSM(DSI_HandleTypeDef * hdsi)2326 HAL_StatusTypeDef HAL_DSI_EnterCKLaneHSM(DSI_HandleTypeDef *hdsi)
2327 {
2328 /* Process locked */
2329 __HAL_LOCK(hdsi);
2330
2331 hdsi->Instance->PHY_CTRL &= ~(DSI_HOST_PHY_CTRL_CKLANE_AUTO_CTRL);
2332 hdsi->Instance->PHY_CTRL |= DSI_HOST_PHY_CTRL_CKLANE_HSTXREQ;
2333
2334 /* Process unlocked */
2335 __HAL_UNLOCK(hdsi);
2336
2337
2338 return HAL_OK;
2339 }
2340
2341
HAL_DSI_ExitCKLaneHSM(DSI_HandleTypeDef * hdsi)2342 HAL_StatusTypeDef HAL_DSI_ExitCKLaneHSM(DSI_HandleTypeDef *hdsi)
2343 {
2344 /* Process locked */
2345 __HAL_LOCK(hdsi);
2346
2347 hdsi->Instance->PHY_CTRL &= ~(DSI_HOST_PHY_CTRL_CKLANE_AUTO_CTRL);
2348 hdsi->Instance->PHY_CTRL |= (DSI_HOST_PHY_CTRL_CKLANE_HSTXREQ | hdsi->Init.AutomaticClockLaneControl);
2349
2350 /* Process unlocked */
2351 __HAL_UNLOCK(hdsi);
2352
2353
2354 return HAL_OK;
2355 }
2356
HAL_DSI_IsBusy(DSI_HandleTypeDef * hdsi)2357 uint8_t HAL_DSI_IsBusy(DSI_HandleTypeDef *hdsi)
2358 {
2359 if (!__HAL_DSI_IS_WRITE_FINISH(hdsi)) return 1;
2360 if (!__HAL_DSI_IS_MASTER_STATE(hdsi)) return 1;
2361
2362 if (0 == (hdsi->Instance->PHY_CTRL & DSI_HOST_PHY_CTRL_DLANE_REQULPS))
2363 {
2364 if (!__HAL_DSI_IS_DLANE0_STOP(hdsi)) return 1;
2365 }
2366
2367
2368 return 0;
2369 }
2370
2371
2372 #ifdef DSI_FIX_ME //PHY timing
2373
2374 /**
2375 * @brief Set Slew-Rate And Delay Tuning
2376 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2377 * the configuration information for the DSI.
2378 * @param CommDelay Communication delay to be adjusted.
2379 * This parameter can be any value of @ref DSI_Communication_Delay
2380 * @param Lane select between clock or data lanes.
2381 * This parameter can be any value of @ref DSI_Lane_Group
2382 * @param Value Custom value of the slew-rate or delay
2383 * @retval HAL status
2384 */
HAL_DSI_SetSlewRateAndDelayTuning(DSI_HandleTypeDef * hdsi,uint32_t CommDelay,uint32_t Lane,uint32_t Value)2385 HAL_StatusTypeDef HAL_DSI_SetSlewRateAndDelayTuning(DSI_HandleTypeDef *hdsi, uint32_t CommDelay, uint32_t Lane, uint32_t Value)
2386 {
2387 /* Process locked */
2388 __HAL_LOCK(hdsi);
2389
2390 /* Check function parameters */
2391 HAL_ASSERT(IS_DSI_COMMUNICATION_DELAY(CommDelay));
2392 HAL_ASSERT(IS_DSI_LANE_GROUP(Lane));
2393
2394 switch (CommDelay)
2395 {
2396 case DSI_SLEW_RATE_HSTX:
2397 if (Lane == DSI_CLOCK_LANE)
2398 {
2399 /* High-Speed Transmission Slew Rate Control on Clock Lane */
2400 hdsi->Instance->WPCR[1U] &= ~DSI_WPCR1_HSTXSRCCL;
2401 hdsi->Instance->WPCR[1U] |= Value << 16U;
2402 }
2403 else if (Lane == DSI_DATA_LANES)
2404 {
2405 /* High-Speed Transmission Slew Rate Control on Data Lanes */
2406 hdsi->Instance->WPCR[1U] &= ~DSI_WPCR1_HSTXSRCDL;
2407 hdsi->Instance->WPCR[1U] |= Value << 18U;
2408 }
2409 else
2410 {
2411 /* Process unlocked */
2412 __HAL_UNLOCK(hdsi);
2413
2414 return HAL_ERROR;
2415 }
2416 break;
2417 case DSI_SLEW_RATE_LPTX:
2418 if (Lane == DSI_CLOCK_LANE)
2419 {
2420 /* Low-Power transmission Slew Rate Compensation on Clock Lane */
2421 hdsi->Instance->WPCR[1U] &= ~DSI_WPCR1_LPSRCCL;
2422 hdsi->Instance->WPCR[1U] |= Value << 6U;
2423 }
2424 else if (Lane == DSI_DATA_LANES)
2425 {
2426 /* Low-Power transmission Slew Rate Compensation on Data Lanes */
2427 hdsi->Instance->WPCR[1U] &= ~DSI_WPCR1_LPSRCDL;
2428 hdsi->Instance->WPCR[1U] |= Value << 8U;
2429 }
2430 else
2431 {
2432 /* Process unlocked */
2433 __HAL_UNLOCK(hdsi);
2434
2435 return HAL_ERROR;
2436 }
2437 break;
2438 case DSI_HS_DELAY:
2439 if (Lane == DSI_CLOCK_LANE)
2440 {
2441 /* High-Speed Transmission Delay on Clock Lane */
2442 hdsi->Instance->WPCR[1U] &= ~DSI_WPCR1_HSTXDCL;
2443 hdsi->Instance->WPCR[1U] |= Value;
2444 }
2445 else if (Lane == DSI_DATA_LANES)
2446 {
2447 /* High-Speed Transmission Delay on Data Lanes */
2448 hdsi->Instance->WPCR[1U] &= ~DSI_WPCR1_HSTXDDL;
2449 hdsi->Instance->WPCR[1U] |= Value << 2U;
2450 }
2451 else
2452 {
2453 /* Process unlocked */
2454 __HAL_UNLOCK(hdsi);
2455
2456 return HAL_ERROR;
2457 }
2458 break;
2459 default:
2460 break;
2461 }
2462
2463 /* Process unlocked */
2464 __HAL_UNLOCK(hdsi);
2465
2466 return HAL_OK;
2467 }
2468
2469 /**
2470 * @brief Low-Power Reception Filter Tuning
2471 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2472 * the configuration information for the DSI.
2473 * @param Frequency cutoff frequency of low-pass filter at the input of LPRX
2474 * @retval HAL status
2475 */
HAL_DSI_SetLowPowerRXFilter(DSI_HandleTypeDef * hdsi,uint32_t Frequency)2476 HAL_StatusTypeDef HAL_DSI_SetLowPowerRXFilter(DSI_HandleTypeDef *hdsi, uint32_t Frequency)
2477 {
2478 /* Process locked */
2479 __HAL_LOCK(hdsi);
2480
2481 /* Low-Power RX low-pass Filtering Tuning */
2482 hdsi->Instance->WPCR[1U] &= ~DSI_WPCR1_LPRXFT;
2483 hdsi->Instance->WPCR[1U] |= Frequency << 25U;
2484
2485 /* Process unlocked */
2486 __HAL_UNLOCK(hdsi);
2487
2488 return HAL_OK;
2489 }
2490
2491 /**
2492 * @brief Activate an additional current path on all lanes to meet the SDDTx parameter
2493 * defined in the MIPI D-PHY specification
2494 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2495 * the configuration information for the DSI.
2496 * @param State ENABLE or DISABLE
2497 * @retval HAL status
2498 */
HAL_DSI_SetSDD(DSI_HandleTypeDef * hdsi,FunctionalState State)2499 HAL_StatusTypeDef HAL_DSI_SetSDD(DSI_HandleTypeDef *hdsi, FunctionalState State)
2500 {
2501 /* Process locked */
2502 __HAL_LOCK(hdsi);
2503
2504 /* Check function parameters */
2505 HAL_ASSERT(IS_FUNCTIONAL_STATE(State));
2506
2507 /* Activate/Disactivate additional current path on all lanes */
2508 hdsi->Instance->WPCR[1U] &= ~DSI_WPCR1_SDDC;
2509 hdsi->Instance->WPCR[1U] |= ((uint32_t)State << 12U);
2510
2511 /* Process unlocked */
2512 __HAL_UNLOCK(hdsi);
2513
2514 return HAL_OK;
2515 }
2516 #endif /* DSI_FIX_ME */
2517
2518 /**
2519 * @brief Custom lane pins configuration
2520 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2521 * the configuration information for the DSI.
2522 * @param CustomLane Function to be applyed on selected lane.
2523 * This parameter can be any value of @ref DSI_CustomLane
2524 * @param Lane select between clock or data lane 0 or data lane 1.
2525 * This parameter can be any value of @ref DSI_Lane_Select
2526 * @param State ENABLE or DISABLE
2527 * @retval HAL status
2528 */
HAL_DSI_SetLanePinsConfiguration(DSI_HandleTypeDef * hdsi,uint32_t CustomLane,uint32_t Lane,FunctionalState State)2529 HAL_StatusTypeDef HAL_DSI_SetLanePinsConfiguration(DSI_HandleTypeDef *hdsi, uint32_t CustomLane, uint32_t Lane, FunctionalState State)
2530 {
2531 /* Process locked */
2532 __HAL_LOCK(hdsi);
2533
2534 /* Check function parameters */
2535 HAL_ASSERT(IS_DSI_CUSTOM_LANE(CustomLane));
2536 HAL_ASSERT(IS_DSI_LANE(Lane));
2537 HAL_ASSERT(IS_FUNCTIONAL_STATE(State));
2538
2539 switch (CustomLane)
2540 {
2541 case DSI_SWAP_LANE_PINS:
2542 if (Lane == DSI_CLK_LANE)
2543 {
2544 /* Swap pins on clock lane */
2545 hdsi->PHY_Instance->CK_LANE_CTRL &= ~DSI_PHY_CK_LANE_CTRL_PN_SWAP;
2546 hdsi->PHY_Instance->CK_LANE_CTRL |= ((uint32_t)State << DSI_PHY_CK_LANE_CTRL_PN_SWAP_Pos);
2547 }
2548 else if (Lane == DSI_DATA_LANE0)
2549 {
2550 /* Swap pins on data lane 0 */
2551 hdsi->PHY_Instance->D_LANE0_CTRL &= ~DSI_PHY_D_LANE0_CTRL_PN_SWAP;
2552 hdsi->PHY_Instance->D_LANE0_CTRL |= ((uint32_t)State << DSI_PHY_D_LANE0_CTRL_PN_SWAP_Pos);
2553 }
2554 else if (Lane == DSI_DATA_LANE1)
2555 {
2556 /* Swap pins on data lane 1 */
2557 hdsi->PHY_Instance->D_LANE1_CTRL &= ~DSI_PHY_D_LANE1_CTRL_PN_SWAP;
2558 hdsi->PHY_Instance->D_LANE1_CTRL |= ((uint32_t)State << DSI_PHY_D_LANE1_CTRL_PN_SWAP_Pos);
2559 }
2560 else
2561 {
2562 /* Process unlocked */
2563 __HAL_UNLOCK(hdsi);
2564
2565 return HAL_ERROR;
2566 }
2567 break;
2568 #ifdef DSI_FIX_ME //NOT suppoert HS invert?
2569 case DSI_INVERT_HS_SIGNAL:
2570 if (Lane == DSI_CLK_LANE)
2571 {
2572 /* Invert HS signal on clock lane */
2573 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_HSICL;
2574 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 9U);
2575 }
2576 else if (Lane == DSI_DATA_LANE0)
2577 {
2578 /* Invert HS signal on data lane 0 */
2579 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_HSIDL0;
2580 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 10U);
2581 }
2582 else if (Lane == DSI_DATA_LANE1)
2583 {
2584 /* Invert HS signal on data lane 1 */
2585 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_HSIDL1;
2586 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 11U);
2587 }
2588 else
2589 {
2590 /* Process unlocked */
2591 __HAL_UNLOCK(hdsi);
2592
2593 return HAL_ERROR;
2594 }
2595 break;
2596 #endif
2597 default:
2598 break;
2599 }
2600
2601 /* Process unlocked */
2602 __HAL_UNLOCK(hdsi);
2603
2604 return HAL_OK;
2605 }
2606 #ifdef DSI_FIX_ME //PHY TIMING
2607
2608 /**
2609 * @brief Set custom timing for the PHY
2610 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2611 * the configuration information for the DSI.
2612 * @param Timing PHY timing to be adjusted.
2613 * This parameter can be any value of @ref DSI_PHY_Timing
2614 * @param State ENABLE or DISABLE
2615 * @param Value Custom value of the timing
2616 * @retval HAL status
2617 */
HAL_DSI_SetPHYTimings(DSI_HandleTypeDef * hdsi,uint32_t Timing,FunctionalState State,uint32_t Value)2618 HAL_StatusTypeDef HAL_DSI_SetPHYTimings(DSI_HandleTypeDef *hdsi, uint32_t Timing, FunctionalState State, uint32_t Value)
2619 {
2620 /* Process locked */
2621 __HAL_LOCK(hdsi);
2622
2623 /* Check function parameters */
2624 HAL_ASSERT(IS_DSI_PHY_TIMING(Timing));
2625 HAL_ASSERT(IS_FUNCTIONAL_STATE(State));
2626
2627 switch (Timing)
2628 {
2629 case DSI_TCLK_POST:
2630 /* Enable/Disable custom timing setting */
2631 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_TCLKPOSTEN;
2632 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 27U);
2633
2634 if (State != DISABLE)
2635 {
2636 /* Set custom value */
2637 hdsi->Instance->WPCR[4U] &= ~DSI_WPCR4_TCLKPOST;
2638 hdsi->Instance->WPCR[4U] |= Value & DSI_WPCR4_TCLKPOST;
2639 }
2640
2641 break;
2642 case DSI_TLPX_CLK:
2643 /* Enable/Disable custom timing setting */
2644 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_TLPXCEN;
2645 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 26U);
2646
2647 if (State != DISABLE)
2648 {
2649 /* Set custom value */
2650 hdsi->Instance->WPCR[3U] &= ~DSI_WPCR3_TLPXC;
2651 hdsi->Instance->WPCR[3U] |= (Value << 24U) & DSI_WPCR3_TLPXC;
2652 }
2653
2654 break;
2655 case DSI_THS_EXIT:
2656 /* Enable/Disable custom timing setting */
2657 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_THSEXITEN;
2658 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 25U);
2659
2660 if (State != DISABLE)
2661 {
2662 /* Set custom value */
2663 hdsi->Instance->WPCR[3U] &= ~DSI_WPCR3_THSEXIT;
2664 hdsi->Instance->WPCR[3U] |= (Value << 16U) & DSI_WPCR3_THSEXIT;
2665 }
2666
2667 break;
2668 case DSI_TLPX_DATA:
2669 /* Enable/Disable custom timing setting */
2670 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_TLPXDEN;
2671 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 24U);
2672
2673 if (State != DISABLE)
2674 {
2675 /* Set custom value */
2676 hdsi->Instance->WPCR[3U] &= ~DSI_WPCR3_TLPXD;
2677 hdsi->Instance->WPCR[3U] |= (Value << 8U) & DSI_WPCR3_TLPXD;
2678 }
2679
2680 break;
2681 case DSI_THS_ZERO:
2682 /* Enable/Disable custom timing setting */
2683 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_THSZEROEN;
2684 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 23U);
2685
2686 if (State != DISABLE)
2687 {
2688 /* Set custom value */
2689 hdsi->Instance->WPCR[3U] &= ~DSI_WPCR3_THSZERO;
2690 hdsi->Instance->WPCR[3U] |= Value & DSI_WPCR3_THSZERO;
2691 }
2692
2693 break;
2694 case DSI_THS_TRAIL:
2695 /* Enable/Disable custom timing setting */
2696 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_THSTRAILEN;
2697 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 22U);
2698
2699 if (State != DISABLE)
2700 {
2701 /* Set custom value */
2702 hdsi->Instance->WPCR[2U] &= ~DSI_WPCR2_THSTRAIL;
2703 hdsi->Instance->WPCR[2U] |= (Value << 24U) & DSI_WPCR2_THSTRAIL;
2704 }
2705
2706 break;
2707 case DSI_THS_PREPARE:
2708 /* Enable/Disable custom timing setting */
2709 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_THSPREPEN;
2710 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 21U);
2711
2712 if (State != DISABLE)
2713 {
2714 /* Set custom value */
2715 hdsi->Instance->WPCR[2U] &= ~DSI_WPCR2_THSPREP;
2716 hdsi->Instance->WPCR[2U] |= (Value << 16U) & DSI_WPCR2_THSPREP;
2717 }
2718
2719 break;
2720 case DSI_TCLK_ZERO:
2721 /* Enable/Disable custom timing setting */
2722 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_TCLKZEROEN;
2723 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 20U);
2724
2725 if (State != DISABLE)
2726 {
2727 /* Set custom value */
2728 hdsi->Instance->WPCR[2U] &= ~DSI_WPCR2_TCLKZERO;
2729 hdsi->Instance->WPCR[2U] |= (Value << 8U) & DSI_WPCR2_TCLKZERO;
2730 }
2731
2732 break;
2733 case DSI_TCLK_PREPARE:
2734 /* Enable/Disable custom timing setting */
2735 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_TCLKPREPEN;
2736 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 19U);
2737
2738 if (State != DISABLE)
2739 {
2740 /* Set custom value */
2741 hdsi->Instance->WPCR[2U] &= ~DSI_WPCR2_TCLKPREP;
2742 hdsi->Instance->WPCR[2U] |= Value & DSI_WPCR2_TCLKPREP;
2743 }
2744
2745 break;
2746 default:
2747 break;
2748 }
2749
2750 /* Process unlocked */
2751 __HAL_UNLOCK(hdsi);
2752
2753 return HAL_OK;
2754 }
2755
2756 /**
2757 * @brief Force the Clock/Data Lane in TX Stop Mode
2758 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2759 * the configuration information for the DSI.
2760 * @param Lane select between clock or data lanes.
2761 * This parameter can be any value of @ref DSI_Lane_Group
2762 * @param State ENABLE or DISABLE
2763 * @retval HAL status
2764 */
HAL_DSI_ForceTXStopMode(DSI_HandleTypeDef * hdsi,uint32_t Lane,FunctionalState State)2765 HAL_StatusTypeDef HAL_DSI_ForceTXStopMode(DSI_HandleTypeDef *hdsi, uint32_t Lane, FunctionalState State)
2766 {
2767 /* Process locked */
2768 __HAL_LOCK(hdsi);
2769
2770 /* Check function parameters */
2771 HAL_ASSERT(IS_DSI_LANE_GROUP(Lane));
2772 HAL_ASSERT(IS_FUNCTIONAL_STATE(State));
2773
2774 if (Lane == DSI_CLOCK_LANE)
2775 {
2776 /* Force/Unforce the Clock Lane in TX Stop Mode */
2777 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_FTXSMCL;
2778 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 12U);
2779 }
2780 else if (Lane == DSI_DATA_LANES)
2781 {
2782 /* Force/Unforce the Data Lanes in TX Stop Mode */
2783 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_FTXSMDL;
2784 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 13U);
2785 }
2786 else
2787 {
2788 /* Process unlocked */
2789 __HAL_UNLOCK(hdsi);
2790
2791 return HAL_ERROR;
2792 }
2793
2794 /* Process unlocked */
2795 __HAL_UNLOCK(hdsi);
2796
2797 return HAL_OK;
2798 }
2799
2800 /**
2801 * @brief Force LP Receiver in Low-Power Mode
2802 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2803 * the configuration information for the DSI.
2804 * @param State ENABLE or DISABLE
2805 * @retval HAL status
2806 */
HAL_DSI_ForceRXLowPower(DSI_HandleTypeDef * hdsi,FunctionalState State)2807 HAL_StatusTypeDef HAL_DSI_ForceRXLowPower(DSI_HandleTypeDef *hdsi, FunctionalState State)
2808 {
2809 /* Process locked */
2810 __HAL_LOCK(hdsi);
2811
2812 /* Check function parameters */
2813 HAL_ASSERT(IS_FUNCTIONAL_STATE(State));
2814
2815 /* Force/Unforce LP Receiver in Low-Power Mode */
2816 hdsi->Instance->WPCR[1U] &= ~DSI_WPCR1_FLPRXLPM;
2817 hdsi->Instance->WPCR[1U] |= ((uint32_t)State << 22U);
2818
2819 /* Process unlocked */
2820 __HAL_UNLOCK(hdsi);
2821
2822 return HAL_OK;
2823 }
2824
2825 /**
2826 * @brief Force Data Lanes in RX Mode after a BTA
2827 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2828 * the configuration information for the DSI.
2829 * @param State ENABLE or DISABLE
2830 * @retval HAL status
2831 */
HAL_DSI_ForceDataLanesInRX(DSI_HandleTypeDef * hdsi,FunctionalState State)2832 HAL_StatusTypeDef HAL_DSI_ForceDataLanesInRX(DSI_HandleTypeDef *hdsi, FunctionalState State)
2833 {
2834 /* Process locked */
2835 __HAL_LOCK(hdsi);
2836
2837 /* Check function parameters */
2838 HAL_ASSERT(IS_FUNCTIONAL_STATE(State));
2839
2840 /* Force Data Lanes in RX Mode */
2841 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_TDDL;
2842 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 16U);
2843
2844 /* Process unlocked */
2845 __HAL_UNLOCK(hdsi);
2846
2847 return HAL_OK;
2848 }
2849
2850 /**
2851 * @brief Enable a pull-down on the lanes to prevent from floating states when unused
2852 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2853 * the configuration information for the DSI.
2854 * @param State ENABLE or DISABLE
2855 * @retval HAL status
2856 */
HAL_DSI_SetPullDown(DSI_HandleTypeDef * hdsi,FunctionalState State)2857 HAL_StatusTypeDef HAL_DSI_SetPullDown(DSI_HandleTypeDef *hdsi, FunctionalState State)
2858 {
2859 /* Process locked */
2860 __HAL_LOCK(hdsi);
2861
2862 /* Check function parameters */
2863 HAL_ASSERT(IS_FUNCTIONAL_STATE(State));
2864
2865 /* Enable/Disable pull-down on lanes */
2866 hdsi->Instance->WPCR[0U] &= ~DSI_WPCR0_PDEN;
2867 hdsi->Instance->WPCR[0U] |= ((uint32_t)State << 18U);
2868
2869 /* Process unlocked */
2870 __HAL_UNLOCK(hdsi);
2871
2872 return HAL_OK;
2873 }
2874 #endif
2875
2876 /**
2877 * @brief Switch off the contention detection on data lanes
2878 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2879 * the configuration information for the DSI.
2880 * @param State ENABLE or DISABLE
2881 * @retval HAL status
2882 */
HAL_DSI_SetContentionDetectionOff(DSI_HandleTypeDef * hdsi,FunctionalState State)2883 HAL_StatusTypeDef HAL_DSI_SetContentionDetectionOff(DSI_HandleTypeDef *hdsi, FunctionalState State)
2884 {
2885 /* Process locked */
2886 __HAL_LOCK(hdsi);
2887
2888 /* Check function parameters */
2889 HAL_ASSERT(IS_FUNCTIONAL_STATE(State));
2890
2891 /* Contention Detection on Data Lanes OFF */
2892 hdsi->PHY_Instance->D_LANE0_CTRL &= ~DSI_PHY_D_LANE0_CTRL_CONTENTION_DET_EN;
2893 hdsi->PHY_Instance->D_LANE0_CTRL |= ((uint32_t)State << DSI_PHY_D_LANE0_CTRL_CONTENTION_DET_EN_Pos);
2894
2895 /* Process unlocked */
2896 __HAL_UNLOCK(hdsi);
2897
2898 return HAL_OK;
2899 }
2900
2901 /**
2902 * @}
2903 */
2904
2905 /** @defgroup DSI_Group4 Peripheral State and Errors functions
2906 * @brief Peripheral State and Errors functions
2907 *
2908 @verbatim
2909 ===============================================================================
2910 ##### Peripheral State and Errors functions #####
2911 ===============================================================================
2912 [..]
2913 This subsection provides functions allowing to
2914 (+) Check the DSI state.
2915 (+) Get error code.
2916
2917 @endverbatim
2918 * @{
2919 */
2920
2921 /**
2922 * @brief Return the DSI state
2923 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2924 * the configuration information for the DSI.
2925 * @retval HAL state
2926 */
HAL_DSI_GetState(DSI_HandleTypeDef * hdsi)2927 HAL_DSI_StateTypeDef HAL_DSI_GetState(DSI_HandleTypeDef *hdsi)
2928 {
2929 return hdsi->State;
2930 }
2931
2932 /**
2933 * @brief Return the DSI error code
2934 * @param hdsi pointer to a DSI_HandleTypeDef structure that contains
2935 * the configuration information for the DSI.
2936 * @retval DSI Error Code
2937 */
HAL_DSI_GetError(DSI_HandleTypeDef * hdsi)2938 uint32_t HAL_DSI_GetError(DSI_HandleTypeDef *hdsi)
2939 {
2940 /* Get the error code */
2941 return hdsi->ErrorCode;
2942 }
2943
2944 /**
2945 * @}
2946 */
2947
2948 /**
2949 * @}
2950 */
2951
2952 /**
2953 * @}
2954 */
2955
2956 #endif /* HAL_DSI_MODULE_ENABLED */
2957 /**
2958 * @}
2959 */