📄 ewl.c
字号:
return NULL;
}
pAlloc = gEnc->FreeMem;
gEnc->FreeMem = pNextFree;
DEBUGMSG( ENC_DEBUG_EXTRA, (_T("EWL_MallocLinear: Ok!\r\n")) );
return pAlloc;
}
/*------------------------------------------------------------------------------
EWL_FreeLinear
------------------------------------------------------------------------------*/
void EWL_FreeLinear( u32* pVirt )
{
ASSERT( gEnc!=NULL );
ASSERT( pVirt >= gEnc->MemBase && pVirt < gEnc->MemBase+gEnc->MemSize/4 );
// Nothing to do, everything is released in EWL_Release
DEBUGMSG( ENC_DEBUG_EXTRA, (_T("EWL_FreeLinear: Ok!\r\n")) );
}
/*------------------------------------------------------------------------------
EWL_Virt2Bus
------------------------------------------------------------------------------*/
u32 EWL_Virt2Bus( u32* pVirt )
{
u32 offset = 0;
u32 busAddr;
ASSERT( gEnc != NULL );
ASSERT( pVirt >= gEnc->MemBase && pVirt < gEnc->MemBase+gEnc->MemSize/4 );
offset = (u32)pVirt - (u32)gEnc->MemBase;
busAddr = (u32)(gEnc->MemBus + offset);
return busAddr;
}
/*------------------------------------------------------------------------------
EWL_PostHwRdy
------------------------------------------------------------------------------*/
i32 EWL_PostHwRdy(void)
{
// PostHwRdy not used by EWL; encoder semaphore (event)
// automatically signaled by interrupt handler
return EWL_OK;
}
/*------------------------------------------------------------------------------
EWL_WaitHwRdy
------------------------------------------------------------------------------*/
i32 EWL_WaitHwRdy(void)
{
DWORD status;
ASSERT( gEnc != NULL );
status = WaitForSingleObject( gEnc->InterruptEvent, ENC_INTR_TIMEOUT );
if( status == WAIT_TIMEOUT )
{
DEBUGMSG( ENC_DEBUG, (_T("EWL_WaitHwRdy: WaitForSingleObject timeout %d\r\n"), GetLastError()) );
return EWL_TIMEOUT;
}
if( status != WAIT_OBJECT_0 )
{
DEBUGMSG( ENC_DEBUG, (_T("EWL_WaitHwRdy: WaitForSingleObject failed %d\r\n"), GetLastError()) );
return EWL_NOK;
}
// Lock access to encoder hw registers
status = ENCHW_LOCK( gEnc->EncHw, ENC_ENCHW_TIMEOUT );
if( !status )
{
DEBUGMSG( ENC_DEBUG, (_T("EWL_WaitHwRdy: ENCHW_LOCK failed. PowerDown failed?\r\n")) );
return EWL_NOK;
}
// Clear HW interrupt flag
EncHw_WriteReg( gEnc->EncHw, 0x10, EncHw_ReadReg(gEnc->EncHw,0x10) & ~0x01 );
ENCHW_UNLOCK( gEnc->EncHw );
// Signal OS for interrupt done
InterruptDone( gEnc->SysIntr );
DEBUGMSG( ENC_DEBUG_EXTRA, (_T("EWL_WaitHwRdy: Ok!\r\n")) );
return EWL_OK;
}
/*------------------------------------------------------------------------------
EWL_ResetHwRdy
------------------------------------------------------------------------------*/
i32 EWL_ResetHwRdy(void)
{
BOOL status;
ASSERT( gEnc != NULL );
// ReseHwRdy is straighforward: just rest the event
// associated with the HW interrupt
status = ResetEvent( gEnc->InterruptEvent );
if( !status )
{
DEBUGMSG( ENC_DEBUG, (_T("EWL_ResetHwRdy: ResetEvent failed %d\r\n"), GetLastError()) );
return EWL_NOK;
}
DEBUGMSG( ENC_DEBUG_EXTRA, (_T("EWL_ResetHwRdy: Ok!\r\n")) );
return EWL_OK;
}
/*------------------------------------------------------------------------------
EWL_IRQ_Enable
------------------------------------------------------------------------------*/
void EWL_IRQ_Enable(void)
{
// IRQ enabling/disabling currently not used by Mp4EncApi
}
/*------------------------------------------------------------------------------
EWL_IRQ_Disable
------------------------------------------------------------------------------*/
void EWL_IRQ_Disable(void)
{
// IRQ enabling/disabling currently not used by Mp4EncApi
}
/*------------------------------------------------------------------------------
AllocSingleEncInstance
------------------------------------------------------------------------------*/
enc_t* AllocSingleEncInstance(void)
{
enc_t* enc;
HANDLE instanceMutex;
// 1. Create named mutex in OS scope
instanceMutex = CreateMutex( NULL, FALSE, ENC_INSTANCE_MUTEX );
if( instanceMutex == NULL )
{
DEBUGMSG( ENC_DEBUG, (_T("AllocSingleEncInstance: CreateMutex failed\r\n")) );
return NULL;
}
// Check for previous mutexes (and hence other encoder instances)
if( GetLastError() == ERROR_ALREADY_EXISTS )
{
CloseHandle( instanceMutex );
DEBUGMSG( ENC_DEBUG, (_T("AllocSingleEncInstance: InstanceMutex exists, failed!\r\n")) );
return NULL;
}
// 2. Allocate memory
enc = malloc( sizeof(enc_t) );
if( enc==NULL )
{
CloseHandle( instanceMutex );
DEBUGMSG( ENC_DEBUG, (_T("AllocSingleEncInstance: malloc failed\r\n")) );
return NULL;
}
// 3. Init allocated structure
enc->EncHw = NULL;
enc->MemBase = NULL;
enc->MemBus = 0;
enc->MemSize = 0;
enc->FreeMem = NULL;
enc->InterruptEvent = NULL;
enc->SysIntr = 0;
enc->SavedClockMode = DDK_CLOCK_GATE_MODE_DISABLED;
enc->InstanceMutex = instanceMutex;
DEBUGMSG( ENC_DEBUG_EXTRA, (_T("AllocSingleEncInstance: Ok!\r\n")) );
return enc;
}
/*------------------------------------------------------------------------------
FreeSingleEncInstance
------------------------------------------------------------------------------*/
i32 FreeSingleEncInstance( enc_t* enc )
{
ASSERT( enc != NULL );
CloseHandle( enc->InstanceMutex );
free( enc );
DEBUGMSG( ENC_DEBUG_EXTRA, (_T("FreeSingleEncInstance: Ok!\r\n")) );
return EWL_OK;
}
/*------------------------------------------------------------------------------
SetupInterrupt
------------------------------------------------------------------------------*/
i32 SetupInterrupt(void)
{
BOOL status;
DWORD dwIrq;
// Create an event to be triggered by interrupt
gEnc->InterruptEvent = CreateEvent( NULL, FALSE, FALSE, NULL );
if( gEnc->InterruptEvent == NULL )
{
DEBUGMSG( ENC_DEBUG, (_T("SetupInterrupt: CreateEvent() failed %d\r\n"), GetLastError()) );
return EWL_NOK;
}
// Associate IRQ with IST
dwIrq = ENC_INTR_IRQ;
status = KernelIoControl( IOCTL_HAL_REQUEST_SYSINTR, &dwIrq, sizeof(DWORD), &gEnc->SysIntr, sizeof(DWORD), NULL );
if( !status )
{
DEBUGMSG( ENC_DEBUG, (_T("SetupInterrupt: IOCTL_HAL_REQUEST_SYSINTR failed %d\r\n"), GetLastError()) );
return EWL_NOK;
}
// Associate the enceoder ionterrupt to the created event
status = InterruptInitialize( gEnc->SysIntr, gEnc->InterruptEvent, NULL, 0 );
if( !status )
{
DEBUGMSG( ENC_DEBUG, (_T("SetupInterrupt: InterruptInitialize() failed %d\r\n"), GetLastError()));
return EWL_NOK;
}
DEBUGMSG( ENC_DEBUG_EXTRA, (_T("SetupInterrupt: Ok!\r\n")) );
return EWL_OK;
}
/*------------------------------------------------------------------------------
DllMain
------------------------------------------------------------------------------*/
BOOL APIENTRY DllMain( HANDLE hModule, DWORD ulReason, LPVOID lpReserved )
{
u32 status = EWL_OK;
switch( ulReason )
{
case DLL_PROCESS_ATTACH:
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
// Nothing to be done for dll load
return TRUE;
break;
case DLL_PROCESS_DETACH:
// Check for clean dll exit
if( gEnc == NULL ) return TRUE;
DEBUGMSG( ENC_DEBUG, (_T("DllMain: EWL not correctly released by ")
_T("mp4encapi, forcing EWL_Release()\r\n")) );
status = EWL_Release();
return status == EWL_OK;
break;
default:
// Shouldn't get here
return FALSE;
break;
}
// Shouldn't get here
return FALSE;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -