source: svn/newcon3bcm2_21bu/nexus/modules/transport/7552/src/nexus_rave.c

Last change on this file was 76, checked in by megakiss, 10 years ago

1W 대기전력을 만족시키기 위하여 POWEROFF시 튜너를 Standby 상태로 함

  • Property svn:executable set to *
File size: 50.5 KB
Line 
1/***************************************************************************
2 *     (c)2007-2011 Broadcom Corporation
3 *
4 *  This program is the proprietary software of Broadcom Corporation and/or its licensors,
5 *  and may only be used, duplicated, modified or distributed pursuant to the terms and
6 *  conditions of a separate, written license agreement executed between you and Broadcom
7 *  (an "Authorized License").  Except as set forth in an Authorized License, Broadcom grants
8 *  no license (express or implied), right to use, or waiver of any kind with respect to the
9 *  Software, and Broadcom expressly reserves all rights in and to the Software and all
10 *  intellectual property rights therein.  IF YOU HAVE NO AUTHORIZED LICENSE, THEN YOU
11 *  HAVE NO RIGHT TO USE THIS SOFTWARE IN ANY WAY, AND SHOULD IMMEDIATELY
12 *  NOTIFY BROADCOM AND DISCONTINUE ALL USE OF THE SOFTWARE.
13 *
14 *  Except as expressly set forth in the Authorized License,
15 *
16 *  1.     This program, including its structure, sequence and organization, constitutes the valuable trade
17 *  secrets of Broadcom, and you shall use all reasonable efforts to protect the confidentiality thereof,
18 *  and to use this information only in connection with your use of Broadcom integrated circuit products.
19 *
20 *  2.     TO THE MAXIMUM EXTENT PERMITTED BY LAW, THE SOFTWARE IS PROVIDED "AS IS"
21 *  AND WITH ALL FAULTS AND BROADCOM MAKES NO PROMISES, REPRESENTATIONS OR
22 *  WARRANTIES, EITHER EXPRESS, IMPLIED, STATUTORY, OR OTHERWISE, WITH RESPECT TO
23 *  THE SOFTWARE.  BROADCOM SPECIFICALLY DISCLAIMS ANY AND ALL IMPLIED WARRANTIES
24 *  OF TITLE, MERCHANTABILITY, NONINFRINGEMENT, FITNESS FOR A PARTICULAR PURPOSE,
25 *  LACK OF VIRUSES, ACCURACY OR COMPLETENESS, QUIET ENJOYMENT, QUIET POSSESSION
26 *  OR CORRESPONDENCE TO DESCRIPTION. YOU ASSUME THE ENTIRE RISK ARISING OUT OF
27 *  USE OR PERFORMANCE OF THE SOFTWARE.
28 *
29 *  3.     TO THE MAXIMUM EXTENT PERMITTED BY LAW, IN NO EVENT SHALL BROADCOM OR ITS
30 *  LICENSORS BE LIABLE FOR (i) CONSEQUENTIAL, INCIDENTAL, SPECIAL, INDIRECT, OR
31 *  EXEMPLARY DAMAGES WHATSOEVER ARISING OUT OF OR IN ANY WAY RELATING TO YOUR
32 *  USE OF OR INABILITY TO USE THE SOFTWARE EVEN IF BROADCOM HAS BEEN ADVISED OF
33 *  THE POSSIBILITY OF SUCH DAMAGES; OR (ii) ANY AMOUNT IN EXCESS OF THE AMOUNT
34 *  ACTUALLY PAID FOR THE SOFTWARE ITSELF OR U.S. $1, WHICHEVER IS GREATER. THESE
35 *  LIMITATIONS SHALL APPLY NOTWITHSTANDING ANY FAILURE OF ESSENTIAL PURPOSE OF
36 *  ANY LIMITED REMEDY.
37 *
38 * $brcm_Workfile: nexus_rave.c $
39 * $brcm_Revision: 85 $
40 * $brcm_Date: 11/21/11 2:48p $
41 *
42 * Module Description:
43 *
44 * Revision History:
45 *
46 * $brcm_Log: /nexus/modules/transport/7400/src/nexus_rave.c $
47 *
48 * 85   11/21/11 2:48p jgarrett
49 * SW7425-1406: Adding Vorbis audio support
50 *
51 * VORBIS_DEVEL/2   11/16/11 4:21p jgarrett
52 * SW7425-1406: Merge latest changes from main branch
53 *
54 * 84   10/19/11 6:03p jtna
55 * SW7422-452: update RAVE programming for vp6 video
56 *
57 * VORBIS_DEVEL/1   10/5/11 6:18p jgarrett
58 * SW7425-1406: Adding Vorbis support
59 *
60 * 83   9/23/11 11:07a jtna
61 * SW7346-493: Coverity defect 35380: DEADCODE
62 *
63 * 82   8/26/11 5:57p jgarrett
64 * SW7344-160: Adding DTS-Legacy support
65 *
66 * 81   8/25/11 3:29p erickson
67 * SW7346-454: add NEXUS_RecpumpStatus.rave.index
68 *
69 * 80   8/15/11 3:11p vsilyaev
70 * SW7425-938: Added mapping for SH263 and VP8 video codecs
71 *
72 * 79   7/1/11 11:18a jgarrett
73 * SW7405-5071: Adding WMA TS
74 *
75 * 78   4/18/11 10:19a erickson
76 * SW7335-1168: add NEXUS_RaveStatus.enabled
77 *
78 * 77   4/12/11 10:28a erickson
79 * SW7342-331: switch SW RAVE extension to use
80 *  BXPT_RaveSoftMode_ePointersOnly, fail on any codec that requires ITB
81 *  manipulation. rename to NEXUS_SW_RAVE_PEEK_EXTENSION.
82 *
83 * 76   4/6/11 2:56p erickson
84 * SW7342-340: add HW rave indices to NEXUS_VideoDecoderExtendedStatus
85 *
86 * 75   3/11/11 3:33p vsilyaev
87 * SW7422-14: Properly signal invalid video codec
88 *
89 * 74   2/28/11 11:06a erickson
90 * SW7342-331: add template SW RAVE extension
91 *
92 * 73   2/14/11 12:09p dlwin
93 * SW7405-5140: Updated with a better fix to the problem.
94 *
95 * 72   2/14/11 11:38a dlwin
96 * SW7405-5140: For ES input streams, Nexus needs to disable XPT
97 *  DISABLE_BEFORE_PES filter.
98 *
99 * 71   1/19/11 3:48p vsilyaev
100 * SW7422-216: Added VP6 video codec
101 *
102 * 70   12/13/10 4:06p erickson
103 * SW35230-179: add NEXUS_RaveStatus.numOutputBytes
104 *
105 * 69   11/29/10 11:33a vsilyaev
106 * SW7422-65: Fixed mapping of SVC/MVC video codecs
107 *
108 * 68   11/18/10 1:49p akam
109 * SW35230-91: Added ADPCM audio decoder support.
110 *
111 * 67   11/5/10 12:28p gmohile
112 * SW7422-20 : Use BXPT_HAS_PID_CHANNEL_PES_FILTERING instead of
113 *  BXPT_P_MAX_PACKETIZERS_PER_PB
114 *
115 * 66   11/3/10 7:10p jgarrett
116 * SW35230-91: Renamed NEXUS_AudioCodec_eRealAudioLbr to _eCook
117 *
118 * 65   11/3/10 4:32p erickson
119 * SW7422-20: use BXPT_P_MAX_PACKETIZERS_PER_PB instead of
120 *  NEXUS_SW_VOB_SUPPORT
121 *
122 * 64   10/28/10 5:09p erickson
123 * SW7422-20: adapt to new XPT PI (backward compat using magnum and nexus
124 *  macros)
125 *
126 * 63   10/14/10 11:19a akam
127 * SW35230-91: Added Real Audio LBR codec support.
128 *
129 * 62   9/8/10 12:06p vsilyaev
130 * SW7468-129: Added video decoder on ZSP
131 *
132 * 61   6/22/10 3:57p erickson
133 * SW7405-4492: refactor RAVE BDBG_MSG to print context #, codec and pid
134 *  ch for audio and video. allow user to figure out which RAVE context is
135 *  being used.
136 *
137 * 60   5/13/10 6:50p jgarrett
138 * SW7405-4298: Adding AD extraction for AAC/AAC-HE/AC3/DDP
139 *
140 * 59   5/3/10 5:22p jgarrett
141 * SW7405-4212: Removing DolbyPulse as an explicit codec type
142 *
143 * SW7405-4212/1   4/26/10 5:23p jgarrett
144 * SW7405-4212: Adding MS10 changes for pulse/transcode
145 *
146 * 58   3/18/10 10:55a jgarrett
147 * SW7405-4030: Adding Dolby Pulse Support
148 *
149 * 57   3/10/10 6:59p jtna
150 * SW3556-1051: enable sw rave for mkv streams
151 *
152 * 56   2/8/10 5:31p jtna
153 * SW3556-1003: added option to disable reordering of video frames
154 *
155 * 55   1/12/10 6:16p jtna
156 * SW3548-2716: fix enabling of swRave for AVI/ASF streams
157 *
158 * 47   7/15/09 7:24p vsilyaev
159 * PR 55653: Added WAV format
160 *
161 * 46   6/30/09 4:49p katrep
162 * PR55809: Add support for PCMWAV used with AVI PCM
163 *
164 * 45   6/4/09 5:45p katrep
165 * PR55074: Add support DTS Broadcast decoder
166 *
167 * 44   5/8/09 2:42p erickson
168 * PR54061: set default values to BXPT_Rave_SetContextConfig. this fixes
169 *  MPEG audio in VOB after AC3 audio in VOB.
170 *
171 * 43   3/30/09 10:35a erickson
172 * PR50748: support the secure heap using module settings handle
173 *
174 * 42   3/17/09 5:41p vsilyaev
175 * PR 46190: Adding mappings to the PCM audio codec
176 *
177 * 41   2/4/09 7:09p vsilyaev
178 * PR 50887: Added bit to enable OTF PVR mode
179 *
180 * 40   1/16/09 2:02p erickson
181 * PR50905: added NEXUS_Rave_GetMostRecentPts_priv
182 *
183 * 39   1/16/09 2:00p erickson
184 * PR51209: must check if swRave is enabled before using its context map
185 *
186 * 38   12/8/08 12:22p erickson
187 * PR48155: check cdb valid and read to determine if fifo is hung
188 *
189 * 37   12/3/08 1:18p erickson
190 * PR45405: rename rave member to pidChannelIndex to avoid
191 *  misunderstanding
192 *
193 * 36   12/3/08 12:26p erickson
194 * PR45405: implicit NEXUS_Rave_RemovePidChannel_priv is needed when
195 *  closing rave
196 *
197 * 35   11/18/08 12:56p erickson
198 * PR48155: report swRave CDB_Valid if appropriate
199 *
200 * 34   10/21/08 3:35p erickson
201 * PR48149: start/stop sw rave timer when rave context is enabled/disabled
202 *
203 * 33   9/11/08 4:37p erickson
204 * PR46825: fix sw rave
205 *
206 * 32   9/9/08 10:04a erickson
207 * PR45940: added NEXUS_Rave_GetCdbValidPointer_isr for better detection
208 *  if source fifo goes dry
209 *
210 * 31   8/14/08 5:25p katrep
211 * PR45674: Fix compiiler warning in kernel mode non debug builds
212 *
213 * 30   8/4/08 9:15a erickson
214 * PR45037: fix 3563 compilation
215 *
216 * 29   7/31/08 9:22a erickson
217 * PR45037: fix HW index detection
218 *
219 * 28   7/29/08 2:24p erickson
220 * PR45238: convert WRN to MSG
221 *
222 * 27   7/23/08 3:01p jgarrett
223 * PR 39452: Merging to main branch
224 *
225 * 26   7/21/08 4:32p katrep
226 * PR44143: Set the LOAS as default configuration for AAC Plus audio
227 *  format.
228 *
229 * 25   7/17/08 5:24p jgarrett
230 * PR 42642: Adding Get/Set thresholds
231 *
232 * 24   7/1/08 11:43a erickson
233 * PR44070: fix non-sw rave chips
234 *
235 * 23   6/30/08 1:45p erickson
236 * PR44165: impl NEXUS_CORE_NUM_SECURE_HEAPS
237 *
238 * 22   6/26/08 4:33p erickson
239 * PR44070: NEXUS_Rave_FindVideoStartCode_priv needs to search swRave
240 *  context if enabled. NEXUS_VideoCodec_eDivx311 should be handled like
241 *  NEXUS_VideoCodec_eDivx311 if SW rave not enabled.
242 *
243 * 21   5/30/08 12:45p erickson
244 * PR43123: fix non-sw rave chips
245 *
246 * 20   5/30/08 12:40p erickson
247 * PR43123: properly flush sw RAVE context if B_USE_SETTOP_API_SW_RAVE is
248 *  defined
249 *
250 * 19   5/30/08 10:54a erickson
251 * PR43123: add USE_SETTOP_API_SW_RAVE build option, but default it off.
252 *
253 * 18   5/22/08 1:48p vsilyaev
254 * PR 42365: Only use SW rave of required by original transport format
255 *
256 * 17   5/20/08 10:08a erickson
257 * PR42758: check pidChannelStatus.originalTransportType for VOB test
258 *
259 * 16   5/19/08 3:48p gmullen
260 * PR42758: Added AC3+ case to VOB config code.
261 *
262 * Nexus_Audio_Descriptors/1   5/15/08 5:35p jgarrett
263 * PR 42360: Adding audio descriptor placeholder
264 *
265 * 15   5/14/08 3:28p jgarrett
266 * PR 42221: Adding audio frame depth
267 *
268 * 14   5/9/08 4:51p erickson
269 * PR34925: added cont_count_ignore env override for debug
270 *
271 * 13   4/30/08 10:11a erickson
272 * PR42349: cancel swRave timer in NEXUS_CancelTimer
273 *
274 * 12   4/10/08 2:04p erickson
275 * PR37893: fix warning
276 *
277 * 11   4/7/08 10:16a erickson
278 * PR37893: convert to XPT PI sw rave
279 *
280 * 10   4/4/08 11:18a erickson
281 * PR40079: impl NEXUS_PidChannel_GetScramblingStatus
282 *
283 * 9   3/26/08 12:14p katrep
284 * PR40841: For DSS ES streams stream type should be changed to DDS PES
285 *  when given to RAVE.
286 *
287 * 8   3/18/08 4:51p erickson
288 * PR40307: perform more robust check of itb pointers before dereferencing
289 *
290 * 7   3/14/08 7:06p katrep
291 * PR40514:Add support for avs
292 *
293 * 6   3/3/08 11:30a erickson
294 * PR39934: fix SW RAVE flush
295 *
296 * 5   2/27/08 9:19a erickson
297 * PR39934: fix non-sw rave platforms
298 *
299 * 4   2/26/08 1:15p erickson
300 * PR39934: don't reschedule a timer when it's already running
301 *
302 * 3   2/26/08 10:01a erickson
303 * PR39934: added SW RAVE support
304 *
305 * 2   2/20/08 4:59p erickson
306 * PR39786: add NEXUS_Rave_FindVideoStartCode_priv
307 *
308 * 1   1/18/08 2:20p jgarrett
309 * PR 38808: Merging to main branch
310 *
311 * Nexus_Devel/29   1/8/08 10:57a erickson
312 * PR36159: refactor some 3563 Display API's
313 *
314 * Nexus_Devel/28   12/28/07 5:19p erickson
315 * PR38470: move conversion functions to core
316 *
317 * Nexus_Devel/27   12/3/07 4:46p vsilyaev
318 * PR 36570: More generous safety thresholds for rave
319 *
320 * Nexus_Devel/26   11/9/07 5:04p erickson
321 * PR36774: fixing 7401
322 *
323 * Nexus_Devel/25   11/9/07 4:23p jgarrett
324 * PR 36774: Adding conditional compiles for certain platforms
325 *
326 * Nexus_Devel/24   11/9/07 4:05p jgarrett
327 * PR 36774: converting to Ac3+ Itb format for 7405
328 *
329 * Nexus_Devel/23   11/6/07 3:43p erickson
330 * PR34925: added BDBG_OBJECT checking
331 *
332 * Nexus_Devel/22   11/1/07 1:30p erickson
333 * PR36637: use latest transport calls
334 *
335 * Nexus_Devel/21   11/1/07 9:06a erickson
336 * PR36633: update base enums
337 *
338 * Nexus_Devel/20   10/31/07 9:07a erickson
339 * PR36570: added 3563 support
340 *
341 * Nexus_Devel/19   10/24/07 5:40p vsilyaev
342 * PR 36404: Added audio decode trick mode
343 *
344 * Nexus_Devel/18   10/19/07 11:21a vsilyaev
345 * PR 35824: Fixed data corruption on trick modes
346 *
347 * Nexus_Devel/17   10/4/07 12:54p erickson
348 * PR34925: use standard NEXUS_Error values
349 *
350 * Nexus_Devel/16   10/3/07 2:50p erickson
351 * PR34925: call BXPT_Rave_GetBufferInfo_isr
352 *
353 * Nexus_Devel/15   10/2/07 1:59p erickson
354 * PR34925: NEXUS_Rave_GetStatus_priv needs to call
355 * BXPT_Rave_GetContextRegisters
356 *
357 * Nexus_Devel/14   10/1/07 1:45p erickson
358 * PR34925: make Rave a private API
359 *
360 * Nexus_Devel/13   9/28/07 4:24p jgarrett
361 * PR 34594: Downgrading prints
362 *
363 * Nexus_Devel/12   9/27/07 7:52p jgarrett
364 * PR 34954: Adding debug
365 *
366 * Nexus_Devel/11   9/27/07 1:43p jgarrett
367 * PR 34954: Adding RAVE Audio config
368 *
369 * Nexus_Devel/10   9/25/07 4:33p erickson
370 * PR34925: fix NEXUS_Rave_Open logic
371 *
372 * Nexus_Devel/9   9/25/07 3:07p erickson
373 * PR34925: update
374 *
375 * Nexus_Devel/8   9/25/07 1:19p erickson
376 * PR34925: update
377 *
378 * Nexus_Devel/7   9/24/07 11:16a erickson
379 * PR34925: update
380 *
381 * Nexus_Devel/6   9/24/07 10:09a erickson
382 * PR34925: update
383 *
384 * Nexus_Devel/5   9/21/07 11:16a erickson
385 * PR34925: update
386 *
387 * Nexus_Devel/4   9/14/07 4:59p erickson
388 * PR34925: update
389 *
390 * Nexus_Devel/3   9/14/07 4:32p erickson
391 * PR34925: added BDBG_MODULE
392 *
393 * Nexus_Devel/2   9/14/07 3:27p erickson
394 * PR34925: initial compilation
395 *
396 * Nexus_Devel/1   9/14/07 12:29p erickson
397 * PR34925: update
398 *
399 **************************************************************************/
400#include "nexus_transport_module.h"
401#if NEXUS_SW_RAVE_PEEK_EXTENSION
402/* The NEXUS_SW_RAVE_PEEK_EXTENSION forces SW RAVE in ePointersOnly mode.
403This is only supported for codecs that don't require SW RAVE for ITB manipulation (e.g. MPEG, AVC).
404By not copying ITB, it requires minimal memory.
405It allows the extension to peek at the ITB before it goes to the decoder. */
406#include "nexus_sw_rave_extension.h"
407#endif
408
409BDBG_MODULE(nexus_rave);
410
411#if BCHP_CHIP == 3563 || BCHP_CHIP == 7401
412#else
413#define UNIFIED_ITB_SUPPORT 1
414#endif
415
416#define ITB_SIZE 16
417#define NEXUS_RAVE_CONTEXT_MAP(RAVE) (((RAVE)->swRave.raveHandle && (RAVE)->swRave.enabled) ? &(RAVE)->swRave.xptContextMap : &(RAVE)->xptContextMap)
418
419/* for SW rave, we need 100 msec. for numBytesOutput, 250 msec is enough (a 20Mbps stream and 1.5MB CDB will wrap every 800 msec) */
420#define NEXUS_RAVE_TIMER_PERIOD(RAVE) ((RAVE)->swRave.enabled?100:250)
421
422void NEXUS_Rave_GetDefaultOpenSettings_priv(NEXUS_RaveOpenSettings *pSettings)
423{
424    NEXUS_ASSERT_MODULE();
425    BKNI_Memset(pSettings, 0, sizeof(*pSettings));
426    /* RAVE only supports buffers aligned on 4-byte boundaries. This alignment is expressed as a power of 2. */
427    pSettings->config.Cdb.Alignment = 2;
428    pSettings->config.Itb.Alignment = 2;
429    return;
430}
431
432NEXUS_RaveHandle NEXUS_Rave_Open_priv(const NEXUS_RaveOpenSettings *pSettings)
433{
434    NEXUS_RaveHandle rave = NULL;
435    BERR_Code rc;
436    unsigned i;
437
438    NEXUS_ASSERT_MODULE();
439    for (i=0;i<NEXUS_NUM_RAVE_CONTEXTS;i++) {
440        /* rave[0] means we are hardcoded for only one RAVE "channel", but many "contexts" */
441        if (!pTransport->rave[0].context[i].raveHandle) {
442            rave = &pTransport->rave[0].context[i];
443            break;
444        }
445    }
446    if (!rave) {
447        BDBG_ERR(("No more RAVE contexts"));
448        (void)BERR_TRACE(NEXUS_NOT_SUPPORTED);
449        return NULL;
450    }
451
452    BDBG_OBJECT_SET(rave, NEXUS_Rave);
453#define INVALID_PID_CHANNEL 0xFFFF
454    rave->pidChannelIndex = INVALID_PID_CHANNEL;
455
456    rc = BXPT_Rave_AllocContext(pTransport->rave[0].channel,
457        pSettings->record?BXPT_RaveCx_eRecord:(pTransport->settings.secureHeap?BXPT_RaveCx_eAvR:BXPT_RaveCx_eAv),
458        (BAVC_CdbItbConfig *)&pSettings->config, &rave->raveHandle);
459    if (rc) {BERR_TRACE(rc); return NULL;}
460
461    BDBG_ASSERT(rave->raveHandle);
462    rc = BXPT_Rave_GetContextRegisters(rave->raveHandle, &rave->xptContextMap);
463    if (rc) {rc = BERR_TRACE(rc); goto error;}
464
465    /* because of XPT sw rave, we can't assume the HW index number. so, we derive it from the registers. */
466    rave->index = NEXUS_RAVE_INDEX(rave->xptContextMap.CDB_Read);
467    rave->swRave.index = -1;
468
469#if NEXUS_SW_RAVE_SUPPORT
470    if (pSettings->allocSoftRave) {
471        BXPT_RaveSoftMode mode = BXPT_RaveSoftMode_eCopyItb;
472
473#if NEXUS_SW_RAVE_PEEK_EXTENSION
474        mode = BXPT_RaveSoftMode_ePointersOnly;
475#endif
476        rc = BXPT_Rave_AllocSoftContext(rave->raveHandle, mode, &rave->swRave.raveHandle);
477        if (rc) {rc = BERR_TRACE(rc); goto error;}
478        rc = BXPT_Rave_GetContextRegisters(rave->swRave.raveHandle, &rave->swRave.xptContextMap);
479        if (rc) {rc = BERR_TRACE(rc); goto error;}
480        rave->swRave.index = NEXUS_RAVE_INDEX(rave->swRave.xptContextMap.CDB_Read);
481
482#if NEXUS_SW_RAVE_PEEK_EXTENSION
483        rc = NEXUS_P_SwRaveExtension_Init(rave);
484        if (rc) { BERR_TRACE(rc); goto error; }
485#endif
486    }
487#endif
488
489    return rave;
490
491error:
492    if (rave) {
493        NEXUS_Rave_Close_priv(rave);
494    }
495    return NULL;
496}
497
498void NEXUS_Rave_Close_priv(NEXUS_RaveHandle rave)
499{
500    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
501    NEXUS_ASSERT_MODULE();
502
503    NEXUS_Rave_Disable_priv(rave);
504    NEXUS_Rave_RemovePidChannel_priv(rave);
505
506#if NEXUS_SW_RAVE_SUPPORT
507    if (rave->swRave.raveHandle) {
508#if NEXUS_SW_RAVE_PEEK_EXTENSION
509        NEXUS_P_SwRaveExtension_Uninit(rave);
510#endif
511        BXPT_Rave_FreeContext(rave->swRave.raveHandle);
512        rave->swRave.raveHandle = NULL;
513    }
514#endif
515    if (rave->raveHandle) {
516        BXPT_Rave_FreeContext(rave->raveHandle);
517        rave->raveHandle = NULL;
518    }
519    BDBG_OBJECT_UNSET(rave, NEXUS_Rave);
520}
521
522void NEXUS_Rave_GetDefaultSettings_priv(NEXUS_RaveSettings *pSettings)
523{
524    NEXUS_ASSERT_MODULE();
525    BKNI_Memset(pSettings, 0, sizeof(*pSettings));
526}
527
528static void NEXUS_Rave_P_Timer(void *context)
529{
530    NEXUS_RaveHandle rave = context;
531
532    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
533    rave->timer = NULL;
534
535    if (rave->swRave.raveHandle && rave->swRave.enabled) {
536#if NEXUS_SW_RAVE_PEEK_EXTENSION
537        /* this extension allows for a custom SW RAVE algorithm */
538        NEXUS_P_SwRaveExtension_Advance(rave);
539#else
540        BXPT_Rave_AdvanceSoftContext(rave->swRave.raveHandle);
541#endif
542    }
543    if (rave->settings.numOutputBytesEnabled) {
544        BAVC_XptContextMap *pXptContextMap = NEXUS_RAVE_CONTEXT_MAP(rave);
545        uint32_t valid = BREG_Read32(g_pCoreHandles->reg, pXptContextMap->CDB_Valid);
546        if (valid < rave->lastValid && rave->lastValid) {
547            /* every time it wraps, we read WRAP-BASE. this is the total number of bytes in the CDB for the past wrap.
548            see GetStatus where we add VALID-BASE to improve the result */
549            unsigned n = BREG_Read32(g_pCoreHandles->reg, pXptContextMap->CDB_Wrap) - BREG_Read32(g_pCoreHandles->reg, pXptContextMap->CDB_Base);
550            rave->numOutputBytes += n;
551            BDBG_MSG(("rave read %lld", rave->numOutputBytes));
552        }
553        rave->lastValid = valid;
554    }
555
556    rave->timer = NEXUS_ScheduleTimer(NEXUS_RAVE_TIMER_PERIOD(rave), NEXUS_Rave_P_Timer, rave);
557    BDBG_ASSERT(rave->timer);
558}
559
560static void NEXUS_Rave_P_ConvertForES(NEXUS_TransportType originalTransportType, BAVC_StreamType streamType, BAVC_StreamType *raveStreamType )
561{
562
563    /* SW7405-5140: if audio is ES format. Nexus needs to tell XPT PI to
564    * disable DISABLE_BEFORE_PES filter.  If DISABLE_BEFORE_PES filter is enabled,
565    * the RAVE discard all ES data as RAVE looks for a valid PES startcode. */
566    *raveStreamType = streamType;
567    if ( originalTransportType == NEXUS_TransportType_eEs )
568    {
569        /* limit change to ES input only */
570        *raveStreamType = BAVC_StreamType_eEs;
571    }
572}
573
574NEXUS_Error NEXUS_Rave_ConfigureVideo_priv(NEXUS_RaveHandle rave,
575    NEXUS_VideoCodec codec, const NEXUS_RaveSettings *pSettings)
576{
577    BERR_Code rc;
578    BXPT_Rave_AvSettings AvCtxCfg;
579    BAVC_StreamType streamType;
580#if NEXUS_SW_RAVE_SUPPORT
581    bool swRave;
582    BXPT_RaveSoftMode sw_rave_mode = BXPT_RaveSoftMode_eCopyItb;
583#endif
584
585    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
586    NEXUS_ASSERT_MODULE();
587
588    rc = NEXUS_P_TransportType_ToMagnum(pSettings->pidChannel->status.transportType, &streamType);
589    if (rc) return BERR_TRACE(rc);
590
591    /* get default state into structure */
592    BXPT_Rave_GetAvConfig(rave->raveHandle, &AvCtxCfg);
593    NEXUS_Rave_P_ConvertForES( pSettings->pidChannel->status.originalTransportType, streamType, &AvCtxCfg.InputFormat );
594    AvCtxCfg.OutputFormat = BAVC_StreamType_eEs;
595
596    /* default all EsRange off, then allow codecs to turn on what's needed */
597    AvCtxCfg.EsRanges[0].Enable = false;
598    AvCtxCfg.EsRanges[1].Enable = false;
599    AvCtxCfg.EsRanges[2].Enable = false;
600    AvCtxCfg.EsRanges[3].Enable = false;
601
602#if NEXUS_SW_RAVE_SUPPORT
603    swRave = false;
604    if (NEXUS_GetEnv("force_sw_rave")) {
605        swRave = true;
606    }
607    switch(pSettings->pidChannel->status.originalTransportType) {
608    case NEXUS_TransportType_eAvi: /* DivX */
609    case NEXUS_TransportType_eAsf:
610    case NEXUS_TransportType_eMkv:
611        switch (codec) {
612        case NEXUS_VideoCodec_eMpeg4Part2:
613        case NEXUS_VideoCodec_eDivx311:
614        case NEXUS_VideoCodec_eVc1SimpleMain:
615            swRave = true;
616            break;
617        default:
618            break;
619        }
620        break;
621    default:
622        break;
623    }
624#if NEXUS_SW_RAVE_PEEK_EXTENSION
625    if (swRave) {
626        /* if swRave is required by the codec, then NEXUS_SW_RAVE_PEEK_EXTENSION does not work. */
627        return BERR_TRACE(NEXUS_NOT_SUPPORTED);
628    }
629    /* force SW RAVE on for peeking */
630    swRave = true;
631    sw_rave_mode = BXPT_RaveSoftMode_ePointersOnly;
632#endif
633#endif
634
635    switch (codec) {
636    case NEXUS_VideoCodec_eH263:
637        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eH263;
638        AvCtxCfg.EsRanges[0].RangeHi = 0xFE; /* everything */
639        AvCtxCfg.EsRanges[0].RangeLo = 0x00;
640        AvCtxCfg.EsRanges[0].RangeIsASlice = false;
641        AvCtxCfg.EsRanges[0].Enable = true;
642        AvCtxCfg.StreamIdHi = 0xEF;
643        AvCtxCfg.StreamIdLo = 0xBD;
644        break;
645    case NEXUS_VideoCodec_eH264_Svc:
646    case NEXUS_VideoCodec_eH264_Mvc:
647    case NEXUS_VideoCodec_eH264:
648        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eAvcVideo;
649        AvCtxCfg.StreamIdHi = 0xEF;
650        AvCtxCfg.StreamIdLo = 0xBD;
651        AvCtxCfg.EsRanges[0].RangeHi = 0xFE; /* everything */
652        AvCtxCfg.EsRanges[0].RangeLo = 0x00;
653        AvCtxCfg.EsRanges[0].RangeIsASlice = false;
654        AvCtxCfg.EsRanges[0].Enable = true;
655        break;
656    case NEXUS_VideoCodec_eVc1:
657        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eVc1Video;
658        AvCtxCfg.StreamIdHi = 0xEF;
659        AvCtxCfg.StreamIdLo = 0xBD;
660        AvCtxCfg.EsRanges[0].RangeHi = 0xFE; /* everything */
661        AvCtxCfg.EsRanges[0].RangeLo = 0x00;
662        AvCtxCfg.EsRanges[0].RangeIsASlice = false;
663        AvCtxCfg.EsRanges[0].Enable = true;
664        break;
665    case NEXUS_VideoCodec_eVc1SimpleMain:
666        /* this allows PES entries through, nothing else. */
667        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eVC1SimpleMain;
668        AvCtxCfg.StreamIdHi = 0xFD;
669        AvCtxCfg.StreamIdLo = 0xBD;
670#if NEXUS_SW_RAVE_SUPPORT
671        sw_rave_mode = BXPT_RaveSoftMode_eVc1SimpleMain;
672#endif
673        break;
674    case NEXUS_VideoCodec_eMpeg1:
675        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eMpeg1Video;
676        AvCtxCfg.StreamIdHi = 0xEF;
677        AvCtxCfg.StreamIdLo = 0xE0;
678        AvCtxCfg.EsRanges[0].RangeHi = 0xAF; /* MPEG slices */
679        AvCtxCfg.EsRanges[0].RangeLo = 0x01;
680        AvCtxCfg.EsRanges[0].RangeIsASlice = true;
681        AvCtxCfg.EsRanges[0].Enable = true;
682        AvCtxCfg.EsRanges[1].RangeHi = 0xBF; /* start of frame */
683        AvCtxCfg.EsRanges[1].RangeLo = 0xB0;
684        AvCtxCfg.EsRanges[1].RangeIsASlice = false;
685        AvCtxCfg.EsRanges[1].Enable = true;
686        AvCtxCfg.EsRanges[2].RangeHi = 0x0; /* start of picture */
687        AvCtxCfg.EsRanges[2].RangeLo = 0x0;
688        AvCtxCfg.EsRanges[2].RangeIsASlice = false;
689        AvCtxCfg.EsRanges[2].Enable = true;
690        break;
691    case NEXUS_VideoCodec_eMpeg2:
692        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eMpeg2Video;
693        AvCtxCfg.StreamIdHi = 0xEF;
694        AvCtxCfg.StreamIdLo = 0xE0;
695        AvCtxCfg.EsRanges[0].RangeHi = 0xAF; /* MPEG slices */
696        AvCtxCfg.EsRanges[0].RangeLo = 0x01;
697        AvCtxCfg.EsRanges[0].RangeIsASlice = true;
698        AvCtxCfg.EsRanges[0].Enable = true;
699        AvCtxCfg.EsRanges[1].RangeHi = 0xBF; /* start of frame */
700        AvCtxCfg.EsRanges[1].RangeLo = 0xB0;
701        AvCtxCfg.EsRanges[1].RangeIsASlice = false;
702        AvCtxCfg.EsRanges[1].Enable = true;
703        AvCtxCfg.EsRanges[2].RangeHi = 0x0; /* start of picture */
704        AvCtxCfg.EsRanges[2].RangeLo = 0x0;
705        AvCtxCfg.EsRanges[2].RangeIsASlice = false;
706        AvCtxCfg.EsRanges[2].Enable = true;
707        break;
708    case NEXUS_VideoCodec_eDivx311:
709#if NEXUS_SW_RAVE_SUPPORT
710        if (swRave) {
711            AvCtxCfg.ItbFormat = BAVC_ItbEsType_eMpeg4Part2;
712            AvCtxCfg.StreamIdHi = 0xEF;
713            AvCtxCfg.StreamIdLo = 0xE0;
714            sw_rave_mode = BXPT_RaveSoftMode_eDivX_311;
715            break;
716        }
717#endif
718        /* if not SW rave, then fall through as Mpeg4Part2 */
719
720    case NEXUS_VideoCodec_eMpeg4Part2:
721        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eMpeg4Part2;
722        AvCtxCfg.StreamIdHi = 0xEF;
723        AvCtxCfg.StreamIdLo = 0xE0;
724        AvCtxCfg.EsRanges[0].RangeHi = 0x2F;
725        AvCtxCfg.EsRanges[0].RangeLo = 0x00;
726        AvCtxCfg.EsRanges[0].RangeIsASlice = true;
727        AvCtxCfg.EsRanges[0].Enable = true;
728        AvCtxCfg.EsRanges[1].RangeHi = 0xB8;
729        AvCtxCfg.EsRanges[1].RangeLo = 0xB0;
730        AvCtxCfg.EsRanges[1].RangeIsASlice = false;
731        AvCtxCfg.EsRanges[1].Enable = true;
732#if NEXUS_SW_RAVE_SUPPORT
733        sw_rave_mode = BXPT_RaveSoftMode_eDivX;
734        if (pSettings->disableReordering) {
735            sw_rave_mode = BXPT_RaveSoftMode_eDivX_noReorder;
736        }
737#endif
738        break;
739    case NEXUS_VideoCodec_eAvs:
740        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eAvsVideo;
741        AvCtxCfg.StreamIdHi = 0xEF;
742        AvCtxCfg.StreamIdLo = 0xE0;
743        AvCtxCfg.EsRanges[0].RangeHi = 0xAF; /* AVS slices */
744        AvCtxCfg.EsRanges[0].RangeLo = 0x00;
745        AvCtxCfg.EsRanges[0].RangeIsASlice = true;
746        AvCtxCfg.EsRanges[0].Enable = true;
747        AvCtxCfg.EsRanges[1].RangeHi = 0xBF; /* start of frame and pictures */
748        AvCtxCfg.EsRanges[1].RangeLo = 0xB0;
749        AvCtxCfg.EsRanges[1].RangeIsASlice = false;
750        AvCtxCfg.EsRanges[1].Enable = true;
751        break;
752    case NEXUS_VideoCodec_eVp6:
753        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eVp6Video;
754        AvCtxCfg.StreamIdHi = 0xEF;
755        AvCtxCfg.StreamIdLo = 0xE0;
756        AvCtxCfg.EsRanges[0].RangeHi = 0xFE; /* everything */
757        AvCtxCfg.EsRanges[0].RangeLo = 0x00;
758        AvCtxCfg.EsRanges[0].RangeIsASlice = false;
759        AvCtxCfg.EsRanges[0].Enable = true;
760        AvCtxCfg.EsRanges[1] = AvCtxCfg.EsRanges[0];
761        AvCtxCfg.EsRanges[2] = AvCtxCfg.EsRanges[0];
762        AvCtxCfg.EsRanges[3] = AvCtxCfg.EsRanges[0];
763        break;
764    case NEXUS_VideoCodec_eRv40:
765    case NEXUS_VideoCodec_eVp8:
766    case NEXUS_VideoCodec_eSpark:
767        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eVC1SimpleMain;
768        AvCtxCfg.StreamIdHi = 0xEF;
769        AvCtxCfg.StreamIdLo = 0xE0;
770        break;
771    default:
772        return BERR_TRACE(NEXUS_INVALID_PARAMETER);
773    }
774
775#if !BXPT_HAS_PID_CHANNEL_PES_FILTERING
776    {
777        BXPT_Rave_ContextSettings CtxConfig;
778        NEXUS_PidChannelStatus pidChannelStatus;
779
780        rc = NEXUS_PidChannel_GetStatus(pSettings->pidChannel, &pidChannelStatus);
781        if (rc) {return BERR_TRACE(rc);}
782        BXPT_Rave_GetContextConfig(rave->raveHandle, &CtxConfig);
783
784        CtxConfig.FilterPidStreamId = 0;
785        CtxConfig.BandNum = 0;
786
787        if(pidChannelStatus.originalTransportType == NEXUS_TransportType_eVob){
788            CtxConfig.FilterPidStreamId = pidChannelStatus.remappedPid;
789            CtxConfig.BandNum = 16;
790
791            AvCtxCfg.VobMode = true;
792
793            /* For 7401 vob streams use all pass mode.
794               When PARSER_ALL_PASS_CTRL is enabled in XPT_PBn_PARSER_CTRL1, the pid channel will be mapped as follows,
795               pid_ch = b'000XYYYY
796               where X = playback or frontend. 1 for playback and 0 for frontend
797               YYYY = parser band number.
798               So in our case, we are using playback and parser band 0. Therefore the pid_ch=b'00010000=d'16.
799            */
800            pSettings->pidChannel->status.pidChannelIndex = 16;
801        }
802
803        BXPT_Rave_SetContextConfig(rave->raveHandle, &CtxConfig);
804    }
805#endif
806
807#if NEXUS_SW_RAVE_SUPPORT
808    /* coverity[dead_error_condition] */
809    if (swRave) {
810        if (!rave->swRave.raveHandle) {
811            BDBG_ERR(("This video codec requires that you set allocSoftRave for ITB transformation."));
812            return BERR_TRACE(NEXUS_UNKNOWN);
813        }
814        rc = BXPT_Rave_ResetSoftContext(rave->swRave.raveHandle, sw_rave_mode);
815        if (rc) return BERR_TRACE(rc);
816        rave->swRave.enabled = true;
817    }
818    else {
819        rave->swRave.enabled = false;
820    }
821#endif
822
823    AvCtxCfg.BandHoldEn = pSettings->bandHold;
824    AvCtxCfg.DisableContinuityCheck = !pSettings->continuityCountEnabled;
825    if (NEXUS_GetEnv("cont_count_ignore")) {
826        AvCtxCfg.DisableContinuityCheck = true;
827    }
828
829    BDBG_MSG(("RAVE_CX%d configured for video codec %d, pid channel %d", rave->index, codec, pSettings->pidChannel->status.pidChannelIndex));
830
831    rc = BXPT_Rave_AddPidChannel(rave->raveHandle, pSettings->pidChannel->status.pidChannelIndex, false);
832    if (rc) {return BERR_TRACE(rc);}
833
834    rave->pidChannelIndex = pSettings->pidChannel->status.pidChannelIndex; /* remember for the remove */
835
836    if(pSettings->otfPvr) {
837        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eOTFVideo;
838    }
839
840    rc = BXPT_Rave_SetAvConfig(rave->raveHandle, &AvCtxCfg);
841    if (rc) {return BERR_TRACE(rc);}
842
843    /* NOTE: do not flush rave here. if playback has already started, then we could lose a small
844    amount of data. rave should already be in a flushed state, either from initial conditions
845    or from a flush after stopping decode. */
846    rave->settings = *pSettings;
847    rave->lastValid = 0;
848
849    return BERR_SUCCESS;
850}
851
852NEXUS_Error NEXUS_Rave_ConfigureAudio_priv(
853    NEXUS_RaveHandle rave,
854    NEXUS_AudioCodec codec,
855    const NEXUS_RaveSettings *pSettings
856    )
857{
858    BERR_Code rc;
859    BXPT_Rave_AvSettings AvCtxCfg;
860    BAVC_StreamType streamType;
861    NEXUS_PidChannelStatus pidChannelStatus;
862
863    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
864    NEXUS_ASSERT_MODULE();
865
866    rc = NEXUS_P_TransportType_ToMagnum(pSettings->pidChannel->status.transportType, &streamType);
867    if (rc) return BERR_TRACE(rc);
868
869    /* There are 4 types of DSS A/V streams:
870    DSS SD video - this is DSS ES
871    DSS HD video - this is DSS PES
872    DSS MPEG audio - this actually uses MPEG1 system headers, but it's very similar to PES, therefore DSS PES
873    Therefore we convert DSS ES to DSS PES here.
874    DSS AC3 audio - uses MPEG2 System PES, therefore DSS PES
875    */
876    if (streamType == BAVC_StreamType_eDssEs)
877    {
878        streamType = BAVC_StreamType_eDssPes;
879    }
880
881    BXPT_Rave_GetAvConfig(rave->raveHandle, &AvCtxCfg);
882    NEXUS_Rave_P_ConvertForES( pSettings->pidChannel->status.originalTransportType, streamType, &AvCtxCfg.InputFormat );
883    AvCtxCfg.OutputFormat = BAVC_StreamType_eEs;
884
885#if BCHP_CHIP == 7400 || BCHP_CHIP == 7118 || BCHP_CHIP == 7401 || BCHP_CHIP == 7403
886    /* Old FW arch only supports AD on MPEG */
887    if ( pSettings->audioDescriptor && (codec != NEXUS_AudioCodec_eMpeg && codec != NEXUS_AudioCodec_eMp3) )
888    {
889        BDBG_ERR(("Audio descriptors are only supported with MPEG audio currently"));
890        return BERR_TRACE(BERR_NOT_SUPPORTED);
891    }
892#endif
893
894    /* TODO: bsettop_p_rap_set_rave_thresholds(rap, mpeg->audio[program].format, cfg->playback, rave->raveHandle, &AvCtxCfg); */
895    BKNI_Memset(AvCtxCfg.EsRanges, 0, sizeof(AvCtxCfg.EsRanges)); /* all disabled */
896    switch (codec) {
897    case NEXUS_AudioCodec_eMpeg:
898        if ( pSettings->audioDescriptor )
899        {
900            /* Currently there is no other way to specify this in RAVE */
901            AvCtxCfg.ItbFormat = BAVC_ItbEsType_eMpegAudioWithDescriptor;
902        }
903        else
904        {
905            AvCtxCfg.ItbFormat = BAVC_ItbEsType_eMpegAudio;
906        }
907        AvCtxCfg.StreamIdHi = 0xEF;
908        AvCtxCfg.StreamIdLo = 0xC0;
909        break;
910    case NEXUS_AudioCodec_eMp3:
911        if ( pSettings->audioDescriptor )
912        {
913            /* Currently there is no other way to specify this in RAVE */
914            AvCtxCfg.ItbFormat = BAVC_ItbEsType_eMpegAudioWithDescriptor;
915        }
916        else
917        {
918            AvCtxCfg.ItbFormat = BAVC_ItbEsType_eMpegAudioLayer3;
919        }
920        AvCtxCfg.StreamIdHi = 0xEF;
921        AvCtxCfg.StreamIdLo = 0xC0;
922        break;
923    case NEXUS_AudioCodec_eAacAdts:
924    case NEXUS_AudioCodec_eAacLoas:
925        if ( pSettings->audioDescriptor )
926        {
927            /* Currently there is no other way to specify this in RAVE */
928            AvCtxCfg.ItbFormat = BAVC_ItbEsType_eAudioDescriptor;
929        }
930        else
931        {
932        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eAacAudio;
933        }
934        AvCtxCfg.StreamIdHi = 0xEF;
935        AvCtxCfg.StreamIdLo = 0xC0;
936        break;
937    case NEXUS_AudioCodec_eAacPlusLoas:
938    case NEXUS_AudioCodec_eAacPlusAdts:
939        /* baudio_format_aac_plus_loas is also handled here as it has the same value as baudio_format_aac_plus */
940        if ( pSettings->audioDescriptor )
941        {
942            /* Currently there is no other way to specify this in RAVE */
943            AvCtxCfg.ItbFormat = BAVC_ItbEsType_eAudioDescriptor;
944        }
945        else
946        {
947        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eAacHe;
948        }
949        AvCtxCfg.StreamIdHi = 0xEF;
950        AvCtxCfg.StreamIdLo = 0xC0;
951        break;
952    case NEXUS_AudioCodec_eDra:
953        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eDra;
954        AvCtxCfg.StreamIdHi = 0xEF;
955        AvCtxCfg.StreamIdLo = 0xBD;
956        break;
957    case NEXUS_AudioCodec_ePcm: /* PCM audio in PES uses the same BCMA header/encapsulation */
958    case NEXUS_AudioCodec_ePcmWav:
959    case NEXUS_AudioCodec_eWmaStd:
960    case NEXUS_AudioCodec_eWmaStdTs:
961    case NEXUS_AudioCodec_eWmaPro:
962    case NEXUS_AudioCodec_eAmr:
963    case NEXUS_AudioCodec_eAdpcm:
964    case NEXUS_AudioCodec_eVorbis:
965        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eWma;
966        AvCtxCfg.StreamIdHi = 0xEF; /* PES stream id 0xCD is set by playpump ASF->PES packetizer.
967                                    but allow a greater range. */
968        AvCtxCfg.StreamIdLo = 0xC0;
969        break;
970    case NEXUS_AudioCodec_eCook:
971        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eAmr;
972        AvCtxCfg.StreamIdHi = 0xEF;
973        AvCtxCfg.StreamIdLo = 0xC0;
974        break;
975    case NEXUS_AudioCodec_eAc3:
976        if ( pSettings->audioDescriptor )
977        {
978            /* Currently there is no other way to specify this in RAVE */
979            AvCtxCfg.ItbFormat = BAVC_ItbEsType_eAudioDescriptor;
980        }
981        else
982        {
983#if BCHP_CHIP != 7401 && BCHP_CHIP != 7403
984        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eAc3Plus; /* Use AC3+ ITB type for AC3 */
985#else
986        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eAc3gAudio;
987#endif
988        }
989        AvCtxCfg.StreamIdHi = 0xEF;
990        AvCtxCfg.StreamIdLo = 0xBD;
991        break;
992    case NEXUS_AudioCodec_eAc3Plus:
993        if ( pSettings->audioDescriptor )
994        {
995            /* Currently there is no other way to specify this in RAVE */
996            AvCtxCfg.ItbFormat = BAVC_ItbEsType_eAudioDescriptor;
997        }
998        else
999        {
1000        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eAc3Plus;
1001        }
1002        AvCtxCfg.StreamIdHi = 0xEF;
1003        AvCtxCfg.StreamIdLo = 0xBD;
1004        break;
1005    case NEXUS_AudioCodec_eLpcmDvd:
1006    case NEXUS_AudioCodec_eLpcmHdDvd:
1007    case NEXUS_AudioCodec_eLpcmBluRay:
1008        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eLpcmAudio;
1009        AvCtxCfg.StreamIdHi = 0xEF; /* TBD */
1010        AvCtxCfg.StreamIdLo = 0xBD;
1011        break;
1012    case NEXUS_AudioCodec_eDts:
1013    case NEXUS_AudioCodec_eDtsHd:
1014    case NEXUS_AudioCodec_eDtsLegacy:
1015        AvCtxCfg.ItbFormat = BAVC_ItbEsType_eDtsAudio;
1016        AvCtxCfg.StreamIdHi = 0xEF; /* TBD */
1017        AvCtxCfg.StreamIdLo = 0xBD;
1018        break;
1019    default:
1020        return BERR_TRACE(BERR_NOT_SUPPORTED);
1021    }
1022
1023    rc = NEXUS_PidChannel_GetStatus(pSettings->pidChannel, &pidChannelStatus);
1024    if (rc) {return BERR_TRACE(rc);}
1025
1026#if BXPT_HAS_PID_CHANNEL_PES_FILTERING
1027    {
1028        BXPT_Rave_ContextSettings CtxConfig;
1029        BXPT_Rave_GetContextConfig(rave->raveHandle, &CtxConfig);
1030
1031        /* this is the default */
1032        CtxConfig.EnablePrivateHdrItbEntry = false;
1033        CtxConfig.AudFrameInfo = 0;
1034
1035        if ( pidChannelStatus.originalTransportType == NEXUS_TransportType_eVob )
1036        {
1037            switch ( AvCtxCfg.ItbFormat )
1038            {
1039            case BAVC_ItbEsType_eLpcmAudio:
1040                CtxConfig.EnablePrivateHdrItbEntry = true;
1041                CtxConfig.AudFrameInfo = 7;
1042                break;
1043            case BAVC_ItbEsType_eAc3gAudio:
1044            case BAVC_ItbEsType_eAc3Plus:
1045        case BAVC_ItbEsType_eDtsAudio:
1046                CtxConfig.EnablePrivateHdrItbEntry = false;
1047                CtxConfig.AudFrameInfo = 4;
1048                break;
1049            default:
1050                break;
1051            }
1052        }
1053        rc = BXPT_Rave_SetContextConfig(rave->raveHandle, &CtxConfig);
1054        if (rc) {return BERR_TRACE(rc);}
1055    }
1056#else
1057    {
1058        BXPT_Rave_ContextSettings CtxConfig;
1059        BXPT_Rave_GetContextConfig(rave->raveHandle, &CtxConfig);
1060
1061        switch (pidChannelStatus.originalTransportType)  {
1062        case NEXUS_TransportType_eVob:
1063            CtxConfig.FilterPidStreamId = pidChannelStatus.remappedPid;
1064            switch (AvCtxCfg.ItbFormat){
1065            case BAVC_ItbEsType_eLpcmAudio:
1066                CtxConfig.SsidEn = true;
1067                CtxConfig.AudFrameInfo = 7;
1068                break;
1069            case BAVC_ItbEsType_eAc3gAudio:
1070                CtxConfig.SsidEn = true;
1071                CtxConfig.AudFrameInfo = 4;
1072                break;
1073            case BAVC_ItbEsType_eMpegAudio:
1074            case BAVC_ItbEsType_eMpegAudioLayer3:
1075                CtxConfig.SsidEn = false;
1076                CtxConfig.AudFrameInfo = 0;
1077                break;
1078            default:
1079                break;
1080        }
1081
1082        CtxConfig.BandNum = 16;
1083        CtxConfig.GenericPsEnable = false;
1084        CtxConfig.GenericPsSsid = 0;
1085
1086        AvCtxCfg.VobMode=true;
1087        break;
1088
1089    case NEXUS_TransportType_eMpeg2Pes:
1090
1091        switch (AvCtxCfg.ItbFormat){
1092        case BAVC_ItbEsType_eAc3gAudio:
1093            CtxConfig.GenericPsEnable = true;
1094            CtxConfig.GenericPsSsid = pidChannelStatus.remappedPid;
1095            CtxConfig.AudFrameInfo = 4;
1096            break;
1097        default:
1098            CtxConfig.GenericPsEnable = false;
1099            break;
1100        }
1101
1102        CtxConfig.SsidEn = false;
1103        CtxConfig.FilterPidStreamId = 0;
1104        CtxConfig.BandNum = 0;
1105
1106        AvCtxCfg.VobMode=false;
1107        break;
1108
1109    default:
1110        CtxConfig.GenericPsEnable = false;
1111        CtxConfig.SsidEn = false;
1112        CtxConfig.AudFrameInfo = 0;
1113        CtxConfig.FilterPidStreamId = 0;
1114        CtxConfig.BandNum = 0;
1115
1116        AvCtxCfg.VobMode=false;
1117        break;
1118    }
1119
1120    BXPT_Rave_SetContextConfig(rave->raveHandle, &CtxConfig);
1121    }
1122#endif
1123
1124    AvCtxCfg.BandHoldEn = pSettings->bandHold;
1125    AvCtxCfg.DisableContinuityCheck = !pSettings->continuityCountEnabled;
1126    if (NEXUS_GetEnv("cont_count_ignore")) {
1127        AvCtxCfg.DisableContinuityCheck = true;
1128    }
1129
1130#if !BXPT_HAS_PID_CHANNEL_PES_FILTERING
1131    /* For 7401 vob streams use all pass mode.
1132       When PARSER_ALL_PASS_CTRL is enabled in XPT_PBn_PARSER_CTRL1, the pid channel will be mapped as follows,
1133       pid_ch = b'000XYYYY
1134       where X = playback or frontend. 1 for playback and 0 for frontend
1135       YYYY = parser band number.
1136       So in our case, we are using playback and parser band 0. Therefore the pid_ch=b'00010000=d'16.
1137    */
1138    if( pidChannelStatus.originalTransportType == NEXUS_TransportType_eVob){
1139        pSettings->pidChannel->status.pidChannelIndex = 16;
1140    }
1141
1142#endif
1143
1144    BDBG_MSG(("RAVE_CX%d configured for audio codec %d, pid channel %d", rave->index, codec, pSettings->pidChannel->status.pidChannelIndex));
1145
1146    rc = BXPT_Rave_AddPidChannel(rave->raveHandle, pSettings->pidChannel->status.pidChannelIndex, pTransport->settings.secureHeap != NULL);
1147    if (rc) {return BERR_TRACE(rc);}
1148
1149    rave->pidChannelIndex = pSettings->pidChannel->status.pidChannelIndex; /* remember for the remove */
1150
1151    rc = BXPT_Rave_SetAvConfig(rave->raveHandle, &AvCtxCfg);
1152    if (rc) {return BERR_TRACE(rc);}
1153
1154    /* NOTE: do not flush rave here. if playback has already started, then we could lose a small
1155    amount of data. rave should already be in a flushed state, either from initial conditions
1156    or from a flush after stopping decode. */
1157    rave->settings = *pSettings;
1158    rave->lastValid = 0;
1159
1160    return NEXUS_SUCCESS;
1161}
1162
1163NEXUS_Error NEXUS_Rave_ConfigureAll_priv(NEXUS_RaveHandle rave, const NEXUS_RaveSettings *pSettings)
1164{
1165    BERR_Code rc;
1166    BXPT_Rave_AvSettings AvCtxCfg;
1167    BAVC_StreamType streamType;
1168
1169    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
1170    NEXUS_ASSERT_MODULE();
1171
1172    rc = NEXUS_P_TransportType_ToMagnum(pSettings->pidChannel->status.transportType, &streamType);
1173    if (rc) return BERR_TRACE(rc);
1174
1175    /* get default state into structure */
1176    BXPT_Rave_GetAvConfig(rave->raveHandle, &AvCtxCfg);
1177    NEXUS_Rave_P_ConvertForES( pSettings->pidChannel->status.originalTransportType, streamType, &AvCtxCfg.InputFormat );
1178    AvCtxCfg.OutputFormat = BAVC_StreamType_eEs;
1179
1180    /* default all EsRange off, then allow codecs to turn on what's needed */
1181    AvCtxCfg.EsRanges[0].Enable = false;
1182    AvCtxCfg.EsRanges[1].Enable = false;
1183    AvCtxCfg.EsRanges[2].Enable = false;
1184    AvCtxCfg.EsRanges[3].Enable = false;
1185    AvCtxCfg.StreamIdHi = 0xEF;
1186    AvCtxCfg.StreamIdLo = 0xBD; /* TODO: 0x00..0xFF? */
1187    AvCtxCfg.BandHoldEn = pSettings->bandHold;
1188    AvCtxCfg.DisableContinuityCheck = !pSettings->continuityCountEnabled;
1189    if (NEXUS_GetEnv("cont_count_ignore")) {
1190        AvCtxCfg.DisableContinuityCheck = true;
1191    }
1192
1193    BDBG_MSG(("RAVE_CX%d configured for data, pid channel %d", rave->index, pSettings->pidChannel->status.pidChannelIndex));
1194
1195    rc = BXPT_Rave_AddPidChannel(rave->raveHandle, pSettings->pidChannel->status.pidChannelIndex, false);
1196    if (rc) {return BERR_TRACE(rc);}
1197
1198    rave->pidChannelIndex = pSettings->pidChannel->status.pidChannelIndex; /* remember for the remove */
1199
1200    rc = BXPT_Rave_SetAvConfig(rave->raveHandle, &AvCtxCfg);
1201    if (rc) {return BERR_TRACE(rc);}
1202    rave->settings = *pSettings;
1203    rave->lastValid = 0;
1204
1205    return BERR_SUCCESS;
1206}
1207
1208void NEXUS_Rave_RemovePidChannel_priv(NEXUS_RaveHandle rave)
1209{
1210    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
1211    NEXUS_ASSERT_MODULE();
1212
1213    if (rave->pidChannelIndex != INVALID_PID_CHANNEL) {
1214        BERR_Code rc;
1215        rc = BXPT_Rave_RemovePidChannel(rave->raveHandle, rave->pidChannelIndex);
1216        if(rc!=BERR_SUCCESS) { rc = BERR_TRACE(rc);}
1217        rave->pidChannelIndex = INVALID_PID_CHANNEL;
1218    }
1219    return;
1220}
1221
1222void NEXUS_Rave_Enable_priv(NEXUS_RaveHandle rave)
1223{
1224    BERR_Code rc;
1225
1226    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
1227    NEXUS_ASSERT_MODULE();
1228
1229    if (rave->swRave.enabled || rave->settings.numOutputBytesEnabled) {
1230        if (!rave->timer) {
1231            rave->timer = NEXUS_ScheduleTimer(NEXUS_RAVE_TIMER_PERIOD(rave), NEXUS_Rave_P_Timer, rave);
1232            BDBG_ASSERT(rave->timer);
1233        }
1234    }
1235
1236    rc = BXPT_Rave_EnableContext(rave->raveHandle);
1237    if(rc!=BERR_SUCCESS) { rc = BERR_TRACE(rc);}
1238    rave->enabled = true;
1239}
1240
1241void NEXUS_Rave_Disable_priv(NEXUS_RaveHandle rave)
1242{
1243    BERR_Code rc;
1244
1245    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
1246    NEXUS_ASSERT_MODULE();
1247
1248    if (rave->timer) {
1249        NEXUS_CancelTimer(rave->timer);
1250        rave->timer = NULL;
1251    }
1252
1253    rc=BXPT_Rave_DisableContext(rave->raveHandle);
1254    if(rc!=BERR_SUCCESS) { rc = BERR_TRACE(rc);}
1255    rave->enabled = false;
1256    return;
1257}
1258
1259void NEXUS_Rave_Flush_priv(NEXUS_RaveHandle rave)
1260{
1261    BERR_Code rc;
1262
1263    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
1264    NEXUS_ASSERT_MODULE();
1265
1266    rave->lastValid = 0;
1267    rc = BXPT_Rave_FlushContext(rave->raveHandle);
1268    if(rc!=BERR_SUCCESS) { rc = BERR_TRACE(rc);}
1269
1270#if NEXUS_SW_RAVE_SUPPORT
1271    if (rave->swRave.raveHandle) {
1272        rc = BXPT_Rave_FlushContext(rave->swRave.raveHandle);
1273        if(rc!=BERR_SUCCESS) { rc = BERR_TRACE(rc);}
1274    }
1275#endif
1276}
1277
1278NEXUS_Error NEXUS_Rave_GetStatus_priv(NEXUS_RaveHandle rave, NEXUS_RaveStatus *pStatus)
1279{
1280    BAVC_XptContextMap *pXptContextMap;
1281
1282    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
1283    NEXUS_ASSERT_MODULE();
1284
1285    BKNI_Memset(pStatus, 0, sizeof(*pStatus));
1286    pStatus->index = rave->index;
1287    pStatus->swRaveIndex = rave->swRave.index;
1288#if NEXUS_SW_RAVE_SUPPORT
1289    if (rave->swRave.raveHandle && rave->swRave.enabled) {
1290        pStatus->xptContextMap = rave->swRave.xptContextMap;
1291    }
1292    else
1293#endif
1294    {
1295        pStatus->xptContextMap = rave->xptContextMap;
1296    }
1297
1298    pStatus->numOutputBytes = rave->numOutputBytes;
1299    /* augment with VALID-BASE. this is useful for low bitrate streams that are just starting decode. */
1300    pXptContextMap = NEXUS_RAVE_CONTEXT_MAP(rave);
1301    pStatus->numOutputBytes += BREG_Read32(g_pCoreHandles->reg, pXptContextMap->CDB_Valid) - BREG_Read32(g_pCoreHandles->reg, pXptContextMap->CDB_Base);
1302    pStatus->enabled = rave->enabled;
1303
1304    return NEXUS_SUCCESS;
1305}
1306
1307void NEXUS_Rave_GetCdbBufferInfo_isr(NEXUS_RaveHandle rave, unsigned *depth, unsigned *size)
1308{
1309    BERR_Code rc;
1310    BXPT_Rave_BufferInfo buffer_info;
1311
1312    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
1313    BKNI_ASSERT_ISR_CONTEXT();
1314
1315    rc = BXPT_Rave_GetBufferInfo_isr(rave->raveHandle, &buffer_info);
1316    if(rc==BERR_SUCCESS) {
1317        *depth = buffer_info.CdbDepth;
1318        *size = buffer_info.CdbSize;
1319    } else {
1320        rc = BERR_TRACE(rc);
1321        *depth=0;
1322        *size=0;
1323    }
1324    return;
1325}
1326
1327#ifdef UNIFIED_ITB_SUPPORT
1328#define ITB_START_CODE 0x00
1329#else
1330#define ITB_START_CODE 0x04
1331#endif
1332
1333bool NEXUS_Rave_FindVideoStartCode_priv(NEXUS_RaveHandle rave, uint8_t startCode)
1334{
1335    uint8_t *ItbByte,i;
1336    BXPT_Rave_ContextPtrs CtxPtrs;
1337    BERR_Code rc;
1338
1339    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
1340    NEXUS_ASSERT_MODULE();
1341
1342#if NEXUS_SW_RAVE_SUPPORT
1343    if (rave->swRave.raveHandle && rave->swRave.enabled) {
1344        rc = BXPT_Rave_CheckBuffer(rave->swRave.raveHandle, &CtxPtrs );
1345        if (rc) {rc = BERR_TRACE(rc); return false;}
1346    }
1347    else
1348#endif
1349    {
1350    rc = BXPT_Rave_CheckBuffer(rave->raveHandle, &CtxPtrs );
1351    if (rc) {rc = BERR_TRACE(rc); return false;}
1352    }
1353
1354    /* check for an empty or reset buffer. super large ByteCount can happen because of reset */
1355    if ( !CtxPtrs.Itb.DataPtr || CtxPtrs.Itb.ByteCount < ITB_SIZE || CtxPtrs.Itb.ByteCount > 0x1000000) {
1356        return false;
1357    }
1358
1359    /*
1360    ** If the entire pic is in the CDB, there will be a startcode at the end of the ITB.
1361    ** Each ITB entry is ITB_SIZE bytes, so back up to the start of the last entry.
1362    */
1363    ItbByte = CtxPtrs.Itb.DataPtr + ( CtxPtrs.Itb.ByteCount - ITB_SIZE );
1364
1365#if BSTD_CPU_ENDIAN==BSTD_ENDIAN_LITTLE
1366    /* detect valid video start code entry */
1367    if(ItbByte[3] != ITB_START_CODE) {
1368        return false;
1369    }
1370    for(i=0;i<ITB_SIZE;i++)
1371    {
1372        /* ignore offset byte */
1373        if(i%2) {
1374            if(ItbByte[i]==startCode)
1375                return true;
1376        }
1377    }
1378#else
1379    if(ItbByte[0] != ITB_START_CODE)
1380        return false;
1381    for(i=0;i<ITB_SIZE;i++)
1382    {
1383        /* ignore offset byte */
1384        if(i%2)
1385            continue;
1386        if(ItbByte[i]==startCode)
1387            return true;
1388    }
1389#endif
1390    return false;
1391}
1392
1393void NEXUS_Rave_GetAudioFrameCount_priv(
1394    NEXUS_RaveHandle rave,
1395    unsigned *pFrameCount
1396    )
1397{
1398    BXPT_Rave_ContextPtrs ptrs;
1399    BERR_Code rc;
1400
1401    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
1402    NEXUS_ASSERT_MODULE();
1403    BDBG_ASSERT(NULL != pFrameCount);
1404
1405    *pFrameCount = 0;
1406    rc = BXPT_Rave_CheckBuffer(rave->raveHandle, &ptrs);
1407    if (rc == BERR_SUCCESS) {
1408        *pFrameCount = (ptrs.Itb.ByteCount+ptrs.Itb.WrapByteCount) / ITB_SIZE;
1409    }
1410}
1411
1412NEXUS_Error NEXUS_Rave_SetCdbThreshold_priv(
1413    NEXUS_RaveHandle rave,
1414    unsigned cdbDepth       /* CDB threshold in bytes (0 is default) */
1415    )
1416{
1417    BERR_Code errCode;
1418    BXPT_Rave_ContextThresholds thresholds;
1419
1420    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
1421    NEXUS_ASSERT_MODULE();
1422
1423    errCode = BXPT_Rave_GetDefaultThresholds(rave->raveHandle, &thresholds);
1424    if ( errCode )
1425    {
1426        return BERR_TRACE(errCode);
1427    }
1428
1429    if ( cdbDepth > 0 )
1430    {
1431        size_t cdbUpper = (cdbDepth + 255)/256; /* Specified in units of 256 bytes */
1432        /* Only permit values less than default */
1433        if ( cdbUpper < thresholds.CdbUpper )
1434        {
1435            thresholds.CdbUpper = cdbUpper;
1436        }
1437    }
1438
1439    errCode = BXPT_Rave_SetThresholds(rave->raveHandle, &thresholds);
1440    if ( errCode )
1441    {
1442        return BERR_TRACE(errCode);
1443    }
1444
1445    return BERR_SUCCESS;
1446}
1447
1448void NEXUS_Rave_GetCdbPointers_isr( NEXUS_RaveHandle rave, uint32_t *validPointer, uint32_t *readPointer)
1449{
1450    BAVC_XptContextMap *pXptContextMap;
1451
1452    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
1453    BKNI_ASSERT_ISR_CONTEXT();
1454
1455    pXptContextMap = NEXUS_RAVE_CONTEXT_MAP(rave);
1456    *validPointer = BREG_Read32(g_pCoreHandles->reg, pXptContextMap->CDB_Valid);
1457    *readPointer = BREG_Read32(g_pCoreHandles->reg, pXptContextMap->CDB_Read);
1458}
1459
1460NEXUS_Error NEXUS_Rave_GetMostRecentPts_priv( NEXUS_RaveHandle rave, uint32_t *pPts )
1461{
1462    BAVC_XptContextMap *pXptContextMap;
1463    uint32_t valid_offset, read_offset, base_offset, end_offset;
1464    uint32_t *valid, *read, *base, *end, *itb_mem;
1465    void *temp;
1466    NEXUS_Error rc;
1467    unsigned itr = 0; /* debug stats */
1468
1469    BDBG_OBJECT_ASSERT(rave, NEXUS_Rave);
1470    NEXUS_ASSERT_MODULE();
1471
1472    pXptContextMap = NEXUS_RAVE_CONTEXT_MAP(rave);
1473    valid_offset = BREG_Read32(g_pCoreHandles->reg, pXptContextMap->ITB_Valid);
1474    valid_offset -= valid_offset % ITB_SIZE; /* VALID points to last byte in ITB entry, move to first byte for easy algo */
1475    read_offset = BREG_Read32(g_pCoreHandles->reg, pXptContextMap->ITB_Read);
1476    base_offset = BREG_Read32(g_pCoreHandles->reg, pXptContextMap->ITB_Base);
1477    end_offset = BREG_Read32(g_pCoreHandles->reg, pXptContextMap->ITB_End);
1478    end_offset -= end_offset % ITB_SIZE; /* END points to last byte in ITB entry, move to first byte for easy algo */
1479
1480    /* validate that we're in range */
1481    if (!base_offset || !end_offset || valid_offset < base_offset || read_offset < base_offset) {
1482        return NEXUS_UNKNOWN;
1483    }
1484
1485    rc = BMEM_ConvertOffsetToAddress( g_pCoreHandles->heap[0], valid_offset, &temp);
1486    if (rc) return rc;
1487    valid = (uint32_t *)temp;
1488    rc = BMEM_ConvertOffsetToAddress( g_pCoreHandles->heap[0], read_offset, &temp);
1489    if (rc) return rc;
1490    read = (uint32_t *)temp;
1491    rc = BMEM_ConvertOffsetToAddress( g_pCoreHandles->heap[0], base_offset, &temp);
1492    if (rc) return rc;
1493    base = (uint32_t *)temp;
1494    rc = BMEM_ConvertOffsetToAddress( g_pCoreHandles->heap[0], end_offset, &temp);
1495    if (rc) return rc;
1496    end = (uint32_t *)temp;
1497
1498    itb_mem = valid;
1499    do {
1500        int itb_type = (itb_mem[0]>>24) & 0xFF;
1501        /* 0x21 for unified ITB, 0x2 for legacy ITB */
1502        if (itb_type == 2 || itb_type == 0x21) {
1503            /* PTS found */
1504            *pPts = itb_mem[1];
1505            BDBG_MSG(("MostRecentPts pts %#x, %d itrs", *pPts, itr));
1506            return 0;
1507        }
1508        if (itb_mem == read) { /* if valid == read, we have just processed the last element. */
1509            break;
1510        }
1511
1512        itb_mem -= ITB_SIZE/sizeof(itb_mem[0]); /* walk backwards */
1513        itr++;
1514
1515        if (itb_mem < base) {
1516            itb_mem = end; /* end points to the last valid */
1517        }
1518    } while (itb_mem != valid); /* this should not occur if read pointer is in range */
1519
1520    BDBG_MSG(("No MostRecentPts found, %d itrs", itr));
1521    return NEXUS_UNKNOWN;
1522}
1523
Note: See TracBrowser for help on using the repository browser.