1 /*
2  * Copyright 2017, 2019-2020 NXP
3  * All rights reserved.
4  *
5  *
6  * SPDX-License-Identifier: BSD-3-Clause
7  */
8 
9 #ifndef FSL_MIPI_CSI2RX_H_
10 #define FSL_MIPI_CSI2RX_H_
11 
12 #include "fsl_common.h"
13 
14 /*!
15  * @addtogroup csi2rx
16  * @{
17  */
18 
19 /*******************************************************************************
20  * Definitions
21  ******************************************************************************/
22 
23 /*! @name Driver version */
24 /*! @{ */
25 /*! @brief CSI2RX driver version. */
26 #define FSL_CSI2RX_DRIVER_VERSION (MAKE_VERSION(2, 0, 4))
27 /*! @} */
28 
29 #if (defined(FSL_FEATURE_CSI2RX_HAS_NO_REG_PREFIX) && FSL_FEATURE_CSI2RX_HAS_NO_REG_PREFIX)
30 
31 #define CSI2RX_REG_CFG_NUM_LANES(base)             (base)->CFG_NUM_LANES
32 #define CSI2RX_REG_CFG_DISABLE_DATA_LANES(base)    (base)->CFG_DISABLE_DATA_LANES
33 #define CSI2RX_REG_BIT_ERR(base)                   (base)->BIT_ERR
34 #define CSI2RX_REG_IRQ_STATUS(base)                (base)->IRQ_STATUS
35 #define CSI2RX_REG_IRQ_MASK(base)                  (base)->IRQ_MASK
36 #define CSI2RX_REG_ULPS_STATUS(base)               (base)->ULPS_STATUS
37 #define CSI2RX_REG_PPI_ERRSOT_HS(base)             (base)->PPI_ERRSOT_HS
38 #define CSI2RX_REG_PPI_ERRSOTSYNC_HS(base)         (base)->PPI_ERRSOTSYNC_HS
39 #define CSI2RX_REG_PPI_ERRESC(base)                (base)->PPI_ERRESC
40 #define CSI2RX_REG_PPI_ERRSYNCESC(base)            (base)->PPI_ERRSYNCESC
41 #define CSI2RX_REG_PPI_ERRCONTROL(base)            (base)->PPI_ERRCONTROL
42 #define CSI2RX_REG_CFG_DISABLE_PAYLOAD_0(base)     (base)->CFG_DISABLE_PAYLOAD_0
43 #define CSI2RX_REG_CFG_DISABLE_PAYLOAD_1(base)     (base)->CFG_DISABLE_PAYLOAD_1
44 #define CSI2RX_REG_CFG_IGNORE_VC(base)             (base)->CFG_IGNORE_VC
45 #define CSI2RX_REG_CFG_VID_VC(base)                (base)->CFG_VID_VC
46 #define CSI2RX_REG_CFG_VID_P_FIFO_SEND_LEVEL(base) (base)->CFG_VID_P_FIFO_SEND_LEVEL
47 #define CSI2RX_REG_CFG_VID_VSYNC(base)             (base)->CFG_VID_VSYNC
48 #define CSI2RX_REG_CFG_VID_HSYNC_FP(base)          (base)->CFG_VID_HSYNC_FP
49 #define CSI2RX_REG_CFG_VID_HSYNC(base)             (base)->CFG_VID_HSYNC
50 #define CSI2RX_REG_CFG_VID_HSYNC_BP(base)          (base)->CFG_VID_HSYNC_BP
51 
52 #else
53 
54 #define CSI2RX_REG_CFG_NUM_LANES(base)             (base)->CSI2RX_CFG_NUM_LANES
55 #define CSI2RX_REG_CFG_DISABLE_DATA_LANES(base)    (base)->CSI2RX_CFG_DISABLE_DATA_LANES
56 #define CSI2RX_REG_BIT_ERR(base)                   (base)->CSI2RX_BIT_ERR
57 #define CSI2RX_REG_IRQ_STATUS(base)                (base)->CSI2RX_IRQ_STATUS
58 #define CSI2RX_REG_IRQ_MASK(base)                  (base)->CSI2RX_IRQ_MASK
59 #define CSI2RX_REG_ULPS_STATUS(base)               (base)->CSI2RX_ULPS_STATUS
60 #define CSI2RX_REG_PPI_ERRSOT_HS(base)             (base)->CSI2RX_PPI_ERRSOT_HS
61 #define CSI2RX_REG_PPI_ERRSOTSYNC_HS(base)         (base)->CSI2RX_PPI_ERRSOTSYNC_HS
62 #define CSI2RX_REG_PPI_ERRESC(base)                (base)->CSI2RX_PPI_ERRESC
63 #define CSI2RX_REG_PPI_ERRSYNCESC(base)            (base)->CSI2RX_PPI_ERRSYNCESC
64 #define CSI2RX_REG_PPI_ERRCONTROL(base)            (base)->CSI2RX_PPI_ERRCONTROL
65 #define CSI2RX_REG_CFG_DISABLE_PAYLOAD_0(base)     (base)->CSI2RX_CFG_DISABLE_PAYLOAD_0
66 #define CSI2RX_REG_CFG_DISABLE_PAYLOAD_1(base)     (base)->CSI2RX_CFG_DISABLE_PAYLOAD_1
67 #define CSI2RX_REG_CFG_IGNORE_VC(base)             (base)->CSI2RX_CFG_IGNORE_VC
68 #define CSI2RX_REG_CFG_VID_VC(base)                (base)->CSI2RX_CFG_VID_VC
69 #define CSI2RX_REG_CFG_VID_P_FIFO_SEND_LEVEL(base) (base)->CSI2RX_CFG_VID_P_FIFO_SEND_LEVEL
70 #define CSI2RX_REG_CFG_VID_VSYNC(base)             (base)->CSI2RX_CFG_VID_VSYNC
71 #define CSI2RX_REG_CFG_VID_HSYNC_FP(base)          (base)->CSI2RX_CFG_VID_HSYNC_FP
72 #define CSI2RX_REG_CFG_VID_HSYNC(base)             (base)->CSI2RX_CFG_VID_HSYNC
73 #define CSI2RX_REG_CFG_VID_HSYNC_BP(base)          (base)->CSI2RX_CFG_VID_HSYNC_BP
74 
75 #endif
76 
77 #ifndef MIPI_CSI2RX_CSI2RX_CFG_NUM_LANES_csi2rx_cfg_num_lanes_MASK
78 #define MIPI_CSI2RX_CSI2RX_CFG_NUM_LANES_csi2rx_cfg_num_lanes_MASK MIPI_CSI2RX_CFG_NUM_LANES_CFG_NUM_LANES_MASK
79 #endif
80 
81 #ifndef MIPI_CSI2RX_CSI2RX_IRQ_MASK_csi2rx_irq_mask_MASK
82 #define MIPI_CSI2RX_CSI2RX_IRQ_MASK_csi2rx_irq_mask_MASK MIPI_CSI2RX_IRQ_MASK_IRQ_MASK_MASK
83 #endif
84 
85 /*! @brief CSI2RX data lanes.  */
86 enum _csi2rx_data_lane
87 {
88     kCSI2RX_DataLane0 = (1U << 0U), /*!< Data lane 0. */
89     kCSI2RX_DataLane1 = (1U << 1U), /*!< Data lane 1. */
90     kCSI2RX_DataLane2 = (1U << 2U), /*!< Data lane 2. */
91     kCSI2RX_DataLane3 = (1U << 3U)  /*!< Data lane 3. */
92 };
93 
94 /*! @brief CSI2RX payload type.  */
95 enum _csi2rx_payload
96 {
97     kCSI2RX_PayloadGroup0Null         = (1U << 0U),  /*!< NULL. */
98     kCSI2RX_PayloadGroup0Blank        = (1U << 1U),  /*!< Blank. */
99     kCSI2RX_PayloadGroup0Embedded     = (1U << 2U),  /*!< Embedded. */
100     kCSI2RX_PayloadGroup0YUV420_8Bit  = (1U << 10U), /*!< Legacy YUV420 8 bit. */
101     kCSI2RX_PayloadGroup0YUV422_8Bit  = (1U << 14U), /*!< YUV422 8 bit. */
102     kCSI2RX_PayloadGroup0YUV422_10Bit = (1U << 15U), /*!< YUV422 10 bit. */
103     kCSI2RX_PayloadGroup0RGB444       = (1U << 16U), /*!< RGB444. */
104     kCSI2RX_PayloadGroup0RGB555       = (1U << 17U), /*!< RGB555. */
105     kCSI2RX_PayloadGroup0RGB565       = (1U << 18U), /*!< RGB565. */
106     kCSI2RX_PayloadGroup0RGB666       = (1U << 19U), /*!< RGB666. */
107     kCSI2RX_PayloadGroup0RGB888       = (1U << 20U), /*!< RGB888. */
108     kCSI2RX_PayloadGroup0Raw6         = (1U << 24U), /*!< Raw 6. */
109     kCSI2RX_PayloadGroup0Raw7         = (1U << 25U), /*!< Raw 7. */
110     kCSI2RX_PayloadGroup0Raw8         = (1U << 26U), /*!< Raw 8. */
111     kCSI2RX_PayloadGroup0Raw10        = (1U << 27U), /*!< Raw 10. */
112     kCSI2RX_PayloadGroup0Raw12        = (1U << 28U), /*!< Raw 12. */
113     kCSI2RX_PayloadGroup0Raw14        = (1U << 29U), /*!< Raw 14. */
114     kCSI2RX_PayloadGroup1UserDefined1 = (1U << 0U),  /*!< User defined 8-bit data type 1, 0x30. */
115     kCSI2RX_PayloadGroup1UserDefined2 = (1U << 1U),  /*!< User defined 8-bit data type 2, 0x31. */
116     kCSI2RX_PayloadGroup1UserDefined3 = (1U << 2U),  /*!< User defined 8-bit data type 3, 0x32. */
117     kCSI2RX_PayloadGroup1UserDefined4 = (1U << 3U),  /*!< User defined 8-bit data type 4, 0x33. */
118     kCSI2RX_PayloadGroup1UserDefined5 = (1U << 4U),  /*!< User defined 8-bit data type 5, 0x34. */
119     kCSI2RX_PayloadGroup1UserDefined6 = (1U << 5U),  /*!< User defined 8-bit data type 6, 0x35. */
120     kCSI2RX_PayloadGroup1UserDefined7 = (1U << 6U),  /*!< User defined 8-bit data type 7, 0x36. */
121     kCSI2RX_PayloadGroup1UserDefined8 = (1U << 7U)   /*!< User defined 8-bit data type 8, 0x37. */
122 };
123 
124 /*! @brief CSI2RX configuration.  */
125 typedef struct _csi2rx_config
126 {
127     uint8_t laneNum;          /*!< Number of active lanes used for receiving data. */
128     uint8_t tHsSettle_EscClk; /*!< Number of rx_clk_esc clock periods for T_HS_SETTLE.
129                                    The T_HS_SETTLE should be in the range of
130                                    85ns + 6UI to 145ns + 10UI. */
131 } csi2rx_config_t;
132 
133 /*! @brief MIPI CSI2RX bit errors. */
134 enum _csi2rx_bit_error
135 {
136     kCSI2RX_BitErrorEccTwoBit = (1U << 0U), /*!< ECC two bit error has occurred. */
137     kCSI2RX_BitErrorEccOneBit = (1U << 1U)  /*!< ECC one bit error has occurred. */
138 };
139 
140 /*! @brief MIPI CSI2RX PPI error types. */
141 typedef enum _csi2rx_ppi_error
142 {
143     kCSI2RX_PpiErrorSotHs,     /*!< CSI2RX DPHY PPI error ErrSotHS. */
144     kCSI2RX_PpiErrorSotSyncHs, /*!< CSI2RX DPHY PPI error ErrSotSync_HS. */
145     kCSI2RX_PpiErrorEsc,       /*!< CSI2RX DPHY PPI error ErrEsc. */
146     kCSI2RX_PpiErrorSyncEsc,   /*!< CSI2RX DPHY PPI error ErrSyncEsc. */
147     kCSI2RX_PpiErrorControl,   /*!< CSI2RX DPHY PPI error ErrControl. */
148 } csi2rx_ppi_error_t;
149 
150 /*! @brief MIPI CSI2RX interrupt. */
151 enum _csi2rx_interrupt
152 {
153     kCSI2RX_InterruptCrcError         = (1U << 0U), /* CRC error. */
154     kCSI2RX_InterruptEccOneBitError   = (1U << 1U), /* One bit ECC error. */
155     kCSI2RX_InterruptEccTwoBitError   = (1U << 2U), /* One bit ECC error. */
156     kCSI2RX_InterruptUlpsStatusChange = (1U << 3U), /* ULPS status changed. */
157     kCSI2RX_InterruptErrorSotHs       = (1U << 4U), /* D-PHY ErrSotHS occurred. */
158     kCSI2RX_InterruptErrorSotSyncHs   = (1U << 5U), /* D-PHY ErrSotSync_HS occurred. */
159     kCSI2RX_InterruptErrorEsc         = (1U << 6U), /* D-PHY ErrEsc occurred. */
160     kCSI2RX_InterruptErrorSyncEsc     = (1U << 7U), /* D-PHY ErrSyncEsc occurred. */
161     kCSI2RX_InterruptErrorControl     = (1U << 8U), /* D-PHY ErrControl occurred. */
162 };
163 
164 /*! @brief MIPI CSI2RX D-PHY ULPS state. */
165 enum _csi2rx_ulps_status
166 {
167     kCSI2RX_ClockLaneUlps = (1U << 0U), /*!< Clock lane is in ULPS state. */
168     kCSI2RX_DataLane0Ulps = (1U << 1U), /*!< Data lane 0 is in ULPS state. */
169     kCSI2RX_DataLane1Ulps = (1U << 2U), /*!< Data lane 1 is in ULPS state. */
170     kCSI2RX_DataLane2Ulps = (1U << 3U), /*!< Data lane 2 is in ULPS state. */
171     kCSI2RX_DataLane3Ulps = (1U << 4U), /*!< Data lane 3 is in ULPS state. */
172     kCSI2RX_ClockLaneMark = (1U << 5U), /*!< Clock lane is in mark state. */
173     kCSI2RX_DataLane0Mark = (1U << 6U), /*!< Data lane 0 is in mark state. */
174     kCSI2RX_DataLane1Mark = (1U << 7U), /*!< Data lane 1 is in mark state. */
175     kCSI2RX_DataLane2Mark = (1U << 8U), /*!< Data lane 2 is in mark state. */
176     kCSI2RX_DataLane3Mark = (1U << 9U), /*!< Data lane 3 is in mark state. */
177 };
178 
179 /*******************************************************************************
180  * API
181  ******************************************************************************/
182 #if defined(__cplusplus)
183 extern "C" {
184 #endif
185 
186 /*!
187  * @brief Enables and configures the CSI2RX peripheral module.
188  *
189  * @param base CSI2RX peripheral address.
190  * @param config CSI2RX module configuration structure.
191  */
192 void CSI2RX_Init(MIPI_CSI2RX_Type *base, const csi2rx_config_t *config);
193 
194 /*!
195  * @brief Disables the CSI2RX peripheral module.
196  *
197  * @param base CSI2RX peripheral address.
198  */
199 void CSI2RX_Deinit(MIPI_CSI2RX_Type *base);
200 
201 /*!
202  * @brief Gets the MIPI CSI2RX bit error status.
203  *
204  * This function gets the RX bit error status, the return value could be compared
205  * with @ref _csi2rx_bit_error. If one bit ECC error detected, the return value
206  * could be passed to the function @ref CSI2RX_GetEccBitErrorPosition to get the
207  * position of the ECC error bit.
208  *
209  * Example:
210  * @code
211     uint32_t bitError;
212     uint32_t bitErrorPosition;
213 
214     bitError = CSI2RX_GetBitError(MIPI_CSI2RX);
215 
216     if (kCSI2RX_BitErrorEccTwoBit & bitError)
217     {
218         Two bits error;
219     }
220     else if (kCSI2RX_BitErrorEccOneBit & bitError)
221     {
222         One bits error;
223         bitErrorPosition = CSI2RX_GetEccBitErrorPosition(bitError);
224     }
225    @endcode
226  *
227  * @param base CSI2RX peripheral address.
228  * @return The RX bit error status.
229  */
CSI2RX_GetBitError(MIPI_CSI2RX_Type * base)230 static inline uint32_t CSI2RX_GetBitError(MIPI_CSI2RX_Type *base)
231 {
232     return CSI2RX_REG_BIT_ERR(base);
233 }
234 
235 /*!
236  * @brief Get ECC one bit error bit position.
237  *
238  * If @ref CSI2RX_GetBitError detects ECC one bit error, this function could
239  * extract the error bit position from the return value of @ref CSI2RX_GetBitError.
240  *
241  * @param bitError The bit error returned by @ref CSI2RX_GetBitError.
242  * @return The position of error bit.
243  */
CSI2RX_GetEccBitErrorPosition(uint32_t bitError)244 static inline uint32_t CSI2RX_GetEccBitErrorPosition(uint32_t bitError)
245 {
246     return (bitError >> 2U) & 0x1FU;
247 }
248 
249 /*!
250  * @brief Gets the MIPI CSI2RX D-PHY ULPS status.
251  *
252  * Example to check whether data lane 0 is in ULPS status.
253  * @code
254    uint32_t status = CSI2RX_GetUlpsStatus(MIPI_CSI2RX);
255 
256    if (kCSI2RX_DataLane0Ulps & status)
257    {
258        Data lane 0 is in ULPS status.
259    }
260    @endcode
261  *
262  * @param base CSI2RX peripheral address.
263  * @return The MIPI CSI2RX D-PHY ULPS status, it is OR'ed value or @ref _csi2rx_ulps_status.
264  */
CSI2RX_GetUlpsStatus(MIPI_CSI2RX_Type * base)265 static inline uint32_t CSI2RX_GetUlpsStatus(MIPI_CSI2RX_Type *base)
266 {
267     return CSI2RX_REG_ULPS_STATUS(base);
268 }
269 
270 /*!
271  * @brief Gets the MIPI CSI2RX D-PHY PPI error lanes.
272  *
273  * This function checks the PPI error occurred on which data lanes, the returned
274  * value is OR'ed value of @ref csi2rx_ppi_error_t. For example, if the ErrSotHS
275  * is detected, to check the ErrSotHS occurred on which data lanes, use like this:
276  *
277  * @code
278    uint32_t errorDataLanes = CSI2RX_GetPpiErrorDataLanes(MIPI_CSI2RX, kCSI2RX_PpiErrorSotHs);
279 
280    if (kCSI2RX_DataLane0 & errorDataLanes)
281    {
282        ErrSotHS occurred on data lane 0.
283    }
284 
285    if (kCSI2RX_DataLane1 & errorDataLanes)
286    {
287        ErrSotHS occurred on data lane 1.
288    }
289    @endcode
290  *
291  * @param base CSI2RX peripheral address.
292  * @param errorType What kind of error to check.
293  * @return The data lane mask that error @p errorType occurred.
294  */
CSI2RX_GetPpiErrorDataLanes(MIPI_CSI2RX_Type * base,csi2rx_ppi_error_t errorType)295 static inline uint32_t CSI2RX_GetPpiErrorDataLanes(MIPI_CSI2RX_Type *base, csi2rx_ppi_error_t errorType)
296 {
297     uint32_t errorLanes;
298 
299     if (kCSI2RX_PpiErrorSotHs == errorType)
300     {
301         errorLanes = CSI2RX_REG_PPI_ERRSOT_HS(base);
302     }
303     else if (kCSI2RX_PpiErrorSotSyncHs == errorType)
304     {
305         errorLanes = CSI2RX_REG_PPI_ERRSOTSYNC_HS(base);
306     }
307     else if (kCSI2RX_PpiErrorEsc == errorType)
308     {
309         errorLanes = CSI2RX_REG_PPI_ERRESC(base);
310     }
311     else if (kCSI2RX_PpiErrorSyncEsc == errorType)
312     {
313         errorLanes = CSI2RX_REG_PPI_ERRSYNCESC(base);
314     }
315     else
316     {
317         errorLanes = CSI2RX_REG_PPI_ERRCONTROL(base);
318     }
319 
320     return errorLanes;
321 }
322 
323 /*!
324  * @brief Enable the MIPI CSI2RX interrupts.
325  *
326  * This function enables the MIPI CSI2RX interrupts. The interrupts to enable
327  * are passed in as an OR'ed value of @ref _csi2rx_interrupt. For example, to enable
328  * one bit and two bit ECC error interrupts, use like this:
329  *
330  * @code
331    CSI2RX_EnableInterrupts(MIPI_CSI2RX, kCSI2RX_InterruptEccOneBitError | kCSI2RX_InterruptEccTwoBitError);
332    @endcode
333  *
334  * @param base CSI2RX peripheral address.
335  * @param mask OR'ed value of @ref _csi2rx_interrupt.
336  */
CSI2RX_EnableInterrupts(MIPI_CSI2RX_Type * base,uint32_t mask)337 static inline void CSI2RX_EnableInterrupts(MIPI_CSI2RX_Type *base, uint32_t mask)
338 {
339     CSI2RX_REG_IRQ_MASK(base) &= ~mask;
340 }
341 
342 /*!
343  * @brief Disable the MIPI CSI2RX interrupts.
344  *
345  * This function disables the MIPI CSI2RX interrupts. The interrupts to disable
346  * are passed in as an OR'ed value of @ref _csi2rx_interrupt. For example, to disable
347  * one bit and two bit ECC error interrupts, use like this:
348  *
349  * @code
350    CSI2RX_DisableInterrupts(MIPI_CSI2RX, kCSI2RX_InterruptEccOneBitError | kCSI2RX_InterruptEccTwoBitError);
351    @endcode
352  *
353  * @param base CSI2RX peripheral address.
354  * @param mask OR'ed value of @ref _csi2rx_interrupt.
355  */
CSI2RX_DisableInterrupts(MIPI_CSI2RX_Type * base,uint32_t mask)356 static inline void CSI2RX_DisableInterrupts(MIPI_CSI2RX_Type *base, uint32_t mask)
357 {
358     CSI2RX_REG_IRQ_MASK(base) |= mask;
359 }
360 
361 /*!
362  * @brief Get the MIPI CSI2RX interrupt status.
363  *
364  * This function returns the MIPI CSI2RX interrupts status as an OR'ed value
365  * of @ref _csi2rx_interrupt.
366  *
367  * @param base CSI2RX peripheral address.
368  * @return OR'ed value of @ref _csi2rx_interrupt.
369  */
CSI2RX_GetInterruptStatus(MIPI_CSI2RX_Type * base)370 static inline uint32_t CSI2RX_GetInterruptStatus(MIPI_CSI2RX_Type *base)
371 {
372     return CSI2RX_REG_IRQ_STATUS(base);
373 }
374 
375 #if defined(__cplusplus)
376 }
377 #endif
378 
379 /*!
380  *@}
381  */
382 
383 #endif /* FSL_MIPI_CSI2RX_H_ */
384