1 /***************************************************************************//**
2 * \file cy_pdm_pcm_v2.c
3 * \version 1.10
4 *
5 * The source code file for the PDM_PCM driver.
6 *
7 ********************************************************************************
8 * \copyright
9 * Copyright 2019-2022 Cypress Semiconductor Corporation
10 * SPDX-License-Identifier: Apache-2.0
11 *
12 * Licensed under the Apache License, Version 2.0 (the "License");
13 * you may not use this file except in compliance with the License.
14 * You may obtain a copy of the License at
15 *
16 * http://www.apache.org/licenses/LICENSE-2.0
17 *
18 * Unless required by applicable law or agreed to in writing, software
19 * distributed under the License is distributed on an "AS IS" BASIS,
20 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
21 * See the License for the specific language governing permissions and
22 * limitations under the License.
23 *******************************************************************************/
24
25 #include "cy_device.h"
26
27 #if defined (CY_IP_MXPDM)
28
29 #include "cy_pdm_pcm_v2.h"
30
31 CY_MISRA_DEVIATE_BLOCK_START('MISRA C-2012 Rule 14.3', 14, \
32 'Checked manually, passed 1 or 0 in _BOOL2FLD for appropriate functionality.')
33
34 CY_MISRA_DEVIATE_BLOCK_START('MISRA C-2012 Rule 10.1', 1, \
35 'Checked manually, passed 1 or 0 in _BOOL2FLD for appropriate functionality.')
36
37 /**
38 * \addtogroup group_pdm_pcm_functions_v2
39 * \{
40 */
41
42 /******************************************************************************
43 * Function Name: Cy_PDM_PCM_Channel_Init
44 ***************************************************************************//**
45 *
46 * Initialize the PDM-PCM Channel
47 *
48 * \pre Make sure PDM-PCM is intialized before calling this function. \ref Cy_PDM_PCM_Init
49 *
50 * \param base The pointer to the PDM-PCM instance address
51 * \param channel_config The pointer to a configuration structure.
52 * \param channel_num The channel number to be initialized.
53 * \return error / status code. See \ref cy_en_pdm_pcm_status_t.
54 *
55 * \funcusage
56 * \snippet pdm_pcmv2/snippet/main.c snippet_Cy_PDM_PCM_Channel_Init
57 *
58 *******************************************************************************/
Cy_PDM_PCM_Channel_Init(PDM_Type * base,cy_stc_pdm_pcm_channel_config_t const * channel_config,uint8_t channel_num)59 cy_en_pdm_pcm_status_t Cy_PDM_PCM_Channel_Init(PDM_Type * base, cy_stc_pdm_pcm_channel_config_t const * channel_config, uint8_t channel_num)
60 {
61 cy_en_pdm_pcm_status_t ret = CY_PDM_PCM_BAD_PARAM;
62
63 if((NULL != base) && (NULL != channel_config))
64 {
65 CY_ASSERT_L2(CY_PDM_PCM_IS_WORD_SIZE_VALID(channel_config->wordSize));
66 CY_ASSERT_L2(CY_PDM_PCM_IS_SIGNEXTENSION_VALID(channel_config->signExtension));
67 CY_ASSERT_L2(CY_PDM_PCM_IS_TRIG_LEVEL(channel_config->rxFifoTriggerLevel));
68 CY_ASSERT_L2(CY_PDM_PCM_IS_SCALE_VALID(channel_config->fir0_scale));
69 CY_ASSERT_L2(CY_PDM_PCM_IS_SCALE_VALID(channel_config->fir1_scale));
70
71
72 ret = CY_PDM_PCM_SUCCESS;
73
74
75 PDM_PCM_RX_FIFO_CTL(base, channel_num) = _VAL2FLD(PDM_CH_RX_FIFO_CTL_TRIGGER_LEVEL, channel_config->rxFifoTriggerLevel);
76
77
78 PDM_PCM_CH_CTL(base, channel_num) = _VAL2FLD(PDM_CH_CTL_WORD_SIZE, channel_config->wordSize) |
79 _BOOL2FLD(PDM_CH_CTL_WORD_SIGN_EXTEND, channel_config->signExtension) |
80 _BOOL2FLD(PDM_CH_CTL_ENABLED, CY_PDM_PCM_ENABLE);
81
82 PDM_PCM_CH_IF_CTL(base, channel_num) = _VAL2FLD(PDM_CH_IF_CTL_SAMPLE_DELAY, channel_config->sampledelay);
83
84
85 PDM_PCM_CH_CIC_CTL(base, channel_num) = ((uint32_t)channel_config->cic_decim_code);
86
87 PDM_PCM_CH_FIR0_CTL(base, channel_num) = _VAL2FLD(PDM_CH_FIR0_CTL_DECIM3, channel_config->fir0_decim_code) |
88 _VAL2FLD(PDM_CH_FIR0_CTL_SCALE, channel_config->fir0_scale) |
89 _VAL2FLD(PDM_CH_FIR0_CTL_ENABLED, channel_config->fir0_enable);
90
91 PDM_PCM_CH_FIR1_CTL(base, channel_num) = _VAL2FLD(PDM_CH_FIR1_CTL_DECIM2, channel_config->fir1_decim_code) |
92 _VAL2FLD(PDM_CH_FIR1_CTL_SCALE, channel_config->fir1_scale) |
93 _VAL2FLD(PDM_CH_FIR1_CTL_ENABLED, CY_PDM_PCM_ENABLE);
94 if(!channel_config->dc_block_disable)
95 {
96 PDM_PCM_CH_DC_BLOCK_CTL(base, channel_num) = _VAL2FLD(PDM_CH_DC_BLOCK_CTL_CODE, channel_config->dc_block_code) |
97 _VAL2FLD(PDM_CH_DC_BLOCK_CTL_ENABLED, CY_PDM_PCM_ENABLE);
98 }
99 else
100 {
101 PDM_PCM_CH_DC_BLOCK_CTL(base, channel_num) = _VAL2FLD(PDM_CH_DC_BLOCK_CTL_ENABLED, CY_PDM_PCM_DISABLE);
102 }
103
104 }
105 return ret;
106 }
107
108 /******************************************************************************
109 * Function Name: Cy_PDM_PCM_Init
110 ***************************************************************************//**
111 *
112 * Initializes the PDM-PCM module
113 *
114 * \param base The pointer to the PDM-PCM instance address
115 * \param config The pointer to a configuration structure. \ref cy_stc_pdm_pcm_config_v2_t
116 * \return error / status code. See \ref cy_en_pdm_pcm_status_t.
117 *
118 * \funcusage
119 * \snippet pdm_pcmv2/snippet/main.c snippet_Cy_PDM_PCM_Init
120 *
121 *******************************************************************************/
Cy_PDM_PCM_Init(PDM_Type * base,cy_stc_pdm_pcm_config_v2_t const * config)122 cy_en_pdm_pcm_status_t Cy_PDM_PCM_Init(PDM_Type * base, cy_stc_pdm_pcm_config_v2_t const * config)
123 {
124 cy_en_pdm_pcm_status_t ret = CY_PDM_PCM_BAD_PARAM;
125
126 if((NULL != base) && (NULL != config))
127 {
128 CY_ASSERT_L2(CY_PDM_PCM_IS_CLK_SEL_VALID(config->clksel));
129 CY_ASSERT_L2(CY_PDM_PCM_IS_HALVE_RATE_SET_VALID(config->halverate));
130 CY_ASSERT_L2(CY_PDM_PCM_IS_ROUTE_VALID(config->route));
131
132 ret = CY_PDM_PCM_SUCCESS;
133
134 /* The clock setting */
135 PDM_PCM_CLOCK_CTL(base) = _VAL2FLD(PDM_CLOCK_CTL_CLOCK_DIV, config->clkDiv) |
136 _VAL2FLD(PDM_CLOCK_CTL_CLOCK_SEL, config->clksel) |
137 _VAL2FLD(PDM_CLOCK_CTL_HALVE, config->halverate);
138
139 /* PDM-PCM ROUTE setting */
140 PDM_PCM_ROUTE_CTL(base) = _VAL2FLD(PDM_ROUTE_CTL_DATA_SEL, config->route);
141
142 if(config->fir0_coeff_user_value != 0U)
143 {
144 PDM_PCM_FIR0_COEFF0(base) = _VAL2FLD(PDM_FIR0_COEFF0_DATA0, config->fir0_coeff[0].coeff_data0) |
145 _VAL2FLD(PDM_FIR0_COEFF0_DATA1, config->fir0_coeff[0].coeff_data1);
146
147 PDM_PCM_FIR0_COEFF1(base) = _VAL2FLD(PDM_FIR0_COEFF1_DATA0, config->fir0_coeff[1].coeff_data0) |
148 _VAL2FLD(PDM_FIR0_COEFF1_DATA1, config->fir0_coeff[1].coeff_data1);
149
150 PDM_PCM_FIR0_COEFF2(base) = _VAL2FLD(PDM_FIR0_COEFF2_DATA0, config->fir0_coeff[2].coeff_data0) |
151 _VAL2FLD(PDM_FIR0_COEFF2_DATA1, config->fir0_coeff[2].coeff_data1);
152
153 PDM_PCM_FIR0_COEFF3(base) = _VAL2FLD(PDM_FIR0_COEFF3_DATA0, config->fir0_coeff[3].coeff_data0) |
154 _VAL2FLD(PDM_FIR0_COEFF3_DATA1, config->fir0_coeff[3].coeff_data1);
155
156 PDM_PCM_FIR0_COEFF4(base) = _VAL2FLD(PDM_FIR0_COEFF4_DATA0, config->fir0_coeff[4].coeff_data0) |
157 _VAL2FLD(PDM_FIR0_COEFF4_DATA1, config->fir0_coeff[4].coeff_data1);
158
159 PDM_PCM_FIR0_COEFF5(base) = _VAL2FLD(PDM_FIR0_COEFF5_DATA0, config->fir0_coeff[5].coeff_data0) |
160 _VAL2FLD(PDM_FIR0_COEFF5_DATA1, config->fir0_coeff[5].coeff_data1);
161
162 PDM_PCM_FIR0_COEFF6(base) = _VAL2FLD(PDM_FIR0_COEFF6_DATA0, config->fir0_coeff[6].coeff_data0) |
163 _VAL2FLD(PDM_FIR0_COEFF6_DATA1, config->fir0_coeff[6].coeff_data1);
164
165 PDM_PCM_FIR0_COEFF7(base) = _VAL2FLD(PDM_FIR0_COEFF7_DATA0, config->fir0_coeff[7].coeff_data0) |
166 _VAL2FLD(PDM_FIR0_COEFF7_DATA1, config->fir0_coeff[7].coeff_data1);
167 }
168
169 if(config->fir1_coeff_user_value != 0U)
170 {
171 PDM_PCM_FIR1_COEFF0(base) = _VAL2FLD(PDM_FIR1_COEFF0_DATA0, config->fir1_coeff[0].coeff_data0) |
172 _VAL2FLD(PDM_FIR1_COEFF0_DATA1, config->fir1_coeff[0].coeff_data1);
173
174 PDM_PCM_FIR1_COEFF1(base) = _VAL2FLD(PDM_FIR1_COEFF1_DATA0, config->fir1_coeff[1].coeff_data0) |
175 _VAL2FLD(PDM_FIR1_COEFF1_DATA1, config->fir1_coeff[1].coeff_data1);
176
177 PDM_PCM_FIR1_COEFF2(base) = _VAL2FLD(PDM_FIR1_COEFF2_DATA0, config->fir1_coeff[2].coeff_data0) |
178 _VAL2FLD(PDM_FIR1_COEFF2_DATA1, config->fir1_coeff[2].coeff_data1);
179
180 PDM_PCM_FIR1_COEFF3(base) = _VAL2FLD(PDM_FIR1_COEFF3_DATA0, config->fir1_coeff[3].coeff_data0) |
181 _VAL2FLD(PDM_FIR1_COEFF3_DATA1, config->fir1_coeff[3].coeff_data1);
182
183 PDM_PCM_FIR1_COEFF4(base) = _VAL2FLD(PDM_FIR1_COEFF4_DATA0, config->fir1_coeff[4].coeff_data0) |
184 _VAL2FLD(PDM_FIR1_COEFF4_DATA1, config->fir1_coeff[4].coeff_data1);
185
186 PDM_PCM_FIR1_COEFF5(base) = _VAL2FLD(PDM_FIR1_COEFF5_DATA0, config->fir1_coeff[5].coeff_data0) |
187 _VAL2FLD(PDM_FIR1_COEFF5_DATA1, config->fir1_coeff[5].coeff_data1);
188
189 PDM_PCM_FIR1_COEFF6(base) = _VAL2FLD(PDM_FIR1_COEFF6_DATA0, config->fir1_coeff[6].coeff_data0) |
190 _VAL2FLD(PDM_FIR1_COEFF6_DATA1, config->fir1_coeff[6].coeff_data1);
191
192 PDM_PCM_FIR1_COEFF7(base) = _VAL2FLD(PDM_FIR1_COEFF7_DATA0, config->fir1_coeff[7].coeff_data0) |
193 _VAL2FLD(PDM_FIR1_COEFF7_DATA1, config->fir1_coeff[7].coeff_data1);
194
195 PDM_PCM_FIR1_COEFF8(base) = _VAL2FLD(PDM_FIR1_COEFF8_DATA0, config->fir1_coeff[8].coeff_data0) |
196 _VAL2FLD(PDM_FIR1_COEFF8_DATA1, config->fir1_coeff[8].coeff_data1);
197
198 PDM_PCM_FIR1_COEFF9(base) = _VAL2FLD(PDM_FIR1_COEFF9_DATA0, config->fir1_coeff[9].coeff_data0) |
199 _VAL2FLD(PDM_FIR1_COEFF9_DATA1, config->fir1_coeff[9].coeff_data1);
200
201 PDM_PCM_FIR1_COEFF10(base) = _VAL2FLD(PDM_FIR1_COEFF10_DATA0, config->fir1_coeff[10].coeff_data0) |
202 _VAL2FLD(PDM_FIR1_COEFF10_DATA1, config->fir1_coeff[10].coeff_data1);
203
204 PDM_PCM_FIR1_COEFF11(base) = _VAL2FLD(PDM_FIR1_COEFF11_DATA0, config->fir1_coeff[11].coeff_data0) |
205 _VAL2FLD(PDM_FIR1_COEFF11_DATA1, config->fir1_coeff[11].coeff_data1);
206
207 PDM_PCM_FIR1_COEFF12(base) = _VAL2FLD(PDM_FIR1_COEFF12_DATA0, config->fir1_coeff[12].coeff_data0) |
208 _VAL2FLD(PDM_FIR1_COEFF12_DATA1, config->fir1_coeff[12].coeff_data1);
209
210 PDM_PCM_FIR1_COEFF13(base) = _VAL2FLD(PDM_FIR1_COEFF13_DATA0, config->fir1_coeff[13].coeff_data0) |
211 _VAL2FLD(PDM_FIR1_COEFF13_DATA1, config->fir1_coeff[13].coeff_data1);
212
213 }
214
215 }
216
217 return (ret);
218 }
219
220 /******************************************************************************
221 * Function Name: Cy_PDM_PCM_test_Init
222 ***************************************************************************//**
223 *
224 * Initializes the PDM-PCM module test mode.
225 *
226 * \param base The pointer to the PDM-PCM instance address
227 * \param config The pointer to a configuration structure. \ref cy_stc_pdm_pcm_config_v2_t
228 * \param test_config test Mode configuration. \ref cy_stc_test_config_t
229 * \return error / status code. See \ref cy_en_pdm_pcm_status_t.
230 *
231 *******************************************************************************/
Cy_PDM_PCM_test_Init(PDM_Type * base,cy_stc_pdm_pcm_config_v2_t const * config,cy_stc_test_config_t const * test_config)232 cy_en_pdm_pcm_status_t Cy_PDM_PCM_test_Init(PDM_Type * base, cy_stc_pdm_pcm_config_v2_t const * config, cy_stc_test_config_t const * test_config)
233 {
234 cy_en_pdm_pcm_status_t ret = CY_PDM_PCM_BAD_PARAM;
235
236 if((NULL != base) && (NULL != config) && (NULL != test_config) )
237 {
238 if(!test_config->enable)
239 {
240 return ret;
241 }
242 CY_ASSERT_L2(CY_PDM_PCM_IS_CLK_SEL_VALID(config->clksel));
243 CY_ASSERT_L2(CY_PDM_PCM_IS_HALVE_RATE_SET_VALID(config->halverate));
244 CY_ASSERT_L2(CY_PDM_PCM_IS_ROUTE_VALID(config->route));
245
246 ret = CY_PDM_PCM_SUCCESS;
247
248 PDM_PCM_TEST_CTL(base) = _VAL2FLD(PDM_TEST_CTL_DRIVE_DELAY_HI, test_config->drive_delay_hi) |
249 _VAL2FLD(PDM_TEST_CTL_DRIVE_DELAY_LO, test_config->drive_delay_lo);
250 PDM_PCM_TEST_CTL(base) |= _VAL2FLD(PDM_TEST_CTL_MODE_HI, test_config->mode_hi) |
251 _VAL2FLD(PDM_TEST_CTL_MODE_LO, test_config->mode_lo);
252 PDM_PCM_TEST_CTL(base) |= _VAL2FLD(PDM_TEST_CTL_AUDIO_FREQ_DIV, test_config->audio_freq_div) |
253 _BOOL2FLD(PDM_TEST_CTL_CH_ENABLED, test_config->enable);
254
255 }
256
257 return (ret);
258 }
259
260
261 /*******************************************************************************
262 * Function Name: Cy_PDM_PCM_Channel_DeInit
263 ****************************************************************************//**
264 *
265 * Uninitializes the PDM-PCM channel.
266 *
267 * \param base The pointer to the PDM-PCM instance address.
268 * \param channel_num channel number to be de initialized.
269 *
270 * \funcusage
271 * \snippet pdm_pcmv2/snippet/main.c snippet_Cy_PDM_PCM_Channel_DeInit
272 *
273 *******************************************************************************/
Cy_PDM_PCM_Channel_DeInit(PDM_Type * base,uint8_t channel_num)274 void Cy_PDM_PCM_Channel_DeInit(PDM_Type * base, uint8_t channel_num)
275 {
276 PDM_PCM_CH_IF_CTL(base, channel_num) = CY_PDM_PCM_CH_IF_CTL_DEFAULT;/* Channel interface control default value */
277 PDM_PCM_CH_CTL(base, channel_num) = CY_PDM_PCM_CH_CTL_DEFAULT; /* Channel control default values */
278 PDM_PCM_CH_CIC_CTL(base, channel_num) = CY_PDM_PCM_CH_CIC_DECIM_CODE_DEFAULT;
279 PDM_PCM_CH_FIR1_CTL(base, channel_num) = CY_PDM_PCM_CH_FIR1_DEFAULT;
280 PDM_PCM_CH_DC_BLOCK_CTL(base, channel_num) = CY_PDM_PCM_CH_DCBLOCK_DEFAULT;
281 PDM_PCM_CH_FIR0_CTL(base, channel_num) = 0UL;
282 PDM_PCM_INTR_RX_MASK(base, channel_num) = 0UL; /* Disable interrupts */
283 PDM_PCM_RX_FIFO_CTL(base, channel_num) = 0UL;
284 PDM_PCM_CTL_CLR(base) = (1UL << channel_num);
285
286 }
287
288
289 /*******************************************************************************
290 * Function Name: Cy_PDM_PCM_DeInit
291 ****************************************************************************//**
292 *
293 * Uninitializes the PDM-PCM module.
294 *
295 * \param base The pointer to the PDM-PCM instance address.
296 *
297 * \funcusage
298 * \snippet pdm_pcmv2/snippet/main.c snippet_Cy_PDM_PCM_DeInit
299 *
300 *******************************************************************************/
Cy_PDM_PCM_DeInit(PDM_Type * base)301 void Cy_PDM_PCM_DeInit(PDM_Type * base)
302 {
303 PDM_PCM_ROUTE_CTL(base) = 0UL; /* Default Route settings */
304 PDM_PCM_TEST_CTL(base) = CY_PDM_PCM_TEST_CTL_DEFAULT; /* Default Test settings */
305 PDM_PCM_CTL(base) = 0UL; /* Disable the PDM_PCM IP block */
306 PDM_PCM_CLOCK_CTL(base) = CY_PDM_PCM_CLK_CTL_DEFAULT; /* The default clock settings */
307 }
308
309 /** \} group_pdm_pcm_functions_v2 */
310
311 CY_MISRA_BLOCK_END('MISRA C-2012 Rule 10.1')
312
313 CY_MISRA_BLOCK_END('MISRA C-2012 Rule 14.3')
314
315 #endif /* CY_IP_MXPDM */
316
317 /* [] END OF FILE */
318