VirtualBox

Changeset 3173 in kBuild


Ignore:
Timestamp:
Mar 21, 2018 9:37:41 PM (7 years ago)
Author:
bird
Message:

kmkbultin: environment fixes and stats.

Location:
trunk/src/kmk
Files:
9 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/kmk/Makefile.kmk

    r3170 r3173  
    2727include $(KBUILD_PATH)/subheader.kmk
    2828
     29# Enable new children handling for windows.
     30CONFIG_NEW_WIN_CHILDREN = 1
    2931
    3032#
     
    225227 kmk_DEFS += CONFIG_WITH_MAKE_STATS
    226228endif
    227 ifdef CONFIG_WITH_KMK_BUILTIN_STATS
     229#ifdef CONFIG_WITH_KMK_BUILTIN_STATS
    228230 kmk_DEFS += CONFIG_WITH_KMK_BUILTIN_STATS
    229 endif
     231#endif
    230232ifdef CONFIG_WITH_EVAL_COMPILER
    231233 kmk_DEFS += CONFIG_WITH_EVAL_COMPILER
  • trunk/src/kmk/kmkbuiltin.c

    r3172 r3173  
    55
    66/*
    7  * Copyright (c) 2005-2010 knut st. osmundsen <[email protected]>
     7 * Copyright (c) 2005-2018 knut st. osmundsen <[email protected]>
    88 *
    99 * This file is part of kBuild.
     
    2424 */
    2525
    26 /*******************************************************************************
    27 *   Header Files                                                               *
    28 *******************************************************************************/
     26
     27/*********************************************************************************************************************************
     28*   Header Files                                                                                                                 *
     29*********************************************************************************************************************************/
    2930#include <string.h>
    3031#include <stdlib.h>
     
    3940#include "makeint.h"
    4041#include "job.h"
     42#include "variable.h"
    4143#if defined(KBUILD_OS_WINDOWS) && defined(CONFIG_NEW_WIN_CHILDREN)
    4244# include "w32/winchildren.h"
     
    4850extern char **environ;
    4951#endif
     52
     53
     54/*********************************************************************************************************************************
     55*   Global Variables                                                                                                             *
     56*********************************************************************************************************************************/
     57#ifdef CONFIG_WITH_KMK_BUILTIN_STATS
     58extern int print_stats_flag;
     59#endif
     60
    5061
    5162
     
    234245static const KMKBUILTINENTRY g_aBuiltIns[] =
    235246{
    236 #define BUILTIN_ENTRY(a_fn, a_sz, a_uFnSignature, fMpSafe, fNeedEnv) \
     247#define BUILTIN_ENTRY(a_fn, a_sz, a_uFnSignature, fMtSafe, fNeedEnv) \
    237248    {  { { sizeof(a_sz) - 1, a_sz, } }, \
    238        (uintptr_t)a_fn,                                 a_uFnSignature,   fMpSafe, fNeedEnv }
     249       (uintptr_t)a_fn,                                 a_uFnSignature,   fMtSafe, fNeedEnv }
    239250
    240251    /* More frequently used commands: */
     
    245256    BUILTIN_ENTRY(kmk_builtin_kDepObj,  "kDepObj",      FN_SIG_MAIN,            1, 0),
    246257#ifdef KBUILD_OS_WINDOWS
    247     BUILTIN_ENTRY(kmk_builtin_kSubmit,  "kSubmit",      FN_SIG_MAIN_SPAWNS,     0, 0),
     258    BUILTIN_ENTRY(kmk_builtin_kSubmit,  "kSubmit",      FN_SIG_MAIN_SPAWNS,     0, 1),
    248259#endif
    249260    BUILTIN_ENTRY(kmk_builtin_mkdir,    "mkdir",        FN_SIG_MAIN,            0, 0),
    250261    BUILTIN_ENTRY(kmk_builtin_mv,       "mv",           FN_SIG_MAIN,            0, 0),
    251     BUILTIN_ENTRY(kmk_builtin_redirect, "redirect",     FN_SIG_MAIN_SPAWNS,     0, 1),
     262    BUILTIN_ENTRY(kmk_builtin_redirect, "redirect",     FN_SIG_MAIN_SPAWNS,     1, 1),
    252263    BUILTIN_ENTRY(kmk_builtin_rm,       "rm",           FN_SIG_MAIN,            0, 1),
    253264    BUILTIN_ENTRY(kmk_builtin_rmdir,    "rmdir",        FN_SIG_MAIN,            0, 0),
     
    347358                /*
    348359                 * That's a match!
     360                 *
     361                 * First get the environment if it is actually needed.  This is
     362                 * especially important when we run on a worker thread as it must
     363                 * not under any circumstances do stuff like target_environment.
    349364                 */
    350                 int rc;
     365                int    rc;
     366                char **papszEnvVars = NULL;
     367                if (pEntry->fNeedEnv)
     368                {
     369                    papszEnvVars = pChild->environment;
     370                    if (!papszEnvVars)
     371                        pChild->environment = papszEnvVars = target_environment(pChild->file);
     372                }
     373
    351374#if defined(KBUILD_OS_WINDOWS) && defined(CONFIG_NEW_WIN_CHILDREN)
    352                 if (pEntry->fMpSafe)
    353                 {
    354                     rc = MkWinChildCreateBuiltIn(pEntry, argc, argv, pEntry->fNeedEnv ? pChild->environment : NULL,
    355                                                  pChild, pPidSpawned);
     375                /*
     376                 * If the built-in is multi thread safe, we will run it on a job slot thread.
     377                 */
     378                if (pEntry->fMtSafe)
     379                {
     380                    rc = MkWinChildCreateBuiltIn(pEntry, argc, argv, papszEnvVars, pChild, pPidSpawned);
    356381# ifdef CONFIG_WITH_KMK_BUILTIN_STATS
    357382                    g_aBuiltInStats[pEntry - &g_aBuiltIns[0]].cAsyncTimes++;
     
    361386#endif
    362387                {
    363                     char **envp = pChild->environment ? pChild->environment : environ;
    364 
    365388                    /*
    366389                     * Call the worker function, making sure to preserve umask.
    367390                     */
    368391#ifdef CONFIG_WITH_KMK_BUILTIN_STATS
    369                     big_int nsStart = nano_timestamp();
     392                    big_int nsStart = print_stats_flag ? nano_timestamp() : 0;
    370393#endif
    371394                    int const iUmask = umask(0);        /* save umask */
     
    373396
    374397                    if (pEntry->uFnSignature == FN_SIG_MAIN)
    375                         rc = pEntry->u.pfnMain(argc, argv, envp);
     398                        rc = pEntry->u.pfnMain(argc, argv, papszEnvVars);
    376399                    else if (pEntry->uFnSignature == FN_SIG_MAIN_SPAWNS)
    377                         rc = pEntry->u.pfnMainSpawns(argc, argv, envp, pChild, pPidSpawned);
     400                        rc = pEntry->u.pfnMainSpawns(argc, argv, papszEnvVars, pChild, pPidSpawned);
    378401                    else if (pEntry->uFnSignature == FN_SIG_MAIN_TO_SPAWN)
    379402                    {
     
    383406                         * problem then (the call stack shows what's been going on).
    384407                         */
    385                         rc = pEntry->u.pfnMainToSpawn(argc, argv, envp, ppapszArgvToSpawn);
     408                        rc = pEntry->u.pfnMainToSpawn(argc, argv, papszEnvVars, ppapszArgvToSpawn);
    386409                        if (   !rc
    387410                            && *ppapszArgvToSpawn
     
    410433
    411434#ifdef CONFIG_WITH_KMK_BUILTIN_STATS
    412                     g_aBuiltInStats[pEntry - &g_aBuiltIns[0]].cTimes++;
    413                     g_aBuiltInStats[pEntry - &g_aBuiltIns[0]].cNs += nano_timestamp() - nsStart;
     435                    if (print_stats_flag)
     436                    {
     437                        uintptr_t iEntry = pEntry - &g_aBuiltIns[0];
     438                        g_aBuiltInStats[iEntry].cTimes++;
     439                        g_aBuiltInStats[iEntry].cNs += nano_timestamp() - nsStart;
     440                    }
    414441#endif
    415442                }
     
    442469extern void kmk_builtin_print_stats(FILE *pOutput, const char *pszPrefix)
    443470{
    444     const unsigned  cEntries = sizeof(g_aBuiltInStats) / sizeof(g_aBuiltInStats[0]);
     471    const unsigned cEntries = sizeof(g_aBuiltInStats) / sizeof(g_aBuiltInStats[0]);
    445472    unsigned i;
     473    assert(print_stats_flag);
    446474    fprintf(pOutput, "\n%skmk built-in command statistics:\n", pszPrefix);
    447475    for (i = 0; i < cEntries; i++)
  • trunk/src/kmk/kmkbuiltin.h

    r3172 r3173  
    8888    } u;
    8989    size_t      uFnSignature : 8;
    90     size_t      fMpSafe : 1;
    91     size_t      fNeedEnv : 1;
     90    size_t      fMtSafe : 1;            /**< Safe for multi threaded execution. */
     91    size_t      fNeedEnv : 1;           /**< Needs the (target) enviornment. */
    9292} KMKBUILTINENTRY;
    9393/** Pointer to kmk built-in command entry. */
     
    138138extern int kBuiltinOptEnvPrepend(char ***ppapszEnv, unsigned *pcEnvVars, unsigned *pcAllocatedEnvVars,
    139139                                 int cVerbosity, const char *pszValue);
    140 extern int kBuiltinOptEnvUnset(char **papszEnv, unsigned *pcEnvVars, int cVerbosity, const char *pszVarToRemove);
     140extern int kBuiltinOptEnvUnset(char ***ppapszEnv, unsigned *pcEnvVars, unsigned *pcAllocatedEnvVars, int cVerbosity, const char *pszVarToRemove);
     141extern int kBuiltinOptEnvZap(char ***ppapszEnv, unsigned *pcEnvVars, unsigned *pcAllocatedEnvVars, int cVerbosity);
     142extern void kBuiltinOptEnvCleanup(char ***ppapszEnv, unsigned cEnvVars, unsigned *pcAllocatedEnvVars);
    141143extern int kBuiltinOptChDir(char *pszCwd, size_t cbCwdBuf, const char *pszValue);
    142144
  • trunk/src/kmk/kmkbuiltin/common-env-and-cwd-opt.c

    r3133 r3173  
    3131#include <stdlib.h>
    3232#include <string.h>
     33#include <assert.h>
    3334
    3435#include "kmkbuiltin.h"
     
    4344# define KSUBMIT_ENV_NCMP   strncmp
    4445#endif
     46
     47
     48/**
     49 * Duplicates a read-only enviornment vector.
     50 *
     51 * @returns The duplicate enviornment.
     52 * @param   papszEnv            The read-only vector.
     53 * @param   cEnvVars            The number of variables.
     54 * @param   pcAllocatedEnvVars  The allocated papszEnv size.  This is zero on
     55 *                              input and non-zero on successful return.
     56 * @param   cVerbosity          The verbosity level.
     57 */
     58static char **kBuiltinOptEnvDuplicate(char **papszEnv, unsigned cEnvVars, unsigned *pcAllocatedEnvVars, int cVerbosity)
     59{
     60    unsigned cAllocatedEnvVars = (cEnvVars + 2 + 0xf) * ~(unsigned)0xf;
     61    char    **papszEnvNew      = malloc(cAllocatedEnvVars * sizeof(papszEnvNew[0]));
     62    assert(*pcAllocatedEnvVars == 0);
     63    if (papszEnvNew)
     64    {
     65        unsigned i;
     66        for (i = 0; i < cEnvVars; i++)
     67        {
     68            papszEnvNew[i] = strdup(papszEnv[i]);
     69            if (!papszEnvNew)
     70            {
     71                while (i-- > 0)
     72                    free(papszEnvNew[i]);
     73                free(papszEnvNew);
     74                errx(1, "out of memory");
     75                return NULL;
     76            }
     77        }
     78        papszEnvNew[i] = NULL;
     79        *pcAllocatedEnvVars = cAllocatedEnvVars;
     80    }
     81    else
     82        errx(1, "out of memory");
     83    return papszEnvNew;
     84}
    4585
    4686
     
    136176        unsigned cEnvVars = *pcEnvVars;
    137177        size_t const cchVar = pszEqual - pszValue;
     178
     179        if (!*pcAllocatedEnvVars)
     180        {
     181            papszEnv = kBuiltinOptEnvDuplicate(papszEnv, cEnvVars, pcAllocatedEnvVars, cVerbosity);
     182            if (!papszEnv)
     183                return errx(1, "out of memory!");
     184            *ppapszEnv = papszEnv;
     185        }
     186
    138187        for (iEnvVar = 0; iEnvVar < cEnvVars; iEnvVar++)
    139188        {
     
    180229        unsigned cEnvVars = *pcEnvVars;
    181230        size_t const cchVar = pszEqual - pszValue;
     231
     232        if (!*pcAllocatedEnvVars)
     233        {
     234            papszEnv = kBuiltinOptEnvDuplicate(papszEnv, cEnvVars, pcAllocatedEnvVars, cVerbosity);
     235            if (!papszEnv)
     236                return errx(1, "out of memory!");
     237            *ppapszEnv = papszEnv;
     238        }
     239
    182240        for (iEnvVar = 0; iEnvVar < cEnvVars; iEnvVar++)
    183241        {
     
    257315 *
    258316 * @returns 0 on success, non-zero exit code on error.
    259  * @param   papszEnv            The environment vector.
    260  * @param   pcEnvVars           Pointer to the variable holding the number of
    261  *                              environment variables held by @a papszEnv.
     317 * @param   ppapszEnv           The environment vector pointer.
     318 * @param   pcEnvVars           Pointer to the variable holding the number of
     319 *                              environment variables held by @a papszEnv.
     320 * @param   pcAllocatedEnvVars  Pointer to the size of the vector allocation.
     321 *                              The size is zero when read-only (CRT, GNU make)
     322 *                              environment.
    262323 * @param   cVerbosity          The verbosity level.
    263324 * @param   pszVarToRemove      The name of the variable to remove.
    264325 */
    265 int kBuiltinOptEnvUnset(char **papszEnv, unsigned *pcEnvVars, int cVerbosity, const char *pszVarToRemove)
     326int kBuiltinOptEnvUnset(char ***ppapszEnv, unsigned *pcEnvVars, unsigned *pcAllocatedEnvVars, int cVerbosity, const char *pszVarToRemove)
    266327{
    267328    if (strchr(pszVarToRemove, '=') == NULL)
    268329    {
     330        char       **papszEnv = *ppapszEnv;
    269331        unsigned     cRemoved = 0;
    270332        size_t const cchVar   = strlen(pszVarToRemove);
     
    278340                if (cVerbosity > 0)
    279341                    warnx(!cRemoved ? "removing '%s'" : "removing duplicate '%s'", papszEnv[iEnvVar]);
     342
     343                if (!*pcAllocatedEnvVars)
     344                {
     345                    papszEnv = kBuiltinOptEnvDuplicate(papszEnv, cEnvVars, pcAllocatedEnvVars, cVerbosity);
     346                    if (!papszEnv)
     347                        return errx(1, "out of memory!");
     348                    *ppapszEnv = papszEnv;
     349                }
     350
    280351                free(papszEnv[iEnvVar]);
    281352                cEnvVars--;
     
    296367}
    297368
     369
     370/**
     371 * Handles the --zap-env & --ignore-environment options.
     372 *
     373 * @returns 0 on success, non-zero exit code on error.
     374 * @param   ppapszEnv           The environment vector pointer.
     375 * @param   pcEnvVars           Pointer to the variable holding the number of
     376 *                              environment variables held by @a papszEnv.
     377 * @param   pcAllocatedEnvVars  Pointer to the size of the vector allocation.
     378 *                              The size is zero when read-only (CRT, GNU make)
     379 *                              environment.
     380 * @param   cVerbosity          The verbosity level.
     381 */
     382int kBuiltinOptEnvZap(char ***ppapszEnv, unsigned *pcEnvVars, unsigned *pcAllocatedEnvVars, int cVerbosity)
     383{
     384    if (*pcAllocatedEnvVars > 0)
     385    {
     386        char **papszEnv = *ppapszEnv;
     387        unsigned i = *pcEnvVars;
     388        while (i-- > 0)
     389        {
     390            free(papszEnv[i]);
     391            papszEnv[i] = NULL;
     392        }
     393    }
     394    else
     395    {
     396        char **papszEnv = calloc(4, sizeof(char *));
     397        if (!papszEnv)
     398            return err(1, "out of memory!");
     399        *ppapszEnv = papszEnv;
     400        *pcAllocatedEnvVars = 4;
     401    }
     402    *pcEnvVars = 0;
     403    return 0;
     404}
     405
     406
     407/**
     408 * Cleans up afterwards, if necessary.
     409 *
     410 * @param   ppapszEnv           The environment vector pointer.
     411 * @param   cEnvVars            The number of variables in the vector.
     412 * @param   pcAllocatedEnvVars  Pointer to the size of the vector allocation.
     413 *                              The size is zero when read-only (CRT, GNU make)
     414 *                              environment.
     415 */
     416void kBuiltinOptEnvCleanup(char ***ppapszEnv, unsigned cEnvVars, unsigned *pcAllocatedEnvVars)
     417{
     418    char **papszEnv = *ppapszEnv;
     419    *ppapszEnv = NULL;
     420    if (*pcAllocatedEnvVars > 0)
     421    {
     422        *pcAllocatedEnvVars = 0;
     423        while (cEnvVars-- > 0)
     424        {
     425            free(papszEnv[cEnvVars]);
     426            papszEnv[cEnvVars] = NULL;
     427        }
     428        free(papszEnv);
     429    }
     430}
    298431
    299432
  • trunk/src/kmk/kmkbuiltin/kSubmit.c

    r3156 r3173  
    12501250    int             iArg;
    12511251    unsigned        cAllocatedEnvVars;
    1252     unsigned        iEnvVar;
    12531252    unsigned        cEnvVars;
    1254     char          **papszEnv            = NULL;
     1253    char          **papszEnvVars;
    12551254    const char     *pszExecutable       = NULL;
    12561255    int             iPostCmd            = argc;
     
    12671266    /*
    12681267     * Create default program environment.
     1268     *
     1269     * Note! We only clean up the environment on successful return, assuming
     1270     *       make will stop after that.
    12691271     */
    12701272    if (getcwd_fs(szCwd, cbCwdBuf) != NULL)
     
    12731275        return err(1, "getcwd_fs failed\n");
    12741276
    1275     papszEnv = pChild->environment;
    1276     if (!papszEnv)
    1277         pChild->environment = papszEnv = target_environment(pChild->file);
     1277    /* The environment starts out in read-only mode and will be duplicated if modified. */
     1278    cAllocatedEnvVars = 0;
     1279    papszEnvVars = envp;
    12781280    cEnvVars = 0;
    1279     while (papszEnv[cEnvVars] != NULL)
     1281    while (papszEnvVars[cEnvVars] != NULL)
    12801282        cEnvVars++;
    1281     cAllocatedEnvVars = cEnvVars;
    12821283
    12831284    /*
     
    13871388                    case 'Z':
    13881389                    case 'i': /* GNU env compatibility. */
    1389                         for (iEnvVar = 0; iEnvVar < cEnvVars; iEnvVar++)
    1390                             free(papszEnv[iEnvVar]);
    1391                         papszEnv[0] = NULL;
    1392                         cEnvVars = 0;
    1393                         break;
    1394 
    1395                     case 'E':
    1396                         rcExit = kBuiltinOptEnvSet(&papszEnv, &cEnvVars, &cAllocatedEnvVars, cVerbosity, pszValue);
    1397                         pChild->environment = papszEnv;
     1390                        rcExit = kBuiltinOptEnvZap(&papszEnvVars, &cEnvVars, &cAllocatedEnvVars, cVerbosity);
    13981391                        if (rcExit == 0)
    13991392                            break;
    14001393                        return rcExit;
    14011394
    1402                     case 'A':
    1403                         rcExit = kBuiltinOptEnvAppend(&papszEnv, &cEnvVars, &cAllocatedEnvVars, cVerbosity, pszValue);
    1404                         pChild->environment = papszEnv;
     1395                    case 'E':
     1396                        rcExit = kBuiltinOptEnvSet(&papszEnvVars, &cEnvVars, &cAllocatedEnvVars, cVerbosity, pszValue);
    14051397                        if (rcExit == 0)
    14061398                            break;
    14071399                        return rcExit;
    14081400
    1409                     case 'D':
    1410                         rcExit = kBuiltinOptEnvPrepend(&papszEnv, &cEnvVars, &cAllocatedEnvVars, cVerbosity, pszValue);
    1411                         pChild->environment = papszEnv;
     1401                    case 'A':
     1402                        rcExit = kBuiltinOptEnvAppend(&papszEnvVars, &cEnvVars, &cAllocatedEnvVars, cVerbosity, pszValue);
    14121403                        if (rcExit == 0)
    14131404                            break;
    14141405                        return rcExit;
    14151406
     1407                    case 'D':
     1408                        rcExit = kBuiltinOptEnvPrepend(&papszEnvVars, &cEnvVars, &cAllocatedEnvVars, cVerbosity, pszValue);
     1409                        if (rcExit == 0)
     1410                            break;
     1411                        return rcExit;
     1412
    14161413                    case 'U':
    1417                         rcExit = kBuiltinOptEnvUnset(papszEnv, &cEnvVars, cVerbosity, pszValue);
     1414                        rcExit = kBuiltinOptEnvUnset(&papszEnvVars, &cEnvVars, &cAllocatedEnvVars, cVerbosity, pszValue);
    14181415                        if (rcExit == 0)
    14191416                            break;
     
    14581455                    case 'h':
    14591456                        usage(stdout, argv[0]);
     1457                        kBuiltinOptEnvCleanup(&papszEnvVars, cEnvVars, &cAllocatedEnvVars);
    14601458                        return 0;
    14611459
    14621460                    case 'V':
     1461                        kBuiltinOptEnvCleanup(&papszEnvVars, cEnvVars, &cAllocatedEnvVars);
    14631462                        return kbuild_version(argv[0]);
    14641463                }
     
    14781477    {
    14791478        uint32_t        cbMsg;
    1480         void           *pvMsg   = kSubmitComposeJobMessage(pszExecutable, &argv[iArg], papszEnv, szCwd,
     1479        void           *pvMsg   = kSubmitComposeJobMessage(pszExecutable, &argv[iArg], papszEnvVars, szCwd,
    14811480                                                           fWatcomBrainDamage, fNoPchCaching,
    14821481                                                           &argv[iPostCmd], cPostCmdArgs, &cbMsg);
     
    15051504    }
    15061505
     1506    kBuiltinOptEnvCleanup(&papszEnvVars, cEnvVars, &cAllocatedEnvVars);
    15071507    return rcExit;
    15081508}
  • trunk/src/kmk/kmkbuiltin/redirect.c

    r3164 r3173  
    7474#include "kmkbuiltin.h"
    7575#ifdef KMK
    76 # include "job.h"
    77 # include "variable.h"
    7876# ifdef KBUILD_OS_WINDOWS
    7977#  ifndef CONFIG_NEW_WIN_CHILDREN
     
    11611159                /* Windows is slightly complicated due to handles and winchildren.c. */
    11621160                HANDLE hProcess = INVALID_HANDLE_VALUE;
    1163                 rcExit = kRedirectCreateProcessWindows(pszExecutable, cArgs, papszArgs, papszEnvVars, pszCwd,
    1164                                                        cOrders, paOrders, &hProcess);
     1161                rcExit = kRedirectCreateProcessWindows(pszExecutable, cArgs, papszArgs, papszEnvVars,
     1162                                                       pszSavedCwd ? pszCwd : NULL, cOrders, paOrders, &hProcess);
    11651163                if (rcExit == 0)
    11661164                {
     
    11681166                    if (process_kmk_register_redirect(hProcess, pPidSpawned) == 0)
    11691167#  else
    1170                     if (MkWinChildCreateRedirect((intptr_t)hProcess, pPidSpawned) == 0)
     1168                    if (   pPidSpawned
     1169                        && MkWinChildCreateRedirect((intptr_t)hProcess, pPidSpawned) == 0)
    11711170#  endif
    11721171                    {
     
    11801179                        warn("sub_proc is out of slots, waiting for child...");
    11811180#  else
    1182                         warn("MkWinChildCreateRedirect failed...");
     1181                        if (pPidSpawned)
     1182                            warn("MkWinChildCreateRedirect failed...");
    11831183#  endif
    11841184                        dwTmp = WaitForSingleObject(hProcess, INFINITE);
     
    11961196
    11971197                        CloseHandle(hProcess);
    1198                         *pPidSpawned = 0;
     1198                        if (pPidSpawned)
     1199                            *pPidSpawned = 0;
    11991200                        *pfIsChildExitCode = K_TRUE;
    12001201                    }
     
    12341235# ifdef KBUILD_OS_WINDOWS
    12351236                HANDLE hProcess = INVALID_HANDLE_VALUE;
    1236                 rcExit = kRedirectCreateProcessWindows(pszExecutable, cArgs, papszArgs, papszEnvVars, pszCwd,
    1237                                                        cOrders, paOrders, &hProcess);
     1237                rcExit = kRedirectCreateProcessWindows(pszExecutable, cArgs, papszArgs, papszEnvVars,
     1238                                                       pszSavedCwd ? pszCwd : NULL, cOrders, paOrders, &hProcess);
    12381239                if (rcExit == 0)
    12391240                {
     
    13481349    char          **papszEnvVars       = NULL;
    13491350    unsigned        cAllocatedEnvVars;
    1350     unsigned        iEnvVar;
    13511351    unsigned        cEnvVars;
    13521352    int             fWatcomBrainDamage = 0;
     
    13781378        return err(9, "getcwd failed");
    13791379
    1380 #if defined(KMK)
    1381     /* We get it from kmk and just count it:  */
    1382     papszEnvVars = pChild->environment;
    1383     if (!papszEnvVars)
    1384         pChild->environment = papszEnvVars = target_environment(pChild->file);
     1380    /* We start out with a read-only enviornment from kmk or the crt, and will
     1381       duplicate it if we make changes to it. */
     1382    cAllocatedEnvVars = 0;
     1383    papszEnvVars = envp;
    13851384    cEnvVars = 0;
    13861385    while (papszEnvVars[cEnvVars] != NULL)
    13871386        cEnvVars++;
    1388     cAllocatedEnvVars = cEnvVars;
    1389 #else
    1390     /* We make a copy and we manage ourselves: */
    1391     cEnvVars = 0;
    1392     while (envp[cEnvVars] != NULL)
    1393         cEnvVars++;
    1394 
    1395     cAllocatedEnvVars = cEnvVars + 4;
    1396     papszEnvVars = malloc((cAllocatedEnvVars + 1) * sizeof(papszEnvVars));
    1397     if (!papszEnvVars)
    1398         return errx(9, "out of memory!");
    1399 
    1400     iEnvVar = cEnvVars;
    1401     papszEnvVars[iEnvVar] = NULL;
    1402     while (iEnvVar-- > 0)
    1403     {
    1404         papszEnvVars[iEnvVar] = strdup(envp[iEnvVar]);
    1405         if (!papszEnvVars[iEnvVar])
    1406         {
    1407             while (iEnvVar-- > 0)
    1408                 free(papszEnvVars[iEnvVar]);
    1409             free(papszEnvVars);
    1410             return errx(9, "out of memory!");
    1411         }
    1412     }
    1413 #endif
    14141387
    14151388#ifdef USE_POSIX_SPAWN
     
    15781551                {
    15791552                    if (pchEqual[1] != '\0')
    1580                     {
    15811553                        rcExit = kBuiltinOptEnvSet(&papszEnvVars, &cEnvVars, &cAllocatedEnvVars, cVerbosity, pszValue);
    1582 #ifdef KMK
    1583                         pChild->environment = papszEnvVars;
    1584 #endif
    1585                     }
    15861554                    else
    15871555                    {
     
    15901558                        {
    15911559                            pszCopy[pchEqual - pszValue] = '\0';
    1592                             rcExit = kBuiltinOptEnvUnset(papszEnvVars, &cEnvVars, cVerbosity, pszCopy);
     1560                            rcExit = kBuiltinOptEnvUnset(&papszEnvVars, &cEnvVars, &cAllocatedEnvVars, cVerbosity, pszCopy);
    15931561                            free(pszCopy);
    15941562                        }
     
    16331601                else
    16341602#endif
    1635                     rcExit = kBuiltinOptEnvUnset(papszEnvVars, &cEnvVars, cVerbosity, pszValue);
     1603                    rcExit = kBuiltinOptEnvUnset(&papszEnvVars, &cEnvVars, &cAllocatedEnvVars, cVerbosity, pszValue);
    16361604                continue;
    16371605            }
     
    16431611                || chOpt == 'i' /* GNU env compatibility. */ )
    16441612            {
    1645                 for (iEnvVar = 0; iEnvVar < cEnvVars; iEnvVar++)
    1646                     free(papszEnvVars[iEnvVar]);
    1647                 papszEnvVars[0] = NULL;
    1648                 cEnvVars = 0;
     1613                rcExit = kBuiltinOptEnvZap(&papszEnvVars, &cEnvVars, &cAllocatedEnvVars, cVerbosity);
    16491614                continue;
    16501615            }
     
    19981963     * Cleanup.
    19991964     */
     1965    kBuiltinOptEnvCleanup(&papszEnvVars, cEnvVars, &cAllocatedEnvVars);
    20001966    if (pszSavedCwd)
    20011967        free(pszSavedCwd);
     
    20041970    posix_spawn_file_actions_destroy(&FileActions);
    20051971#endif
    2006 #ifndef KMK
    2007     iEnvVar = cEnvVars;
    2008     while (iEnvVar-- > 0)
    2009         free(papszEnvVars[iEnvVar]);
    2010     free(papszEnvVars);
    2011 #endif
    20121972#ifdef KBUILD_OS_OS2
    20131973    for (ulLibPath = 0; ulLibPath < K_ELEMENTS(apszSavedLibPaths); ulLibPath++)
  • trunk/src/kmk/misc.c

    r3170 r3173  
    10721072  printf (_("\n# CRT Heap: %u bytes in use, in %u blocks, avg %u bytes/block\n"),
    10731073          (unsigned)s.size_in_use, (unsigned)s.blocks_in_use,
    1074           (unsigned)(s.size_in_use / s.blocks_in_use));
     1074          s.blocks_in_use ? (unsigned)(s.size_in_use / s.blocks_in_use : 0));
    10751075  printf (_("#           %u bytes max in use (high water mark)\n"),
    10761076          (unsigned)s.max_size_in_use);
     
    11041104
    11051105  printf (_("\n# CRT Heap: %u bytes in use, in %u blocks, avg %u bytes/block\n"),
    1106           bytes_used, blocks_used, bytes_used / blocks_used);
     1106          bytes_used, blocks_used, blocks_used ? bytes_used / blocks_used : 0);
    11071107  printf (_("#           %u bytes avail, in %u blocks, avg %u bytes/block\n"),
    1108           bytes_avail, blocks_avail, bytes_avail / blocks_avail);
     1108          bytes_avail, blocks_avail, blocks_avail ? bytes_avail / blocks_avail : 0);
    11091109# endif /* _MSC_VER */
    11101110
  • trunk/src/kmk/w32/w32os.c

    r3156 r3173  
    187187    /* Build array of handles to wait for.  */
    188188    dwHandleCount = 1 + process_set_handles (&handles[1]);
    189 #else
    190     /* Add the completed children event as the 2nd one. */
    191     handles[1] = (HANDLE)MkWinChildGetCompleteEventHandle();
    192     dwHandleCount = 2;
    193 #endif
    194 
    195189    dwEvent = WaitForMultipleObjects (
    196190        dwHandleCount,  /* number of objects in array */
     
    198192        FALSE,          /* wait for any object */
    199193        INFINITE);      /* wait until object is signalled */
     194#else
     195    /* Add the completed children event as the 2nd one. */
     196    handles[1] = (HANDLE)MkWinChildGetCompleteEventHandle();
     197    if (handles[1] == NULL)
     198      return 0;
     199    dwHandleCount = 2;
     200    dwEvent = WaitForMultipleObjectsEx (dwHandleCount,
     201                                        handles,
     202                                        FALSE /*bWaitAll*/,
     203                                        256, /* INFINITE - paranoia, only wait 256 ms before checking again. */
     204                                        TRUE /*bAlertable*/);
     205#endif
    200206
    201207    if (dwEvent == WAIT_FAILED)
  • trunk/src/kmk/w32/winchildren.c

    r3172 r3173  
    25362536 * that completed children is the typical source of these tokens (esp. for kmk).
    25372537 *
    2538  * @returns Event handle.
     2538 * @returns Zero if completed children, event handle if waiting is required.
    25392539 */
    25402540intptr_t MkWinChildGetCompleteEventHandle(void)
    25412541{
    2542     return (intptr_t)g_hEvtWaitChildren;
     2542    /* We don't return the handle if we've got completed children.  This
     2543       is a safe guard against being called twice in a row without any
     2544       MkWinChildWait call inbetween. */
     2545    if (!g_pTailCompletedChildren)
     2546        return (intptr_t)g_hEvtWaitChildren;
     2547    return 0;
    25432548}
    25442549
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