bpo-43933: Show frame.f_lineno as None, rather than -1, if there is no line number. (GH-25717)

This commit is contained in:
Mark Shannon 2021-04-29 19:28:50 +01:00 committed by GitHub
parent 2fd928c8c1
commit 088a15c49d
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 20 additions and 2 deletions

View File

@ -2081,7 +2081,10 @@ class PEP626Tests(unittest.TestCase):
while t.tb_next:
t = t.tb_next
frame = t.tb_frame
self.assertEqual(frame.f_lineno-frame.f_code.co_firstlineno, line)
if line is None:
self.assertEqual(frame.f_lineno, line)
else:
self.assertEqual(frame.f_lineno-frame.f_code.co_firstlineno, line)
def test_lineno_after_raise_simple(self):
def simple():
@ -2153,6 +2156,12 @@ class PEP626Tests(unittest.TestCase):
pass
self.lineno_after_raise(after_with, 2)
def test_missing_lineno_shows_as_none(self):
def f():
1/0
self.lineno_after_raise(f, 1)
f.__code__ = f.__code__.replace(co_linetable=b'\x04\x80\xff\x80')
self.lineno_after_raise(f, None)
if __name__ == '__main__':
unittest.main()

View File

@ -0,0 +1,3 @@
If the current position in a frame has no line number then set the f_lineno
attribute to None, instead of -1, to conform to PEP 626. This should not
normally be possible, but might occur in some unusual circumstances.

View File

@ -53,7 +53,13 @@ PyFrame_GetLineNumber(PyFrameObject *f)
static PyObject *
frame_getlineno(PyFrameObject *f, void *closure)
{
return PyLong_FromLong(PyFrame_GetLineNumber(f));
int lineno = PyFrame_GetLineNumber(f);
if (lineno < 0) {
Py_RETURN_NONE;
}
else {
return PyLong_FromLong(lineno);
}
}
static PyObject *