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
bpo-31810: Add smelly.py to check exported symbols #4057
Conversation
* Add Tools/scripts/smelly.py: script checking if all symbols exported by libpython start with "Py" or "_Py". * Modify "make smelly" to run smelly.py: the command now fails with a non-zero exit code if libpython leaks a "smelly" symbol. * Travis CI now runs "make smelly"
|
@CuriousLearner proposed a simpler patch which only runs "make smelly" : PR #4054, as I proposed in the BPO. Sadly, I didn't notice that "make smelly" always exits with an exit code 0, even if libpython leaks symbols. @taleinat: Would you mind to review this PR please? |
|
I tested my change manually with this diff: make smelly fails as expected with non-zero exit code: When libpython doesn't leak symbols, "make smelly" succeed: |
Use a blacklist of symbol types rather than a whitelist of symbol
types ("T", "D", "B").
Display the list of ignored symbol types, and add also the symbol
type in the list of smelly symbols.
.travis.yml
Outdated
| @@ -91,6 +91,8 @@ script: | |||
| - if [[ "$TRAVIS_OS_NAME" == "linux" ]]; then ./python Tools/scripts/patchcheck.py --travis $TRAVIS_PULL_REQUEST; fi | |||
| # `-r -w` implicitly provided through `make buildbottest`. | |||
| - make buildbottest TESTOPTS="-j4 -uall,-cpu" | |||
| # Check if all symbols exported by libpython start with "Py" or "_Py" | |||
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.
Maybe change "Check if" to "Check that" or "Validate that" for better clarity?
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.
done
Makefile.pre.in
Outdated
| @@ -1659,10 +1659,9 @@ distclean: clobber | |||
| -o -name '*.bak' ')' \ | |||
| -exec rm -f {} ';' | |||
|
|
|||
| # Check for smelly exported symbols (not starting with Py/_Py) | |||
| # Check if all symbols exported by libpython start with "Py" or "_Py" | |||
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.
See previous comment.
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.
done
| return stdout | ||
|
|
||
|
|
||
| def get_smelly_symbols(stdout): |
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.
stdout is not a very informative name here, and somewhat confusing in the body of the function.
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.
Done, renamed to nm_output.
|
|
||
|
|
||
| def get_smelly_symbols(stdout): | ||
| symbols = [] |
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.
Why not have this function be a generator and just yield the smelly symbols? Just style preference so feel free to ignore.
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.
I prefer a list :-)
Tools/scripts/smelly.py
Outdated
| # If lowercase, the symbol is usually local; if uppercase, the symbol | ||
| # is global (external). There are however a few lowercase symbols that | ||
| # are shown for special global symbols ("u", "v" and "w"). | ||
| if symtype.islower() and symtype not in ("u", "v" "w"): |
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.
Is the lack of comma between 'v' and 'w' intended or is it just a typo ?
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.
Oops, it's a bug. Fixed.
|
The current "make smelly" rule don't check for these symbol types:
This list seems incomplete. "C" symbols are ignored, whereas there are also exported:
I modified the code to use a blacklist of private symbol types, rather than a whitelist of public symbols. I tested manually: the new modified smelly.py is now able to detect a leaked "C" symbol which doesn't start with Py/_Py. |
Tools/scripts/smelly.py
Outdated
| @@ -1,5 +1,5 @@ | |||
| #!/usr/bin/env python | |||
| # Script checking if all symbols exported by libpython start with "Py" or "_Py" | |||
| # Script checking that all symbols exported by libpython start with Py or _Py | |||
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.
I would use "Py" or "_Py" to keep the same style with others comments
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.
I tried, but it doesn't fit into 80 characters :-)
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.
You can write:
# Script checking that all symbols exported by libpython
# start with Py or _Py
Is just a style preference =D
|
Thanks for your reviews @taleinat, @eamanu and @SylvainDe! I merged my PR. |
exported by libpython start with "Py" or "_Py".
non-zero exit code if libpython leaks a "smelly" symbol.
https://bugs.python.org/issue31810