annotate Python/traceback.c @ 33940:dfd07b7be407 legacy-trunk

SF bug 1061968: threads: segfault or Py_FatalError at exit PyGILState_Ensure(): The fix in 2.4a3 for bug 1010677 reintroduced thread shutdown race bug 225673. Repaired by (once again) ensuring the GIL is held whenever deleting a thread state. Alas, there's no useful test case for this shy bug. Four years ago, only Guido could provoke it, on his box, and today only Armin can provoke it on his box. I've never been able to provoke it (but not for lack of trying!). This is a critical fix for 2.3.5 too, since the fix for 1010677 got backported there already and so also reintroduced 225673. I don't intend to backport this fix. For whoever (if anyone) does, there are other thread fixes in 2.4 that need backporting too, and I bet they need to happen first for this patch to apply cleanly.
author Tim Peters <tim.peters@gmail.com>
date Mon, 08 Nov 2004 04:30:21 +0000
parents 49ec0d8f08ec
children accfb156f9cc 1c4d192f1568
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
145
853b736a6a9e Added copyright notice.
Guido van Rossum <guido@python.org>
parents: 86
diff changeset
1
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
2 /* Traceback implementation */
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
3
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
4 #include "Python.h"
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
5
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
6 #include "compile.h"
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
7 #include "frameobject.h"
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
8 #include "structmember.h"
674
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
9 #include "osdefs.h"
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
10 #include "traceback.h"
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
11
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
12 #define OFF(x) offsetof(PyTracebackObject, x)
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
13
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
14 static struct memberlist tb_memberlist[] = {
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
15 {"tb_next", T_OBJECT, OFF(tb_next)},
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
16 {"tb_frame", T_OBJECT, OFF(tb_frame)},
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
17 {"tb_lasti", T_INT, OFF(tb_lasti)},
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
18 {"tb_lineno", T_INT, OFF(tb_lineno)},
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
19 {NULL} /* Sentinel */
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
20 };
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
21
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
22 static PyObject *
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
23 tb_getattr(PyTracebackObject *tb, char *name)
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
24 {
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
25 return PyMember_Get((char *)tb, tb_memberlist, name);
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
26 }
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
27
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
28 static void
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
29 tb_dealloc(PyTracebackObject *tb)
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
30 {
22650
2288c724fe2b Call PyObject_GC_UnTrack before putting an object on the list of trash.
Neil Schemenauer <nascheme@enme.ucalgary.ca>
parents: 21077
diff changeset
31 PyObject_GC_UnTrack(tb);
11999
c94247b5c355 Christian Tismer's "trashcan" patch:
Guido van Rossum <guido@python.org>
parents: 11294
diff changeset
32 Py_TRASHCAN_SAFE_BEGIN(tb)
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
33 Py_XDECREF(tb->tb_next);
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
34 Py_XDECREF(tb->tb_frame);
20623
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
35 PyObject_GC_Del(tb);
11999
c94247b5c355 Christian Tismer's "trashcan" patch:
Guido van Rossum <guido@python.org>
parents: 11294
diff changeset
36 Py_TRASHCAN_SAFE_END(tb)
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
37 }
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
38
20623
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
39 static int
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
40 tb_traverse(PyTracebackObject *tb, visitproc visit, void *arg)
20623
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
41 {
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
42 int err = 0;
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
43 if (tb->tb_next) {
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
44 err = visit((PyObject *)tb->tb_next, arg);
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
45 if (err)
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
46 return err;
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
47 }
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
48 if (tb->tb_frame)
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
49 err = visit((PyObject *)tb->tb_frame, arg);
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
50 return err;
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
51 }
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
52
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
53 static void
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
54 tb_clear(PyTracebackObject *tb)
20623
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
55 {
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
56 Py_XDECREF(tb->tb_next);
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
57 Py_XDECREF(tb->tb_frame);
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
58 tb->tb_next = NULL;
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
59 tb->tb_frame = NULL;
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
60 }
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
61
20618
57b51966a4f1 Removed two pointless and obfuscating macros.
Tim Peters <tim.peters@gmail.com>
parents: 14375
diff changeset
62 PyTypeObject PyTraceBack_Type = {
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
63 PyObject_HEAD_INIT(&PyType_Type)
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
64 0,
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
65 "traceback",
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
66 sizeof(PyTracebackObject),
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
67 0,
1831
216b755515e6 add function name to traceback info
Guido van Rossum <guido@python.org>
parents: 1425
diff changeset
68 (destructor)tb_dealloc, /*tp_dealloc*/
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
69 0, /*tp_print*/
1831
216b755515e6 add function name to traceback info
Guido van Rossum <guido@python.org>
parents: 1425
diff changeset
70 (getattrfunc)tb_getattr, /*tp_getattr*/
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
71 0, /*tp_setattr*/
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
72 0, /*tp_compare*/
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
73 0, /*tp_repr*/
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
74 0, /*tp_as_number*/
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
75 0, /*tp_as_sequence*/
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
76 0, /*tp_as_mapping*/
20623
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
77 0, /* tp_hash */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
78 0, /* tp_call */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
79 0, /* tp_str */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
80 0, /* tp_getattro */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
81 0, /* tp_setattro */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
82 0, /* tp_as_buffer */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
83 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC,/* tp_flags */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
84 0, /* tp_doc */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
85 (traverseproc)tb_traverse, /* tp_traverse */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
86 (inquiry)tb_clear, /* tp_clear */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
87 0, /* tp_richcompare */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
88 0, /* tp_weaklistoffset */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
89 0, /* tp_iter */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
90 0, /* tp_iternext */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
91 0, /* tp_methods */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
92 0, /* tp_members */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
93 0, /* tp_getset */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
94 0, /* tp_base */
4fb7727e4f47 Make traceback objects collectable.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 20618
diff changeset
95 0, /* tp_dict */
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
96 };
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
97
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
98 static PyTracebackObject *
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
99 newtracebackobject(PyTracebackObject *next, PyFrameObject *frame)
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
100 {
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
101 PyTracebackObject *tb;
20618
57b51966a4f1 Removed two pointless and obfuscating macros.
Tim Peters <tim.peters@gmail.com>
parents: 14375
diff changeset
102 if ((next != NULL && !PyTraceBack_Check(next)) ||
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
103 frame == NULL || !PyFrame_Check(frame)) {
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
104 PyErr_BadInternalCall();
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
105 return NULL;
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
106 }
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
107 tb = PyObject_GC_New(PyTracebackObject, &PyTraceBack_Type);
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
108 if (tb != NULL) {
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
109 Py_XINCREF(next);
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
110 tb->tb_next = next;
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
111 Py_XINCREF(frame);
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
112 tb->tb_frame = frame;
24844
cf5928fab108 This is my patch
Michael W. Hudson <mwh@python.net>
parents: 23029
diff changeset
113 tb->tb_lasti = frame->f_lasti;
cf5928fab108 This is my patch
Michael W. Hudson <mwh@python.net>
parents: 23029
diff changeset
114 tb->tb_lineno = PyCode_Addr2Line(frame->f_code,
cf5928fab108 This is my patch
Michael W. Hudson <mwh@python.net>
parents: 23029
diff changeset
115 frame->f_lasti);
22650
2288c724fe2b Call PyObject_GC_UnTrack before putting an object on the list of trash.
Neil Schemenauer <nascheme@enme.ucalgary.ca>
parents: 21077
diff changeset
116 PyObject_GC_Track(tb);
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
117 }
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
118 return tb;
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
119 }
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
120
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
121 int
13658
f79434ee41fa Mass ANSIfication of function definitions. Doesn't cover all 'extern'
Thomas Wouters <thomas@python.org>
parents: 13256
diff changeset
122 PyTraceBack_Here(PyFrameObject *frame)
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
123 {
5405
b7871ca930ad Massive changes for separate thread state management.
Guido van Rossum <guido@python.org>
parents: 5404
diff changeset
124 PyThreadState *tstate = frame->f_tstate;
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
125 PyTracebackObject *oldtb = (PyTracebackObject *) tstate->curexc_traceback;
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
126 PyTracebackObject *tb = newtracebackobject(oldtb, frame);
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
127 if (tb == NULL)
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
128 return -1;
5405
b7871ca930ad Massive changes for separate thread state management.
Guido van Rossum <guido@python.org>
parents: 5404
diff changeset
129 tstate->curexc_traceback = (PyObject *)tb;
b7871ca930ad Massive changes for separate thread state management.
Guido van Rossum <guido@python.org>
parents: 5404
diff changeset
130 Py_XDECREF(oldtb);
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
131 return 0;
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
132 }
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
133
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
134 static int
13658
f79434ee41fa Mass ANSIfication of function definitions. Doesn't cover all 'extern'
Thomas Wouters <thomas@python.org>
parents: 13256
diff changeset
135 tb_displayline(PyObject *f, char *filename, int lineno, char *name)
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
136 {
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
137 int err = 0;
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
138 FILE *xfp;
21057
2c0a9a5086e1 SF bug 485175: buffer overflow in traceback.c.
Tim Peters <tim.peters@gmail.com>
parents: 20623
diff changeset
139 char linebuf[2000];
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
140 int i;
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
141 if (filename == NULL || name == NULL)
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
142 return -1;
1831
216b755515e6 add function name to traceback info
Guido van Rossum <guido@python.org>
parents: 1425
diff changeset
143 /* This is needed by Emacs' compile command */
21057
2c0a9a5086e1 SF bug 485175: buffer overflow in traceback.c.
Tim Peters <tim.peters@gmail.com>
parents: 20623
diff changeset
144 #define FMT " File \"%.500s\", line %d, in %.500s\n"
23029
8291473fde3e Mass checkin of universal newline support.
Jack Jansen <jack.jansen@cwi.nl>
parents: 22650
diff changeset
145 xfp = fopen(filename, "r" PY_STDIOTEXTMODE);
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
146 if (xfp == NULL) {
674
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
147 /* Search tail of filename in sys.path before giving up */
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
148 PyObject *path;
674
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
149 char *tail = strrchr(filename, SEP);
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
150 if (tail == NULL)
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
151 tail = filename;
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
152 else
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
153 tail++;
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
154 path = PySys_GetObject("path");
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
155 if (path != NULL && PyList_Check(path)) {
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
156 int npath = PyList_Size(path);
13096
8c8de5b736dc Trent Mick's Win64 changes: size_t vs. int or long; also some overflow
Guido van Rossum <guido@python.org>
parents: 12576
diff changeset
157 size_t taillen = strlen(tail);
674
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
158 char namebuf[MAXPATHLEN+1];
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
159 for (i = 0; i < npath; i++) {
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
160 PyObject *v = PyList_GetItem(path, i);
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
161 if (v == NULL) {
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
162 PyErr_Clear();
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
163 break;
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
164 }
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
165 if (PyString_Check(v)) {
13096
8c8de5b736dc Trent Mick's Win64 changes: size_t vs. int or long; also some overflow
Guido van Rossum <guido@python.org>
parents: 12576
diff changeset
166 size_t len;
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
167 len = PyString_Size(v);
1909
0c232194a64f * Python/traceback.c: security fix -- check for buffer oveflow
Guido van Rossum <guido@python.org>
parents: 1831
diff changeset
168 if (len + 1 + taillen >= MAXPATHLEN)
0c232194a64f * Python/traceback.c: security fix -- check for buffer oveflow
Guido van Rossum <guido@python.org>
parents: 1831
diff changeset
169 continue; /* Too long */
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
170 strcpy(namebuf, PyString_AsString(v));
13096
8c8de5b736dc Trent Mick's Win64 changes: size_t vs. int or long; also some overflow
Guido van Rossum <guido@python.org>
parents: 12576
diff changeset
171 if (strlen(namebuf) != len)
1909
0c232194a64f * Python/traceback.c: security fix -- check for buffer oveflow
Guido van Rossum <guido@python.org>
parents: 1831
diff changeset
172 continue; /* v contains '\0' */
674
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
173 if (len > 0 && namebuf[len-1] != SEP)
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
174 namebuf[len++] = SEP;
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
175 strcpy(namebuf+len, tail);
23029
8291473fde3e Mass checkin of universal newline support.
Jack Jansen <jack.jansen@cwi.nl>
parents: 22650
diff changeset
176 xfp = fopen(namebuf, "r" PY_STDIOTEXTMODE);
674
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
177 if (xfp != NULL) {
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
178 filename = namebuf;
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
179 break;
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
180 }
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
181 }
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
182 }
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
183 }
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
184 }
21077
379fc66f4c96 Use PyOS_snprintf instead of sprintf.
Jeremy Hylton <jeremy@alum.mit.edu>
parents: 21057
diff changeset
185 PyOS_snprintf(linebuf, sizeof(linebuf), FMT, filename, lineno, name);
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
186 err = PyFile_WriteString(linebuf, f);
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
187 if (xfp == NULL || err != 0)
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
188 return err;
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
189 for (i = 0; i < lineno; i++) {
11294
d3696bf08eee Tim Peters fixed PR#75: very long lines cause incorrect tracebacks.
Guido van Rossum <guido@python.org>
parents: 5608
diff changeset
190 char* pLastChar = &linebuf[sizeof(linebuf)-2];
d3696bf08eee Tim Peters fixed PR#75: very long lines cause incorrect tracebacks.
Guido van Rossum <guido@python.org>
parents: 5608
diff changeset
191 do {
d3696bf08eee Tim Peters fixed PR#75: very long lines cause incorrect tracebacks.
Guido van Rossum <guido@python.org>
parents: 5608
diff changeset
192 *pLastChar = '\0';
23029
8291473fde3e Mass checkin of universal newline support.
Jack Jansen <jack.jansen@cwi.nl>
parents: 22650
diff changeset
193 if (Py_UniversalNewlineFgets(linebuf, sizeof linebuf, xfp, NULL) == NULL)
11294
d3696bf08eee Tim Peters fixed PR#75: very long lines cause incorrect tracebacks.
Guido van Rossum <guido@python.org>
parents: 5608
diff changeset
194 break;
d3696bf08eee Tim Peters fixed PR#75: very long lines cause incorrect tracebacks.
Guido van Rossum <guido@python.org>
parents: 5608
diff changeset
195 /* fgets read *something*; if it didn't get as
d3696bf08eee Tim Peters fixed PR#75: very long lines cause incorrect tracebacks.
Guido van Rossum <guido@python.org>
parents: 5608
diff changeset
196 far as pLastChar, it must have found a newline
d3696bf08eee Tim Peters fixed PR#75: very long lines cause incorrect tracebacks.
Guido van Rossum <guido@python.org>
parents: 5608
diff changeset
197 or hit the end of the file; if pLastChar is \n,
d3696bf08eee Tim Peters fixed PR#75: very long lines cause incorrect tracebacks.
Guido van Rossum <guido@python.org>
parents: 5608
diff changeset
198 it obviously found a newline; else we haven't
d3696bf08eee Tim Peters fixed PR#75: very long lines cause incorrect tracebacks.
Guido van Rossum <guido@python.org>
parents: 5608
diff changeset
199 yet seen a newline, so must continue */
d3696bf08eee Tim Peters fixed PR#75: very long lines cause incorrect tracebacks.
Guido van Rossum <guido@python.org>
parents: 5608
diff changeset
200 } while (*pLastChar != '\0' && *pLastChar != '\n');
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
201 }
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
202 if (i == lineno) {
674
4e2d239dc64c Move printing of filename and lineno to tb_displayline.
Guido van Rossum <guido@python.org>
parents: 597
diff changeset
203 char *p = linebuf;
2811
07fc4fefb683 ignore control-l (parallelling change to tokenizer.c)
Guido van Rossum <guido@python.org>
parents: 2062
diff changeset
204 while (*p == ' ' || *p == '\t' || *p == '\014')
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
205 p++;
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
206 err = PyFile_WriteString(" ", f);
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
207 if (err == 0) {
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
208 err = PyFile_WriteString(p, f);
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
209 if (err == 0 && strchr(p, '\n') == NULL)
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
210 err = PyFile_WriteString("\n", f);
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
211 }
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
212 }
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
213 fclose(xfp);
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
214 return err;
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
215 }
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
216
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
217 static int
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
218 tb_printinternal(PyTracebackObject *tb, PyObject *f, int limit)
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
219 {
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
220 int err = 0;
1425
72bddfad351a * mpzmodule.c: cast some methods to the proper type.
Guido van Rossum <guido@python.org>
parents: 1257
diff changeset
221 int depth = 0;
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
222 PyTracebackObject *tb1 = tb;
1425
72bddfad351a * mpzmodule.c: cast some methods to the proper type.
Guido van Rossum <guido@python.org>
parents: 1257
diff changeset
223 while (tb1 != NULL) {
72bddfad351a * mpzmodule.c: cast some methods to the proper type.
Guido van Rossum <guido@python.org>
parents: 1257
diff changeset
224 depth++;
72bddfad351a * mpzmodule.c: cast some methods to the proper type.
Guido van Rossum <guido@python.org>
parents: 1257
diff changeset
225 tb1 = tb1->tb_next;
72bddfad351a * mpzmodule.c: cast some methods to the proper type.
Guido van Rossum <guido@python.org>
parents: 1257
diff changeset
226 }
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
227 while (tb != NULL && err == 0) {
5046
658815230546 Get the line number from PyCode_Addr2Line instead of believing
Guido van Rossum <guido@python.org>
parents: 4503
diff changeset
228 if (depth <= limit) {
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
229 err = tb_displayline(f,
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
230 PyString_AsString(
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
231 tb->tb_frame->f_code->co_filename),
1831
216b755515e6 add function name to traceback info
Guido van Rossum <guido@python.org>
parents: 1425
diff changeset
232 tb->tb_lineno,
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
233 PyString_AsString(tb->tb_frame->f_code->co_name));
5046
658815230546 Get the line number from PyCode_Addr2Line instead of believing
Guido van Rossum <guido@python.org>
parents: 4503
diff changeset
234 }
1425
72bddfad351a * mpzmodule.c: cast some methods to the proper type.
Guido van Rossum <guido@python.org>
parents: 1257
diff changeset
235 depth--;
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
236 tb = tb->tb_next;
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
237 if (err == 0)
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
238 err = PyErr_CheckSignals();
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
239 }
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
240 return err;
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
241 }
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
242
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
243 int
13658
f79434ee41fa Mass ANSIfication of function definitions. Doesn't cover all 'extern'
Thomas Wouters <thomas@python.org>
parents: 13256
diff changeset
244 PyTraceBack_Print(PyObject *v, PyObject *f)
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
245 {
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
246 int err;
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
247 PyObject *limitv;
1425
72bddfad351a * mpzmodule.c: cast some methods to the proper type.
Guido van Rossum <guido@python.org>
parents: 1257
diff changeset
248 int limit = 1000;
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
249 if (v == NULL)
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
250 return 0;
20618
57b51966a4f1 Removed two pointless and obfuscating macros.
Tim Peters <tim.peters@gmail.com>
parents: 14375
diff changeset
251 if (!PyTraceBack_Check(v)) {
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
252 PyErr_BadInternalCall();
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
253 return -1;
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
254 }
5372
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
255 limitv = PySys_GetObject("tracebacklimit");
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
256 if (limitv && PyInt_Check(limitv)) {
424922afc1bb Quickly renamed.
Guido van Rossum <guido@python.org>
parents: 5317
diff changeset
257 limit = PyInt_AsLong(limitv);
1425
72bddfad351a * mpzmodule.c: cast some methods to the proper type.
Guido van Rossum <guido@python.org>
parents: 1257
diff changeset
258 if (limit <= 0)
72bddfad351a * mpzmodule.c: cast some methods to the proper type.
Guido van Rossum <guido@python.org>
parents: 1257
diff changeset
259 return 0;
72bddfad351a * mpzmodule.c: cast some methods to the proper type.
Guido van Rossum <guido@python.org>
parents: 1257
diff changeset
260 }
12137
5b5581af951c Change traceback error message to "most recent call last" from
Guido van Rossum <guido@python.org>
parents: 11999
diff changeset
261 err = PyFile_WriteString("Traceback (most recent call last):\n", f);
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
262 if (!err)
31739
49ec0d8f08ec Moved tracebackobject to traceback.h, Closes SF Bug #497067
Nicholas Bastin <nick.bastin@gmail.com>
parents: 30968
diff changeset
263 err = tb_printinternal((PyTracebackObject *)v, f, limit);
5608
79e49cbce2ef PyFile_WriteString now returns an error indicator instead of calling
Guido van Rossum <guido@python.org>
parents: 5405
diff changeset
264 return err;
86
a6934380c6e7 "Compiling" version
Guido van Rossum <guido@python.org>
parents:
diff changeset
265 }