VirtualBox

Changeset 40570 in vbox for trunk


Ignore:
Timestamp:
Mar 21, 2012 9:53:57 PM (13 years ago)
Author:
vboxsync
Message:

More of the generation code.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/bldprogs/VBoxTpG.cpp

    r40569 r40570  
    9595    RTLISTANCHOR    ArgHead;
    9696    uint32_t        cArgs;
     97    uint32_t        offArgList;
     98    uint32_t        iProbe;
    9799} VTGPROBE;
    98100typedef VTGPROBE *PVTGPROBE;
     
    154156#ifdef RT_OS_DARWIN
    155157static const char          *g_pszAssembler              = "yasm";
    156 static const char          *g_pszAssemblerFmtOpt        = "--oformat";
     158static const char          *g_pszAssemblerFmtOpt        = "-f";
    157159static const char           g_szAssemblerFmtVal32[]     = "macho32";
    158160static const char           g_szAssemblerFmtVal64[]     = "macho64";
     
    174176#endif
    175177static const char          *g_pszAssemblerFmtVal        = RT_CONCAT(g_szAssemblerFmtVal, ARCH_BITS);
     178static const char          *g_pszAssemblerDefOpt        = "-D";
     179static const char          *g_pszAssemblerIncOpt        = "-I";
     180static char                 g_szAssemblerIncVal[RTPATH_MAX];
     181static const char          *g_pszAssemblerIncVal        = __FILE__ "/../../../include/";
    176182static const char          *g_pszAssemblerOutputOpt     = "-o";
    177183static unsigned             g_cAssemblerOptions         = 0;
     
    212218
    213219
     220/**
     221 * Retrieves the string table offset of the given string table string.
     222 *
     223 * @returns String table offset.
     224 * @param   pszStrTabString     The string table string.
     225 */
     226static uint32_t strtabGetOff(const char *pszStrTabString)
     227{
     228    PVTGSTRING pStr = RT_FROM_MEMBER(pszStrTabString, VTGSTRING, szString[0]);
     229    Assert(pStr->Core.pszString == pszStrTabString);
     230    return pStr->offStrTab;
     231}
     232
     233
    214234static RTEXITCODE generateInvokeAssembler(const char *pszOutput, const char *pszTempAsm)
    215235{
    216     RTPrintf("Todo invoke the assembler\n");
    217     return RTEXITCODE_SKIPPED;
     236    const char     *apszArgs[64];
     237    unsigned        iArg = 0;
     238
     239    apszArgs[iArg++] = g_pszAssembler;
     240    apszArgs[iArg++] = g_pszAssemblerFmtOpt;
     241    apszArgs[iArg++] = g_pszAssemblerFmtVal;
     242    apszArgs[iArg++] = g_pszAssemblerDefOpt;
     243    if (!strcmp(g_pszAssemblerFmtVal, "macho32") || !strcmp(g_pszAssemblerFmtVal, "macho64"))
     244        apszArgs[iArg++] = "ASM_FORMAT_MACHO";
     245    else if (!strcmp(g_pszAssemblerFmtVal, "obj") || !strcmp(g_pszAssemblerFmtVal, "omf"))
     246        apszArgs[iArg++] = "ASM_FORMAT_OMF";
     247    else if (   !strcmp(g_pszAssemblerFmtVal, "win32")
     248             || !strcmp(g_pszAssemblerFmtVal, "win64")
     249             || !strcmp(g_pszAssemblerFmtVal, "pe32")
     250             || !strcmp(g_pszAssemblerFmtVal, "pe64")
     251             || !strcmp(g_pszAssemblerFmtVal, "pe") )
     252        apszArgs[iArg++] = "ASM_FORMAT_PE";
     253    else if (   !strcmp(g_pszAssemblerFmtVal, "elf32")
     254             || !strcmp(g_pszAssemblerFmtVal, "elf64")
     255             || !strcmp(g_pszAssemblerFmtVal, "elf"))
     256        apszArgs[iArg++] = "ASM_FORMAT_ELF";
     257    else
     258        return RTMsgErrorExit(RTEXITCODE_FAILURE, "Unknown assembler format '%s'", g_pszAssemblerFmtVal);
     259    apszArgs[iArg++] = g_pszAssemblerDefOpt;
     260    if (g_cBits == 32)
     261        apszArgs[iArg++] = "ARCH_BITS=32";
     262    else
     263        apszArgs[iArg++] = "ARCH_BITS=64";
     264    apszArgs[iArg++] = g_pszAssemblerDefOpt;
     265    if (g_cBits == 32)
     266        apszArgs[iArg++] = "RT_ARCH_X86";
     267    else
     268        apszArgs[iArg++] = "RT_ARCH_AMD64";
     269    apszArgs[iArg++] = g_pszAssemblerIncOpt;
     270    apszArgs[iArg++] = g_pszAssemblerIncVal;
     271    apszArgs[iArg++] = g_pszAssemblerOutputOpt;
     272    apszArgs[iArg++] = pszOutput;
     273    for (unsigned i = 0; i < g_cAssemblerOptions; i++)
     274        apszArgs[iArg++] = g_apszAssemblerOptions[i];
     275    apszArgs[iArg++] = pszTempAsm;
     276    apszArgs[iArg]   = NULL;
     277
     278    if (g_cVerbosity > 1)
     279    {
     280        RTMsgInfo("Starting assmbler '%s' with arguments:\n",  g_pszAssembler);
     281        for (unsigned i = 0; i < iArg; i++)
     282            RTMsgInfo("  #%02u: '%s'\n",  i, apszArgs[i]);
     283    }
     284
     285    RTPROCESS hProc;
     286    int rc = RTProcCreate(apszArgs[0], apszArgs, RTENV_DEFAULT, RTPROC_FLAGS_SEARCH_PATH, &hProc);
     287    if (RT_FAILURE(rc))
     288        return RTMsgErrorExit(RTEXITCODE_FAILURE, "Failed to start '%s' (assmebler): %Rrc", apszArgs[0], rc);
     289
     290    RTPROCSTATUS Status;
     291    rc = RTProcWait(hProc, RTPROCWAIT_FLAGS_BLOCK, &Status);
     292    if (RT_FAILURE(rc))
     293    {
     294        RTProcTerminate(hProc);
     295        return RTMsgErrorExit(RTEXITCODE_FAILURE, "RTProcWait failed: %Rrc", rc);
     296    }
     297    if (Status.enmReason == RTPROCEXITREASON_SIGNAL)
     298        return RTMsgErrorExit(RTEXITCODE_FAILURE, "The assembler failed: signal %d", Status.iStatus);
     299    if (Status.enmReason == RTPROCEXITREASON_ABEND)
     300        return RTMsgErrorExit(RTEXITCODE_FAILURE, "The assembler failed: abend");
     301    if (   Status.enmReason != RTPROCEXITREASON_NORMAL
     302        || Status.iStatus != 0)
     303        return RTMsgErrorExit(RTEXITCODE_FAILURE, "The assembler failed: exit code %d", Status.iStatus);
     304
     305    return RTEXITCODE_SUCCESS;
    218306}
    219307
     
    315403                    ";\n"
    316404                    "\n"
    317                     "%include \"iprt/asmdefs.h\"\n"
     405                    "%%include \"iprt/asmdefs.mac\"\n"
    318406                    "\n"
    319                     "%ifdef ASM_FORMAT_OMF\n"
    320                     " segment VTGObject public CLASS=VTGObject align=16 use32"
     407                    "\n"
     408                    ";"
     409                    "; Put all the data in a dedicated section / segment."
     410                    ";\n"
     411                    "%%ifdef ASM_FORMAT_OMF\n"
     412                    " segment VTG.Obj public CLASS=DATA align=4096 use32\n"
     413                    "%%elifdef ASM_FORMAT_MACHO\n"
     414                    " ;[section VTG Obj align=4096]\n"
     415                    " [section .data]\n"
     416                    "%%elifdef ASM_FORMAT_PE\n"
     417                    " [section VTGObj align=4096]\n"
     418                    "%%elifdef ASM_FORMAT_ELF\n"
     419                    " [section .VTGObj progbits alloc noexec write align=4096]\n"
     420                    "%%else\n"
     421                    " %%error \"ASM_FORMAT_XXX is not defined\"\n"
     422                    "%%endif\n"
     423                    "\n"
     424                    "GLOBALNAME g_VTGObjStart\n"
     425                    "    db          'VBoxTpG Obj v1', 0, 0\n"
     426                    "    RTCCPTR_DEF g_aVTGProviders\n"
     427                    "    RTCCPTR_DEF g_aVTGProviders_End     - g_aVTGProviders\n"
     428                    "    RTCCPTR_DEF g_aVTGProbes\n"
     429                    "    RTCCPTR_DEF g_aVTGProbes_End        - g_aVTGProbes\n"
     430                    "    RTCCPTR_DEF g_afVTGProbeEnabled\n"
     431                    "    RTCCPTR_DEF g_afVTGProbeEnabled_End - g_afVTGProbeEnabled\n"
     432                    "    RTCCPTR_DEF g_achVTGStringTable\n"
     433                    "    RTCCPTR_DEF g_achVTGStringTable_End - g_achVTGStringTable\n"
     434                    "    RTCCPTR_DEF g_aVTGArgLists\n"
     435                    "    RTCCPTR_DEF g_aVTGArgLists_End      - g_aVTGArgLists\n"
     436                    "    RTCCPTR_DEF 0\n"
     437                    "    RTCCPTR_DEF 0\n"
     438                    "    RTCCPTR_DEF 0\n"
     439                    "    RTCCPTR_DEF 0\n"
    321440                    ,
    322441                    g_pszScript);
    323 
    324     /*
    325      * Dump the string table to set the offsets before we use them anywhere.
    326      */
    327     ScmStreamPrintf(pStrm,
    328                     ";\n"
    329                     "; The string table.\n"
    330                     ";\n"
    331                     "BEGINDATA\n"
    332                     "GLOBALNAME g_achVTGStringTable\n");
    333     g_offStrTab = 0;
    334     RTStrSpaceEnumerate(&g_StrSpace, generateAssemblyStrTabCallback, pStrm);
    335     ScmStreamPrintf(pStrm,
    336                     "GLOBALNAME g_achVTGStringTable_End\n");
    337442
    338443    /*
     
    342447                    ";\n"
    343448                    "; Probe enabled flags.  Since these will be accessed all the time\n"
    344                     "; they are placed together to get some more cache and TLB hits when\n"
    345                     "; the probes are disabled."
     449                    "; they are placed together and early in the section to get some more\n"
     450                    "; cache and TLB hits when the probes are disabled.\n"
    346451                    ";\n"
    347                     "BEGINDATA\n"
    348                     "ALIGNDATA(16)\n"
    349452                    "GLOBALNAME g_afVTGProbeEnabled\n"
    350453                    );
     
    364467
    365468    /*
    366      * Declare the probe data.
     469     * Dump the string table before we start using the strings.
     470     */
     471    ScmStreamPrintf(pStrm,
     472                    ";\n"
     473                    "; The string table.\n"
     474                    ";\n"
     475                    "GLOBALNAME g_achVTGStringTable\n");
     476    g_offStrTab = 0;
     477    RTStrSpaceEnumerate(&g_StrSpace, generateAssemblyStrTabCallback, pStrm);
     478    ScmStreamPrintf(pStrm,
     479                    "GLOBALNAME g_achVTGStringTable_End\n");
     480
     481    /*
     482     * Write out the argument lists before we use them.
     483     */
     484    ScmStreamPrintf(pStrm,
     485                    ";\n"
     486                    "; The argument lists.\n"
     487                    ";\n"
     488                    "GLOBALNAME g_aVTGArgLists\n");
     489    uint32_t off = 0;
     490    RTListForEach(&g_ProviderHead, pProv, VTGPROVIDER, ListEntry)
     491    {
     492        PVTGPROBE pProbe;
     493        RTListForEach(&pProv->ProbeHead, pProbe, VTGPROBE, ListEntry)
     494        {
     495            if (pProbe->offArgList != UINT32_MAX)
     496                continue;
     497
     498            /* Write it. */
     499            pProbe->offArgList = off;
     500            ScmStreamPrintf(pStrm,
     501                            "    ; off=%u\n"
     502                            "    db   %2u     ; Argument count\n"
     503                            "    db  0, 0, 0 ; Reserved\n"
     504                            , off, pProbe->cArgs);
     505            off += 4;
     506            PVTGARG pArg;
     507            RTListForEach(&pProbe->ArgHead, pArg, VTGARG, ListEntry)
     508            {
     509                ScmStreamPrintf(pStrm,
     510                                "    dd %6u   ; type '%s'\n"
     511                                "    dd %6u   ; name '%s'\n",
     512                                strtabGetOff(pArg->pszType), pArg->pszType,
     513                                strtabGetOff(pArg->pszName), pArg->pszName);
     514                off += 8;
     515            }
     516
     517            /* Look for matching argument lists (lazy bird walks the whole list). */
     518            PVTGPROVIDER pProv2;
     519            RTListForEach(&g_ProviderHead, pProv2, VTGPROVIDER, ListEntry)
     520            {
     521                PVTGPROBE pProbe2;
     522                RTListForEach(&pProv->ProbeHead, pProbe2, VTGPROBE, ListEntry)
     523                {
     524                    if (pProbe2->offArgList != UINT32_MAX)
     525                        continue;
     526                    if (pProbe2->cArgs != pProbe->cArgs)
     527                        continue;
     528
     529                    PVTGARG pArg2;
     530                    pArg  = RTListNodeGetNext(&pProbe->ArgHead, VTGARG, ListEntry);
     531                    pArg2 = RTListNodeGetNext(&pProbe2->ArgHead, VTGARG, ListEntry);
     532                    int32_t cArgs = pProbe->cArgs;
     533                    while (   cArgs-- > 0
     534                           && pArg2->pszName == pArg2->pszName
     535                           && pArg2->pszType == pArg2->pszType)
     536                    {
     537                        pArg  = RTListNodeGetNext(&pArg->ListEntry, VTGARG, ListEntry);
     538                        pArg2 = RTListNodeGetNext(&pArg2->ListEntry, VTGARG, ListEntry);
     539                    }
     540                    if (cArgs >= 0)
     541                        continue;
     542                    pProbe2->offArgList = pProbe->offArgList;
     543                }
     544            }
     545        }
     546    }
     547    ScmStreamPrintf(pStrm,
     548                    "GLOBALNAME g_aVTGArgLists_End\n");
     549
     550
     551    /*
     552     * Probe definitions..
    367553     */
    368554    ScmStreamPrintf(pStrm,
    369555                    "\n"
    370556                    ";\n"
    371                     "; Prob data.\n"
     557                    "; Prob definitions.\n"
    372558                    ";\n"
    373                     "BEGINDATA\n"
    374                     "GLOBALNAME g_abVTGProbeData\n"
     559                    "GLOBALNAME g_aVTGProbes\n"
    375560                    "\n");
     561    uint32_t iProbe = 0;
    376562    RTListForEach(&g_ProviderHead, pProv, VTGPROVIDER, ListEntry)
    377563    {
     
    379565        RTListForEach(&pProv->ProbeHead, pProbe, VTGPROBE, ListEntry)
    380566        {
    381             /** @todo  */
    382             //ScmStreamPrintf(pStrm,
    383             //                "GLOBALNAME g_fVTGProbeEnabled_%s_%s\n"
    384             //                "    db 0\n",
    385             //                pProv->pszName, pProbe->pszName);
     567            ScmStreamPrintf(pStrm,
     568                            "    ; idx=#%4u - %s::%s\n "
     569                            "    dd %6u  ; name\n"
     570                            "    dd %6u  ; provider index\n"
     571                            "    dd %6u  ; Argument list offset\n"
     572                            "    dd g_fVTGProbeEnabled_%s_%s - g_afVTGProbeEnabled\n"
     573                            ,
     574                            iProbe, pProv->pszName, pProbe->pszName,
     575                            strtabGetOff(pProbe->pszName),
     576                            0 /** @todo provider index */,
     577                            pProbe->offArgList,
     578                            pProv->pszName, pProbe->pszName);
     579            pProbe->iProbe = iProbe;
     580            iProbe++;
    386581        }
    387582    }
    388     ScmStreamPrintf(pStrm, "GLOBALNAME g_abVTGProbeData_End\n");
     583    ScmStreamPrintf(pStrm, "GLOBALNAME g_aVTGProbes_End\n");
     584
     585    /*
     586     * The providers data.
     587     */
     588    ScmStreamPrintf(pStrm,
     589                    "\n"
     590                    ";\n"
     591                    "; Provider data.\n"
     592                    ";\n"
     593                    "GLOBALNAME g_aVTGProviders\n"
     594                    "\n");
     595    uint32_t iProvider = 0;
     596    RTListForEach(&g_ProviderHead, pProv, VTGPROVIDER, ListEntry)
     597    {
     598        ScmStreamPrintf(pStrm,
     599                        "    ; idx=#%4u - %s\n "
     600                        "    dd %6u  ; name\n"
     601                        "    dd %6u  ; index of first probe\n"
     602                        "    dd %6u  ; index of last probe\n"
     603                        "    db 0, 0, 0  ; AttrSelf\n"
     604                        "    db 0, 0, 0  ; AttrModules\n"
     605                        "    db 0, 0, 0  ; AttrFunctions\n"
     606                        "    db 0, 0, 0  ; AttrName\n"
     607                        "    db 0, 0, 0  ; AttrArguments\n"
     608                        ,
     609                        iProvider, pProv->pszName,
     610                        strtabGetOff(pProv->pszName),
     611                        0 /** @todo probe index */,
     612                        0 /** @todo probe index */
     613                        /** @todo attributes */);
     614        iProvider++;
     615    }
     616    ScmStreamPrintf(pStrm, "GLOBALNAME g_aVTGProviders_End\n");
     617
     618    /*
     619     * Emit code for the stub functions.
     620     */
    389621
    390622    return RTEXITCODE_SUCCESS;
     
    11281360    RTListInit(&pProbe->ArgHead);
    11291361    RTListAppend(&pProv->ProbeHead, &pProbe->ListEntry);
    1130     pProbe->pszName = strtabInsertN(pszProbe, cchProbe);
     1362    pProbe->offArgList = UINT32_MAX;
     1363    pProbe->pszName    = strtabInsertN(pszProbe, cchProbe);
    11311364    if (!pProbe->pszName)
    11321365        return parseError(pStrm, 0, "Out of memory");
     
    13661599static RTEXITCODE parseArguments(int argc,  char **argv)
    13671600{
     1601    /*
     1602     * Set / Adjust defaults.
     1603     */
     1604    int rc = RTPathAbs(g_pszAssemblerIncVal, g_szAssemblerIncVal, sizeof(g_szAssemblerIncVal) - 1);
     1605    if (RT_FAILURE(rc))
     1606        return RTMsgErrorExit(RTEXITCODE_FAILURE, "RTPathAbs failed: %Rrc", rc);
     1607    strcat(g_szAssemblerIncVal, "/");
     1608    g_pszAssemblerIncVal = g_szAssemblerIncVal;
     1609
     1610    /*
     1611     * Option config.
     1612     */
    13681613    enum
    13691614    {
     
    13991644    RTGETOPTUNION   ValueUnion;
    14001645    RTGETOPTSTATE   GetOptState;
    1401     int rc = RTGetOptInit(&GetOptState, argc, argv, &s_aOpts[0], RT_ELEMENTS(s_aOpts), 1, RTGETOPTINIT_FLAGS_OPTS_FIRST);
     1646    rc = RTGetOptInit(&GetOptState, argc, argv, &s_aOpts[0], RT_ELEMENTS(s_aOpts), 1, RTGETOPTINIT_FLAGS_OPTS_FIRST);
    14021647    AssertReleaseRCReturn(rc, RTEXITCODE_FAILURE);
    14031648
     1649    /*
     1650     * Process \the options.
     1651     */
    14041652    while ((rc = RTGetOpt(&GetOptState, &ValueUnion)) != 0)
    14051653    {
     
    14111659            case kVBoxTpGOpt_32Bit:
    14121660                g_cBits = 32;
    1413                 g_pszAssemblerFmtOpt = g_szAssemblerFmtVal32;
     1661                g_pszAssemblerFmtVal = g_szAssemblerFmtVal32;
    14141662                break;
    14151663
    14161664            case kVBoxTpGOpt_64Bit:
    14171665                g_cBits = 64;
    1418                 g_pszAssemblerFmtOpt = g_szAssemblerFmtVal64;
     1666                g_pszAssemblerFmtVal = g_szAssemblerFmtVal64;
    14191667                break;
    14201668
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