-
Notifications
You must be signed in to change notification settings - Fork 203
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Increase functionality of try_toolchain #2539
Changes from 5 commits
d5ba7d6
cb4904d
b0c5406
5259b4a
c7ddafe
21b3a53
d3aba89
46714a9
4a86c2b
a5f1d36
69080d3
7867ba9
444aea5
f256a32
619c9ff
9b20491
ee1eb88
1d07e4a
9abfe53
97e7d82
9d25494
46a7f7f
eddc050
e685231
f003b17
a40c2d6
cc2168c
53646aa
b060dfa
2073e38
b46b093
746471d
6c26f79
133b4c7
bb3bcde
a137e27
dd0a7dd
ae4d50e
059a621
1cf9d36
db1400a
583f047
6c13972
1f1b03d
0965f9a
5377ff8
61a0bcb
14d80b7
4d8b503
21a638c
07384d5
5569c50
b6942cc
6c49a39
67b816e
6b627a0
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -115,16 +115,16 @@ def toolchain_hierarchy_cache(func): | |
cache = {} | ||
|
||
@functools.wraps(func) | ||
def cache_aware_func(toolchain): | ||
def cache_aware_func(toolchain, require_capabilities=False): | ||
"""Look up toolchain hierarchy in cache first, determine and cache it if not available yet.""" | ||
cache_key = (toolchain['name'], toolchain['version']) | ||
cache_key = (toolchain['name'], toolchain['version'], require_capabilities) | ||
|
||
# fetch from cache if available, cache it if it's not | ||
if cache_key in cache: | ||
_log.debug("Using cache to return hierarchy for toolchain %s: %s", str(toolchain), cache[cache_key]) | ||
return cache[cache_key] | ||
else: | ||
toolchain_hierarchy = func(toolchain) | ||
toolchain_hierarchy = func(toolchain, require_capabilities) | ||
cache[cache_key] = toolchain_hierarchy | ||
return cache[cache_key] | ||
|
||
|
@@ -135,7 +135,7 @@ def cache_aware_func(toolchain): | |
|
||
|
||
@toolchain_hierarchy_cache | ||
def get_toolchain_hierarchy(parent_toolchain): | ||
def get_toolchain_hierarchy(parent_toolchain, require_capabilities=False): | ||
""" | ||
Determine list of subtoolchains for specified parent toolchain. | ||
Result starts with the most minimal subtoolchains first, ends with specified toolchain. | ||
|
@@ -234,6 +234,32 @@ def get_toolchain_hierarchy(parent_toolchain): | |
subtoolchain_name, subtoolchain_version = subtoolchains[current_tc_name], None | ||
toolchain_hierarchy.insert(0, {'name': current_tc_name, 'version': current_tc_version}) | ||
|
||
# also add toolchain capabilities | ||
if require_capabilities: | ||
for toolchain in toolchain_hierarchy: | ||
toolchain_class, _ = search_toolchain(toolchain['name']) | ||
tc = toolchain_class(version=toolchain['version']) | ||
try: | ||
toolchain['compiler_family'] = tc.comp_family() | ||
except EasyBuildError: | ||
toolchain['compiler_family'] = None | ||
try: | ||
toolchain['mpi_family'] = tc.mpi_family() | ||
except EasyBuildError: | ||
toolchain['mpi_family'] = None | ||
try: | ||
toolchain['blas_family'] = tc.blas_family() | ||
except EasyBuildError: | ||
toolchain['blas_family'] = None | ||
try: | ||
toolchain['lapack_family'] = tc.lapack_family() | ||
except EasyBuildError: | ||
toolchain['lapack_family'] = None | ||
if 'CUDA_CC' in tc.variables: | ||
toolchain['cuda'] = True | ||
else: | ||
toolchain['cuda'] = None # Useful to have it consistent with the rest | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. at least two spaces before inline comment |
||
|
||
_log.info("Found toolchain hierarchy for toolchain %s: %s", parent_toolchain, toolchain_hierarchy) | ||
return toolchain_hierarchy | ||
|
||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -44,6 +44,7 @@ | |
|
||
from easybuild.framework.easyconfig.default import get_easyconfig_parameter_default | ||
from easybuild.framework.easyconfig.easyconfig import EasyConfig, create_paths, process_easyconfig | ||
from easybuild.framework.easyconfig.easyconfig import get_toolchain_hierarchy | ||
from easybuild.tools.build_log import EasyBuildError, print_warning | ||
from easybuild.tools.config import build_option | ||
from easybuild.tools.filetools import read_file, write_file | ||
|
@@ -183,7 +184,7 @@ def __repr__(self): | |
tweaks['checksums'] = [] | ||
_log.warning("Tweaking version: checksums cleared, verification disabled.") | ||
|
||
# we need to treat list values seperately, i.e. we prepend to the current value (if any) | ||
# we need to treat list values separately, i.e. we prepend to the current value (if any) | ||
for (key, val) in tweaks.items(): | ||
|
||
if isinstance(val, list): | ||
|
@@ -615,3 +616,64 @@ def obtain_ec_for(specs, paths, fp=None): | |
return res | ||
else: | ||
raise EasyBuildError("No easyconfig found for requested software, and also failed to generate one.") | ||
|
||
def compare_toolchain_specs(source_tc_spec, target_tc_spec): | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. expected 2 blank lines, found 1 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. expected 2 blank lines, found 1 |
||
""" | ||
Compare whether a source and target toolchain have compatible characteristics | ||
|
||
:param source_tc_spec: specs of source toolchain | ||
:param target_tc_spec: specs of target toolchain | ||
ocaisa marked this conversation as resolved.
Show resolved
Hide resolved
|
||
""" | ||
can_map = True | ||
# Check they have same capabilities | ||
for key in ['compiler_family', 'mpi_family','blas_family', 'lapack_family', 'cuda']: | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. missing whitespace after ',' There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. missing whitespace after ',' |
||
if target_tc_spec[key] is None and source_tc_spec[key] is not None: | ||
ocaisa marked this conversation as resolved.
Show resolved
Hide resolved
|
||
can_map = False | ||
break | ||
|
||
return can_map | ||
|
||
def match_minimum_tc_specs(source_tc_spec, target_tc_hierarchy): | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. expected 2 blank lines, found 1 There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. expected 2 blank lines, found 1 |
||
""" | ||
Match a source toolchain spec to the minimal corresponding toolchain in a target hierarchy | ||
|
||
:param source_tc_spec: specs of source toolchain | ||
:param target_tc_hierarchy: hierarchy of specs for target toolchain | ||
""" | ||
minimal_matching_toolchain = {} | ||
# Do a complete loop so we always end up with the minimal value in the hierarchy | ||
for target_tc_spec in target_tc_hierarchy: | ||
if compare_toolchain_specs(source_tc_spec, target_tc_spec): | ||
# GCCcore has compiler capabilities but should only be used if the original toolchain was also GCCcore | ||
if source_tc_spec['name'] != 'GCCcore' and target_tc_spec['name'] == 'GCCcore': | ||
minimal_matching_toolchain = {'name': target_tc_spec['name'], 'version': target_tc_spec['version']} | ||
target_compiler_family = target_tc_spec['compiler_family'] | ||
|
||
|
||
if not minimal_matching_toolchain: | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. too many blank lines (2) There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. too many blank lines (2) |
||
EasyBuildError("No possible mapping from source toolchain spec %s and target toolchain hierarchy specs %s", | ||
source_tc_spec, target_tc_hierarchy) | ||
|
||
# Warn if we are changing compiler families, this is very likely to cause problems | ||
if target_compiler_family != source_tc_spec['compiler_family']: | ||
print_warning("Your request will results in a compiler family switch (%s to %s). Here be dragons!", | ||
source_tc_spec['compiler_family'], target_compiler_family) | ||
|
||
|
||
return minimal_matching_toolchain | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. too many blank lines (2) There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. too many blank lines (2) |
||
|
||
|
||
def map_toolchain_hierarchies(source_toolchain, target_toolchain): | ||
""" | ||
Create a map between toolchain hierarchy of the initial toolchain and that of the target toolchain | ||
|
||
:param source_toolchain: initial toolchain of the easyconfig(s) | ||
:param target_toolchain: target toolchain for tweaked easyconfig(s) | ||
ocaisa marked this conversation as resolved.
Show resolved
Hide resolved
|
||
""" | ||
tc_mapping = {} | ||
initial_tc_hierarchy = get_toolchain_hierarchy(source_toolchain, require_capabilities=True) | ||
ocaisa marked this conversation as resolved.
Show resolved
Hide resolved
|
||
target_tc_hierarchy = get_toolchain_hierarchy(target_toolchain, require_capabilities=True) | ||
for toolchain_spec in initial_tc_hierarchy: | ||
tc_mapping[toolchain_spec['name']] = match_minimum_tc_specs(toolchain_spec, target_tc_hierarchy) | ||
|
||
return tc_mapping | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. no newline at end of file There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. no newline at end of file |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
at least two spaces before inline comment