Skip to content

Commit 0e9b689

Browse files
author
Release Manager
committed
gh-39776: Safeguard _sage_getargspec_cython Fix #39735 Actually just a workaround, this sweeps the fundamental problem under the rug. Without source available: ``` sage: from sage.structure.category_object import CategoryObject sage: CategoryObject._CategoryObject__gens_dict Cached version of <method '_CategoryObject__gens_dict' of 'sage.structure.category_object.CategoryObject' objects> sage: type(CategoryObject._CategoryObject__gens_dict) <class 'sage.misc.cachefunc.CachedMethodCaller'> ``` With source available (specialized version `CachedMethodCallerNoArgs` is used, thus more efficient): ``` sage: from sage.structure.category_object import CategoryObject sage: CategoryObject._CategoryObject__gens_dict Cached version of <method '_CategoryObject__gens_dict' of 'sage.structure.category_object.CategoryObject' objects> sage: type(CategoryObject._CategoryObject__gens_dict) <class 'sage.misc.cachefunc.CachedMethodCallerNoArgs'> ``` The proper fix should be to either somehow make `sage_getargspec` always return the correct value, or to somehow make the cache function mechanism know when to use specialization. In any case, it can't hurt to make the function raise the correct exception type. ### 📝 Checklist <!-- Put an `x` in all the boxes that apply. --> - [x] The title is concise and informative. - [x] The description explains in detail what this PR is about. - [x] I have linked a relevant issue or discussion. - [ ] I have created tests covering the changes. - [ ] I have updated the documentation and checked the documentation preview. ### ⌛ Dependencies <!-- List all open PRs that this PR logically depends on. For example, --> <!-- - #12345: short description why this is a dependency --> <!-- - #34567: ... --> URL: #39776 Reported by: user202729 Reviewer(s): Tobias Diez, user202729
2 parents 329be07 + 21dd822 commit 0e9b689

File tree

1 file changed

+12
-5
lines changed

1 file changed

+12
-5
lines changed

src/sage/misc/sageinspect.py

Lines changed: 12 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1140,6 +1140,10 @@ def _sage_getargspec_cython(source):
11401140
defaults=('a string', {(1, 2, 3): True}),
11411141
kwonlyargs=[], kwonlydefaults=None, annotations={})
11421142
"""
1143+
assert isinstance(source, str)
1144+
# the caller ought to ensure this, but if it forgets (e.g. passing None),
1145+
# we avoid raising AttributeError to avoid confusing error message
1146+
# and possible further hard-to-debug errors, see :issue:`39735`
11431147
defpos = source.find('def ')
11441148
assert defpos > -1, "The given source does not contain 'def'"
11451149
s = source[defpos:].strip()
@@ -1677,12 +1681,15 @@ def foo(x, a='\')"', b={not (2+1==3):'bar'}): return
16771681
except TypeError: # arg is not a code object
16781682
# The above "hopefully" was wishful thinking:
16791683
try:
1680-
return inspect.FullArgSpec(*_sage_getargspec_cython(sage_getsource(obj)))
1684+
source = sage_getsource(obj)
16811685
except TypeError: # This happens for Python builtins
1682-
# The best we can do is to return a generic argspec
1683-
args = []
1684-
varargs = 'args'
1685-
varkw = 'kwds'
1686+
source = None
1687+
if source is not None:
1688+
return inspect.FullArgSpec(*_sage_getargspec_cython(source))
1689+
# The best we can do is to return a generic argspec
1690+
args = []
1691+
varargs = 'args'
1692+
varkw = 'kwds'
16861693
try:
16871694
defaults = func_obj.__defaults__
16881695
except AttributeError:

0 commit comments

Comments
 (0)