/* Return the initial module search path. */

#include "Python.h"
#include "marshal.h"              // PyMarshal_ReadObjectFromString
#include "osdefs.h"               // DELIM
#include "pycore_initconfig.h"
#include "pycore_fileutils.h"
#include "pycore_pathconfig.h"
#include "pycore_pymem.h"         // _PyMem_SetDefaultAllocator()
#include <wchar.h>

#ifdef MS_WINDOWS
#  include <windows.h>            // GetFullPathNameW(), MAX_PATH
#  include <pathcch.h>
#endif

#ifdef __APPLE__
#  include <mach-o/dyld.h>
#endif

/* Reference the precompiled getpath.py */
#include "../Python/frozen_modules/getpath.h"

#if (!defined(PREFIX) || !defined(EXEC_PREFIX) \
        || !defined(VERSION) || !defined(VPATH) \
        || !defined(PLATLIBDIR))
#error "PREFIX, EXEC_PREFIX, VERSION, VPATH and PLATLIBDIR macros must be defined"
#endif

#if !defined(PYTHONPATH)
#define PYTHONPATH NULL
#endif

#if !defined(PYDEBUGEXT)
#define PYDEBUGEXT NULL
#endif

#if !defined(PYWINVER)
#ifdef MS_DLL_ID
#define PYWINVER MS_DLL_ID
#else
#define PYWINVER NULL
#endif
#endif

#if !defined(EXE_SUFFIX)
#if defined(MS_WINDOWS) || defined(__CYGWIN__) || defined(__MINGW32__)
#define EXE_SUFFIX L".exe"
#else
#define EXE_SUFFIX NULL
#endif
#endif


/* HELPER FUNCTIONS for getpath.py */

static PyObject *
getpath_abspath(PyObject *Py_UNUSED(self), PyObject *args)
{
    PyObject *r = NULL;
    PyObject *pathobj;
    wchar_t *path;
    if (!PyArg_ParseTuple(args, "U", &pathobj)) {
        return NULL;
    }
    Py_ssize_t len;
    path = PyUnicode_AsWideCharString(pathobj, &len);
    if (path) {
        wchar_t *abs;
        if (_Py_abspath((const wchar_t *)_Py_normpath(path, -1), &abs) == 0 && abs) {
            r = PyUnicode_FromWideChar(abs, -1);
            PyMem_RawFree((void *)abs);
        } else {
            PyErr_SetString(PyExc_OSError, "failed to make path absolute");
        }
        PyMem_Free((void *)path);
    }
    return r;
}


static PyObject *
getpath_basename(PyObject *Py_UNUSED(self), PyObject *args)
{
    PyObject *path;
    if (!PyArg_ParseTuple(args, "U", &path)) {
        return NULL;
    }
    Py_ssize_t end = PyUnicode_GET_LENGTH(path);
    Py_ssize_t pos = PyUnicode_FindChar(path, SEP, 0, end, -1);
    if (pos < 0) {
        return Py_NewRef(path);
    }
    return PyUnicode_Substring(path, pos + 1, end);
}


static PyObject *
getpath_dirname(PyObject *Py_UNUSED(self), PyObject *args)
{
    PyObject *path;
    if (!PyArg_ParseTuple(args, "U", &path)) {
        return NULL;
    }
    Py_ssize_t end = PyUnicode_GET_LENGTH(path);
    Py_ssize_t pos = PyUnicode_FindChar(path, SEP, 0, end, -1);
    if (pos < 0) {
        return PyUnicode_FromStringAndSize(NULL, 0);
    }
    return PyUnicode_Substring(path, 0, pos);
}


static PyObject *
getpath_isabs(PyObject *Py_UNUSED(self), PyObject *args)
{
    PyObject *r = NULL;
    PyObject *pathobj;
    const wchar_t *path;
    if (!PyArg_ParseTuple(args, "U", &pathobj)) {
        return NULL;
    }
    path = PyUnicode_AsWideCharString(pathobj, NULL);
    if (path) {
        r = _Py_isabs(path) ? Py_True : Py_False;
        PyMem_Free((void *)path);
    }
    Py_XINCREF(r);
    return r;
}


static PyObject *
getpath_hassuffix(PyObject *Py_UNUSED(self), PyObject *args)
{
    PyObject *r = NULL;
    PyObject *pathobj;
    PyObject *suffixobj;
    const wchar_t *path;
    const wchar_t *suffix;
    if (!PyArg_ParseTuple(args, "UU", &pathobj, &suffixobj)) {
        return NULL;
    }
    Py_ssize_t len, suffixLen;
    path = PyUnicode_AsWideCharString(pathobj, &len);
    if (path) {
        suffix = PyUnicode_AsWideCharString(suffixobj, &suffixLen);
        if (suffix) {
            if (suffixLen > len ||
#ifdef MS_WINDOWS
                wcsicmp(&path[len - suffixLen], suffix) != 0
#else
                wcscmp(&path[len - suffixLen], suffix) != 0
#endif
            ) {
                r = Py_False;
            } else {
                r = Py_True;
            }
            Py_INCREF(r);
            PyMem_Free((void *)suffix);
        }
        PyMem_Free((void *)path);
    }
    return r;
}


static PyObject *
getpath_isdir(PyObject *Py_UNUSED(self), PyObject *args)
{
    PyObject *r = NULL;
    PyObject *pathobj;
    const wchar_t *path;
    if (!PyArg_ParseTuple(args, "U", &pathobj)) {
        return NULL;
    }
    path = PyUnicode_AsWideCharString(pathobj, NULL);
    if (path) {
#ifdef MS_WINDOWS
        DWORD attr = GetFileAttributesW(path);
        r = (attr != INVALID_FILE_ATTRIBUTES) &&
            (attr & FILE_ATTRIBUTE_DIRECTORY) ? Py_True : Py_False;
#else
        struct stat st;
        r = (_Py_wstat(path, &st) == 0) && S_ISDIR(st.st_mode) ? Py_True : Py_False;
#endif
        PyMem_Free((void *)path);
    }
    Py_XINCREF(r);
    return r;
}


static PyObject *
getpath_isfile(PyObject *Py_UNUSED(self), PyObject *args)
{
    PyObject *r = NULL;
    PyObject *pathobj;
    const wchar_t *path;
    if (!PyArg_ParseTuple(args, "U", &pathobj)) {
        return NULL;
    }
    path = PyUnicode_AsWideCharString(pathobj, NULL);
    if (path) {
#ifdef MS_WINDOWS
        DWORD attr = GetFileAttributesW(path);
        r = (attr != INVALID_FILE_ATTRIBUTES) &&
            !(attr & FILE_ATTRIBUTE_DIRECTORY) ? Py_True : Py_False;
#else
        struct stat st;
        r = (_Py_wstat(path, &st) == 0) && S_ISREG(st.st_mode) ? Py_True : Py_False;
#endif
        PyMem_Free((void *)path);
    }
    Py_XINCREF(r);
    return r;
}


static PyObject *
getpath_isxfile(PyObject *Py_UNUSED(self), PyObject *args)
{
    PyObject *r = NULL;
    PyObject *pathobj;
    const wchar_t *path;
    Py_ssize_t cchPath;
    if (!PyArg_ParseTuple(args, "U", &pathobj)) {
        return NULL;
    }
    path = PyUnicode_AsWideCharString(pathobj, &cchPath);
    if (path) {
#ifdef MS_WINDOWS
        const wchar_t *ext;
        DWORD attr = GetFileAttributesW(path);
        r = (attr != INVALID_FILE_ATTRIBUTES) &&
            !(attr & FILE_ATTRIBUTE_DIRECTORY) &&
            SUCCEEDED(PathCchFindExtension(path, cchPath + 1, &ext)) &&
            (CompareStringOrdinal(ext, -1, L".exe", -1, 1 /* ignore case */) == CSTR_EQUAL)
            ? Py_True : Py_False;
#else
        struct stat st;
        r = (_Py_wstat(path, &st) == 0) &&
            S_ISREG(st.st_mode) &&
            (st.st_mode & 0111)
            ? Py_True : Py_False;
#endif
        PyMem_Free((void *)path);
    }
    Py_XINCREF(r);
    return r;
}


static PyObject *
getpath_joinpath(PyObject *Py_UNUSED(self), PyObject *args)
{
    if (!PyTuple_Check(args)) {
        PyErr_SetString(PyExc_TypeError, "requires tuple of arguments");
        return NULL;
    }
    Py_ssize_t n = PyTuple_GET_SIZE(args);
    if (n == 0) {
        return PyUnicode_FromStringAndSize(NULL, 0);
    }
    /* Convert all parts to wchar and accumulate max final length */
    wchar_t **parts = (wchar_t **)PyMem_Malloc(n * sizeof(wchar_t *));
    memset(parts, 0, n * sizeof(wchar_t *));
    Py_ssize_t cchFinal = 0;
    Py_ssize_t first = 0;

    for (Py_ssize_t i = 0; i < n; ++i) {
        PyObject *s = PyTuple_GET_ITEM(args, i);
        Py_ssize_t cch;
        if (s == Py_None) {
            cch = 0;
        } else if (PyUnicode_Check(s)) {
            parts[i] = PyUnicode_AsWideCharString(s, &cch);
            if (!parts[i]) {
                cchFinal = -1;
                break;
            }
            if (_Py_isabs(parts[i])) {
                first = i;
            }
        } else {
            PyErr_SetString(PyExc_TypeError, "all arguments to joinpath() must be str or None");
            cchFinal = -1;
            break;
        }
        cchFinal += cch + 1;
    }

    wchar_t *final = cchFinal > 0 ? (wchar_t *)PyMem_Malloc(cchFinal * sizeof(wchar_t)) : NULL;
    if (!final) {
        for (Py_ssize_t i = 0; i < n; ++i) {
            PyMem_Free(parts[i]);
        }
        PyMem_Free(parts);
        if (cchFinal) {
            PyErr_NoMemory();
            return NULL;
        }
        return PyUnicode_FromStringAndSize(NULL, 0);
    }

    final[0] = '\0';
    /* Now join all the paths. The final result should be shorter than the buffer */
    for (Py_ssize_t i = 0; i < n; ++i) {
        if (!parts[i]) {
            continue;
        }
        if (i >= first && final) {
            if (!final[0]) {
                /* final is definitely long enough to fit any individual part */
                wcscpy(final, parts[i]);
            } else if (_Py_add_relfile(final, parts[i], cchFinal) < 0) {
                /* if we fail, keep iterating to free memory, but stop adding parts */
                PyMem_Free(final);
                final = NULL;
            }
        }
        PyMem_Free(parts[i]);
    }
    PyMem_Free(parts);
    if (!final) {
        PyErr_SetString(PyExc_SystemError, "failed to join paths");
        return NULL;
    }
    PyObject *r = PyUnicode_FromWideChar(_Py_normpath(final, -1), -1);
    PyMem_Free(final);
    return r;
}


static PyObject *
getpath_readlines(PyObject *Py_UNUSED(self), PyObject *args)
{
    PyObject *r = NULL;
    PyObject *pathobj;
    const wchar_t *path;
    if (!PyArg_ParseTuple(args, "U", &pathobj)) {
        return NULL;
    }
    path = PyUnicode_AsWideCharString(pathobj, NULL);
    if (!path) {
        return NULL;
    }
    FILE *fp = _Py_wfopen(path, L"rb");
    PyMem_Free((void *)path);
    if (!fp) {
        PyErr_SetFromErrno(PyExc_OSError);
        return NULL;
    }

    r = PyList_New(0);
    if (!r) {
        fclose(fp);
        return NULL;
    }
    const size_t MAX_FILE = 32 * 1024;
    char *buffer = (char *)PyMem_Malloc(MAX_FILE);
    if (!buffer) {
        Py_DECREF(r);
        fclose(fp);
        return NULL;
    }

    size_t cb = fread(buffer, 1, MAX_FILE, fp);
    fclose(fp);
    if (!cb) {
        return r;
    }
    if (cb >= MAX_FILE) {
        Py_DECREF(r);
        PyErr_SetString(PyExc_MemoryError,
            "cannot read file larger than 32KB during initialization");
        return NULL;
    }
    buffer[cb] = '\0';

    size_t len;
    wchar_t *wbuffer = _Py_DecodeUTF8_surrogateescape(buffer, cb, &len);
    PyMem_Free((void *)buffer);
    if (!wbuffer) {
        Py_DECREF(r);
        PyErr_NoMemory();
        return NULL;
    }

    wchar_t *p1 = wbuffer;
    wchar_t *p2 = p1;
    while ((p2 = wcschr(p1, L'\n')) != NULL) {
        Py_ssize_t cb = p2 - p1;
        while (cb >= 0 && (p1[cb] == L'\n' || p1[cb] == L'\r')) {
            --cb;
        }
        PyObject *u = PyUnicode_FromWideChar(p1, cb >= 0 ? cb + 1 : 0);
        if (!u || PyList_Append(r, u) < 0) {
            Py_XDECREF(u);
            Py_CLEAR(r);
            break;
        }
        Py_DECREF(u);
        p1 = p2 + 1;
    }
    if (r && p1 && *p1) {
        PyObject *u = PyUnicode_FromWideChar(p1, -1);
        if (!u || PyList_Append(r, u) < 0) {
            Py_CLEAR(r);
        }
        Py_XDECREF(u);
    }
    PyMem_RawFree(wbuffer);
    return r;
}


static PyObject *
getpath_realpath(PyObject *Py_UNUSED(self) , PyObject *args)
{
    PyObject *pathobj;
    if (!PyArg_ParseTuple(args, "U", &pathobj)) {
        return NULL;
    }
#if defined(HAVE_READLINK)
    /* This readlink calculation only resolves a symlinked file, and
       does not resolve any path segments. This is consistent with
       prior releases, however, the realpath implementation below is
       potentially correct in more cases. */
    PyObject *r = NULL;
    int nlink = 0;
    wchar_t *path = PyUnicode_AsWideCharString(pathobj, NULL);
    if (!path) {
        goto done;
    }
    wchar_t *path2 = _PyMem_RawWcsdup(path);
    PyMem_Free((void *)path);
    path = path2;
    while (path) {
        wchar_t resolved[MAXPATHLEN + 1];
        int linklen = _Py_wreadlink(path, resolved, Py_ARRAY_LENGTH(resolved));
        if (linklen == -1) {
            r = PyUnicode_FromWideChar(path, -1);
            break;
        }
        if (_Py_isabs(resolved)) {
            PyMem_RawFree((void *)path);
            path = _PyMem_RawWcsdup(resolved);
        } else {
            wchar_t *s = wcsrchr(path, SEP);
            if (s) {
                *s = L'\0';
            }
            path2 = _Py_normpath(_Py_join_relfile(path, resolved), -1);
            PyMem_RawFree((void *)path);
            path = path2;
        }
        nlink++;
        /* 40 is the Linux kernel 4.2 limit */
        if (nlink >= 40) {
            PyErr_SetString(PyExc_OSError, "maximum number of symbolic links reached");
            break;
        }
    }
    if (!path) {
        PyErr_NoMemory();
    }
done:
    PyMem_RawFree((void *)path);
    return r;

#elif defined(HAVE_REALPATH)
    PyObject *r = NULL;
    struct stat st;
    const char *narrow = NULL;
    wchar_t *path = PyUnicode_AsWideCharString(pathobj, NULL);
    if (!path) {
        goto done;
    }
    narrow = Py_EncodeLocale(path, NULL);
    if (!narrow) {
        PyErr_NoMemory();
        goto done;
    }
    if (lstat(narrow, &st)) {
        PyErr_SetFromErrno(PyExc_OSError);
        goto done;
    }
    if (!S_ISLNK(st.st_mode)) {
        Py_INCREF(pathobj);
        r = pathobj;
        goto done;
    }
    wchar_t resolved[MAXPATHLEN+1];
    if (_Py_wrealpath(path, resolved, MAXPATHLEN) == NULL) {
        PyErr_SetFromErrno(PyExc_OSError);
    } else {
        r = PyUnicode_FromWideChar(resolved, -1);
    }
done:
    PyMem_Free((void *)path);
    PyMem_Free((void *)narrow);
    return r;
#endif

    Py_INCREF(pathobj);
    return pathobj;
}


static PyMethodDef getpath_methods[] = {
    {"abspath", getpath_abspath, METH_VARARGS, NULL},
    {"basename", getpath_basename, METH_VARARGS, NULL},
    {"dirname", getpath_dirname, METH_VARARGS, NULL},
    {"hassuffix", getpath_hassuffix, METH_VARARGS, NULL},
    {"isabs", getpath_isabs, METH_VARARGS, NULL},
    {"isdir", getpath_isdir, METH_VARARGS, NULL},
    {"isfile", getpath_isfile, METH_VARARGS, NULL},
    {"isxfile", getpath_isxfile, METH_VARARGS, NULL},
    {"joinpath", getpath_joinpath, METH_VARARGS, NULL},
    {"readlines", getpath_readlines, METH_VARARGS, NULL},
    {"realpath", getpath_realpath, METH_VARARGS, NULL},
    {NULL, NULL, 0, NULL}
};


/* Two implementations of warn() to use depending on whether warnings
   are enabled or not. */

static PyObject *
getpath_warn(PyObject *Py_UNUSED(self), PyObject *args)
{
    PyObject *msgobj;
    if (!PyArg_ParseTuple(args, "U", &msgobj)) {
        return NULL;
    }
    fprintf(stderr, "%s\n", PyUnicode_AsUTF8(msgobj));
    Py_RETURN_NONE;
}


static PyObject *
getpath_nowarn(PyObject *Py_UNUSED(self), PyObject *args)
{
    Py_RETURN_NONE;
}


static PyMethodDef getpath_warn_method = {"warn", getpath_warn, METH_VARARGS, NULL};
static PyMethodDef getpath_nowarn_method = {"warn", getpath_nowarn, METH_VARARGS, NULL};

/* Add the helper functions to the dict */
static int
funcs_to_dict(PyObject *dict, int warnings)
{
    for (PyMethodDef *m = getpath_methods; m->ml_name; ++m) {
        PyObject *f = PyCFunction_NewEx(m, NULL, NULL);
        if (!f) {
            return 0;
        }
        if (PyDict_SetItemString(dict, m->ml_name, f) < 0) {
            Py_DECREF(f);
            return 0;
        }
        Py_DECREF(f);
    }
    PyMethodDef *m2 = warnings ? &getpath_warn_method : &getpath_nowarn_method;
    PyObject *f = PyCFunction_NewEx(m2, NULL, NULL);
    if (!f) {
        return 0;
    }
    if (PyDict_SetItemString(dict, m2->ml_name, f) < 0) {
        Py_DECREF(f);
        return 0;
    }
    Py_DECREF(f);
    return 1;
}


/* Add a wide-character string constant to the dict */
static int
wchar_to_dict(PyObject *dict, const char *key, const wchar_t *s)
{
    PyObject *u;
    int r;
    if (s && s[0]) {
        u = PyUnicode_FromWideChar(s, -1);
        if (!u) {
            return 0;
        }
    } else {
        u = Py_None;
        Py_INCREF(u);
    }
    r = PyDict_SetItemString(dict, key, u) == 0;
    Py_DECREF(u);
    return r;
}


/* Add a narrow string constant to the dict, using default locale decoding */
static int
decode_to_dict(PyObject *dict, const char *key, const char *s)
{
    PyObject *u = NULL;
    int r;
    if (s && s[0]) {
        size_t len;
        const wchar_t *w = Py_DecodeLocale(s, &len);
        if (w) {
            u = PyUnicode_FromWideChar(w, len);
            PyMem_RawFree((void *)w);
        }
        if (!u) {
            return 0;
        }
    } else {
        u = Py_None;
        Py_INCREF(u);
    }
    r = PyDict_SetItemString(dict, key, u) == 0;
    Py_DECREF(u);
    return r;
}

/* Add an environment variable to the dict, optionally clearing it afterwards */
static int
env_to_dict(PyObject *dict, const char *key, int and_clear)
{
    PyObject *u = NULL;
    int r = 0;
    assert(strncmp(key, "ENV_", 4) == 0);
    assert(strlen(key) < 64);
#ifdef MS_WINDOWS
    wchar_t wkey[64];
    // Quick convert to wchar_t, since we know key is ASCII
    wchar_t *wp = wkey;
    for (const char *p = &key[4]; *p; ++p) {
        assert(*p < 128);
        *wp++ = *p;
    }
    *wp = L'\0';
    const wchar_t *v = _wgetenv(wkey);
    if (v) {
        u = PyUnicode_FromWideChar(v, -1);
        if (!u) {
            PyErr_Clear();
        }
    }
#else
    const char *v = getenv(&key[4]);
    if (v) {
        size_t len;
        const wchar_t *w = Py_DecodeLocale(v, &len);
        if (w) {
            u = PyUnicode_FromWideChar(w, len);
            if (!u) {
                PyErr_Clear();
            }
            PyMem_RawFree((void *)w);
        }
    }
#endif
    if (u) {
        r = PyDict_SetItemString(dict, key, u) == 0;
        Py_DECREF(u);
    } else {
        r = PyDict_SetItemString(dict, key, Py_None) == 0;
    }
    if (r && and_clear) {
#ifdef MS_WINDOWS
        _wputenv_s(wkey, L"");
#else
        unsetenv(&key[4]);
#endif
    }
    return r;
}


/* Add an integer constant to the dict */
static int
int_to_dict(PyObject *dict, const char *key, int v)
{
    PyObject *o;
    int r;
    o = PyLong_FromLong(v);
    if (!o) {
        return 0;
    }
    r = PyDict_SetItemString(dict, key, o) == 0;
    Py_DECREF(o);
    return r;
}


#ifdef MS_WINDOWS
static int
winmodule_to_dict(PyObject *dict, const char *key, HMODULE mod)
{
    wchar_t *buffer = NULL;
    for (DWORD cch = 256; buffer == NULL && cch < (1024 * 1024); cch *= 2) {
        buffer = (wchar_t*)PyMem_RawMalloc(cch * sizeof(wchar_t));
        if (buffer) {
            if (GetModuleFileNameW(mod, buffer, cch) == cch) {
                PyMem_RawFree(buffer);
                buffer = NULL;
            }
        }
    }
    int r = wchar_to_dict(dict, key, buffer);
    PyMem_RawFree(buffer);
    return r;
}
#endif


/* Add the current executable's path to the dict */
static int
progname_to_dict(PyObject *dict, const char *key)
{
#ifdef MS_WINDOWS
    return winmodule_to_dict(dict, key, NULL);
#elif defined(__APPLE__)
    char *path;
    uint32_t pathLen = 256;
    while (pathLen) {
        path = PyMem_RawMalloc((pathLen + 1) * sizeof(char));
        if (!path) {
            return 0;
        }
        if (_NSGetExecutablePath(path, &pathLen) != 0) {
            PyMem_RawFree(path);
            continue;
        }
        // Only keep if the path is absolute
        if (path[0] == SEP) {
            int r = decode_to_dict(dict, key, path);
            PyMem_RawFree(path);
            return r;
        }
        // Fall back and store None
        PyMem_RawFree(path);
        break;
    }
#endif
    return PyDict_SetItemString(dict, key, Py_None) == 0;
}


/* Add the runtime library's path to the dict */
static int
library_to_dict(PyObject *dict, const char *key)
{
#ifdef MS_WINDOWS
    extern HMODULE PyWin_DLLhModule;
    if (PyWin_DLLhModule) {
        return winmodule_to_dict(dict, key, PyWin_DLLhModule);
    }
#elif defined(WITH_NEXT_FRAMEWORK)
    static char modPath[MAXPATHLEN + 1];
    static int modPathInitialized = -1;
    if (modPathInitialized < 0) {
        modPathInitialized = 0;

        /* On Mac OS X we have a special case if we're running from a framework.
           This is because the python home should be set relative to the library,
           which is in the framework, not relative to the executable, which may
           be outside of the framework. Except when we're in the build
           directory... */
        NSSymbol symbol = NSLookupAndBindSymbol("_Py_Initialize");
        if (symbol != NULL) {
            NSModule pythonModule = NSModuleForSymbol(symbol);
            if (pythonModule != NULL) {
                /* Use dylib functions to find out where the framework was loaded from */
                const char *path = NSLibraryNameForModule(pythonModule);
                if (path) {
                    strncpy(modPath, path, MAXPATHLEN);
                    modPathInitialized = 1;
                }
            }
        }
    }
    if (modPathInitialized > 0) {
        return decode_to_dict(dict, key, modPath);
    }
#endif
    return PyDict_SetItemString(dict, key, Py_None) == 0;
}


PyObject *
_Py_Get_Getpath_CodeObject(void)
{
    return PyMarshal_ReadObjectFromString(
        (const char*)_Py_M__getpath, sizeof(_Py_M__getpath));
}


/* Perform the actual path calculation.

   When compute_path_config is 0, this only reads any initialised path
   config values into the PyConfig struct. For example, Py_SetHome() or
   Py_SetPath(). The only error should be due to failed memory allocation.

   When compute_path_config is 1, full path calculation is performed.
   The GIL must be held, and there may be filesystem access, side
   effects, and potential unraisable errors that are reported directly
   to stderr.

   Calling this function multiple times on the same PyConfig is only
   safe because already-configured values are not recalculated. To
   actually recalculate paths, you need a clean PyConfig.
*/
PyStatus
_PyConfig_InitPathConfig(PyConfig *config, int compute_path_config)
{
    PyStatus status = _PyPathConfig_ReadGlobal(config);

    if (_PyStatus_EXCEPTION(status) || !compute_path_config) {
        return status;
    }

    if (!_PyThreadState_UncheckedGet()) {
        return PyStatus_Error("cannot calculate path configuration without GIL");
    }

    PyObject *configDict = _PyConfig_AsDict(config);
    if (!configDict) {
        PyErr_Clear();
        return PyStatus_NoMemory();
    }

    PyObject *dict = PyDict_New();
    if (!dict) {
        PyErr_Clear();
        Py_DECREF(configDict);
        return PyStatus_NoMemory();
    }

    if (PyDict_SetItemString(dict, "config", configDict) < 0) {
        PyErr_Clear();
        Py_DECREF(configDict);
        Py_DECREF(dict);
        return PyStatus_NoMemory();
    }
    /* reference now held by dict */
    Py_DECREF(configDict);

    PyObject *co = _Py_Get_Getpath_CodeObject();
    if (!co || !PyCode_Check(co)) {
        PyErr_Clear();
        Py_XDECREF(co);
        Py_DECREF(dict);
        return PyStatus_Error("error reading frozen getpath.py");
    }

#ifdef MS_WINDOWS
    PyObject *winreg = PyImport_ImportModule("winreg");
    if (!winreg || PyDict_SetItemString(dict, "winreg", winreg) < 0) {
        PyErr_Clear();
        Py_XDECREF(winreg);
        if (PyDict_SetItemString(dict, "winreg", Py_None) < 0) {
            PyErr_Clear();
            Py_DECREF(co);
            Py_DECREF(dict);
            return PyStatus_Error("error importing winreg module");
        }
    } else {
        Py_DECREF(winreg);
    }
#endif

    if (
#ifdef MS_WINDOWS
        !decode_to_dict(dict, "os_name", "nt") ||
#elif defined(__APPLE__)
        !decode_to_dict(dict, "os_name", "darwin") ||
#else
        !decode_to_dict(dict, "os_name", "posix") ||
#endif
#ifdef WITH_NEXT_FRAMEWORK
        !int_to_dict(dict, "WITH_NEXT_FRAMEWORK", 1) ||
#else
        !int_to_dict(dict, "WITH_NEXT_FRAMEWORK", 0) ||
#endif
        !decode_to_dict(dict, "PREFIX", PREFIX) ||
        !decode_to_dict(dict, "EXEC_PREFIX", EXEC_PREFIX) ||
        !decode_to_dict(dict, "PYTHONPATH", PYTHONPATH) ||
        !decode_to_dict(dict, "VPATH", VPATH) ||
        !decode_to_dict(dict, "PLATLIBDIR", PLATLIBDIR) ||
        !decode_to_dict(dict, "PYDEBUGEXT", PYDEBUGEXT) ||
        !int_to_dict(dict, "VERSION_MAJOR", PY_MAJOR_VERSION) ||
        !int_to_dict(dict, "VERSION_MINOR", PY_MINOR_VERSION) ||
        !decode_to_dict(dict, "PYWINVER", PYWINVER) ||
        !wchar_to_dict(dict, "EXE_SUFFIX", EXE_SUFFIX) ||
        !env_to_dict(dict, "ENV_PATH", 0) ||
        !env_to_dict(dict, "ENV_PYTHONHOME", 0) ||
        !env_to_dict(dict, "ENV_PYTHONEXECUTABLE", 0) ||
        !env_to_dict(dict, "ENV___PYVENV_LAUNCHER__", 1) ||
        !progname_to_dict(dict, "real_executable") ||
        !library_to_dict(dict, "library") ||
        !wchar_to_dict(dict, "executable_dir", NULL) ||
        !wchar_to_dict(dict, "py_setpath", _PyPathConfig_GetGlobalModuleSearchPath()) ||
        !funcs_to_dict(dict, config->pathconfig_warnings) ||
#ifndef MS_WINDOWS
        PyDict_SetItemString(dict, "winreg", Py_None) < 0 ||
#endif
        PyDict_SetItemString(dict, "__builtins__", PyEval_GetBuiltins()) < 0
    ) {
        Py_DECREF(co);
        Py_DECREF(dict);
        _PyErr_WriteUnraisableMsg("error evaluating initial values", NULL);
        return PyStatus_Error("error evaluating initial values");
    }

    PyObject *r = PyEval_EvalCode(co, dict, dict);
    Py_DECREF(co);

    if (!r) {
        Py_DECREF(dict);
        _PyErr_WriteUnraisableMsg("error evaluating path", NULL);
        return PyStatus_Error("error evaluating path");
    }
    Py_DECREF(r);

#if 0
    PyObject *it = PyObject_GetIter(configDict);
    for (PyObject *k = PyIter_Next(it); k; k = PyIter_Next(it)) {
        if (!strcmp("__builtins__", PyUnicode_AsUTF8(k))) {
            Py_DECREF(k);
            continue;
        }
        fprintf(stderr, "%s = ", PyUnicode_AsUTF8(k));
        PyObject *o = PyDict_GetItem(configDict, k);
        o = PyObject_Repr(o);
        fprintf(stderr, "%s\n", PyUnicode_AsUTF8(o));
        Py_DECREF(o);
        Py_DECREF(k);
    }
    Py_DECREF(it);
#endif

    if (_PyConfig_FromDict(config, configDict) < 0) {
        _PyErr_WriteUnraisableMsg("reading getpath results", NULL);
        Py_DECREF(dict);
        return PyStatus_Error("error getting getpath results");
    }

    Py_DECREF(dict);

    return _PyStatus_OK();
}

