@@ -131,8 +131,6 @@ typedef struct {
131131 wchar_t * machine_path ; /* from HKEY_LOCAL_MACHINE */
132132 wchar_t * user_path ; /* from HKEY_CURRENT_USER */
133133
134- wchar_t * dll_path ;
135-
136134 const wchar_t * pythonpath_env ;
137135} PyCalculatePath ;
138136
@@ -168,27 +166,37 @@ reduce(wchar_t *dir)
168166static int
169167change_ext (wchar_t * dest , const wchar_t * src , const wchar_t * ext )
170168{
171- size_t src_len = wcsnlen_s (src , MAXPATHLEN + 1 );
172- size_t i = src_len ;
173- if (i >= MAXPATHLEN + 1 ) {
174- Py_FatalError ("buffer overflow in getpathp.c's reduce()" );
175- }
169+ if (src && src != dest ) {
170+ size_t src_len = wcsnlen_s (src , MAXPATHLEN + 1 );
171+ size_t i = src_len ;
172+ if (i >= MAXPATHLEN + 1 ) {
173+ Py_FatalError ("buffer overflow in getpathp.c's reduce()" );
174+ }
176175
177- while (i > 0 && src [i ] != '.' && !is_sep (src [i ]))
178- -- i ;
176+ while (i > 0 && src [i ] != '.' && !is_sep (src [i ]))
177+ -- i ;
179178
180- if (i == 0 ) {
181- dest [0 ] = '\0' ;
182- return -1 ;
183- }
179+ if (i == 0 ) {
180+ dest [0 ] = '\0' ;
181+ return -1 ;
182+ }
183+
184+ if (is_sep (src [i ])) {
185+ i = src_len ;
186+ }
184187
185- if (is_sep (src [i ])) {
186- i = src_len ;
188+ if (wcsncpy_s (dest , MAXPATHLEN + 1 , src , i )) {
189+ dest [0 ] = '\0' ;
190+ return -1 ;
191+ }
192+ } else {
193+ wchar_t * s = wcsrchr (dest , L'.' );
194+ if (s ) {
195+ s [0 ] = '\0' ;
196+ }
187197 }
188198
189- if (wcsncpy_s (dest , MAXPATHLEN + 1 , src , i ) ||
190- wcscat_s (dest , MAXPATHLEN + 1 , ext ))
191- {
199+ if (wcscat_s (dest , MAXPATHLEN + 1 , ext )) {
192200 dest [0 ] = '\0' ;
193201 return -1 ;
194202 }
@@ -297,6 +305,19 @@ search_for_prefix(wchar_t *prefix, const wchar_t *argv0_path, const wchar_t *lan
297305}
298306
299307
308+ static int
309+ get_dllpath (wchar_t * dllpath )
310+ {
311+ #ifdef Py_ENABLE_SHARED
312+ extern HANDLE PyWin_DLLhModule ;
313+ if (PyWin_DLLhModule && GetModuleFileNameW (PyWin_DLLhModule , dllpath , MAXPATHLEN )) {
314+ return 0 ;
315+ }
316+ #endif
317+ return -1 ;
318+ }
319+
320+
300321#ifdef Py_ENABLE_SHARED
301322
302323/* a string loaded from the DLL at startup.*/
@@ -468,27 +489,6 @@ getpythonregpath(HKEY keyBase, int skipcore)
468489#endif /* Py_ENABLE_SHARED */
469490
470491
471- wchar_t *
472- _Py_GetDLLPath (void )
473- {
474- wchar_t dll_path [MAXPATHLEN + 1 ];
475- memset (dll_path , 0 , sizeof (dll_path ));
476-
477- #ifdef Py_ENABLE_SHARED
478- extern HANDLE PyWin_DLLhModule ;
479- if (PyWin_DLLhModule ) {
480- if (!GetModuleFileNameW (PyWin_DLLhModule , dll_path , MAXPATHLEN )) {
481- dll_path [0 ] = 0 ;
482- }
483- }
484- #else
485- dll_path [0 ] = 0 ;
486- #endif
487-
488- return _PyMem_RawWcsdup (dll_path );
489- }
490-
491-
492492static PyStatus
493493get_program_full_path (_PyPathConfig * pathconfig )
494494{
@@ -669,19 +669,17 @@ static int
669669get_pth_filename (PyCalculatePath * calculate , wchar_t * filename ,
670670 const _PyPathConfig * pathconfig )
671671{
672- if (calculate -> dll_path [0 ]) {
673- if (!change_ext (filename , calculate -> dll_path , L"._pth" ) &&
674- exists (filename ))
675- {
676- return 1 ;
677- }
672+ if (get_dllpath (filename ) &&
673+ !change_ext (filename , filename , L"._pth" ) &&
674+ exists (filename ))
675+ {
676+ return 1 ;
678677 }
679- if (pathconfig -> program_full_path [0 ]) {
680- if (!change_ext (filename , pathconfig -> program_full_path , L"._pth" ) &&
681- exists (filename ))
682- {
683- return 1 ;
684- }
678+ if (pathconfig -> program_full_path [0 ] &&
679+ !change_ext (filename , pathconfig -> program_full_path , L"._pth" ) &&
680+ exists (filename ))
681+ {
682+ return 1 ;
685683 }
686684 return 0 ;
687685}
@@ -994,9 +992,12 @@ calculate_path(PyCalculatePath *calculate, _PyPathConfig *pathconfig)
994992 wchar_t zip_path [MAXPATHLEN + 1 ];
995993 memset (zip_path , 0 , sizeof (zip_path ));
996994
997- change_ext (zip_path ,
998- calculate -> dll_path [0 ] ? calculate -> dll_path : pathconfig -> program_full_path ,
999- L".zip" );
995+ if (get_dllpath (zip_path ) || change_ext (zip_path , zip_path , L".zip" ))
996+ {
997+ if (change_ext (zip_path , pathconfig -> program_full_path , L".zip" )) {
998+ zip_path [0 ] = L'\0' ;
999+ }
1000+ }
10001001
10011002 calculate_home_prefix (calculate , argv0_path , zip_path , prefix );
10021003
@@ -1033,11 +1034,6 @@ calculate_init(PyCalculatePath *calculate, _PyPathConfig *pathconfig,
10331034 calculate -> home = pathconfig -> home ;
10341035 calculate -> path_env = _wgetenv (L"PATH" );
10351036
1036- calculate -> dll_path = _Py_GetDLLPath ();
1037- if (calculate -> dll_path == NULL ) {
1038- return _PyStatus_NO_MEMORY ();
1039- }
1040-
10411037 calculate -> pythonpath_env = config -> pythonpath_env ;
10421038
10431039 return _PyStatus_OK ();
@@ -1049,7 +1045,6 @@ calculate_free(PyCalculatePath *calculate)
10491045{
10501046 PyMem_RawFree (calculate -> machine_path );
10511047 PyMem_RawFree (calculate -> user_path );
1052- PyMem_RawFree (calculate -> dll_path );
10531048}
10541049
10551050
@@ -1059,7 +1054,6 @@ calculate_free(PyCalculatePath *calculate)
10591054
10601055 - PyConfig.pythonpath_env: PYTHONPATH environment variable
10611056 - _PyPathConfig.home: Py_SetPythonHome() or PYTHONHOME environment variable
1062- - DLL path: _Py_GetDLLPath()
10631057 - PATH environment variable
10641058 - __PYVENV_LAUNCHER__ environment variable
10651059 - GetModuleFileNameW(NULL): fully qualified path of the executable file of
@@ -1113,33 +1107,35 @@ int
11131107_Py_CheckPython3 (void )
11141108{
11151109 wchar_t py3path [MAXPATHLEN + 1 ];
1116- wchar_t * s ;
11171110 if (python3_checked ) {
11181111 return hPython3 != NULL ;
11191112 }
11201113 python3_checked = 1 ;
11211114
11221115 /* If there is a python3.dll next to the python3y.dll,
1123- assume this is a build tree; use that DLL */
1124- if (_Py_dll_path != NULL ) {
1125- wcscpy (py3path , _Py_dll_path );
1126- }
1127- else {
1128- wcscpy (py3path , L"" );
1129- }
1130- s = wcsrchr (py3path , L'\\' );
1131- if (!s ) {
1132- s = py3path ;
1116+ use that DLL */
1117+ if (!get_dllpath (py3path )) {
1118+ reduce (py3path );
1119+ join (py3path , PY3_DLLNAME );
1120+ hPython3 = LoadLibraryExW (py3path , NULL , LOAD_LIBRARY_SEARCH_DEFAULT_DIRS );
1121+ if (hPython3 != NULL ) {
1122+ return 1 ;
1123+ }
11331124 }
1134- wcscpy (s , L"\\python3.dll" );
1135- hPython3 = LoadLibraryExW (py3path , NULL , LOAD_WITH_ALTERED_SEARCH_PATH );
1125+
1126+ /* If we can locate python3.dll in our application dir,
1127+ use that DLL */
1128+ hPython3 = LoadLibraryExW (PY3_DLLNAME , NULL , LOAD_LIBRARY_SEARCH_APPLICATION_DIR );
11361129 if (hPython3 != NULL ) {
11371130 return 1 ;
11381131 }
11391132
1140- /* Check sys.prefix\DLLs\python3.dll */
1133+ /* For back-compat, also search {sys.prefix}\DLLs, though
1134+ that has not been a normal install layout for a while */
11411135 wcscpy (py3path , Py_GetPrefix ());
1142- wcscat (py3path , L"\\DLLs\\python3.dll" );
1143- hPython3 = LoadLibraryExW (py3path , NULL , LOAD_WITH_ALTERED_SEARCH_PATH );
1136+ if (py3path [0 ]) {
1137+ join (py3path , L"DLLs\\" PY3_DLLNAME );
1138+ hPython3 = LoadLibraryExW (py3path , NULL , LOAD_LIBRARY_SEARCH_DEFAULT_DIRS );
1139+ }
11441140 return hPython3 != NULL ;
11451141}
0 commit comments