VirtualBox

Changeset 75166 in vbox


Ignore:
Timestamp:
Oct 29, 2018 9:01:59 PM (6 years ago)
Author:
vboxsync
Message:

DBGFPlugInOS2: Added some code for walking the MTE list. (Though this was done a while ago,)

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Debugger/DBGPlugInOS2.cpp

    r73460 r75166  
    7171/** Pointer to the OS/2 guest OS digger instance data. */
    7272typedef DBGDIGGEROS2 *PDBGDIGGEROS2;
     73
     74/**
     75 * 32-bit OS/2 loader module table entry.
     76 */
     77typedef struct LDRMTE
     78{
     79    uint16_t    mte_flags2;
     80    uint16_t    mte_handle;
     81    uint32_t    mte_swapmte;    /**< Pointer to LDRSMTE. */
     82    uint32_t    mte_link;       /**< Pointer to next LDRMTE. */
     83    uint32_t    mte_flags1;
     84    uint32_t    mte_impmodcnt;
     85    uint16_t    mte_sfn;
     86    uint16_t    mte_usecnt;
     87    char        mte_modname[8];
     88    uint32_t    mte_RAS;        /**< added later */
     89    uint32_t    mte_modver;     /**< added even later. */
     90} LDRMTE;
     91
     92/**
     93 * 32-bit OS/2 swappable module table entry.
     94 */
     95typedef struct LDRSMTE
     96{
     97    uint32_t    smte_mpages;      /**< module page count. */
     98    uint32_t    smte_startobj;    /**< Entrypoint segment number. */
     99    uint32_t    smte_eip;         /**< Entrypoint offset value. */
     100    uint32_t    smte_stackobj;    /**< Stack segment number. */
     101    uint32_t    smte_esp;         /**< Stack offset value*/
     102    uint32_t    smte_pageshift;   /**< Page shift value. */
     103    uint32_t    smte_fixupsize;   /**< Size of the fixup section. */
     104    uint32_t    smte_objtab;      /**< Pointer to LDROTE array. */
     105    uint32_t    smte_objcnt;      /**< Number of segments. */
     106    uint32_t    smte_objmap;      /**< Address of the object page map. */
     107    uint32_t    smte_itermap;     /**< File offset of the iterated data map*/
     108    uint32_t    smte_rsrctab;     /**< Pointer to resource table? */
     109    uint32_t    smte_rsrccnt;     /**< Number of resource table entries. */
     110    uint32_t    smte_restab;      /**< Pointer to the resident name table. */
     111    uint32_t    smte_enttab;      /**< Possibly entry point table address, if not file offset. */
     112    uint32_t    smte_fpagetab;    /* Offset of Fixup Page Table */
     113    uint32_t    smte_frectab;     /* Offset of Fixup Record Table */
     114    uint32_t    smte_impmod;
     115    uint32_t    smte_impproc;
     116    uint32_t    smte_datapage;
     117    uint32_t    smte_nrestab;
     118    uint32_t    smte_cbnrestab;
     119    uint32_t    smte_autods;
     120    uint32_t    smte_debuginfo;   /* Offset of the debugging info */
     121    uint32_t    smte_debuglen;    /* The len of the debug info in bytes */
     122    uint32_t    smte_heapsize;
     123    uint32_t    smte_path;        /**< Address of full name string. */
     124    uint16_t    smte_semcount;
     125    uint16_t    smte_semowner;
     126    uint32_t    smte_pfilecache;  /** Address of cached data if replace-module is used. */
     127    uint32_t    smte_stacksize;   /**< Stack size for .exe thread 1. */
     128    uint16_t    smte_alignshift;
     129    uint16_t    smte_NEexpver;
     130    uint16_t    smte_pathlen;     /**< Length of smte_path */
     131    uint16_t    smte_NEexetype;
     132    uint16_t    smte_csegpack;
     133    uint8_t     smte_major_os;    /**< added later to lie about OS version */
     134    uint8_t     smte_minor_os;    /**< added later to lie about OS version */
     135} LDRSMTE;
     136
     137typedef struct LDROTE
     138{
     139    uint32_t    ote_size;
     140    uint32_t    ote_base;
     141    uint32_t    ote_flags;
     142    uint32_t    ote_pagemap;
     143    uint32_t    ote_mapsize;
     144    union
     145    {
     146        uint32_t ote_vddaddr;
     147        uint32_t ote_krnaddr;
     148        struct
     149        {
     150            uint16_t ote_selector;
     151            uint16_t ote_handle;
     152        } s;
     153    };
     154} LDROTE;
     155AssertCompileSize(LDROTE, 24);
     156
     157
     158/**
     159 * 32-bit system anchor block segment header.
     160 */
     161typedef struct SAS
     162{
     163    uint8_t     SAS_signature[4];
     164    uint16_t    SAS_tables_data;    /**< Offset to SASTABLES.  */
     165    uint16_t    SAS_flat_sel;       /**< 32-bit kernel DS (flat). */
     166    uint16_t    SAS_config_data;    /**< Offset to SASCONFIG. */
     167    uint16_t    SAS_dd_data;        /**< Offset to SASDD. */
     168    uint16_t    SAS_vm_data;        /**< Offset to SASVM. */
     169    uint16_t    SAS_task_data;      /**< Offset to SASTASK. */
     170    uint16_t    SAS_RAS_data;       /**< Offset to SASRAS. */
     171    uint16_t    SAS_file_data;      /**< Offset to SASFILE. */
     172    uint16_t    SAS_info_data;      /**< Offset to SASINFO. */
     173    uint16_t    SAS_mp_data;        /**< Offset to SASMP. SMP only. */
     174} SAS;
     175#define SAS_SIGNATURE "SAS "
     176
     177typedef struct SASTABLES
     178{
     179    uint16_t    SAS_tbl_GDT;
     180    uint16_t    SAS_tbl_LDT;
     181    uint16_t    SAS_tbl_IDT;
     182    uint16_t    SAS_tbl_GDTPOOL;
     183} SASTABLES;
     184
     185typedef struct SASCONFIG
     186{
     187    uint16_t    SAS_config_table;
     188} SASCONFIG;
     189
     190typedef struct SASDD
     191{
     192    uint16_t    SAS_dd_bimodal_chain;
     193    uint16_t    SAS_dd_real_chain;
     194    uint16_t    SAS_dd_DPB_segment;
     195    uint16_t    SAS_dd_CDA_anchor_p;
     196    uint16_t    SAS_dd_CDA_anchor_r;
     197    uint16_t    SAS_dd_FSC;
     198} SASDD;
     199
     200typedef struct SASVM
     201{
     202    uint32_t    SAS_vm_arena;
     203    uint32_t    SAS_vm_object;
     204    uint32_t    SAS_vm_context;
     205    uint32_t    SAS_vm_krnl_mte;    /**< Flat address of kernel MTE. */
     206    uint32_t    SAS_vm_glbl_mte;    /**< Flat address of global MTE list head pointer variable. */
     207    uint32_t    SAS_vm_pft;
     208    uint32_t    SAS_vm_prt;
     209    uint32_t    SAS_vm_swap;
     210    uint32_t    SAS_vm_idle_head;
     211    uint32_t    SAS_vm_free_head;
     212    uint32_t    SAS_vm_heap_info;
     213    uint32_t    SAS_vm_all_mte;     /**< Flat address of global MTE list head pointer variable. */
     214} SASVM;
     215
     216
     217#pragma pack(1)
     218typedef struct SASTASK
     219{
     220    uint16_t    SAS_task_PTDA;        /**< Current PTDA selector. */
     221    uint32_t    SAS_task_ptdaptrs;    /**< Flat address of process tree root. */
     222    uint32_t    SAS_task_threadptrs;  /**< Flat address array of thread pointer array. */
     223    uint32_t    SAS_task_tasknumber;  /**< Flat address of the TaskNumber variable. */
     224    uint32_t    SAS_task_threadcount; /**< Flat address of the ThreadCount variable. */
     225} SASTASK;
     226#pragma pack()
     227
     228
     229#pragma pack(1)
     230typedef struct SASRAS
     231{
     232    uint16_t    SAS_RAS_STDA_p;
     233    uint16_t    SAS_RAS_STDA_r;
     234    uint16_t    SAS_RAS_event_mask;
     235    uint32_t    SAS_RAS_Perf_Buff;
     236} SASRAS;
     237#pragma pack()
     238
     239typedef struct SASFILE
     240{
     241    uint32_t    SAS_file_MFT;       /**< Handle. */
     242    uint16_t    SAS_file_SFT;       /**< Selector. */
     243    uint16_t    SAS_file_VPB;       /**< Selector. */
     244    uint16_t    SAS_file_CDS;       /**< Selector. */
     245    uint16_t    SAS_file_buffers;   /**< Selector. */
     246} SASFILE;
     247
     248#pragma pack(1)
     249typedef struct SASINFO
     250{
     251    uint16_t    SAS_info_global;    /**< GIS selector. */
     252    uint32_t    SAS_info_local;     /**< Flat address of LIS for current task. */
     253    uint32_t    SAS_info_localRM;
     254    uint16_t    SAS_info_CDIB;      /**< Selector. */
     255} SASINFO;
     256#pragma pack()
     257
     258typedef struct SASMP
     259{
     260    uint32_t    SAS_mp_PCBFirst;        /**< Flat address of PCB head. */
     261    uint32_t    SAS_mp_pLockHandles;    /**< Flat address of lock handles. */
     262    uint32_t    SAS_mp_cProcessors;     /**< Flat address of CPU count variable. */
     263    uint32_t    SAS_mp_pIPCInfo;        /**< Flat address of IPC info pointer variable. */
     264    uint32_t    SAS_mp_pIPCHistory;     /**< Flat address of IPC history pointer. */
     265    uint32_t    SAS_mp_IPCHistoryIdx;   /**< Flat address of IPC history index variable. */
     266    uint32_t    SAS_mp_pFirstPSA;       /**< Flat address of PSA. Added later. */
     267    uint32_t    SAS_mp_pPSAPages;       /**< Flat address of PSA pages. */
     268} SASMP;
     269
    73270
    74271
     
    231428}
    232429
     430/** Buffer shared by dbgdiggerOS2ProcessModule and dbgDiggerOS2Init.*/
     431typedef union DBGDIGGEROS2BUF
     432{
     433    uint8_t             au8[0x2000];
     434    uint16_t            au16[0x2000/2];
     435    uint32_t            au32[0x2000/4];
     436    RTUTF16             wsz[0x2000/2];
     437    char                ach[0x2000];
     438    LDROTE              aOtes[0x2000 / sizeof(LDROTE)];
     439    SAS                 sas;
     440    SASVM               sasvm;
     441    LDRMTE              mte;
     442    LDRSMTE             smte;
     443    LDROTE              ote;
     444} DBGDIGGEROS2BUF;
     445
     446
     447static void dbgdiggerOS2ProcessModule(PUVM pUVM, PDBGDIGGEROS2 pThis, DBGDIGGEROS2BUF *pBuf)
     448{
     449    RT_NOREF(pThis);
     450
     451    /*
     452     * Save the MTE.
     453     */
     454    LDRMTE const Mte = pBuf->mte;
     455
     456    /*
     457     * Try read the swappable MTE.  Save it too.
     458     */
     459    DBGFADDRESS     Addr;
     460    int rc = DBGFR3MemRead(pUVM, 0 /*idCpu*/, DBGFR3AddrFromFlat(pUVM, &Addr, Mte.mte_swapmte), &pBuf->smte, sizeof(pBuf->smte));
     461    if (RT_FAILURE(rc))
     462    {
     463        LogRel(("DbgDiggerOs2: Error reading swap mte @ %RX32: %Rrc\n", Mte.mte_swapmte, rc));
     464        return;
     465    }
     466    LDRSMTE const   SwapMte = pBuf->smte;
     467
     468    /* Ignore empty modules or modules with too many segments. */
     469    if (SwapMte.smte_objcnt == 0 || SwapMte.smte_objcnt > RT_ELEMENTS(pBuf->aOtes))
     470    {
     471        LogRel(("DbgDiggerOs2: Skipping: smte_objcnt= %#RX32\n", SwapMte.smte_objcnt));
     472        return;
     473    }
     474
     475#if 0
     476    /*
     477     * Try read the path name, falling back on module name.
     478     */
     479    rc = VERR_NOT_AVAILABLE;
     480    if (SwapMte.smte_path != 0 && SwapMte.smte_pathlen > 0)
     481    {
     482        uint32_t cbToRead = RT_MIN(SwapMte.smte_path, sizeof(*pBuf) - 1);
     483        rc = DBGFR3MemRead(pUVM, 0 /*idCpu*/, DBGFR3AddrFromFlat(pUVM, &Addr, SwapMte.smte_path), pBuf->ach, cbToRead);
     484        pBuf->ach[cbToRead] = '\0';
     485    }
     486    if (RT_FAILURE(rc))
     487    {
     488        memcpy(pBuf->ach, Mte.mte_modname, sizeof(Mte.mte_modname));
     489        pBuf->ach[sizeof(Mte.mte_modname)] = '\0';
     490        RTStrStripR(pBuf->ach);
     491    }
     492#endif
     493
     494    /*
     495     * Create a simple module.
     496     */
     497    memcpy(pBuf->ach, Mte.mte_modname, sizeof(Mte.mte_modname));
     498    pBuf->ach[sizeof(Mte.mte_modname)] = '\0';
     499    RTStrStripR(pBuf->ach);
     500
     501    RTDBGMOD hDbgMod;
     502    rc = RTDbgModCreate(&hDbgMod, pBuf->ach, 0 /*cbSeg*/, 0 /*fFlags*/);
     503    if (RT_FAILURE(rc))
     504    {
     505        LogRel(("DbgDiggerOs2: RTDbgModCreate failed: %Rrc\n", rc));
     506        return;
     507    }
     508    rc = RTDbgModSetTag(hDbgMod, DIG_OS2_MOD_TAG);
     509    if (RT_SUCCESS(rc))
     510    {
     511        RTDBGAS hAs = DBGFR3AsResolveAndRetain(pUVM, DBGF_AS_KERNEL);
     512        if (hAs != NIL_RTDBGAS)
     513        {
     514            /*
     515             * Read the object table and do the linking of each of them.
     516             */
     517            rc = DBGFR3MemRead(pUVM, 0 /*idCpu*/, DBGFR3AddrFromFlat(pUVM, &Addr, SwapMte.smte_objtab),
     518                               &pBuf->aOtes[0], sizeof(pBuf->aOtes[0]) * SwapMte.smte_objcnt);
     519            if (RT_SUCCESS(rc))
     520            {
     521                uint32_t uRva = 0;
     522                for (uint32_t i = 0; i < SwapMte.smte_objcnt; i++)
     523                {
     524                    char szSegNm[16];
     525                    RTStrPrintf(szSegNm, sizeof(szSegNm), "seg%u", i);
     526                    rc = RTDbgModSegmentAdd(hDbgMod, uRva, pBuf->aOtes[i].ote_size, szSegNm, 0 /*fFlags*/, NULL);
     527                    if (RT_FAILURE(rc))
     528                    {
     529                        LogRel(("DbgDiggerOs2: RTDbgModSegmentAdd failed (i=%u, ote_size=%#x): %Rrc\n",
     530                                i, pBuf->aOtes[i].ote_size, rc));
     531                        break;
     532                    }
     533                    rc = RTDbgAsModuleLinkSeg(hAs, hDbgMod, i, pBuf->aOtes[i].ote_base, RTDBGASLINK_FLAGS_REPLACE /*fFlags*/);
     534                    if (RT_FAILURE(rc))
     535                        LogRel(("DbgDiggerOs2: RTDbgAsModuleLinkSeg failed (i=%u, ote_base=%#x): %Rrc\n",
     536                                i, pBuf->aOtes[i].ote_base, rc));
     537                    uRva += RT_ALIGN_32(pBuf->aOtes[i].ote_size, _4K);
     538                }
     539            }
     540            else
     541                LogRel(("DbgDiggerOs2: Error reading object table @ %#RX32 LB %#zx: %Rrc\n",
     542                        SwapMte.smte_objtab, sizeof(pBuf->aOtes[0]) * SwapMte.smte_objcnt, rc));
     543        }
     544        else
     545            LogRel(("DbgDiggerOs2: DBGFR3AsResolveAndRetain failed\n"));
     546        RTDbgAsRelease(hAs);
     547    }
     548    else
     549        LogRel(("DbgDiggerOs2: RTDbgModSetTag failed: %Rrc\n", rc));
     550    RTDbgModRelease(hDbgMod);
     551
     552}
     553
    233554
    234555/**
     
    240561    Assert(!pThis->fValid);
    241562
    242     union
    243     {
    244         uint8_t             au8[0x2000];
    245         uint16_t            au16[0x2000/2];
    246         uint32_t            au32[0x2000/4];
    247         RTUTF16             wsz[0x2000/2];
    248     }               u;
     563    DBGDIGGEROS2BUF uBuf;
    249564    DBGFADDRESS     Addr;
    250565    int             rc;
     
    253568     * Determine the OS/2 version.
    254569     */
    255     do {
    256         /* Version info is at GIS:15h (major/minor/revision). */
    257         rc = DBGFR3AddrFromSelOff(pUVM, 0 /*idCpu*/, &Addr, pThis->selGIS, 0x15);
    258         if (RT_FAILURE(rc))
    259             break;
    260         rc = DBGFR3MemRead(pUVM, 0 /*idCpu*/, &Addr, u.au32, sizeof(uint32_t));
    261         if (RT_FAILURE(rc))
    262             break;
    263 
    264         pThis->OS2MajorVersion = u.au8[0];
    265         pThis->OS2MinorVersion = u.au8[1];
    266 
    267         pThis->fValid = true;
    268         return VINF_SUCCESS;
    269     } while (0);
    270     return VERR_NOT_SUPPORTED;
     570    /* Version info is at GIS:15h (major/minor/revision). */
     571    rc = DBGFR3AddrFromSelOff(pUVM, 0 /*idCpu*/, &Addr, pThis->selGIS, 0x15);
     572    if (RT_FAILURE(rc))
     573        return VERR_NOT_SUPPORTED;
     574    rc = DBGFR3MemRead(pUVM, 0 /*idCpu*/, &Addr, uBuf.au32, sizeof(uint32_t));
     575    if (RT_FAILURE(rc))
     576        return VERR_NOT_SUPPORTED;
     577
     578    pThis->OS2MajorVersion = uBuf.au8[0];
     579    pThis->OS2MinorVersion = uBuf.au8[1];
     580
     581    pThis->fValid = true;
     582
     583    /*
     584     * Try use SAS to find the module list.
     585     */
     586    rc = DBGFR3AddrFromSelOff(pUVM, 0 /*idCpu*/, &Addr, 0x70, 0x00);
     587    if (RT_SUCCESS(rc))
     588    {
     589        rc = DBGFR3MemRead(pUVM, 0 /*idCpu*/, &Addr, &uBuf.sas, sizeof(uBuf.sas));
     590        if (RT_SUCCESS(rc))
     591        {
     592            rc = DBGFR3AddrFromSelOff(pUVM, 0 /*idCpu*/, &Addr, 0x70, uBuf.sas.SAS_vm_data);
     593            if (RT_SUCCESS(rc))
     594                rc = DBGFR3MemRead(pUVM, 0 /*idCpu*/, &Addr, &uBuf.sasvm, sizeof(uBuf.sasvm));
     595            if (RT_SUCCESS(rc))
     596            {
     597                /*
     598                 * Work the module list.
     599                 */
     600                rc = DBGFR3MemRead(pUVM, 0 /*idCpu*/, DBGFR3AddrFromFlat(pUVM, &Addr, uBuf.sasvm.SAS_vm_all_mte),
     601                                   &uBuf.au32[0], sizeof(uBuf.au32[0]));
     602                if (RT_SUCCESS(rc))
     603                {
     604                    DBGFR3AddrFromFlat(pUVM, &Addr, uBuf.au32[0]);
     605                    while (Addr.FlatPtr != 0 && Addr.FlatPtr != UINT32_MAX)
     606                    {
     607                        rc = DBGFR3MemRead(pUVM, 0 /*idCpu*/, &Addr, &uBuf.mte, sizeof(uBuf.mte));
     608                        if (RT_FAILURE(rc))
     609                            break;
     610                        LogRel(("DbgDiggerOs2: Module @ %#010RX32: %.8s %#x %#x\n", (uint32_t)Addr.FlatPtr,
     611                                uBuf.mte.mte_modname, uBuf.mte.mte_flags1, uBuf.mte.mte_flags2));
     612
     613                        DBGFR3AddrFromFlat(pUVM, &Addr, uBuf.mte.mte_link);
     614                        dbgdiggerOS2ProcessModule(pUVM, pThis, &uBuf);
     615                    }
     616                }
     617            }
     618        }
     619    }
     620
     621    return VINF_SUCCESS;
    271622}
    272623
Note: See TracChangeset for help on using the changeset viewer.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette