Changeset 2854


Ignore:
Timestamp:
Nov 3, 2006, 4:39:12 AM (19 years ago)
Author:
bird
Message:

Hacking away on the PE module interpreter.

Location:
trunk/kLdr
Files:
2 added
6 edited

Legend:

Unmodified
Added
Removed
  • trunk/kLdr/Makefile.kmk

    r2846 r2854  
    100100        kLdrRdrFile.c \
    101101        kLdrMod.c \
    102         kLdrModLX.c
     102        kLdrModLX.c \
     103        kLdrModPE.c
    103104kLdr_SOURCES.os2 = \
    104105        kLdr-os2.def \
  • trunk/kLdr/kLdr.h

    r2851 r2854  
    341341    /** Variable free to use for the kLdr user. */
    342342    void           *pvUser;
    343     /** The segment name. */
    344     const char     *pszName;
     343    /** The segment name. (Might not be zero terminated!) */
     344    const char     *pchName;
     345    /** The length of the segment name. */
     346    uint32_t        cchName;
    345347    /** The size of the segment. */
    346348    KLDRSIZE        cb;
    347     /** The link time load address. */
     349    /** The required segment alignment. */
     350    KLDRADDR        Alignment;
     351    /** The link address.
     352     * Set to NIL_KLDRADDR if the segment isn't supposed to be mapped. */
    348353    KLDRADDR        LinkAddress;
    349354    /** The address the segment was mapped at by kLdrModMap().
     
    569574     * Not meant for calling directly thru! */
    570575    PCKLDRMODOPS        pOps;
     576    /** Pointer to the read instance. (Can be NULL after kLdrModDone().)*/
     577    PKLDRRDR            pRdr;
    571578    /** The module data. */
    572579    void               *pvData;
     
    617624/** Weak symbol. */
    618625#define KLDRSYMKIND_WEAK                    0x00000100
     626/** Forwarder symbol. */
     627#define KLDRSYMKIND_FORWARDER               0x00000200
    619628/** @} */
    620629
     
    691700
    692701int     kLdrModQuerySymbol(PKLDRMOD pMod, const void *pvBits, KLDRADDR BaseAddress, uint32_t uSymbol,
    693                            const char *pszSymbol, PKLDRADDR puValue, uint32_t *pfKind);
    694 int     kLdrModEnumSymbols(PKLDRMOD pMod, uint32_t fFlags, const void *pvBits, KLDRADDR BaseAddress,
    695                            PFNKLDRMODENUMSYMS pfnCallback, void *pvUser);
     702                           const char *pszSymbol, PFNKLDRMODGETIMPORT pfnGetForwarder, void *pvUser,
     703                           PKLDRADDR puValue, uint32_t *pfKind);
     704int     kLdrModEnumSymbols(PKLDRMOD pMod, const void *pvBits, KLDRADDR BaseAddress,
     705                           uint32_t fFlags, PFNKLDRMODENUMSYMS pfnCallback, void *pvUser);
    696706int     kLdrModGetImport(PKLDRMOD pMod, void *pvBits, uint32_t iImport, const char *pszName, size_t cchName);
    697707int32_t kLdrModNumberOfImports(PKLDRMOD pMod, void *pvBits);
     
    761771    /** @copydoc kLdrModQuerySymbol */
    762772    int (* pfnQuerySymbol)(PKLDRMOD pMod, const void *pvBits, KLDRADDR BaseAddress, uint32_t uSymbol,
    763                            const char *pszSymbol, PKLDRADDR puValue, uint32_t *pfKind);
     773                           const char *pszSymbol, PFNKLDRMODGETIMPORT pfnGetForwarder, void *pvUser,
     774                           PKLDRADDR puValue, uint32_t *pfKind);
    764775    /** @copydoc kLdrModEnumSymbols */
    765     int (* pfnEnumSymbols)(PKLDRMOD pMod, uint32_t fFlags, const void *pvBits, KLDRADDR BaseAddress,
     776    int (* pfnEnumSymbols)(PKLDRMOD pMod, const void *pvBits, KLDRADDR BaseAddress, uint32_t fFlags,
    766777                           PFNKLDRMODENUMSYMS pfnCallback, void *pvUser);
    767778    /** @copydoc kLdrModGetImport */
     
    10161027/** Symbol not found. */
    10171028#define KLDR_ERR_SYMBOL_NOT_FOUND                           (KLDR_ERR_BASE + 46)
    1018 
     1029/** A forward symbol was encountered but the caller didn't provide any means to resolve it. */
     1030#define KLDR_ERR_FORWARDER_SYMBOL                           (KLDR_ERR_BASE + 47)
    10191031/** Encountered a bad fixup. */
    10201032#define KLDR_ERR_BAD_FIXUP                                  (KLDR_ERR_BASE + 48)
    1021 
    10221033/** A memory allocation failed. */
    1023 #define KLDR_ERR_NO_MEMORY                                  (KLDR_ERR_BASE + 64)
     1034#define KLDR_ERR_NO_MEMORY                                  (KLDR_ERR_BASE + 49)
     1035
     1036
     1037/** @name kLdrModPE status codes
     1038 * @{ */
     1039#define KLDR_ERR_BASE_PE                                    (KLDR_ERR_BASE + 96)
     1040/** The machine isn't supported by the interpreter. */
     1041#define KLDR_ERR_PE_UNSUPPORTED_MACHINE                     (KLDR_ERR_BASE_PE + 0)
     1042/** The file handler isn't valid. */
     1043#define KLDR_ERR_PE_BAD_FILE_HEADER                         (KLDR_ERR_BASE_PE + 1)
     1044/** The the optional headers isn't valid. */
     1045#define KLDR_ERR_PE_BAD_OPTIONAL_HEADER                     (KLDR_ERR_BASE_PE + 2)
     1046/** One of the section headers aren't valid. */
     1047#define KLDR_ERR_PE_BAD_SECTION_HEADER                      (KLDR_ERR_BASE_PE + 3)
     1048/** Bad forwarder entry. */
     1049#define KLDR_ERR_PE_BAD_FORWARDER                           (KLDR_ERR_BASE_PE + 4)
     1050/** Forwarder module not found in the import descriptor table. */
     1051#define KLDR_ERR_PE_FORWARDER_IMPORT_NOT_FOUND              (KLDR_ERR_BASE_PE + 5)
     1052/** @} */
     1053
    10241054
    10251055/** @} */
  • trunk/kLdr/kLdrDyldMod.c

    r2850 r2854  
    884884                                             PKLDRADDR puValue, uint32_t *pfKind, void *pvUser)
    885885{
     886    static int s_cRecursiveCalls = 0;
     887    PKLDRDYLDMOD pDyldMod = (PKLDRDYLDMOD)pvUser;
    886888    int rc;
    887     PKLDRDYLDMOD pDyldMod = (PKLDRDYLDMOD)pvUser;
     889
     890    /* guard against too deep forwarder recursion. */
     891    if (s_cRecursiveCalls >= 5)
     892        return KLDR_ERR_TOO_LONG_FORWARDER_CHAIN;
     893    s_cRecursiveCalls++;
    888894
    889895    if (iImport != NIL_KLDRMOD_IMPORT)
     
    901907
    902908        rc = kLdrModQuerySymbol(pPrereqMod->pMod, NULL, KLDRMOD_BASEADDRESS_MAP,
    903                                 uSymbol, pszSymbol, puValue, pfKind);
     909                                uSymbol, pszSymbol, kldrDyldModFixupGetImportCallback, pPrereqMod, puValue, pfKind);
    904910        if (rc)
    905911        {
     
    923929            KLDRADDR uValue;
    924930            rc = kLdrModQuerySymbol(pBindMod->pMod, NULL, KLDRMOD_BASEADDRESS_MAP,
    925                                     uSymbol, pszSymbol, &uValue, &fKind);
     931                                    uSymbol, pszSymbol, kldrDyldModFixupGetImportCallback, pPrereqMod, &uValue, &fKind);
    926932            if (    !rc
    927933                &&  (   !fFound
     
    950956    }
    951957
     958    s_cRecursiveCalls--;
    952959    return rc;
    953960}
     
    12051212
    12061213    rc = kLdrModQuerySymbol(pMod->pMod, NULL, KLDRMOD_BASEADDRESS_MAP,
    1207                             uSymbolOrdinal, pszSymbolName, &uValue, &fKind);
     1214                            uSymbolOrdinal, pszSymbolName, kldrDyldModFixupGetImportCallback, pPrereqMod,
     1215                            &uValue, &fKind);
    12081216    if (!rc)
    12091217    {
  • trunk/kLdr/kLdrHlp.c

    r2846 r2854  
    527527
    528528/**
     529 * Get the pointer to the filename part of the name.
     530 *
     531 * @returns Pointer to where the filename starts within the string pointed to by pszFilename.
     532 * @returns Pointer to the terminator char if no filename.
     533 * @param   pszFilename     The filename to parse.
     534 */
     535char   *kldrHlpGetFilename(const char *pszFilename)
     536{
     537    const char *pszLast = NULL;
     538    for (;;)
     539    {
     540        char ch = *pszFilename;
     541#if defined(__OS2__) || defined(__WIN__)
     542        if (ch == '/' || ch == '\\' || ch == ':')
     543        {
     544            while ((ch = *++pszFilename) == '/' || ch == '\\' || ch == ':')
     545                /* nothing */;
     546            pszLast = pszFilename;
     547        }
     548#else
     549        if (ch == '/')
     550        {
     551            while ((ch = *++pszFilename) == '/')
     552                /* betsuni */;
     553            pszLast = pszFilename;
     554        }
     555#endif
     556        if (!ch)
     557            return (char *)(pszLast ? pszLast : pszFilename);
     558        pszFilename++;
     559    }
     560}
     561
     562
     563/**
     564 * Gets the filename suffix.
     565 *
     566 * @returns Pointer to where the suffix starts within the string pointed to by pszFilename.
     567 * @returns Pointer to the terminator char if no suffix.
     568 * @param   pszFilename     The filename to parse.
     569 */
     570char   *kldrHlpGetSuff(const char *pszFilename)
     571{
     572    const char *pszDot = NULL;
     573    pszFilename = kldrHlpGetFilename(pszFilename);
     574    for (;;)
     575    {
     576        char ch = *pszFilename;
     577        if (ch == '.')
     578        {
     579            while ((ch = *++pszFilename) == '.')
     580                /* nothing */;
     581            if (ch)
     582                pszDot = pszFilename - 1;
     583        }
     584        if (!ch)
     585            return (char *)(pszDot ? pszDot : pszFilename);
     586        pszFilename++;
     587    }
     588}
     589
     590
     591/**
     592 * Gets the filename extention.
     593 *
     594 * @returns Pointer to where the extension starts within the string pointed to by pszFilename.
     595 * @returns Pointer to the terminator char if no extension.
     596 * @param   pszFilename     The filename to parse.
     597 */
     598char   *kldrHlpGetExt(const char *pszFilename)
     599{
     600    char *psz = kldrHlpGetSuff(pszFilename);
     601    return *psz ? psz + 1 : psz;
     602}
     603
     604
     605
     606/**
    529607 * Terminate the process.
    530608 *
     
    717795#endif
    718796
     797
     798int     kLdrHlpMemIComp(const void *pv1, const void *pv2, size_t cb)
     799{
     800    const uint8_t *pb1 = (const uint8_t *)pv1;
     801    const uint8_t *pb2 = (const uint8_t *)pv2;
     802    while (cb)
     803    {
     804        if (*pb1 != *pb2)
     805        {
     806            const uint8_t u1 = *pb1 >= 'a' && *pb1 <= 'z' ? *pb1 - 'a' : *pb1;
     807            const uint8_t u2 = *pb2 >= 'a' && *pb2 <= 'z' ? *pb2 - 'a' : *pb2;
     808            if (u1 != u2)
     809                return (int)*pb1 - (int)*pb2;
     810        }
     811        pb1++;
     812        pb2++;
     813    }
     814    return 0;
     815}
     816
     817
     818int     kLdrHlpStrIComp(const char *pv1, const char *pv2)
     819{
     820    const uint8_t *pb1 = (const uint8_t *)pv1;
     821    const uint8_t *pb2 = (const uint8_t *)pv2;
     822    for (;;)
     823    {
     824        if (*pb1 != *pb2)
     825        {
     826            const uint8_t u1 = *pb1 >= 'a' && *pb1 <= 'z' ? *pb1 - 'a' : *pb1;
     827            const uint8_t u2 = *pb2 >= 'a' && *pb2 <= 'z' ? *pb2 - 'a' : *pb2;
     828            if (u1 != u2)
     829                return (int)*pb1 - (int)*pb2;
     830        }
     831        if (!*pb1)
     832            break;
     833        pb1++;
     834        pb2++;
     835    }
     836    return 0;
     837}
     838
  • trunk/kLdr/kLdrHlp.h

    r2851 r2854  
    7474/** strchr */
    7575# define kLdrHlpStrChr(a, b)   __builtin_strchr(a, b)
     76/** strcmp */
     77# define kLdrHlpStrComp(a, b)  __builtin_strcmp(a, b)
    7678/** strlen */
    7779# define kLdrHlpStrLen(a)      __builtin_strlen(a)
     
    8991# include <string.h>
    9092# include <malloc.h>
    91 # pragma intrinsic(memcmp, memcpy, memset, strlen, __debugbreak)
     93# pragma intrinsic(memcmp, memcpy, memset, strcmp, strlen, __debugbreak)
    9294/** memchr */
    9395# define kLdrHlpMemChr_needed
     
    98100/** memset */
    99101# define kLdrHlpMemSet(a,b,c)  memset(a,b,c)
     102/** strcmp */
     103# define kLdrHlpStrComp(a, b)  strcmp(a, b)
    100104/** strlen */
    101105# define kLdrHlpStrLen(a)      strlen(a)
     
    118122void   *kLdrHlpMemChr(const void *pv, int ch, size_t cb);
    119123#endif
     124int     kLdrHlpMemIComp(const void *pv1, const void *pv2, size_t cb);
     125int     kLdrHlpStrIComp(const char *pv1, const char *pv2);
     126
    120127
    121128#if (!defined(kLdrHlpMemChr) && !defined(kLdrHlpStrChr_needed))\
     
    148155int     kldrHlpGetEnv(const char *pszVar, char *pszVal, size_t *pcchVal);
    149156int     kldrHlpGetEnvUZ(const char *pszVar, size_t *pcb);
     157char   *kldrHlpGetFilename(const char *pszFilename);
     158char   *kldrHlpGetExt(const char *pszFilename);
    150159void    kldrHlpExit(int rc);
    151160void    kldrHlpSleep(unsigned cMillies);
  • trunk/kLdr/kLdrMod.c

    r2851 r2854  
    22/** @file
    33 *
    4  * kLdr - The Dynamic Loader, The module interpreter.
     4 * kLdr - The Module Interpreter.
    55 *
    66 * Copyright (c) 2006 knut st. osmundsen <bird-kbuild-src@anduin.net>
     
    262262 * @param   uSymbol         The symbol ordinal. (optional)
    263263 * @param   pszSymbol       The symbol name. (optional)
     264 * @param   pfnGetForwarder The callback to use when resolving a forwarder symbol. This is optional
     265 *                          and if not specified KLDR_ERR_FORWARDER is returned instead.
     266 * @param   pvUser          The user argument for the pfnGetForwarder callback.
    264267 * @param   puValue         Where to store the symbol value. (optional)
    265268 * @param   pfKind          Where to store the symbol kind. (optional)
    266269 */
    267270int     kLdrModQuerySymbol(PKLDRMOD pMod, const void *pvBits, KLDRADDR BaseAddress, uint32_t uSymbol,
    268                            const char *pszSymbol, PKLDRADDR puValue, uint32_t *pfKind)
     271                           const char *pszSymbol, PFNKLDRMODGETIMPORT pfnGetForwarder, void *pvUser,
     272                           PKLDRADDR puValue, uint32_t *pfKind)
    269273{
    270274    KLDRMOD_VALIDATE(pMod);
     
    275279    if (pfKind)
    276280        *pfKind = 0;
    277     return pMod->pOps->pfnDestroy(pMod);
     281    return pMod->pOps->pfnQuerySymbol(pMod, pvBits, BaseAddress, uSymbol, pszSymbol, pfnGetForwarder, pvUser, puValue, pfKind);
    278282}
    279283
     
    284288 * @returns 0 on success and non-zero a status code on failure.
    285289 * @param   pMod            The module which symbols should be enumerated.
    286  * @param   fFlags          The enumeration flags. A combination of the KLDRMOD_ENUM_SYMS_FLAGS_* \#defines.
    287290 * @param   pvBits          Optional pointer to bits returned by kLdrModGetBits() currently located at BaseAddress.
    288291 *                          This can be used by some module interpreters to reduce memory consumption.
     
    290293 *                          There are two special values that could be can:
    291294 *                              KLDRMOD_BASEADDRESS_LINK and KLDRMOD_BASEADDRESS_MAP.
     295 * @param   fFlags          The enumeration flags. A combination of the KLDRMOD_ENUM_SYMS_FLAGS_* \#defines.
    292296 * @param   pfnCallback     The enumeration callback function.
    293297 * @param   pvUser          The user argument to the callback function.
    294298 */
    295 int     kLdrModEnumSymbols(PKLDRMOD pMod, uint32_t fFlags, const void *pvBits, KLDRADDR BaseAddress,
     299int     kLdrModEnumSymbols(PKLDRMOD pMod, const void *pvBits, KLDRADDR BaseAddress, uint32_t fFlags,
    296300                           PFNKLDRMODENUMSYMS pfnCallback, void *pvUser)
    297301{
    298302    KLDRMOD_VALIDATE(pMod);
    299303    KLDRHLP_VALIDATE_FLAGS(fFlags, KLDRMOD_ENUM_SYMS_FLAGS_ALL);
    300     return pMod->pOps->pfnEnumSymbols(pMod, fFlags, pvBits, BaseAddress, pfnCallback, pvUser);
     304    return pMod->pOps->pfnEnumSymbols(pMod, pvBits, BaseAddress, fFlags, pfnCallback, pvUser);
    301305}
    302306
Note: See TracChangeset for help on using the changeset viewer.