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

📄 show16.c

📁 Windows 95 系統程式設計大奧秘书籍源码
💻 C
📖 第 1 页 / 共 2 页
字号:
//==================================
// SHOW16 - Matt Pietrek 1995
// FILE: SHOW16.C
//==================================
#include <windows.h>
#include <stdio.h>
#include <string.h>
#include <memory.h>
#include <stdarg.h>
#include <toolhelp.h>
#include <assert.h>
#include <malloc.h>
#pragma hdrstop
#include "show16.h"
#include "tdb.h"
#include "hmodule.h"

// GetModuleName is KERNEL.27, and undocumented, so prototype it
BOOL WINAPI GetModuleName(HMODULE hModule, LPSTR lpszName, UINT cb);

// Prototype the functions for this
void Handle_WM_COMMAND(HWND hWndDlg, WPARAM wParam, LPARAM lParam);
void Handle_WM_INITDIALOG(HWND hWndDlg);
BOOL CALLBACK _export Show16DlgProc(HWND, UINT, WPARAM, LPARAM);
void RecordListboxLineTypeAndValue(HWND hWnd, WORD type, WORD value);
BOOL RetrieveListboxLineTypeAndValue(HWND hWnd, WORD *type, WORD *value);
void UpdateTaskList(void);
void UpdateModuleList(void);
void ShowTaskDetails(HTASK hTask);
void ShowModuleDetails(HMODULE hModule);
void ShowSegmentTableDetails(HMODULE hModule);
void ShowEntryTableDetails(HMODULE hModule);
void ShowResourceDetails(HMODULE hModule);
void ShowResidentNamesDetails(HMODULE hModule);
void ShowNonResidentNamesDetails(HMODULE hModule);
void lbprintf(HWND hWnd, char * format, ...);
LPSTR GetResourceTypeName(WORD id);
BOOL IsModule(HMODULE hModule);
BOOL IsA32BitHMODULE(WORD selector);
LPSTR GetTaskModuleName(HTASK hTask);

// HWNDs of the commonly used dialog controls
HWND HWndMainList;
HWND HWndDetails;
HWND HWndDetailsDescription;


int PASCAL WinMain( HANDLE hInstance, HANDLE hPrevInstance,
                    LPSTR lpszCmdLine, int nCmdShow )
{
    DialogBox(hInstance, "Show16Dlg", 0, (DLGPROC)Show16DlgProc);
    return 0;
}

//
// Handle the dialog's WM_COMMAND messages
//
void Handle_WM_COMMAND(HWND hWndDlg, WPARAM wParam, LPARAM lParam)
{
    //
    // If user hit <enter> see which listbox has the focus, and
    // change wParam and lParam to look as if the user performed
    // the equivalent dbl-click action.
    //
    if ( wParam == IDOK )
    {
        HWND hWndFocus = GetFocus();
        if (hWndFocus == HWndDetails )
        {
            wParam = IDC_LB_DETAILS; lParam = MAKELONG(0,LBN_DBLCLK);
        }
    }
    
    switch ( wParam )
    {
        case IDC_BUTTON_EXIT:
            EndDialog(hWndDlg, 0);
            break;
            
        case IDC_RB_TASKS:
            UpdateTaskList();
            // Set focus to main listbox
            //SendMessage( hWndDlg, WM_NEXTDLGCTL, FALSE, 0 );
            break;
            
        case IDC_RB_MODULES:
            UpdateModuleList();
            // Set focus to main listbox
            //SendMessage( hWndDlg, WM_NEXTDLGCTL, FALSE, 0 );
            break;
            
        case IDC_LB_MAIN_LIST:
            if ( HIWORD(lParam) == LBN_SELCHANGE )
            {
                WORD handle;
                WORD lbSelectedIndex;
                
                lbSelectedIndex =
                    (WORD)SendMessage( HWndMainList, LB_GETCURSEL, 0, 0 );
                handle =
                    (WORD)SendMessage(HWndMainList, LB_GETITEMDATA,
                                        lbSelectedIndex, 0 );
                                    
                if ( IsDlgButtonChecked(hWndDlg, IDC_RB_TASKS) )
                    ShowTaskDetails( (HTASK)handle );
                else
                    ShowModuleDetails( (HMODULE)handle );
            }
            break;
            
        case IDC_LB_DETAILS:
            if ( HIWORD(lParam) == LBN_DBLCLK )
            {
                WORD type, value;
                
                if ( !RetrieveListboxLineTypeAndValue(HWndDetails,
                                                        &type, &value) )
                    break;
                
                switch ( type )
                {
                    case LB_ITEM_HMODULE:
                        ShowModuleDetails( (HMODULE)value ); break;
                    case LB_ITEM_TASK:
                        ShowTaskDetails( (HTASK)value ); break;
                    case LB_ITEM_SEGMENTS:
                        ShowSegmentTableDetails( (HMODULE)value ); break;
                    case LB_ITEM_ENTRY_TABLE:
                        ShowEntryTableDetails( (HMODULE)value ); break;
                    case LB_ITEM_RESOURCES:
                        ShowResourceDetails( (HMODULE)value ); break;
                    case LB_ITEM_RESIDENT_NAMES:
                        ShowResidentNamesDetails( (HMODULE)value ); break;
                    case LB_ITEM_NONRESIDENT_NAMES:
                        ShowNonResidentNamesDetails( (HMODULE)value ); break;
                }
            }
            break;
    }
    return;
}

void Handle_WM_INITDIALOG(HWND hWndDlg)
{
    HWndMainList = GetDlgItem(hWndDlg, IDC_LB_MAIN_LIST);
    HWndDetails = GetDlgItem(hWndDlg, IDC_LB_DETAILS);
    HWndDetailsDescription = GetDlgItem(hWndDlg, IDC_DETAILS_TYPE );
    
    CheckDlgButton(hWndDlg, IDC_RB_TASKS, 1);
    
    if ( IsDlgButtonChecked(hWndDlg, IDC_RB_TASKS) )
        UpdateTaskList();   
}

//
// Dialog proc for the main dialog
//
BOOL CALLBACK _export Show16DlgProc(HWND hWndDlg, UINT msg,
                                     WPARAM wParam, LPARAM lParam)
{
    switch ( msg )
    {
        case WM_COMMAND:
            Handle_WM_COMMAND(hWndDlg, wParam, lParam); return TRUE;
        case WM_INITDIALOG:
            Handle_WM_INITDIALOG(hWndDlg); return TRUE;
        case WM_CLOSE:
            EndDialog(hWndDlg, 0); return FALSE;
    }
    return FALSE;
}

void UpdateTaskList(void)
{
    LPTDB lpTDB = 0;
    HTASK headHTask;
    char szModName[10];
    char szBuffer[64];
    unsigned lbIndex = 0;
    
    SendMessage(HWndMainList, LB_RESETCONTENT, 0, 0);
    
    GetCurrentTask();
    __asm mov [headHTask], DX

    lpTDB = MAKELP( headHTask, 0 );

    while ( lpTDB )
    {
        memcpy( szModName, lpTDB->TDB_ModName, 8 );
        szModName[8] = 0;

        wsprintf( szBuffer, "%s %s", szModName,
            lpTDB->TDB_flags & TDB_FLAGS_WIN32 ? "(Win32)" : "" );

        SendMessage( HWndMainList, LB_ADDSTRING, 0, (LPARAM)szBuffer );
        SendMessage( HWndMainList, LB_SETITEMDATA,
                        lbIndex, (LPARAM)SELECTOROF(lpTDB) );
        lbIndex++;
        
        lpTDB = MAKELP( lpTDB->TDB_next, 0 );
    }
    
    // Set selection to first task in list, and show its details
    SendMessage( HWndMainList, LB_SETCURSEL, 0, 0 );
    PostMessage( GetParent(HWndMainList), WM_COMMAND, IDC_LB_MAIN_LIST,
                    MAKELPARAM(HWndMainList, LBN_SELCHANGE) );
}

void UpdateModuleList(void)
{
    LPMODULE lpMODULE = 0;
    HMODULE headHModule;
    char szBuffer[32];
    LPSTR lpszModuleName;
    unsigned lbIndex = 0;
    WORD selector;
    
    SendMessage(HWndMainList, LB_RESETCONTENT, 0, 0);

    //
    // First we're going to walk the regular 16 bit module list.
    //
    GetModuleHandle("KERNEL");   // There will always be a "KERNEL" module
    __asm mov [headHModule], DX

    lpMODULE = MAKELP( headHModule, 0 );
    while ( lpMODULE )
    {
        lpszModuleName = MAKELP(SELECTOROF(lpMODULE),
                                lpMODULE->ne_resNamesTab );

        strncpy( szBuffer, lpszModuleName + 1, *lpszModuleName );
        szBuffer[ *lpszModuleName ] = 0;
        
        SendMessage( HWndMainList, LB_ADDSTRING, 0, (LPARAM)szBuffer );
        SendMessage( HWndMainList, LB_SETITEMDATA,
                        lbIndex, (LPARAM)SELECTOROF(lpMODULE) );
        lbIndex++;

        lpMODULE = MAKELP( lpMODULE->ne_npNextExe, 0 );
    }

    //
    // Now, let's go find the pseudo 16-bit modules created for Win32
    // EXEs and DLLs.
    for ( selector = 7; ; selector += 8 )
    {
        if ( IsA32BitHMODULE(selector) )
        {
            GetModuleName( selector, szBuffer, sizeof(szBuffer) );
            lbprintf( HWndMainList, "%s (Win32)", szBuffer );
            SendMessage( HWndMainList, LB_SETITEMDATA, lbIndex,
                        (LPARAM)selector );
                lbIndex++;
        }
        if ( selector == 0xFFFF )
            break;
    }

    // Set selection to first module in list, and show its details
    SendMessage( HWndMainList, LB_SETCURSEL, 0, 0 );
    PostMessage( GetParent(HWndMainList), WM_COMMAND, IDC_LB_MAIN_LIST,
                    MAKELPARAM(HWndMainList, LBN_SELCHANGE) );
}

BYTE HookedInts[7] = {0, 2, 4, 6, 7, 0x3E, 0x75};

WORD_FLAGS ErrorModeFlags[] = 
{
{ SEM_FAILCRITICALERRORS, "FailCriticalErrors" },
{ SEM_NOGPFAULTERRORBOX, "NoGPFaultErrorBox" },
{ SEM_NOOPENFILEERRORBOX, "NoOpenFileErrorBox" },
};

void ShowTaskDetails(HTASK hTask)
{
    LPTDB lpTDB = MAKELP( hTask, 0 );
    char szBuffer[260];
    unsigned i;
    
    if ( !IsTask(hTask) )
        return;
    
    wsprintf(szBuffer, "Task: %04X (%s)", hTask, GetTaskModuleName(hTask) );
    SendMessage( HWndDetailsDescription, WM_SETTEXT, 0, (LPARAM)szBuffer );
    SendMessage(HWndDetails, LB_RESETCONTENT, 0, 0);

    lbprintf( HWndDetails, "ModuleName: %.8s", lpTDB->TDB_ModName );
        
    GetModuleFileName( lpTDB->TDB_HMODULE, szBuffer, sizeof(szBuffer) );
    lbprintf( HWndDetails, "+ HMODULE: %04Xh %s",
                lpTDB->TDB_HMODULE, szBuffer ); 
    RecordListboxLineTypeAndValue(  HWndDetails, LB_ITEM_HMODULE,
                                    lpTDB->TDB_HMODULE );
    lbprintf( HWndDetails, "HINSTANCE: %04X", lpTDB->TDB_HInstance );

    lbprintf( HWndDetails, "CurrentDir: %c:%s",
                'A' + lpTDB->TDB_Drive - 0x80,
                lpTDB->TDB_current_directory );

    lbprintf( HWndDetails, "ExpWinVer: %u.%02u",
            HIBYTE(lpTDB->TDB_ExpWinVer), LOBYTE(lpTDB->TDB_ExpWinVer) );

    lbprintf( HWndDetails, "PSP: %04X", lpTDB->TDB_PSP );

    lbprintf( HWndDetails, "DOS DTA: %04X:%04X",
                    SELECTOROF(lpTDB->TDB_DTA),
                    OFFSETOF(lpTDB->TDB_DTA) );

    lbprintf( HWndDetails, "Queue: %04X", lpTDB->TDB_Queue );
    lbprintf( HWndDetails, "+ Parent: %04X %s",
        lpTDB->TDB_Parent, GetTaskModuleName(lpTDB->TDB_Parent) );
    RecordListboxLineTypeAndValue(  HWndDetails, LB_ITEM_TASK,
                                    lpTDB->TDB_Parent );
    
    lbprintf( HWndDetails, "TaskFlags: %04X", lpTDB->TDB_flags );
    if ( lpTDB->TDB_flags & TDB_FLAGS_WIN32 )
        lbprintf( HWndDetails, "    Win32 task" );
    if ( lpTDB->TDB_flags & TDB_FLAGS_WINOLDAP )
        lbprintf( HWndDetails, "    Winoldap task (DOS)" );
        
    lbprintf( HWndDetails, "ErrMode: %04X", lpTDB->TDB_ErrMode );
    for ( i=0; i < sizeof(ErrorModeFlags)/sizeof(WORD_FLAGS); i++ )
        if ( ErrorModeFlags[i].value & lpTDB->TDB_ErrMode )
            lbprintf( HWndDetails, "    %s", ErrorModeFlags[i].name );

    lbprintf( HWndDetails, "CompatFlags: %04X", lpTDB->TDB_CompatFlags );
    lbprintf( HWndDetails, "FS Selector: %04X", lpTDB->TDB_FS_selector );
    lbprintf( HWndDetails, "Ring 3 thread database: %08lX",
                            lpTDB->TDB_ring3_thread_db );
    lbprintf( HWndDetails, "Thunk SS: %04X", lpTDB->TDB_thunk_stack_ss );

    lbprintf( HWndDetails, "MakeProcInstance selector: %04X",
                lpTDB->TDB_MPI_Sel );
                
    lbprintf( HWndDetails, "SS:SP: %04X:%04X",
                lpTDB->TDB_taskSS, lpTDB->TDB_taskSP );

    lbprintf( HWndDetails, "FP CtrlWord: %04X", lpTDB->TDB_FCW );
    lbprintf( HWndDetails, "SigAction: %04X", lpTDB->TDB_SigAction );
    lbprintf( HWndDetails, "USER SignalProc: %04X:%04X",
                    SELECTOROF(lpTDB->TDB_USignalProc),
                    OFFSETOF(lpTDB->TDB_USignalProc) );
    lbprintf( HWndDetails, "GlobalNotify Proc: %04X:%04X",
                    SELECTOROF(lpTDB->TDB_GNotifyProc),
                    OFFSETOF(lpTDB->TDB_GNotifyProc) );
                
    for ( i=0; i < 7; i++ )
        lbprintf( HWndDetails, "INT %Xh handler: %04X:%04X",
                    HookedInts[i],
                    SELECTOROF(lpTDB->TDB_INTVECS[i]),
                    OFFSETOF(lpTDB->TDB_INTVECS[i]) );

    lbprintf( HWndDetails, "Events: %u", lpTDB->TDB_nEvents );
    lbprintf( HWndDetails, "Priority: %u", lpTDB->TDB_priority );

    // All these fields should be 0.  If they aren't, we want to know
    // about them PRONTO!  There may be useful information in them.
    assert( !lpTDB->TDB_thread_ordinal );
    assert( !lpTDB->TDB_thread_next );
    assert( !lpTDB->TDB_thread_tdb );
    assert( !lpTDB->TDB_thread_list );
    assert( !lpTDB->TDB_thread_free );
    assert( !lpTDB->TDB_thread_count );
    assert( !lpTDB->TDB_ASignalProc );
    assert( !lpTDB->TDB_filler[0] );
    assert( !lpTDB->TDB_filler[1] );
    assert( !lpTDB->TDB_filler[2] );
    assert( !lpTDB->TDB_Directory[0] );
    assert( !lpTDB->TDB_unused1 );
    assert( !lpTDB->TDB_unused2 );
}

WORD_FLAGS ModuleFlags[] = 
{
{ MODFLAGS_DLL,         "DLL" },
{ MODFLAGS_CALL_WEP,    "CallWep" },
{ 0x1000,               "0x1000" },
{ MODFLAGS_SELF_LOADING,"SelfLoading" },
{ 0x0400,               "0x0400" },
{ 0x0080,               "0x0080" },
{ 0x0040,               "ImplicitLoad" },
{ 0x0020,               "0x0020" },
{ MODFLAGS_WIN32,       "Win32" },
{ 0x0008,               "0x0008" },
{ 0x0004,               "0x0004" },
{ MODFLAGS_AUTODATA,    "PerProcessData" },
{ MODFLAGS_SINGLEDATA,  "SharedData" } 
};

void ShowModuleDetails(HMODULE hModule)
{
    LPMODULE lpMODULE = MAKELP( hModule, 0 );
    char szBuffer[260];
    OFSTRUCT_EXT FAR * lpofstruct;
    unsigned i;
    
    if ( !IsModule(hModule) )
        return;

    wsprintf(szBuffer, "Module: %04X", hModule);
    SendMessage( HWndDetailsDescription, WM_SETTEXT, 0, (LPARAM)szBuffer );
    SendMessage(HWndDetails, LB_RESETCONTENT, 0, 0);
    
    lpofstruct = MAKELP( hModule, lpMODULE->ne_npFileInfo );
    lbprintf( HWndDetails, "Filename: %s", lpofstruct->szPathName );
    lbprintf( HWndDetails, "+ Segments: %Xh", lpMODULE->ne_cseg );
    RecordListboxLineTypeAndValue(  HWndDetails, LB_ITEM_SEGMENTS, hModule );

    lbprintf(HWndDetails, "+ Resources: %04Xh", lpMODULE->ne_rsrcTab);
    RecordListboxLineTypeAndValue( HWndDetails, LB_ITEM_RESOURCES, hModule );

    lbprintf(HWndDetails, "+ ResidentNames: %04Xh", lpMODULE->ne_resNamesTab);
    RecordListboxLineTypeAndValue(HWndDetails, LB_ITEM_RESIDENT_NAMES,
                                    hModule );

    lbprintf(HWndDetails, "+ Non-ResidentNames Offs: %lXh  size: %04X",
            lpMODULE->ne_nonResNamesTab, lpMODULE->ne_cbNonResNamesTab );
    RecordListboxLineTypeAndValue(HWndDetails, LB_ITEM_NONRESIDENT_NAMES,
                                    hModule );

    lbprintf( HWndDetails, "+ EntryTableOffs: %04Xh",
                lpMODULE->ne_npEntryTable );
    RecordListboxLineTypeAndValue(HWndDetails, LB_ITEM_ENTRY_TABLE, hModule );

    lbprintf( HWndDetails, "Usage: %Xh", lpMODULE->ne_usage );
    lbprintf( HWndDetails, "Flags: %02Xh", lpMODULE->ne_flags );
    for ( i=0; i < sizeof(ModuleFlags)/sizeof(WORD_FLAGS); i++ )
        if ( ModuleFlags[i].value & lpMODULE->ne_flags )
            lbprintf( HWndDetails, "    %s", ModuleFlags[i].name );
        
    lbprintf( HWndDetails, "ExpWinVer: %u.%02u",
            HIBYTE(lpMODULE->ne_expver), LOBYTE(lpMODULE->ne_expver) );
    lbprintf( HWndDetails, "DGROUP index: %Xh", lpMODULE->ne_autodata );
    lbprintf( HWndDetails, "Local heap size: %Xh bytes", lpMODULE->ne_heap );
    lbprintf( HWndDetails, "Stack size: %Xh bytes", lpMODULE->ne_stack );
    lbprintf( HWndDetails, "Entry point: %04X:%04X",
                    SELECTOROF(lpMODULE->ne_csip),
                    OFFSETOF(lpMODULE->ne_csip) );
    lbprintf( HWndDetails, "Initial SS:SP: %04X:%04X",

⌨️ 快捷键说明

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