/*
 * Copyright (C) 2011-2013 Vinay Sajip.
 * Licensed to PSF under a contributor agreement.
 *
 * Based on the work of:
 *
 * Mark Hammond (original author of Python version)
 * Curt Hagenlocher (job management)
 */

#include <windows.h>
#include <shlobj.h>
#include <stdio.h>
#include <tchar.h>

#define BUFSIZE 256
#define MSGSIZE 1024

/* Build options. */
#define SKIP_PREFIX
#define SEARCH_PATH

/* Error codes */

#define RC_NO_STD_HANDLES   100
#define RC_CREATE_PROCESS   101
#define RC_BAD_VIRTUAL_PATH 102
#define RC_NO_PYTHON        103
#define RC_NO_MEMORY        104
/*
 * SCRIPT_WRAPPER is used to choose one of the variants of an executable built
 * from this source file. If not defined, the PEP 397 Python launcher is built;
 * if defined, a script launcher of the type used by setuptools is built, which
 * looks for a script name related to the executable name and runs that script
 * with the appropriate Python interpreter.
 *
 * SCRIPT_WRAPPER should be undefined in the source, and defined in a VS project
 * which builds the setuptools-style launcher.
 */
#if defined(SCRIPT_WRAPPER)
#define RC_NO_SCRIPT        105
#endif
/*
 * VENV_REDIRECT is used to choose the variant that looks for an adjacent or
 * one-level-higher pyvenv.cfg, and uses its "home" property to locate and
 * launch the original python.exe.
 */
#if defined(VENV_REDIRECT)
#define RC_NO_VENV_CFG      106
#define RC_BAD_VENV_CFG     107
#endif

/* Just for now - static definition */

static FILE * log_fp = NULL;

static wchar_t *
skip_whitespace(wchar_t * p)
{
    while (*p && isspace(*p))
        ++p;
    return p;
}

static void
debug(wchar_t * format, ...)
{
    va_list va;

    if (log_fp != NULL) {
        va_start(va, format);
        vfwprintf_s(log_fp, format, va);
        va_end(va);
    }
}

static void
winerror(int rc, wchar_t * message, int size)
{
    FormatMessageW(
        FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,
        NULL, rc, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
        message, size, NULL);
}

static void
error(int rc, wchar_t * format, ... )
{
    va_list va;
    wchar_t message[MSGSIZE];
    wchar_t win_message[MSGSIZE];
    int len;

    va_start(va, format);
    len = _vsnwprintf_s(message, MSGSIZE, _TRUNCATE, format, va);
    va_end(va);

    if (rc == 0) {  /* a Windows error */
        winerror(GetLastError(), win_message, MSGSIZE);
        if (len >= 0) {
            _snwprintf_s(&message[len], MSGSIZE - len, _TRUNCATE, L": %ls",
                         win_message);
        }
    }

#if !defined(_WINDOWS)
    fwprintf(stderr, L"%ls\n", message);
#else
    MessageBoxW(NULL, message, L"Python Launcher is sorry to say ...",
               MB_OK);
#endif
    exit(rc);
}

/*
 * This function is here to simplify memory management
 * and to treat blank values as if they are absent.
 */
static wchar_t * get_env(wchar_t * key)
{
    /* This is not thread-safe, just like getenv */
    static wchar_t buf[BUFSIZE];
    DWORD result = GetEnvironmentVariableW(key, buf, BUFSIZE);

    if (result >= BUFSIZE) {
        /* Large environment variable. Accept some leakage */
        wchar_t *buf2 = (wchar_t*)malloc(sizeof(wchar_t) * (result+1));
        if (buf2 == NULL) {
            error(RC_NO_MEMORY, L"Could not allocate environment buffer");
        }
        GetEnvironmentVariableW(key, buf2, result);
        return buf2;
    }

    if (result == 0)
        /* Either some error, e.g. ERROR_ENVVAR_NOT_FOUND,
           or an empty environment variable. */
        return NULL;

    return buf;
}

#if defined(_DEBUG)
/* Do not define EXECUTABLEPATH_VALUE in debug builds as it'll
   never point to the debug build. */
#if defined(_WINDOWS)

#define PYTHON_EXECUTABLE L"pythonw_d.exe"

#else

#define PYTHON_EXECUTABLE L"python_d.exe"

#endif
#else
#if defined(_WINDOWS)

#define PYTHON_EXECUTABLE L"pythonw.exe"
#define EXECUTABLEPATH_VALUE L"WindowedExecutablePath"

#else

#define PYTHON_EXECUTABLE L"python.exe"
#define EXECUTABLEPATH_VALUE L"ExecutablePath"

#endif
#endif

#define MAX_VERSION_SIZE    8

typedef struct {
    wchar_t version[MAX_VERSION_SIZE]; /* m.n */
    int bits;   /* 32 or 64 */
    wchar_t executable[MAX_PATH];
    wchar_t exe_display[MAX_PATH];
} INSTALLED_PYTHON;

/*
 * To avoid messing about with heap allocations, just assume we can allocate
 * statically and never have to deal with more versions than this.
 */
#define MAX_INSTALLED_PYTHONS   100

static INSTALLED_PYTHON installed_pythons[MAX_INSTALLED_PYTHONS];

static size_t num_installed_pythons = 0;

/*
 * To hold SOFTWARE\Python\PythonCore\X.Y...\InstallPath
 * The version name can be longer than MAX_VERSION_SIZE, but will be
 * truncated to just X.Y for comparisons.
 */
#define IP_BASE_SIZE 80
#define IP_VERSION_SIZE 8
#define IP_SIZE (IP_BASE_SIZE + IP_VERSION_SIZE)
#define CORE_PATH L"SOFTWARE\\Python\\PythonCore"
/*
 * Installations from the Microsoft Store will set the same registry keys,
 * but because of a limitation in Windows they cannot be enumerated normally
 * (unless you have no other Python installations... which is probably false
 * because that's the most likely way to get this launcher!)
 * This key is under HKEY_LOCAL_MACHINE
 */
#define LOOKASIDE_PATH L"SOFTWARE\\Microsoft\\AppModel\\Lookaside\\user\\Software\\Python\\PythonCore"

static wchar_t * location_checks[] = {
    L"\\",
    L"\\PCbuild\\win32\\",
    L"\\PCbuild\\amd64\\",
    /* To support early 32bit versions of Python that stuck the build binaries
    * directly in PCbuild... */
    L"\\PCbuild\\",
    NULL
};

static INSTALLED_PYTHON *
find_existing_python(const wchar_t * path)
{
    INSTALLED_PYTHON * result = NULL;
    size_t i;
    INSTALLED_PYTHON * ip;

    for (i = 0, ip = installed_pythons; i < num_installed_pythons; i++, ip++) {
        if (_wcsicmp(path, ip->executable) == 0) {
            result = ip;
            break;
        }
    }
    return result;
}

static INSTALLED_PYTHON *
find_existing_python2(int bits, const wchar_t * version)
{
    INSTALLED_PYTHON * result = NULL;
    size_t i;
    INSTALLED_PYTHON * ip;

    for (i = 0, ip = installed_pythons; i < num_installed_pythons; i++, ip++) {
        if (bits == ip->bits && _wcsicmp(version, ip->version) == 0) {
            result = ip;
            break;
        }
    }
    return result;
}

static void
_locate_pythons_for_key(HKEY root, LPCWSTR subkey, REGSAM flags, int bits,
                        int display_name_only)
{
    HKEY core_root, ip_key;
    LSTATUS status = RegOpenKeyExW(root, subkey, 0, flags, &core_root);
    wchar_t message[MSGSIZE];
    DWORD i;
    size_t n;
    BOOL ok, append_name;
    DWORD type, data_size, attrs;
    INSTALLED_PYTHON * ip, * pip;
    wchar_t ip_version[IP_VERSION_SIZE];
    wchar_t ip_path[IP_SIZE];
    wchar_t * check;
    wchar_t ** checkp;
    wchar_t *key_name = (root == HKEY_LOCAL_MACHINE) ? L"HKLM" : L"HKCU";

    if (status != ERROR_SUCCESS)
        debug(L"locate_pythons_for_key: unable to open PythonCore key in %ls\n",
              key_name);
    else {
        ip = &installed_pythons[num_installed_pythons];
        for (i = 0; num_installed_pythons < MAX_INSTALLED_PYTHONS; i++) {
            status = RegEnumKeyW(core_root, i, ip_version, IP_VERSION_SIZE);
            if (status != ERROR_SUCCESS) {
                if (status != ERROR_NO_MORE_ITEMS) {
                    /* unexpected error */
                    winerror(status, message, MSGSIZE);
                    debug(L"Can't enumerate registry key for version %ls: %ls\n",
                          ip_version, message);
                }
                break;
            }
            else {
                wcsncpy_s(ip->version, MAX_VERSION_SIZE, ip_version,
                          MAX_VERSION_SIZE-1);
                /* Still treating version as "x.y" rather than sys.winver
                 * When PEP 514 tags are properly used, we shouldn't need
                 * to strip this off here.
                 */
                check = wcsrchr(ip->version, L'-');
                if (check && !wcscmp(check, L"-32")) {
                    *check = L'\0';
                }
                _snwprintf_s(ip_path, IP_SIZE, _TRUNCATE,
                             L"%ls\\%ls\\InstallPath", subkey, ip_version);
                status = RegOpenKeyExW(root, ip_path, 0, flags, &ip_key);
                if (status != ERROR_SUCCESS) {
                    winerror(status, message, MSGSIZE);
                    /* Note: 'message' already has a trailing \n*/
                    debug(L"%ls\\%ls: %ls", key_name, ip_path, message);
                    continue;
                }
                data_size = sizeof(ip->executable) - 1;
                append_name = FALSE;
#ifdef EXECUTABLEPATH_VALUE
                status = RegQueryValueExW(ip_key, EXECUTABLEPATH_VALUE, NULL, &type,
                                          (LPBYTE)ip->executable, &data_size);
#else
                status = ERROR_FILE_NOT_FOUND; /* actual error doesn't matter */
#endif
                if (status != ERROR_SUCCESS || type != REG_SZ || !data_size) {
                    append_name = TRUE;
                    data_size = sizeof(ip->executable) - 1;
                    status = RegQueryValueExW(ip_key, NULL, NULL, &type,
                                              (LPBYTE)ip->executable, &data_size);
                    if (status != ERROR_SUCCESS) {
                        winerror(status, message, MSGSIZE);
                        debug(L"%ls\\%ls: %ls\n", key_name, ip_path, message);
                        RegCloseKey(ip_key);
                        continue;
                    }
                }
                RegCloseKey(ip_key);
                if (type != REG_SZ) {
                    continue;
                }

                data_size = data_size / sizeof(wchar_t) - 1;  /* for NUL */
                if (ip->executable[data_size - 1] == L'\\')
                    --data_size; /* reg value ended in a backslash */
                /* ip->executable is data_size long */
                for (checkp = location_checks; *checkp; ++checkp) {
                    check = *checkp;
                    if (append_name) {
                        _snwprintf_s(&ip->executable[data_size],
                                     MAX_PATH - data_size,
                                     MAX_PATH - data_size,
                                     L"%ls%ls", check, PYTHON_EXECUTABLE);
                    }
                    attrs = GetFileAttributesW(ip->executable);
                    if (attrs == INVALID_FILE_ATTRIBUTES) {
                        winerror(GetLastError(), message, MSGSIZE);
                        debug(L"locate_pythons_for_key: %ls: %ls",
                              ip->executable, message);
                    }
                    else if (attrs & FILE_ATTRIBUTE_DIRECTORY) {
                        debug(L"locate_pythons_for_key: '%ls' is a directory\n",
                              ip->executable, attrs);
                    }
                    else if (find_existing_python(ip->executable)) {
                        debug(L"locate_pythons_for_key: %ls: already found\n",
                              ip->executable);
                    }
                    else {
                        /* check the executable type. */
                        if (bits) {
                            ip->bits = bits;
                        } else {
                            ok = GetBinaryTypeW(ip->executable, &attrs);
                            if (!ok) {
                                debug(L"Failure getting binary type: %ls\n",
                                      ip->executable);
                            }
                            else {
                                if (attrs == SCS_64BIT_BINARY)
                                    ip->bits = 64;
                                else if (attrs == SCS_32BIT_BINARY)
                                    ip->bits = 32;
                                else
                                    ip->bits = 0;
                            }
                        }
                        if (ip->bits == 0) {
                            debug(L"locate_pythons_for_key: %ls: \
invalid binary type: %X\n",
                                  ip->executable, attrs);
                        }
                        else {
                            if (display_name_only) {
                                /* display just the executable name. This is
                                 * primarily for the Store installs */
                                const wchar_t *name = wcsrchr(ip->executable, L'\\');
                                if (name) {
                                    wcscpy_s(ip->exe_display, MAX_PATH, name+1);
                                }
                            }
                            if (wcschr(ip->executable, L' ') != NULL) {
                                /* has spaces, so quote, and set original as
                                 * the display name */
                                if (!ip->exe_display[0]) {
                                    wcscpy_s(ip->exe_display, MAX_PATH, ip->executable);
                                }
                                n = wcslen(ip->executable);
                                memmove(&ip->executable[1],
                                        ip->executable, n * sizeof(wchar_t));
                                ip->executable[0] = L'\"';
                                ip->executable[n + 1] = L'\"';
                                ip->executable[n + 2] = L'\0';
                            }
                            debug(L"locate_pythons_for_key: %ls \
is a %dbit executable\n",
                                ip->executable, ip->bits);
                            if (find_existing_python2(ip->bits, ip->version)) {
                                debug(L"locate_pythons_for_key: %ls-%i: already \
found\n", ip->version, ip->bits);
                            }
                            else {
                                ++num_installed_pythons;
                                pip = ip++;
                                if (num_installed_pythons >=
                                    MAX_INSTALLED_PYTHONS)
                                    break;
                            }
                        }
                    }
                }
            }
        }
        RegCloseKey(core_root);
    }
}

static int
compare_pythons(const void * p1, const void * p2)
{
    INSTALLED_PYTHON * ip1 = (INSTALLED_PYTHON *) p1;
    INSTALLED_PYTHON * ip2 = (INSTALLED_PYTHON *) p2;
    /* note reverse sorting on version */
    int result = CompareStringW(LOCALE_INVARIANT, SORT_DIGITSASNUMBERS,
                                ip2->version, -1, ip1->version, -1);
    switch (result) {
    case 0:
        error(0, L"CompareStringW failed");
        return 0;
    case CSTR_LESS_THAN:
        return -1;
    case CSTR_EQUAL:
        return ip2->bits - ip1->bits; /* 64 before 32 */
    case CSTR_GREATER_THAN:
        return 1;
    default:
        return 0; // This should never be reached.
    }
}

static void
locate_pythons_for_key(HKEY root, REGSAM flags)
{
    _locate_pythons_for_key(root, CORE_PATH, flags, 0, FALSE);
}

static void
locate_store_pythons()
{
#if defined(_M_X64)
    /* 64bit process, so look in native registry */
    _locate_pythons_for_key(HKEY_LOCAL_MACHINE, LOOKASIDE_PATH,
                            KEY_READ, 64, TRUE);
#else
    /* 32bit process, so check that we're on 64bit OS */
    BOOL f64 = FALSE;
    if (IsWow64Process(GetCurrentProcess(), &f64) && f64) {
        _locate_pythons_for_key(HKEY_LOCAL_MACHINE, LOOKASIDE_PATH,
                                KEY_READ | KEY_WOW64_64KEY, 64, TRUE);
    }
#endif
}

static void
locate_venv_python()
{
    static wchar_t venv_python[MAX_PATH];
    INSTALLED_PYTHON * ip;
    wchar_t *virtual_env = get_env(L"VIRTUAL_ENV");
    DWORD attrs;

    /* Check for VIRTUAL_ENV environment variable */
    if (virtual_env == NULL || virtual_env[0] == L'\0') {
        return;
    }

    /* Check for a python executable in the venv */
    debug(L"Checking for Python executable in virtual env '%ls'\n", virtual_env);
    _snwprintf_s(venv_python, MAX_PATH, _TRUNCATE,
            L"%ls\\Scripts\\%ls", virtual_env, PYTHON_EXECUTABLE);
    attrs = GetFileAttributesW(venv_python);
    if (attrs == INVALID_FILE_ATTRIBUTES) {
        debug(L"Python executable %ls missing from virtual env\n", venv_python);
        return;
    }

    ip = &installed_pythons[num_installed_pythons++];
    wcscpy_s(ip->executable, MAX_PATH, venv_python);
    ip->bits = 0;
    wcscpy_s(ip->version, MAX_VERSION_SIZE, L"venv");
}

static void
locate_all_pythons()
{
    /* venv Python is highest priority */
    locate_venv_python();
#if defined(_M_X64)
    /* If we are a 64bit process, first hit the 32bit keys. */
    debug(L"locating Pythons in 32bit registry\n");
    locate_pythons_for_key(HKEY_CURRENT_USER, KEY_READ | KEY_WOW64_32KEY);
    locate_pythons_for_key(HKEY_LOCAL_MACHINE, KEY_READ | KEY_WOW64_32KEY);
#else
    /* If we are a 32bit process on a 64bit Windows, first hit the 64bit keys.*/
    BOOL f64 = FALSE;
    if (IsWow64Process(GetCurrentProcess(), &f64) && f64) {
        debug(L"locating Pythons in 64bit registry\n");
        locate_pythons_for_key(HKEY_CURRENT_USER, KEY_READ | KEY_WOW64_64KEY);
        locate_pythons_for_key(HKEY_LOCAL_MACHINE, KEY_READ | KEY_WOW64_64KEY);
    }
#endif
    /* now hit the "native" key for this process bittedness. */
    debug(L"locating Pythons in native registry\n");
    locate_pythons_for_key(HKEY_CURRENT_USER, KEY_READ);
    locate_pythons_for_key(HKEY_LOCAL_MACHINE, KEY_READ);
    /* Store-installed Python is lowest priority */
    locate_store_pythons();
    qsort(installed_pythons, num_installed_pythons, sizeof(INSTALLED_PYTHON),
          compare_pythons);
}

static INSTALLED_PYTHON *
find_python_by_version(wchar_t const * wanted_ver)
{
    INSTALLED_PYTHON * result = NULL;
    INSTALLED_PYTHON * ip = installed_pythons;
    size_t i, n;
    size_t wlen = wcslen(wanted_ver);
    int bits = 0;

    if (wcsstr(wanted_ver, L"-32")) {
        bits = 32;
        wlen -= wcslen(L"-32");
    }
    else if (wcsstr(wanted_ver, L"-64")) { /* Added option to select 64 bit explicitly */
        bits = 64;
        wlen -= wcslen(L"-64");
    }
    for (i = 0; i < num_installed_pythons; i++, ip++) {
        n = wcslen(ip->version);
        if (n > wlen)
            n = wlen;
        if ((wcsncmp(ip->version, wanted_ver, n) == 0) &&
            /* bits == 0 => don't care */
            ((bits == 0) || (ip->bits == bits))) {
            result = ip;
            break;
        }
    }
    return result;
}


static wchar_t appdata_ini_path[MAX_PATH];
static wchar_t launcher_ini_path[MAX_PATH];

/*
 * Get a value either from the environment or a configuration file.
 * The key passed in will either be "python", "python2" or "python3".
 */
static wchar_t *
get_configured_value(wchar_t * key)
{
/*
 * Note: this static value is used to return a configured value
 * obtained either from the environment or configuration file.
 * This should be OK since there wouldn't be any concurrent calls.
 */
    static wchar_t configured_value[MSGSIZE];
    wchar_t * result = NULL;
    wchar_t * found_in = L"environment";
    DWORD size;

    /* First, search the environment. */
    _snwprintf_s(configured_value, MSGSIZE, _TRUNCATE, L"py_%ls", key);
    result = get_env(configured_value);
    if (result == NULL && appdata_ini_path[0]) {
        /* Not in environment: check local configuration. */
        size = GetPrivateProfileStringW(L"defaults", key, NULL,
                                        configured_value, MSGSIZE,
                                        appdata_ini_path);
        if (size > 0) {
            result = configured_value;
            found_in = appdata_ini_path;
        }
    }
    if (result == NULL && launcher_ini_path[0]) {
        /* Not in environment or local: check global configuration. */
        size = GetPrivateProfileStringW(L"defaults", key, NULL,
                                        configured_value, MSGSIZE,
                                        launcher_ini_path);
        if (size > 0) {
            result = configured_value;
            found_in = launcher_ini_path;
        }
    }
    if (result) {
        debug(L"found configured value '%ls=%ls' in %ls\n",
              key, result, found_in ? found_in : L"(unknown)");
    } else {
        debug(L"found no configured value for '%ls'\n", key);
    }
    return result;
}

static INSTALLED_PYTHON *
locate_python(wchar_t * wanted_ver, BOOL from_shebang)
{
    static wchar_t config_key [] = { L"pythonX" };
    static wchar_t * last_char = &config_key[sizeof(config_key) /
                                             sizeof(wchar_t) - 2];
    INSTALLED_PYTHON * result = NULL;
    size_t n = wcslen(wanted_ver);
    wchar_t * configured_value;

    if (num_installed_pythons == 0)
        locate_all_pythons();

    if (n == 1) {   /* just major version specified */
        *last_char = *wanted_ver;
        configured_value = get_configured_value(config_key);
        if (configured_value != NULL)
            wanted_ver = configured_value;
    }
    if (*wanted_ver) {
        result = find_python_by_version(wanted_ver);
        debug(L"search for Python version '%ls' found ", wanted_ver);
        if (result) {
            debug(L"'%ls'\n", result->executable);
        } else {
            debug(L"no interpreter\n");
        }
    }
    else {
        *last_char = L'\0'; /* look for an overall default */
        result = find_python_by_version(L"venv");
        if (result == NULL) {
            configured_value = get_configured_value(config_key);
            if (configured_value)
                result = find_python_by_version(configured_value);
        }
        /* Not found a value yet - try by major version.
         * If we're looking for an interpreter specified in a shebang line,
         * we want to try Python 2 first, then Python 3 (for Unix and backward
         * compatibility). If we're being called interactively, assume the user
         * wants the latest version available, so try Python 3 first, then
         * Python 2.
         */
        if (result == NULL)
            result = find_python_by_version(from_shebang ? L"2" : L"3");
        if (result == NULL)
            result = find_python_by_version(from_shebang ? L"3" : L"2");
        debug(L"search for default Python found ");
        if (result) {
            debug(L"version %ls at '%ls'\n",
                  result->version, result->executable);
        } else {
            debug(L"no interpreter\n");
        }
    }
    return result;
}

#if defined(SCRIPT_WRAPPER)
/*
 * Check for a script located alongside the executable
 */

#if defined(_WINDOWS)
#define SCRIPT_SUFFIX L"-script.pyw"
#else
#define SCRIPT_SUFFIX L"-script.py"
#endif

static wchar_t wrapped_script_path[MAX_PATH];

/* Locate the script being wrapped.
 *
 * This code should store the name of the wrapped script in
 * wrapped_script_path, or terminate the program with an error if there is no
 * valid wrapped script file.
 */
static void
locate_wrapped_script()
{
    wchar_t * p;
    size_t plen;
    DWORD attrs;

    plen = GetModuleFileNameW(NULL, wrapped_script_path, MAX_PATH);
    p = wcsrchr(wrapped_script_path, L'.');
    if (p == NULL) {
        debug(L"GetModuleFileNameW returned value has no extension: %ls\n",
              wrapped_script_path);
        error(RC_NO_SCRIPT, L"Wrapper name '%ls' is not valid.", wrapped_script_path);
    }

    wcsncpy_s(p, MAX_PATH - (p - wrapped_script_path) + 1, SCRIPT_SUFFIX, _TRUNCATE);
    attrs = GetFileAttributesW(wrapped_script_path);
    if (attrs == INVALID_FILE_ATTRIBUTES) {
        debug(L"File '%ls' non-existent\n", wrapped_script_path);
        error(RC_NO_SCRIPT, L"Script file '%ls' is not present.", wrapped_script_path);
    }

    debug(L"Using wrapped script file '%ls'\n", wrapped_script_path);
}
#endif

/*
 * Process creation code
 */

static BOOL
safe_duplicate_handle(HANDLE in, HANDLE * pout)
{
    BOOL ok;
    HANDLE process = GetCurrentProcess();
    DWORD rc;

    *pout = NULL;
    ok = DuplicateHandle(process, in, process, pout, 0, TRUE,
                         DUPLICATE_SAME_ACCESS);
    if (!ok) {
        rc = GetLastError();
        if (rc == ERROR_INVALID_HANDLE) {
            debug(L"DuplicateHandle returned ERROR_INVALID_HANDLE\n");
            ok = TRUE;
        }
        else {
            debug(L"DuplicateHandle returned %d\n", rc);
        }
    }
    return ok;
}

static BOOL WINAPI
ctrl_c_handler(DWORD code)
{
    return TRUE;    /* We just ignore all control events. */
}

static void
run_child(wchar_t * cmdline)
{
    HANDLE job;
    JOBOBJECT_EXTENDED_LIMIT_INFORMATION info;
    DWORD rc;
    BOOL ok;
    STARTUPINFOW si;
    PROCESS_INFORMATION pi;

#if defined(_WINDOWS)
    /*
    When explorer launches a Windows (GUI) application, it displays
    the "app starting" (the "pointer + hourglass") cursor for a number
    of seconds, or until the app does something UI-ish (eg, creating a
    window, or fetching a message).  As this launcher doesn't do this
    directly, that cursor remains even after the child process does these
    things.  We avoid that by doing a simple post+get message.
    See http://bugs.python.org/issue17290 and
    https://bitbucket.org/vinay.sajip/pylauncher/issue/20/busy-cursor-for-a-long-time-when-running
    */
    MSG msg;

    PostMessage(0, 0, 0, 0);
    GetMessage(&msg, 0, 0, 0);
#endif

    debug(L"run_child: about to run '%ls'\n", cmdline);
    job = CreateJobObject(NULL, NULL);
    ok = QueryInformationJobObject(job, JobObjectExtendedLimitInformation,
                                  &info, sizeof(info), &rc);
    if (!ok || (rc != sizeof(info)) || !job)
        error(RC_CREATE_PROCESS, L"Job information querying failed");
    info.BasicLimitInformation.LimitFlags |= JOB_OBJECT_LIMIT_KILL_ON_JOB_CLOSE |
                                             JOB_OBJECT_LIMIT_SILENT_BREAKAWAY_OK;
    ok = SetInformationJobObject(job, JobObjectExtendedLimitInformation, &info,
                                 sizeof(info));
    if (!ok)
        error(RC_CREATE_PROCESS, L"Job information setting failed");
    memset(&si, 0, sizeof(si));
    GetStartupInfoW(&si);
    ok = safe_duplicate_handle(GetStdHandle(STD_INPUT_HANDLE), &si.hStdInput);
    if (!ok)
        error(RC_NO_STD_HANDLES, L"stdin duplication failed");
    ok = safe_duplicate_handle(GetStdHandle(STD_OUTPUT_HANDLE), &si.hStdOutput);
    if (!ok)
        error(RC_NO_STD_HANDLES, L"stdout duplication failed");
    ok = safe_duplicate_handle(GetStdHandle(STD_ERROR_HANDLE), &si.hStdError);
    if (!ok)
        error(RC_NO_STD_HANDLES, L"stderr duplication failed");

    ok = SetConsoleCtrlHandler(ctrl_c_handler, TRUE);
    if (!ok)
        error(RC_CREATE_PROCESS, L"control handler setting failed");

    si.dwFlags = STARTF_USESTDHANDLES;
    ok = CreateProcessW(NULL, cmdline, NULL, NULL, TRUE,
                        0, NULL, NULL, &si, &pi);
    if (!ok)
        error(RC_CREATE_PROCESS, L"Unable to create process using '%ls'", cmdline);
    AssignProcessToJobObject(job, pi.hProcess);
    CloseHandle(pi.hThread);
    WaitForSingleObjectEx(pi.hProcess, INFINITE, FALSE);
    ok = GetExitCodeProcess(pi.hProcess, &rc);
    if (!ok)
        error(RC_CREATE_PROCESS, L"Failed to get exit code of process");
    debug(L"child process exit code: %d\n", rc);
    exit(rc);
}

static void
invoke_child(wchar_t * executable, wchar_t * suffix, wchar_t * cmdline)
{
    wchar_t * child_command;
    size_t child_command_size;
    BOOL no_suffix = (suffix == NULL) || (*suffix == L'\0');
    BOOL no_cmdline = (*cmdline == L'\0');

    if (no_suffix && no_cmdline)
        run_child(executable);
    else {
        if (no_suffix) {
            /* add 2 for space separator + terminating NUL. */
            child_command_size = wcslen(executable) + wcslen(cmdline) + 2;
        }
        else {
            /* add 3 for 2 space separators + terminating NUL. */
            child_command_size = wcslen(executable) + wcslen(suffix) +
                                    wcslen(cmdline) + 3;
        }
        child_command = calloc(child_command_size, sizeof(wchar_t));
        if (child_command == NULL)
            error(RC_CREATE_PROCESS, L"unable to allocate %zd bytes for child command.",
                  child_command_size);
        if (no_suffix)
            _snwprintf_s(child_command, child_command_size,
                         child_command_size - 1, L"%ls %ls",
                         executable, cmdline);
        else
            _snwprintf_s(child_command, child_command_size,
                         child_command_size - 1, L"%ls %ls %ls",
                         executable, suffix, cmdline);
        run_child(child_command);
        free(child_command);
    }
}

typedef struct {
    wchar_t *shebang;
    BOOL search;
} SHEBANG;

static SHEBANG builtin_virtual_paths [] = {
    { L"/usr/bin/env python", TRUE },
    { L"/usr/bin/python", FALSE },
    { L"/usr/local/bin/python", FALSE },
    { L"python", FALSE },
    { NULL, FALSE },
};

/* For now, a static array of commands. */

#define MAX_COMMANDS 100

typedef struct {
    wchar_t key[MAX_PATH];
    wchar_t value[MSGSIZE];
} COMMAND;

static COMMAND commands[MAX_COMMANDS];
static int num_commands = 0;

#if defined(SKIP_PREFIX)

static wchar_t * builtin_prefixes [] = {
    /* These must be in an order that the longest matches should be found,
     * i.e. if the prefix is "/usr/bin/env ", it should match that entry
     * *before* matching "/usr/bin/".
     */
    L"/usr/bin/env ",
    L"/usr/bin/",
    L"/usr/local/bin/",
    NULL
};

static wchar_t * skip_prefix(wchar_t * name)
{
    wchar_t ** pp = builtin_prefixes;
    wchar_t * result = name;
    wchar_t * p;
    size_t n;

    for (; p = *pp; pp++) {
        n = wcslen(p);
        if (_wcsnicmp(p, name, n) == 0) {
            result += n;   /* skip the prefix */
            if (p[n - 1] == L' ') /* No empty strings in table, so n > 1 */
                result = skip_whitespace(result);
            break;
        }
    }
    return result;
}

#endif

#if defined(SEARCH_PATH)

static COMMAND path_command;

static COMMAND * find_on_path(wchar_t * name)
{
    wchar_t * pathext;
    size_t    varsize;
    wchar_t * context = NULL;
    wchar_t * extension;
    COMMAND * result = NULL;
    DWORD     len;
    errno_t   rc;

    wcscpy_s(path_command.key, MAX_PATH, name);
    if (wcschr(name, L'.') != NULL) {
        /* assume it has an extension. */
        len = SearchPathW(NULL, name, NULL, MSGSIZE, path_command.value, NULL);
        if (len) {
            result = &path_command;
        }
    }
    else {
        /* No extension - search using registered extensions. */
        rc = _wdupenv_s(&pathext, &varsize, L"PATHEXT");
        if (rc == 0) {
            extension = wcstok_s(pathext, L";", &context);
            while (extension) {
                len = SearchPathW(NULL, name, extension, MSGSIZE, path_command.value, NULL);
                if (len) {
                    result = &path_command;
                    break;
                }
                extension = wcstok_s(NULL, L";", &context);
            }
            free(pathext);
        }
    }
    return result;
}

#endif

static COMMAND * find_command(wchar_t * name)
{
    COMMAND * result = NULL;
    COMMAND * cp = commands;
    int i;

    for (i = 0; i < num_commands; i++, cp++) {
        if (_wcsicmp(cp->key, name) == 0) {
            result = cp;
            break;
        }
    }
#if defined(SEARCH_PATH)
    if (result == NULL)
        result = find_on_path(name);
#endif
    return result;
}

static void
update_command(COMMAND * cp, wchar_t * name, wchar_t * cmdline)
{
    wcsncpy_s(cp->key, MAX_PATH, name, _TRUNCATE);
    wcsncpy_s(cp->value, MSGSIZE, cmdline, _TRUNCATE);
}

static void
add_command(wchar_t * name, wchar_t * cmdline)
{
    if (num_commands >= MAX_COMMANDS) {
        debug(L"can't add %ls = '%ls': no room\n", name, cmdline);
    }
    else {
        COMMAND * cp = &commands[num_commands++];

        update_command(cp, name, cmdline);
    }
}

static void
read_config_file(wchar_t * config_path)
{
    wchar_t keynames[MSGSIZE];
    wchar_t value[MSGSIZE];
    DWORD read;
    wchar_t * key;
    COMMAND * cp;
    wchar_t * cmdp;

    read = GetPrivateProfileStringW(L"commands", NULL, NULL, keynames, MSGSIZE,
                                    config_path);
    if (read == MSGSIZE - 1) {
        debug(L"read_commands: %ls: not enough space for names\n", config_path);
    }
    key = keynames;
    while (*key) {
        read = GetPrivateProfileStringW(L"commands", key, NULL, value, MSGSIZE,
                                       config_path);
        if (read == MSGSIZE - 1) {
            debug(L"read_commands: %ls: not enough space for %ls\n",
                  config_path, key);
        }
        cmdp = skip_whitespace(value);
        if (*cmdp) {
            cp = find_command(key);
            if (cp == NULL)
                add_command(key, value);
            else
                update_command(cp, key, value);
        }
        key += wcslen(key) + 1;
    }
}

static void read_commands()
{
    if (launcher_ini_path[0])
        read_config_file(launcher_ini_path);
    if (appdata_ini_path[0])
        read_config_file(appdata_ini_path);
}

static BOOL
parse_shebang(wchar_t * shebang_line, int nchars, wchar_t ** command,
              wchar_t ** suffix, BOOL *search)
{
    BOOL rc = FALSE;
    SHEBANG * vpp;
    size_t plen;
    wchar_t * p;
    wchar_t zapped;
    wchar_t * endp = shebang_line + nchars - 1;
    COMMAND * cp;
    wchar_t * skipped;

    *command = NULL;    /* failure return */
    *suffix = NULL;
    *search = FALSE;

    if ((*shebang_line++ == L'#') && (*shebang_line++ == L'!')) {
        shebang_line = skip_whitespace(shebang_line);
        if (*shebang_line) {
            *command = shebang_line;
            for (vpp = builtin_virtual_paths; vpp->shebang; ++vpp) {
                plen = wcslen(vpp->shebang);
                if (wcsncmp(shebang_line, vpp->shebang, plen) == 0) {
                    rc = TRUE;
                    *search = vpp->search;
                    /* We can do this because all builtin commands contain
                     * "python".
                     */
                    *command = wcsstr(shebang_line, L"python");
                    break;
                }
            }
            if (vpp->shebang == NULL) {
                /*
                 * Not found in builtins - look in customized commands.
                 *
                 * We can't permanently modify the shebang line in case
                 * it's not a customized command, but we can temporarily
                 * stick a NUL after the command while searching for it,
                 * then put back the char we zapped.
                 */
#if defined(SKIP_PREFIX)
                skipped = skip_prefix(shebang_line);
#else
                skipped = shebang_line;
#endif
                p = wcspbrk(skipped, L" \t\r\n");
                if (p != NULL) {
                    zapped = *p;
                    *p = L'\0';
                }
                cp = find_command(skipped);
                if (p != NULL)
                    *p = zapped;
                if (cp != NULL) {
                    *command = cp->value;
                    if (p != NULL)
                        *suffix = skip_whitespace(p);
                }
            }
            /* remove trailing whitespace */
            while ((endp > shebang_line) && isspace(*endp))
                --endp;
            if (endp > shebang_line)
                endp[1] = L'\0';
        }
    }
    return rc;
}

/* #define CP_UTF8             65001 defined in winnls.h */
#define CP_UTF16LE          1200
#define CP_UTF16BE          1201
#define CP_UTF32LE          12000
#define CP_UTF32BE          12001

typedef struct {
    int length;
    char sequence[4];
    UINT code_page;
} BOM;

/*
 * Strictly, we don't need to handle UTF-16 and UTF-32, since Python itself
 * doesn't. Never mind, one day it might - there's no harm leaving it in.
 */
static BOM BOMs[] = {
    { 3, { 0xEF, 0xBB, 0xBF }, CP_UTF8 },           /* UTF-8 - keep first */
    /* Test UTF-32LE before UTF-16LE since UTF-16LE BOM is a prefix
     * of UTF-32LE BOM. */
    { 4, { 0xFF, 0xFE, 0x00, 0x00 }, CP_UTF32LE },  /* UTF-32LE */
    { 4, { 0x00, 0x00, 0xFE, 0xFF }, CP_UTF32BE },  /* UTF-32BE */
    { 2, { 0xFF, 0xFE }, CP_UTF16LE },              /* UTF-16LE */
    { 2, { 0xFE, 0xFF }, CP_UTF16BE },              /* UTF-16BE */
    { 0 }                                           /* sentinel */
};

static BOM *
find_BOM(char * buffer)
{
/*
 * Look for a BOM in the input and return a pointer to the
 * corresponding structure, or NULL if not found.
 */
    BOM * result = NULL;
    BOM *bom;

    for (bom = BOMs; bom->length; bom++) {
        if (strncmp(bom->sequence, buffer, bom->length) == 0) {
            result = bom;
            break;
        }
    }
    return result;
}

static char *
find_terminator(char * buffer, int len, BOM *bom)
{
    char * result = NULL;
    char * end = buffer + len;
    char  * p;
    char c;
    int cp;

    for (p = buffer; p < end; p++) {
        c = *p;
        if (c == '\r') {
            result = p;
            break;
        }
        if (c == '\n') {
            result = p;
            break;
        }
    }
    if (result != NULL) {
        cp = bom->code_page;

        /* adjustments to include all bytes of the char */
        /* no adjustment needed for UTF-8 or big endian */
        if (cp == CP_UTF16LE)
            ++result;
        else if (cp == CP_UTF32LE)
            result += 3;
        ++result; /* point just past terminator */
    }
    return result;
}

static BOOL
validate_version(wchar_t * p)
{
    /*
    Version information should start with the major version,
    Optionally followed by a period and a minor version,
    Optionally followed by a minus and one of 32 or 64.
    Valid examples:
      2
      3
      2.7
      3.6
      2.7-32
      The intent is to add to the valid patterns:
      3.10
      3-32
      3.6-64
      3-64
    */
    BOOL result = (p != NULL); /* Default to False if null pointer. */

    result = result && iswdigit(*p);  /* Result = False if first string element is not a digit. */

    while (result && iswdigit(*p))   /* Require a major version */
        ++p;  /* Skip all leading digit(s) */
    if (result && (*p == L'.'))     /* Allow . for major minor separator.*/
    {
        result = iswdigit(*++p);     /* Must be at least one digit */
        while (result && iswdigit(*++p)) ; /* Skip any more Digits */
    }
    if (result && (*p == L'-')) {   /* Allow - for Bits Separator */
        switch(*++p){
        case L'3':                            /* 3 is OK */
            result = (*++p == L'2') && !*++p; /* only if followed by 2 and ended.*/
            break;
        case L'6':                            /* 6 is OK */
            result = (*++p == L'4') && !*++p; /* only if followed by 4 and ended.*/
            break;
        default:
            result = FALSE;
            break;
        }
    }
    result = result && !*p; /* Must have reached EOS */
    return result;

}

typedef struct {
    unsigned short min;
    unsigned short max;
    wchar_t version[MAX_VERSION_SIZE];
} PYC_MAGIC;

static PYC_MAGIC magic_values[] = {
    { 50823, 50823, L"2.0" },
    { 60202, 60202, L"2.1" },
    { 60717, 60717, L"2.2" },
    { 62011, 62021, L"2.3" },
    { 62041, 62061, L"2.4" },
    { 62071, 62131, L"2.5" },
    { 62151, 62161, L"2.6" },
    { 62171, 62211, L"2.7" },
    { 3000, 3131, L"3.0" },
    { 3141, 3151, L"3.1" },
    { 3160, 3180, L"3.2" },
    { 3190, 3230, L"3.3" },
    { 3250, 3310, L"3.4" },
    { 3320, 3351, L"3.5" },
    { 3360, 3379, L"3.6" },
    { 3390, 3399, L"3.7" },
    { 3400, 3419, L"3.8" },
    { 3420, 3429, L"3.9" },
    { 3430, 3439, L"3.10" },
    { 0 }
};

static INSTALLED_PYTHON *
find_by_magic(unsigned short magic)
{
    INSTALLED_PYTHON * result = NULL;
    PYC_MAGIC * mp;

    for (mp = magic_values; mp->min; mp++) {
        if ((magic >= mp->min) && (magic <= mp->max)) {
            result = locate_python(mp->version, FALSE);
            if (result != NULL)
                break;
        }
    }
    return result;
}

static void
maybe_handle_shebang(wchar_t ** argv, wchar_t * cmdline)
{
/*
 * Look for a shebang line in the first argument.  If found
 * and we spawn a child process, this never returns.  If it
 * does return then we process the args "normally".
 *
 * argv[0] might be a filename with a shebang.
 */
    FILE * fp;
    errno_t rc = _wfopen_s(&fp, *argv, L"rb");
    char buffer[BUFSIZE];
    wchar_t shebang_line[BUFSIZE + 1];
    size_t read;
    char *p;
    char * start;
    char * shebang_alias = (char *) shebang_line;
    BOM* bom;
    int i, j, nchars = 0;
    int header_len;
    BOOL is_virt;
    BOOL search;
    wchar_t * command;
    wchar_t * suffix;
    COMMAND *cmd = NULL;
    INSTALLED_PYTHON * ip;

    if (rc == 0) {
        read = fread(buffer, sizeof(char), BUFSIZE, fp);
        debug(L"maybe_handle_shebang: read %zd bytes\n", read);
        fclose(fp);

        if ((read >= 4) && (buffer[3] == '\n') && (buffer[2] == '\r')) {
            ip = find_by_magic((((unsigned char)buffer[1]) << 8 |
                                (unsigned char)buffer[0]) & 0xFFFF);
            if (ip != NULL) {
                debug(L"script file is compiled against Python %ls\n",
                      ip->version);
                invoke_child(ip->executable, NULL, cmdline);
            }
        }
        /* Look for BOM */
        bom = find_BOM(buffer);
        if (bom == NULL) {
            start = buffer;
            debug(L"maybe_handle_shebang: BOM not found, using UTF-8\n");
            bom = BOMs; /* points to UTF-8 entry - the default */
        }
        else {
            debug(L"maybe_handle_shebang: BOM found, code page %u\n",
                  bom->code_page);
            start = &buffer[bom->length];
        }
        p = find_terminator(start, BUFSIZE, bom);
        /*
         * If no CR or LF was found in the heading,
         * we assume it's not a shebang file.
         */
        if (p == NULL) {
            debug(L"maybe_handle_shebang: No line terminator found\n");
        }
        else {
            /*
             * Found line terminator - parse the shebang.
             *
             * Strictly, we don't need to handle UTF-16 anf UTF-32,
             * since Python itself doesn't.
             * Never mind, one day it might.
             */
            header_len = (int) (p - start);
            switch(bom->code_page) {
            case CP_UTF8:
                nchars = MultiByteToWideChar(bom->code_page,
                                             0,
                                             start, header_len, shebang_line,
                                             BUFSIZE);
                break;
            case CP_UTF16BE:
                if (header_len % 2 != 0) {
                    debug(L"maybe_handle_shebang: UTF-16BE, but an odd number \
of bytes: %d\n", header_len);
                    /* nchars = 0; Not needed - initialised to 0. */
                }
                else {
                    for (i = header_len; i > 0; i -= 2) {
                        shebang_alias[i - 1] = start[i - 2];
                        shebang_alias[i - 2] = start[i - 1];
                    }
                    nchars = header_len / sizeof(wchar_t);
                }
                break;
            case CP_UTF16LE:
                if ((header_len % 2) != 0) {
                    debug(L"UTF-16LE, but an odd number of bytes: %d\n",
                          header_len);
                    /* nchars = 0; Not needed - initialised to 0. */
                }
                else {
                    /* no actual conversion needed. */
                    memcpy(shebang_line, start, header_len);
                    nchars = header_len / sizeof(wchar_t);
                }
                break;
            case CP_UTF32BE:
                if (header_len % 4 != 0) {
                    debug(L"UTF-32BE, but not divisible by 4: %d\n",
                          header_len);
                    /* nchars = 0; Not needed - initialised to 0. */
                }
                else {
                    for (i = header_len, j = header_len / 2; i > 0; i -= 4,
                                                                    j -= 2) {
                        shebang_alias[j - 1] = start[i - 2];
                        shebang_alias[j - 2] = start[i - 1];
                    }
                    nchars = header_len / sizeof(wchar_t);
                }
                break;
            case CP_UTF32LE:
                if (header_len % 4 != 0) {
                    debug(L"UTF-32LE, but not divisible by 4: %d\n",
                          header_len);
                    /* nchars = 0; Not needed - initialised to 0. */
                }
                else {
                    for (i = header_len, j = header_len / 2; i > 0; i -= 4,
                                                                    j -= 2) {
                        shebang_alias[j - 1] = start[i - 3];
                        shebang_alias[j - 2] = start[i - 4];
                    }
                    nchars = header_len / sizeof(wchar_t);
                }
                break;
            }
            if (nchars > 0) {
                shebang_line[--nchars] = L'\0';
                is_virt = parse_shebang(shebang_line, nchars, &command,
                                        &suffix, &search);
                if (command != NULL) {
                    debug(L"parse_shebang: found command: %ls\n", command);
                    if (!is_virt) {
                        invoke_child(command, suffix, cmdline);
                    }
                    else {
                        suffix = wcschr(command, L' ');
                        if (suffix != NULL) {
                            *suffix++ = L'\0';
                            suffix = skip_whitespace(suffix);
                        }
                        if (wcsncmp(command, L"python", 6))
                            error(RC_BAD_VIRTUAL_PATH, L"Unknown virtual \
path '%ls'", command);
                        command += 6;   /* skip past "python" */
                        if (search && ((*command == L'\0') || isspace(*command))) {
                            /* Command is eligible for path search, and there
                             * is no version specification.
                             */
                            debug(L"searching PATH for python executable\n");
                            cmd = find_on_path(PYTHON_EXECUTABLE);
                            debug(L"Python on path: %ls\n", cmd ? cmd->value : L"<not found>");
                            if (cmd) {
                                debug(L"located python on PATH: %ls\n", cmd->value);
                                invoke_child(cmd->value, suffix, cmdline);
                                /* Exit here, as we have found the command */
                                return;
                            }
                            /* FALL THROUGH: No python found on PATH, so fall
                             * back to locating the correct installed python.
                             */
                        }
                        if (*command && !validate_version(command))
                            error(RC_BAD_VIRTUAL_PATH, L"Invalid version \
specification: '%ls'.\nIn the first line of the script, 'python' needs to be \
followed by a valid version specifier.\nPlease check the documentation.",
                                  command);
                        /* TODO could call validate_version(command) */
                        ip = locate_python(command, TRUE);
                        if (ip == NULL) {
                            error(RC_NO_PYTHON, L"Requested Python version \
(%ls) is not installed", command);
                        }
                        else {
                            invoke_child(ip->executable, suffix, cmdline);
                        }
                    }
                }
            }
        }
    }
}

static wchar_t *
skip_me(wchar_t * cmdline)
{
    BOOL quoted;
    wchar_t c;
    wchar_t * result = cmdline;

    quoted = cmdline[0] == L'\"';
    if (!quoted)
        c = L' ';
    else {
        c = L'\"';
        ++result;
    }
    result = wcschr(result, c);
    if (result == NULL) /* when, for example, just exe name on command line */
        result = L"";
    else {
        ++result; /* skip past space or closing quote */
        result = skip_whitespace(result);
    }
    return result;
}

static DWORD version_high = 0;
static DWORD version_low = 0;

static void
get_version_info(wchar_t * version_text, size_t size)
{
    WORD maj, min, rel, bld;

    if (!version_high && !version_low)
        wcsncpy_s(version_text, size, L"0.1", _TRUNCATE);   /* fallback */
    else {
        maj = HIWORD(version_high);
        min = LOWORD(version_high);
        rel = HIWORD(version_low);
        bld = LOWORD(version_low);
        _snwprintf_s(version_text, size, _TRUNCATE, L"%d.%d.%d.%d", maj,
                     min, rel, bld);
    }
}

static void
show_help_text(wchar_t ** argv)
{
    wchar_t version_text [MAX_PATH];
#if defined(_M_X64)
    BOOL canDo64bit = TRUE;
#else
    /* If we are a 32bit process on a 64bit Windows, first hit the 64bit keys. */
    BOOL canDo64bit = FALSE;
    IsWow64Process(GetCurrentProcess(), &canDo64bit);
#endif

    get_version_info(version_text, MAX_PATH);
    fwprintf(stdout, L"\
Python Launcher for Windows Version %ls\n\n", version_text);
    fwprintf(stdout, L"\
usage:\n\
%ls [launcher-args] [python-args] [script [script-args]]\n\n", argv[0]);
    fputws(L"\
Launcher arguments:\n\n\
-2     : Launch the latest Python 2.x version\n\
-3     : Launch the latest Python 3.x version\n\
-X.Y   : Launch the specified Python version\n", stdout);
    if (canDo64bit) {
        fputws(L"\
     The above all default to 64 bit if a matching 64 bit python is present.\n\
-X.Y-32: Launch the specified 32bit Python version\n\
-X-32  : Launch the latest 32bit Python X version\n\
-X.Y-64: Launch the specified 64bit Python version\n\
-X-64  : Launch the latest 64bit Python X version", stdout);
    }
    fputws(L"\n-0  --list       : List the available pythons", stdout);
    fputws(L"\n-0p --list-paths : List with paths", stdout);
    fputws(L"\n\n If no script is specified the specified interpreter is opened.", stdout);
    fputws(L"\nIf an exact version is not given, using the latest version can be overridden by", stdout);
    fputws(L"\nany of the following, (in priority order):", stdout);
    fputws(L"\n An active virtual environment", stdout);
    fputws(L"\n A shebang line in the script (if present)", stdout);
    fputws(L"\n With -2 or -3 flag a matching PY_PYTHON2 or PY_PYTHON3 Enviroment variable", stdout);
    fputws(L"\n A PY_PYTHON Enviroment variable", stdout);
    fputws(L"\n From [defaults] in py.ini in your %LOCALAPPDATA%\\py.ini", stdout);
    fputws(L"\n From [defaults] in py.ini beside py.exe (use `where py` to locate)", stdout);
    fputws(L"\n\nThe following help text is from Python:\n\n", stdout);
    fflush(stdout);
}

static BOOL
show_python_list(wchar_t ** argv)
{
    /*
     * Display options -0
     */
    INSTALLED_PYTHON * result = NULL;
    INSTALLED_PYTHON * ip = installed_pythons; /* List of installed pythons */
    INSTALLED_PYTHON * defpy = locate_python(L"", FALSE);
    size_t i = 0;
    wchar_t *p = argv[1];
    wchar_t *ver_fmt = L"-%ls-%d";
    wchar_t *fmt = L"\n %ls";
    wchar_t *defind = L" *"; /* Default indicator */

    /*
    * Output informational messages to stderr to keep output
    * clean for use in pipes, etc.
    */
    fwprintf(stderr,
             L"Installed Pythons found by %s Launcher for Windows", argv[0]);
    if (!_wcsicmp(p, L"-0p") || !_wcsicmp(p, L"--list-paths"))
        fmt = L"\n %-15ls%ls"; /* include path */

    if (num_installed_pythons == 0) /* We have somehow got here without searching for pythons */
        locate_all_pythons(); /* Find them, Populates installed_pythons */

    if (num_installed_pythons == 0) /* No pythons found */
        fwprintf(stderr, L"\nNo Installed Pythons Found!");
    else
    {
        for (i = 0; i < num_installed_pythons; i++, ip++) {
            wchar_t version[BUFSIZ];
            if (wcscmp(ip->version, L"venv") == 0) {
                wcscpy_s(version, BUFSIZ, L"(venv)");
            }
            else {
                swprintf_s(version, BUFSIZ, ver_fmt, ip->version, ip->bits);
            }

            if (ip->exe_display[0]) {
                fwprintf(stdout, fmt, version, ip->exe_display);
            }
            else {
                fwprintf(stdout, fmt, version, ip->executable);
            }
            /* If there is a default indicate it */
            if (defpy == ip)
                fwprintf(stderr, defind);
        }
    }

    if ((defpy == NULL) && (num_installed_pythons > 0))
        /* We have pythons but none is the default */
        fwprintf(stderr, L"\n\nCan't find a Default Python.\n\n");
    else
        fwprintf(stderr, L"\n\n"); /* End with a blank line */
    return FALSE; /* If this has been called we cannot continue */
}

#if defined(VENV_REDIRECT)

static int
find_home_value(const char *buffer, const char **start, DWORD *length)
{
    for (const char *s = strstr(buffer, "home"); s; s = strstr(s + 1, "\nhome")) {
        if (*s == '\n') {
            ++s;
        }
        for (int i = 4; i > 0 && *s; --i, ++s);

        while (*s && iswspace(*s)) {
            ++s;
        }
        if (*s != L'=') {
            continue;
        }

        do {
            ++s;
        } while (*s && iswspace(*s));

        *start = s;
        char *nl = strchr(s, '\n');
        if (nl) {
            *length = (DWORD)((ptrdiff_t)nl - (ptrdiff_t)s);
        } else {
            *length = (DWORD)strlen(s);
        }
        return 1;
    }
    return 0;
}
#endif

static wchar_t *
wcsdup_pad(const wchar_t *s, int padding, int *newlen)
{
    size_t len = wcslen(s);
    len += 1 + padding;
    wchar_t *r = (wchar_t *)malloc(len * sizeof(wchar_t));
    if (!r) {
        return NULL;
    }
    if (wcscpy_s(r, len, s)) {
        free(r);
        return NULL;
    }
    *newlen = len < MAXINT ? (int)len : MAXINT;
    return r;
}

static wchar_t *
get_process_name()
{
    DWORD bufferLen = MAX_PATH;
    DWORD len = bufferLen;
    wchar_t *r = NULL;

    while (!r) {
        r = (wchar_t *)malloc(bufferLen * sizeof(wchar_t));
        if (!r) {
            error(RC_NO_MEMORY, L"out of memory");
            return NULL;
        }
        len = GetModuleFileNameW(NULL, r, bufferLen);
        if (len == 0) {
            free(r);
            error(0, L"Failed to get module name");
            return NULL;
        } else if (len == bufferLen &&
                   GetLastError() == ERROR_INSUFFICIENT_BUFFER) {
            free(r);
            r = NULL;
            bufferLen *= 2;
        }
    }

    return r;
}

static int
process(int argc, wchar_t ** argv)
{
    wchar_t * wp;
    wchar_t * command;
    wchar_t * executable;
    wchar_t * p;
    wchar_t * argv0;
    int rc = 0;
    INSTALLED_PYTHON * ip;
    BOOL valid;
    DWORD size, attrs;
    wchar_t message[MSGSIZE];
    void * version_data;
    VS_FIXEDFILEINFO * file_info;
    UINT block_size;
#if defined(VENV_REDIRECT)
    wchar_t * venv_cfg_path;
    int newlen;
#elif defined(SCRIPT_WRAPPER)
    wchar_t * newcommand;
    wchar_t * av[2];
    int newlen;
    HRESULT hr;
    int index;
#else
    HRESULT hr;
    int index;
#endif

    setvbuf(stderr, (char *)NULL, _IONBF, 0);
    wp = get_env(L"PYLAUNCH_DEBUG");
    if ((wp != NULL) && (*wp != L'\0'))
        log_fp = stderr;

#if defined(_M_X64)
    debug(L"launcher build: 64bit\n");
#else
    debug(L"launcher build: 32bit\n");
#endif
#if defined(_WINDOWS)
    debug(L"launcher executable: Windows\n");
#else
    debug(L"launcher executable: Console\n");
#endif
#if !defined(VENV_REDIRECT)
    /* Get the local appdata folder (non-roaming) */
    hr = SHGetFolderPathW(NULL, CSIDL_LOCAL_APPDATA,
                          NULL, 0, appdata_ini_path);
    if (hr != S_OK) {
        debug(L"SHGetFolderPath failed: %X\n", hr);
        appdata_ini_path[0] = L'\0';
    }
    else {
        wcsncat_s(appdata_ini_path, MAX_PATH, L"\\py.ini", _TRUNCATE);
        attrs = GetFileAttributesW(appdata_ini_path);
        if (attrs == INVALID_FILE_ATTRIBUTES) {
            debug(L"File '%ls' non-existent\n", appdata_ini_path);
            appdata_ini_path[0] = L'\0';
        } else {
            debug(L"Using local configuration file '%ls'\n", appdata_ini_path);
        }
    }
#endif
    argv0 = get_process_name();
    size = GetFileVersionInfoSizeW(argv0, &size);
    if (size == 0) {
        winerror(GetLastError(), message, MSGSIZE);
        debug(L"GetFileVersionInfoSize failed: %ls\n", message);
    }
    else {
        version_data = malloc(size);
        if (version_data) {
            valid = GetFileVersionInfoW(argv0, 0, size,
                                        version_data);
            if (!valid)
                debug(L"GetFileVersionInfo failed: %X\n", GetLastError());
            else {
                valid = VerQueryValueW(version_data, L"\\",
                                       (LPVOID *) &file_info, &block_size);
                if (!valid)
                    debug(L"VerQueryValue failed: %X\n", GetLastError());
                else {
                    version_high = file_info->dwFileVersionMS;
                    version_low = file_info->dwFileVersionLS;
                }
            }
            free(version_data);
        }
    }

#if defined(VENV_REDIRECT)
    /* Allocate some extra space for new filenames */
    venv_cfg_path = wcsdup_pad(argv0, 32, &newlen);
    if (!venv_cfg_path) {
        error(RC_NO_MEMORY, L"Failed to copy module name");
    }
    p = wcsrchr(venv_cfg_path, L'\\');

    if (p == NULL) {
        error(RC_NO_VENV_CFG, L"No pyvenv.cfg file");
    }
    p[0] = L'\0';
    wcscat_s(venv_cfg_path, newlen, L"\\pyvenv.cfg");
    attrs = GetFileAttributesW(venv_cfg_path);
    if (attrs == INVALID_FILE_ATTRIBUTES) {
        debug(L"File '%ls' non-existent\n", venv_cfg_path);
        p[0] = '\0';
        p = wcsrchr(venv_cfg_path, L'\\');
        if (p != NULL) {
            p[0] = '\0';
            wcscat_s(venv_cfg_path, newlen, L"\\pyvenv.cfg");
            attrs = GetFileAttributesW(venv_cfg_path);
            if (attrs == INVALID_FILE_ATTRIBUTES) {
                debug(L"File '%ls' non-existent\n", venv_cfg_path);
                error(RC_NO_VENV_CFG, L"No pyvenv.cfg file");
            }
        }
    }
    debug(L"Using venv configuration file '%ls'\n", venv_cfg_path);
#else
    /* Allocate some extra space for new filenames */
    if (wcscpy_s(launcher_ini_path, MAX_PATH, argv0)) {
        error(RC_NO_MEMORY, L"Failed to copy module name");
    }
    p = wcsrchr(launcher_ini_path, L'\\');

    if (p == NULL) {
        debug(L"GetModuleFileNameW returned value has no backslash: %ls\n",
              launcher_ini_path);
        launcher_ini_path[0] = L'\0';
    }
    else {
        p[0] = L'\0';
        wcscat_s(launcher_ini_path, MAX_PATH, L"\\py.ini");
        attrs = GetFileAttributesW(launcher_ini_path);
        if (attrs == INVALID_FILE_ATTRIBUTES) {
            debug(L"File '%ls' non-existent\n", launcher_ini_path);
            launcher_ini_path[0] = L'\0';
        } else {
            debug(L"Using global configuration file '%ls'\n", launcher_ini_path);
        }
    }
#endif

    command = skip_me(GetCommandLineW());
    debug(L"Called with command line: %ls\n", command);

#if !defined(VENV_REDIRECT)
    /* bpo-35811: The __PYVENV_LAUNCHER__ variable is used to
     * override sys.executable and locate the original prefix path.
     * However, if it is silently inherited by a non-venv Python
     * process, that process will believe it is running in the venv
     * still. This is the only place where *we* can clear it (that is,
     * when py.exe is being used to launch Python), so we do.
     */
    SetEnvironmentVariableW(L"__PYVENV_LAUNCHER__", NULL);
#endif

#if defined(SCRIPT_WRAPPER)
    /* The launcher is being used in "script wrapper" mode.
     * There should therefore be a Python script named <exename>-script.py in
     * the same directory as the launcher executable.
     * Put the script name into argv as the first (script name) argument.
     */

    /* Get the wrapped script name - if the script is not present, this will
     * terminate the program with an error.
     */
    locate_wrapped_script();

    /* Add the wrapped script to the start of command */
    newlen = wcslen(wrapped_script_path) + wcslen(command) + 2; /* ' ' + NUL */
    newcommand = malloc(sizeof(wchar_t) * newlen);
    if (!newcommand) {
        error(RC_NO_MEMORY, L"Could not allocate new command line");
    }
    else {
        wcscpy_s(newcommand, newlen, wrapped_script_path);
        wcscat_s(newcommand, newlen, L" ");
        wcscat_s(newcommand, newlen, command);
        debug(L"Running wrapped script with command line '%ls'\n", newcommand);
        read_commands();
        av[0] = wrapped_script_path;
        av[1] = NULL;
        maybe_handle_shebang(av, newcommand);
        /* Returns if no shebang line - pass to default processing */
        command = newcommand;
        valid = FALSE;
    }
#elif defined(VENV_REDIRECT)
    {
        FILE *f;
        char buffer[4096]; /* 4KB should be enough for anybody */
        char *start;
        DWORD len, cch, cch_actual;
        size_t cb;
        if (_wfopen_s(&f, venv_cfg_path, L"r")) {
            error(RC_BAD_VENV_CFG, L"Cannot read '%ls'", venv_cfg_path);
        }
        cb = fread_s(buffer, sizeof(buffer), sizeof(buffer[0]),
                     sizeof(buffer) / sizeof(buffer[0]), f);
        fclose(f);

        if (!find_home_value(buffer, &start, &len)) {
            error(RC_BAD_VENV_CFG, L"Cannot find home in '%ls'",
                  venv_cfg_path);
        }

        cch = MultiByteToWideChar(CP_UTF8, 0, start, len, NULL, 0);
        if (!cch) {
            error(0, L"Cannot determine memory for home path");
        }
        cch += (DWORD)wcslen(PYTHON_EXECUTABLE) + 1 + 1; /* include sep and null */
        executable = (wchar_t *)malloc(cch * sizeof(wchar_t));
        if (executable == NULL) {
            error(RC_NO_MEMORY, L"A memory allocation failed");
        }
        cch_actual = MultiByteToWideChar(CP_UTF8, 0, start, len, executable, cch);
        if (!cch_actual) {
            error(RC_BAD_VENV_CFG, L"Cannot decode home path in '%ls'",
                  venv_cfg_path);
        }
        if (executable[cch_actual - 1] != L'\\') {
            executable[cch_actual++] = L'\\';
            executable[cch_actual] = L'\0';
        }
        if (wcscat_s(executable, cch, PYTHON_EXECUTABLE)) {
            error(RC_BAD_VENV_CFG, L"Cannot create executable path from '%ls'",
                  venv_cfg_path);
        }
        if (GetFileAttributesW(executable) == INVALID_FILE_ATTRIBUTES) {
            error(RC_NO_PYTHON, L"No Python at '%ls'", executable);
        }
        if (!SetEnvironmentVariableW(L"__PYVENV_LAUNCHER__", argv0)) {
            error(0, L"Failed to set launcher environment");
        }
        valid = 1;
    }
#else
    if (argc <= 1) {
        valid = FALSE;
        p = NULL;
    }
    else {
        p = argv[1];
        if ((argc == 2) && // list version args
            (!wcsncmp(p, L"-0", wcslen(L"-0")) ||
            !wcsncmp(p, L"--list", wcslen(L"--list"))))
        {
            show_python_list(argv);
            return rc;
        }
        valid = valid && (*p == L'-') && validate_version(&p[1]);
        if (valid) {
            ip = locate_python(&p[1], FALSE);
            if (ip == NULL)
            {
                fwprintf(stdout, \
                         L"Python %ls not found!\n", &p[1]);
                valid = show_python_list(argv);
                error(RC_NO_PYTHON, L"Requested Python version (%ls) not \
installed, use -0 for available pythons", &p[1]);
            }
            executable = ip->executable;
            command += wcslen(p);
            command = skip_whitespace(command);
        }
        else {
            for (index = 1; index < argc; ++index) {
                if (*argv[index] != L'-')
                    break;
            }
            if (index < argc) {
                read_commands();
                maybe_handle_shebang(&argv[index], command);
            }
        }
    }
#endif

    if (!valid) {
        if ((argc == 2) && (!_wcsicmp(p, L"-h") || !_wcsicmp(p, L"--help")))
            show_help_text(argv);
        if ((argc == 2) &&
            (!_wcsicmp(p, L"-0") || !_wcsicmp(p, L"--list") ||
            !_wcsicmp(p, L"-0p") || !_wcsicmp(p, L"--list-paths")))
        {
            executable = NULL; /* Info call only */
        }
        else {
            /* look for the default Python */
            ip = locate_python(L"", FALSE);
            if (ip == NULL)
                error(RC_NO_PYTHON, L"Can't find a default Python.");
            executable = ip->executable;
        }
    }
    if (executable != NULL)
        invoke_child(executable, NULL, command);
    else
        rc = RC_NO_PYTHON;
    return rc;
}

#if defined(_WINDOWS)

int WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
                   LPWSTR lpstrCmd, int nShow)
{
    return process(__argc, __wargv);
}

#else

int cdecl wmain(int argc, wchar_t ** argv)
{
    return process(argc, argv);
}

#endif
