📄 pindevice.cpp
字号:
//-----------------------------------------------------------------------------
//
// Copyright (C) 2003-2004, MOTOROLA, INC. All Rights Reserved
// THIS SOURCE CODE IS CONFIDENTIAL AND PROPRIETARY AND MAY NOT
// BE USED OR DISTRIBUTED WITHOUT THE WRITTEN PERMISSION OF
// MOTOROLA, INC.
//
//------------------------------------------------------------------------------
//
// Copyright (C) 2004, Freescale Semiconductor, Inc. All Rights Reserved
// THIS SOURCE CODE IS CONFIDENTIAL AND PROPRIETARY AND MAY NOT
// BE USED OR DISTRIBUTED WITHOUT THE WRITTEN PERMISSION OF
// Freescale Semiconductor, Inc.
//
//------------------------------------------------------------------------------
//------------------------------------------------------------------------------
//
// File: Pindevice.cpp
//
// PinDevice Class Implementation
//
//------------------------------------------------------------------------------
#define PININTERFACE
#include <windows.h>
#include <ceddk.h>
#include <Msgqueue.h>
#include <pwinbase.h>
#include <camera.h>
#include "mxarm11.h"
#include "cameradbg.h"
#include "PinDriver.h"
//------------------------------------------------------------------------------
// External Functions
//------------------------------------------------------------------------------
// External Variables
//------------------------------------------------------------------------------
// Defines
//------------------------------------------------------------------------------
// Types
//------------------------------------------------------------------------------
// Global Variables
//------------------------------------------------------------------------------
// Local Variables
//------------------------------------------------------------------------------
// Local Functions
/********************************************************************
*
* FUNCTION: CPinDevice
*
* DESCRIPTION: CPinDevice constructor
*
* PARAMETERS: None
*
* RETURNS: None
*
********************************************************************/
CPinDevice :: CPinDevice(void)
{
m_fClientAllocateBuffers = false;
m_fClientInitialized = false;
m_fDiscontinuity = true;
m_fPrpChannelEnabled = false;
m_bBuffersAllocated = false;
m_ulPinId = -1; //Invalid Pin Id
m_ulMaxNumOfBuffers = 4;
m_ulCurrNumOfBuffers = 0;
m_ulFrameSize = 0;
m_RtAveTimePerFrame = 0;
m_ulFramesDropped = 0;
m_ulPictureNumber = 0;
m_pHeadBuffer = NULL;
m_pHeadBufferOri = NULL;
m_hMsgQ = NULL;
m_hTimerDll = NULL;
m_TimerIdentifier = NULL;
m_CsState = CSSTATE_STOP;
m_pfnTimeSetEvent = NULL;
m_pfnTimeKillEvent = NULL;
InitializeCriticalSection(&m_csStreamBuffer);
m_hPrPBuffFilled = NULL;
m_BufferFilled = 0;
}
/********************************************************************
*
* FUNCTION: ~CPinDevice
*
* DESCRIPTION: CPinDevice disstructor
*
* PARAMETERS: None
*
* RETURNS: None
*
********************************************************************/
CPinDevice :: ~CPinDevice(void)
{
DeleteBufferList();
if (NULL != m_TimerIdentifier && NULL != m_pfnTimeKillEvent)
{
m_pfnTimeKillEvent(m_TimerIdentifier);
m_TimerIdentifier = NULL;
}
if (NULL != m_hMsgQ)
CloseMsgQueue(m_hMsgQ);
if (NULL != m_hTimerDll)
FreeLibrary(m_hTimerDll);
if (m_hPrPBuffFilled != NULL)
CloseHandle(m_hPrPBuffFilled);
m_CsState = CSSTATE_STOP;
DeleteCriticalSection(&m_csStreamBuffer);
}
/********************************************************************
*
* FUNCTION: InitializeSubDevice
*
* DESCRIPTION: Bind caller CamDevice to this PinDevice
*
* PARAMETERS: PCAMERADEVICE pCamDevice
*
* RETURNS: TRUE if successfully, otherwise return FALSE
*
********************************************************************/
bool CPinDevice :: InitializeSubDevice( PCAMERADEVICE pCamDevice )
{
m_pCamAdapter = pCamDevice;
if (NULL == m_pCamAdapter)
return false;
return true;
}
/********************************************************************
*
* FUNCTION: CloseSubDevice
*
* DESCRIPTION: Bind caller CamDevice to this PinDevice
*
* PARAMETERS: None
*
* RETURNS: TRUE if successfully, otherwise return FALSE
*
********************************************************************/
bool CPinDevice :: CloseSubDevice()
{
m_pCamAdapter->DecrCInstances(m_ulPinId);
return true;
}
/********************************************************************
*
* FUNCTION: StreamInstantiate
*
* DESCRIPTION: Initiate a stream instance
*
* PARAMETERS: PCSPROPERTY_STREAMEX_S pCsPropStreamEx,
* PUCHAR pOutBuf,
* DWORD OutBufLen,
* PDWORD pdwBytesTransferred
*
* RETURNS: ERROR_SUCCESS if successfully, otherwise return ERROR_INVALID_PARAMETER
*
********************************************************************/
DWORD CPinDevice :: StreamInstantiate(
PCSPROPERTY_STREAMEX_S pCsPropStreamEx,
PUCHAR pOutBuf,
DWORD OutBufLen,
PDWORD pdwBytesTransferred
)
{
DEBUGMSG(ZONE_IOCTL, (_T("+StreamInstantiate\r\n")));
PCS_DATARANGE_VIDEO pCsDataRangeVid = NULL;
DWORD dwError = ERROR_INVALID_PARAMETER;
if (-1 != m_ulPinId)
{
DEBUGMSG(ZONE_IOCTL|ZONE_ERROR, (_T("PIN_IOControl(%08x): Pin %d is already instantiated.\r\n"), this, m_ulPinId));
return dwError;
}
if (false == m_pCamAdapter->IsValidPin(pCsPropStreamEx->CsPin.PinId))
{
DEBUGMSG(ZONE_IOCTL|ZONE_ERROR, (_T("PIN_IOControl(%08x): Invalid Pin Id\r\n"), this));
return dwError;
}
m_ulPinId = pCsPropStreamEx->CsPin.PinId ;
DEBUGMSG(ZONE_IOCTL, (_T("PIN_IOControl(%08x): m_ulPinId = %d \r\n"),this, m_ulPinId)) ;
// Let us set a default format for this pin
// for STILL Pin, we can only use the format that Preview or Capture pin use.
if (m_ulPinId == STILL)
{
if (m_pCamAdapter->m_StrmInstances[PREVIEW].pPinDev != NULL)
{
memcpy(&m_CsDataRangeVideo, &m_pCamAdapter->m_StrmInstances[PREVIEW].pPinDev->m_CsDataRangeVideo, sizeof(CS_DATARANGE_VIDEO));
m_RtAveTimePerFrame = m_CsDataRangeVideo.VideoInfoHeader.AvgTimePerFrame;
m_pCamAdapter->m_StillPinInherited = PREVIEW;
}
else if (m_pCamAdapter->m_StrmInstances[CAPTURE].pPinDev != NULL)
{
memcpy(&m_CsDataRangeVideo, &m_pCamAdapter->m_StrmInstances[CAPTURE].pPinDev->m_CsDataRangeVideo, sizeof(CS_DATARANGE_VIDEO));
m_RtAveTimePerFrame = m_CsDataRangeVideo.VideoInfoHeader.AvgTimePerFrame;
m_pCamAdapter->m_StillPinInherited = CAPTURE;
}
else
{
DEBUGMSG(ZONE_IOCTL|ZONE_ERROR, (_T("PIN_IOControl(%08x): Still pin can not be initiated before capture and preview pins.\r\n"), this)) ;
return dwError;
}
}
else
{
if (false == m_pCamAdapter->GetPinFormat(m_ulPinId, 1, &pCsDataRangeVid))
{
DEBUGMSG(ZONE_IOCTL|ZONE_ERROR, (_T("PIN_IOControl(%08x): No Pin Format provided for pin\r\n"), this)) ;
return dwError ;
}
memcpy(&m_CsDataRangeVideo, pCsDataRangeVid, sizeof(CS_DATARANGE_VIDEO)) ;
m_RtAveTimePerFrame = m_CsDataRangeVideo.VideoInfoHeader.AvgTimePerFrame;
}
DEBUGMSG(ZONE_IOCTL, (_T("StreamInstantiate: Setting a default format for this pin done.\r\n")));
m_pCamAdapter->CameraMarkAsModified(m_ulPinId);
m_hPrPBuffFilled = CreateEvent(NULL, FALSE, FALSE, NULL);
if (m_hPrPBuffFilled == NULL) {
ERRORMSG(ZONE_ERROR, (TEXT("CSI_Init: CreateEvent m_hPrPBuffFilled failed!\r\n")));
return dwError;
}
if (NULL == pCsPropStreamEx->hMsgQueue)
{
DEBUGMSG(ZONE_IOCTL|ZONE_ERROR, (_T("PIN_IOControl(%08x): NULL Handle provided for msgqueue\r\n"), this));
return dwError;
}
if (false == m_pCamAdapter->IncrCInstances(m_ulPinId, this))
{
DEBUGMSG(ZONE_IOCTL|ZONE_ERROR, (_T("PIN_IOControl(%08x): Pin %d is already instantiated.\r\n"), this, m_ulPinId));
return dwError;
}
//TODO : Check whether the client created msgqueue with enough buffersize and number of buffers.
MSGQUEUEOPTIONS msgQueueOptions;
msgQueueOptions.bReadAccess = FALSE; // we need write-access to msgqueue
msgQueueOptions.dwSize = sizeof(MSGQUEUEOPTIONS);
if (NULL == (m_hMsgQ = OpenMsgQueue(GetCallerProcess(),pCsPropStreamEx->hMsgQueue, &msgQueueOptions)))
{
DEBUGMSG(ZONE_IOCTL|ZONE_ERROR, (_T("PIN_IOControl(%08x): Failed to open MsgQueue\r\n"), this));
m_pCamAdapter->DecrCInstances(m_ulPinId);
return dwError;
}
DEBUGMSG(ZONE_IOCTL, (_T("-StreamInstantiate\r\n")));
return ERROR_SUCCESS;
}
/********************************************************************
*
* FUNCTION: SetState
*
* DESCRIPTION: Set Pin state
*
* PARAMETERS: CSSTATE CsState
* CSSTATE *CsPrevState
*
* RETURNS: None
*
********************************************************************/
void CPinDevice :: SetState(CSSTATE CsState, CSSTATE *CsPrevState)
{
if (NULL != CsPrevState)
*CsPrevState = m_CsState;
m_CsState = CsState;
return;
}
/********************************************************************
*
* FUNCTION: AllocateBuffers
*
* DESCRIPTION: Allocate stream buffers.
* This function is called when client calls
* IOCTL_CS_ALLOCATE_BUFFERS, or when the data
* format changes and the buffers must be
* reallocated.
*
* PARAMETERS: None
*
* RETURNS: true if success, otherwise false.
*
********************************************************************/
bool CPinDevice :: AllocateBuffers()
{
DEBUGMSG(ZONE_IOCTL, ( _T("PIN_IOControl(%08x): AllocateBuffers\r\n"), this));
if (NULL != m_pHeadBufferOri)
DeleteBufferList();
m_ulFrameSize = CS__DIBSIZE(m_CsDataRangeVideo.VideoInfoHeader.bmiHeader); // by bytes
// Call down to Prp to allocate new buffers
switch (m_ulPinId)
{
case PREVIEW:
if (!m_pCamAdapter->m_pPrp->PrpAllocateVfBuffers(m_ulMaxNumOfBuffers, m_ulFrameSize))
{
DEBUGMSG(ZONE_ERROR,(_T("AllocateBuffers: Prp Buffer allocation failed.\r\n")));
return false;
}
break;
case CAPTURE:
if (!m_pCamAdapter->m_pPrp->PrpAllocateEncBuffers(m_ulMaxNumOfBuffers, m_ulFrameSize))
{
DEBUGMSG(ZONE_ERROR,(_T("AllocateBuffers: Prp Buffer allocation failed.\r\n")));
return false;
}
break;
case STILL:
// No need to allocate buffers in the Prp, as those buffers
// will already have been allocated by the Still Pin's
// channel (enc or vf).
break;
default:
DEBUGMSG(ZONE_ERROR,(_T("AllocateBuffers: Invalid pin id.\r\n"))) ;
return FALSE;
}
for (int iCount=m_ulMaxNumOfBuffers; iCount > 0; iCount--)
{
PCS_STREAM_DESCRIPTOR pCsStreamDesc = reinterpret_cast<PCS_STREAM_DESCRIPTOR>(RemoteLocalAlloc(LPTR, sizeof(CS_STREAM_DESCRIPTOR)));
if (NULL == pCsStreamDesc)
{
return false;
}
PCSSTREAM_HEADER pCsStreamHeader = reinterpret_cast<PCSSTREAM_HEADER>(pCsStreamDesc);
pCsStreamHeader->Size = sizeof(CSSTREAM_HEADER);
pCsStreamHeader->TypeSpecificFlags = 0;
pCsStreamHeader->PresentationTime.Time = 0; //Specifies the time value, usually in 100-nanosecond units.
pCsStreamHeader->PresentationTime.Numerator = 1; //Specifies the numerator of the scaling factor for a scaled time value. For a nonscaled value, this should be one. Numerator must not be zero.
pCsStreamHeader->PresentationTime.Denominator = 1; //Specifies the denominator of the scaling factor for a scaled time value. For a nonscaled value, this should be one. Denominator must not be zero.
pCsStreamHeader->Duration = 0;
pCsStreamHeader->FrameExtent = m_ulFrameSize;
pCsStreamHeader->DataUsed = m_ulFrameSize;
pCsStreamHeader->OptionsFlags = CSSTREAM_HEADER_OPTIONSF_DATADISCONTINUITY;
pCsStreamHeader->Data = RemoteLocalAlloc(LPTR, m_ulFrameSize );
if (NULL == pCsStreamHeader->Data)
{
RemoteLocalFree(pCsStreamDesc);
return false ; // We'll clean up any previously allocated buffers and PIN_Close time;
}
PCS_FRAME_INFO pCsFrameInfo = reinterpret_cast<PCS_FRAME_INFO>(pCsStreamHeader + 1);
pCsFrameInfo->ExtendedHeaderSize = sizeof(CS_FRAME_INFO);
pCsFrameInfo->dwFrameFlags = CS_VIDEO_FLAG_FRAME;
pCsFrameInfo->PictureNumber = 0;
pCsFrameInfo->DropCount = 0;
if (false == AddFreeBuf(true, pCsStreamDesc))
{
RemoteLocalFree(pCsStreamHeader->Data);
RemoteLocalFree(pCsStreamDesc);
return false;
}
m_ulCurrNumOfBuffers++;
}
m_bBuffersAllocated = true;
return true;
}
/********************************************************************
*
* FUNCTION: CreateTimer
*
* DESCRIPTION: Creat timer for each pin.
*
* PARAMETERS: None
*
* RETURNS: True if success, otherwise false.
********************************************************************/
bool CPinDevice :: CreateTimer()
{
if (NULL == m_hTimerDll)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -