⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 pindevice.cpp

📁 Microsoft WinCE 6.0 BSP FINAL release source code for use with the i.MX27ADS TO2 WCE600_FINAL_MX27_S
💻 CPP
📖 第 1 页 / 共 5 页
字号:
    else
    {
        DEBUGMSG(ZONE_IOCTL|ZONE_ERROR, (_T("PIN_IOControl(%08x): Timer already created.\r\n"), this));
    }

    return TRUE;
}

//------------------------------------------------------------------------------
//
//  FUNCTION:        TimerCallBack
//
//  DESCRIPTION:     Handle the call back of timer
//
//  PARAMETERS:      None
//
//  RETURNS:         TRUE if success, otherwise FALSE.
//------------------------------------------------------------------------------
void CPinDevice :: TimerCallBack( UINT uTimerID, UINT uMsg, DWORD_PTR dwUser, DWORD_PTR dw1, DWORD_PTR dw2 )
{
    UNREFERENCED_PARAMETER(uTimerID) ;
    UNREFERENCED_PARAMETER(uMsg);
    UNREFERENCED_PARAMETER(dw1);
    UNREFERENCED_PARAMETER(dw2);

    PPINDEVICE pPinDevice = reinterpret_cast<PPINDEVICE>(dwUser) ;
    if (NULL == pPinDevice)
    {
        DEBUGMSG(ZONE_IOCTL|ZONE_ERROR, (_T("PIN_IOControl: TimerCallBack PinDevice is NULL.\r\n"))) ;
    }
    else
    {
        pPinDevice->HandlePinIO() ;
    }
}

//------------------------------------------------------------------------------
//
//  FUNCTION:        InitMsgQueueDescriptor
//
//  DESCRIPTION:     Handle the call back of timer
//
//  PARAMETERS:      None
//
//  RETURNS:         TRUE if success, otherwise FALSE.
//------------------------------------------------------------------------------
BOOL CPinDevice::InitMsgQueueDescriptor (
    PCS_MSGQUEUE_BUFFER pCsMsgQBuff, 
    PCS_STREAM_DESCRIPTOR pCsStreamDesc, 
    PVOID pMappedData, 
    PVOID pUnmappedData, 
    BOOL bBufferFill
    )
{
    PCSSTREAM_HEADER pCsStreamHeader = reinterpret_cast<PCSSTREAM_HEADER>(pCsStreamDesc);
    PCS_FRAME_INFO   pCsFrameInfo    = reinterpret_cast<PCS_FRAME_INFO>(pCsStreamHeader + 1);

    if ((pCsStreamHeader == NULL) || (pCsFrameInfo == NULL))
    {
        DEBUGMSG(ZONE_FUNCTION|ZONE_ERROR, (_T("InitMsgQueueDescriptor(%08x): Invalid Stream Descriptor\r\n"), this));
        return FALSE;
    }

    if (bBufferFill)
    {
        // The buffer fill function must use the pointer that's been mapped into this process.
        pCsStreamHeader->Data = pMappedData;

        //BUFFERFILLPARAMS buffFillParams;
        //m_pCamAdapter->GetBrightness( &(buffFillParams.ulBrightness) );
        //m_pCamAdapter->GetZoom( &(buffFillParams.ulZoom) );

        EnterCriticalSection(&m_csStreamBuffer) ;
        pCsStreamHeader->DataUsed = m_pfnBufferFill( (PUCHAR) pMappedData, reinterpret_cast<PCS_VIDEOINFOHEADER>(&m_CsDataRangeVideo.VideoInfoHeader),  IMAGE_GRAY_INCREASING, FALSE, (LPVOID)this ) ;
        LeaveCriticalSection(&m_csStreamBuffer) ;

        pCsFrameInfo->PictureNumber = (LONGLONG)++m_ulPictureNumber;
        pCsFrameInfo->DropCount     = (LONGLONG)m_ulFramesDropped;
    }

    // The message queue requires the original pointer value.
    pCsStreamHeader->Data = pUnmappedData;

    // Init the flags to zero
    pCsStreamHeader->OptionsFlags = 0;

    // Set the discontinuity flag if frames have been previously
    // dropped, and then reset our internal flag

    if (TRUE == m_fDiscontinuity) 
    {
        pCsStreamHeader->OptionsFlags |= CSSTREAM_HEADER_OPTIONSF_DATADISCONTINUITY;
        m_fDiscontinuity = FALSE;
    }

    DWORD msNow = GetTickCount();

    if (m_msStart == 0xFFFFFFFF)
    {
        m_msStart = msNow;
    }

    //
    // Return the timestamp for the frame
    //
    pCsStreamHeader->PresentationTime.Numerator   = 1;
    pCsStreamHeader->PresentationTime.Denominator = 1;
    pCsStreamHeader->Duration                     = m_RtAveTimePerFrame;
    DWORD prevPT = m_msLastPT;
    if (bBufferFill)
    {
        m_msLastPT = msNow - m_msStart;

        pCsStreamHeader->PresentationTime.Time = (LONGLONG) m_msLastPT * 10000;  // presentation time stamp in 100s of ns

    }
    else
    {
        pCsStreamHeader->PresentationTime.Time = 0;
    }

    DEBUGMSG(ZONE_FUNCTION, (_T("InitMsgQueueDescriptor: LastPT = %d, elapsed = %d\n"), m_msLastPT, m_msLastPT - prevPT));

    // clear the timestamp valid flags
    pCsStreamHeader->OptionsFlags &= ~( CSSTREAM_HEADER_OPTIONSF_TIMEVALID | CSSTREAM_HEADER_OPTIONSF_DURATIONVALID );

    // Every frame we generate is a key frame (aka SplicePoint)
    // Delta frames (B or P) should not set this flag

    pCsStreamHeader->OptionsFlags |= CSSTREAM_HEADER_OPTIONSF_SPLICEPOINT;

    pCsMsgQBuff->CsMsgQueueHeader.Size    = sizeof(CS_MSGQUEUE_HEADER);
    pCsMsgQBuff->CsMsgQueueHeader.Flags   = FLAG_MSGQ_FRAME_BUFFER;
    pCsMsgQBuff->CsMsgQueueHeader.Context = NULL;

    //Get the unmarshalled StreamDescriptor in order to send the message to the application
    pCsMsgQBuff->pStreamDescriptor = NULL;
    for (UINT ii = 0; ii < m_dwBufferCount; ii++)
    {
        if(m_pStreamDescriptorList[ii].csStreamDescriptorShadow.CsStreamHeader.Data == pUnmappedData)
        {
            pCsMsgQBuff->pStreamDescriptor = m_pStreamDescriptorList[ii].m_pUnMarshalledStreamDesc;
            break;
        }
    }

    if(NULL == pCsMsgQBuff->pStreamDescriptor)
    {
        DEBUGMSG(ZONE_FUNCTION, (_T("InitMsgQueueDescriptor(%08x): Unable to find Unmarshalled Stream Desc\n"), this));
        return FALSE;
    }

    DEBUGMSG(ZONE_FUNCTION, (_T("InitMsgQueueDescriptor(%08x): Frame buf queued: %d (dropped %d), start %d, time %d\n"), 
        this,
        (LONG)pCsFrameInfo->PictureNumber, 
        (LONG)pCsFrameInfo->DropCount, 
        (LONG)m_msStart,
        (LONG)(pCsStreamHeader->PresentationTime.Time / 10000)));

    return TRUE;
}

//------------------------------------------------------------------------------
//
//  FUNCTION:        FlushBufferQueue
//
//  DESCRIPTION:     Flush Buffer Queue
//
//  PARAMETERS:      None
//
//  RETURNS:         None
//------------------------------------------------------------------------------
void  CPinDevice::FlushBufferQueue()
{
    PCS_STREAM_DESCRIPTOR pCsStreamDesc = NULL;
    PVOID                 pMappedData   = NULL;
    PVOID                 pUnmappedData = NULL;
    CS_MSGQUEUE_BUFFER    CsMsgQBuff ;

    DWORD dwSavedPermissions = SetProcPermissions( (DWORD)-1 ) ;

    while (( TRUE == RemoveBufferFromList( &pCsStreamDesc, &pMappedData, &pUnmappedData )) && ( NULL != pCsStreamDesc ) && ( m_hMsgQ != NULL ))
    {
        if (!InitMsgQueueDescriptor (&CsMsgQBuff, pCsStreamDesc, pMappedData, pUnmappedData, FALSE))
        {
            continue;
        }

        if ( FALSE == WriteMsgQueue( m_hMsgQ, reinterpret_cast<LPVOID>(&CsMsgQBuff),  sizeof(CS_MSGQUEUE_BUFFER), PIN_TIMEOUT, 0 ) )
        {
            DEBUGMSG(ZONE_FUNCTION|ZONE_ERROR, (_T("PIN_Function(%08x): WriteMsgQueue returned false\r\n"), this));
        }
    }

    SetProcPermissions( dwSavedPermissions );

    return;
}

//------------------------------------------------------------------------------
//
//  FUNCTION:        HandlePinIO
//
//  DESCRIPTION:     Handle Pin IO request 
//
//  PARAMETERS:      None
//
//  RETURNS:         None
//------------------------------------------------------------------------------
void CPinDevice :: HandlePinIO()
{
    DEBUGMSG(ZONE_FUNCTION, (_T("HandlePinIO(%08x): HandlePinIO\r\n"), this)) ;
    if ( CSSTATE_RUN != m_CsState ) 
    {
        DEBUGMSG(ZONE_FUNCTION, (_T("HandlePinIO(%08x): CSSTATE_RUN != m_CsState\r\n"), this)) ;
        return;
    }

    DEBUGMSG(ZONE_FUNCTION, (_T("HandlePinIO(%08x): CSSTATE_RUN == m_CsState\r\n"), this)) ;
    if ( STILL == m_ulPinId )
    {
       DEBUGMSG(ZONE_IOCTL, (_T("HandlePinIO(%08x): Preparing for STILL capture.\r\n"), this));
    
       m_pCamAdapter->PauseCaptureAndPreview( ) ;
    }

    DWORD dwSavedPermissions = SetProcPermissions( (DWORD)-1 ) ;
    
    PCS_STREAM_DESCRIPTOR pCsStreamDesc = NULL;
    PVOID                 pMappedData   = NULL;
    PVOID                 pUnmappedData = NULL;
    CS_MSGQUEUE_BUFFER    CsMsgQBuff ;

    if ( FALSE == RemoveBufferFromList( &pCsStreamDesc, &pMappedData, &pUnmappedData ) || NULL == pCsStreamDesc )
    {
        // We dropped a frame
        m_ulFramesDropped++;
        m_fDiscontinuity = TRUE;
        SetProcPermissions( dwSavedPermissions  );
        return;
    }

    if (!InitMsgQueueDescriptor (&CsMsgQBuff, pCsStreamDesc, pMappedData, pUnmappedData, TRUE))
    {
        DEBUGMSG(ZONE_FUNCTION|ZONE_ERROR, (_T("HandlePinIO(%08x): Invalid Stream Descriptor\r\n"), this)) ;
        SetProcPermissions(dwSavedPermissions);
        return ;
    }

    if (NULL == m_hMsgQ)
    {
        DEBUGMSG(ZONE_FUNCTION|ZONE_ERROR, (_T("HandlePinIO(%08x): MsgQueue is not opened\r\n"), this)) ;
        SetProcPermissions( dwSavedPermissions  ) ;
        return ;
    }

    if ( FALSE == WriteMsgQueue( m_hMsgQ, reinterpret_cast<LPVOID>(&CsMsgQBuff),  sizeof(CS_MSGQUEUE_BUFFER), PIN_TIMEOUT, 0 ) )
    {
        DEBUGMSG(ZONE_FUNCTION|ZONE_ERROR, (_T("HandlePinIO(%08x): WriteMsgQueue returned FALSE\r\n"), this)) ;
    }

    if (STILL == m_ulPinId)
    {
        DEBUGMSG(ZONE_IOCTL, (_T("HandlePinIO(%08x): Reverting state after STILL capture.\r\n"), this));

        m_CsState = CSSTATE_PAUSE;

        m_pCamAdapter->RevertCaptureAndPreviewState( );
    }
    
    SetProcPermissions( dwSavedPermissions );
    return;
}


//------------------------------------------------------------------------------
//
//  FUNCTION:        BufferFill
//
//  DESCRIPTION:     Fill data to buffer 
//
//  PARAMETERS:      PUCHAR pImage, 
//                   PCS_VIDEOINFOHEADER pCsVideoInfoHdr, 
//                   IMAGECOMMAND Command, 
//                   BOOL FlipHorizontal, 
//                   LPVOID lpParam 
//
//  RETURNS:         The size of the image filled
//------------------------------------------------------------------------------
UINT CPinDevice::PinBufferFill( 
    PUCHAR pImage, 
    PCS_VIDEOINFOHEADER pCsVideoInfoHdr, 
    IMAGECOMMAND Command, 
    BOOL FlipHorizontal, 
    LPVOID lpParam 
    )
{
    ULONG ulPinId;
    
    DEBUGMSG(ZONE_FUNCTION, (TEXT("PIN_Function(%08x): +BufferFill\r\n"), this));

    UNREFERENCED_PARAMETER( Command );
    UNREFERENCED_PARAMETER( FlipHorizontal );

    DEBUGMSG(ZONE_FUNCTION, (TEXT("PIN_Function(%08x):+BufferFill: EnterCriticalSection\r\n"),this));
    ULONG BufferSize = abs(CS__DIBSIZE (pCsVideoInfoHdr->bmiHeader));
    PUINT8 pbySrcBuffer, pbyDstBuffer;
    prpBufferData  prpBuffData;
    UINT retVal = 0;
        
    if (m_ulPinId == STILL)
    {
        ulPinId = m_pCamAdapter->m_StillPinInherited; 
    }
    else
    {
        ulPinId = m_ulPinId;
    }

    while (1)
    {
        switch (ulPinId)
        {
            case PREVIEW:
                {
                    if (WaitForSingleObject(m_pCamAdapter->m_pPrp->m_hVfEOFEvent, WAIT_BUFFER_TIMEOUT) != WAIT_OBJECT_0) 
                    {
                        ERRORMSG(ZONE_ERROR, (TEXT("+BufferFill:WaitForSingleObject m_hPrPBuffFilled timeout!\r\n")));
                        // If camera driver get a fame from PrP timeout. Restart the channel.
                        m_pCamAdapter->m_pPrp->PrpStopVfChannel();
                        m_pCamAdapter->m_pPrp->PrpStartVfChannel();
                        return -1;                        
                    }

                    if (FALSE == m_pCamAdapter->m_pPrp->PrpGetVfBufFilled(&prpBuffData))
                    {
                        DEBUGMSG(ZONE_ERROR, (TEXT("+BufferFill:Get viewfinding filled buffer error!\r\n")));
                        return -1;                        
                    }

                    if (FALSE == m_bDirectMode)   
                    {
                       //For normal mode, we free the buffer automatically.or we should free it manually.
                       m_pCamAdapter->m_pPrp->PrpPutVfBufIdle(&prpBuffData);
                    }
                }
                break;

            case CAPTURE:
                {
                    if (WaitForSingleObject(m_pCamAdapter->m_pPrp->m_hEncEOFEvent, WAIT_BUFFER_TIMEOUT) != WAIT_OBJECT_0) 
                    {
                        DEBUGMSG(ZONE_ERROR, (TEXT("+BufferFill:WaitForSingleObject m_hPrPBuffFilled timeout!\r\n")));
                        // If camera driver get a fame from PrP timeout. Restart the channel.
                        m_pCamAdapter->m_pPrp->PrpStopEncChannel();
                        m_pCamAdapter->m_pPrp->PrpStartEncChannel();
                        return -1;                        
                    }

                    if (FALSE == m_pCamAdapter->m_pPrp->PrpGetEncBufFilled(&prpBuffData))
                    {
                        DEBUGMSG(ZONE_ERROR, (TEXT("+BufferFill:Get encoder filled buffer error!\r\n")));
                        return -1;                        

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -