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

📄 hdstub.c

📁 WinCE5.0部分核心源码
💻 C
📖 第 1 页 / 共 2 页
字号:
//
// Copyright (c) Microsoft Corporation.  All rights reserved.
//
//
// This source code is licensed under Microsoft Shared Source License
// Version 1.0 for Windows CE.
// For a copy of the license visit http://go.microsoft.com/fwlink/?LinkId=3223.
//
/*++

Module Name:
    
    hdstub.c : HDStub layer

Abstract:

    HDStub is a small kernel dll that accepts and filters notifications from
    the kernel.  These notifications include (and are not limited to)
    exceptions, virtual memory paging, module load, and module unload.

Environment:

    CE kernel

History:

--*/

#include "hdstub_p.h"

// BEGIN OsAxsHCe50.dll parameters
// Global stopping event structure.
HDSTUB_EVENT g_Event;

// Hardware event filter.
static ULONG s_ulFakeHDEventFilter = 0;
static ULONG* s_pulHDEventFilter = &s_ulFakeHDEventFilter;

// Taint flag for modules.  Indicates the number of module events that OsAccess
// has missed.
static BOOL s_dwTaintedModuleCount = 0;
// END parameters


// Pointer to kdata
struct KDataStruct *g_pKData;


// Current Hdstub event handlers
HDSTUB_CLIENT *pClientListHead;

// KITL Ioctl
DWORD (*g_pfnKitlIoctl) (DWORD, LPVOID, DWORD, LPVOID, DWORD, LPDWORD) = 0;

// Sprintf
void (WINAPIV* g_pfnNKvsprintfW)(LPWSTR, LPCWSTR, va_list, int) = 0;
void (*g_pfnOutputDebugString)(const char *sz, ...) = 0;


static void PageInModule (DWORD dwVmBaseAddr);

#ifdef MIPS
/* Interlocked functions for mips */
LONG (*g_pfnInterlockedDecrement)(LPLONG);
LONG (*g_pfnInterlockedIncrement)(LPLONG);
#endif

CRITICAL_SECTION csModLoad;
CRITICAL_SECTION csHdStubEventRecord;

HDSTUB_INIT g_HdStubData = {0};

static ULONG s_ulOldHDEventFilter = 0;

// During boot, allow 2 load events to go through without altering the event flags.
// This is for performance reasons, because 2 load events would guarantee the hardware debugger starting up.
DWORD g_dwModInitCount = 2;


/*++

Routine Name:

    HdstubCallClientIoctl

Routine Description:

    Call any of hdstub's clients.  This is used for inter Kdstub - Osaccess communication.

Arguments:

    szClientName - name of the client ("kdstub", "osaxst0", "osaxst1", etc.)
    dwFunction   - Which function to call.
    dwArg1,2,3,4 - Arguments 1 - 4.  Size of a machine word and should be castable to pointers
                                     if necessary.

Return Value:

    E_FAIL - Unable to find client (Must Change.)

--*/
HRESULT HdstubCallClientIoctl (const char *szClientName, DWORD dwFunction, DWORD dwArg1, DWORD dwArg2, DWORD dwArg3, DWORD dwArg4)
{
    HDSTUB_CLIENT *pClient;
    HRESULT hr = HDSTUB_E_NOCLIENT;

    DEBUGGERMSG (HDZONE_CLIENT, (L"++HdstubCallClientIoctl, %S, %d, %d, %d, %d, %d\r\n", szClientName,
        dwFunction, dwArg1, dwArg2, dwArg3, dwArg4));

    pClient = pClientListHead;
    while (pClient)
    {
        if (!strcmp (pClient->szClientName, szClientName))
        {
            DEBUGGERMSG (HDZONE_CLIENT, (L"  HdstubCallClientIoctl: Found and calling.\r\n"));
            if (pClient->pfnIoctl)
            {
                hr = pClient->pfnIoctl (dwFunction, dwArg1, dwArg2, dwArg3, dwArg4);
                DEBUGGERMSG (HDZONE_CLIENT, (L"  HdstubCallClientIoctl: returned 0x%.08x\r\n", hr));
            }
            break;
        }
        pClient = pClient->pCliNext;
    }

    DEBUGGERMSG (HDZONE_CLIENT, (L"--HdstubCallClientIoctl: 0x%.08x\r\n", hr));    
    return hr;          
}


/*++

Routine Name:

    HdstubConnectKdstub

Routine Description:

    Hook KDStub to HDStub.  Assume that the Kernel debugger dll is already
    loaded.

Arguments:

    pfnCliInit    - in, Pointer to Client init function
    pvExtra       - in, Pointer to Extra Data to pass through to Client

Return Value:

    TRUE    : Load successful
    FALSE   : Failure

--*/
BOOL HdstubConnectClient (HDSTUB_CLINIT_FUNC pfnCliInit, void *pvExtra)
{
    BOOL fReturn;
    HDSTUB_DATA HdstubData =
    {
        HdstubRegisterClient,
        HdstubUnregisterClient,
        HdstubCallClientIoctl
    };
    
    DEBUGGERMSG (HDZONE_INIT, (L"++HdstubConnectKdstub: CliInit=0x%.8x, pvExtra=0x%.8x\r\n", pfnCliInit, pvExtra));
    fReturn = pfnCliInit (&HdstubData, pvExtra);
    DEBUGGERMSG (HDZONE_INIT, (L"--HdstubConnectKdstub: return %d\r\n", fReturn));
    return fReturn;
}


/*++

Routine Name:

    HdstubDLLEntry

Routine Description:

    Attach to nk.exe.  Provide nk.exe with a pointer to HdstubInit

Arguments:

    hInstance -
    ulReason -
    pvReserved -

Return Value:

    TRUE  - Loaded
    FALSE - Error during entry.

--*/
BOOL WINAPI HdstubDLLEntry (HINSTANCE hInstance, ULONG ulReason,
        LPVOID pvReserved)
{
    BOOL bResult;
    FARPROC pfnKernelLibIoctl;
    FARPROC pfnInit;
    
    pfnKernelLibIoctl = (FARPROC)pvReserved;
    pfnInit = (FARPROC)HdstubInit;
    bResult = TRUE;

    DEBUGREGISTER(hInstance);
    
    switch (ulReason)
    {
        case DLL_PROCESS_ATTACH:
            bResult = pfnKernelLibIoctl
                && pfnKernelLibIoctl ((HANDLE)KMOD_DBG,
                        IOCTL_DBG_HDSTUB_INIT,
                        (void *) &pfnInit,
                        sizeof (pfnInit),
                        NULL,
                        0,
                        NULL);
            break;

        case DLL_PROCESS_DETACH:
            break;
    }

    return bResult;
}


/*++

Routine Name:

    HdstubInit

Routine Description:

    Initialize Hdstub.

Arguments:

    pHdInit     - out, export event notification functions.

Return Value:

    TRUE : success.

--*/
BOOL HdstubInit(HDSTUB_INIT *pHdInit)
{
    BOOL fResult = FALSE;

    if (pHdInit && (pHdInit->cbSize == sizeof(*pHdInit)))
    {
        g_HdStubData = *pHdInit;

        g_HdStubData.pfnInitializeCriticalSection(&csModLoad);

#ifdef MIPS
        g_pfnInterlockedDecrement = pHdInit->pfnInterlockedDecrement;
        g_pfnInterlockedIncrement = pHdInit->pfnInterlockedIncrement;
#endif
        // Get existing imported functions and data
        g_pfnNKvsprintfW = pHdInit->pNKSprintfW;
        g_pfnKitlIoctl = pHdInit->pKITLIoCtl;
        g_pKData = pHdInit->pKData;
        s_pulHDEventFilter = pHdInit->pulHDEventFilter;

        // Obtain KITLOutputDebugString
        if (g_pfnKitlIoctl)
        {
            g_pfnKitlIoctl(IOCTL_EDBG_GET_OUTPUT_DEBUG_FN, NULL, 0, (VOID*)&g_pfnOutputDebugString,
                sizeof(g_pfnOutputDebugString), NULL);
        }

        // Export trap functions
        pHdInit->pfnException = HdstubTrapException;
        pHdInit->pfnVmPageIn = HdstubTrapVmPageIn;
        pHdInit->pfnModLoad = HdstubTrapModuleLoad;
        pHdInit->pfnModUnload = HdstubTrapModuleUnload;
        pHdInit->pfnConnectClient = HdstubConnectClient;

        // Export hw debug notification function and structure.
        pHdInit->pEvent = &g_Event;
        pHdInit->pdwTaintedModuleCount = &s_dwTaintedModuleCount;

        fResult = TRUE;
    }
    
    return fResult;
}


/*++

Routine Name:

    HdstubRegisterClient

Routine Description:

    Add a client structure into the linked list.  Does not copy.

Arguments:

    pClient     - Client Structure, must be either allocated or static data from client..
    Disposition - Position to insert the element, either at head or at tail.

Return Value:

    TRUE - successfully added client.
    FALSE - unable to add the client.

--*/
BOOL HdstubRegisterClient (HDSTUB_CLIENT *pClient, int Disposition)
{
    HDSTUB_CLIENT *pClientCur = NULL;
    HDSTUB_CLIENT *pClientLast = NULL;
    BOOL fResult = FALSE;

    DEBUGGERMSG (HDZONE_CLIENT, (L"++HdstubRegisterClient: 0x%.08x, %d\r\n", pClient, Disposition));

    pClientCur = pClientListHead;
    while (pClientCur)
    {
        if (pClientCur == pClient)
        {
            DEBUGGERMSG (HDZONE_CLIENT, (L"  HdstubRegisterClient: Already registered.\r\n"));
            fResult = TRUE;
            goto Done;
        }
        pClientLast = pClientCur;
        pClientCur = pClientCur->pCliNext;
    }

    pClient->pCliNext = NULL;
    switch (Disposition)
    {
        case HdstubClientFirst:
            DEBUGGERMSG (HDZONE_CLIENT, (L"  HdstubRegisterClient: Insert at head.\r\n"));
            pClient->pCliNext = pClientListHead;
            pClientListHead = pClient;
            fResult = TRUE;
            break;
            
        case HdstubClientLast:
            if (pClientLast)
            {
                DEBUGGERMSG (HDZONE_CLIENT, (L"  HdstubRegisterClient: Insert at tail after 0x%.08x\r\n", pClientLast));
                pClientLast->pCliNext = pClient;
            }
            else
            {
                DEBUGGERMSG (HDZONE_CLIENT, (L"  HdstubRegisterClient: Tail, Insert at head because no other clients.\r\n"));
                pClientListHead = pClient;
            }
            fResult = TRUE;
            break;

        default:

⌨️ 快捷键说明

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