blob: b08cbdd6aed3572d4026ff2acb7694ae3a216090 [file] [log] [blame]
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001/*
2 * New exceptions.c written in Iceland by Richard Jones and Georg Brandl.
3 *
4 * Thanks go to Tim Peters and Michael Hudson for debugging.
5 */
6
Thomas Wouters477c8d52006-05-27 19:21:47 +00007#define PY_SSIZE_T_CLEAN
8#include <Python.h>
Victor Stinner331a6a52019-05-27 16:39:22 +02009#include "pycore_initconfig.h"
Victor Stinnerbcda8f12018-11-21 22:27:47 +010010#include "pycore_object.h"
Victor Stinner4a21e572020-04-15 02:35:41 +020011#include "structmember.h" // PyMemberDef
Victor Stinner361dcdc2020-04-15 03:24:57 +020012#include "osdefs.h" // SEP
Thomas Wouters477c8d52006-05-27 19:21:47 +000013
Thomas Wouters477c8d52006-05-27 19:21:47 +000014
Antoine Pitrou6b4883d2011-10-12 02:54:14 +020015/* Compatibility aliases */
16PyObject *PyExc_EnvironmentError = NULL;
17PyObject *PyExc_IOError = NULL;
18#ifdef MS_WINDOWS
19PyObject *PyExc_WindowsError = NULL;
20#endif
Antoine Pitrou6b4883d2011-10-12 02:54:14 +020021
Victor Stinner281cce12020-06-23 22:55:46 +020022
23static struct _Py_exc_state*
24get_exc_state(void)
25{
26 PyInterpreterState *interp = _PyInterpreterState_GET();
27 return &interp->exc_state;
28}
Antoine Pitrou6b4883d2011-10-12 02:54:14 +020029
30
Thomas Wouters477c8d52006-05-27 19:21:47 +000031/* NOTE: If the exception class hierarchy changes, don't forget to update
32 * Lib/test/exception_hierarchy.txt
33 */
34
Thomas Wouters477c8d52006-05-27 19:21:47 +000035/*
36 * BaseException
37 */
38static PyObject *
39BaseException_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
40{
41 PyBaseExceptionObject *self;
42
43 self = (PyBaseExceptionObject *)type->tp_alloc(type, 0);
Guido van Rossumd8faa362007-04-27 19:54:29 +000044 if (!self)
45 return NULL;
Thomas Wouters477c8d52006-05-27 19:21:47 +000046 /* the dict is created on the fly in PyObject_GenericSetAttr */
Guido van Rossumebe3e162007-05-17 18:20:34 +000047 self->dict = NULL;
Collin Winter1966f1c2007-09-01 20:26:44 +000048 self->traceback = self->cause = self->context = NULL;
Benjamin Petersond5a1c442012-05-14 22:09:31 -070049 self->suppress_context = 0;
Thomas Wouters477c8d52006-05-27 19:21:47 +000050
Richard Oudkerk5562d9d2012-07-28 17:45:28 +010051 if (args) {
52 self->args = args;
53 Py_INCREF(args);
54 return (PyObject *)self;
55 }
56
Thomas Wouters477c8d52006-05-27 19:21:47 +000057 self->args = PyTuple_New(0);
58 if (!self->args) {
59 Py_DECREF(self);
60 return NULL;
61 }
62
Thomas Wouters477c8d52006-05-27 19:21:47 +000063 return (PyObject *)self;
64}
65
66static int
67BaseException_init(PyBaseExceptionObject *self, PyObject *args, PyObject *kwds)
68{
Christian Heimes90aa7642007-12-19 02:45:37 +000069 if (!_PyArg_NoKeywords(Py_TYPE(self)->tp_name, kwds))
Thomas Wouters4d70c3d2006-06-08 14:42:34 +000070 return -1;
71
Serhiy Storchaka576f1322016-01-05 21:27:54 +020072 Py_INCREF(args);
Serhiy Storchakaec397562016-04-06 09:50:03 +030073 Py_XSETREF(self->args, args);
Thomas Wouters477c8d52006-05-27 19:21:47 +000074
Thomas Wouters477c8d52006-05-27 19:21:47 +000075 return 0;
76}
77
Thomas Wouters4d70c3d2006-06-08 14:42:34 +000078static int
Thomas Wouters477c8d52006-05-27 19:21:47 +000079BaseException_clear(PyBaseExceptionObject *self)
80{
81 Py_CLEAR(self->dict);
82 Py_CLEAR(self->args);
Collin Winter828f04a2007-08-31 00:04:24 +000083 Py_CLEAR(self->traceback);
Collin Winter1966f1c2007-09-01 20:26:44 +000084 Py_CLEAR(self->cause);
85 Py_CLEAR(self->context);
Thomas Wouters477c8d52006-05-27 19:21:47 +000086 return 0;
87}
88
89static void
90BaseException_dealloc(PyBaseExceptionObject *self)
91{
Thomas Wouters89f507f2006-12-13 04:49:30 +000092 _PyObject_GC_UNTRACK(self);
Thomas Wouters477c8d52006-05-27 19:21:47 +000093 BaseException_clear(self);
Christian Heimes90aa7642007-12-19 02:45:37 +000094 Py_TYPE(self)->tp_free((PyObject *)self);
Thomas Wouters477c8d52006-05-27 19:21:47 +000095}
96
Thomas Wouters4d70c3d2006-06-08 14:42:34 +000097static int
Thomas Wouters477c8d52006-05-27 19:21:47 +000098BaseException_traverse(PyBaseExceptionObject *self, visitproc visit, void *arg)
99{
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000100 Py_VISIT(self->dict);
Thomas Wouters477c8d52006-05-27 19:21:47 +0000101 Py_VISIT(self->args);
Collin Winter828f04a2007-08-31 00:04:24 +0000102 Py_VISIT(self->traceback);
Collin Winter1966f1c2007-09-01 20:26:44 +0000103 Py_VISIT(self->cause);
104 Py_VISIT(self->context);
Thomas Wouters477c8d52006-05-27 19:21:47 +0000105 return 0;
106}
107
108static PyObject *
109BaseException_str(PyBaseExceptionObject *self)
110{
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000111 switch (PyTuple_GET_SIZE(self->args)) {
Thomas Wouters477c8d52006-05-27 19:21:47 +0000112 case 0:
Walter Dörwaldf5bec7c2007-05-26 15:03:32 +0000113 return PyUnicode_FromString("");
Thomas Wouters477c8d52006-05-27 19:21:47 +0000114 case 1:
Thomas Heller519a0422007-11-15 20:48:54 +0000115 return PyObject_Str(PyTuple_GET_ITEM(self->args, 0));
Thomas Wouters477c8d52006-05-27 19:21:47 +0000116 default:
Thomas Heller519a0422007-11-15 20:48:54 +0000117 return PyObject_Str(self->args);
Thomas Wouters477c8d52006-05-27 19:21:47 +0000118 }
Thomas Wouters477c8d52006-05-27 19:21:47 +0000119}
120
121static PyObject *
122BaseException_repr(PyBaseExceptionObject *self)
123{
Serhiy Storchaka4ab46d72017-09-17 21:11:04 +0300124 const char *name = _PyType_Name(Py_TYPE(self));
Serhiy Storchakaf8a4c032017-11-15 17:53:28 +0200125 if (PyTuple_GET_SIZE(self->args) == 1)
126 return PyUnicode_FromFormat("%s(%R)", name,
127 PyTuple_GET_ITEM(self->args, 0));
128 else
129 return PyUnicode_FromFormat("%s%R", name, self->args);
Thomas Wouters477c8d52006-05-27 19:21:47 +0000130}
131
132/* Pickling support */
133static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +0530134BaseException_reduce(PyBaseExceptionObject *self, PyObject *Py_UNUSED(ignored))
Thomas Wouters477c8d52006-05-27 19:21:47 +0000135{
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000136 if (self->args && self->dict)
Christian Heimes90aa7642007-12-19 02:45:37 +0000137 return PyTuple_Pack(3, Py_TYPE(self), self->args, self->dict);
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000138 else
Christian Heimes90aa7642007-12-19 02:45:37 +0000139 return PyTuple_Pack(2, Py_TYPE(self), self->args);
Thomas Wouters477c8d52006-05-27 19:21:47 +0000140}
141
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000142/*
143 * Needed for backward compatibility, since exceptions used to store
144 * all their attributes in the __dict__. Code is taken from cPickle's
145 * load_build function.
146 */
147static PyObject *
148BaseException_setstate(PyObject *self, PyObject *state)
149{
150 PyObject *d_key, *d_value;
151 Py_ssize_t i = 0;
152
153 if (state != Py_None) {
154 if (!PyDict_Check(state)) {
155 PyErr_SetString(PyExc_TypeError, "state is not a dictionary");
156 return NULL;
157 }
158 while (PyDict_Next(state, &i, &d_key, &d_value)) {
159 if (PyObject_SetAttr(self, d_key, d_value) < 0)
160 return NULL;
161 }
162 }
163 Py_RETURN_NONE;
164}
Thomas Wouters477c8d52006-05-27 19:21:47 +0000165
Collin Winter828f04a2007-08-31 00:04:24 +0000166static PyObject *
167BaseException_with_traceback(PyObject *self, PyObject *tb) {
168 if (PyException_SetTraceback(self, tb))
169 return NULL;
170
171 Py_INCREF(self);
172 return self;
173}
174
Georg Brandl76941002008-05-05 21:38:47 +0000175PyDoc_STRVAR(with_traceback_doc,
176"Exception.with_traceback(tb) --\n\
177 set self.__traceback__ to tb and return self.");
178
Thomas Wouters477c8d52006-05-27 19:21:47 +0000179
180static PyMethodDef BaseException_methods[] = {
181 {"__reduce__", (PyCFunction)BaseException_reduce, METH_NOARGS },
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000182 {"__setstate__", (PyCFunction)BaseException_setstate, METH_O },
Georg Brandl76941002008-05-05 21:38:47 +0000183 {"with_traceback", (PyCFunction)BaseException_with_traceback, METH_O,
184 with_traceback_doc},
Thomas Wouters477c8d52006-05-27 19:21:47 +0000185 {NULL, NULL, 0, NULL},
186};
187
Thomas Wouters477c8d52006-05-27 19:21:47 +0000188static PyObject *
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +0200189BaseException_get_args(PyBaseExceptionObject *self, void *Py_UNUSED(ignored))
Thomas Wouters477c8d52006-05-27 19:21:47 +0000190{
191 if (self->args == NULL) {
Serhiy Storchaka228b12e2017-01-23 09:47:21 +0200192 Py_RETURN_NONE;
Thomas Wouters477c8d52006-05-27 19:21:47 +0000193 }
194 Py_INCREF(self->args);
195 return self->args;
196}
197
198static int
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +0200199BaseException_set_args(PyBaseExceptionObject *self, PyObject *val, void *Py_UNUSED(ignored))
Thomas Wouters477c8d52006-05-27 19:21:47 +0000200{
201 PyObject *seq;
202 if (val == NULL) {
203 PyErr_SetString(PyExc_TypeError, "args may not be deleted");
204 return -1;
205 }
206 seq = PySequence_Tuple(val);
Benjamin Peterson90b13582012-02-03 19:22:31 -0500207 if (!seq)
208 return -1;
Serhiy Storchaka48842712016-04-06 09:45:48 +0300209 Py_XSETREF(self->args, seq);
Thomas Wouters477c8d52006-05-27 19:21:47 +0000210 return 0;
211}
212
Collin Winter828f04a2007-08-31 00:04:24 +0000213static PyObject *
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +0200214BaseException_get_tb(PyBaseExceptionObject *self, void *Py_UNUSED(ignored))
Collin Winter828f04a2007-08-31 00:04:24 +0000215{
216 if (self->traceback == NULL) {
Serhiy Storchaka228b12e2017-01-23 09:47:21 +0200217 Py_RETURN_NONE;
Collin Winter828f04a2007-08-31 00:04:24 +0000218 }
219 Py_INCREF(self->traceback);
220 return self->traceback;
221}
222
223static int
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +0200224BaseException_set_tb(PyBaseExceptionObject *self, PyObject *tb, void *Py_UNUSED(ignored))
Collin Winter828f04a2007-08-31 00:04:24 +0000225{
226 if (tb == NULL) {
227 PyErr_SetString(PyExc_TypeError, "__traceback__ may not be deleted");
228 return -1;
229 }
230 else if (!(tb == Py_None || PyTraceBack_Check(tb))) {
231 PyErr_SetString(PyExc_TypeError,
232 "__traceback__ must be a traceback or None");
233 return -1;
234 }
235
Serhiy Storchaka37665722016-08-20 21:22:03 +0300236 Py_INCREF(tb);
Serhiy Storchaka48842712016-04-06 09:45:48 +0300237 Py_XSETREF(self->traceback, tb);
Collin Winter828f04a2007-08-31 00:04:24 +0000238 return 0;
239}
240
Georg Brandlab6f2f62009-03-31 04:16:10 +0000241static PyObject *
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +0200242BaseException_get_context(PyObject *self, void *Py_UNUSED(ignored))
243{
Georg Brandlab6f2f62009-03-31 04:16:10 +0000244 PyObject *res = PyException_GetContext(self);
Benjamin Peterson90b13582012-02-03 19:22:31 -0500245 if (res)
246 return res; /* new reference already returned above */
Georg Brandlab6f2f62009-03-31 04:16:10 +0000247 Py_RETURN_NONE;
248}
249
250static int
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +0200251BaseException_set_context(PyObject *self, PyObject *arg, void *Py_UNUSED(ignored))
252{
Georg Brandlab6f2f62009-03-31 04:16:10 +0000253 if (arg == NULL) {
254 PyErr_SetString(PyExc_TypeError, "__context__ may not be deleted");
255 return -1;
256 } else if (arg == Py_None) {
257 arg = NULL;
258 } else if (!PyExceptionInstance_Check(arg)) {
259 PyErr_SetString(PyExc_TypeError, "exception context must be None "
260 "or derive from BaseException");
261 return -1;
262 } else {
263 /* PyException_SetContext steals this reference */
264 Py_INCREF(arg);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000265 }
Georg Brandlab6f2f62009-03-31 04:16:10 +0000266 PyException_SetContext(self, arg);
267 return 0;
268}
269
270static PyObject *
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +0200271BaseException_get_cause(PyObject *self, void *Py_UNUSED(ignored))
272{
Georg Brandlab6f2f62009-03-31 04:16:10 +0000273 PyObject *res = PyException_GetCause(self);
Benjamin Peterson90b13582012-02-03 19:22:31 -0500274 if (res)
275 return res; /* new reference already returned above */
Benjamin Petersond5a1c442012-05-14 22:09:31 -0700276 Py_RETURN_NONE;
Georg Brandlab6f2f62009-03-31 04:16:10 +0000277}
278
279static int
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +0200280BaseException_set_cause(PyObject *self, PyObject *arg, void *Py_UNUSED(ignored))
281{
Georg Brandlab6f2f62009-03-31 04:16:10 +0000282 if (arg == NULL) {
283 PyErr_SetString(PyExc_TypeError, "__cause__ may not be deleted");
284 return -1;
Benjamin Petersond5a1c442012-05-14 22:09:31 -0700285 } else if (arg == Py_None) {
286 arg = NULL;
287 } else if (!PyExceptionInstance_Check(arg)) {
288 PyErr_SetString(PyExc_TypeError, "exception cause must be None "
289 "or derive from BaseException");
290 return -1;
291 } else {
292 /* PyException_SetCause steals this reference */
293 Py_INCREF(arg);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000294 }
Benjamin Petersond5a1c442012-05-14 22:09:31 -0700295 PyException_SetCause(self, arg);
296 return 0;
Georg Brandlab6f2f62009-03-31 04:16:10 +0000297}
298
Guido van Rossum360e4b82007-05-14 22:51:27 +0000299
Thomas Wouters477c8d52006-05-27 19:21:47 +0000300static PyGetSetDef BaseException_getset[] = {
Benjamin Peterson23d7f122012-02-19 20:02:57 -0500301 {"__dict__", PyObject_GenericGetDict, PyObject_GenericSetDict},
Thomas Wouters477c8d52006-05-27 19:21:47 +0000302 {"args", (getter)BaseException_get_args, (setter)BaseException_set_args},
Collin Winter828f04a2007-08-31 00:04:24 +0000303 {"__traceback__", (getter)BaseException_get_tb, (setter)BaseException_set_tb},
Serhiy Storchakad4f9cf52018-11-27 19:34:35 +0200304 {"__context__", BaseException_get_context,
305 BaseException_set_context, PyDoc_STR("exception context")},
306 {"__cause__", BaseException_get_cause,
307 BaseException_set_cause, PyDoc_STR("exception cause")},
Thomas Wouters477c8d52006-05-27 19:21:47 +0000308 {NULL},
309};
310
311
Victor Stinnerb0be6b32020-05-05 17:07:41 +0200312static inline PyBaseExceptionObject*
313_PyBaseExceptionObject_cast(PyObject *exc)
314{
315 assert(PyExceptionInstance_Check(exc));
316 return (PyBaseExceptionObject *)exc;
317}
318
319
Collin Winter828f04a2007-08-31 00:04:24 +0000320PyObject *
Victor Stinnerb0be6b32020-05-05 17:07:41 +0200321PyException_GetTraceback(PyObject *self)
322{
323 PyBaseExceptionObject *base_self = _PyBaseExceptionObject_cast(self);
Collin Winter828f04a2007-08-31 00:04:24 +0000324 Py_XINCREF(base_self->traceback);
325 return base_self->traceback;
326}
327
328
329int
Victor Stinnerb0be6b32020-05-05 17:07:41 +0200330PyException_SetTraceback(PyObject *self, PyObject *tb)
331{
332 return BaseException_set_tb(_PyBaseExceptionObject_cast(self), tb, NULL);
Collin Winter828f04a2007-08-31 00:04:24 +0000333}
334
335PyObject *
Victor Stinnerb0be6b32020-05-05 17:07:41 +0200336PyException_GetCause(PyObject *self)
337{
338 PyObject *cause = _PyBaseExceptionObject_cast(self)->cause;
Collin Winter828f04a2007-08-31 00:04:24 +0000339 Py_XINCREF(cause);
340 return cause;
341}
342
343/* Steals a reference to cause */
344void
Serhiy Storchaka576f1322016-01-05 21:27:54 +0200345PyException_SetCause(PyObject *self, PyObject *cause)
346{
Victor Stinnerb0be6b32020-05-05 17:07:41 +0200347 PyBaseExceptionObject *base_self = _PyBaseExceptionObject_cast(self);
348 base_self->suppress_context = 1;
349 Py_XSETREF(base_self->cause, cause);
Collin Winter828f04a2007-08-31 00:04:24 +0000350}
351
352PyObject *
Victor Stinnerb0be6b32020-05-05 17:07:41 +0200353PyException_GetContext(PyObject *self)
354{
355 PyObject *context = _PyBaseExceptionObject_cast(self)->context;
Collin Winter828f04a2007-08-31 00:04:24 +0000356 Py_XINCREF(context);
357 return context;
358}
359
360/* Steals a reference to context */
361void
Serhiy Storchaka576f1322016-01-05 21:27:54 +0200362PyException_SetContext(PyObject *self, PyObject *context)
363{
Victor Stinnerb0be6b32020-05-05 17:07:41 +0200364 Py_XSETREF(_PyBaseExceptionObject_cast(self)->context, context);
Collin Winter828f04a2007-08-31 00:04:24 +0000365}
366
Christian Tismerea62ce72018-06-09 20:32:25 +0200367#undef PyExceptionClass_Name
Christian Tismer83987132018-06-11 00:48:28 +0200368
Serhiy Storchakaceeef102018-06-15 11:09:43 +0300369const char *
Christian Tismerea62ce72018-06-09 20:32:25 +0200370PyExceptionClass_Name(PyObject *ob)
371{
Victor Stinnerb0be6b32020-05-05 17:07:41 +0200372 assert(PyExceptionClass_Check(ob));
Serhiy Storchakaceeef102018-06-15 11:09:43 +0300373 return ((PyTypeObject*)ob)->tp_name;
Christian Tismerea62ce72018-06-09 20:32:25 +0200374}
Collin Winter828f04a2007-08-31 00:04:24 +0000375
Benjamin Petersond5a1c442012-05-14 22:09:31 -0700376static struct PyMemberDef BaseException_members[] = {
377 {"__suppress_context__", T_BOOL,
Antoine Pitrou32bc80c2012-05-16 12:51:55 +0200378 offsetof(PyBaseExceptionObject, suppress_context)},
379 {NULL}
Benjamin Petersond5a1c442012-05-14 22:09:31 -0700380};
381
382
Thomas Wouters477c8d52006-05-27 19:21:47 +0000383static PyTypeObject _PyExc_BaseException = {
Martin v. Löwis9f2e3462007-07-21 17:22:18 +0000384 PyVarObject_HEAD_INIT(NULL, 0)
Neal Norwitz2633c692007-02-26 22:22:47 +0000385 "BaseException", /*tp_name*/
Thomas Wouters477c8d52006-05-27 19:21:47 +0000386 sizeof(PyBaseExceptionObject), /*tp_basicsize*/
387 0, /*tp_itemsize*/
388 (destructor)BaseException_dealloc, /*tp_dealloc*/
Jeroen Demeyer530f5062019-05-31 04:13:39 +0200389 0, /*tp_vectorcall_offset*/
Thomas Wouters477c8d52006-05-27 19:21:47 +0000390 0, /*tp_getattr*/
391 0, /*tp_setattr*/
Jeroen Demeyer530f5062019-05-31 04:13:39 +0200392 0, /*tp_as_async*/
Thomas Wouters477c8d52006-05-27 19:21:47 +0000393 (reprfunc)BaseException_repr, /*tp_repr*/
394 0, /*tp_as_number*/
Brett Cannonba7bf492007-02-27 00:15:55 +0000395 0, /*tp_as_sequence*/
Thomas Wouters477c8d52006-05-27 19:21:47 +0000396 0, /*tp_as_mapping*/
397 0, /*tp_hash */
398 0, /*tp_call*/
399 (reprfunc)BaseException_str, /*tp_str*/
400 PyObject_GenericGetAttr, /*tp_getattro*/
401 PyObject_GenericSetAttr, /*tp_setattro*/
402 0, /*tp_as_buffer*/
Thomas Wouters27d517b2007-02-25 20:39:11 +0000403 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC |
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000404 Py_TPFLAGS_BASE_EXC_SUBCLASS, /*tp_flags*/
Thomas Wouters477c8d52006-05-27 19:21:47 +0000405 PyDoc_STR("Common base class for all exceptions"), /* tp_doc */
406 (traverseproc)BaseException_traverse, /* tp_traverse */
407 (inquiry)BaseException_clear, /* tp_clear */
408 0, /* tp_richcompare */
409 0, /* tp_weaklistoffset */
410 0, /* tp_iter */
411 0, /* tp_iternext */
412 BaseException_methods, /* tp_methods */
Benjamin Petersond5a1c442012-05-14 22:09:31 -0700413 BaseException_members, /* tp_members */
Thomas Wouters477c8d52006-05-27 19:21:47 +0000414 BaseException_getset, /* tp_getset */
415 0, /* tp_base */
416 0, /* tp_dict */
417 0, /* tp_descr_get */
418 0, /* tp_descr_set */
419 offsetof(PyBaseExceptionObject, dict), /* tp_dictoffset */
420 (initproc)BaseException_init, /* tp_init */
421 0, /* tp_alloc */
422 BaseException_new, /* tp_new */
423};
424/* the CPython API expects exceptions to be (PyObject *) - both a hold-over
Min ho Kimc4cacc82019-07-31 08:16:13 +1000425from the previous implementation and also allowing Python objects to be used
Thomas Wouters477c8d52006-05-27 19:21:47 +0000426in the API */
427PyObject *PyExc_BaseException = (PyObject *)&_PyExc_BaseException;
428
429/* note these macros omit the last semicolon so the macro invocation may
430 * include it and not look strange.
431 */
432#define SimpleExtendsException(EXCBASE, EXCNAME, EXCDOC) \
433static PyTypeObject _PyExc_ ## EXCNAME = { \
Martin v. Löwis9f2e3462007-07-21 17:22:18 +0000434 PyVarObject_HEAD_INIT(NULL, 0) \
Neal Norwitz2633c692007-02-26 22:22:47 +0000435 # EXCNAME, \
Thomas Wouters477c8d52006-05-27 19:21:47 +0000436 sizeof(PyBaseExceptionObject), \
437 0, (destructor)BaseException_dealloc, 0, 0, 0, 0, 0, 0, 0, \
438 0, 0, 0, 0, 0, 0, 0, \
439 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC, \
440 PyDoc_STR(EXCDOC), (traverseproc)BaseException_traverse, \
441 (inquiry)BaseException_clear, 0, 0, 0, 0, 0, 0, 0, &_ ## EXCBASE, \
442 0, 0, 0, offsetof(PyBaseExceptionObject, dict), \
443 (initproc)BaseException_init, 0, BaseException_new,\
444}; \
445PyObject *PyExc_ ## EXCNAME = (PyObject *)&_PyExc_ ## EXCNAME
446
447#define MiddlingExtendsException(EXCBASE, EXCNAME, EXCSTORE, EXCDOC) \
448static PyTypeObject _PyExc_ ## EXCNAME = { \
Martin v. Löwis9f2e3462007-07-21 17:22:18 +0000449 PyVarObject_HEAD_INIT(NULL, 0) \
Neal Norwitz2633c692007-02-26 22:22:47 +0000450 # EXCNAME, \
Thomas Wouters477c8d52006-05-27 19:21:47 +0000451 sizeof(Py ## EXCSTORE ## Object), \
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000452 0, (destructor)EXCSTORE ## _dealloc, 0, 0, 0, 0, 0, 0, 0, 0, 0, \
Thomas Wouters477c8d52006-05-27 19:21:47 +0000453 0, 0, 0, 0, 0, \
454 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC, \
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000455 PyDoc_STR(EXCDOC), (traverseproc)EXCSTORE ## _traverse, \
456 (inquiry)EXCSTORE ## _clear, 0, 0, 0, 0, 0, 0, 0, &_ ## EXCBASE, \
Thomas Wouters477c8d52006-05-27 19:21:47 +0000457 0, 0, 0, offsetof(Py ## EXCSTORE ## Object, dict), \
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200458 (initproc)EXCSTORE ## _init, 0, 0, \
Thomas Wouters477c8d52006-05-27 19:21:47 +0000459}; \
460PyObject *PyExc_ ## EXCNAME = (PyObject *)&_PyExc_ ## EXCNAME
461
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200462#define ComplexExtendsException(EXCBASE, EXCNAME, EXCSTORE, EXCNEW, \
463 EXCMETHODS, EXCMEMBERS, EXCGETSET, \
464 EXCSTR, EXCDOC) \
Thomas Wouters477c8d52006-05-27 19:21:47 +0000465static PyTypeObject _PyExc_ ## EXCNAME = { \
Martin v. Löwis9f2e3462007-07-21 17:22:18 +0000466 PyVarObject_HEAD_INIT(NULL, 0) \
Neal Norwitz2633c692007-02-26 22:22:47 +0000467 # EXCNAME, \
Thomas Wouters477c8d52006-05-27 19:21:47 +0000468 sizeof(Py ## EXCSTORE ## Object), 0, \
469 (destructor)EXCSTORE ## _dealloc, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, \
470 (reprfunc)EXCSTR, 0, 0, 0, \
471 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC, \
472 PyDoc_STR(EXCDOC), (traverseproc)EXCSTORE ## _traverse, \
473 (inquiry)EXCSTORE ## _clear, 0, 0, 0, 0, EXCMETHODS, \
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200474 EXCMEMBERS, EXCGETSET, &_ ## EXCBASE, \
Thomas Wouters477c8d52006-05-27 19:21:47 +0000475 0, 0, 0, offsetof(Py ## EXCSTORE ## Object, dict), \
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200476 (initproc)EXCSTORE ## _init, 0, EXCNEW,\
Thomas Wouters477c8d52006-05-27 19:21:47 +0000477}; \
478PyObject *PyExc_ ## EXCNAME = (PyObject *)&_PyExc_ ## EXCNAME
479
480
481/*
482 * Exception extends BaseException
483 */
484SimpleExtendsException(PyExc_BaseException, Exception,
485 "Common base class for all non-exit exceptions.");
486
487
488/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000489 * TypeError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +0000490 */
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000491SimpleExtendsException(PyExc_Exception, TypeError,
Thomas Wouters477c8d52006-05-27 19:21:47 +0000492 "Inappropriate argument type.");
493
494
495/*
Yury Selivanov75445082015-05-11 22:57:16 -0400496 * StopAsyncIteration extends Exception
497 */
498SimpleExtendsException(PyExc_Exception, StopAsyncIteration,
499 "Signal the end from iterator.__anext__().");
500
501
502/*
Thomas Wouters477c8d52006-05-27 19:21:47 +0000503 * StopIteration extends Exception
504 */
Nick Coghlan1f7ce622012-01-13 21:43:40 +1000505
506static PyMemberDef StopIteration_members[] = {
507 {"value", T_OBJECT, offsetof(PyStopIterationObject, value), 0,
508 PyDoc_STR("generator return value")},
509 {NULL} /* Sentinel */
510};
511
512static int
513StopIteration_init(PyStopIterationObject *self, PyObject *args, PyObject *kwds)
514{
515 Py_ssize_t size = PyTuple_GET_SIZE(args);
516 PyObject *value;
517
518 if (BaseException_init((PyBaseExceptionObject *)self, args, kwds) == -1)
519 return -1;
520 Py_CLEAR(self->value);
521 if (size > 0)
522 value = PyTuple_GET_ITEM(args, 0);
523 else
524 value = Py_None;
525 Py_INCREF(value);
526 self->value = value;
527 return 0;
528}
529
530static int
531StopIteration_clear(PyStopIterationObject *self)
532{
533 Py_CLEAR(self->value);
534 return BaseException_clear((PyBaseExceptionObject *)self);
535}
536
537static void
538StopIteration_dealloc(PyStopIterationObject *self)
539{
540 _PyObject_GC_UNTRACK(self);
541 StopIteration_clear(self);
542 Py_TYPE(self)->tp_free((PyObject *)self);
543}
544
545static int
546StopIteration_traverse(PyStopIterationObject *self, visitproc visit, void *arg)
547{
548 Py_VISIT(self->value);
549 return BaseException_traverse((PyBaseExceptionObject *)self, visit, arg);
550}
551
Nick Coghlan1f7ce622012-01-13 21:43:40 +1000552ComplexExtendsException(
553 PyExc_Exception, /* base */
554 StopIteration, /* name */
555 StopIteration, /* prefix for *_init, etc */
556 0, /* new */
557 0, /* methods */
558 StopIteration_members, /* members */
559 0, /* getset */
560 0, /* str */
561 "Signal the end from iterator.__next__()."
562);
Thomas Wouters477c8d52006-05-27 19:21:47 +0000563
564
565/*
Christian Heimescbf3b5c2007-12-03 21:02:03 +0000566 * GeneratorExit extends BaseException
Thomas Wouters477c8d52006-05-27 19:21:47 +0000567 */
Christian Heimescbf3b5c2007-12-03 21:02:03 +0000568SimpleExtendsException(PyExc_BaseException, GeneratorExit,
Thomas Wouters477c8d52006-05-27 19:21:47 +0000569 "Request that a generator exit.");
570
571
572/*
573 * SystemExit extends BaseException
574 */
Thomas Wouters477c8d52006-05-27 19:21:47 +0000575
576static int
577SystemExit_init(PySystemExitObject *self, PyObject *args, PyObject *kwds)
578{
579 Py_ssize_t size = PyTuple_GET_SIZE(args);
580
581 if (BaseException_init((PyBaseExceptionObject *)self, args, kwds) == -1)
582 return -1;
583
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000584 if (size == 0)
585 return 0;
Serhiy Storchaka191321d2015-12-27 15:41:34 +0200586 if (size == 1) {
587 Py_INCREF(PyTuple_GET_ITEM(args, 0));
Serhiy Storchaka48842712016-04-06 09:45:48 +0300588 Py_XSETREF(self->code, PyTuple_GET_ITEM(args, 0));
Serhiy Storchaka191321d2015-12-27 15:41:34 +0200589 }
590 else { /* size > 1 */
591 Py_INCREF(args);
Serhiy Storchaka48842712016-04-06 09:45:48 +0300592 Py_XSETREF(self->code, args);
Serhiy Storchaka191321d2015-12-27 15:41:34 +0200593 }
Thomas Wouters477c8d52006-05-27 19:21:47 +0000594 return 0;
595}
596
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000597static int
Thomas Wouters477c8d52006-05-27 19:21:47 +0000598SystemExit_clear(PySystemExitObject *self)
599{
600 Py_CLEAR(self->code);
601 return BaseException_clear((PyBaseExceptionObject *)self);
602}
603
604static void
605SystemExit_dealloc(PySystemExitObject *self)
606{
Thomas Wouters89f507f2006-12-13 04:49:30 +0000607 _PyObject_GC_UNTRACK(self);
Thomas Wouters477c8d52006-05-27 19:21:47 +0000608 SystemExit_clear(self);
Christian Heimes90aa7642007-12-19 02:45:37 +0000609 Py_TYPE(self)->tp_free((PyObject *)self);
Thomas Wouters477c8d52006-05-27 19:21:47 +0000610}
611
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000612static int
Thomas Wouters477c8d52006-05-27 19:21:47 +0000613SystemExit_traverse(PySystemExitObject *self, visitproc visit, void *arg)
614{
615 Py_VISIT(self->code);
616 return BaseException_traverse((PyBaseExceptionObject *)self, visit, arg);
617}
618
619static PyMemberDef SystemExit_members[] = {
Thomas Wouters477c8d52006-05-27 19:21:47 +0000620 {"code", T_OBJECT, offsetof(PySystemExitObject, code), 0,
621 PyDoc_STR("exception code")},
622 {NULL} /* Sentinel */
623};
624
625ComplexExtendsException(PyExc_BaseException, SystemExit, SystemExit,
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200626 0, 0, SystemExit_members, 0, 0,
Thomas Wouters477c8d52006-05-27 19:21:47 +0000627 "Request to exit from the interpreter.");
628
629/*
630 * KeyboardInterrupt extends BaseException
631 */
632SimpleExtendsException(PyExc_BaseException, KeyboardInterrupt,
633 "Program interrupted by user.");
634
635
636/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000637 * ImportError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +0000638 */
Thomas Wouters477c8d52006-05-27 19:21:47 +0000639
Brett Cannon79ec55e2012-04-12 20:24:54 -0400640static int
641ImportError_init(PyImportErrorObject *self, PyObject *args, PyObject *kwds)
642{
Serhiy Storchaka47dee112016-09-27 20:45:35 +0300643 static char *kwlist[] = {"name", "path", 0};
644 PyObject *empty_tuple;
Brett Cannon79ec55e2012-04-12 20:24:54 -0400645 PyObject *msg = NULL;
646 PyObject *name = NULL;
647 PyObject *path = NULL;
648
Serhiy Storchaka47dee112016-09-27 20:45:35 +0300649 if (BaseException_init((PyBaseExceptionObject *)self, args, NULL) == -1)
Brett Cannon79ec55e2012-04-12 20:24:54 -0400650 return -1;
651
Serhiy Storchaka47dee112016-09-27 20:45:35 +0300652 empty_tuple = PyTuple_New(0);
653 if (!empty_tuple)
654 return -1;
655 if (!PyArg_ParseTupleAndKeywords(empty_tuple, kwds, "|$OO:ImportError", kwlist,
656 &name, &path)) {
657 Py_DECREF(empty_tuple);
658 return -1;
659 }
660 Py_DECREF(empty_tuple);
661
Serhiy Storchakae9e44482016-09-28 07:53:32 +0300662 Py_XINCREF(name);
663 Py_XSETREF(self->name, name);
664
665 Py_XINCREF(path);
666 Py_XSETREF(self->path, path);
667
Serhiy Storchaka47dee112016-09-27 20:45:35 +0300668 if (PyTuple_GET_SIZE(args) == 1) {
669 msg = PyTuple_GET_ITEM(args, 0);
670 Py_INCREF(msg);
Serhiy Storchaka47dee112016-09-27 20:45:35 +0300671 }
Serhiy Storchakae9e44482016-09-28 07:53:32 +0300672 Py_XSETREF(self->msg, msg);
Brett Cannon79ec55e2012-04-12 20:24:54 -0400673
674 return 0;
675}
676
677static int
678ImportError_clear(PyImportErrorObject *self)
679{
680 Py_CLEAR(self->msg);
681 Py_CLEAR(self->name);
682 Py_CLEAR(self->path);
683 return BaseException_clear((PyBaseExceptionObject *)self);
684}
685
686static void
687ImportError_dealloc(PyImportErrorObject *self)
688{
689 _PyObject_GC_UNTRACK(self);
690 ImportError_clear(self);
691 Py_TYPE(self)->tp_free((PyObject *)self);
692}
693
694static int
695ImportError_traverse(PyImportErrorObject *self, visitproc visit, void *arg)
696{
697 Py_VISIT(self->msg);
698 Py_VISIT(self->name);
699 Py_VISIT(self->path);
700 return BaseException_traverse((PyBaseExceptionObject *)self, visit, arg);
701}
702
703static PyObject *
704ImportError_str(PyImportErrorObject *self)
705{
Brett Cannon07c6e712012-08-24 13:05:09 -0400706 if (self->msg && PyUnicode_CheckExact(self->msg)) {
Brett Cannon79ec55e2012-04-12 20:24:54 -0400707 Py_INCREF(self->msg);
708 return self->msg;
709 }
710 else {
711 return BaseException_str((PyBaseExceptionObject *)self);
712 }
713}
714
Serhiy Storchakab7853962017-04-08 09:55:07 +0300715static PyObject *
716ImportError_getstate(PyImportErrorObject *self)
717{
718 PyObject *dict = ((PyBaseExceptionObject *)self)->dict;
719 if (self->name || self->path) {
720 _Py_IDENTIFIER(name);
721 _Py_IDENTIFIER(path);
722 dict = dict ? PyDict_Copy(dict) : PyDict_New();
723 if (dict == NULL)
724 return NULL;
725 if (self->name && _PyDict_SetItemId(dict, &PyId_name, self->name) < 0) {
726 Py_DECREF(dict);
727 return NULL;
728 }
729 if (self->path && _PyDict_SetItemId(dict, &PyId_path, self->path) < 0) {
730 Py_DECREF(dict);
731 return NULL;
732 }
733 return dict;
734 }
735 else if (dict) {
736 Py_INCREF(dict);
737 return dict;
738 }
739 else {
740 Py_RETURN_NONE;
741 }
742}
743
744/* Pickling support */
745static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +0530746ImportError_reduce(PyImportErrorObject *self, PyObject *Py_UNUSED(ignored))
Serhiy Storchakab7853962017-04-08 09:55:07 +0300747{
748 PyObject *res;
749 PyObject *args;
750 PyObject *state = ImportError_getstate(self);
751 if (state == NULL)
752 return NULL;
753 args = ((PyBaseExceptionObject *)self)->args;
754 if (state == Py_None)
755 res = PyTuple_Pack(2, Py_TYPE(self), args);
756 else
757 res = PyTuple_Pack(3, Py_TYPE(self), args, state);
758 Py_DECREF(state);
759 return res;
760}
761
Brett Cannon79ec55e2012-04-12 20:24:54 -0400762static PyMemberDef ImportError_members[] = {
763 {"msg", T_OBJECT, offsetof(PyImportErrorObject, msg), 0,
764 PyDoc_STR("exception message")},
765 {"name", T_OBJECT, offsetof(PyImportErrorObject, name), 0,
766 PyDoc_STR("module name")},
767 {"path", T_OBJECT, offsetof(PyImportErrorObject, path), 0,
768 PyDoc_STR("module path")},
769 {NULL} /* Sentinel */
770};
771
772static PyMethodDef ImportError_methods[] = {
Serhiy Storchakab7853962017-04-08 09:55:07 +0300773 {"__reduce__", (PyCFunction)ImportError_reduce, METH_NOARGS},
Brett Cannon79ec55e2012-04-12 20:24:54 -0400774 {NULL}
775};
776
777ComplexExtendsException(PyExc_Exception, ImportError,
778 ImportError, 0 /* new */,
779 ImportError_methods, ImportError_members,
780 0 /* getset */, ImportError_str,
781 "Import can't find module, or can't find name in "
782 "module.");
Thomas Wouters477c8d52006-05-27 19:21:47 +0000783
784/*
Eric Snowc9432652016-09-07 15:42:32 -0700785 * ModuleNotFoundError extends ImportError
786 */
787
788MiddlingExtendsException(PyExc_ImportError, ModuleNotFoundError, ImportError,
789 "Module not found.");
790
791/*
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200792 * OSError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +0000793 */
794
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200795#ifdef MS_WINDOWS
796#include "errmap.h"
797#endif
798
Thomas Wouters477c8d52006-05-27 19:21:47 +0000799/* Where a function has a single filename, such as open() or some
800 * of the os module functions, PyErr_SetFromErrnoWithFilename() is
801 * called, giving a third argument which is the filename. But, so
802 * that old code using in-place unpacking doesn't break, e.g.:
803 *
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200804 * except OSError, (errno, strerror):
Thomas Wouters477c8d52006-05-27 19:21:47 +0000805 *
806 * we hack args so that it only contains two items. This also
807 * means we need our own __str__() which prints out the filename
808 * when it was supplied.
Larry Hastingsb0827312014-02-09 22:05:19 -0800809 *
810 * (If a function has two filenames, such as rename(), symlink(),
Larry Hastings8f9f0f12014-02-10 03:43:57 -0800811 * or copy(), PyErr_SetFromErrnoWithFilenameObjects() is called,
812 * which allows passing in a second filename.)
Thomas Wouters477c8d52006-05-27 19:21:47 +0000813 */
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200814
Antoine Pitroue0e27352011-12-15 14:31:28 +0100815/* This function doesn't cleanup on error, the caller should */
816static int
817oserror_parse_args(PyObject **p_args,
818 PyObject **myerrno, PyObject **strerror,
Larry Hastingsb0827312014-02-09 22:05:19 -0800819 PyObject **filename, PyObject **filename2
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200820#ifdef MS_WINDOWS
Antoine Pitroue0e27352011-12-15 14:31:28 +0100821 , PyObject **winerror
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200822#endif
Antoine Pitroue0e27352011-12-15 14:31:28 +0100823 )
824{
825 Py_ssize_t nargs;
826 PyObject *args = *p_args;
Larry Hastingsb0827312014-02-09 22:05:19 -0800827#ifndef MS_WINDOWS
828 /*
829 * ignored on non-Windows platforms,
830 * but parsed so OSError has a consistent signature
831 */
832 PyObject *_winerror = NULL;
833 PyObject **winerror = &_winerror;
834#endif /* MS_WINDOWS */
Thomas Wouters477c8d52006-05-27 19:21:47 +0000835
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200836 nargs = PyTuple_GET_SIZE(args);
Thomas Wouters477c8d52006-05-27 19:21:47 +0000837
Larry Hastingsb0827312014-02-09 22:05:19 -0800838 if (nargs >= 2 && nargs <= 5) {
839 if (!PyArg_UnpackTuple(args, "OSError", 2, 5,
840 myerrno, strerror,
841 filename, winerror, filename2))
Antoine Pitroue0e27352011-12-15 14:31:28 +0100842 return -1;
Larry Hastingsb0827312014-02-09 22:05:19 -0800843#ifdef MS_WINDOWS
Antoine Pitroue0e27352011-12-15 14:31:28 +0100844 if (*winerror && PyLong_Check(*winerror)) {
845 long errcode, winerrcode;
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200846 PyObject *newargs;
847 Py_ssize_t i;
848
Antoine Pitroue0e27352011-12-15 14:31:28 +0100849 winerrcode = PyLong_AsLong(*winerror);
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200850 if (winerrcode == -1 && PyErr_Occurred())
Antoine Pitroue0e27352011-12-15 14:31:28 +0100851 return -1;
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200852 /* Set errno to the corresponding POSIX errno (overriding
853 first argument). Windows Socket error codes (>= 10000)
854 have the same value as their POSIX counterparts.
855 */
856 if (winerrcode < 10000)
857 errcode = winerror_to_errno(winerrcode);
858 else
859 errcode = winerrcode;
Antoine Pitroue0e27352011-12-15 14:31:28 +0100860 *myerrno = PyLong_FromLong(errcode);
861 if (!*myerrno)
862 return -1;
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200863 newargs = PyTuple_New(nargs);
864 if (!newargs)
Antoine Pitroue0e27352011-12-15 14:31:28 +0100865 return -1;
866 PyTuple_SET_ITEM(newargs, 0, *myerrno);
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200867 for (i = 1; i < nargs; i++) {
868 PyObject *val = PyTuple_GET_ITEM(args, i);
869 Py_INCREF(val);
870 PyTuple_SET_ITEM(newargs, i, val);
871 }
872 Py_DECREF(args);
Antoine Pitroue0e27352011-12-15 14:31:28 +0100873 args = *p_args = newargs;
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200874 }
Larry Hastingsb0827312014-02-09 22:05:19 -0800875#endif /* MS_WINDOWS */
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200876 }
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000877
Antoine Pitroue0e27352011-12-15 14:31:28 +0100878 return 0;
879}
Thomas Wouters477c8d52006-05-27 19:21:47 +0000880
Antoine Pitroue0e27352011-12-15 14:31:28 +0100881static int
882oserror_init(PyOSErrorObject *self, PyObject **p_args,
883 PyObject *myerrno, PyObject *strerror,
Larry Hastingsb0827312014-02-09 22:05:19 -0800884 PyObject *filename, PyObject *filename2
Antoine Pitroue0e27352011-12-15 14:31:28 +0100885#ifdef MS_WINDOWS
886 , PyObject *winerror
887#endif
888 )
889{
890 PyObject *args = *p_args;
891 Py_ssize_t nargs = PyTuple_GET_SIZE(args);
Thomas Wouters477c8d52006-05-27 19:21:47 +0000892
893 /* self->filename will remain Py_None otherwise */
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200894 if (filename && filename != Py_None) {
Andy Lesterdffe4c02020-03-04 07:15:20 -0600895 if (Py_IS_TYPE(self, (PyTypeObject *) PyExc_BlockingIOError) &&
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200896 PyNumber_Check(filename)) {
897 /* BlockingIOError's 3rd argument can be the number of
898 * characters written.
899 */
900 self->written = PyNumber_AsSsize_t(filename, PyExc_ValueError);
901 if (self->written == -1 && PyErr_Occurred())
Antoine Pitroue0e27352011-12-15 14:31:28 +0100902 return -1;
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200903 }
904 else {
905 Py_INCREF(filename);
906 self->filename = filename;
Thomas Wouters477c8d52006-05-27 19:21:47 +0000907
Larry Hastingsb0827312014-02-09 22:05:19 -0800908 if (filename2 && filename2 != Py_None) {
909 Py_INCREF(filename2);
910 self->filename2 = filename2;
911 }
912
913 if (nargs >= 2 && nargs <= 5) {
914 /* filename, filename2, and winerror are removed from the args tuple
915 (for compatibility purposes, see test_exceptions.py) */
Antoine Pitroue0e27352011-12-15 14:31:28 +0100916 PyObject *subslice = PyTuple_GetSlice(args, 0, 2);
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200917 if (!subslice)
Antoine Pitroue0e27352011-12-15 14:31:28 +0100918 return -1;
Thomas Wouters477c8d52006-05-27 19:21:47 +0000919
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200920 Py_DECREF(args); /* replacing args */
Antoine Pitroue0e27352011-12-15 14:31:28 +0100921 *p_args = args = subslice;
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200922 }
923 }
Thomas Wouters477c8d52006-05-27 19:21:47 +0000924 }
Antoine Pitrou6b4883d2011-10-12 02:54:14 +0200925 Py_XINCREF(myerrno);
926 self->myerrno = myerrno;
927
928 Py_XINCREF(strerror);
929 self->strerror = strerror;
930
931#ifdef MS_WINDOWS
932 Py_XINCREF(winerror);
933 self->winerror = winerror;
934#endif
935
Antoine Pitroue0e27352011-12-15 14:31:28 +0100936 /* Steals the reference to args */
Serhiy Storchaka48842712016-04-06 09:45:48 +0300937 Py_XSETREF(self->args, args);
Victor Stinner46ef3192013-11-14 22:31:41 +0100938 *p_args = args = NULL;
Antoine Pitroue0e27352011-12-15 14:31:28 +0100939
940 return 0;
941}
942
943static PyObject *
944OSError_new(PyTypeObject *type, PyObject *args, PyObject *kwds);
945static int
946OSError_init(PyOSErrorObject *self, PyObject *args, PyObject *kwds);
947
948static int
949oserror_use_init(PyTypeObject *type)
950{
Martin Panter7462b6492015-11-02 03:37:02 +0000951 /* When __init__ is defined in an OSError subclass, we want any
Antoine Pitroue0e27352011-12-15 14:31:28 +0100952 extraneous argument to __new__ to be ignored. The only reasonable
953 solution, given __new__ takes a variable number of arguments,
954 is to defer arg parsing and initialization to __init__.
955
Martin Pantere26da7c2016-06-02 10:07:09 +0000956 But when __new__ is overridden as well, it should call our __new__
Antoine Pitroue0e27352011-12-15 14:31:28 +0100957 with the right arguments.
958
959 (see http://bugs.python.org/issue12555#msg148829 )
960 */
961 if (type->tp_init != (initproc) OSError_init &&
962 type->tp_new == (newfunc) OSError_new) {
963 assert((PyObject *) type != PyExc_OSError);
964 return 1;
965 }
966 return 0;
967}
968
969static PyObject *
970OSError_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
971{
972 PyOSErrorObject *self = NULL;
Larry Hastingsb0827312014-02-09 22:05:19 -0800973 PyObject *myerrno = NULL, *strerror = NULL;
974 PyObject *filename = NULL, *filename2 = NULL;
Antoine Pitroue0e27352011-12-15 14:31:28 +0100975#ifdef MS_WINDOWS
976 PyObject *winerror = NULL;
977#endif
978
Victor Stinner46ef3192013-11-14 22:31:41 +0100979 Py_INCREF(args);
980
Antoine Pitroue0e27352011-12-15 14:31:28 +0100981 if (!oserror_use_init(type)) {
982 if (!_PyArg_NoKeywords(type->tp_name, kwds))
Victor Stinner46ef3192013-11-14 22:31:41 +0100983 goto error;
Antoine Pitroue0e27352011-12-15 14:31:28 +0100984
Larry Hastingsb0827312014-02-09 22:05:19 -0800985 if (oserror_parse_args(&args, &myerrno, &strerror,
986 &filename, &filename2
Antoine Pitroue0e27352011-12-15 14:31:28 +0100987#ifdef MS_WINDOWS
988 , &winerror
989#endif
990 ))
991 goto error;
992
Victor Stinner281cce12020-06-23 22:55:46 +0200993 struct _Py_exc_state *state = get_exc_state();
Antoine Pitroue0e27352011-12-15 14:31:28 +0100994 if (myerrno && PyLong_Check(myerrno) &&
Victor Stinner281cce12020-06-23 22:55:46 +0200995 state->errnomap && (PyObject *) type == PyExc_OSError) {
Antoine Pitroue0e27352011-12-15 14:31:28 +0100996 PyObject *newtype;
Victor Stinner281cce12020-06-23 22:55:46 +0200997 newtype = PyDict_GetItemWithError(state->errnomap, myerrno);
Antoine Pitroue0e27352011-12-15 14:31:28 +0100998 if (newtype) {
999 assert(PyType_Check(newtype));
1000 type = (PyTypeObject *) newtype;
1001 }
1002 else if (PyErr_Occurred())
1003 goto error;
1004 }
1005 }
1006
1007 self = (PyOSErrorObject *) type->tp_alloc(type, 0);
1008 if (!self)
1009 goto error;
1010
1011 self->dict = NULL;
1012 self->traceback = self->cause = self->context = NULL;
1013 self->written = -1;
1014
1015 if (!oserror_use_init(type)) {
Larry Hastingsb0827312014-02-09 22:05:19 -08001016 if (oserror_init(self, &args, myerrno, strerror, filename, filename2
Antoine Pitroue0e27352011-12-15 14:31:28 +01001017#ifdef MS_WINDOWS
1018 , winerror
1019#endif
1020 ))
1021 goto error;
1022 }
Antoine Pitrouf87289b2012-06-30 23:37:47 +02001023 else {
1024 self->args = PyTuple_New(0);
1025 if (self->args == NULL)
1026 goto error;
1027 }
Antoine Pitroue0e27352011-12-15 14:31:28 +01001028
Victor Stinner46ef3192013-11-14 22:31:41 +01001029 Py_XDECREF(args);
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001030 return (PyObject *) self;
1031
1032error:
1033 Py_XDECREF(args);
1034 Py_XDECREF(self);
1035 return NULL;
1036}
1037
1038static int
Antoine Pitroue0e27352011-12-15 14:31:28 +01001039OSError_init(PyOSErrorObject *self, PyObject *args, PyObject *kwds)
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001040{
Larry Hastingsb0827312014-02-09 22:05:19 -08001041 PyObject *myerrno = NULL, *strerror = NULL;
1042 PyObject *filename = NULL, *filename2 = NULL;
Antoine Pitroue0e27352011-12-15 14:31:28 +01001043#ifdef MS_WINDOWS
1044 PyObject *winerror = NULL;
1045#endif
1046
1047 if (!oserror_use_init(Py_TYPE(self)))
1048 /* Everything already done in OSError_new */
1049 return 0;
1050
1051 if (!_PyArg_NoKeywords(Py_TYPE(self)->tp_name, kwds))
1052 return -1;
1053
1054 Py_INCREF(args);
Larry Hastingsb0827312014-02-09 22:05:19 -08001055 if (oserror_parse_args(&args, &myerrno, &strerror, &filename, &filename2
Antoine Pitroue0e27352011-12-15 14:31:28 +01001056#ifdef MS_WINDOWS
1057 , &winerror
1058#endif
1059 ))
1060 goto error;
1061
Larry Hastingsb0827312014-02-09 22:05:19 -08001062 if (oserror_init(self, &args, myerrno, strerror, filename, filename2
Antoine Pitroue0e27352011-12-15 14:31:28 +01001063#ifdef MS_WINDOWS
1064 , winerror
1065#endif
1066 ))
1067 goto error;
1068
Thomas Wouters477c8d52006-05-27 19:21:47 +00001069 return 0;
Antoine Pitroue0e27352011-12-15 14:31:28 +01001070
1071error:
Serhiy Storchaka37665722016-08-20 21:22:03 +03001072 Py_DECREF(args);
Antoine Pitroue0e27352011-12-15 14:31:28 +01001073 return -1;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001074}
1075
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001076static int
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001077OSError_clear(PyOSErrorObject *self)
Thomas Wouters477c8d52006-05-27 19:21:47 +00001078{
1079 Py_CLEAR(self->myerrno);
1080 Py_CLEAR(self->strerror);
1081 Py_CLEAR(self->filename);
Larry Hastingsb0827312014-02-09 22:05:19 -08001082 Py_CLEAR(self->filename2);
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001083#ifdef MS_WINDOWS
1084 Py_CLEAR(self->winerror);
1085#endif
Thomas Wouters477c8d52006-05-27 19:21:47 +00001086 return BaseException_clear((PyBaseExceptionObject *)self);
1087}
1088
1089static void
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001090OSError_dealloc(PyOSErrorObject *self)
Thomas Wouters477c8d52006-05-27 19:21:47 +00001091{
Thomas Wouters89f507f2006-12-13 04:49:30 +00001092 _PyObject_GC_UNTRACK(self);
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001093 OSError_clear(self);
Christian Heimes90aa7642007-12-19 02:45:37 +00001094 Py_TYPE(self)->tp_free((PyObject *)self);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001095}
1096
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001097static int
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001098OSError_traverse(PyOSErrorObject *self, visitproc visit,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001099 void *arg)
1100{
1101 Py_VISIT(self->myerrno);
1102 Py_VISIT(self->strerror);
1103 Py_VISIT(self->filename);
Larry Hastingsb0827312014-02-09 22:05:19 -08001104 Py_VISIT(self->filename2);
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001105#ifdef MS_WINDOWS
1106 Py_VISIT(self->winerror);
1107#endif
Thomas Wouters477c8d52006-05-27 19:21:47 +00001108 return BaseException_traverse((PyBaseExceptionObject *)self, visit, arg);
1109}
1110
1111static PyObject *
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001112OSError_str(PyOSErrorObject *self)
Thomas Wouters477c8d52006-05-27 19:21:47 +00001113{
Larry Hastingsb0827312014-02-09 22:05:19 -08001114#define OR_NONE(x) ((x)?(x):Py_None)
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001115#ifdef MS_WINDOWS
1116 /* If available, winerror has the priority over myerrno */
Larry Hastingsb0827312014-02-09 22:05:19 -08001117 if (self->winerror && self->filename) {
1118 if (self->filename2) {
1119 return PyUnicode_FromFormat("[WinError %S] %S: %R -> %R",
1120 OR_NONE(self->winerror),
1121 OR_NONE(self->strerror),
1122 self->filename,
1123 self->filename2);
1124 } else {
1125 return PyUnicode_FromFormat("[WinError %S] %S: %R",
1126 OR_NONE(self->winerror),
1127 OR_NONE(self->strerror),
1128 self->filename);
1129 }
1130 }
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001131 if (self->winerror && self->strerror)
Richard Oudkerk30147712012-08-28 19:33:26 +01001132 return PyUnicode_FromFormat("[WinError %S] %S",
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001133 self->winerror ? self->winerror: Py_None,
1134 self->strerror ? self->strerror: Py_None);
1135#endif
Larry Hastingsb0827312014-02-09 22:05:19 -08001136 if (self->filename) {
1137 if (self->filename2) {
1138 return PyUnicode_FromFormat("[Errno %S] %S: %R -> %R",
1139 OR_NONE(self->myerrno),
1140 OR_NONE(self->strerror),
1141 self->filename,
1142 self->filename2);
1143 } else {
1144 return PyUnicode_FromFormat("[Errno %S] %S: %R",
1145 OR_NONE(self->myerrno),
1146 OR_NONE(self->strerror),
1147 self->filename);
1148 }
1149 }
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001150 if (self->myerrno && self->strerror)
Walter Dörwaldf5bec7c2007-05-26 15:03:32 +00001151 return PyUnicode_FromFormat("[Errno %S] %S",
Serhiy Storchaka37665722016-08-20 21:22:03 +03001152 self->myerrno, self->strerror);
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001153 return BaseException_str((PyBaseExceptionObject *)self);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001154}
1155
Thomas Wouters477c8d52006-05-27 19:21:47 +00001156static PyObject *
Siddhesh Poyarekar55edd0c2018-04-30 00:29:33 +05301157OSError_reduce(PyOSErrorObject *self, PyObject *Py_UNUSED(ignored))
Thomas Wouters477c8d52006-05-27 19:21:47 +00001158{
1159 PyObject *args = self->args;
1160 PyObject *res = NULL, *tmp;
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001161
Thomas Wouters477c8d52006-05-27 19:21:47 +00001162 /* self->args is only the first two real arguments if there was a
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001163 * file name given to OSError. */
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001164 if (PyTuple_GET_SIZE(args) == 2 && self->filename) {
Larry Hastingsb0827312014-02-09 22:05:19 -08001165 Py_ssize_t size = self->filename2 ? 5 : 3;
1166 args = PyTuple_New(size);
Benjamin Peterson90b13582012-02-03 19:22:31 -05001167 if (!args)
1168 return NULL;
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001169
1170 tmp = PyTuple_GET_ITEM(self->args, 0);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001171 Py_INCREF(tmp);
1172 PyTuple_SET_ITEM(args, 0, tmp);
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001173
1174 tmp = PyTuple_GET_ITEM(self->args, 1);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001175 Py_INCREF(tmp);
1176 PyTuple_SET_ITEM(args, 1, tmp);
1177
1178 Py_INCREF(self->filename);
1179 PyTuple_SET_ITEM(args, 2, self->filename);
Larry Hastingsb0827312014-02-09 22:05:19 -08001180
1181 if (self->filename2) {
1182 /*
1183 * This tuple is essentially used as OSError(*args).
1184 * So, to recreate filename2, we need to pass in
1185 * winerror as well.
1186 */
1187 Py_INCREF(Py_None);
1188 PyTuple_SET_ITEM(args, 3, Py_None);
1189
1190 /* filename2 */
1191 Py_INCREF(self->filename2);
1192 PyTuple_SET_ITEM(args, 4, self->filename2);
1193 }
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001194 } else
Thomas Wouters477c8d52006-05-27 19:21:47 +00001195 Py_INCREF(args);
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001196
1197 if (self->dict)
Christian Heimes90aa7642007-12-19 02:45:37 +00001198 res = PyTuple_Pack(3, Py_TYPE(self), args, self->dict);
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001199 else
Christian Heimes90aa7642007-12-19 02:45:37 +00001200 res = PyTuple_Pack(2, Py_TYPE(self), args);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001201 Py_DECREF(args);
1202 return res;
1203}
1204
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001205static PyObject *
1206OSError_written_get(PyOSErrorObject *self, void *context)
1207{
1208 if (self->written == -1) {
1209 PyErr_SetString(PyExc_AttributeError, "characters_written");
1210 return NULL;
1211 }
1212 return PyLong_FromSsize_t(self->written);
1213}
Thomas Wouters477c8d52006-05-27 19:21:47 +00001214
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001215static int
1216OSError_written_set(PyOSErrorObject *self, PyObject *arg, void *context)
1217{
Serhiy Storchakae2af34f2018-12-17 16:43:14 +02001218 if (arg == NULL) {
1219 if (self->written == -1) {
1220 PyErr_SetString(PyExc_AttributeError, "characters_written");
1221 return -1;
1222 }
1223 self->written = -1;
1224 return 0;
1225 }
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001226 Py_ssize_t n;
1227 n = PyNumber_AsSsize_t(arg, PyExc_ValueError);
1228 if (n == -1 && PyErr_Occurred())
1229 return -1;
1230 self->written = n;
1231 return 0;
1232}
1233
1234static PyMemberDef OSError_members[] = {
1235 {"errno", T_OBJECT, offsetof(PyOSErrorObject, myerrno), 0,
1236 PyDoc_STR("POSIX exception code")},
1237 {"strerror", T_OBJECT, offsetof(PyOSErrorObject, strerror), 0,
1238 PyDoc_STR("exception strerror")},
1239 {"filename", T_OBJECT, offsetof(PyOSErrorObject, filename), 0,
1240 PyDoc_STR("exception filename")},
Larry Hastingsb0827312014-02-09 22:05:19 -08001241 {"filename2", T_OBJECT, offsetof(PyOSErrorObject, filename2), 0,
1242 PyDoc_STR("second exception filename")},
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001243#ifdef MS_WINDOWS
1244 {"winerror", T_OBJECT, offsetof(PyOSErrorObject, winerror), 0,
1245 PyDoc_STR("Win32 exception code")},
1246#endif
1247 {NULL} /* Sentinel */
1248};
1249
1250static PyMethodDef OSError_methods[] = {
1251 {"__reduce__", (PyCFunction)OSError_reduce, METH_NOARGS},
Thomas Wouters477c8d52006-05-27 19:21:47 +00001252 {NULL}
1253};
1254
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001255static PyGetSetDef OSError_getset[] = {
1256 {"characters_written", (getter) OSError_written_get,
1257 (setter) OSError_written_set, NULL},
1258 {NULL}
1259};
1260
1261
1262ComplexExtendsException(PyExc_Exception, OSError,
1263 OSError, OSError_new,
1264 OSError_methods, OSError_members, OSError_getset,
1265 OSError_str,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001266 "Base class for I/O related errors.");
1267
1268
1269/*
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001270 * Various OSError subclasses
Thomas Wouters477c8d52006-05-27 19:21:47 +00001271 */
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001272MiddlingExtendsException(PyExc_OSError, BlockingIOError, OSError,
1273 "I/O operation would block.");
1274MiddlingExtendsException(PyExc_OSError, ConnectionError, OSError,
1275 "Connection error.");
1276MiddlingExtendsException(PyExc_OSError, ChildProcessError, OSError,
1277 "Child process error.");
1278MiddlingExtendsException(PyExc_ConnectionError, BrokenPipeError, OSError,
1279 "Broken pipe.");
1280MiddlingExtendsException(PyExc_ConnectionError, ConnectionAbortedError, OSError,
1281 "Connection aborted.");
1282MiddlingExtendsException(PyExc_ConnectionError, ConnectionRefusedError, OSError,
1283 "Connection refused.");
1284MiddlingExtendsException(PyExc_ConnectionError, ConnectionResetError, OSError,
1285 "Connection reset.");
1286MiddlingExtendsException(PyExc_OSError, FileExistsError, OSError,
1287 "File already exists.");
1288MiddlingExtendsException(PyExc_OSError, FileNotFoundError, OSError,
1289 "File not found.");
1290MiddlingExtendsException(PyExc_OSError, IsADirectoryError, OSError,
1291 "Operation doesn't work on directories.");
1292MiddlingExtendsException(PyExc_OSError, NotADirectoryError, OSError,
1293 "Operation only works on directories.");
1294MiddlingExtendsException(PyExc_OSError, InterruptedError, OSError,
1295 "Interrupted by signal.");
1296MiddlingExtendsException(PyExc_OSError, PermissionError, OSError,
1297 "Not enough permissions.");
1298MiddlingExtendsException(PyExc_OSError, ProcessLookupError, OSError,
1299 "Process not found.");
1300MiddlingExtendsException(PyExc_OSError, TimeoutError, OSError,
1301 "Timeout expired.");
Thomas Wouters477c8d52006-05-27 19:21:47 +00001302
1303/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001304 * EOFError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +00001305 */
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001306SimpleExtendsException(PyExc_Exception, EOFError,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001307 "Read beyond end of file.");
1308
1309
1310/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001311 * RuntimeError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +00001312 */
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001313SimpleExtendsException(PyExc_Exception, RuntimeError,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001314 "Unspecified run-time error.");
1315
Yury Selivanovf488fb42015-07-03 01:04:23 -04001316/*
1317 * RecursionError extends RuntimeError
1318 */
1319SimpleExtendsException(PyExc_RuntimeError, RecursionError,
1320 "Recursion limit exceeded.");
Thomas Wouters477c8d52006-05-27 19:21:47 +00001321
1322/*
1323 * NotImplementedError extends RuntimeError
1324 */
1325SimpleExtendsException(PyExc_RuntimeError, NotImplementedError,
1326 "Method or function hasn't been implemented yet.");
1327
1328/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001329 * NameError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +00001330 */
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001331SimpleExtendsException(PyExc_Exception, NameError,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001332 "Name not found globally.");
1333
1334/*
1335 * UnboundLocalError extends NameError
1336 */
1337SimpleExtendsException(PyExc_NameError, UnboundLocalError,
1338 "Local name referenced but not bound to a value.");
1339
1340/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001341 * AttributeError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +00001342 */
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001343SimpleExtendsException(PyExc_Exception, AttributeError,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001344 "Attribute not found.");
1345
1346
1347/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001348 * SyntaxError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +00001349 */
Thomas Wouters477c8d52006-05-27 19:21:47 +00001350
Raymond Hettinger7ea386e2016-08-25 21:11:50 -07001351/* Helper function to customize error message for some syntax errors */
Nick Coghlan5b1fdc12014-06-16 19:48:02 +10001352static int _report_missing_parentheses(PySyntaxErrorObject *self);
1353
Thomas Wouters477c8d52006-05-27 19:21:47 +00001354static int
1355SyntaxError_init(PySyntaxErrorObject *self, PyObject *args, PyObject *kwds)
1356{
1357 PyObject *info = NULL;
1358 Py_ssize_t lenargs = PyTuple_GET_SIZE(args);
1359
1360 if (BaseException_init((PyBaseExceptionObject *)self, args, kwds) == -1)
1361 return -1;
1362
1363 if (lenargs >= 1) {
Serhiy Storchaka4a1e70f2015-12-27 12:36:18 +02001364 Py_INCREF(PyTuple_GET_ITEM(args, 0));
Serhiy Storchaka48842712016-04-06 09:45:48 +03001365 Py_XSETREF(self->msg, PyTuple_GET_ITEM(args, 0));
Thomas Wouters477c8d52006-05-27 19:21:47 +00001366 }
1367 if (lenargs == 2) {
1368 info = PyTuple_GET_ITEM(args, 1);
1369 info = PySequence_Tuple(info);
Benjamin Peterson90b13582012-02-03 19:22:31 -05001370 if (!info)
1371 return -1;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001372
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001373 if (PyTuple_GET_SIZE(info) != 4) {
1374 /* not a very good error message, but it's what Python 2.4 gives */
1375 PyErr_SetString(PyExc_IndexError, "tuple index out of range");
1376 Py_DECREF(info);
1377 return -1;
1378 }
1379
Serhiy Storchaka4a1e70f2015-12-27 12:36:18 +02001380 Py_INCREF(PyTuple_GET_ITEM(info, 0));
Serhiy Storchaka48842712016-04-06 09:45:48 +03001381 Py_XSETREF(self->filename, PyTuple_GET_ITEM(info, 0));
Thomas Wouters477c8d52006-05-27 19:21:47 +00001382
Serhiy Storchaka4a1e70f2015-12-27 12:36:18 +02001383 Py_INCREF(PyTuple_GET_ITEM(info, 1));
Serhiy Storchaka48842712016-04-06 09:45:48 +03001384 Py_XSETREF(self->lineno, PyTuple_GET_ITEM(info, 1));
Thomas Wouters477c8d52006-05-27 19:21:47 +00001385
Serhiy Storchaka4a1e70f2015-12-27 12:36:18 +02001386 Py_INCREF(PyTuple_GET_ITEM(info, 2));
Serhiy Storchaka48842712016-04-06 09:45:48 +03001387 Py_XSETREF(self->offset, PyTuple_GET_ITEM(info, 2));
Thomas Wouters477c8d52006-05-27 19:21:47 +00001388
Serhiy Storchaka4a1e70f2015-12-27 12:36:18 +02001389 Py_INCREF(PyTuple_GET_ITEM(info, 3));
Serhiy Storchaka48842712016-04-06 09:45:48 +03001390 Py_XSETREF(self->text, PyTuple_GET_ITEM(info, 3));
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001391
1392 Py_DECREF(info);
Nick Coghlan5b1fdc12014-06-16 19:48:02 +10001393
Martijn Pieters772d8092017-08-22 21:16:23 +01001394 /*
1395 * Issue #21669: Custom error for 'print' & 'exec' as statements
1396 *
1397 * Only applies to SyntaxError instances, not to subclasses such
1398 * as TabError or IndentationError (see issue #31161)
1399 */
Andy Lesterdffe4c02020-03-04 07:15:20 -06001400 if (Py_IS_TYPE(self, (PyTypeObject *)PyExc_SyntaxError) &&
Martijn Pieters772d8092017-08-22 21:16:23 +01001401 self->text && PyUnicode_Check(self->text) &&
1402 _report_missing_parentheses(self) < 0) {
1403 return -1;
Nick Coghlan5b1fdc12014-06-16 19:48:02 +10001404 }
Thomas Wouters477c8d52006-05-27 19:21:47 +00001405 }
1406 return 0;
1407}
1408
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001409static int
Thomas Wouters477c8d52006-05-27 19:21:47 +00001410SyntaxError_clear(PySyntaxErrorObject *self)
1411{
1412 Py_CLEAR(self->msg);
1413 Py_CLEAR(self->filename);
1414 Py_CLEAR(self->lineno);
1415 Py_CLEAR(self->offset);
1416 Py_CLEAR(self->text);
1417 Py_CLEAR(self->print_file_and_line);
1418 return BaseException_clear((PyBaseExceptionObject *)self);
1419}
1420
1421static void
1422SyntaxError_dealloc(PySyntaxErrorObject *self)
1423{
Thomas Wouters89f507f2006-12-13 04:49:30 +00001424 _PyObject_GC_UNTRACK(self);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001425 SyntaxError_clear(self);
Christian Heimes90aa7642007-12-19 02:45:37 +00001426 Py_TYPE(self)->tp_free((PyObject *)self);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001427}
1428
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001429static int
Thomas Wouters477c8d52006-05-27 19:21:47 +00001430SyntaxError_traverse(PySyntaxErrorObject *self, visitproc visit, void *arg)
1431{
1432 Py_VISIT(self->msg);
1433 Py_VISIT(self->filename);
1434 Py_VISIT(self->lineno);
1435 Py_VISIT(self->offset);
1436 Py_VISIT(self->text);
1437 Py_VISIT(self->print_file_and_line);
1438 return BaseException_traverse((PyBaseExceptionObject *)self, visit, arg);
1439}
1440
1441/* This is called "my_basename" instead of just "basename" to avoid name
1442 conflicts with glibc; basename is already prototyped if _GNU_SOURCE is
1443 defined, and Python does define that. */
Victor Stinner6237daf2010-04-28 17:26:19 +00001444static PyObject*
1445my_basename(PyObject *name)
Thomas Wouters477c8d52006-05-27 19:21:47 +00001446{
Victor Stinner6237daf2010-04-28 17:26:19 +00001447 Py_ssize_t i, size, offset;
Victor Stinner31392e72011-10-05 20:14:23 +02001448 int kind;
Serhiy Storchakacd8295f2020-04-11 10:48:40 +03001449 const void *data;
Victor Stinner31392e72011-10-05 20:14:23 +02001450
1451 if (PyUnicode_READY(name))
1452 return NULL;
1453 kind = PyUnicode_KIND(name);
1454 data = PyUnicode_DATA(name);
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02001455 size = PyUnicode_GET_LENGTH(name);
Victor Stinner6237daf2010-04-28 17:26:19 +00001456 offset = 0;
1457 for(i=0; i < size; i++) {
Victor Stinner361dcdc2020-04-15 03:24:57 +02001458 if (PyUnicode_READ(kind, data, i) == SEP) {
Victor Stinner6237daf2010-04-28 17:26:19 +00001459 offset = i + 1;
Victor Stinner361dcdc2020-04-15 03:24:57 +02001460 }
Thomas Wouters477c8d52006-05-27 19:21:47 +00001461 }
Victor Stinner361dcdc2020-04-15 03:24:57 +02001462 if (offset != 0) {
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02001463 return PyUnicode_Substring(name, offset, size);
Victor Stinner361dcdc2020-04-15 03:24:57 +02001464 }
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02001465 else {
Victor Stinner6237daf2010-04-28 17:26:19 +00001466 Py_INCREF(name);
1467 return name;
1468 }
Thomas Wouters477c8d52006-05-27 19:21:47 +00001469}
1470
1471
1472static PyObject *
1473SyntaxError_str(PySyntaxErrorObject *self)
1474{
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001475 int have_lineno = 0;
Victor Stinner6237daf2010-04-28 17:26:19 +00001476 PyObject *filename;
1477 PyObject *result;
Martin v. Löwisd1a1d1e2007-12-04 22:10:37 +00001478 /* Below, we always ignore overflow errors, just printing -1.
1479 Still, we cannot allow an OverflowError to be raised, so
1480 we need to call PyLong_AsLongAndOverflow. */
1481 int overflow;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001482
1483 /* XXX -- do all the additional formatting with filename and
1484 lineno here */
1485
Neal Norwitzed2b7392007-08-26 04:51:10 +00001486 if (self->filename && PyUnicode_Check(self->filename)) {
Victor Stinner6237daf2010-04-28 17:26:19 +00001487 filename = my_basename(self->filename);
1488 if (filename == NULL)
1489 return NULL;
1490 } else {
1491 filename = NULL;
Martin v. Löwis10a60b32007-07-18 02:28:27 +00001492 }
Martin v. Löwisd1a1d1e2007-12-04 22:10:37 +00001493 have_lineno = (self->lineno != NULL) && PyLong_CheckExact(self->lineno);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001494
Martin v. Löwis10a60b32007-07-18 02:28:27 +00001495 if (!filename && !have_lineno)
Thomas Heller519a0422007-11-15 20:48:54 +00001496 return PyObject_Str(self->msg ? self->msg : Py_None);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001497
Martin v. Löwis10a60b32007-07-18 02:28:27 +00001498 if (filename && have_lineno)
Victor Stinner6237daf2010-04-28 17:26:19 +00001499 result = PyUnicode_FromFormat("%S (%U, line %ld)",
Walter Dörwaldf5bec7c2007-05-26 15:03:32 +00001500 self->msg ? self->msg : Py_None,
Victor Stinner6237daf2010-04-28 17:26:19 +00001501 filename,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001502 PyLong_AsLongAndOverflow(self->lineno, &overflow));
Martin v. Löwis10a60b32007-07-18 02:28:27 +00001503 else if (filename)
Victor Stinner6237daf2010-04-28 17:26:19 +00001504 result = PyUnicode_FromFormat("%S (%U)",
Walter Dörwaldf5bec7c2007-05-26 15:03:32 +00001505 self->msg ? self->msg : Py_None,
Victor Stinner6237daf2010-04-28 17:26:19 +00001506 filename);
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001507 else /* only have_lineno */
Victor Stinner6237daf2010-04-28 17:26:19 +00001508 result = PyUnicode_FromFormat("%S (line %ld)",
Walter Dörwaldf5bec7c2007-05-26 15:03:32 +00001509 self->msg ? self->msg : Py_None,
Martin v. Löwisd1a1d1e2007-12-04 22:10:37 +00001510 PyLong_AsLongAndOverflow(self->lineno, &overflow));
Victor Stinner6237daf2010-04-28 17:26:19 +00001511 Py_XDECREF(filename);
1512 return result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001513}
1514
1515static PyMemberDef SyntaxError_members[] = {
Thomas Wouters477c8d52006-05-27 19:21:47 +00001516 {"msg", T_OBJECT, offsetof(PySyntaxErrorObject, msg), 0,
1517 PyDoc_STR("exception msg")},
1518 {"filename", T_OBJECT, offsetof(PySyntaxErrorObject, filename), 0,
1519 PyDoc_STR("exception filename")},
1520 {"lineno", T_OBJECT, offsetof(PySyntaxErrorObject, lineno), 0,
1521 PyDoc_STR("exception lineno")},
1522 {"offset", T_OBJECT, offsetof(PySyntaxErrorObject, offset), 0,
1523 PyDoc_STR("exception offset")},
1524 {"text", T_OBJECT, offsetof(PySyntaxErrorObject, text), 0,
1525 PyDoc_STR("exception text")},
1526 {"print_file_and_line", T_OBJECT,
1527 offsetof(PySyntaxErrorObject, print_file_and_line), 0,
1528 PyDoc_STR("exception print_file_and_line")},
1529 {NULL} /* Sentinel */
1530};
1531
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001532ComplexExtendsException(PyExc_Exception, SyntaxError, SyntaxError,
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001533 0, 0, SyntaxError_members, 0,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001534 SyntaxError_str, "Invalid syntax.");
1535
1536
1537/*
1538 * IndentationError extends SyntaxError
1539 */
1540MiddlingExtendsException(PyExc_SyntaxError, IndentationError, SyntaxError,
1541 "Improper indentation.");
1542
1543
1544/*
1545 * TabError extends IndentationError
1546 */
1547MiddlingExtendsException(PyExc_IndentationError, TabError, SyntaxError,
1548 "Improper mixture of spaces and tabs.");
1549
1550
1551/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001552 * LookupError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +00001553 */
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001554SimpleExtendsException(PyExc_Exception, LookupError,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001555 "Base class for lookup errors.");
1556
1557
1558/*
1559 * IndexError extends LookupError
1560 */
1561SimpleExtendsException(PyExc_LookupError, IndexError,
1562 "Sequence index out of range.");
1563
1564
1565/*
1566 * KeyError extends LookupError
1567 */
1568static PyObject *
1569KeyError_str(PyBaseExceptionObject *self)
1570{
1571 /* If args is a tuple of exactly one item, apply repr to args[0].
1572 This is done so that e.g. the exception raised by {}[''] prints
1573 KeyError: ''
1574 rather than the confusing
1575 KeyError
1576 alone. The downside is that if KeyError is raised with an explanatory
1577 string, that string will be displayed in quotes. Too bad.
1578 If args is anything else, use the default BaseException__str__().
1579 */
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001580 if (PyTuple_GET_SIZE(self->args) == 1) {
Walter Dörwaldf5bec7c2007-05-26 15:03:32 +00001581 return PyObject_Repr(PyTuple_GET_ITEM(self->args, 0));
Thomas Wouters477c8d52006-05-27 19:21:47 +00001582 }
1583 return BaseException_str(self);
1584}
1585
1586ComplexExtendsException(PyExc_LookupError, KeyError, BaseException,
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02001587 0, 0, 0, 0, KeyError_str, "Mapping key not found.");
Thomas Wouters477c8d52006-05-27 19:21:47 +00001588
1589
1590/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001591 * ValueError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +00001592 */
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001593SimpleExtendsException(PyExc_Exception, ValueError,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001594 "Inappropriate argument value (of correct type).");
1595
1596/*
1597 * UnicodeError extends ValueError
1598 */
1599
1600SimpleExtendsException(PyExc_ValueError, UnicodeError,
1601 "Unicode related error.");
1602
Thomas Wouters477c8d52006-05-27 19:21:47 +00001603static PyObject *
Guido van Rossum98297ee2007-11-06 21:34:58 +00001604get_string(PyObject *attr, const char *name)
Walter Dörwald612344f2007-05-04 19:28:21 +00001605{
1606 if (!attr) {
1607 PyErr_Format(PyExc_TypeError, "%.200s attribute not set", name);
1608 return NULL;
1609 }
1610
Christian Heimes72b710a2008-05-26 13:28:38 +00001611 if (!PyBytes_Check(attr)) {
Walter Dörwald612344f2007-05-04 19:28:21 +00001612 PyErr_Format(PyExc_TypeError, "%.200s attribute must be bytes", name);
1613 return NULL;
1614 }
1615 Py_INCREF(attr);
1616 return attr;
1617}
1618
1619static PyObject *
Thomas Wouters477c8d52006-05-27 19:21:47 +00001620get_unicode(PyObject *attr, const char *name)
1621{
1622 if (!attr) {
1623 PyErr_Format(PyExc_TypeError, "%.200s attribute not set", name);
1624 return NULL;
1625 }
1626
1627 if (!PyUnicode_Check(attr)) {
1628 PyErr_Format(PyExc_TypeError,
1629 "%.200s attribute must be unicode", name);
1630 return NULL;
1631 }
1632 Py_INCREF(attr);
1633 return attr;
1634}
1635
Walter Dörwaldd2034312007-05-18 16:29:38 +00001636static int
1637set_unicodefromstring(PyObject **attr, const char *value)
1638{
1639 PyObject *obj = PyUnicode_FromString(value);
1640 if (!obj)
1641 return -1;
Serhiy Storchaka48842712016-04-06 09:45:48 +03001642 Py_XSETREF(*attr, obj);
Walter Dörwaldd2034312007-05-18 16:29:38 +00001643 return 0;
1644}
1645
Thomas Wouters477c8d52006-05-27 19:21:47 +00001646PyObject *
1647PyUnicodeEncodeError_GetEncoding(PyObject *exc)
1648{
Walter Dörwaldd2034312007-05-18 16:29:38 +00001649 return get_unicode(((PyUnicodeErrorObject *)exc)->encoding, "encoding");
Thomas Wouters477c8d52006-05-27 19:21:47 +00001650}
1651
1652PyObject *
1653PyUnicodeDecodeError_GetEncoding(PyObject *exc)
1654{
Walter Dörwaldd2034312007-05-18 16:29:38 +00001655 return get_unicode(((PyUnicodeErrorObject *)exc)->encoding, "encoding");
Thomas Wouters477c8d52006-05-27 19:21:47 +00001656}
1657
1658PyObject *
1659PyUnicodeEncodeError_GetObject(PyObject *exc)
1660{
1661 return get_unicode(((PyUnicodeErrorObject *)exc)->object, "object");
1662}
1663
1664PyObject *
1665PyUnicodeDecodeError_GetObject(PyObject *exc)
1666{
Guido van Rossum98297ee2007-11-06 21:34:58 +00001667 return get_string(((PyUnicodeErrorObject *)exc)->object, "object");
Thomas Wouters477c8d52006-05-27 19:21:47 +00001668}
1669
1670PyObject *
1671PyUnicodeTranslateError_GetObject(PyObject *exc)
1672{
1673 return get_unicode(((PyUnicodeErrorObject *)exc)->object, "object");
1674}
1675
1676int
1677PyUnicodeEncodeError_GetStart(PyObject *exc, Py_ssize_t *start)
1678{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001679 Py_ssize_t size;
1680 PyObject *obj = get_unicode(((PyUnicodeErrorObject *)exc)->object,
1681 "object");
1682 if (!obj)
1683 return -1;
1684 *start = ((PyUnicodeErrorObject *)exc)->start;
Victor Stinner9e30aa52011-11-21 02:49:52 +01001685 size = PyUnicode_GET_LENGTH(obj);
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001686 if (*start<0)
1687 *start = 0; /*XXX check for values <0*/
1688 if (*start>=size)
1689 *start = size-1;
1690 Py_DECREF(obj);
1691 return 0;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001692}
1693
1694
1695int
1696PyUnicodeDecodeError_GetStart(PyObject *exc, Py_ssize_t *start)
1697{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001698 Py_ssize_t size;
Guido van Rossum98297ee2007-11-06 21:34:58 +00001699 PyObject *obj = get_string(((PyUnicodeErrorObject *)exc)->object, "object");
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001700 if (!obj)
1701 return -1;
Christian Heimes72b710a2008-05-26 13:28:38 +00001702 size = PyBytes_GET_SIZE(obj);
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001703 *start = ((PyUnicodeErrorObject *)exc)->start;
1704 if (*start<0)
1705 *start = 0;
1706 if (*start>=size)
1707 *start = size-1;
1708 Py_DECREF(obj);
1709 return 0;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001710}
1711
1712
1713int
1714PyUnicodeTranslateError_GetStart(PyObject *exc, Py_ssize_t *start)
1715{
1716 return PyUnicodeEncodeError_GetStart(exc, start);
1717}
1718
1719
1720int
1721PyUnicodeEncodeError_SetStart(PyObject *exc, Py_ssize_t start)
1722{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001723 ((PyUnicodeErrorObject *)exc)->start = start;
1724 return 0;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001725}
1726
1727
1728int
1729PyUnicodeDecodeError_SetStart(PyObject *exc, Py_ssize_t start)
1730{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001731 ((PyUnicodeErrorObject *)exc)->start = start;
1732 return 0;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001733}
1734
1735
1736int
1737PyUnicodeTranslateError_SetStart(PyObject *exc, Py_ssize_t start)
1738{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001739 ((PyUnicodeErrorObject *)exc)->start = start;
1740 return 0;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001741}
1742
1743
1744int
1745PyUnicodeEncodeError_GetEnd(PyObject *exc, Py_ssize_t *end)
1746{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001747 Py_ssize_t size;
1748 PyObject *obj = get_unicode(((PyUnicodeErrorObject *)exc)->object,
1749 "object");
1750 if (!obj)
1751 return -1;
1752 *end = ((PyUnicodeErrorObject *)exc)->end;
Victor Stinner9e30aa52011-11-21 02:49:52 +01001753 size = PyUnicode_GET_LENGTH(obj);
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001754 if (*end<1)
1755 *end = 1;
1756 if (*end>size)
1757 *end = size;
1758 Py_DECREF(obj);
1759 return 0;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001760}
1761
1762
1763int
1764PyUnicodeDecodeError_GetEnd(PyObject *exc, Py_ssize_t *end)
1765{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001766 Py_ssize_t size;
Guido van Rossum98297ee2007-11-06 21:34:58 +00001767 PyObject *obj = get_string(((PyUnicodeErrorObject *)exc)->object, "object");
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001768 if (!obj)
1769 return -1;
Christian Heimes72b710a2008-05-26 13:28:38 +00001770 size = PyBytes_GET_SIZE(obj);
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001771 *end = ((PyUnicodeErrorObject *)exc)->end;
1772 if (*end<1)
1773 *end = 1;
1774 if (*end>size)
1775 *end = size;
1776 Py_DECREF(obj);
1777 return 0;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001778}
1779
1780
1781int
Max Bernsteine6a0e802019-04-02 01:16:22 -07001782PyUnicodeTranslateError_GetEnd(PyObject *exc, Py_ssize_t *end)
Thomas Wouters477c8d52006-05-27 19:21:47 +00001783{
Max Bernsteine6a0e802019-04-02 01:16:22 -07001784 return PyUnicodeEncodeError_GetEnd(exc, end);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001785}
1786
1787
1788int
1789PyUnicodeEncodeError_SetEnd(PyObject *exc, Py_ssize_t end)
1790{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001791 ((PyUnicodeErrorObject *)exc)->end = end;
1792 return 0;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001793}
1794
1795
1796int
1797PyUnicodeDecodeError_SetEnd(PyObject *exc, Py_ssize_t end)
1798{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001799 ((PyUnicodeErrorObject *)exc)->end = end;
1800 return 0;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001801}
1802
1803
1804int
1805PyUnicodeTranslateError_SetEnd(PyObject *exc, Py_ssize_t end)
1806{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001807 ((PyUnicodeErrorObject *)exc)->end = end;
1808 return 0;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001809}
1810
1811PyObject *
1812PyUnicodeEncodeError_GetReason(PyObject *exc)
1813{
Walter Dörwaldd2034312007-05-18 16:29:38 +00001814 return get_unicode(((PyUnicodeErrorObject *)exc)->reason, "reason");
Thomas Wouters477c8d52006-05-27 19:21:47 +00001815}
1816
1817
1818PyObject *
1819PyUnicodeDecodeError_GetReason(PyObject *exc)
1820{
Walter Dörwaldd2034312007-05-18 16:29:38 +00001821 return get_unicode(((PyUnicodeErrorObject *)exc)->reason, "reason");
Thomas Wouters477c8d52006-05-27 19:21:47 +00001822}
1823
1824
1825PyObject *
1826PyUnicodeTranslateError_GetReason(PyObject *exc)
1827{
Walter Dörwaldd2034312007-05-18 16:29:38 +00001828 return get_unicode(((PyUnicodeErrorObject *)exc)->reason, "reason");
Thomas Wouters477c8d52006-05-27 19:21:47 +00001829}
1830
1831
1832int
1833PyUnicodeEncodeError_SetReason(PyObject *exc, const char *reason)
1834{
Walter Dörwaldd2034312007-05-18 16:29:38 +00001835 return set_unicodefromstring(&((PyUnicodeErrorObject *)exc)->reason,
1836 reason);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001837}
1838
1839
1840int
1841PyUnicodeDecodeError_SetReason(PyObject *exc, const char *reason)
1842{
Walter Dörwaldd2034312007-05-18 16:29:38 +00001843 return set_unicodefromstring(&((PyUnicodeErrorObject *)exc)->reason,
1844 reason);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001845}
1846
1847
1848int
1849PyUnicodeTranslateError_SetReason(PyObject *exc, const char *reason)
1850{
Walter Dörwaldd2034312007-05-18 16:29:38 +00001851 return set_unicodefromstring(&((PyUnicodeErrorObject *)exc)->reason,
1852 reason);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001853}
1854
1855
Thomas Wouters477c8d52006-05-27 19:21:47 +00001856static int
Thomas Wouters477c8d52006-05-27 19:21:47 +00001857UnicodeError_clear(PyUnicodeErrorObject *self)
1858{
1859 Py_CLEAR(self->encoding);
1860 Py_CLEAR(self->object);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001861 Py_CLEAR(self->reason);
1862 return BaseException_clear((PyBaseExceptionObject *)self);
1863}
1864
1865static void
1866UnicodeError_dealloc(PyUnicodeErrorObject *self)
1867{
Thomas Wouters89f507f2006-12-13 04:49:30 +00001868 _PyObject_GC_UNTRACK(self);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001869 UnicodeError_clear(self);
Christian Heimes90aa7642007-12-19 02:45:37 +00001870 Py_TYPE(self)->tp_free((PyObject *)self);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001871}
1872
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001873static int
Thomas Wouters477c8d52006-05-27 19:21:47 +00001874UnicodeError_traverse(PyUnicodeErrorObject *self, visitproc visit, void *arg)
1875{
1876 Py_VISIT(self->encoding);
1877 Py_VISIT(self->object);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001878 Py_VISIT(self->reason);
1879 return BaseException_traverse((PyBaseExceptionObject *)self, visit, arg);
1880}
1881
1882static PyMemberDef UnicodeError_members[] = {
Thomas Wouters477c8d52006-05-27 19:21:47 +00001883 {"encoding", T_OBJECT, offsetof(PyUnicodeErrorObject, encoding), 0,
1884 PyDoc_STR("exception encoding")},
1885 {"object", T_OBJECT, offsetof(PyUnicodeErrorObject, object), 0,
1886 PyDoc_STR("exception object")},
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001887 {"start", T_PYSSIZET, offsetof(PyUnicodeErrorObject, start), 0,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001888 PyDoc_STR("exception start")},
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001889 {"end", T_PYSSIZET, offsetof(PyUnicodeErrorObject, end), 0,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001890 PyDoc_STR("exception end")},
1891 {"reason", T_OBJECT, offsetof(PyUnicodeErrorObject, reason), 0,
1892 PyDoc_STR("exception reason")},
1893 {NULL} /* Sentinel */
1894};
1895
1896
1897/*
1898 * UnicodeEncodeError extends UnicodeError
1899 */
Thomas Wouters477c8d52006-05-27 19:21:47 +00001900
1901static int
1902UnicodeEncodeError_init(PyObject *self, PyObject *args, PyObject *kwds)
1903{
Guido van Rossum98297ee2007-11-06 21:34:58 +00001904 PyUnicodeErrorObject *err;
1905
Thomas Wouters477c8d52006-05-27 19:21:47 +00001906 if (BaseException_init((PyBaseExceptionObject *)self, args, kwds) == -1)
1907 return -1;
Guido van Rossum98297ee2007-11-06 21:34:58 +00001908
1909 err = (PyUnicodeErrorObject *)self;
1910
1911 Py_CLEAR(err->encoding);
1912 Py_CLEAR(err->object);
1913 Py_CLEAR(err->reason);
1914
Serhiy Storchakaf8d7d412016-10-23 15:12:25 +03001915 if (!PyArg_ParseTuple(args, "UUnnU",
1916 &err->encoding, &err->object,
1917 &err->start, &err->end, &err->reason)) {
1918 err->encoding = err->object = err->reason = NULL;
Martin v. Löwisb09af032011-11-04 11:16:41 +01001919 return -1;
1920 }
1921
Guido van Rossum98297ee2007-11-06 21:34:58 +00001922 Py_INCREF(err->encoding);
1923 Py_INCREF(err->object);
1924 Py_INCREF(err->reason);
1925
1926 return 0;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001927}
1928
1929static PyObject *
1930UnicodeEncodeError_str(PyObject *self)
1931{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001932 PyUnicodeErrorObject *uself = (PyUnicodeErrorObject *)self;
Eric Smith0facd772010-02-24 15:42:29 +00001933 PyObject *result = NULL;
1934 PyObject *reason_str = NULL;
1935 PyObject *encoding_str = NULL;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001936
Benjamin Peterson9b09ba12014-04-02 12:15:06 -04001937 if (!uself->object)
1938 /* Not properly initialized. */
1939 return PyUnicode_FromString("");
1940
Eric Smith0facd772010-02-24 15:42:29 +00001941 /* Get reason and encoding as strings, which they might not be if
Martin Pantereb995702016-07-28 01:11:04 +00001942 they've been modified after we were constructed. */
Eric Smith0facd772010-02-24 15:42:29 +00001943 reason_str = PyObject_Str(uself->reason);
1944 if (reason_str == NULL)
1945 goto done;
1946 encoding_str = PyObject_Str(uself->encoding);
1947 if (encoding_str == NULL)
1948 goto done;
1949
Victor Stinnerda1ddf32011-11-20 22:50:23 +01001950 if (uself->start < PyUnicode_GET_LENGTH(uself->object) && uself->end == uself->start+1) {
1951 Py_UCS4 badchar = PyUnicode_ReadChar(uself->object, uself->start);
Walter Dörwald787b03b2007-06-05 13:29:29 +00001952 const char *fmt;
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001953 if (badchar <= 0xff)
Walter Dörwald32a4c712007-06-20 09:25:34 +00001954 fmt = "'%U' codec can't encode character '\\x%02x' in position %zd: %U";
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001955 else if (badchar <= 0xffff)
Walter Dörwald32a4c712007-06-20 09:25:34 +00001956 fmt = "'%U' codec can't encode character '\\u%04x' in position %zd: %U";
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001957 else
Walter Dörwald32a4c712007-06-20 09:25:34 +00001958 fmt = "'%U' codec can't encode character '\\U%08x' in position %zd: %U";
Eric Smith0facd772010-02-24 15:42:29 +00001959 result = PyUnicode_FromFormat(
Walter Dörwald787b03b2007-06-05 13:29:29 +00001960 fmt,
Eric Smith0facd772010-02-24 15:42:29 +00001961 encoding_str,
Victor Stinnerda1ddf32011-11-20 22:50:23 +01001962 (int)badchar,
Guido van Rossum7eaf8222007-06-18 17:58:50 +00001963 uself->start,
Eric Smith0facd772010-02-24 15:42:29 +00001964 reason_str);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001965 }
Eric Smith0facd772010-02-24 15:42:29 +00001966 else {
1967 result = PyUnicode_FromFormat(
1968 "'%U' codec can't encode characters in position %zd-%zd: %U",
1969 encoding_str,
1970 uself->start,
1971 uself->end-1,
1972 reason_str);
1973 }
1974done:
1975 Py_XDECREF(reason_str);
1976 Py_XDECREF(encoding_str);
1977 return result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001978}
1979
1980static PyTypeObject _PyExc_UnicodeEncodeError = {
Martin v. Löwis9f2e3462007-07-21 17:22:18 +00001981 PyVarObject_HEAD_INIT(NULL, 0)
Neal Norwitz2633c692007-02-26 22:22:47 +00001982 "UnicodeEncodeError",
Thomas Wouters477c8d52006-05-27 19:21:47 +00001983 sizeof(PyUnicodeErrorObject), 0,
1984 (destructor)UnicodeError_dealloc, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1985 (reprfunc)UnicodeEncodeError_str, 0, 0, 0,
1986 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC,
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001987 PyDoc_STR("Unicode encoding error."), (traverseproc)UnicodeError_traverse,
1988 (inquiry)UnicodeError_clear, 0, 0, 0, 0, 0, UnicodeError_members,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001989 0, &_PyExc_UnicodeError, 0, 0, 0, offsetof(PyUnicodeErrorObject, dict),
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001990 (initproc)UnicodeEncodeError_init, 0, BaseException_new,
Thomas Wouters477c8d52006-05-27 19:21:47 +00001991};
1992PyObject *PyExc_UnicodeEncodeError = (PyObject *)&_PyExc_UnicodeEncodeError;
1993
1994PyObject *
1995PyUnicodeEncodeError_Create(
1996 const char *encoding, const Py_UNICODE *object, Py_ssize_t length,
1997 Py_ssize_t start, Py_ssize_t end, const char *reason)
1998{
Victor Stinner7eeb5b52010-06-07 19:57:46 +00001999 return PyObject_CallFunction(PyExc_UnicodeEncodeError, "su#nns",
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002000 encoding, object, length, start, end, reason);
Thomas Wouters477c8d52006-05-27 19:21:47 +00002001}
2002
2003
2004/*
2005 * UnicodeDecodeError extends UnicodeError
2006 */
Thomas Wouters477c8d52006-05-27 19:21:47 +00002007
2008static int
2009UnicodeDecodeError_init(PyObject *self, PyObject *args, PyObject *kwds)
2010{
Guido van Rossum98297ee2007-11-06 21:34:58 +00002011 PyUnicodeErrorObject *ude;
Guido van Rossum98297ee2007-11-06 21:34:58 +00002012
Thomas Wouters477c8d52006-05-27 19:21:47 +00002013 if (BaseException_init((PyBaseExceptionObject *)self, args, kwds) == -1)
2014 return -1;
Guido van Rossum98297ee2007-11-06 21:34:58 +00002015
2016 ude = (PyUnicodeErrorObject *)self;
2017
2018 Py_CLEAR(ude->encoding);
2019 Py_CLEAR(ude->object);
2020 Py_CLEAR(ude->reason);
2021
Serhiy Storchakaf8d7d412016-10-23 15:12:25 +03002022 if (!PyArg_ParseTuple(args, "UOnnU",
2023 &ude->encoding, &ude->object,
2024 &ude->start, &ude->end, &ude->reason)) {
Guido van Rossum98297ee2007-11-06 21:34:58 +00002025 ude->encoding = ude->object = ude->reason = NULL;
2026 return -1;
2027 }
2028
Guido van Rossum98297ee2007-11-06 21:34:58 +00002029 Py_INCREF(ude->encoding);
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +02002030 Py_INCREF(ude->object);
Guido van Rossum98297ee2007-11-06 21:34:58 +00002031 Py_INCREF(ude->reason);
2032
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +02002033 if (!PyBytes_Check(ude->object)) {
2034 Py_buffer view;
2035 if (PyObject_GetBuffer(ude->object, &view, PyBUF_SIMPLE) != 0)
2036 goto error;
Serhiy Storchaka48842712016-04-06 09:45:48 +03002037 Py_XSETREF(ude->object, PyBytes_FromStringAndSize(view.buf, view.len));
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +02002038 PyBuffer_Release(&view);
2039 if (!ude->object)
2040 goto error;
2041 }
Guido van Rossum98297ee2007-11-06 21:34:58 +00002042 return 0;
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +02002043
2044error:
2045 Py_CLEAR(ude->encoding);
2046 Py_CLEAR(ude->object);
2047 Py_CLEAR(ude->reason);
2048 return -1;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002049}
2050
2051static PyObject *
2052UnicodeDecodeError_str(PyObject *self)
2053{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00002054 PyUnicodeErrorObject *uself = (PyUnicodeErrorObject *)self;
Eric Smith0facd772010-02-24 15:42:29 +00002055 PyObject *result = NULL;
2056 PyObject *reason_str = NULL;
2057 PyObject *encoding_str = NULL;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002058
Benjamin Peterson9b09ba12014-04-02 12:15:06 -04002059 if (!uself->object)
2060 /* Not properly initialized. */
2061 return PyUnicode_FromString("");
2062
Eric Smith0facd772010-02-24 15:42:29 +00002063 /* Get reason and encoding as strings, which they might not be if
Martin Pantereb995702016-07-28 01:11:04 +00002064 they've been modified after we were constructed. */
Eric Smith0facd772010-02-24 15:42:29 +00002065 reason_str = PyObject_Str(uself->reason);
2066 if (reason_str == NULL)
2067 goto done;
2068 encoding_str = PyObject_Str(uself->encoding);
2069 if (encoding_str == NULL)
2070 goto done;
2071
2072 if (uself->start < PyBytes_GET_SIZE(uself->object) && uself->end == uself->start+1) {
Christian Heimes72b710a2008-05-26 13:28:38 +00002073 int byte = (int)(PyBytes_AS_STRING(((PyUnicodeErrorObject *)self)->object)[uself->start]&0xff);
Eric Smith0facd772010-02-24 15:42:29 +00002074 result = PyUnicode_FromFormat(
Walter Dörwald787b03b2007-06-05 13:29:29 +00002075 "'%U' codec can't decode byte 0x%02x in position %zd: %U",
Eric Smith0facd772010-02-24 15:42:29 +00002076 encoding_str,
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002077 byte,
Guido van Rossum7eaf8222007-06-18 17:58:50 +00002078 uself->start,
Eric Smith0facd772010-02-24 15:42:29 +00002079 reason_str);
Thomas Wouters477c8d52006-05-27 19:21:47 +00002080 }
Eric Smith0facd772010-02-24 15:42:29 +00002081 else {
2082 result = PyUnicode_FromFormat(
2083 "'%U' codec can't decode bytes in position %zd-%zd: %U",
2084 encoding_str,
2085 uself->start,
2086 uself->end-1,
2087 reason_str
2088 );
2089 }
2090done:
2091 Py_XDECREF(reason_str);
2092 Py_XDECREF(encoding_str);
2093 return result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002094}
2095
2096static PyTypeObject _PyExc_UnicodeDecodeError = {
Martin v. Löwis9f2e3462007-07-21 17:22:18 +00002097 PyVarObject_HEAD_INIT(NULL, 0)
Neal Norwitz2633c692007-02-26 22:22:47 +00002098 "UnicodeDecodeError",
Thomas Wouters477c8d52006-05-27 19:21:47 +00002099 sizeof(PyUnicodeErrorObject), 0,
2100 (destructor)UnicodeError_dealloc, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
2101 (reprfunc)UnicodeDecodeError_str, 0, 0, 0,
2102 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC,
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002103 PyDoc_STR("Unicode decoding error."), (traverseproc)UnicodeError_traverse,
2104 (inquiry)UnicodeError_clear, 0, 0, 0, 0, 0, UnicodeError_members,
Thomas Wouters477c8d52006-05-27 19:21:47 +00002105 0, &_PyExc_UnicodeError, 0, 0, 0, offsetof(PyUnicodeErrorObject, dict),
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002106 (initproc)UnicodeDecodeError_init, 0, BaseException_new,
Thomas Wouters477c8d52006-05-27 19:21:47 +00002107};
2108PyObject *PyExc_UnicodeDecodeError = (PyObject *)&_PyExc_UnicodeDecodeError;
2109
2110PyObject *
2111PyUnicodeDecodeError_Create(
2112 const char *encoding, const char *object, Py_ssize_t length,
2113 Py_ssize_t start, Py_ssize_t end, const char *reason)
2114{
Victor Stinner7eeb5b52010-06-07 19:57:46 +00002115 return PyObject_CallFunction(PyExc_UnicodeDecodeError, "sy#nns",
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002116 encoding, object, length, start, end, reason);
Thomas Wouters477c8d52006-05-27 19:21:47 +00002117}
2118
2119
2120/*
2121 * UnicodeTranslateError extends UnicodeError
2122 */
Thomas Wouters477c8d52006-05-27 19:21:47 +00002123
2124static int
2125UnicodeTranslateError_init(PyUnicodeErrorObject *self, PyObject *args,
2126 PyObject *kwds)
2127{
2128 if (BaseException_init((PyBaseExceptionObject *)self, args, kwds) == -1)
2129 return -1;
2130
2131 Py_CLEAR(self->object);
Thomas Wouters477c8d52006-05-27 19:21:47 +00002132 Py_CLEAR(self->reason);
2133
Serhiy Storchakaf8d7d412016-10-23 15:12:25 +03002134 if (!PyArg_ParseTuple(args, "UnnU",
2135 &self->object,
2136 &self->start, &self->end, &self->reason)) {
Guido van Rossum7eaf8222007-06-18 17:58:50 +00002137 self->object = self->reason = NULL;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002138 return -1;
2139 }
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002140
Thomas Wouters477c8d52006-05-27 19:21:47 +00002141 Py_INCREF(self->object);
Thomas Wouters477c8d52006-05-27 19:21:47 +00002142 Py_INCREF(self->reason);
2143
2144 return 0;
2145}
2146
2147
2148static PyObject *
2149UnicodeTranslateError_str(PyObject *self)
2150{
Guido van Rossum7eaf8222007-06-18 17:58:50 +00002151 PyUnicodeErrorObject *uself = (PyUnicodeErrorObject *)self;
Eric Smith0facd772010-02-24 15:42:29 +00002152 PyObject *result = NULL;
2153 PyObject *reason_str = NULL;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002154
Benjamin Peterson9b09ba12014-04-02 12:15:06 -04002155 if (!uself->object)
2156 /* Not properly initialized. */
2157 return PyUnicode_FromString("");
2158
Eric Smith0facd772010-02-24 15:42:29 +00002159 /* Get reason as a string, which it might not be if it's been
Martin Pantereb995702016-07-28 01:11:04 +00002160 modified after we were constructed. */
Eric Smith0facd772010-02-24 15:42:29 +00002161 reason_str = PyObject_Str(uself->reason);
2162 if (reason_str == NULL)
2163 goto done;
2164
Victor Stinner53b33e72011-11-21 01:17:27 +01002165 if (uself->start < PyUnicode_GET_LENGTH(uself->object) && uself->end == uself->start+1) {
2166 Py_UCS4 badchar = PyUnicode_ReadChar(uself->object, uself->start);
Walter Dörwald787b03b2007-06-05 13:29:29 +00002167 const char *fmt;
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002168 if (badchar <= 0xff)
Walter Dörwald32a4c712007-06-20 09:25:34 +00002169 fmt = "can't translate character '\\x%02x' in position %zd: %U";
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002170 else if (badchar <= 0xffff)
Walter Dörwald32a4c712007-06-20 09:25:34 +00002171 fmt = "can't translate character '\\u%04x' in position %zd: %U";
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002172 else
Walter Dörwald32a4c712007-06-20 09:25:34 +00002173 fmt = "can't translate character '\\U%08x' in position %zd: %U";
Benjamin Petersonc5f4e1e2010-02-25 01:22:28 +00002174 result = PyUnicode_FromFormat(
Walter Dörwald787b03b2007-06-05 13:29:29 +00002175 fmt,
Victor Stinner53b33e72011-11-21 01:17:27 +01002176 (int)badchar,
Guido van Rossum7eaf8222007-06-18 17:58:50 +00002177 uself->start,
Eric Smith0facd772010-02-24 15:42:29 +00002178 reason_str
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002179 );
Eric Smith0facd772010-02-24 15:42:29 +00002180 } else {
2181 result = PyUnicode_FromFormat(
2182 "can't translate characters in position %zd-%zd: %U",
2183 uself->start,
2184 uself->end-1,
2185 reason_str
2186 );
Thomas Wouters477c8d52006-05-27 19:21:47 +00002187 }
Eric Smith0facd772010-02-24 15:42:29 +00002188done:
2189 Py_XDECREF(reason_str);
2190 return result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002191}
2192
2193static PyTypeObject _PyExc_UnicodeTranslateError = {
Martin v. Löwis9f2e3462007-07-21 17:22:18 +00002194 PyVarObject_HEAD_INIT(NULL, 0)
Neal Norwitz2633c692007-02-26 22:22:47 +00002195 "UnicodeTranslateError",
Thomas Wouters477c8d52006-05-27 19:21:47 +00002196 sizeof(PyUnicodeErrorObject), 0,
2197 (destructor)UnicodeError_dealloc, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
2198 (reprfunc)UnicodeTranslateError_str, 0, 0, 0,
2199 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC,
Thomas Wouters89f507f2006-12-13 04:49:30 +00002200 PyDoc_STR("Unicode translation error."), (traverseproc)UnicodeError_traverse,
Thomas Wouters477c8d52006-05-27 19:21:47 +00002201 (inquiry)UnicodeError_clear, 0, 0, 0, 0, 0, UnicodeError_members,
2202 0, &_PyExc_UnicodeError, 0, 0, 0, offsetof(PyUnicodeErrorObject, dict),
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002203 (initproc)UnicodeTranslateError_init, 0, BaseException_new,
Thomas Wouters477c8d52006-05-27 19:21:47 +00002204};
2205PyObject *PyExc_UnicodeTranslateError = (PyObject *)&_PyExc_UnicodeTranslateError;
2206
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02002207/* Deprecated. */
Thomas Wouters477c8d52006-05-27 19:21:47 +00002208PyObject *
2209PyUnicodeTranslateError_Create(
2210 const Py_UNICODE *object, Py_ssize_t length,
2211 Py_ssize_t start, Py_ssize_t end, const char *reason)
2212{
2213 return PyObject_CallFunction(PyExc_UnicodeTranslateError, "u#nns",
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00002214 object, length, start, end, reason);
Thomas Wouters477c8d52006-05-27 19:21:47 +00002215}
Thomas Wouters477c8d52006-05-27 19:21:47 +00002216
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02002217PyObject *
2218_PyUnicodeTranslateError_Create(
2219 PyObject *object,
2220 Py_ssize_t start, Py_ssize_t end, const char *reason)
2221{
Victor Stinner69598d42014-04-04 20:59:44 +02002222 return PyObject_CallFunction(PyExc_UnicodeTranslateError, "Onns",
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02002223 object, start, end, reason);
2224}
Thomas Wouters477c8d52006-05-27 19:21:47 +00002225
2226/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +00002227 * AssertionError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +00002228 */
Guido van Rossumcd16bf62007-06-13 18:07:49 +00002229SimpleExtendsException(PyExc_Exception, AssertionError,
Thomas Wouters477c8d52006-05-27 19:21:47 +00002230 "Assertion failed.");
2231
2232
2233/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +00002234 * ArithmeticError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +00002235 */
Guido van Rossumcd16bf62007-06-13 18:07:49 +00002236SimpleExtendsException(PyExc_Exception, ArithmeticError,
Thomas Wouters477c8d52006-05-27 19:21:47 +00002237 "Base class for arithmetic errors.");
2238
2239
2240/*
2241 * FloatingPointError extends ArithmeticError
2242 */
2243SimpleExtendsException(PyExc_ArithmeticError, FloatingPointError,
2244 "Floating point operation failed.");
2245
2246
2247/*
2248 * OverflowError extends ArithmeticError
2249 */
2250SimpleExtendsException(PyExc_ArithmeticError, OverflowError,
2251 "Result too large to be represented.");
2252
2253
2254/*
2255 * ZeroDivisionError extends ArithmeticError
2256 */
2257SimpleExtendsException(PyExc_ArithmeticError, ZeroDivisionError,
2258 "Second argument to a division or modulo operation was zero.");
2259
2260
2261/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +00002262 * SystemError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +00002263 */
Guido van Rossumcd16bf62007-06-13 18:07:49 +00002264SimpleExtendsException(PyExc_Exception, SystemError,
Thomas Wouters477c8d52006-05-27 19:21:47 +00002265 "Internal error in the Python interpreter.\n"
2266 "\n"
2267 "Please report this to the Python maintainer, along with the traceback,\n"
2268 "the Python version, and the hardware/OS platform and version.");
2269
2270
2271/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +00002272 * ReferenceError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +00002273 */
Guido van Rossumcd16bf62007-06-13 18:07:49 +00002274SimpleExtendsException(PyExc_Exception, ReferenceError,
Thomas Wouters477c8d52006-05-27 19:21:47 +00002275 "Weak ref proxy used after referent went away.");
2276
2277
2278/*
Guido van Rossumcd16bf62007-06-13 18:07:49 +00002279 * MemoryError extends Exception
Thomas Wouters477c8d52006-05-27 19:21:47 +00002280 */
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002281
2282#define MEMERRORS_SAVE 16
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002283
2284static PyObject *
2285MemoryError_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
2286{
2287 PyBaseExceptionObject *self;
2288
Pablo Galindo9b648a92020-09-01 19:39:46 +01002289 /* If this is a subclass of MemoryError, don't use the freelist
2290 * and just return a fresh object */
2291 if (type != (PyTypeObject *) PyExc_MemoryError) {
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002292 return BaseException_new(type, args, kwds);
Pablo Galindo9b648a92020-09-01 19:39:46 +01002293 }
Victor Stinner281cce12020-06-23 22:55:46 +02002294
2295 struct _Py_exc_state *state = get_exc_state();
2296 if (state->memerrors_freelist == NULL) {
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002297 return BaseException_new(type, args, kwds);
Victor Stinner281cce12020-06-23 22:55:46 +02002298 }
2299
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002300 /* Fetch object from freelist and revive it */
Victor Stinner281cce12020-06-23 22:55:46 +02002301 self = state->memerrors_freelist;
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002302 self->args = PyTuple_New(0);
2303 /* This shouldn't happen since the empty tuple is persistent */
Victor Stinner281cce12020-06-23 22:55:46 +02002304 if (self->args == NULL) {
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002305 return NULL;
Victor Stinner281cce12020-06-23 22:55:46 +02002306 }
2307
2308 state->memerrors_freelist = (PyBaseExceptionObject *) self->dict;
2309 state->memerrors_numfree--;
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002310 self->dict = NULL;
2311 _Py_NewReference((PyObject *)self);
2312 _PyObject_GC_TRACK(self);
2313 return (PyObject *)self;
2314}
2315
2316static void
2317MemoryError_dealloc(PyBaseExceptionObject *self)
2318{
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002319 BaseException_clear(self);
Victor Stinner281cce12020-06-23 22:55:46 +02002320
Pablo Galindo9b648a92020-09-01 19:39:46 +01002321 /* If this is a subclass of MemoryError, we don't need to
2322 * do anything in the free-list*/
2323 if (!Py_IS_TYPE(self, (PyTypeObject *) PyExc_MemoryError)) {
2324 return Py_TYPE(self)->tp_free((PyObject *)self);
2325 }
2326
2327 _PyObject_GC_UNTRACK(self);
2328
Victor Stinner281cce12020-06-23 22:55:46 +02002329 struct _Py_exc_state *state = get_exc_state();
2330 if (state->memerrors_numfree >= MEMERRORS_SAVE) {
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002331 Py_TYPE(self)->tp_free((PyObject *)self);
Victor Stinner281cce12020-06-23 22:55:46 +02002332 }
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002333 else {
Victor Stinner281cce12020-06-23 22:55:46 +02002334 self->dict = (PyObject *) state->memerrors_freelist;
2335 state->memerrors_freelist = self;
2336 state->memerrors_numfree++;
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002337 }
2338}
2339
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002340static int
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002341preallocate_memerrors(void)
2342{
2343 /* We create enough MemoryErrors and then decref them, which will fill
2344 up the freelist. */
2345 int i;
2346 PyObject *errors[MEMERRORS_SAVE];
2347 for (i = 0; i < MEMERRORS_SAVE; i++) {
2348 errors[i] = MemoryError_new((PyTypeObject *) PyExc_MemoryError,
2349 NULL, NULL);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002350 if (!errors[i]) {
2351 return -1;
2352 }
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002353 }
2354 for (i = 0; i < MEMERRORS_SAVE; i++) {
2355 Py_DECREF(errors[i]);
2356 }
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002357 return 0;
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002358}
2359
2360static void
Victor Stinner281cce12020-06-23 22:55:46 +02002361free_preallocated_memerrors(struct _Py_exc_state *state)
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002362{
Victor Stinner281cce12020-06-23 22:55:46 +02002363 while (state->memerrors_freelist != NULL) {
2364 PyObject *self = (PyObject *) state->memerrors_freelist;
2365 state->memerrors_freelist = (PyBaseExceptionObject *)state->memerrors_freelist->dict;
Antoine Pitrou07e20ef2010-10-28 22:56:58 +00002366 Py_TYPE(self)->tp_free((PyObject *)self);
2367 }
2368}
2369
2370
2371static PyTypeObject _PyExc_MemoryError = {
2372 PyVarObject_HEAD_INIT(NULL, 0)
2373 "MemoryError",
2374 sizeof(PyBaseExceptionObject),
2375 0, (destructor)MemoryError_dealloc, 0, 0, 0, 0, 0, 0, 0,
2376 0, 0, 0, 0, 0, 0, 0,
2377 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC,
2378 PyDoc_STR("Out of memory."), (traverseproc)BaseException_traverse,
2379 (inquiry)BaseException_clear, 0, 0, 0, 0, 0, 0, 0, &_PyExc_Exception,
2380 0, 0, 0, offsetof(PyBaseExceptionObject, dict),
2381 (initproc)BaseException_init, 0, MemoryError_new
2382};
2383PyObject *PyExc_MemoryError = (PyObject *) &_PyExc_MemoryError;
2384
Thomas Wouters477c8d52006-05-27 19:21:47 +00002385
Travis E. Oliphantb99f7622007-08-18 11:21:56 +00002386/*
2387 * BufferError extends Exception
2388 */
2389SimpleExtendsException(PyExc_Exception, BufferError, "Buffer error.");
2390
Thomas Wouters477c8d52006-05-27 19:21:47 +00002391
2392/* Warning category docstrings */
2393
2394/*
2395 * Warning extends Exception
2396 */
2397SimpleExtendsException(PyExc_Exception, Warning,
2398 "Base class for warning categories.");
2399
2400
2401/*
2402 * UserWarning extends Warning
2403 */
2404SimpleExtendsException(PyExc_Warning, UserWarning,
2405 "Base class for warnings generated by user code.");
2406
2407
2408/*
2409 * DeprecationWarning extends Warning
2410 */
2411SimpleExtendsException(PyExc_Warning, DeprecationWarning,
2412 "Base class for warnings about deprecated features.");
2413
2414
2415/*
2416 * PendingDeprecationWarning extends Warning
2417 */
2418SimpleExtendsException(PyExc_Warning, PendingDeprecationWarning,
2419 "Base class for warnings about features which will be deprecated\n"
2420 "in the future.");
2421
2422
2423/*
2424 * SyntaxWarning extends Warning
2425 */
2426SimpleExtendsException(PyExc_Warning, SyntaxWarning,
2427 "Base class for warnings about dubious syntax.");
2428
2429
2430/*
2431 * RuntimeWarning extends Warning
2432 */
2433SimpleExtendsException(PyExc_Warning, RuntimeWarning,
2434 "Base class for warnings about dubious runtime behavior.");
2435
2436
2437/*
2438 * FutureWarning extends Warning
2439 */
2440SimpleExtendsException(PyExc_Warning, FutureWarning,
2441 "Base class for warnings about constructs that will change semantically\n"
2442 "in the future.");
2443
2444
2445/*
2446 * ImportWarning extends Warning
2447 */
2448SimpleExtendsException(PyExc_Warning, ImportWarning,
2449 "Base class for warnings about probable mistakes in module imports");
2450
2451
Thomas Wouters00ee7ba2006-08-21 19:07:27 +00002452/*
2453 * UnicodeWarning extends Warning
2454 */
2455SimpleExtendsException(PyExc_Warning, UnicodeWarning,
2456 "Base class for warnings about Unicode related problems, mostly\n"
2457 "related to conversion problems.");
2458
Georg Brandl08be72d2010-10-24 15:11:22 +00002459
Guido van Rossum98297ee2007-11-06 21:34:58 +00002460/*
2461 * BytesWarning extends Warning
2462 */
2463SimpleExtendsException(PyExc_Warning, BytesWarning,
2464 "Base class for warnings about bytes and buffer related problems, mostly\n"
2465 "related to conversion from str or comparing to str.");
2466
2467
Georg Brandl08be72d2010-10-24 15:11:22 +00002468/*
2469 * ResourceWarning extends Warning
2470 */
2471SimpleExtendsException(PyExc_Warning, ResourceWarning,
2472 "Base class for warnings about resource usage.");
2473
2474
Thomas Wouters00ee7ba2006-08-21 19:07:27 +00002475
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02002476#ifdef MS_WINDOWS
Antoine Pitrou7faf7052013-03-31 22:48:04 +02002477#include <winsock2.h>
Brian Curtin401f9f32012-05-13 11:19:23 -05002478/* The following constants were added to errno.h in VS2010 but have
2479 preferred WSA equivalents. */
2480#undef EADDRINUSE
2481#undef EADDRNOTAVAIL
2482#undef EAFNOSUPPORT
2483#undef EALREADY
2484#undef ECONNABORTED
2485#undef ECONNREFUSED
2486#undef ECONNRESET
2487#undef EDESTADDRREQ
2488#undef EHOSTUNREACH
2489#undef EINPROGRESS
2490#undef EISCONN
2491#undef ELOOP
2492#undef EMSGSIZE
2493#undef ENETDOWN
2494#undef ENETRESET
2495#undef ENETUNREACH
2496#undef ENOBUFS
2497#undef ENOPROTOOPT
2498#undef ENOTCONN
2499#undef ENOTSOCK
2500#undef EOPNOTSUPP
2501#undef EPROTONOSUPPORT
2502#undef EPROTOTYPE
2503#undef ETIMEDOUT
2504#undef EWOULDBLOCK
2505
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02002506#if defined(WSAEALREADY) && !defined(EALREADY)
2507#define EALREADY WSAEALREADY
2508#endif
2509#if defined(WSAECONNABORTED) && !defined(ECONNABORTED)
2510#define ECONNABORTED WSAECONNABORTED
2511#endif
2512#if defined(WSAECONNREFUSED) && !defined(ECONNREFUSED)
2513#define ECONNREFUSED WSAECONNREFUSED
2514#endif
2515#if defined(WSAECONNRESET) && !defined(ECONNRESET)
2516#define ECONNRESET WSAECONNRESET
2517#endif
2518#if defined(WSAEINPROGRESS) && !defined(EINPROGRESS)
2519#define EINPROGRESS WSAEINPROGRESS
2520#endif
2521#if defined(WSAESHUTDOWN) && !defined(ESHUTDOWN)
2522#define ESHUTDOWN WSAESHUTDOWN
2523#endif
2524#if defined(WSAETIMEDOUT) && !defined(ETIMEDOUT)
2525#define ETIMEDOUT WSAETIMEDOUT
2526#endif
2527#if defined(WSAEWOULDBLOCK) && !defined(EWOULDBLOCK)
2528#define EWOULDBLOCK WSAEWOULDBLOCK
2529#endif
2530#endif /* MS_WINDOWS */
Thomas Wouters0e3f5912006-08-11 14:57:12 +00002531
Victor Stinner331a6a52019-05-27 16:39:22 +02002532PyStatus
Victor Stinner281cce12020-06-23 22:55:46 +02002533_PyExc_Init(PyThreadState *tstate)
Thomas Wouters477c8d52006-05-27 19:21:47 +00002534{
Victor Stinner281cce12020-06-23 22:55:46 +02002535 struct _Py_exc_state *state = &tstate->interp->exc_state;
2536
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002537#define PRE_INIT(TYPE) \
2538 if (!(_PyExc_ ## TYPE.tp_flags & Py_TPFLAGS_READY)) { \
2539 if (PyType_Ready(&_PyExc_ ## TYPE) < 0) { \
Victor Stinner331a6a52019-05-27 16:39:22 +02002540 return _PyStatus_ERR("exceptions bootstrapping error."); \
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002541 } \
2542 Py_INCREF(PyExc_ ## TYPE); \
2543 }
2544
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002545#define ADD_ERRNO(TYPE, CODE) \
2546 do { \
2547 PyObject *_code = PyLong_FromLong(CODE); \
2548 assert(_PyObject_RealIsSubclass(PyExc_ ## TYPE, PyExc_OSError)); \
Victor Stinner281cce12020-06-23 22:55:46 +02002549 if (!_code || PyDict_SetItem(state->errnomap, _code, PyExc_ ## TYPE)) \
Victor Stinner331a6a52019-05-27 16:39:22 +02002550 return _PyStatus_ERR("errmap insertion problem."); \
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002551 Py_DECREF(_code); \
2552 } while (0)
2553
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002554 PRE_INIT(BaseException);
2555 PRE_INIT(Exception);
2556 PRE_INIT(TypeError);
2557 PRE_INIT(StopAsyncIteration);
2558 PRE_INIT(StopIteration);
2559 PRE_INIT(GeneratorExit);
2560 PRE_INIT(SystemExit);
2561 PRE_INIT(KeyboardInterrupt);
2562 PRE_INIT(ImportError);
2563 PRE_INIT(ModuleNotFoundError);
2564 PRE_INIT(OSError);
2565 PRE_INIT(EOFError);
2566 PRE_INIT(RuntimeError);
2567 PRE_INIT(RecursionError);
2568 PRE_INIT(NotImplementedError);
2569 PRE_INIT(NameError);
2570 PRE_INIT(UnboundLocalError);
2571 PRE_INIT(AttributeError);
2572 PRE_INIT(SyntaxError);
2573 PRE_INIT(IndentationError);
2574 PRE_INIT(TabError);
2575 PRE_INIT(LookupError);
2576 PRE_INIT(IndexError);
2577 PRE_INIT(KeyError);
2578 PRE_INIT(ValueError);
2579 PRE_INIT(UnicodeError);
2580 PRE_INIT(UnicodeEncodeError);
2581 PRE_INIT(UnicodeDecodeError);
2582 PRE_INIT(UnicodeTranslateError);
2583 PRE_INIT(AssertionError);
2584 PRE_INIT(ArithmeticError);
2585 PRE_INIT(FloatingPointError);
2586 PRE_INIT(OverflowError);
2587 PRE_INIT(ZeroDivisionError);
2588 PRE_INIT(SystemError);
2589 PRE_INIT(ReferenceError);
2590 PRE_INIT(MemoryError);
2591 PRE_INIT(BufferError);
2592 PRE_INIT(Warning);
2593 PRE_INIT(UserWarning);
2594 PRE_INIT(DeprecationWarning);
2595 PRE_INIT(PendingDeprecationWarning);
2596 PRE_INIT(SyntaxWarning);
2597 PRE_INIT(RuntimeWarning);
2598 PRE_INIT(FutureWarning);
2599 PRE_INIT(ImportWarning);
2600 PRE_INIT(UnicodeWarning);
2601 PRE_INIT(BytesWarning);
2602 PRE_INIT(ResourceWarning);
Thomas Wouters477c8d52006-05-27 19:21:47 +00002603
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02002604 /* OSError subclasses */
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002605 PRE_INIT(ConnectionError);
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02002606
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002607 PRE_INIT(BlockingIOError);
2608 PRE_INIT(BrokenPipeError);
2609 PRE_INIT(ChildProcessError);
2610 PRE_INIT(ConnectionAbortedError);
2611 PRE_INIT(ConnectionRefusedError);
2612 PRE_INIT(ConnectionResetError);
2613 PRE_INIT(FileExistsError);
2614 PRE_INIT(FileNotFoundError);
2615 PRE_INIT(IsADirectoryError);
2616 PRE_INIT(NotADirectoryError);
2617 PRE_INIT(InterruptedError);
2618 PRE_INIT(PermissionError);
2619 PRE_INIT(ProcessLookupError);
2620 PRE_INIT(TimeoutError);
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02002621
Victor Stinner6d43f6f2019-01-22 21:18:05 +01002622 if (preallocate_memerrors() < 0) {
Victor Stinner281cce12020-06-23 22:55:46 +02002623 return _PyStatus_NO_MEMORY();
Victor Stinner6d43f6f2019-01-22 21:18:05 +01002624 }
2625
2626 /* Add exceptions to errnomap */
Victor Stinner281cce12020-06-23 22:55:46 +02002627 assert(state->errnomap == NULL);
2628 state->errnomap = PyDict_New();
2629 if (!state->errnomap) {
2630 return _PyStatus_NO_MEMORY();
Victor Stinner6d43f6f2019-01-22 21:18:05 +01002631 }
2632
2633 ADD_ERRNO(BlockingIOError, EAGAIN);
2634 ADD_ERRNO(BlockingIOError, EALREADY);
2635 ADD_ERRNO(BlockingIOError, EINPROGRESS);
2636 ADD_ERRNO(BlockingIOError, EWOULDBLOCK);
2637 ADD_ERRNO(BrokenPipeError, EPIPE);
2638#ifdef ESHUTDOWN
2639 ADD_ERRNO(BrokenPipeError, ESHUTDOWN);
2640#endif
2641 ADD_ERRNO(ChildProcessError, ECHILD);
2642 ADD_ERRNO(ConnectionAbortedError, ECONNABORTED);
2643 ADD_ERRNO(ConnectionRefusedError, ECONNREFUSED);
2644 ADD_ERRNO(ConnectionResetError, ECONNRESET);
2645 ADD_ERRNO(FileExistsError, EEXIST);
2646 ADD_ERRNO(FileNotFoundError, ENOENT);
2647 ADD_ERRNO(IsADirectoryError, EISDIR);
2648 ADD_ERRNO(NotADirectoryError, ENOTDIR);
2649 ADD_ERRNO(InterruptedError, EINTR);
2650 ADD_ERRNO(PermissionError, EACCES);
2651 ADD_ERRNO(PermissionError, EPERM);
2652 ADD_ERRNO(ProcessLookupError, ESRCH);
2653 ADD_ERRNO(TimeoutError, ETIMEDOUT);
2654
Victor Stinner331a6a52019-05-27 16:39:22 +02002655 return _PyStatus_OK();
Victor Stinner6d43f6f2019-01-22 21:18:05 +01002656
2657#undef PRE_INIT
2658#undef ADD_ERRNO
2659}
2660
2661
2662/* Add exception types to the builtins module */
Victor Stinner331a6a52019-05-27 16:39:22 +02002663PyStatus
Victor Stinner6d43f6f2019-01-22 21:18:05 +01002664_PyBuiltins_AddExceptions(PyObject *bltinmod)
2665{
2666#define POST_INIT(TYPE) \
2667 if (PyDict_SetItemString(bdict, # TYPE, PyExc_ ## TYPE)) { \
Victor Stinner331a6a52019-05-27 16:39:22 +02002668 return _PyStatus_ERR("Module dictionary insertion problem."); \
Victor Stinner6d43f6f2019-01-22 21:18:05 +01002669 }
2670
2671#define INIT_ALIAS(NAME, TYPE) \
2672 do { \
2673 Py_INCREF(PyExc_ ## TYPE); \
2674 Py_XDECREF(PyExc_ ## NAME); \
2675 PyExc_ ## NAME = PyExc_ ## TYPE; \
2676 if (PyDict_SetItemString(bdict, # NAME, PyExc_ ## NAME)) { \
Victor Stinner331a6a52019-05-27 16:39:22 +02002677 return _PyStatus_ERR("Module dictionary insertion problem."); \
Victor Stinner6d43f6f2019-01-22 21:18:05 +01002678 } \
2679 } while (0)
2680
2681 PyObject *bdict;
2682
Thomas Wouters477c8d52006-05-27 19:21:47 +00002683 bdict = PyModule_GetDict(bltinmod);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002684 if (bdict == NULL) {
Victor Stinner331a6a52019-05-27 16:39:22 +02002685 return _PyStatus_ERR("exceptions bootstrapping error.");
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002686 }
Thomas Wouters477c8d52006-05-27 19:21:47 +00002687
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002688 POST_INIT(BaseException);
2689 POST_INIT(Exception);
2690 POST_INIT(TypeError);
2691 POST_INIT(StopAsyncIteration);
2692 POST_INIT(StopIteration);
2693 POST_INIT(GeneratorExit);
2694 POST_INIT(SystemExit);
2695 POST_INIT(KeyboardInterrupt);
2696 POST_INIT(ImportError);
2697 POST_INIT(ModuleNotFoundError);
2698 POST_INIT(OSError);
2699 INIT_ALIAS(EnvironmentError, OSError);
2700 INIT_ALIAS(IOError, OSError);
Thomas Wouters477c8d52006-05-27 19:21:47 +00002701#ifdef MS_WINDOWS
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002702 INIT_ALIAS(WindowsError, OSError);
Thomas Wouters477c8d52006-05-27 19:21:47 +00002703#endif
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002704 POST_INIT(EOFError);
2705 POST_INIT(RuntimeError);
2706 POST_INIT(RecursionError);
2707 POST_INIT(NotImplementedError);
2708 POST_INIT(NameError);
2709 POST_INIT(UnboundLocalError);
2710 POST_INIT(AttributeError);
2711 POST_INIT(SyntaxError);
2712 POST_INIT(IndentationError);
2713 POST_INIT(TabError);
2714 POST_INIT(LookupError);
2715 POST_INIT(IndexError);
2716 POST_INIT(KeyError);
2717 POST_INIT(ValueError);
2718 POST_INIT(UnicodeError);
2719 POST_INIT(UnicodeEncodeError);
2720 POST_INIT(UnicodeDecodeError);
2721 POST_INIT(UnicodeTranslateError);
2722 POST_INIT(AssertionError);
2723 POST_INIT(ArithmeticError);
2724 POST_INIT(FloatingPointError);
2725 POST_INIT(OverflowError);
2726 POST_INIT(ZeroDivisionError);
2727 POST_INIT(SystemError);
2728 POST_INIT(ReferenceError);
2729 POST_INIT(MemoryError);
2730 POST_INIT(BufferError);
2731 POST_INIT(Warning);
2732 POST_INIT(UserWarning);
2733 POST_INIT(DeprecationWarning);
2734 POST_INIT(PendingDeprecationWarning);
2735 POST_INIT(SyntaxWarning);
2736 POST_INIT(RuntimeWarning);
2737 POST_INIT(FutureWarning);
2738 POST_INIT(ImportWarning);
2739 POST_INIT(UnicodeWarning);
2740 POST_INIT(BytesWarning);
2741 POST_INIT(ResourceWarning);
Thomas Wouters477c8d52006-05-27 19:21:47 +00002742
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02002743 /* OSError subclasses */
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002744 POST_INIT(ConnectionError);
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02002745
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002746 POST_INIT(BlockingIOError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002747 POST_INIT(BrokenPipeError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002748 POST_INIT(ChildProcessError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002749 POST_INIT(ConnectionAbortedError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002750 POST_INIT(ConnectionRefusedError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002751 POST_INIT(ConnectionResetError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002752 POST_INIT(FileExistsError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002753 POST_INIT(FileNotFoundError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002754 POST_INIT(IsADirectoryError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002755 POST_INIT(NotADirectoryError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002756 POST_INIT(InterruptedError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002757 POST_INIT(PermissionError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002758 POST_INIT(ProcessLookupError);
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002759 POST_INIT(TimeoutError);
Antoine Pitrou6b4883d2011-10-12 02:54:14 +02002760
Victor Stinner331a6a52019-05-27 16:39:22 +02002761 return _PyStatus_OK();
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002762
Victor Stinnerbf4ac2d2019-01-22 17:39:03 +01002763#undef POST_INIT
2764#undef INIT_ALIAS
Thomas Wouters477c8d52006-05-27 19:21:47 +00002765}
2766
2767void
Victor Stinner281cce12020-06-23 22:55:46 +02002768_PyExc_Fini(PyThreadState *tstate)
Thomas Wouters477c8d52006-05-27 19:21:47 +00002769{
Victor Stinner281cce12020-06-23 22:55:46 +02002770 struct _Py_exc_state *state = &tstate->interp->exc_state;
2771 free_preallocated_memerrors(state);
2772 Py_CLEAR(state->errnomap);
Thomas Wouters477c8d52006-05-27 19:21:47 +00002773}
Nick Coghlan8b097b42013-11-13 23:49:21 +10002774
2775/* Helper to do the equivalent of "raise X from Y" in C, but always using
2776 * the current exception rather than passing one in.
2777 *
2778 * We currently limit this to *only* exceptions that use the BaseException
2779 * tp_init and tp_new methods, since we can be reasonably sure we can wrap
2780 * those correctly without losing data and without losing backwards
2781 * compatibility.
2782 *
2783 * We also aim to rule out *all* exceptions that might be storing additional
2784 * state, whether by having a size difference relative to BaseException,
2785 * additional arguments passed in during construction or by having a
2786 * non-empty instance dict.
2787 *
2788 * We need to be very careful with what we wrap, since changing types to
2789 * a broader exception type would be backwards incompatible for
2790 * existing codecs, and with different init or new method implementations
2791 * may either not support instantiation with PyErr_Format or lose
2792 * information when instantiated that way.
2793 *
2794 * XXX (ncoghlan): This could be made more comprehensive by exploiting the
2795 * fact that exceptions are expected to support pickling. If more builtin
2796 * exceptions (e.g. AttributeError) start to be converted to rich
2797 * exceptions with additional attributes, that's probably a better approach
2798 * to pursue over adding special cases for particular stateful subclasses.
2799 *
2800 * Returns a borrowed reference to the new exception (if any), NULL if the
2801 * existing exception was left in place.
2802 */
2803PyObject *
2804_PyErr_TrySetFromCause(const char *format, ...)
2805{
2806 PyObject* msg_prefix;
2807 PyObject *exc, *val, *tb;
2808 PyTypeObject *caught_type;
Christian Heimes6a3db252013-11-14 01:47:14 +01002809 PyObject **dictptr;
Nick Coghlan8b097b42013-11-13 23:49:21 +10002810 PyObject *instance_args;
Nick Coghlanf1de55f2013-11-19 22:33:10 +10002811 Py_ssize_t num_args, caught_type_size, base_exc_size;
Nick Coghlan8b097b42013-11-13 23:49:21 +10002812 PyObject *new_exc, *new_val, *new_tb;
2813 va_list vargs;
Nick Coghlanf1de55f2013-11-19 22:33:10 +10002814 int same_basic_size;
Nick Coghlan8b097b42013-11-13 23:49:21 +10002815
Nick Coghlan8b097b42013-11-13 23:49:21 +10002816 PyErr_Fetch(&exc, &val, &tb);
Benjamin Peterson079c9982013-11-13 23:25:01 -05002817 caught_type = (PyTypeObject *)exc;
Nick Coghlanf1de55f2013-11-19 22:33:10 +10002818 /* Ensure type info indicates no extra state is stored at the C level
2819 * and that the type can be reinstantiated using PyErr_Format
2820 */
2821 caught_type_size = caught_type->tp_basicsize;
2822 base_exc_size = _PyExc_BaseException.tp_basicsize;
2823 same_basic_size = (
2824 caught_type_size == base_exc_size ||
2825 (PyType_SUPPORTS_WEAKREFS(caught_type) &&
Victor Stinner12174a52014-08-15 23:17:38 +02002826 (caught_type_size == base_exc_size + (Py_ssize_t)sizeof(PyObject *))
Nick Coghlanf1de55f2013-11-19 22:33:10 +10002827 )
2828 );
Benjamin Peterson079c9982013-11-13 23:25:01 -05002829 if (caught_type->tp_init != (initproc)BaseException_init ||
Nick Coghlan8b097b42013-11-13 23:49:21 +10002830 caught_type->tp_new != BaseException_new ||
Nick Coghlanf1de55f2013-11-19 22:33:10 +10002831 !same_basic_size ||
Benjamin Peterson079c9982013-11-13 23:25:01 -05002832 caught_type->tp_itemsize != _PyExc_BaseException.tp_itemsize) {
Nick Coghlan8b097b42013-11-13 23:49:21 +10002833 /* We can't be sure we can wrap this safely, since it may contain
2834 * more state than just the exception type. Accordingly, we just
2835 * leave it alone.
2836 */
2837 PyErr_Restore(exc, val, tb);
2838 return NULL;
2839 }
2840
2841 /* Check the args are empty or contain a single string */
2842 PyErr_NormalizeException(&exc, &val, &tb);
Benjamin Peterson079c9982013-11-13 23:25:01 -05002843 instance_args = ((PyBaseExceptionObject *)val)->args;
Nick Coghlan8b097b42013-11-13 23:49:21 +10002844 num_args = PyTuple_GET_SIZE(instance_args);
Benjamin Peterson079c9982013-11-13 23:25:01 -05002845 if (num_args > 1 ||
Nick Coghlan8b097b42013-11-13 23:49:21 +10002846 (num_args == 1 &&
Benjamin Peterson079c9982013-11-13 23:25:01 -05002847 !PyUnicode_CheckExact(PyTuple_GET_ITEM(instance_args, 0)))) {
Nick Coghlan8b097b42013-11-13 23:49:21 +10002848 /* More than 1 arg, or the one arg we do have isn't a string
2849 */
2850 PyErr_Restore(exc, val, tb);
2851 return NULL;
2852 }
2853
2854 /* Ensure the instance dict is also empty */
Christian Heimes6a3db252013-11-14 01:47:14 +01002855 dictptr = _PyObject_GetDictPtr(val);
Benjamin Peterson079c9982013-11-13 23:25:01 -05002856 if (dictptr != NULL && *dictptr != NULL &&
Serhiy Storchakabf623ae2017-04-19 20:03:52 +03002857 PyDict_GET_SIZE(*dictptr) > 0) {
Nick Coghlan8b097b42013-11-13 23:49:21 +10002858 /* While we could potentially copy a non-empty instance dictionary
2859 * to the replacement exception, for now we take the more
2860 * conservative path of leaving exceptions with attributes set
2861 * alone.
2862 */
2863 PyErr_Restore(exc, val, tb);
2864 return NULL;
2865 }
2866
2867 /* For exceptions that we can wrap safely, we chain the original
2868 * exception to a new one of the exact same type with an
2869 * error message that mentions the additional details and the
2870 * original exception.
2871 *
2872 * It would be nice to wrap OSError and various other exception
2873 * types as well, but that's quite a bit trickier due to the extra
2874 * state potentially stored on OSError instances.
2875 */
Nick Coghlan77b286b2014-01-27 00:53:38 +10002876 /* Ensure the traceback is set correctly on the existing exception */
2877 if (tb != NULL) {
2878 PyException_SetTraceback(val, tb);
2879 Py_DECREF(tb);
2880 }
Benjamin Petersone109ee82013-11-13 23:49:49 -05002881
Christian Heimes507eabd2013-11-14 01:39:35 +01002882#ifdef HAVE_STDARG_PROTOTYPES
2883 va_start(vargs, format);
2884#else
2885 va_start(vargs);
2886#endif
Nick Coghlan8b097b42013-11-13 23:49:21 +10002887 msg_prefix = PyUnicode_FromFormatV(format, vargs);
Christian Heimes507eabd2013-11-14 01:39:35 +01002888 va_end(vargs);
Benjamin Petersone109ee82013-11-13 23:49:49 -05002889 if (msg_prefix == NULL) {
Nick Coghlan4b9b9362013-11-16 00:34:13 +10002890 Py_DECREF(exc);
Benjamin Petersone109ee82013-11-13 23:49:49 -05002891 Py_DECREF(val);
Nick Coghlan8b097b42013-11-13 23:49:21 +10002892 return NULL;
Benjamin Petersone109ee82013-11-13 23:49:49 -05002893 }
Nick Coghlan8b097b42013-11-13 23:49:21 +10002894
2895 PyErr_Format(exc, "%U (%s: %S)",
2896 msg_prefix, Py_TYPE(val)->tp_name, val);
Nick Coghlan4b9b9362013-11-16 00:34:13 +10002897 Py_DECREF(exc);
Benjamin Petersone109ee82013-11-13 23:49:49 -05002898 Py_DECREF(msg_prefix);
Nick Coghlan8b097b42013-11-13 23:49:21 +10002899 PyErr_Fetch(&new_exc, &new_val, &new_tb);
2900 PyErr_NormalizeException(&new_exc, &new_val, &new_tb);
2901 PyException_SetCause(new_val, val);
2902 PyErr_Restore(new_exc, new_val, new_tb);
2903 return new_val;
2904}
Nick Coghlan5b1fdc12014-06-16 19:48:02 +10002905
2906
2907/* To help with migration from Python 2, SyntaxError.__init__ applies some
2908 * heuristics to try to report a more meaningful exception when print and
2909 * exec are used like statements.
2910 *
2911 * The heuristics are currently expected to detect the following cases:
2912 * - top level statement
2913 * - statement in a nested suite
2914 * - trailing section of a one line complex statement
2915 *
2916 * They're currently known not to trigger:
2917 * - after a semi-colon
2918 *
2919 * The error message can be a bit odd in cases where the "arguments" are
2920 * completely illegal syntactically, but that isn't worth the hassle of
2921 * fixing.
2922 *
2923 * We also can't do anything about cases that are legal Python 3 syntax
2924 * but mean something entirely different from what they did in Python 2
2925 * (omitting the arguments entirely, printing items preceded by a unary plus
2926 * or minus, using the stream redirection syntax).
2927 */
2928
Sanyam Khurana3a7f0352017-06-20 19:01:32 +05302929
2930// Static helper for setting legacy print error message
2931static int
2932_set_legacy_print_statement_msg(PySyntaxErrorObject *self, Py_ssize_t start)
2933{
Nitish Chandra43c0f1a2018-01-28 16:26:02 +05302934 // PRINT_OFFSET is to remove the `print ` prefix from the data.
Sanyam Khurana3a7f0352017-06-20 19:01:32 +05302935 const int PRINT_OFFSET = 6;
Sanyam Khuranad57f26c2018-01-20 08:42:22 +05302936 const int STRIP_BOTH = 2;
Nitish Chandra43c0f1a2018-01-28 16:26:02 +05302937 Py_ssize_t start_pos = start + PRINT_OFFSET;
2938 Py_ssize_t text_len = PyUnicode_GET_LENGTH(self->text);
2939 Py_UCS4 semicolon = ';';
2940 Py_ssize_t end_pos = PyUnicode_FindChar(self->text, semicolon,
2941 start_pos, text_len, 1);
2942 if (end_pos < -1) {
2943 return -1;
2944 } else if (end_pos == -1) {
2945 end_pos = text_len;
Sanyam Khuranad57f26c2018-01-20 08:42:22 +05302946 }
Nitish Chandra43c0f1a2018-01-28 16:26:02 +05302947
2948 PyObject *data = PyUnicode_Substring(self->text, start_pos, end_pos);
Sanyam Khurana3a7f0352017-06-20 19:01:32 +05302949 if (data == NULL) {
Sanyam Khurana3a7f0352017-06-20 19:01:32 +05302950 return -1;
2951 }
Nitish Chandra43c0f1a2018-01-28 16:26:02 +05302952
2953 PyObject *strip_sep_obj = PyUnicode_FromString(" \t\r\n");
2954 if (strip_sep_obj == NULL) {
2955 Py_DECREF(data);
2956 return -1;
2957 }
2958
Sanyam Khuranad57f26c2018-01-20 08:42:22 +05302959 PyObject *new_data = _PyUnicode_XStrip(data, STRIP_BOTH, strip_sep_obj);
Sanyam Khurana3a7f0352017-06-20 19:01:32 +05302960 Py_DECREF(data);
2961 Py_DECREF(strip_sep_obj);
Sanyam Khurana3a7f0352017-06-20 19:01:32 +05302962 if (new_data == NULL) {
2963 return -1;
2964 }
2965 // gets the modified text_len after stripping `print `
2966 text_len = PyUnicode_GET_LENGTH(new_data);
2967 const char *maybe_end_arg = "";
2968 if (text_len > 0 && PyUnicode_READ_CHAR(new_data, text_len-1) == ',') {
2969 maybe_end_arg = " end=\" \"";
2970 }
2971 PyObject *error_msg = PyUnicode_FromFormat(
2972 "Missing parentheses in call to 'print'. Did you mean print(%U%s)?",
2973 new_data, maybe_end_arg
2974 );
2975 Py_DECREF(new_data);
2976 if (error_msg == NULL)
2977 return -1;
2978
2979 Py_XSETREF(self->msg, error_msg);
2980 return 1;
2981}
2982
Nick Coghlan5b1fdc12014-06-16 19:48:02 +10002983static int
2984_check_for_legacy_statements(PySyntaxErrorObject *self, Py_ssize_t start)
2985{
2986 /* Return values:
2987 * -1: an error occurred
2988 * 0: nothing happened
2989 * 1: the check triggered & the error message was changed
2990 */
2991 static PyObject *print_prefix = NULL;
2992 static PyObject *exec_prefix = NULL;
Zackery Spytza4b48f12018-10-12 02:20:59 -06002993 Py_ssize_t text_len = PyUnicode_GET_LENGTH(self->text), match;
Nick Coghlan5b1fdc12014-06-16 19:48:02 +10002994 int kind = PyUnicode_KIND(self->text);
Serhiy Storchakacd8295f2020-04-11 10:48:40 +03002995 const void *data = PyUnicode_DATA(self->text);
Nick Coghlan5b1fdc12014-06-16 19:48:02 +10002996
2997 /* Ignore leading whitespace */
2998 while (start < text_len) {
2999 Py_UCS4 ch = PyUnicode_READ(kind, data, start);
3000 if (!Py_UNICODE_ISSPACE(ch))
3001 break;
3002 start++;
3003 }
3004 /* Checking against an empty or whitespace-only part of the string */
3005 if (start == text_len) {
3006 return 0;
3007 }
3008
3009 /* Check for legacy print statements */
3010 if (print_prefix == NULL) {
3011 print_prefix = PyUnicode_InternFromString("print ");
3012 if (print_prefix == NULL) {
3013 return -1;
3014 }
3015 }
Zackery Spytza4b48f12018-10-12 02:20:59 -06003016 match = PyUnicode_Tailmatch(self->text, print_prefix,
3017 start, text_len, -1);
3018 if (match == -1) {
3019 return -1;
3020 }
3021 if (match) {
Sanyam Khurana3a7f0352017-06-20 19:01:32 +05303022 return _set_legacy_print_statement_msg(self, start);
Nick Coghlan5b1fdc12014-06-16 19:48:02 +10003023 }
3024
3025 /* Check for legacy exec statements */
3026 if (exec_prefix == NULL) {
3027 exec_prefix = PyUnicode_InternFromString("exec ");
3028 if (exec_prefix == NULL) {
3029 return -1;
3030 }
3031 }
Zackery Spytza4b48f12018-10-12 02:20:59 -06003032 match = PyUnicode_Tailmatch(self->text, exec_prefix, start, text_len, -1);
3033 if (match == -1) {
3034 return -1;
3035 }
3036 if (match) {
3037 PyObject *msg = PyUnicode_FromString("Missing parentheses in call "
3038 "to 'exec'");
3039 if (msg == NULL) {
3040 return -1;
3041 }
3042 Py_XSETREF(self->msg, msg);
Nick Coghlan5b1fdc12014-06-16 19:48:02 +10003043 return 1;
3044 }
3045 /* Fall back to the default error message */
3046 return 0;
3047}
3048
3049static int
3050_report_missing_parentheses(PySyntaxErrorObject *self)
3051{
3052 Py_UCS4 left_paren = 40;
3053 Py_ssize_t left_paren_index;
3054 Py_ssize_t text_len = PyUnicode_GET_LENGTH(self->text);
3055 int legacy_check_result = 0;
3056
3057 /* Skip entirely if there is an opening parenthesis */
3058 left_paren_index = PyUnicode_FindChar(self->text, left_paren,
3059 0, text_len, 1);
3060 if (left_paren_index < -1) {
3061 return -1;
3062 }
3063 if (left_paren_index != -1) {
3064 /* Use default error message for any line with an opening paren */
3065 return 0;
3066 }
3067 /* Handle the simple statement case */
3068 legacy_check_result = _check_for_legacy_statements(self, 0);
3069 if (legacy_check_result < 0) {
3070 return -1;
3071
3072 }
3073 if (legacy_check_result == 0) {
3074 /* Handle the one-line complex statement case */
3075 Py_UCS4 colon = 58;
3076 Py_ssize_t colon_index;
3077 colon_index = PyUnicode_FindChar(self->text, colon,
3078 0, text_len, 1);
3079 if (colon_index < -1) {
3080 return -1;
3081 }
3082 if (colon_index >= 0 && colon_index < text_len) {
3083 /* Check again, starting from just after the colon */
3084 if (_check_for_legacy_statements(self, colon_index+1) < 0) {
3085 return -1;
3086 }
3087 }
3088 }
3089 return 0;
3090}