Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
On Cygwin and MinGW, ensure that ``sys.executable`` always includes the full
filename in the path, including the ``.exe`` suffix (unless it is a symbolic
link).
45 changes: 45 additions & 0 deletions Modules/getpath.c
Original file line number Diff line number Diff line change
Expand Up @@ -296,6 +296,41 @@ absolutize(wchar_t *path)
}


#if defined(__CYGWIN__) || defined(__MINGW32__)
/* add_exe_suffix requires that progpath be allocated at least
MAXPATHLEN + 1 bytes.
*/

#ifndef EXE_SUFFIX
#define EXE_SUFFIX L".exe"
#endif

static void
add_exe_suffix(wchar_t *progpath)
{
/* Check for already have an executable suffix */
size_t n = wcslen(progpath);
size_t s = wcslen(EXE_SUFFIX);
if (wcsncasecmp(EXE_SUFFIX, progpath+n-s, s) != 0) {
if (n + s > MAXPATHLEN) {
Py_FatalError("progpath overflow in getpath.c's add_exe_suffix()");
}
/* Save original path for revert */
wchar_t orig[MAXPATHLEN+1];
wcsncpy(orig, progpath, MAXPATHLEN);

wcsncpy(progpath+n, EXE_SUFFIX, s);
progpath[n+s] = '\0';

if (!isxfile(progpath)) {
/* Path that added suffix is invalid */
wcsncpy(progpath, orig, MAXPATHLEN);
}
}
}
#endif


/* search_for_prefix requires that argv0_path be no more than MAXPATHLEN
bytes long.
*/
Expand Down Expand Up @@ -605,6 +640,16 @@ calculate_program_full_path(const _PyCoreConfig *core_config,
if (program_full_path[0] != SEP && program_full_path[0] != '\0') {
absolutize(program_full_path);
}
#if defined(__CYGWIN__) || defined(__MINGW32__)
/* For these platforms it is necessary to ensure that the .exe suffix
* is appended to the filename, otherwise there is potential for
* sys.executable to return the name of a directory under the same
* path (bpo-28441).
*/
if (program_full_path[0] != '\0') {
add_exe_suffix(program_full_path);
}
#endif

config->program_full_path = _PyMem_RawWcsdup(program_full_path);
if (config->program_full_path == NULL) {
Expand Down