Skip to content

Commit

Permalink
Respond to review.
Browse files Browse the repository at this point in the history
* Update text to reflect that "max" optimisation is trading
  potentially longer compilation time for potentially better
  run-time but without being specific about how this is
  implemented.
* Add `is_opt_max` property to `_OptLevel` to avoid attr access.
* Add unit test to ensure that invalid opt level behaves as
  default.
  • Loading branch information
stuartarchibald committed Jul 27, 2023
1 parent c6b226b commit c91b102
Show file tree
Hide file tree
Showing 4 changed files with 34 additions and 18 deletions.
12 changes: 6 additions & 6 deletions docs/upcoming_changes/9094.new_feature.rst
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,9 @@ Add support for value ``max`` to ``NUMBA_OPT``.
The optimisation level that Numba applies when compiling can be set through the
environment variable ``NUMBA_OPT``. This has historically been a value between
0 and 3 (inclusive). Support for the value ``max`` has now been added, this is a
Numba-specific optimisation level which will result in Numba running a -O3-like
optimistion before reference counting operations are pruned and then running
another -O3-like optimisation afterwards. This may or may not benefit the
run-time or compile-time performance of user code, but it has been added as it
is similar to the compilation behaviour prior to Numba 0.54 and some users found
it leads to better performance for their programs.
Numba-specific optimisation level which indicates that the user would like Numba
to try running the most optimisation possible, potentially trading a longer
compilation time for better run-time performance. In practice, use of the ``max``
level of optimisation may or may not benefit the run-time or compile-time
performance of user code, but it has been added to present an easy to access
option for users to try if they so wish.
16 changes: 8 additions & 8 deletions numba/core/codegen.py
Original file line number Diff line number Diff line change
Expand Up @@ -1188,14 +1188,14 @@ def _init(self, llvm_module):
self._target_data = engine.target_data
self._data_layout = str(self._target_data)

if config.OPT._raw_value == 'max':
# If the OPT level is set to 'max' then run the cheap pass at O3
# with loop-vectorize enabled. This _may_ result in more optimised
# code, but it also may have the opposite effect. It may also
# increase compilation time, but also may have the opposite effect.
# This behaviour is present so that users can choose what's
# appropriate for their application if they wish to, but there's a
# reasonable default present.
if config.OPT.is_opt_max:
# If the OPT level is set to 'max' then the user is requesting that
# compilation time is traded for potential performance gain. This
# currently manifests as running the "cheap" pass at -O3
# optimisation level with loop-vectorization enabled. There's no
# guarantee that this will increase runtime performance, it may
# detriment it, this is here to give the user an easily accessible
# option to try.
loopvect = True
opt_level = 3
else:
Expand Down
15 changes: 11 additions & 4 deletions numba/core/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -82,10 +82,11 @@ def _validate_captured_errors_style(style_str):

class _OptLevel(int):
"""This class holds the "optimisation level" set in `NUMBA_OPT`. As this env
var can be an int or a string, but is almost always interpreted as an int.
This class subclasses int so as to get the common behaviour but stores the
actual value as a `_raw_value` member to make it available for cases where
accounting for the specific string supplied by the user is necessary."""
var can be an int or a string, but is almost always interpreted as an int,
this class subclasses int so as to get the common behaviour but stores the
actual value as a `_raw_value` member. The value "max" is a special case
and the property `is_opt_max` can be queried to find if the optimisation
level (supplied value at construction time) is "max"."""

def __new__(cls, *args, **kwargs):
assert len(args) == 1
Expand All @@ -97,6 +98,12 @@ def __new__(cls, *args, **kwargs):
new._raw_value = value if value == 'max' else _int_value
return new

@property
def is_opt_max(self):
"""Returns True if the the optimisation level is "max" False
otherwise."""
return self._raw_value == "max"

def __repr__(self):
if isinstance(self._raw_value, str):
arg = f"'{self._raw_value}'"
Expand Down
9 changes: 9 additions & 0 deletions numba/tests/test_config.py
Original file line number Diff line number Diff line change
Expand Up @@ -194,6 +194,15 @@ def test_opt_default(self):
'cost': 'cheap'}
self.check(expected, 3, 3)

@TestCase.run_test_in_subprocess(envvars={'NUMBA_OPT': 'invalid'})
def test_opt_invalid(self):
# NUMBA_OPT='invalid' should just proceed as default case
expected = {'loop_vectorize': False,
'slp_vectorize': False,
'opt': 0,
'cost': 'cheap'}
self.check(expected, 3, 3)


if __name__ == '__main__':
unittest.main()

0 comments on commit c91b102

Please sign in to comment.