📄 bluraycps.c
字号:
/* * * Copyright (c) Sigma Designs, Inc. 2006. All rights reserved. * */#include "cps_context.h"//FIXME: Static CPS context - can only init_cps once.// Is this a BUG or a FEATURE ?static struct cps_context_s g_cps_context = {0,};#if 0#define LOCALDBG ENABLE#else#define LOCALDBG DISABLE#endif/* Helpers *//* Check callback structure is valid */static RMstatus check_callbacks(struct cps_callbacks_s *callbacks){ if (callbacks==NULL) { RMDBGLOG((ENABLE, "Callbacks Undefined\n")); return RM_ERROR; } #define CHECK_CALLBACK(fn) \ if(callbacks->fn==NULL) { \ RMDBGLOG((ENABLE, "Undefined callback %s required\n", #fn)); \ return RM_ERROR; \ } \ CHECK_CALLBACK(packetcommand_callback); CHECK_CALLBACK(file_read_callback); CHECK_CALLBACK(file_size_callback); CHECK_CALLBACK(file_lba_callback); CHECK_CALLBACK(nvs_read_callback); CHECK_CALLBACK(nvs_write_callback); CHECK_CALLBACK(bdp_app_layer_callback); CHECK_CALLBACK(bdp_getportinfo_callback); CHECK_CALLBACK(bdp_discoveryram_callback); CHECK_CALLBACK(bdp_runnative_callback); CHECK_CALLBACK(bdp_lock_q_callback); CHECK_CALLBACK(bdp_unlock_q_callback); CHECK_CALLBACK(bdp_lock_vm_callback); CHECK_CALLBACK(bdp_unlock_q_callback);#undef CHECK_CALLBACK return RM_OK;}/* VM helpers */#define take(cps) RMDBGLOG((DISABLE,"TAKING vm semaphore!\n"));cps->callbacks->bdp_lock_vm_callback(cps_context->callback_context);RMDBGLOG((DISABLE,"Semaphore locked!\n"));#define release(cps) RMDBGLOG((DISABLE,"Releasing vm semahpore!\n"));cps->callbacks->bdp_unlock_vm_callback(cps_context->callback_context);RMDBGLOG((DISABLE,"Semaphore released!\n"));#define PRINT_PROGRESS() ; static RMstatus do_svm_interrupt(struct cps_context_s *cps_context, union SVMINTRP *pIntrp){ RMstatus rc; RMuint32 id=pIntrp->base.InterruptID; rc=SVM_QueueInterrupt(cps_context->svm, pIntrp); if (rc!=RM_OK) return rc; take(cps_context); rc=RM_OK; while(pIntrp->base.InterruptID==id && rc!=RM_ERROR && rc!=RM_INVALIDMODE && rc!=RM_FATAL) { PRINT_PROGRESS(); RMint32 instrCountdown = 1000; rc=SVM_VMRun(cps_context->svm, &instrCountdown); } release(cps_context); /* Check interrupt return value, treat all AppLayer returns as OK */ if ((pIntrp->base.ReturnVal != INTERRUPT_RETURN_OK) && (pIntrp->base.InterruptID != INTRP_ApplicationLayer)) { RMDBGLOG((ENABLE,"Interrupt Failed! (0x%08lx)\n",pIntrp->base.ReturnVal)); if ((pIntrp->base.InterruptID == INTRP_InitializeMedia) && (RMFAILED(rc))) { RMDBGLOG((ENABLE,"INTRP_InitializeMedia failed the initial BOOT process.\n")); return RM_FATAL; } if (pIntrp->base.ReturnVal == INTERRUPT_RETURN_FATAL) { /* The interrupt failed with FATAL, the player must stop! */ RMDBGLOG((ENABLE,"The player must stop BDSVM and AV output!!!!\n")); return RM_FATAL; } else { // treat all non-fatal errors as success. return RM_OK; } } /* DEBUG: */ if (RMFAILED(rc)) { RMDBGLOG((ENABLE,"Interrupt failed with \"%s\"(%d)", (rc==RM_INVALIDMODE)?"Invalid mode!\0": (rc==RM_TIMEOUT)?"Timeout!\0":"Generic Error!\0",rc)); } return rc;}static RMstatus do_svm_background(struct cps_context_s *cps_context, RMint32* cycles){ RMstatus rc; take(cps_context); rc=SVM_VMRun(cps_context->svm, cycles); release(cps_context); return rc;}/* CPS API */#define CPS_MEM_AACS_OFFSET (0)#define CPS_MEM_AACS_SIZE (3*1024*1024)#define CPS_MEM_SPDC_OFFSET (CPS_MEM_AACS_OFFSET + CPS_MEM_AACS_SIZE)#define CPS_MEM_SPDC_SIZE (SVM_MEMORY_SIZE)#define CPS_MEM_SIZE (CPS_MEM_SPDC_SIZE + CPS_MEM_AACS_SIZE)RMuint32 cps_get_memsize(void){ return CPS_MEM_SIZE;}RMstatus init_cps_preloaded(struct cps_context_s **cps_context, RMuint32 chip, RMuint32 cps_buffer_physaddr, RMuint32 cps_buffer_virtaddr, struct cps_callbacks_s *callbacks, void *callback_context, RMuint32 bdplus_xtask_id, RMuint32 aacs_xtask_id, struct demux_cipher *dmx_cphr){ g_cps_context.bdplus_xtask_slot_id = bdplus_xtask_id; g_cps_context.aacs_xtask_slot_id = aacs_xtask_id; g_cps_context.dmx_cphr = dmx_cphr; g_cps_context.preloaded = TRUE; /* CALL Init CPS with globals set */ return init_cps(cps_context, chip, cps_buffer_physaddr, cps_buffer_virtaddr, callbacks, callback_context);}RMstatus init_cps(struct cps_context_s **cps_context, RMuint32 chip, RMuint32 cps_buffer_physaddr, RMuint32 cps_buffer_virtaddr, struct cps_callbacks_s *callbacks, void *callback_context){ struct cps_context_s *cps; RMstatus rc; /* Already opened ? */ if (g_cps_context.callbacks) { RMDBGLOG((ENABLE,"Error: CPS Callbacks already set, " "CPS module has already been initialized!\n")); return RM_ERROR; } cps=&g_cps_context; /* Check callbacks */ rc=check_callbacks(callbacks); if (rc!=RM_OK) return rc; if (cps_context==NULL) return RM_ERROR; /* return the allocated context */ cps->callbacks = callbacks; cps->callback_context = callback_context; *cps_context = cps; cps->aacs_passthrough = FALSE; /* Enable extended BD+ check by default */ (void)cps_enable_extended_bdplus(cps,TRUE); /*--- Open aacs module : ---*/ if (cps->preloaded) { cps->aacs = aacs_open_preloaded(cps_buffer_physaddr + CPS_MEM_AACS_OFFSET, cps_buffer_virtaddr + CPS_MEM_AACS_OFFSET, CPS_MEM_AACS_SIZE, chip, cps->aacs_xtask_slot_id, cps->dmx_cphr); } else { cps->aacs = aacs_open(cps_buffer_physaddr + CPS_MEM_AACS_OFFSET, cps_buffer_virtaddr + CPS_MEM_AACS_OFFSET, CPS_MEM_AACS_SIZE, chip); } if (cps->aacs==NULL) { RMDBGLOG((ENABLE, "Failed to open aacs module\n")); rc = RM_ERROR; goto safe_exit; } #ifdef DISABLE_BDPLUS // FOR non BD+ licensees this must be enabled to allow use of BDROM // commercial titles. RMDBGLOG((ENABLE,"XXXX BYPASSING BD+ XXXX\n")); cps->bdplus_disabled = TRUE;#else /*--- Open BD+ SVM module : ---*/ cps->bdplus_disabled = FALSE; if (cps->preloaded) { rc=SVM_Init_Preloaded(&cps->svm, &g_spdc_callbacks, cps, (RMuint8*)(cps_buffer_virtaddr + CPS_MEM_SPDC_OFFSET), (RMuint32)cps_buffer_physaddr + CPS_MEM_SPDC_OFFSET, CPS_MEM_SPDC_SIZE, BDPLUS_FLASH_PAGE, cps->bdplus_xtask_slot_id); } else { rc=SVM_Init(&cps->svm, &g_spdc_callbacks, cps, (RMuint8*)(cps_buffer_virtaddr + CPS_MEM_SPDC_OFFSET), (RMuint32)cps_buffer_physaddr + CPS_MEM_SPDC_OFFSET, CPS_MEM_SPDC_SIZE, BDPLUS_FLASH_PAGE); } if (rc != RM_OK) { if (rc == RM_NOT_FOUND) { /* BD+ not found on disc */ RMDBGLOG((ENABLE,"Failed to find BD+ on disc. BD+ has been disabled!\n")); cps->bdplus_disabled = TRUE; } else { RMDBGLOG((ENABLE,"Failed to initialize BD+ with error %d\n",rc)); goto safe_exit; } }#endif rc = RM_OK;safe_exit: if (rc != RM_OK) { term_cps(cps); return rc; } /* Report back that aacs/ or bd+ is disabled */ if (cps->bdplus_disabled) { rc |= CPS_BDPLUS_DISABLED; } return rc;}RMstatus cps_media_initialize(struct cps_context_s *cps_context, RMuint32 flags){ RMuint32 aacs_flags = 0; RMuint32 aacs_fs_type = flags & CPS_FLAGS_AACS_FS_TYPE_MASK; RMuint32 media_type = flags & CPS_FLAGS_MEDIA_TYPE_MASK; cps_context->media_info_bits_0=0; switch(media_type) { case CPS_FLAGS_MEDIA_TYPE_BD_ROM: if( aacs_fs_type == CPS_FLAGS_AACS_FS_TYPE_BDROM ) aacs_flags = AACS_BD_ROM; else aacs_flags = AACS_BD_ROM | AACS_PASSTHROUGH; cps_context->media_info_bits_0 |= SPDC_MEDIAINFOBITS0_BD_ROM; break; case CPS_FLAGS_MEDIA_TYPE_BD_RE: RMDBGLOG((ENABLE,"Media type BD-RE\n")); if (aacs_fs_type == CPS_FLAGS_AACS_FS_TYPE_BD_RE_20) aacs_flags = AACS_BD_RE | AACS_BD_RE_20; else if (aacs_fs_type == CPS_FLAGS_AACS_FS_TYPE_BD_RE_30) aacs_flags = AACS_BD_RE | AACS_BD_RE_30; else aacs_flags = AACS_BD_RE | AACS_PASSTHROUGH; cps_context->media_info_bits_0 |= SPDC_MEDIAINFOBITS0_BD_RE; break; case CPS_FLAGS_MEDIA_TYPE_BD_R: aacs_flags= AACS_BD_R | AACS_PASSTHROUGH; RMDBGLOG((ENABLE,"Media type BD-R\n")); if (aacs_fs_type == CPS_FLAGS_AACS_FS_TYPE_BD_RE_20) aacs_flags = AACS_BD_R | AACS_BD_RE_20; else if (aacs_fs_type == CPS_FLAGS_AACS_FS_TYPE_BD_RE_30) aacs_flags = AACS_BD_R | AACS_BD_RE_30; else aacs_flags = AACS_BD_R | AACS_PASSTHROUGH; cps_context->media_info_bits_0 |= SPDC_MEDIAINFOBITS0_BD_R; break; case CPS_FLAGS_MEDIA_TYPE_SIGMA_MC: aacs_flags|= AACS_SIGMA_MC; if(aacs_fs_type == CPS_FLAGS_AACS_FS_TYPE_BD_RE_20) aacs_flags |= AACS_BD_RE_20; if(aacs_fs_type == CPS_FLAGS_AACS_FS_TYPE_BD_RE_30) aacs_flags |= AACS_BD_RE_30; if(aacs_fs_type == CPS_FLAGS_AACS_FS_TYPE_BDROM) aacs_flags |= AACS_BD_ROM; cps_context->media_info_bits_0 |= SPDC_MEDIAINFOBITS0_BD_ROM; break; default: RMDBGLOG((ENABLE, "Unsupported media type %d\n", media_type)); return RM_ERROR; } /* Enforce restrictions on Extended BD+ support */ if (!cps_context->extended_bdplus_check && (media_type != CPS_FLAGS_MEDIA_TYPE_BD_ROM)) {
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -