2 /*
3 Copyright (c) 2017, Texas Instruments Incorporated - http://www.ti.com/
4 All rights reserved.
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:
9 *
10 * Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 *
13 * Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the
16 * distribution.
17 *
18 * Neither the name of Texas Instruments Incorporated nor the names of
19 * its contributors may be used to endorse or promote products derived
20 * from this software without specific prior written permission.
21 *
22 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
23 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
24 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
25 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
26 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
27 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
28 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
29 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
30 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
31 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
32 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
33 *
34 */
36 //
37 //
38 // SIO driver implementation for audio I/O using McASP.
39 //
40 //
41 //
43 #ifndef SAP_CACHE_SUPPORT
44 // if you rebuild sap.c in your project without this defined,
45 // the result is quite hard to find: Occasional glitches in the sound.
46 #define SAP_CACHE_SUPPORT // typically defined in the project
47 #endif
49 #ifdef SAP_CACHE_SUPPORT
50 #include <ti/sysbios/hal/Cache.h>
51 #endif
53 #include <stdlib.h>
54 #include <stdio.h>
55 #include <string.h> //memset
57 #include <xdc/std.h>
59 #include "sap.h"
61 #include <ti/sdo/edma3/drv/edma3_drv.h>
62 #include <ti/sdo/edma3/drv/src/edma3.h>
63 #include <ti/sdo/edma3/rm/edma3_rm.h>
64 #include <ti/sdo/edma3/drv/sample/bios6_edma3_drv_sample.h>
66 #include <ti/csl/cslr_device.h>
68 #define EDMA_HINV NULL
69 #define EDMA_NUM_PARAMS 6
71 #include "sap_mcasp.h"
72 #include <pafsio.h>
74 // This works to set a breakpoint
75 #define SW_BREAKPOINT asm( " SWBP 0" );
77 // global allocated in bios_edma3_drv_sample_init.c
78 extern EDMA3_DRV_Handle hEdma0;
79 extern EDMA3_DRV_Handle hEdma1;
81 // global variables for debug-assist
82 int gStartError;
83 int gIsrInputCnt;
84 int gIsrOutputCnt;
85 int gIsrElseCnt;
86 int gIsrInErrCnt;
87 int gIsrOutErrCnt;
88 int gIsrRunCnt;
89 int gIsrNotRunCnt;
90 int gisrOutput;
91 int gSAPResetIn;
92 int gSAPResetOut;
94 typedef xdc_Short MdInt;
96 void swapHdmi(Ptr, int);
98 #define SAP_UNDER_LEN 8
100 #pragma DATA_SECTION(sap_UNDER, ".sap_UNDER");
101 int sap_UNDER[SAP_UNDER_LEN]; // used for underrun
102 int sap_OVER_1LANE = 0; // used for overrun
103 int sap_OVER_4LANE[4] = {0,0,0,0}; // used for overrun
105 #ifdef DEBUG
106 void SAP_EDMA_dumpParams(int tag_place)
107 {
108 //unsigned int *ptrPARAM_BASE = (unsigned int *)0x02704000;
109 unsigned int *ptrPARAM0x18 = (unsigned int *)0x02704300; // ((*((EDMA3_CCRL_Regs *) 0x02700000)).PARAMENTRY)[24]
110 //unsigned int *ptrPARAM0x19 = (unsigned int *)0x02704320; // ((*((EDMA3_CCRL_Regs *) 0x02700000)).PARAMENTRY)[24]
111 //unsigned int *ptrPARAM0x41 = (unsigned int *)0x027048A0; // ((*((EDMA3_CCRL_Regs *) 0x02700000)).PARAMENTRY)[24]
112 //unsigned int *ptrPARAM0x42 = (unsigned int *)0x027048C0; // ((*((EDMA3_CCRL_Regs *) 0x02700000)).PARAMENTRY)[24]
113 //unsigned int *ptrPARAM0x43 = (unsigned int *)0x027048E0; // ((*((EDMA3_CCRL_Regs *) 0x02700000)).PARAMENTRY)[24]
114 //unsigned int *ptrPARAM0x48 = (unsigned int *)0x02704910; // ((*((EDMA3_CCRL_Regs *) 0x02700000)).PARAMENTRY)[24]
115 unsigned int *ptrPARAM0x45 = (unsigned int *)0x027048A0; // ((*((EDMA3_CCRL_Regs *) 0x02700000)).PARAMENTRY)[69]
116 unsigned int *ptrPARAM0x46 = (unsigned int *)0x027048C0; // ((*((EDMA3_CCRL_Regs *) 0x02700000)).PARAMENTRY)[70]
117 unsigned int *ptrPARAM0x47 = (unsigned int *)0x027048E0; // ((*((EDMA3_CCRL_Regs *) 0x02700000)).PARAMENTRY)[71]
118 unsigned int *ptrPARAM0x48 = (unsigned int *)0x02704900; // ((*((EDMA3_CCRL_Regs *) 0x02700000)).PARAMENTRY)[72]
119 unsigned int *ptrPARAM0x49 = (unsigned int *)0x02704920; // ((*((EDMA3_CCRL_Regs *) 0x02700000)).PARAMENTRY)[73]
120 unsigned int *ptrPARAM0x4A = (unsigned int *)0x02704940; // ((*((EDMA3_CCRL_Regs *) 0x02700000)).PARAMENTRY)[74]
122 //Log_info5("PARAM0x18a(%d): 0x%x 0x%x 0x%x 0x%x", tag_place, ptrPARAM0x18[0], ptrPARAM0x18[1], ptrPARAM0x18[2], ptrPARAM0x18[3]);
123 //Log_info5("PARAM0x18b(%d): 0x%x 0x%x 0x%x 0x%x", tag_place, ptrPARAM0x18[4], ptrPARAM0x18[5], ptrPARAM0x18[6], ptrPARAM0x18[7]);
125 /*Log_info5("PARAM0x19a(%d): ITCINTEN: 0x%02x, TCINTEN: 0x%02x, TCC: 0x%02x, TCCMODE: %d", tag_place, ((ptrPARAM0x19[0] & 0x200000) >> 21), ((ptrPARAM0x19[0] & 0x100000) >> 20), ((ptrPARAM0x19[0] & 0x3F000) >> 12), ((ptrPARAM0x19[0] & 0x800) >> 11));
126 Log_info5("PARAM0x19b(%d): SRC: 0x%08x, A_B_CNT: 0x%08x, DST: 0x%08x, SRC_DST_BIDX: 0x%08x", tag_place, ptrPARAM0x19[1], ptrPARAM0x19[2], ptrPARAM0x19[3], ptrPARAM0x19[4]);
127 Log_info4("PARAM0x19b(%d): LINK_BCNTRLD: 0x%08x, SRC_DST_CIDX: 0x%08x, CCNT: 0x%08x", tag_place, ptrPARAM0x19[5], ptrPARAM0x19[6], ptrPARAM0x19[7]);
129 Log_info5("PARAM0x41a(%d): ITCINTEN: 0x%02x, TCINTEN: 0x%02x, TCC: 0x%02x, TCCMODE: %d", tag_place, ((ptrPARAM0x41[0] & 0x200000) >> 21), ((ptrPARAM0x41[0] & 0x100000) >> 20), ((ptrPARAM0x41[0] & 0x3F000) >> 12), ((ptrPARAM0x41[0] & 0x800) >> 11));
130 Log_info5("PARAM0x41b(%d): SRC: 0x%08x, A_B_CNT: 0x%08x, DST: 0x%08x, SRC_DST_BIDX: 0x%08x", tag_place, ptrPARAM0x41[1], ptrPARAM0x41[2], ptrPARAM0x41[3], ptrPARAM0x41[4]);
131 Log_info4("PARAM0x41b(%d): LINK_BCNTRLD: 0x%08x, SRC_DST_CIDX: 0x%08x, CCNT: 0x%08x", tag_place, ptrPARAM0x41[5], ptrPARAM0x41[6], ptrPARAM0x41[7]);
133 Log_info5("PARAM0x42a(%d): ITCINTEN: 0x%02x, TCINTEN: 0x%02x, TCC: 0x%02x, TCCMODE: %d", tag_place, ((ptrPARAM0x42[0] & 0x200000) >> 21), ((ptrPARAM0x42[0] & 0x100000) >> 20), ((ptrPARAM0x42[0] & 0x3F000) >> 12), ((ptrPARAM0x42[0] & 0x800) >> 11));
134 Log_info5("PARAM0x42b(%d): SRC: 0x%08x, A_B_CNT: 0x%08x, DST: 0x%08x, SRC_DST_BIDX: 0x%08x", tag_place, ptrPARAM0x42[1], ptrPARAM0x42[2], ptrPARAM0x42[3], ptrPARAM0x42[4]);
135 Log_info4("PARAM0x42b(%d): LINK_BCNTRLD: 0x%08x, SRC_DST_CIDX: 0x%08x, CCNT: 0x%08x", tag_place, ptrPARAM0x42[5], ptrPARAM0x42[6], ptrPARAM0x42[7]);
137 Log_info5("PARAM0x43a(%d): ITCINTEN: 0x%02x, TCINTEN: 0x%02x, TCC: 0x%02x, TCCMODE: %d", tag_place, ((ptrPARAM0x43[0] & 0x200000) >> 21), ((ptrPARAM0x43[0] & 0x100000) >> 20), ((ptrPARAM0x43[0] & 0x3F000) >> 12), ((ptrPARAM0x43[0] & 0x800) >> 11));
138 Log_info5("PARAM0x43b(%d): SRC: 0x%08x, A_B_CNT: 0x%08x, DST: 0x%08x, SRC_DST_BIDX: 0x%08x", tag_place, ptrPARAM0x43[1], ptrPARAM0x43[2], ptrPARAM0x43[3], ptrPARAM0x43[4]);
139 Log_info4("PARAM0x43b(%d): LINK_BCNTRLD: 0x%08x, SRC_DST_CIDX: 0x%08x, CCNT: 0x%08x", tag_place, ptrPARAM0x43[5], ptrPARAM0x43[6], ptrPARAM0x43[7]);
141 Log_info5("PARAM0x48a(%d): ITCINTEN: 0x%02x, TCINTEN: 0x%02x, TCC: 0x%02x, TCCMODE: %d", tag_place, ((ptrPARAM0x48[0] & 0x200000) >> 21), ((ptrPARAM0x48[0] & 0x100000) >> 20), ((ptrPARAM0x48[0] & 0x3F000) >> 12), ((ptrPARAM0x48[0] & 0x800) >> 11));
142 Log_info5("PARAM0x48b(%d): SRC: 0x%08x, A_B_CNT: 0x%08x, DST: 0x%08x, SRC_DST_BIDX: 0x%08x", tag_place, ptrPARAM0x48[1], ptrPARAM0x48[2], ptrPARAM0x48[3], ptrPARAM0x48[4]);
143 Log_info4("PARAM0x48b(%d): LINK_BCNTRLD: 0x%08x, SRC_DST_CIDX: 0x%08x, CCNT: 0x%08x", tag_place, ptrPARAM0x48[5], ptrPARAM0x48[6], ptrPARAM0x48[7]);*/
145 Log_info5("PARAM0x18a(%d): ITCINTEN: 0x%02x, TCINTEN: 0x%02x, TCC: 0x%02x, TCCMODE: %d", tag_place, ((ptrPARAM0x18[0] & 0x200000) >> 21), ((ptrPARAM0x18[0] & 0x100000) >> 20), ((ptrPARAM0x18[0] & 0x3F000) >> 12), ((ptrPARAM0x18[0] & 0x800) >> 11));
146 Log_info5("PARAM0x18b(%d): SRC: 0x%08x, A_B_CNT: 0x%08x, DST: 0x%08x, SRC_DST_BIDX: 0x%08x", tag_place, ptrPARAM0x18[1], ptrPARAM0x18[2], ptrPARAM0x18[3], ptrPARAM0x18[4]);
147 Log_info4("PARAM0x18c(%d): LINK_BCNTRLD: 0x%08x, SRC_DST_CIDX: 0x%08x, CCNT: 0x%08x", tag_place, ptrPARAM0x18[5], ptrPARAM0x18[6], ptrPARAM0x18[7]);
149 Log_info5("PARAM0x45a(%d): ITCINTEN: 0x%02x, TCINTEN: 0x%02x, TCC: 0x%02x, TCCMODE: %d", tag_place, ((ptrPARAM0x45[0] & 0x200000) >> 21), ((ptrPARAM0x45[0] & 0x100000) >> 20), ((ptrPARAM0x45[0] & 0x3F000) >> 12), ((ptrPARAM0x45[0] & 0x800) >> 11));
150 Log_info5("PARAM0x45b(%d): SRC: 0x%08x, A_B_CNT: 0x%08x, DST: 0x%08x, SRC_DST_BIDX: 0x%08x", tag_place, ptrPARAM0x45[1], ptrPARAM0x45[2], ptrPARAM0x45[3], ptrPARAM0x45[4]);
151 Log_info4("PARAM0x45c(%d): LINK_BCNTRLD: 0x%08x, SRC_DST_CIDX: 0x%08x, CCNT: 0x%08x", tag_place, ptrPARAM0x45[5], ptrPARAM0x45[6], ptrPARAM0x45[7]);
153 Log_info5("PARAM0x46a(%d): ITCINTEN: 0x%02x, TCINTEN: 0x%02x, TCC: 0x%02x, TCCMODE: %d", tag_place, ((ptrPARAM0x46[0] & 0x200000) >> 21), ((ptrPARAM0x46[0] & 0x100000) >> 20), ((ptrPARAM0x46[0] & 0x3F000) >> 12), ((ptrPARAM0x46[0] & 0x800) >> 11));
154 Log_info5("PARAM0x46b(%d): SRC: 0x%08x, A_B_CNT: 0x%08x, DST: 0x%08x, SRC_DST_BIDX: 0x%08x", tag_place, ptrPARAM0x46[1], ptrPARAM0x46[2], ptrPARAM0x46[3], ptrPARAM0x46[4]);
155 Log_info4("PARAM0x46c(%d): LINK_BCNTRLD: 0x%08x, SRC_DST_CIDX: 0x%08x, CCNT: 0x%08x", tag_place, ptrPARAM0x46[5], ptrPARAM0x46[6], ptrPARAM0x46[7]);
157 Log_info5("PARAM0x47a(%d): ITCINTEN: 0x%02x, TCINTEN: 0x%02x, TCC: 0x%02x, TCCMODE: %d", tag_place, ((ptrPARAM0x47[0] & 0x200000) >> 21), ((ptrPARAM0x47[0] & 0x100000) >> 20), ((ptrPARAM0x47[0] & 0x3F000) >> 12), ((ptrPARAM0x47[0] & 0x800) >> 11));
158 Log_info5("PARAM0x47b(%d): SRC: 0x%08x, A_B_CNT: 0x%08x, DST: 0x%08x, SRC_DST_BIDX: 0x%08x", tag_place, ptrPARAM0x47[1], ptrPARAM0x47[2], ptrPARAM0x47[3], ptrPARAM0x47[4]);
159 Log_info4("PARAM0x47c(%d): LINK_BCNTRLD: 0x%08x, SRC_DST_CIDX: 0x%08x, CCNT: 0x%08x", tag_place, ptrPARAM0x47[5], ptrPARAM0x47[6], ptrPARAM0x47[7]);
161 Log_info5("PARAM0x48a(%d): ITCINTEN: 0x%02x, TCINTEN: 0x%02x, TCC: 0x%02x, TCCMODE: %d", tag_place, ((ptrPARAM0x48[0] & 0x200000) >> 21), ((ptrPARAM0x48[0] & 0x100000) >> 20), ((ptrPARAM0x48[0] & 0x3F000) >> 12), ((ptrPARAM0x48[0] & 0x800) >> 11));
162 Log_info5("PARAM0x48b(%d): SRC: 0x%08x, A_B_CNT: 0x%08x, DST: 0x%08x, SRC_DST_BIDX: 0x%08x", tag_place, ptrPARAM0x48[1], ptrPARAM0x48[2], ptrPARAM0x48[3], ptrPARAM0x48[4]);
163 Log_info4("PARAM0x48c(%d): LINK_BCNTRLD: 0x%08x, SRC_DST_CIDX: 0x%08x, CCNT: 0x%08x", tag_place, ptrPARAM0x48[5], ptrPARAM0x48[6], ptrPARAM0x48[7]);
165 Log_info5("PARAM0x49a(%d): ITCINTEN: 0x%02x, TCINTEN: 0x%02x, TCC: 0x%02x, TCCMODE: %d", tag_place, ((ptrPARAM0x49[0] & 0x200000) >> 21), ((ptrPARAM0x49[0] & 0x100000) >> 20), ((ptrPARAM0x49[0] & 0x3F000) >> 12), ((ptrPARAM0x49[0] & 0x800) >> 11));
166 Log_info5("PARAM0x49b(%d): SRC: 0x%08x, A_B_CNT: 0x%08x, DST: 0x%08x, SRC_DST_BIDX: 0x%08x", tag_place, ptrPARAM0x49[1], ptrPARAM0x49[2], ptrPARAM0x49[3], ptrPARAM0x49[4]);
167 Log_info4("PARAM0x49c(%d): LINK_BCNTRLD: 0x%08x, SRC_DST_CIDX: 0x%08x, CCNT: 0x%08x", tag_place, ptrPARAM0x49[5], ptrPARAM0x49[6], ptrPARAM0x49[7]);
169 Log_info5("PARAM0x4Aa(%d): ITCINTEN: 0x%02x, TCINTEN: 0x%02x, TCC: 0x%02x, TCCMODE: %d", tag_place, ((ptrPARAM0x4A[0] & 0x200000) >> 21), ((ptrPARAM0x4A[0] & 0x100000) >> 20), ((ptrPARAM0x4A[0] & 0x3F000) >> 12), ((ptrPARAM0x4A[0] & 0x800) >> 11));
170 Log_info5("PARAM0x4Ab(%d): SRC: 0x%08x, A_B_CNT: 0x%08x, DST: 0x%08x, SRC_DST_BIDX: 0x%08x", tag_place, ptrPARAM0x4A[1], ptrPARAM0x4A[2], ptrPARAM0x4A[3], ptrPARAM0x4A[4]);
171 Log_info4("PARAM0x4Ac(%d): LINK_BCNTRLD: 0x%08x, SRC_DST_CIDX: 0x%08x, CCNT: 0x%08x", tag_place, ptrPARAM0x4A[5], ptrPARAM0x4A[6], ptrPARAM0x4A[7]);
173 Log_info1("TCC0: ERR reg %x", *((unsigned int *)0x02760120));
174 }
175 #endif
176 // .............................................................................
177 // notes:
178 // . add control function to PORT table
179 // . how to handle DMA/PORT specifics in parameter entries
180 // can assume numSers = numChans is general and can be applied by DMA
181 // same for wordSize?
182 // . why are two idle stages needed (seems like 1 is enough)?
184 // .............................................................................
185 // only one global variable, not static so that DMA and port functions
186 // can access. We cant just store the address in devExt since the ISR has
187 // no context.
189 SAP_DriverObject sapDrv;
191 // needed since SAP_watchDog is called before SAP_init
192 Int SAP_initialized = 0;
194 Int SAP_ctrl(DEV2_Handle, Uns, Arg);
195 Int SAP_idle(DEV2_Handle, Bool);
196 Int SAP_issue(DEV2_Handle);
197 Int SAP_open(DEV2_Handle, String);
198 void SAP_isrCallback (Uint32 tcc, EDMA3_RM_TccStatus status, Ptr context);
199 Int SAP_reclaim(DEV2_Handle);
200 Int SAP_shutdown(DEV2_Handle);
201 Int SAP_start(DEV2_Handle);
202 Int SAP_config(DEV2_Handle device, const SAP_Params *pParams);
203 Int SAP_EDMA_setupParam (DEV2_Handle device, XDAS_UInt32 targetEdma, XDAS_UInt32 childEdma, XDAS_UInt32 addr, XDAS_UInt32 size);
204 Int SAP_EDMA_setupXfer (DEV2_Handle device, XDAS_UInt32 targetEdma, XDAS_UInt32 parentEdma, XDAS_UInt32 childEdma, DEV2_Frame *pFrame);
206 // .............................................................................
208 // .............................................................................
210 SAP_DMA_Fxns SAP_EDMA_FXNS =
211 {
212 SAP_EDMA_setupParam,
213 SAP_EDMA_setupXfer,
214 };
217 SAP_Fxns SAP_FXNS =
218 {
219 NULL, //SAP_close, -- remove for IROM since not using
220 SAP_ctrl,
221 SAP_idle,
222 SAP_issue,
223 SAP_open,
224 NULL, //SAP_ready, -- remove for IROM since not using
225 SAP_reclaim,
226 SAP_shutdown,
227 SAP_start,
228 SAP_config,
230 #ifdef SAP_PORT_MCASP
231 (SAP_PORT_Fxns *) &SAP_MCASP_FXNS,
232 #endif
233 #ifdef SAP_DMA_EDMA
234 (SAP_DMA_Fxns *) &SAP_EDMA_FXNS,
235 #endif
236 };
238 // -----------------------------------------------------------------------------
239 // This function is not in the driver function table.
240 // Must be pointed at in GUI config tool.
241 //
242 Void SAP_init (Void)
243 {
244 DEV2_Device *entry;
245 SAP_Fxns *pFxns;
247 //TRACE_GEN((&TR_MOD, "SAP_init.%d", __LINE__));
249 // find function table pointer (used by SAP_XX_FTABLE_init macros)
250 DEV2_match(SAP_NAME, &entry);
251 if (entry == NULL) {
252 Log_error1 ("SAP", SIO2_ENODEV);
253 return;
254 }
255 pFxns = (SAP_Fxns *) entry->fxns;
257 //SAP_DMA_FTABLE_init ();
258 SAP_PORT_FTABLE_init ();
260 sapDrv.numDevices = 0;
261 SAP_initialized = 1;
263 return;
264 } // SAP_init
266 // -----------------------------------------------------------------------------
268 int gSapInput_ControlOpen = 0;
269 int gSapOutput_ControlOpen = 0;
271 int gSapInput_ControlClose = 0;
272 int gSapOutput_ControlClose = 0;
274 Int SAP_ctrl (DEV2_Handle device, Uns code, Arg arg)
275 {
276 SAP_DeviceExtension *pDevExt = (SAP_DeviceExtension *)device->object;
277 const SAP_Params *pParams;
278 Int i, result = SIO2_OK;
279 EDMA3_DRV_Handle hEdma;
280 //TRACE_GEN((&TR_MOD, "SAP_ctrl.%d (0x%x) code = 0x%x", __LINE__, device, code));
282 switch (code) {
284 /* .......................................................................... */
286 case PAF_SIO_CONTROL_MUTE:
287 case PAF_SIO_CONTROL_UNMUTE:
288 pParams = pDevExt->pParams;
289 if (pParams == NULL)
290 return SIO2_OK;
292 if (pParams->sio.control != NULL)
293 result = pParams->sio.control (device, (const PAF_SIO_Params *)pParams, code, arg);
294 break;
296 /* .......................................................................... */
298 case PAF_SIO_CONTROL_OPEN:
299 if (pDevExt->runState)
300 return SIO2_EBUSY;
302 if (!( pParams = (const SAP_Params *) arg ))
303 return SIO2_OK;
305 if(device->mode == DEV2_OUTPUT)
306 gSapOutput_ControlOpen++;
307 else
308 gSapInput_ControlOpen++;
310 if (result = SAP_FTABLE_config (device, pParams))
311 return result;
313 if (pParams->sio.control && (result = pParams->sio.control (device, (const PAF_SIO_Params *)pParams, code, arg)))
314 return result;
316 break;
318 /* .......................................................................... */
320 case PAF_SIO_CONTROL_CLOSE:
321 if (pDevExt->runState)
322 return SIO2_EBUSY;
324 if (pDevExt->pParams == NULL)
325 return SIO2_EINVAL;
327 pParams = pDevExt->pParams;
329 if (pParams->sio.moduleNum == 0)
330 hEdma = hEdma0;
331 else if (pParams->sio.moduleNum == 1 || pParams->sio.moduleNum == 2)
332 hEdma = hEdma1;
334 if (pDevExt->activeEdma != EDMA_HINV) {
335 EDMA3_DRV_freeChannel (hEdma, pDevExt->activeEdma);
336 pDevExt->activeEdma = EDMA_HINV;
337 }
339 if(device->mode == DEV2_INPUT)
340 gSapInput_ControlClose++;
341 else
342 gSapOutput_ControlClose++;
344 for (i=0; i < pDevExt->numEdmaParams; i++) {
345 if (pDevExt->edmaParams[i].hEdmaParam != EDMA_HINV)
346 {
347 EDMA3_DRV_freeChannel (hEdma, pDevExt->edmaParams[i].hEdmaParam);
348 pDevExt->edmaParams[i].hEdmaParam = EDMA_HINV;
349 }
350 }
352 if (pDevExt->errorEdma != EDMA_HINV) {
353 EDMA3_DRV_freeChannel (hEdma, pDevExt->errorEdma);
354 pDevExt->errorEdma = EDMA_HINV;
355 }
357 if (!(pParams = pDevExt->pParams))
358 return SIO2_OK;
360 if (pParams->sio.control && (result = pParams->sio.control (device, (const PAF_SIO_Params *)pParams, code, arg)))
361 return result;
363 result = SAP_PORT_FTABLE_close (device);
364 if (result)
365 return result;
367 pDevExt->pParams = NULL;
368 break;
370 /* .......................................................................... */
372 case PAF_SIO_CONTROL_GET_WORDSIZE:
373 if (!arg)
374 return SIO2_EINVAL;
375 *((int *) arg) = pDevExt->edmaWordSize;
376 break;
378 case PAF_SIO_CONTROL_SET_WORDSIZE:
379 // defer to DMA processing
380 // currently only supported for input
381 if (device->mode != DEV2_INPUT)
382 return SIO2_EINVAL;
384 // can't be running
385 if (pDevExt->runState)
386 return SIO2_EBUSY;
388 // driver only supports 2 or 4 bytes
389 if ((arg != 2) && (arg != 4))
390 return SIO2_EINVAL;
392 // return success for unconfigured devices?
393 if (!pDevExt->pParams)
394 return SIO2_OK;
396 // ask platform if size is supported
397 pParams = pDevExt->pParams;
398 if (pDevExt->pParams->sio.control && (result = pDevExt->pParams->sio.control (device, (const PAF_SIO_Params *)pParams, code, arg)))
399 return result;
401 pDevExt->edmaWordSize = arg;
402 break;
404 case PAF_SIO_CONTROL_GET_PRECISION:
405 if (arg == 0)
406 return SIO2_EINVAL;
408 pParams = pDevExt->pParams;
409 if (pParams == NULL)
410 return( SIO2_EINVAL );
412 *((int *) arg) = pParams->sio.precision;
413 break;
415 case PAF_SIO_CONTROL_GET_NUMCHANNELS:
416 if (arg == 0)
417 return SIO2_EINVAL;
419 *((int *) arg) = pDevExt->numSlots * pDevExt->numSers;
420 break;
422 case PAF_SIO_CONTROL_SET_RATEX:
423 pParams = pDevExt->pParams;
424 if (pParams == NULL)
425 return SIO2_OK ;
427 if (pParams->sio.control == NULL)
428 return SIO2_EINVAL;
430 result = pParams->sio.control( device, (const PAF_SIO_Params *)pParams, PAF_SIO_CONTROL_SET_RATEX, arg);
431 break;
433 /* .......................................................................... */
435 case PAF_SIO_CONTROL_IDLE:
436 pParams = pDevExt->pParams;
437 if (pParams == NULL)
438 return SIO2_OK ;
440 if (pParams->sio.control == NULL)
441 return SIO2_EINVAL;
443 result = pParams->sio.control( device, (const PAF_SIO_Params *)pParams, PAF_SIO_CONTROL_IDLE, arg);
444 break;
446 case PAF_SIO_CONTROL_IDLE_WITH_CLOCKS:
447 // 1. Here we are intentionally not using SIO_Idle() and
448 // leaving the Tx clock running. We need this to avoid DAC noise,
449 // as well as provide a DIT clock when using digital output.
450 if (device->mode != DEV2_OUTPUT || pDevExt->pParams == NULL)
451 return SIO2_EINVAL;
453 pParams = pDevExt->pParams;
455 if (pParams->sio.moduleNum == 0)
456 hEdma = hEdma0;
457 else if (pParams->sio.moduleNum == 1 || pParams->sio.moduleNum == 2)
458 hEdma = hEdma1;
460 result = SAP_FTABLE_shutdown (device);
461 if (result)
462 return result;
464 Log_info0 ("SAP PAF_SIO_CONTROL_IDLE_WITH_CLOCKS; PAF_SIO_ERROR_IDLE_STAGE1");
465 pDevExt->errorState = PAF_SIO_ERROR_IDLE_STAGE1;
467 if (pDevExt->activeEdma != EDMA_HINV)
468 EDMA3_DRV_enableTransfer (hEdma, pDevExt->activeEdma, EDMA3_DRV_TRIG_MODE_EVENT);
470 //TRACE_GEN((&TR_MOD, "SAP_ctrl.%d: (0x%x) errorState = PAF_SIO_ERROR_IDLE_STAGE1 0x%x.", __LINE__, device, PAF_SIO_ERROR_IDLE_STAGE1));
472 break;
474 /* .......................................................................... */
476 case PAF_SIO_CONTROL_GET_INPUT_STATUS:
477 // needs to be attached
478 pParams = pDevExt->pParams;
479 if (pParams == NULL)
480 return SIO2_OK;
482 if (pParams->sio.control == NULL)
483 return SIO2_EINVAL;
485 result = pParams->sio.control( device, (const PAF_SIO_Params *)pParams, code, arg );
486 break;
488 case PAF_SIO_CONTROL_WATCHDOG:
489 pParams = pDevExt->pParams;
490 if (pParams == NULL)
491 return SIO2_OK;
492 if (pParams->sio.control && (result = pParams->sio.control (device, (const PAF_SIO_Params *)pParams, code, arg)))
493 return result;
494 break;
496 /* .......................................................................... */
498 // Timing stats specific to DMA engine
499 case PAF_SIO_CONTROL_ENABLE_STATS:
500 case PAF_SIO_CONTROL_DISABLE_STATS:
501 case PAF_SIO_CONTROL_GET_STATS:
502 case PAF_SIO_CONTROL_GET_NUM_EVENTS:
503 case PAF_SIO_CONTROL_GET_NUM_REMAINING:
504 //result = SAP_DMA_FTABLE_ctrl (device, code, arg);
505 // TRACE_VERBOSE((&TR_MOD, "SAP_ctrl: (0x%x) code 0x%x. result 0x%x.", device, code, result));
506 break;
508 /* .......................................................................... */
510 case PAF_SIO_CONTROL_SET_DITSTATUS:
511 if(device->mode == DEV2_OUTPUT)
512 {
513 const SAP_Params *pParams = pDevExt->pParams;
514 MCASP_Handle hPort = sapMcaspDrv.hPort[pParams->sio.moduleNum];
515 volatile Uint32 *base = (volatile Uint32 *)(hPort->baseAddr);
516 MCASP_ConfigXmt *pTxConfig = (MCASP_ConfigXmt *)pParams->sio.pConfig;
517 int encSelect = *((int *) arg);
519 // HACK -- determine DIT need by FXWID
520 if (((pTxConfig->afsxctl & _MCASP_AFSXCTL_FXWID_MASK)>> _MCASP_AFSXCTL_FXWID_SHIFT) == MCASP_AFSXCTL_FXWID_BIT)
521 {
522 if ( (encSelect == 0x13) ||
523 (encSelect == 0xa) ||
524 (encSelect == 0x6)) // DTE, DDE, MPE
525 {
526 base[_MCASP_DITCSRA0_OFFSET] |= 2;
527 base[_MCASP_DITCSRB0_OFFSET] |= 2;
528 }
529 else
530 {
531 base[_MCASP_DITCSRA0_OFFSET] &= 0xfffffffd;
532 base[_MCASP_DITCSRB0_OFFSET] &= 0xfffffffd;
533 }
534 }
536 pParams = pDevExt->pParams;
537 if (pParams == NULL)
538 return SIO2_OK;
540 if (pParams->sio.control != NULL)
541 result = pParams->sio.control (device, (const PAF_SIO_Params *)pParams, code, arg);
542 }
543 break;
545 /* .......................................................................... */
547 }
549 return result;
550 } // SAP_ctrl
552 int gSAPIdleShutdownIn=0;
553 int gSAPIdleShutdownOut=0;
555 // -----------------------------------------------------------------------------
557 Int SAP_idle (DEV2_Handle device, Bool flush)
558 {
559 SAP_DeviceExtension *pDevExt = (SAP_DeviceExtension *)device->object;
560 Int result = SIO2_OK;
561 EDMA3_DRV_Handle hEdma;
563 // do nothing if already idled or unattached
564 if ((!pDevExt->runState) || (pDevExt->pParams == NULL))
565 return result;
567 if (pDevExt->pParams->sio.moduleNum == 0)
568 hEdma = hEdma0;
569 else if (pDevExt->pParams->sio.moduleNum == 1 || pDevExt->pParams->sio.moduleNum == 2)
570 hEdma = hEdma1;
572 // reset serial port -- stop generating sync events
573 result = SAP_PORT_FTABLE_reset (device);
574 if(device->mode == DEV2_OUTPUT)
575 gSAPResetOut++;
576 else
577 gSAPResetIn++;
578 if (result)
579 {
580 //TRACE_VERBOSE((&TR_MOD, "%s.%d: SAP_PORT_FTABLE_reset returned %d.\n", __FUNCTION__, __LINE__, result));
581 return result;
582 }
584 pDevExt->shutDown = 0; // force shutdown to run
585 result = SAP_FTABLE_shutdown (device);
586 if(device->mode == DEV2_OUTPUT)
587 gSAPIdleShutdownOut++;
588 else
589 gSAPIdleShutdownIn++;
591 if (result)
592 {
593 //TRACE_VERBOSE((&TR_MOD, "%s.%d: SAP_FTABLE_shutdown returned %d.\n", __FUNCTION__, __LINE__, result));
594 return result;
595 }
597 Log_info0("SAP_idle:Before EDMA3_DRV_disableTransfer");
599 // disable interrupts and EDMA servicing
600 if (pDevExt->activeEdma != EDMA_HINV)
601 EDMA3_DRV_disableTransfer (hEdma, pDevExt->activeEdma, EDMA3_DRV_TRIG_MODE_EVENT);
603 Log_info0("SAP_idle:Before pDevExt->numQueued = 0");
604 pDevExt->numQueued = 0;
606 // signal stopped
607 pDevExt->runState = 0;
608 Log_info0("SAP_idle: runState = 0");
610 // reset errorState
611 pDevExt->errorState = PAF_SIO_ERROR_NONE;
612 //TRACE_VERBOSE((&TR_MOD, "SAP_ctrl.%d: errorState = PAF_SIO_ERROR_NONE 0x%x.", __LINE__, PAF_SIO_ERROR_NONE));
614 // place call to physical device
615 if ((pDevExt->pParams != NULL) && (pDevExt->pParams->sio.control != NULL))
616 result = pDevExt->pParams->sio.control(device, (const PAF_SIO_Params *)pDevExt->pParams, PAF_SIO_CONTROL_IDLE, 0);
618 return result;
619 } // SAP_idle
621 // -----------------------------------------------------------------------------
623 Int SAP_start (DEV2_Handle device)
624 {
625 SAP_DeviceExtension *pDevExt = (SAP_DeviceExtension *)device->object;
626 DEV2_Frame *pFrame;
627 int result;
628 EDMA3_DRV_Handle hEdma;
630 Log_info2("SAP_start.%d (0x%x)", __LINE__, (xdc_IArg)device);
632 // Assume todevice queue is not empty -- how else could we be here?
633 pFrame = (DEV2_Frame *) Queue_get (device->todevice);
635 // inidicate this xfer did not use param entry - just the active one
636 pFrame->misc = NULL;
637 if (pDevExt->pParams->sio.moduleNum == 0)
638 hEdma = hEdma0;
639 else if (pDevExt->pParams->sio.moduleNum == 1 || pDevExt->pParams->sio.moduleNum == 2)
640 hEdma = hEdma1;
642 // non-atomic functions since not running yet.
643 Queue_enqueue (Queue_handle(&pDevExt->xferQue), (Queue_Elem *)pFrame);
645 // initialize count
646 pDevExt->numQueued = 1;
648 result = SAP_PORT_FTABLE_reset (device);
649 if (result)
650 {
651 //TRACE_VERBOSE((&TR_MOD, "%s.%d: SAP_PORT_FTABLE_reset returned %d.\n", __FUNCTION__, __LINE__, result));
652 return result;
653 }
655 // enable DMA processing
656 if (device->mode == DEV2_OUTPUT)
657 Log_info3("SAP_start.%d, pDevExt->activeEdma 0x%x (pDevExt->errorEdma = 0x%x)",
658 __LINE__, pDevExt->activeEdma, pDevExt->errorEdma);
659 // config active xfer for this buffer
660 result = SAP_EDMA_setupXfer(device, pDevExt->activeEdma, EDMA_HINV, pDevExt->errorEdma, pFrame);
663 // signal we have started -- this must come before last enable to prevent a race
664 // condition where the initial EDMA transfer is very small (e.g. due to startClocks)
665 // and completes before any further instructions in this thread are executed.
666 // This comes before the EDMA enable since, if the # of samples is 1, then the EDMA
667 // will be serviced and generate an interrupt even before the McASP is enabled.
668 pDevExt->runState = 1;
669 pDevExt->shutDown = 0;
670 if (device->mode == DEV2_OUTPUT)
671 Log_info2 ("SAP: %d, SAP_start runState=1 & ENABLE TRANSFERS for activeEdma = 0x%x", __LINE__, pDevExt->activeEdma);
672 // enable interrupts and event servicing for this channel
673 EDMA3_DRV_enableTransfer (hEdma, pDevExt->activeEdma, EDMA3_DRV_TRIG_MODE_EVENT);
675 // enable peripheral
676 result = SAP_PORT_FTABLE_enable (device);
678 if (result)
679 {
680 //TRACE_VERBOSE((&TR_MOD, "%s.%d: SAP_PORT_FTABLE_enable returned %d.\n", __FUNCTION__, __LINE__, result));
681 return result;
682 }
684 return SIO2_OK;
685 } // SAP_start
687 int gDmaParamsarray[17][3];
688 int gDmaParamsidx=0, gSAPSpecialCase=0;
689 // -----------------------------------------------------------------------------
691 Int SAP_issue (DEV2_Handle device)
692 {
693 SAP_DeviceExtension *pDevExt = (SAP_DeviceExtension *)device->object;
694 DEV2_Frame *pFrame;
695 Int result;
696 SAP_EDMA_Param *pParam;
697 XDAS_UInt32 parentEdma;
699 if (device->mode == DEV2_OUTPUT)
700 Log_info3("SAP_issue for output device with pDevExt->errorState = 0x%x, pDevExt->runState = 0x%x, pDevExt->numQueued = 0x%x", pDevExt->errorState, pDevExt->runState, pDevExt->numQueued);
702 if ((device->mode == DEV2_OUTPUT) && (pDevExt->errorState >= PAF_SIO_ERROR_ERRBUF_XFER))
703 {
704 /*TRACE_TERSE((&TR_MOD, "SAP_issue.%d, errorState 0x%x (PAF_SIO_ERROR_ERRBUF_XFER = 0x%x)",
705 __LINE__, pDevExt->errorState, PAF_SIO_ERROR_ERRBUF_XFER));*/
706 Log_info3("SAP_issue.%d, PAF_SIO_ERROR_ERRBUF_XFER = 0x%x, mode = 0x%x)",
707 __LINE__, PAF_SIO_ERROR_ERRBUF_XFER, device->mode );
708 return SIO2_EBADIO;
709 }
711 if ((device->mode == DEV2_INPUT) && pDevExt->errorState)
712 {
713 Log_info1("SAP_issue: Input Error Trap, with errorState = 0x%x", pDevExt->errorState);
714 return SIO2_EBADIO;
715 }
717 // if not yet running then configure active xfer and start
718 if (pDevExt->runState == 0)
719 return (SAP_FTABLE_start(device));
721 // .........................................................................
722 // here if running
724 // disable device interrupts
725 // TODO: is there an API to just disable the IER bit for this tcc?
726 unsigned int key = Hwi_disable ();
727 /* determine parent EDMA
728 if no xfers in queue and we are running then must be in the
729 error state so link to active channel otherwise link to last
730 transfer queued.
731 */
733 /* here we assume after Tx SIO_idle or overrun, the user
734 will issue, at least, back-to-back issue requests so
735 there should be no problem here.
736 */
737 if ((pDevExt->numQueued <= 1) && (pDevExt->errorState != 2))
738 parentEdma = pDevExt->activeEdma;
739 else {
740 // if here then xferQue has more than one element so ok to use tail
741 // last scheduled transfer must be queue->prev
742 DEV2_Frame *tail = (DEV2_Frame *) Queue_prev ((Queue_Elem *)&pDevExt->xferQue);
743 parentEdma = ((SAP_EDMA_Param *) tail->misc)->hEdmaParam;
744 }
746 //if (device->mode == DEV2_OUTPUT)
747 Log_info2("SAP_issue: Determined Parent = 0x%x for device = 0x%x", parentEdma, device->mode );
749 // get frame and parameter table to use; ints off => non-atomic OK
750 // dont need to check for empty queues since were here then todevice
751 // must have a frame placed there by the SIO_issue layer.
752 // paramQue must be valid since it is accessed the same as todevice.
753 // (indirectly -- isr places used items onto paramQue and fromdevice que
754 // at the same time)
755 // set misc argument to pParam so get enqueue later
756 //pFrame = (DEV2_Frame *) Queue_dequeue (device->todevice);
757 pFrame = Queue_dequeue (device->todevice);
758 pParam = (SAP_EDMA_Param *) Queue_dequeue (Queue_handle(&pDevExt->paramQue));
760 if (pParam->hEdmaParam == NULL)
761 Log_info1("SAP_issue: hEdma value is NULL for device = 0x%x", device->mode);
762 // set misc argument to pParam so get enqueue later
763 pFrame->misc = (Arg) pParam;
765 // place on holder queue, ints off => non-atomic OK
766 Queue_enqueue (Queue_handle(&pDevExt->xferQue), (Queue_Elem *) pFrame);
767 if (pFrame->addr) {
768 if (device->mode == DEV2_INPUT)
769 Cache_inv (pFrame->addr, pFrame->size, Cache_Type_ALL, TRUE);
770 else
771 Cache_wbInv (pFrame->addr, pFrame->size, Cache_Type_ALL, TRUE);
772 }
774 // increment count
775 pDevExt->numQueued += 1;
777 result = SAP_EDMA_setupXfer (device, pParam->hEdmaParam, parentEdma, pDevExt->errorEdma, pFrame);
778 if (device->mode == DEV2_OUTPUT)
779 {
780 Log_info4("SAP_issue.%d, EDMA_setupXfer: Target EDMA: 0x%x, Parent Edma: 0x%x Error Edma: 0x%x",
781 __LINE__, pParam->hEdmaParam, parentEdma, pDevExt->errorEdma);
782 }
784 if ((pDevExt->errorState == PAF_SIO_ERROR_IDLE_STAGE1) && (device->mode == DEV2_OUTPUT))
785 pDevExt->errorState = PAF_SIO_ERROR_NONE;
787 pDevExt->shutDown = 0;
789 // special case enables when not yet started
790 if (pDevExt->runState == 0) {
791 gSAPSpecialCase++;
792 result = SAP_FTABLE_start (device);
793 if (result) {
794 Hwi_restore (key);
795 return result;
796 }
797 }
798 Hwi_restore (key);
800 return result;
801 } // SAP_issue
803 // -----------------------------------------------------------------------------
805 void swapHdmi(Ptr Input, int size)
806 {
808 MdInt L0, L1, L2, L3, R0, R1, R2, R3 = 0;
809 MdInt *p1, *p2;
810 int i=0;
812 for (i=0; i< size; i+=16)
813 {
814 p1 = (MdInt *)&Input[i];
815 p2 = p1;
817 L0 = *p1++;
818 L1 = *p1++;
819 L2 = *p1++;
820 L3 = *p1++;
821 R0 = *p1++;
822 R1 = *p1++;
823 R2 = *p1++;
824 R3 = *p1++;
826 *p2++ = L0;
827 *p2++ = R0;
828 *p2++ = L1;
829 *p2++ = R1;
830 *p2++ = L2;
831 *p2++ = R2;
832 *p2++ = L3;
833 *p2++ = R3;
835 }
837 Log_info3("SAP: Exiting swapHdmi with Frame->Addr: 0x%x, p1->addr: 0x%x, p2->addr: 0x%x ", (xdc_IArg)Input, (xdc_IArg)p1, (xdc_IArg)p2);
839 return;
840 }
842 Int SAP_reclaim (DEV2_Handle device)
843 {
844 SAP_DeviceExtension *pDevExt = (SAP_DeviceExtension *)(device->object);
845 #ifdef SAP_CACHE_SUPPORT
846 DEV2_Frame *pFrame;
847 #endif
849 //TRACE_GEN((&TR_MOD, "SAP_reclaim.%d (0x%x)", __LINE__, device));
850 if (device->mode == DEV2_OUTPUT)
851 Log_info3("SAP_reclaim for output device with pDevExt->errorState = 0x%x, runState: 0x%x & pDevExt->numQueued = 0x%x", pDevExt->errorState, pDevExt->runState, pDevExt->numQueued);
852 // must be running and error free
853 if ((!pDevExt->runState) || (pDevExt->errorState))
854 {
855 Log_info3("SAP_reclaim.%d, error-state: 0x%x, mode = 0x%x", __LINE__, pDevExt->errorState, device->mode);
856 return SIO2_EBADIO;
857 }
859 Log_info1("SAP_reclaim: Before SEM Pend for mode: 0x%x", device->mode);
861 // wait for ISR to signal block completion
862 //TRACE_VERBOSE((&TR_MOD, "SAP_reclaim.%d wait for ISR to signal block completion", __LINE__));
863 if (!Semaphore_pend(pDevExt->sync, device->timeout))
864 {
865 Log_info0("SAP_reclaim, SYS_ETIMEOUT");
866 return SIO2_ETIMEOUT;
867 }
868 Log_info1("SAP_reclaim: After SEM Pend for mode: 0x%x", device->mode);
870 // return error (owner must idle)
871 if (pDevExt->errorState == PAF_SIO_ERROR_FATAL)
872 {
873 DEV2_idle (device, 1);
874 Log_info2("SAP_reclaim.%d, PAF_SIO_ERROR_FATAL: 0x%x", __LINE__, pDevExt->errorState);
875 return PAF_SIO_ERROR_FATAL;
876 }
878 #ifdef SAP_CACHE_SUPPORT
879 // invalidate CACHE region if input -- use clean since
880 // Dont clean if was for fill.
881 // since pend returned we know that head of fromdevice is valid
882 pFrame = Queue_head (device->fromdevice);
883 Log_info2("SAP: Inside SAP_Reclaim with From Device Frame->Addr: 0x%x and Frame->Size: %d", (xdc_IArg)pFrame->addr, pFrame->size);
884 if ((device->mode == DEV2_INPUT) && (pFrame->addr != NULL))
885 {
886 if(pDevExt->edmaWordSize == 2 && pDevExt->numSers == 4)
887 {
888 Cache_inv (pFrame->addr, pFrame->size, Cache_Type_ALL, 0);
889 Cache_wait();
891 // max HWI disable duration ~1ms observed
892 //unsigned int key = Hwi_disable (); // GJ: Revisit, along with other context protections here.
893 swapHdmi(pFrame->addr, pFrame->size);
894 //Hwi_restore(key);
896 Cache_wb (pFrame->addr, pFrame->size, Cache_Type_ALL, 0);
897 Cache_wait();
898 }
899 }
901 #endif
902 /*if ((device->mode == DEV2_OUTPUT) && (pFrame->addr == NULL))
903 SW_BREAKPOINT; */
905 Log_info1("SAP_reclaim: Exiting with SIO2_OK for device 0x%x ", device->mode);
906 //TRACE_VERBOSE((&TR_MOD, "SAP_reclaim.%d, exit SIO2_OK", __LINE__));
907 return SIO2_OK;
908 } // SAP_reclaim
911 // -----------------------------------------------------------------------------
913 Int SAP_open (DEV2_Handle device, String name)
914 {
915 SAP_DeviceExtension *pDevExt;
916 DEV2_Device *entry;
917 Int oldMask, result;
918 Error_Block eb;
919 //TRACE_GEN((&TR_MOD, "SAP_open.%d (0x%x)", __LINE__, device));
921 // check SIO mode
922 if ((device->mode != DEV2_INPUT) && (device->mode != DEV2_OUTPUT))
923 return SIO2_EMODE;
925 // allocate memory for device extension
926 device->object = NULL;
927 pDevExt = (SAP_DeviceExtension *) Memory_alloc (device->bufSeg, (sizeof(SAP_DeviceExtension)+3)/4*4, 4, &eb);
928 if (pDevExt == NULL)
929 {
930 printf("%s.%d: MEM_alloc failed.\n", __FUNCTION__, __LINE__);
931 //TRACE_TERSE((&TR_MOD, "%s.%d: MEM_alloc failed.\n", __FUNCTION__, __LINE__));
932 asm( " SWBP 0" ); // SW Breakpoint
933 return SIO2_EALLOC;
934 }
935 device->object = (Ptr)pDevExt;
937 // inits
938 pDevExt->device = device;
939 pDevExt->sync = NULL;
940 pDevExt->pParams = NULL;
941 pDevExt->runState = 0; // not yet started
942 pDevExt->errorState = PAF_SIO_ERROR_NONE;
943 pDevExt->shutDown = 1;
944 pDevExt->numQueued = 0;
945 pDevExt->activeEdma = EDMA_HINV;
946 pDevExt->errorEdma = EDMA_HINV;
947 pDevExt->firstTCC = 0;
948 pDevExt->optLevel = 0;
949 pDevExt->numParamSetup = 0;
950 pDevExt->numEdmaParams = EDMA_NUM_PARAMS; // We need more than 4 spare params to handle the immediate transition from Unknown
951 // to a Known program. Cheap resource to spend.
953 // use dev match to fetch function table pointer for SAP
954 DEV2_match(SAP_NAME, &entry);
955 if (entry == NULL) {
956 Log_error1("SAP", SIO2_ENODEV);
957 return SIO2_ENODEV;
958 }
959 pDevExt->pFxns = (SAP_Fxns *) entry->fxns;
961 // create semaphore for device
962 pDevExt->sync = Semaphore_create (0, NULL, NULL);
963 if (pDevExt->sync == NULL)
964 {
965 //TRACE_TERSE((&TR_MOD, "%s.%d: create semaphore for device failed.\n", __FUNCTION__, __LINE__));
966 return SIO2_EALLOC;
967 }
969 // queue inits
970 Queue_construct (&pDevExt->xferQue, NULL);
971 Queue_construct (&pDevExt->paramQue, NULL);
973 // update driver global (need to protect context)
974 if (sapDrv.numDevices >= MAX_SAP_DEVICES)
975 {
976 /*TRACE_TERSE((&TR_MOD, "%s.%d: add device failure: no. of devices = %d; need to increase MAX_SAP_DEVICES.\n",
977 __FUNCTION__, __LINE__, dapDrv.numDevices));*/
978 SW_BREAKPOINT;
979 }
980 oldMask = Hwi_disable ();
981 sapDrv.device[sapDrv.numDevices] = device;
982 pDevExt->deviceNum = sapDrv.numDevices++;
983 Hwi_restore (oldMask);
985 // PORT init
986 result = SAP_PORT_FTABLE_open (device);
987 if (result)
988 {
989 //TRACE_TERSE((&TR_MOD, "%s.%d: SAP_PORT_FTABLE_open returned %d.\n", __FUNCTION__, __LINE__, result));
990 return result;
991 }
993 return result;
994 } // SAP_open
996 // -----------------------------------------------------------------------------
998 Int SAP_config (DEV2_Handle device, const SAP_Params *pParams)
999 {
1000 SAP_DeviceExtension *pDevExt = (SAP_DeviceExtension *)device->object;
1001 Int result, Que_num, i;
1002 EDMA3_DRV_Result edmaResult;
1003 Uint32 reqTcc;
1004 EDMA3_DRV_Handle hEdma;
1005 Log_info2("SAP_config.%d (0x%x)", __LINE__, (xdc_IArg)device);
1007 // cannot configure if transfer started
1008 if (pDevExt->runState == 1)
1009 return SIO2_EBADIO;
1011 // save pointer to config structure in device extension. here so that
1012 // forthcoming functions can use/modify config structure.
1013 pDevExt->pParams = pParams;
1014 pDevExt->edmaWordSize = pParams->sio.wordSize;
1016 // allocate Port resources.
1017 // This must come before DMA configuration
1018 result = SAP_PORT_FTABLE_alloc (device);
1019 if (result)
1020 {
1021 Log_info3("%s.%d: SAP_PORT_FTABLE_alloc returned %d.\n", (xdc_IArg) __FUNCTION__, __LINE__, result);
1022 return result;
1023 }
1025 // .............................................................................
1026 // EDMA configuration
1028 // DA10x McASP0 Specific
1029 if (pParams->sio.moduleNum == 0)
1030 {
1031 hEdma = hEdma0;
1032 if (device->mode == DEV2_INPUT)
1033 {
1034 Que_num = 0;
1035 pDevExt->activeEdma = CSL_EDMACC_0_McASP_0_REVT;
1036 }
1037 else
1038 {
1039 Que_num = 0;
1040 pDevExt->activeEdma = CSL_EDMACC_0_McASP_0_XEVT;
1041 }
1042 }
1043 // DA10x McASP1 Specific
1044 else if (pParams->sio.moduleNum == 1)
1045 {
1046 hEdma = hEdma1;
1047 if (device->mode == DEV2_INPUT)
1048 {
1049 Que_num = 0;
1050 pDevExt->activeEdma = CSL_EDMACC_1_McASP_1_REVT;
1051 }
1052 else
1053 {
1054 Que_num = 0;
1055 pDevExt->activeEdma = CSL_EDMACC_1_McASP_1_XEVT;
1056 }
1057 }
1058 // DA10x McASP2 Specific
1059 else if (pParams->sio.moduleNum == 2)
1060 {
1061 hEdma = hEdma1;
1062 if (device->mode == DEV2_INPUT)
1063 {
1064 Que_num = 0;
1065 pDevExt->activeEdma = CSL_EDMACC_1_McASP_2_REVT;
1066 }
1067 else
1068 {
1069 Que_num = 0;
1070 pDevExt->activeEdma = CSL_EDMACC_1_McASP_2_XEVT;
1071 }
1072 }
1075 for (i=0; i < pDevExt->numEdmaParams; i++) {
1077 reqTcc = EDMA3_DRV_TCC_ANY;
1078 pDevExt->edmaParams[i].hEdmaParam = EDMA3_DRV_LINK_CHANNEL;
1079 edmaResult = EDMA3_DRV_requestChannel (
1080 hEdma,
1081 &pDevExt->edmaParams[i].hEdmaParam,
1082 &reqTcc,
1083 (EDMA3_RM_EventQueue) Que_num,
1084 SAP_isrCallback,
1085 (void *) device);
1087 if (edmaResult != EDMA3_DRV_SOK)
1088 return SIO2_EALLOC;
1090 //not running => can use non-atomic functions
1091 Queue_enqueue (Queue_handle(&pDevExt->paramQue), (Queue_Elem *)&pDevExt->edmaParams[i]);
1093 }
1095 reqTcc = EDMA3_DRV_TCC_ANY;
1096 pDevExt->errorEdma = EDMA3_DRV_LINK_CHANNEL;
1097 edmaResult = EDMA3_DRV_requestChannel (
1098 hEdma,
1099 &pDevExt->errorEdma,
1100 &reqTcc,
1101 (EDMA3_RM_EventQueue)Que_num,
1102 SAP_isrCallback,
1103 (void *) device);
1104 if (edmaResult != EDMA3_DRV_SOK)
1105 return SIO2_EALLOC;
1107 // allocate edma channel -- also disable and clear the interrupt
1110 pDevExt->firstTCC = pDevExt->activeEdma ;
1111 edmaResult = EDMA3_DRV_requestChannel (
1112 hEdma,
1113 &pDevExt->activeEdma,
1114 &pDevExt->firstTCC,
1115 (EDMA3_RM_EventQueue) 0,
1116 SAP_isrCallback,
1117 (void *) device);
1118 if (edmaResult != EDMA3_DRV_SOK)
1119 {
1120 Log_info3("%s.%d: SAP_DMA_FTABLE_alloc returned %d.\n", (xdc_IArg)__FUNCTION__, __LINE__, edmaResult);
1121 return SIO2_EALLOC;
1122 }
1124 // Configure error transfer
1125 // make cnt same as # of channels in order to maintain alignment
1126 // and the error transfer small so that we never have to wait
1127 // long for it to complete and trigger a linked transfer. This is
1128 // important for establishing output timing when we are idling with
1129 // clocks still running. Is fine for Rx as well.
1130 result = SAP_DMA_FTABLE_setupParam (device, pDevExt->errorEdma, pDevExt->errorEdma, NULL, pDevExt->edmaWordSize * pDevExt->numSers);
1132 Log_info3("%s.%d: Exiting SAP_alloc for %d.\n", (xdc_IArg)__FUNCTION__, __LINE__, pDevExt->activeEdma);
1134 return SIO2_OK;
1135 } // SAP_config
1137 // -----------------------------------------------------------------------------
1139 Int SAP_shutdown (DEV2_Handle device)
1140 {
1141 SAP_DeviceExtension *pDevExt = (SAP_DeviceExtension *)(device->object);
1142 SIO2_Handle stream = (SIO2_Handle) device;
1143 DEV2_Frame *pFrame;
1144 Int i;
1145 EDMA3_DRV_Handle hEdma;
1146 //TRACE_GEN((&TR_MOD, "SAP_shutdown.%d (0x%x)", __LINE__, device));
1148 if (pDevExt->shutDown)
1149 return SIO2_EBADIO;
1151 if (pDevExt->pParams == NULL)
1152 return SIO2_EINVAL;
1154 if (pDevExt->pParams->sio.moduleNum == 0)
1155 hEdma = hEdma0;
1156 else if (pDevExt->pParams->sio.moduleNum == 1 || pDevExt->pParams->sio.moduleNum == 2)
1157 hEdma = hEdma1;
1158 if (pDevExt->activeEdma != EDMA_HINV)
1159 EDMA3_DRV_disableTransfer (hEdma, pDevExt->activeEdma, EDMA3_DRV_TRIG_MODE_EVENT);
1161 // reset queues
1162 while (!Queue_empty(device->todevice)) {
1163 // place oustanding requests onto holding queue
1164 pFrame = (DEV2_Frame *) Queue_dequeue (device->todevice);
1165 Queue_enqueue (Queue_handle(&pDevExt->xferQue), (Queue_Elem *) pFrame);
1166 }
1168 while (!Queue_empty(Queue_handle(&pDevExt->xferQue))) {
1169 // pull frame from holding queue and place on user queue
1170 pFrame = (DEV2_Frame *) Queue_dequeue (Queue_handle(&pDevExt->xferQue));
1171 Queue_enqueue (device->fromdevice, (Queue_Elem *) pFrame);
1172 }
1175 while (!Queue_empty(Queue_handle(&pDevExt->paramQue)))
1176 Queue_dequeue (Queue_handle(&pDevExt->paramQue));
1178 // not running => can use non-atomic functions
1179 for (i=0; i < pDevExt->numEdmaParams; i++)
1180 Queue_enqueue (Queue_handle(&pDevExt->paramQue), (Queue_Elem *) &pDevExt->edmaParams[i]);
1182 // reset counter
1183 pDevExt->numQueued = 0;
1185 Log_info0("SAP_shutdown: After pDevExt->numQueued = 0 ");
1187 //SAP_EDMA_dumpParams(8);
1188 // make sure active is linked to error
1189 EDMA3_DRV_linkChannel (hEdma, pDevExt->activeEdma, pDevExt->errorEdma);
1191 // think this is better (from SIO_idle for standard model )
1192 // refill frame list -- so user needn't call reclaim, which may cause Rx underrun.
1193 while (!Queue_empty(device->fromdevice)) {
1194 /* place oustanding requests onto holding queue */
1195 pFrame = (DEV2_Frame *) Queue_dequeue (device->fromdevice);
1196 Queue_enqueue (Queue_handle(&stream->framelist), (Queue_Elem *) pFrame);
1197 }
1198 Semaphore_reset (pDevExt->sync, 0);
1200 pDevExt->shutDown = 1;
1201 pDevExt->numParamSetup = 0;
1203 return SIO2_OK;
1204 } // SAP_shutdown
1206 // -----------------------------------------------------------------------------
1207 int gSapWatchDogThrottle = 0;
1208 int gSapWatchDogIn =0;
1209 int gSapWatchDogOut = 0;
1210 int gSapWatchDogInSemPost = 0;
1211 int gSapWatchDogOutSemPost = 0;
1213 Void SAP_watchDog (Void)
1214 {
1215 DEV2_Handle device;
1216 SAP_DeviceExtension *pDevExt;
1217 int i, oldMask, result;
1219 //Log_info2("SAP_watchDog.%d (0x%x)", __LINE__, device);
1221 // do nothing if SAP_init not yet called
1222 if (!SAP_initialized)
1223 {
1224 //Log_info2("%s.%d: SAP_init not yet called.\n", (xdc_IArg)__FUNCTION__, __LINE__);
1225 return;
1226 }
1228 // protect context
1229 Task_disable (); // needed since we may call SEM_post
1230 //oldMask = Hwi_disable ();
1233 //Log_info3("%s.%d: devices loop, numDevices = %d", __FUNCTION__, __LINE__, sapDrv.numDevices);
1235 for (i=0; i < sapDrv.numDevices; i++) {
1236 device = sapDrv.device[i];
1238 //Log_info3("%s.%d, devices loop start, device = 0x%x", __FUNCTION__, __LINE__, device);
1240 pDevExt = (SAP_DeviceExtension *) device->object;
1242 // do nothing if not running
1243 if (!pDevExt->runState)
1244 continue;
1246 // call board specific watchdog
1247 // TODO: handle return value
1248 SIO2_ctrl (device, PAF_SIO_CONTROL_WATCHDOG, NULL);
1250 // if port layer returns error then must need to clean up
1251 result = SAP_PORT_FTABLE_watchDog (device);
1252 if (result) {
1253 // set errorState which will force owner thread
1254 // to clean up via SIO_idle()
1255 pDevExt->errorState = PAF_SIO_ERROR_FATAL;
1256 if(device->mode == DEV2_INPUT)
1257 gSapWatchDogIn++;
1258 else
1259 gSapWatchDogOut++;
1261 //TRACE_TERSE((&TR_MOD, "SAP_watchDog.%d, PAF_SIO_ERROR_FATAL: 0x%x", __LINE__, pDevExt->errorState));
1263 // if outstanding pend then post to free owner thead
1264 if (!Semaphore_pend(pDevExt->sync, 0))
1265 {
1266 if(device->mode == DEV2_INPUT)
1267 gSapWatchDogInSemPost++;
1268 else
1269 gSapWatchDogOutSemPost++;
1270 Semaphore_post (pDevExt->sync);
1271 }
1272 }
1273 }
1276 // renable interrupts and task manager.
1277 // If we posted to the semaphore then the TSK_enable call will lead to
1278 // an immediate task switch to the associated audio thread.
1279 //Hwi_restore (oldMask);
1280 Task_enable ();
1282 } // SAP_watchDog
1284 // -----------------------------------------------------------------------------
1285 // Assumes that EDMA3 dispatcher handles TCC clearing.
1287 void SAP_isrCallback (Uint32 tcc, EDMA3_RM_TccStatus status, Ptr context)
1288 {
1289 DEV2_Handle device;
1290 SAP_DeviceExtension *pDevExt;
1291 DEV2_Frame *pFrame;
1292 unsigned int opt;
1293 EDMA3_DRV_Handle hEdma;
1295 // could be here after Tx idle/overrun and this is the interrupt
1296 // for the last occuring error transfer so there is no transfer
1297 // to release, we just clear the int and exit.
1299 device = (DEV2_Handle) context;
1300 pDevExt = (SAP_DeviceExtension *)(device->object);
1301 //if (pDevExt->pParams == NULL)
1302 //return SIO2_EINVAL;
1304 if (pDevExt->pParams->sio.moduleNum == 0)
1305 hEdma = hEdma0;
1306 else if (pDevExt->pParams->sio.moduleNum == 1 || pDevExt->pParams->sio.moduleNum == 2)
1307 hEdma = hEdma1;
1309 if ((pDevExt->runState == 1) && !pDevExt->errorState) {
1310 // if here then an interrupt occured due to errorEdma or valid
1311 // transfer, we assume the xfer is long enough so it will not complete
1312 // before we are finished here.
1314 // if last transfer was valid then complete it
1315 if (!Queue_empty(Queue_handle(&pDevExt->xferQue))) {
1317 // pull frame from holding queue
1318 pFrame = (DEV2_Frame *) Queue_dequeue (Queue_handle(&pDevExt->xferQue));
1320 // if used param entry then return it to queue
1321 if (pFrame->misc != NULL)
1322 {
1323 Queue_enqueue (Queue_handle(&pDevExt->paramQue), (Ptr) pFrame->misc);
1324 if (device->mode == 1)
1325 gisrOutput+=100;
1326 }
1328 // decrement count
1329 pDevExt->numQueued -= 1;
1330 //gIsrCnt++;
1331 if (device->mode == 1)
1332 {
1333 gIsrOutputCnt++;
1334 //Log_info1("SAP isrCallback for 0x%x", pDevExt->activeEdma);
1335 }
1336 else
1337 gIsrInputCnt++;
1338 // place frame onto user queue and signal user thread
1339 Queue_enqueue (device->fromdevice, (Ptr) pFrame);
1341 //Log_info2("Before SEM_post for device: 0x%x gIsrOutput: %d", device->mode, gisrOutput);
1342 // signal user thread
1343 Semaphore_post (pDevExt->sync);
1344 }
1345 else
1346 gIsrElseCnt++;
1348 // determine if currently transferring buffer is valid based on interrupt enable bit
1349 // only valid transfers will generate interrupts
1350 EDMA3_DRV_getPaRAMEntry (hEdma, pDevExt->activeEdma, EDMA3_DRV_PARAM_ENTRY_OPT, &opt);
1352 if (!(opt & EDMA3_DRV_OPT_TCINTEN_SET_MASK (1)))
1353 {
1354 if (device->mode == 1)
1355 gIsrOutErrCnt++;
1356 else
1357 gIsrInErrCnt++;
1358 pDevExt->errorState = PAF_SIO_ERROR_ERRBUF_XFER;
1359 }
1361 } // runState
1362 else
1363 {
1364 if (pDevExt->runState != 1)
1365 gIsrRunCnt++;
1366 else
1367 gIsrNotRunCnt++;
1368 }
1370 return;
1371 } //SAP_isrCallback
1373 // -----------------------------------------------------------------------------
1375 Int SAP_EDMA_setupXfer (DEV2_Handle device, XDAS_UInt32 targetEdma, XDAS_UInt32 parentEdma, XDAS_UInt32 childEdma, DEV2_Frame *pFrame)
1376 {
1377 EDMA3_DRV_Handle hEdma;
1378 SAP_DeviceExtension *pDevExt = (SAP_DeviceExtension *)device->object;
1379 // int mcbspNum = pDevExt->pParams->sio.moduleNum;
1381 if (pDevExt->pParams == NULL)
1382 return SIO2_EINVAL;
1384 if (pDevExt->pParams->sio.moduleNum == 0)
1385 hEdma = hEdma0;
1386 else if (pDevExt->pParams->sio.moduleNum == 1 || pDevExt->pParams->sio.moduleNum == 2)
1387 hEdma = hEdma1;
1389 // TODO: shouldn't this just be tcc interrupt disable?
1390 // at least until linkage phase...
1391 unsigned int key = Hwi_disable ();
1393 if(targetEdma == NULL)
1394 {
1395 Log_info0("targetEdma is NULL");
1396 }
1397 // configure transfer
1398 if(pFrame->addr == NULL)
1399 {
1400 Log_info0("pFrame has NULL address?");
1401 }
1402 SAP_DMA_FTABLE_setupParam (device, targetEdma, childEdma, (XDAS_UInt32) pFrame->addr, pFrame->size);
1404 if (device->mode == DEV2_OUTPUT)
1405 Log_info4("SAP: Inside SAP_EDMA_setupXfer with childEdma=0x%x & targetEdma = 0x%x; pFrame->addr = 0x%x, pFrame->size=0x%x", childEdma, targetEdma, (xdc_IArg)pFrame->addr, pFrame->size);
1407 if (parentEdma != EDMA_HINV)
1408 EDMA3_DRV_linkChannel (hEdma, parentEdma, targetEdma);
1410 if (device->mode == DEV2_OUTPUT)
1411 Log_info3("SAP: Inside SAP_EDMA_setupXfer linked targetEdma = 0x%x with parentEdma=0x%x on Edma=0x%x", targetEdma, parentEdma, (xdc_IArg)hEdma);
1413 Hwi_restore (key);
1415 return SIO2_OK;
1416 } // SAP_setupXfer
1418 // -----------------------------------------------------------------------------
1419 // Configure EDMA3 parameter entry
1421 Int SAP_EDMA_setupParam (DEV2_Handle device, XDAS_UInt32 targetEdma, XDAS_UInt32 childEdma, XDAS_UInt32 addr, XDAS_UInt32 size)
1422 {
1423 SAP_DeviceExtension *pDevExt = (SAP_DeviceExtension *)device->object;
1424 EDMA3_DRV_Handle hEdma;
1425 EDMA3_DRV_PaRAMRegs edmaConfig;
1427 if (pDevExt->pParams == NULL)
1428 return SIO2_EINVAL;
1430 if (pDevExt->pParams->sio.moduleNum == 0)
1431 hEdma = hEdma0;
1432 else if (pDevExt->pParams->sio.moduleNum == 1 || pDevExt->pParams->sio.moduleNum == 2)
1433 hEdma = hEdma1;
1434 MCASP_Handle hPort = sapMcaspDrv.hPort[pDevExt->pParams->sio.moduleNum];
1435 // volatile Uint32 *base = (volatile Uint32 *)(hPort->baseAddr);
1437 //Log_info3("%s.%d: Entered SAP_EDMA_setupParam for Target: 0x%x.\n", (xdc_IArg)__FUNCTION__, __LINE__, targetEdma);
1439 // Init opt parameter to 0 which, without being overriden, configures as:
1440 // AB synchronized transfer
1441 // no chaining or intermediate interrupts
1442 // param is not static
1443 // normal completion
1444 // don't generate an interrupt (overriden below for regular xfers)
1445 edmaConfig.opt = 0;
1447 // not transferring blocks so c index is 0
1448 edmaConfig.destCIdx = 0;
1449 edmaConfig.srcCIdx = 0;
1451 edmaConfig.opt |= EDMA3_DRV_OPT_SYNCDIM_SET_MASK (EDMA3_DRV_SYNC_AB);
1452 if (device->mode == DEV2_OUTPUT)
1453 edmaConfig.opt |= 2; //DAM=CONST addr mode
1454 else
1455 edmaConfig.opt |= 1; //SAM=CONST addr mode
1457 // if regular transfer then enable interrupt with tcc code
1458 if (targetEdma != pDevExt->errorEdma) {
1459 edmaConfig.opt |= EDMA3_DRV_OPT_SYNCDIM_SET_MASK (EDMA3_DRV_SYNC_AB);
1460 edmaConfig.opt |= EDMA3_DRV_OPT_TCINTEN_SET_MASK (1);
1461 edmaConfig.opt |= EDMA3_DRV_OPT_TCC_SET_MASK (pDevExt->firstTCC);
1462 }
1465 edmaConfig.aCnt = 4;
1466 edmaConfig.bCnt = pDevExt->numSers;
1467 edmaConfig.cCnt = size/(edmaConfig.aCnt * edmaConfig.bCnt);
1468 edmaConfig.bCntReload = edmaConfig.bCnt;
1471 // handle direction specific requirements
1472 if (device->mode == DEV2_INPUT) {
1473 edmaConfig.srcBIdx = 0;
1474 edmaConfig.srcAddr = (unsigned int) (hPort->rbufAddr);
1476 if (addr) {
1477 edmaConfig.destBIdx = pDevExt->edmaWordSize;
1478 edmaConfig.destAddr = addr;
1479 edmaConfig.destCIdx = pDevExt->edmaWordSize * pDevExt->numSers ;
1480 if(pDevExt->edmaWordSize == 2)
1481 edmaConfig.cCnt= (size)/((edmaConfig.aCnt * edmaConfig.bCnt)/2);
1482 }
1483 else {
1484 edmaConfig.destBIdx = 0;
1485 edmaConfig.destAddr = (unsigned int) &sap_OVER_4LANE;
1486 edmaConfig.cCnt = 1;
1487 }
1488 }
1489 else {
1490 edmaConfig.destBIdx = 0;
1491 edmaConfig.srcBIdx = pDevExt->edmaWordSize;
1492 edmaConfig.destAddr = (unsigned int) (hPort->xbufAddr);
1493 if (addr) {
1494 edmaConfig.srcCIdx = pDevExt->edmaWordSize * pDevExt->numSers ;
1495 edmaConfig.srcAddr = addr;
1496 }
1497 else {
1498 edmaConfig.srcBIdx = 0;
1499 edmaConfig.srcAddr = (unsigned int) &sap_UNDER[0];
1500 }
1501 }
1502 edmaConfig.srcAddr = (unsigned int) getGlobalAddr(edmaConfig.srcAddr);
1503 edmaConfig.destAddr = (unsigned int) getGlobalAddr(edmaConfig.destAddr);
1505 EDMA3_DRV_setPaRAM (hEdma, targetEdma, &edmaConfig);
1507 // link child xfer
1508 if (childEdma != EDMA_HINV)
1509 EDMA3_DRV_linkChannel (hEdma, targetEdma, childEdma);
1511 if (device->mode == DEV2_OUTPUT) {
1512 Log_info5("SAP: Inside SAP_EDMA_setupParam: size=0x%x, targetEdma = 0x%x, CCNT = %d with dest-addr: 0x%x and OPT=0x%x", size, targetEdma, edmaConfig.cCnt, edmaConfig.destAddr, edmaConfig.opt);
1513 Log_info5("SAP: Inside SAP_EDMA_setupParam: aCnt=0x%x, bCnt = 0x%x; linked targetEdma = 0x%x with childEdma=0x%x on Edma=0x%x", edmaConfig.aCnt, edmaConfig.bCnt, targetEdma, childEdma, (xdc_IArg)hEdma );
1514 }
1516 return SIO2_OK;
1517 } //SAP_setupParam