Skip to content

Commit b6a2b51

Browse files
committed
MSVS: revise the vcxproj embedded python script contents to be backward compatible with current master
Changes: * Determine the SCons module path in the same manner as the current master code. * Adjust the SCons module path using the generated path location under certain conditions.
1 parent b2170a1 commit b6a2b51

File tree

2 files changed

+43
-43
lines changed

2 files changed

+43
-43
lines changed

SCons/Tool/msvs.py

Lines changed: 20 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@
3333
import uuid
3434
import ntpath
3535
import os
36+
import pathlib
3637
import pickle
3738
import re
3839
import sys
@@ -180,36 +181,35 @@ def getExecScriptMain(env, xml=None):
180181
scons_abspath = os.path.abspath(os.path.dirname(os.path.dirname(SCons.__file__)))
181182

182183
def _in_pytree(scons_abspath):
183-
scons_norm = os.path.normcase(scons_abspath)
184-
for py_prefix in [sys.prefix]: # sys.exec_prefix also on windows?
185-
py_norm = os.path.normcase(os.path.abspath(py_prefix))
186-
try:
187-
common = os.path.commonpath([py_norm, scons_norm])
188-
if common == py_norm:
189-
return True
190-
break
191-
except ValueError:
192-
pass
193-
return False
184+
py_comps = pathlib.Path(os.path.normcase(os.path.abspath(sys.prefix))).parts
185+
comps = pathlib.Path(os.path.normcase(scons_abspath)).parts
186+
rval = bool(comps[:len(py_comps)] == py_comps)
187+
return rval
194188

195189
in_pytree = _in_pytree(scons_abspath)
196-
# print(f"in_pytree={in_pytree}, scons_abspath=`{scons_abspath}', sys.prefix='{sys.prefix}', sys.exec_prefix='{sys.exec_prefix}'")
190+
# print(f"in_pytree={in_pytree}, scons_abspath=`{scons_abspath}', sys.prefix='{sys.prefix}'")
197191

198192
if _exec_script_main_template is None:
199193
_exec_script_main_template = "; ".join(textwrap.dedent(
200194
"""\
201195
import importlib.util
202196
import sys
203-
from os.path import abspath, dirname, isdir, isfile, join, realpath
197+
from os.path import abspath, dirname, join, normcase, realpath
198+
from pathlib import Path
204199
usr_path = r'{scons_home}'
205200
gen_path = r'{scons_abspath}'
206-
syspath = sys.path
207-
search, path = ([usr_path], usr_path) if usr_path else ([gen_path], gen_path) if gen_path else ([join(sys.prefix, *t) for t in [('Lib', 'site-packages', 'scons-{scons_version}'), ('scons-{scons_version}',), ('Lib', 'site-packages', 'scons'), ('scons',), ('Lib', 'site-packages')]] + sys.path, None)
208-
sys.path = search
209-
spec = importlib.util.find_spec('SCons')
210-
orig = dirname(dirname(abspath(spec.origin))) if (spec and spec.origin) else ''
211-
sys.path = [orig] + syspath if orig else syspath
212-
_ = print(f'proj: Using SCons path \\\'{{orig}}\\\' (realpath=\\\'{{realpath(orig)}}\\\').') if orig else (print(f'proj: Error: SCons not found (path=\\\'{{path if path else search}}\\\').'), sys.exit(1))
201+
syspath = list(sys.path)
202+
memo = {{'pycomps': Path(normcase(abspath(sys.prefix))).parts}}
203+
origin = lambda l: (sys.path.clear(), sys.path.extend(l), memo.update({{'spec': importlib.util.find_spec('SCons')}}), dirname(dirname(abspath(memo['spec'].origin))) if (memo['spec'] and memo['spec'].origin) else '')[-1]
204+
pytree = lambda p: (memo.update({{'comps': Path(normcase(p)).parts}}), memo['comps'][:len(memo['pycomps'])] == memo['pycomps'])[-1] if p else False
205+
search = ([usr_path] + syspath if usr_path else [join(sys.prefix, *t) for t in [('Lib', 'site-packages', 'scons-{scons_version}'), ('scons-{scons_version}',), ('Lib', 'site-packages', 'scons'), ('scons',), ('Lib', 'site-packages')]] + syspath)
206+
begpath = origin(search)
207+
user = begpath and usr_path and normcase(begpath) == normcase(abspath(usr_path))
208+
endpath = (search.insert(0, gen_path), origin([gen_path]))[-1] if (not user and gen_path and (not begpath or pytree(begpath))) else ''
209+
path = endpath if endpath else begpath
210+
_ = (print(f'proj: Error: SCons not found (path=\\\'{{search}}\\\').'), sys.exit(1)) if (not path) else None
211+
sys.path = [path] + syspath
212+
print(f'proj: Using SCons path \\\'{{path}}\\\' (realpath=\\\'{{realpath(path)}}\\\').')
213213
import SCons.Script
214214
SCons.Script.main()
215215
"""

testing/framework/TestSConsMSVS.py

Lines changed: 23 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@
3737

3838
import os
3939
import sys
40+
import pathlib
4041
import platform
4142
import textwrap
4243
import traceback
@@ -835,7 +836,7 @@ def get_tested_proj_file_vc_versions():
835836

836837
_exec_script_main_template = None
837838

838-
def get_exec_script_main(scons_home=None):
839+
def get_exec_script_main(scons_home=''):
839840
"""
840841
Returns the python script string embedded in the msvs project files.
841842
"""
@@ -854,36 +855,35 @@ def get_exec_script_main(scons_home=None):
854855
scons_abspath = os.path.abspath(os.path.dirname(os.path.dirname(SCons.__file__)))
855856

856857
def _in_pytree(scons_abspath):
857-
scons_norm = os.path.normcase(scons_abspath)
858-
for py_prefix in [sys.prefix]: # sys.exec_prefix also on windows?
859-
py_norm = os.path.normcase(os.path.abspath(py_prefix))
860-
try:
861-
common = os.path.commonpath([py_norm, scons_norm])
862-
if common == py_norm:
863-
return True
864-
break
865-
except ValueError:
866-
pass
867-
return False
858+
py_comps = pathlib.Path(os.path.normcase(os.path.abspath(sys.prefix))).parts
859+
comps = pathlib.Path(os.path.normcase(scons_abspath)).parts
860+
rval = bool(comps[:len(py_comps)] == py_comps)
861+
return rval
868862

869863
in_pytree = _in_pytree(scons_abspath)
870-
# print(f"in_pytree={in_pytree}, scons_abspath=`{scons_abspath}', sys.prefix='{sys.prefix}', sys.exec_prefix='{sys.exec_prefix}'")
864+
# print(f"in_pytree={in_pytree}, scons_abspath=`{scons_abspath}', sys.prefix='{sys.prefix}'")
871865

872866
if _exec_script_main_template is None:
873867
_exec_script_main_template = "; ".join(textwrap.dedent(
874868
"""\
875869
import importlib.util
876870
import sys
877-
from os.path import abspath, dirname, isdir, isfile, join, realpath
871+
from os.path import abspath, dirname, join, normcase, realpath
872+
from pathlib import Path
878873
usr_path = r'{scons_home}'
879874
gen_path = r'{scons_abspath}'
880-
syspath = sys.path
881-
search, path = ([usr_path], usr_path) if usr_path else ([gen_path], gen_path) if gen_path else ([join(sys.prefix, *t) for t in [('Lib', 'site-packages', 'scons-{scons_version}'), ('scons-{scons_version}',), ('Lib', 'site-packages', 'scons'), ('scons',), ('Lib', 'site-packages')]] + sys.path, None)
882-
sys.path = search
883-
spec = importlib.util.find_spec('SCons')
884-
orig = dirname(dirname(abspath(spec.origin))) if (spec and spec.origin) else ''
885-
sys.path = [orig] + syspath if orig else syspath
886-
_ = print(f'proj: Using SCons path \\\'{{orig}}\\\' (realpath=\\\'{{realpath(orig)}}\\\').') if orig else (print(f'proj: Error: SCons not found (path=\\\'{{path if path else search}}\\\').'), sys.exit(1))
875+
syspath = list(sys.path)
876+
memo = {{'pycomps': Path(normcase(abspath(sys.prefix))).parts}}
877+
origin = lambda l: (sys.path.clear(), sys.path.extend(l), memo.update({{'spec': importlib.util.find_spec('SCons')}}), dirname(dirname(abspath(memo['spec'].origin))) if (memo['spec'] and memo['spec'].origin) else '')[-1]
878+
pytree = lambda p: (memo.update({{'comps': Path(normcase(p)).parts}}), memo['comps'][:len(memo['pycomps'])] == memo['pycomps'])[-1] if p else False
879+
search = ([usr_path] + syspath if usr_path else [join(sys.prefix, *t) for t in [('Lib', 'site-packages', 'scons-{scons_version}'), ('scons-{scons_version}',), ('Lib', 'site-packages', 'scons'), ('scons',), ('Lib', 'site-packages')]] + syspath)
880+
begpath = origin(search)
881+
user = begpath and usr_path and normcase(begpath) == normcase(abspath(usr_path))
882+
endpath = (search.insert(0, gen_path), origin([gen_path]))[-1] if (not user and gen_path and (not begpath or pytree(begpath))) else ''
883+
path = endpath if endpath else begpath
884+
_ = (print(f'proj: Error: SCons not found (path=\\\'{{search}}\\\').'), sys.exit(1)) if (not path) else None
885+
sys.path = [path] + syspath
886+
print(f'proj: Using SCons path \\\'{{path}}\\\' (realpath=\\\'{{realpath(path)}}\\\').')
887887
import SCons.Script
888888
SCons.Script.main()
889889
"""
@@ -947,9 +947,9 @@ def msvs_substitute(
947947
sconscript=None,
948948
python=None,
949949
project_guid=None,
950+
scons_home: str = '',
950951
vcproj_sccinfo: str = '',
951952
sln_sccinfo: str = '',
952-
scons_home=None,
953953
):
954954
if not hasattr(self, '_msvs_versions'):
955955
self.msvs_versions()
@@ -1213,9 +1213,9 @@ def msvs_substitute_projects(
12131213
project_guid_2=None,
12141214
solution_guid_1=None,
12151215
solution_guid_2=None,
1216+
scons_home: str = '',
12161217
vcproj_sccinfo: str = '',
12171218
sln_sccinfo: str = '',
1218-
scons_home=None,
12191219
):
12201220
if not hasattr(self, '_msvs_versions'):
12211221
self.msvs_versions()

0 commit comments

Comments
 (0)