12e80a665fb4990b78e60bd9dcde855e7c3d1197
[processor-sdk/performance-audio-sr.git] / processor_audio_sdk_1_00_00_00 / pasdk / common / paf_decOpCircBuf.c
2 /*
3 Copyright (c) 2016, 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 #include <string.h> // for memset()
37 #include <xdc/std.h>
38 #include <ti/sysbios/hal/Cache.h>
39 #include <xdc/runtime/Log.h>
41 #include "common.h"
42 #include "pafdec.h"
43 #include "pafsp.h"
44 #include "paf_decOpCircBuf.h"
46 #define MAX_NUM_AF_PCM ( 4 )
47 #define MAX_NUM_AF_DDP ( 2 )
49 #define CB_INIT_RD_LAG ( 2 )
51 // Initialize circular buffer
52 Int cbInit(
53 Int8 sourceSelect, // source select (PCM, DDP, etc.)
54 Int16 decOpFrameLen, // decoder output frame length (PCM samples)
55 Int16 strFrameLen, // stream frame length (PCM samples)
56 PAF_DecodeOpCircBuf *pCb, // decoder output circular buffer
57 Int8 resetRwFlags // whether to reset reader, writer, and empty flags
58 )
59 {
60 PAF_AudioFrame *pAfCb;
61 PAF_AudioData *pPcmBuf;
62 Int8 *pMetaBuf; //QIN
63 Int8 n;
64 Int8 i;
66 // set input frame length
67 pCb->decOpFrameLen = decOpFrameLen;
69 // set output frame length
70 pCb->strFrameLen = strFrameLen;
72 // initialize circular buffer maximum number of audio frames
73 if (sourceSelect == PAF_SOURCE_PCM)
74 {
75 pCb->maxNumAfCb = MAX_NUM_AF_PCM;
76 pCb->afWrtIdx = CB_INIT_RD_LAG;
77 pCb->afRdIdx = 0;
78 pCb->pcmRdIdx = 0; // 2*256 in behind
80 // initialize audio frames
81 for (n=0; n<pCb->maxNumAfCb; n++)
82 {
83 pAfCb = &pCb->afCb[n];
84 pAfCb->sampleDecode = PAF_SOURCE_PCM;
85 PAF_PROCESS_ZERO(pAfCb->sampleProcess);
86 pAfCb->sampleRate = PAF_SAMPLERATE_48000HZ;
87 pAfCb->sampleCount = decOpFrameLen;
88 pAfCb->channelConfigurationRequest.full = 0;
89 pAfCb->channelConfigurationRequest.part.sat = PAF_CC_SAT_SURROUND4;
90 pAfCb->channelConfigurationRequest.part.sub = PAF_CC_SUB_ONE;
91 pAfCb->channelConfigurationStream.full = 0;
92 pAfCb->channelConfigurationStream.part.sat = PAF_CC_SAT_SURROUND4;
93 pAfCb->channelConfigurationStream.part.sub = PAF_CC_SUB_ONE;
94 }
95 }
96 else if (sourceSelect == PAF_SOURCE_DDP)
97 {
98 pCb->maxNumAfCb = MAX_NUM_AF_DDP;
99 pCb->afRdIdx = 0;
100 pCb->pcmRdIdx = decOpFrameLen - CB_INIT_RD_LAG*strFrameLen;
101 pCb->afWrtIdx = 1;
103 // initialize audio frames
104 for (n=0; n<pCb->maxNumAfCb; n++)
105 {
106 pAfCb = &pCb->afCb[n];
107 pAfCb->sampleDecode = PAF_SOURCE_DDP;
108 PAF_PROCESS_ZERO(pAfCb->sampleProcess);
109 pAfCb->sampleRate = PAF_SAMPLERATE_48000HZ;
110 pAfCb->sampleCount = decOpFrameLen;
111 pAfCb->channelConfigurationRequest.full = 0;
112 pAfCb->channelConfigurationRequest.part.sat = PAF_CC_SAT_SURROUND4;
113 pAfCb->channelConfigurationRequest.part.sub = PAF_CC_SUB_ONE;
114 pAfCb->channelConfigurationStream.full = 0;
115 pAfCb->channelConfigurationStream.part.sat = PAF_CC_SAT_SURROUND4;
116 pAfCb->channelConfigurationStream.part.sub = PAF_CC_SUB_ONE;
117 }
118 }
119 else
120 {
121 return PAF_DECOP_CB_INIT_INV_SOURCE_SEL;
122 }
124 // initialize circular buffer current number of frames
125 pCb->numAfCb = pCb->afWrtIdx - pCb->afRdIdx;
127 // initialize audio frame PCM buffers
128 pPcmBuf = pCb->pcmBuf;
129 pMetaBuf = pCb->metaBuf; //QIN
130 for (n=0; n<pCb->maxNumAfCb; n++)
131 {
132 pAfCb = &pCb->afCb[n];
133 pAfCb->data.nChannels = PAF_DECOP_CB_MAX_NUM_PCM_CH;
134 pAfCb->data.nSamples = decOpFrameLen;
135 for (i=0; i<PAF_DECOP_CB_MAX_NUM_PCM_CH; i++)
136 {
137 pAfCb->data.sample[i] = pPcmBuf;
138 memset(pAfCb->data.sample[i], decOpFrameLen, 0);
139 pPcmBuf += decOpFrameLen;
141 pAfCb->data.samsiz[i] = 0;
142 }
143 //Initialize metadata buffers //QIN
144 for (i=0; i<PAF_MAX_NUM_PRIVATE_MD; i++)
145 {
146 pAfCb->pafPrivateMetadata[i].offset = 0;
147 pAfCb->pafPrivateMetadata[i].size = 0;
148 pAfCb->pafPrivateMetadata[i].pMdBuf = pMetaBuf;
149 pMetaBuf += PAF_MAX_PRIVATE_MD_SZ;
150 }
151 }
153 // reset read/write flags
154 if (resetRwFlags)
155 {
156 pCb->writerActiveFlag = 0;
157 pCb->readerActiveFlag = 0;
158 pCb->emptyFlag = 0;
159 }
160 // reset error counts
161 pCb->errUndCnt = 0;
162 pCb->errOvrCnt = 0;
164 // (***) FL: revisit
165 // Write back circular buffer configuration
166 Cache_wb(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
167 // Write back AF circular buffer
168 Cache_wb(pCb->afCb, pCb->maxNumAfCb*sizeof(PAF_AudioFrame), Cache_Type_ALLD, 0);
169 // Write back PCM data
170 for (n=0; n<pCb->maxNumAfCb; n++)
171 {
172 pAfCb = &pCb->afCb[n];
173 Cache_wb(pAfCb->data.samsiz, PAF_DECOP_CB_MAX_NUM_PCM_CH*sizeof(PAF_AudioSize), Cache_Type_ALLD, 0);
174 Cache_wb(pAfCb->data.sample, PAF_DECOP_CB_MAX_NUM_PCM_CH*sizeof(PAF_AudioData *), Cache_Type_ALLD, 0);
175 for (i=0; i<PAF_DECOP_CB_MAX_NUM_PCM_CH; i++)
176 {
177 Cache_wb(pAfCb->data.sample[i], decOpFrameLen*sizeof(PAF_AudioData), Cache_Type_ALLD, 0);
178 }
179 for (i=0; i<PAF_MAX_NUM_PRIVATE_MD; i++) // Write back metadata //QIN
180 {
181 Cache_wb(&pAfCb->pafPrivateMetadata[i], sizeof(PAF_PrivateMetadata), Cache_Type_ALLD, 0);
182 }
183 }
184 Cache_wait();
186 return PAF_DECOP_CB_SOK;
187 }
189 // Start writes to circular buffer
190 Int cbWriteStart(
191 PAF_DecodeOpCircBuf *pCb // decoder output circular buffer
192 )
193 {
194 PAF_AudioFrame *pAfCb;
195 Int8 n;
196 Int8 i;
198 // (***) FL: revisit
199 // Invalidate circular buffer configuration.
200 // NOTE: Probably only a subset of this information needs to be updated.
201 Cache_inv(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
202 Cache_wait();
204 // Invalidate AF circular buffer
205 Cache_inv(pCb->afCb, pCb->maxNumAfCb*sizeof(PAF_AudioFrame), Cache_Type_ALLD, 0);
206 for (n=0; n<pCb->maxNumAfCb; n++)
207 {
208 pAfCb = &pCb->afCb[n];
209 Cache_inv(pAfCb->data.sample, PAF_DECOP_CB_MAX_NUM_PCM_CH*sizeof(PAF_AudioData *), Cache_Type_ALLD, 0);
210 for (i=0; i<PAF_MAX_NUM_PRIVATE_MD; i++) //QIN
211 {
212 Cache_inv(&pAfCb->pafPrivateMetadata[i], sizeof(PAF_PrivateMetadata), Cache_Type_ALLD, 0);
213 }
214 }
215 Cache_wait();
217 // update flags
218 pCb->writerActiveFlag = 1;
219 pCb->emptyFlag = 0;
221 // (***) FL: revisit
222 // Write back circular buffer configuration
223 Cache_wb(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
224 Cache_wait();
226 return PAF_DECOP_CB_SOK;
227 };
229 // Stop writes to circular buffer
230 Int cbWriteStop(
231 PAF_DecodeOpCircBuf *pCb // decoder output circular buffer
232 )
233 {
234 // Invalidate circular buffer configuration
235 Cache_inv(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
236 Cache_wait();
238 // update flags
239 pCb->writerActiveFlag = 0;
240 pCb->emptyFlag = 1;
242 // (***) FL: revisit
243 // Write back circular buffer configuration
244 Cache_wb(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
245 Cache_wait();
247 return PAF_DECOP_CB_SOK;
248 }
250 // Start reads from circular buffer
251 Int cbReadStart(
252 PAF_DecodeOpCircBuf *pCb // decoder output circular buffer
253 )
254 {
255 // Invalidate circular buffer configuration
256 Cache_inv(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
257 Cache_wait();
259 // update flags
260 pCb->readerActiveFlag = 1;
262 // (***) FL: revisit
263 // Write back circular buffer configuration
264 Cache_wb(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
265 Cache_wait();
267 return PAF_DECOP_CB_SOK;
268 }
270 // Stop reads from circular buffer
271 Int cbReadStop(
272 PAF_DecodeOpCircBuf *pCb // decoder output circular buffer
273 )
274 {
275 // Invalidate circular buffer configuration
276 Cache_inv(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
277 Cache_wait();
279 // update flags
280 pCb->readerActiveFlag = 0;
282 // (***) FL: revisit
283 // Write back circular buffer configuration
284 Cache_wb(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
285 Cache_wait();
287 return PAF_DECOP_CB_SOK;
288 }
290 // Read audio frame from circular buffer
291 Int cbReadAf(
292 PAF_DecodeOpCircBuf *pCb, // decoder output circular buffer
293 PAF_AudioFrame *pAfRd // audio frame into which to read
294 )
295 {
296 PAF_AudioFrame *pAfCb;
297 PAF_ChannelMask_HD streamMask;
298 Int8 i;
299 Int16 j;
301 // (***) FL: revisit
302 // Invalidate circular buffer configuration.
303 Cache_inv(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
304 Cache_wait();
306 if ((pCb->writerActiveFlag == 1) && (pCb->emptyFlag == 1))
307 {
308 // This shouldn't occur:
309 // writer is active AND draining circular buffer
310 Log_info2("cbReadAf: ERROR: writerActiveFlag=%d, emptyFlag=%d", pCb->writerActiveFlag, pCb->emptyFlag);
311 SW_BREAKPOINT; // FL: debug
312 return PAF_DECOP_CB_READ_INVSTATE;
313 }
315 if ((pCb->writerActiveFlag == 0) && (pCb->emptyFlag == 0))
316 {
317 //
318 // No active writer, not draining circular buffer.
319 // Skip UNDerflow check, mute output.
320 //
321 pAfRd->sampleDecode = PAF_SOURCE_PCM;
322 PAF_PROCESS_ZERO(pAfRd->sampleProcess);
323 pAfRd->sampleRate = PAF_SAMPLERATE_48000HZ;
324 pAfRd->sampleCount = pCb->strFrameLen;
325 pAfRd->channelConfigurationRequest.full = 0;
326 pAfRd->channelConfigurationRequest.part.sat = PAF_CC_SAT_SURROUND4;
327 pAfRd->channelConfigurationRequest.part.sub = PAF_CC_SUB_ONE;
328 pAfRd->channelConfigurationStream.full = 0;
329 pAfRd->channelConfigurationStream.part.sat = PAF_CC_SAT_SURROUND4;
330 pAfRd->channelConfigurationStream.part.sub = PAF_CC_SUB_ONE;
332 // compute stream mask
333 streamMask = pAfRd->fxns->channelMask(pAfRd, pAfRd->channelConfigurationStream);
334 // Clear PCM data
335 for (i = 0; i < PAF_DECOP_CB_MAX_NUM_PCM_CH; i++)
336 {
337 if ((streamMask >> i) & 0x1)
338 {
339 memset(pAfRd->data.sample[i], pCb->strFrameLen, 0);
340 }
341 pAfRd->data.samsiz[i] = 0;
342 }
344 return PAF_DECOP_CB_SOK;
345 }
347 if ((pCb->writerActiveFlag == 1))
348 {
349 // check underflow
350 if (pCb->numAfCb <= 0)
351 {
352 pCb->errUndCnt++;
353 //SW_BREAKPOINT; // FL: debug
354 Log_info1("cbReadAf: ERROR: underflow, numAfCb=%d", pCb->numAfCb);
355 return PAF_DECOP_CB_READ_UNDERFLOW;
356 }
357 }
359 if ((pCb->writerActiveFlag == 1) || (pCb->emptyFlag == 1))
360 {
361 //
362 // Writer active or draining remaining frames in circular buffer.
363 // Get next output audio frame.
364 //
366 // get pointer to current audio frame in circular buffer
367 pAfCb = &pCb->afCb[pCb->afRdIdx];
369 // (***) FL: revisit
370 // Invalidate audio frame
371 Cache_inv(pAfCb, sizeof(PAF_AudioFrame), Cache_Type_ALLD, 0);
372 Cache_inv(pAfCb->data.samsiz, PAF_DECOP_CB_MAX_NUM_PCM_CH*sizeof(PAF_AudioSize), Cache_Type_ALLD, 0);
373 for (i=0; i<PAF_MAX_NUM_PRIVATE_MD; i++) //QIN
374 {
375 Cache_inv(&pAfCb->pafPrivateMetadata[i], sizeof(PAF_PrivateMetadata), Cache_Type_ALLD, 0);
376 Cache_inv(pAfCb->pafPrivateMetadata[i].pMdBuf, PAF_MAX_PRIVATE_MD_SZ*sizeof(Int8), Cache_Type_ALLD, 0);
377 }
378 Cache_wait();
380 // compute stream mask
381 streamMask = pAfRd->fxns->channelMask(pAfRd, pAfCb->channelConfigurationStream);
383 // Invalidate PCM data
384 for (i = 0; i < PAF_DECOP_CB_MAX_NUM_PCM_CH; i++)
385 {
386 if ((streamMask >> i) & 0x1)
387 {
388 Cache_inv(&pAfCb->data.sample[i][pCb->pcmRdIdx], pCb->strFrameLen*sizeof(PAF_AudioData), Cache_Type_ALLD, 0);
389 }
390 }
391 Cache_wait();
393 // read audio frame information updated by decoder
394 pAfRd->sampleDecode = pAfCb->sampleDecode;
395 PAF_PROCESS_COPY(pAfRd->sampleProcess, pAfCb->sampleProcess);
396 pAfRd->sampleRate = pAfCb->sampleRate;
397 pAfRd->sampleCount = pCb->strFrameLen;
398 pAfRd->channelConfigurationRequest = pAfCb->channelConfigurationRequest;
399 pAfRd->channelConfigurationStream = pAfCb->channelConfigurationStream;
401 // read metadata information updated by decoder //QIN
402 pAfRd->bsMetadata_type = pAfCb->bsMetadata_type; /* non zero if metadata is attached. */
403 pAfRd->pafBsMetadataUpdate = pAfCb->pafBsMetadataUpdate; /* indicates whether bit-stream metadata update */
404 pAfRd->numPrivateMetadata = pAfCb->numPrivateMetadata; /* number of valid private metadata (0 or 1 if metadata filtering enabled) */
405 pAfRd->bsMetadata_offset = pAfCb->bsMetadata_offset; /* offset into audio frame for change in bsMetadata_type field */
407 // read PCM samples
408 for (i = 0; i < PAF_DECOP_CB_MAX_NUM_PCM_CH; i++)
409 {
410 if ((streamMask >> i) & 0x1)
411 {
412 for (j = 0; j < pCb->strFrameLen; j++)
413 {
414 pAfRd->data.sample[i][j] = pAfCb->data.sample[i][pCb->pcmRdIdx+j];
415 }
417 pAfRd->data.samsiz[i] = pAfCb->data.samsiz[i];
418 }
419 }
420 // read metadata //QIN
421 for (i = 0; i < PAF_MAX_NUM_PRIVATE_MD; i++)
422 {
423 //Invalidate metadata data
424 Cache_inv(&pAfCb->pafPrivateMetadata[i], sizeof(PAF_PrivateMetadata), Cache_Type_ALLD, 0);
425 Cache_wait();
426 if ((pAfCb->pafPrivateMetadata[i].offset >= pCb->pcmRdIdx)
427 &&(pAfCb->pafPrivateMetadata[i].offset < (pCb->pcmRdIdx + pCb->strFrameLen))
428 &&(pAfCb->pafPrivateMetadata[i].size))
429 {
430 //Invalidate metadata data
431 Cache_inv(pAfCb->pafPrivateMetadata[i].pMdBuf, pAfCb->pafPrivateMetadata[i].size, Cache_Type_ALLD, 0);
432 Cache_wait();
434 // the offset is adjusted for segment [pCb->pcmRdIdx, (pCb->pcmRdIdx + pCb->pafFrameLen)]
435 pAfRd->pafPrivateMetadata[i].offset = 0;//pAfCb->pafPrivateMetadata[i].offset - pCb->pcmRdIdx;
436 pAfRd->pafPrivateMetadata[i].size = pAfCb->pafPrivateMetadata[i].size;
437 memcpy (pAfRd->pafPrivateMetadata[i].pMdBuf, pAfCb->pafPrivateMetadata[i].pMdBuf, pAfCb->pafPrivateMetadata[i].size);
438 }
439 else //reset un-used buf
440 {
441 pAfRd->pafPrivateMetadata[i].offset = 0;
442 pAfRd->pafPrivateMetadata[i].size = 0;
443 }
444 }
445 pCb->pcmRdIdx += pCb->strFrameLen; // update PCM read index
446 if (pCb->pcmRdIdx == pCb->decOpFrameLen)
447 {
448 // update audio frame read index
449 pCb->afRdIdx++;
450 if (pCb->afRdIdx >= pCb->maxNumAfCb)
451 {
452 pCb->afRdIdx = 0;
453 }
455 // update PCM read index
456 pCb->pcmRdIdx = 0;
458 // update number of audio frames in circular buffer
459 pCb->numAfCb--;
460 }
461 }
463 if (pCb->emptyFlag == 1)
464 {
465 //
466 // Writer inactive, but remaining frames in circular buffer.
467 // Update empty flag.
468 //
469 if (pCb->numAfCb <= 0)
470 {
471 pCb->emptyFlag = 0;
472 }
473 }
475 // (***) FL: revisit
476 // Write back circular buffer configuration.
477 // NOTE: Probably only a subset of this information needs to be updated.
478 Cache_wb(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
479 Cache_wait();
481 return PAF_DECOP_CB_SOK;
482 }
484 // Write audio frame to circular buffer
485 Int cbWriteAf(
486 PAF_DecodeOpCircBuf *pCb, // decoder output circular buffer
487 PAF_AudioFrame *pAfWrt // audio frame from which to write
488 )
489 {
490 PAF_AudioFrame *pAfCb;
491 PAF_ChannelMask_HD streamMask;
492 Int8 i;
493 Int16 j;
495 // (***) FL: revisit
496 // Invalidate circular buffer configuration.
497 // NOTE: Probably only a subset of this information needs to be updated.
498 Cache_inv(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
499 Cache_wait();
501 if (pCb->readerActiveFlag == 1)
502 {
503 //
504 // Normal case, reader active.
505 // If reader not active, don't write to circular buffer or check OVRflow.
507 #if 0
508 if (pCb->cbWriteAfInit == 0)
509 {
510 // Invalidate AF circular buffer
511 Cache_inv(pCb->afCb, pCb->maxNumAfCb*sizeof(PAF_AudioFrame), Cache_Type_ALLD, 0);
512 for (n=0; n<pCb->maxNumAfCb; n++)
513 {
514 pAfCb = &pCb->afCb[n];
515 Cache_inv(pAfCb->data.sample, PAF_DECOP_CB_MAX_NUM_PCM_CH*sizeof(PAF_AudioData *), Cache_Type_ALLD, 0);
516 }
517 Cache_wait();
519 pCb->cbWriteAfInit = 1;
520 }
521 #endif
523 // check overflow
524 if (pCb->numAfCb >= pCb->maxNumAfCb)
525 {
526 pCb->errOvrCnt++;
527 //SW_BREAKPOINT;
528 Log_info1("cbWriteAf: ERROR: overflow, numAfCb=%d", pCb->numAfCb);
529 return PAF_DECOP_CB_WRITE_OVERFLOW;
530 }
531 //while (pCb->numAfCb >= pCb->maxNumAfCb); //Qin replace with while loop for debugging
532 // get pointer to current audio frame in circular buffer
533 pAfCb = &pCb->afCb[pCb->afWrtIdx];
535 // write audio frame information updated by decoder
536 pAfCb->sampleDecode = pAfWrt->sampleDecode;
537 PAF_PROCESS_COPY(pAfCb->sampleProcess, pAfWrt->sampleProcess);
538 pAfCb->sampleRate = pAfWrt->sampleRate;
539 pAfCb->sampleCount = pAfWrt->sampleCount;
540 pAfCb->channelConfigurationRequest = pAfWrt->channelConfigurationRequest;
541 pAfCb->channelConfigurationStream = pAfWrt->channelConfigurationStream;
542 // write metadata information updated by decoder//QIN
543 pAfCb->bsMetadata_type = pAfWrt->bsMetadata_type; /* non zero if metadata is attached. */
544 pAfCb->pafBsMetadataUpdate = pAfWrt->pafBsMetadataUpdate; /* indicates whether bit-stream metadata update */
545 pAfCb->numPrivateMetadata = pAfWrt->numPrivateMetadata; /* number of valid private metadata (0 or 1 if metadata filtering enabled) */
546 pAfCb->bsMetadata_offset = pAfWrt->bsMetadata_offset; /* offset into audio frame for change in bsMetadata_type field */
547 // write PCM samples
548 streamMask = pAfWrt->fxns->channelMask(pAfWrt, pAfCb->channelConfigurationStream);
549 for (i = 0; i < PAF_DECOP_CB_MAX_NUM_PCM_CH; i++)
550 {
551 if ((streamMask >> i) & 0x1)
552 {
553 for (j = 0; j < pCb->decOpFrameLen; j++)
554 {
555 pAfCb->data.sample[i][j] = pAfWrt->data.sample[i][j];
556 }
558 pAfCb->data.samsiz[i] = pAfWrt->data.samsiz[i];
559 }
560 }
562 //Write metadata to circular buffer //QIN
563 for (i = 0; i < PAF_MAX_NUM_PRIVATE_MD; i++)
564 {
565 if (pAfWrt->pafPrivateMetadata[i].size)
566 {
567 pAfCb->pafPrivateMetadata[i].offset = pAfWrt->pafPrivateMetadata[i].offset;
568 pAfCb->pafPrivateMetadata[i].size = pAfWrt->pafPrivateMetadata[i].size;
569 memcpy (pAfCb->pafPrivateMetadata[i].pMdBuf, pAfWrt->pafPrivateMetadata[i].pMdBuf, pAfWrt->pafPrivateMetadata[i].size);
570 }
571 else
572 {
573 pAfCb->pafPrivateMetadata[i].offset = 0;
574 pAfCb->pafPrivateMetadata[i].size = 0;
575 }
576 }
577 // update audio frame write index
578 pCb->afWrtIdx++;
579 if (pCb->afWrtIdx >= pCb->maxNumAfCb)
580 {
581 pCb->afWrtIdx = 0;
582 }
584 // update number of audio frames in circular buffer
585 pCb->numAfCb++;
587 // (***) FL: revisit
588 // Write back circular buffer configuration
589 Cache_wb(pCb, sizeof(PAF_DecodeOpCircBuf), Cache_Type_ALLD, 0);
590 // write back audio frame
591 Cache_wb(pAfCb, sizeof(PAF_AudioFrame), Cache_Type_ALLD, 0);
592 Cache_wb(pAfCb->data.samsiz, PAF_DECOP_CB_MAX_NUM_PCM_CH*sizeof(PAF_AudioSize), Cache_Type_ALLD, 0);
593 // write back PCM data
594 for (i = 0; i < PAF_DECOP_CB_MAX_NUM_PCM_CH; i++)
595 {
596 if ((streamMask >> i) & 0x1)
597 {
598 Cache_wb(pAfCb->data.sample[i], pCb->decOpFrameLen*sizeof(PAF_AudioData), Cache_Type_ALLD, 0);
599 }
600 }
601 // write back private metadata
602 for (i=0; i<PAF_MAX_NUM_PRIVATE_MD; i++) //QIN
603 {
604 Cache_wb(&pAfCb->pafPrivateMetadata[i], sizeof(PAF_PrivateMetadata), Cache_Type_ALLD, 0);
605 Cache_wb(pAfCb->pafPrivateMetadata[i].pMdBuf, PAF_MAX_PRIVATE_MD_SZ*sizeof(Int8), Cache_Type_ALLD, 0);
606 }
607 Cache_wait();
608 }
610 return PAF_DECOP_CB_SOK;
611 }
613 // Get next audio frame to write in circular buffer
614 Int cbGetNextWriteAf(
615 PAF_DecodeOpCircBuf *pCb, // decoder output circular buffer
616 PAF_AudioFrame **ppAfWrt // audio frame next to be written
617 )
618 {
619 // get pointer to current audio frame in circular buffer
620 *ppAfWrt = &pCb->afCb[pCb->afWrtIdx];
622 // update audio frame write index
623 pCb->afWrtIdx++;
624 if (pCb->afWrtIdx > pCb->maxNumAfCb)
625 {
626 pCb->afWrtIdx = 0;
627 }
629 return PAF_DECOP_CB_SOK;
630 }
632 // Output log of circular buffer control variables (debug)
633 Int cbLog(
634 PAF_DecodeOpCircBuf *pCb,
635 Int8 fullLog,
636 char *locInfo
637 )
638 {
639 Log_info1("CB: %s", (IArg)locInfo);
640 Log_info3("CB: readerActiveFlag=%d, writerActiveFlag=%d, emptyFlag=%d", pCb->readerActiveFlag, pCb->writerActiveFlag, pCb->emptyFlag);
641 Log_info4("CB: afRdIdx=%d, pcmRdIdx=%d, afWrtIdx=%d, numAfCb=%d", pCb->afRdIdx, pCb->pcmRdIdx,
642 pCb->afWrtIdx,
643 pCb->numAfCb);
644 if (fullLog)
645 {
646 Log_info1("CB: maxNumAfCb=%d", pCb->maxNumAfCb);
647 Log_info2("CB: decOpFrameLen=%d, strFrameLen=%d", pCb->decOpFrameLen, pCb->strFrameLen);
648 //Log_info1("cbWriteInit=%d", pCb->cbWriteAfInit);
649 }
651 return 0;
652 }