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

📄 hwsim.cpp

📁 audio and video stream driver for windows. Tool: winddk
💻 CPP
📖 第 1 页 / 共 2 页
字号:
/**************************************************************************

    AVStream Simulated Hardware Sample

    Copyright (c) 2001, Microsoft Corporation.

    File:

        hwsim.cpp

    Abstract:
        
        This file contains the hardware simulation.  It fakes "DMA" transfers,
        scatter gather mapping handling, ISR's, etc...  The ISR routine in
        here will be called when an ISR would be generated by the fake hardware
        and it will directly call into the device level ISR for more accurate
        simulation.

    History:

        created 3/9/2001

**************************************************************************/

#include "avshws.h"

/**************************************************************************

    PAGEABLE CODE

**************************************************************************/

#ifdef ALLOC_PRAGMA
#pragma code_seg("PAGE")
#endif // ALLOC_PRAGMA


CHardwareSimulation::
CHardwareSimulation (
    IN IHardwareSink *HardwareSink
    ) :
    m_HardwareSink (HardwareSink),
    m_ScatterGatherMappingsMax (SCATTER_GATHER_MAPPINGS_MAX)

/*++

Routine Description:

    Construct a hardware simulation

Arguments:

    HardwareSink -
        The hardware sink interface.  This is used to trigger
        fake interrupt service routines from.

Return Value:

    Success / Failure

--*/

{

    PAGED_CODE();

    //
    // Initialize the DPC's, timer's, and locks necessary to simulate
    // this capture hardware.
    //
    KeInitializeDpc (
        &m_IsrFakeDpc, 
        reinterpret_cast <PKDEFERRED_ROUTINE> 
            (CHardwareSimulation::SimulatedInterrupt),
        this
        );

    KeInitializeEvent (
        &m_HardwareEvent,
        SynchronizationEvent,
        FALSE
        );

    KeInitializeTimer (&m_IsrTimer);

    KeInitializeSpinLock (&m_ListLock);

}

/*************************************************/


CHardwareSimulation *
CHardwareSimulation::
Initialize (
    IN KSOBJECT_BAG Bag,
    IN IHardwareSink *HardwareSink
    )

/*++

Routine Description:

    Initialize the hardware simulation

Arguments:

    HardwareSink -
        The hardware sink interface.  This is what ISR's will be
        triggered through.

Return Value:

    A fully initialized hardware simulation or NULL if the simulation
    could not be initialized.

--*/

{

    PAGED_CODE();

    CHardwareSimulation *HwSim = 
        new (NonPagedPool) CHardwareSimulation (HardwareSink);

    return HwSim;

}

/*************************************************/


NTSTATUS
CHardwareSimulation::
Start (
    IN CImageSynthesizer *ImageSynth,
    IN LONGLONG TimePerFrame,
    IN ULONG Width,
    IN ULONG Height,
    IN ULONG ImageSize
    )

/*++

Routine Description:

    Start the hardware simulation.  This will kick the interrupts on,
    begin issuing DPC's, filling in capture information, etc...
    We keep track of starvation starting at this point.

Arguments:

    ImageSynth -
        The image synthesizer to use to generate pictures to display
        on the capture buffer.

    TimePerFrame -
        The time per frame...  we issue interrupts this often.

    Width -
        The image width

    Height -
        The image height

    ImageSize - 
        The size of the image.  We allocate a temporary scratch buffer
        based on this size to fake hardware.

Return Value:

    Success / Failure (typical failure will be out of memory on the 
    scratch buffer, etc...)

--*/

{

    PAGED_CODE();

    NTSTATUS Status = STATUS_SUCCESS;

    m_ImageSynth = ImageSynth;
    m_TimePerFrame = TimePerFrame;
    m_ImageSize = ImageSize;
    m_Height = Height;
    m_Width = Width;

    InitializeListHead (&m_ScatterGatherMappings);
    m_NumMappingsCompleted = 0;
    m_ScatterGatherMappingsQueued = 0;
    m_NumFramesSkipped = 0;
    m_InterruptTime = 0;

    KeQuerySystemTime (&m_StartTime);

    //
    // Allocate a scratch buffer for the synthesizer.
    //
    m_SynthesisBuffer = reinterpret_cast <PUCHAR> (
        ExAllocatePool (
            NonPagedPool,
            m_ImageSize
            )
        );

    if (!m_SynthesisBuffer) {
        Status = STATUS_INSUFFICIENT_RESOURCES;
    }

    //
    // If everything is ok, start issuing interrupts.
    //
    if (NT_SUCCESS (Status)) {

        //
        // Initialize the entry lookaside.
        //
        ExInitializeNPagedLookasideList (
            &m_ScatterGatherLookaside,
            NULL,
            NULL,
            0,
            sizeof (SCATTER_GATHER_ENTRY),
            'nEGS',
            0
            );

        //
        // Set up the synthesizer with the width, height, and scratch buffer.
        //
        m_ImageSynth -> SetImageSize (m_Width, m_Height);
        m_ImageSynth -> SetBuffer (m_SynthesisBuffer);

        LARGE_INTEGER NextTime;
        NextTime.QuadPart = m_StartTime.QuadPart + m_TimePerFrame;

        m_HardwareState = HardwareRunning;
        KeSetTimer (&m_IsrTimer, NextTime, &m_IsrFakeDpc);

    }

    return Status;
        
}

/*************************************************/


NTSTATUS
CHardwareSimulation::
Pause (
    BOOLEAN Pausing
    )

/*++

Routine Description:

    Pause the hardware simulation...  When the hardware simulation is told
    to pause, it stops issuing interrupts, etc...  but it does not reset
    the counters 

Arguments:

    Pausing -
        Indicates whether the hardware is pausing or not. 

        TRUE -
            Pause the hardware

        FALSE -
            Unpause the hardware from a previous pause


Return Value:

    Success / Failure

--*/

{

    PAGED_CODE();

    if (Pausing && m_HardwareState == HardwareRunning) {
        //
        // If we were running, stop completing mappings, etc...
        //
        m_StopHardware = TRUE;
    
        KeWaitForSingleObject (
            &m_HardwareEvent,
            Suspended,
            KernelMode,
            FALSE,
            NULL
            );

        ASSERT (m_StopHardware == FALSE);

        m_HardwareState = HardwarePaused; 

    } else if (!Pausing && m_HardwareState == HardwarePaused) {

        //
        // For unpausing the hardware, we need to compute the relative time
        // and restart interrupts.
        //
        LARGE_INTEGER UnpauseTime;

        KeQuerySystemTime (&UnpauseTime);
        m_InterruptTime = (ULONG) (
            (UnpauseTime.QuadPart - m_StartTime.QuadPart) /
            m_TimePerFrame
            );

        UnpauseTime.QuadPart = m_StartTime.QuadPart +
            (m_InterruptTime + 1) * m_TimePerFrame;

        m_HardwareState = HardwareRunning;
        KeSetTimer (&m_IsrTimer, UnpauseTime, &m_IsrFakeDpc);

    }

    return STATUS_SUCCESS;

}

/*************************************************/


NTSTATUS
CHardwareSimulation::
Stop (
    )

/*++

Routine Description:

    Stop the hardware simulation....  Wait until the hardware simulation
    has successfully stopped and then return.

Arguments:

    None

Return Value:

    Success / Failure

--*/

{

    PAGED_CODE();

    //
    // If the hardware is told to stop while it's running, we need to
    // halt the interrupts first.  If we're already paused, this has
    // already been done.
    //
    if (m_HardwareState == HardwareRunning) {
    
        m_StopHardware = TRUE;
    
        KeWaitForSingleObject (
            &m_HardwareEvent,
            Suspended,
            KernelMode,
            FALSE,
            NULL
            );
    
        ASSERT (m_StopHardware == FALSE);

    }

    m_HardwareState = HardwareStopped;

    //
    // The image synthesizer may still be around.  Just for safety's
    // sake, NULL out the image synthesis buffer and toast it.

⌨️ 快捷键说明

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