blob: dcac57bda58811261d9f7403b18470f6e4f26a7e [file] [log] [blame]
Christian Heimes33fe8092008-04-13 13:53:33 +00001#include "Python.h"
2#include "frameobject.h"
3
4#define MODULE_NAME "_warnings"
Christian Heimes33fe8092008-04-13 13:53:33 +00005
6PyDoc_STRVAR(warnings__doc__,
7MODULE_NAME " provides basic warning filtering support.\n"
8"It is a helper module to speed up interpreter start-up.");
9
10/* Both 'filters' and 'onceregistry' can be set in warnings.py;
11 get_warnings_attr() will reset these variables accordingly. */
12static PyObject *_filters; /* List */
13static PyObject *_once_registry; /* Dict */
Brett Cannon0759dd62009-04-01 18:13:07 +000014static PyObject *_default_action; /* String */
Antoine Pitroucb0a0062014-09-18 02:40:46 +020015static long _filters_version;
Christian Heimes33fe8092008-04-13 13:53:33 +000016
Victor Stinnerbd303c12013-11-07 23:07:29 +010017_Py_IDENTIFIER(argv);
18_Py_IDENTIFIER(stderr);
Christian Heimes33fe8092008-04-13 13:53:33 +000019
20static int
21check_matched(PyObject *obj, PyObject *arg)
22{
23 PyObject *result;
Martin v. Löwisbd928fe2011-10-14 10:20:37 +020024 _Py_IDENTIFIER(match);
Christian Heimes33fe8092008-04-13 13:53:33 +000025 int rc;
26
27 if (obj == Py_None)
28 return 1;
Martin v. Löwisafe55bb2011-10-09 10:38:36 +020029 result = _PyObject_CallMethodId(obj, &PyId_match, "O", arg);
Christian Heimes33fe8092008-04-13 13:53:33 +000030 if (result == NULL)
31 return -1;
32
33 rc = PyObject_IsTrue(result);
34 Py_DECREF(result);
35 return rc;
36}
37
38/*
39 Returns a new reference.
40 A NULL return value can mean false or an error.
41*/
42static PyObject *
43get_warnings_attr(const char *attr)
44{
45 static PyObject *warnings_str = NULL;
46 PyObject *all_modules;
47 PyObject *warnings_module;
48 int result;
49
50 if (warnings_str == NULL) {
51 warnings_str = PyUnicode_InternFromString("warnings");
52 if (warnings_str == NULL)
53 return NULL;
54 }
55
56 all_modules = PyImport_GetModuleDict();
57 result = PyDict_Contains(all_modules, warnings_str);
58 if (result == -1 || result == 0)
59 return NULL;
60
61 warnings_module = PyDict_GetItem(all_modules, warnings_str);
62 if (!PyObject_HasAttrString(warnings_module, attr))
63 return NULL;
64 return PyObject_GetAttrString(warnings_module, attr);
65}
66
67
Neal Norwitz32dde222008-04-15 06:43:13 +000068static PyObject *
Christian Heimes33fe8092008-04-13 13:53:33 +000069get_once_registry(void)
70{
71 PyObject *registry;
72
73 registry = get_warnings_attr("onceregistry");
74 if (registry == NULL) {
75 if (PyErr_Occurred())
76 return NULL;
77 return _once_registry;
78 }
79 Py_DECREF(_once_registry);
80 _once_registry = registry;
81 return registry;
82}
83
84
Brett Cannon0759dd62009-04-01 18:13:07 +000085static PyObject *
86get_default_action(void)
87{
88 PyObject *default_action;
89
90 default_action = get_warnings_attr("defaultaction");
91 if (default_action == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000092 if (PyErr_Occurred()) {
93 return NULL;
94 }
95 return _default_action;
Brett Cannon0759dd62009-04-01 18:13:07 +000096 }
97
98 Py_DECREF(_default_action);
99 _default_action = default_action;
100 return default_action;
101}
102
103
Benjamin Petersondeff2b72015-05-03 11:23:37 -0400104/* The item is a new reference. */
Victor Stinnera4c704b2013-10-29 23:43:41 +0100105static PyObject*
Christian Heimes33fe8092008-04-13 13:53:33 +0000106get_filter(PyObject *category, PyObject *text, Py_ssize_t lineno,
107 PyObject *module, PyObject **item)
108{
Brett Cannon0759dd62009-04-01 18:13:07 +0000109 PyObject *action;
Christian Heimes33fe8092008-04-13 13:53:33 +0000110 Py_ssize_t i;
111 PyObject *warnings_filters;
112
113 warnings_filters = get_warnings_attr("filters");
114 if (warnings_filters == NULL) {
115 if (PyErr_Occurred())
116 return NULL;
117 }
118 else {
119 Py_DECREF(_filters);
120 _filters = warnings_filters;
121 }
122
Victor Stinner7d79b8b2010-05-19 20:40:50 +0000123 if (_filters == NULL || !PyList_Check(_filters)) {
Christian Heimes33fe8092008-04-13 13:53:33 +0000124 PyErr_SetString(PyExc_ValueError,
125 MODULE_NAME ".filters must be a list");
126 return NULL;
127 }
128
129 /* _filters could change while we are iterating over it. */
130 for (i = 0; i < PyList_GET_SIZE(_filters); i++) {
131 PyObject *tmp_item, *action, *msg, *cat, *mod, *ln_obj;
132 Py_ssize_t ln;
133 int is_subclass, good_msg, good_mod;
134
Benjamin Petersondeff2b72015-05-03 11:23:37 -0400135 tmp_item = PyList_GET_ITEM(_filters, i);
136 if (!PyTuple_Check(tmp_item) || PyTuple_GET_SIZE(tmp_item) != 5) {
Christian Heimes33fe8092008-04-13 13:53:33 +0000137 PyErr_Format(PyExc_ValueError,
138 MODULE_NAME ".filters item %zd isn't a 5-tuple", i);
139 return NULL;
140 }
141
142 /* Python code: action, msg, cat, mod, ln = item */
Benjamin Petersondeff2b72015-05-03 11:23:37 -0400143 Py_INCREF(tmp_item);
Christian Heimes33fe8092008-04-13 13:53:33 +0000144 action = PyTuple_GET_ITEM(tmp_item, 0);
145 msg = PyTuple_GET_ITEM(tmp_item, 1);
146 cat = PyTuple_GET_ITEM(tmp_item, 2);
147 mod = PyTuple_GET_ITEM(tmp_item, 3);
148 ln_obj = PyTuple_GET_ITEM(tmp_item, 4);
149
150 good_msg = check_matched(msg, text);
Benjamin Peterson8c598162015-05-03 11:28:46 -0400151 if (good_msg == -1) {
152 Py_DECREF(tmp_item);
Victor Stinner3cd04aa2013-10-31 14:46:00 +0100153 return NULL;
Benjamin Peterson8c598162015-05-03 11:28:46 -0400154 }
Victor Stinner3cd04aa2013-10-31 14:46:00 +0100155
Christian Heimes33fe8092008-04-13 13:53:33 +0000156 good_mod = check_matched(mod, module);
Benjamin Peterson8c598162015-05-03 11:28:46 -0400157 if (good_mod == -1) {
158 Py_DECREF(tmp_item);
Victor Stinner3cd04aa2013-10-31 14:46:00 +0100159 return NULL;
Benjamin Peterson8c598162015-05-03 11:28:46 -0400160 }
Victor Stinner3cd04aa2013-10-31 14:46:00 +0100161
Christian Heimes33fe8092008-04-13 13:53:33 +0000162 is_subclass = PyObject_IsSubclass(category, cat);
Benjamin Peterson8c598162015-05-03 11:28:46 -0400163 if (is_subclass == -1) {
164 Py_DECREF(tmp_item);
Victor Stinner3cd04aa2013-10-31 14:46:00 +0100165 return NULL;
Benjamin Peterson8c598162015-05-03 11:28:46 -0400166 }
Victor Stinner3cd04aa2013-10-31 14:46:00 +0100167
Christian Heimes33fe8092008-04-13 13:53:33 +0000168 ln = PyLong_AsSsize_t(ln_obj);
Benjamin Peterson8c598162015-05-03 11:28:46 -0400169 if (ln == -1 && PyErr_Occurred()) {
Benjamin Petersondeff2b72015-05-03 11:23:37 -0400170 Py_DECREF(tmp_item);
Christian Heimes33fe8092008-04-13 13:53:33 +0000171 return NULL;
Benjamin Petersondeff2b72015-05-03 11:23:37 -0400172 }
Christian Heimes33fe8092008-04-13 13:53:33 +0000173
Benjamin Petersondeff2b72015-05-03 11:23:37 -0400174 if (good_msg && is_subclass && good_mod && (ln == 0 || lineno == ln)) {
175 *item = tmp_item;
Victor Stinnera4c704b2013-10-29 23:43:41 +0100176 return action;
Benjamin Petersondeff2b72015-05-03 11:23:37 -0400177 }
178
179 Py_DECREF(tmp_item);
Christian Heimes33fe8092008-04-13 13:53:33 +0000180 }
181
Brett Cannon0759dd62009-04-01 18:13:07 +0000182 action = get_default_action();
183 if (action != NULL) {
Benjamin Petersondeff2b72015-05-03 11:23:37 -0400184 Py_INCREF(Py_None);
185 *item = Py_None;
Victor Stinnera4c704b2013-10-29 23:43:41 +0100186 return action;
Brett Cannon0759dd62009-04-01 18:13:07 +0000187 }
Christian Heimes33fe8092008-04-13 13:53:33 +0000188
189 PyErr_SetString(PyExc_ValueError,
Brett Cannon0759dd62009-04-01 18:13:07 +0000190 MODULE_NAME ".defaultaction not found");
Christian Heimes33fe8092008-04-13 13:53:33 +0000191 return NULL;
192}
193
Brett Cannon0759dd62009-04-01 18:13:07 +0000194
Christian Heimes33fe8092008-04-13 13:53:33 +0000195static int
196already_warned(PyObject *registry, PyObject *key, int should_set)
197{
Antoine Pitroucb0a0062014-09-18 02:40:46 +0200198 PyObject *version_obj, *already_warned;
199 _Py_IDENTIFIER(version);
Christian Heimes33fe8092008-04-13 13:53:33 +0000200
201 if (key == NULL)
202 return -1;
203
Antoine Pitroucb0a0062014-09-18 02:40:46 +0200204 version_obj = _PyDict_GetItemId(registry, &PyId_version);
205 if (version_obj == NULL
206 || !PyLong_CheckExact(version_obj)
207 || PyLong_AsLong(version_obj) != _filters_version) {
208 PyDict_Clear(registry);
209 version_obj = PyLong_FromLong(_filters_version);
210 if (version_obj == NULL)
211 return -1;
212 if (_PyDict_SetItemId(registry, &PyId_version, version_obj) < 0) {
213 Py_DECREF(version_obj);
214 return -1;
215 }
216 Py_DECREF(version_obj);
217 }
218 else {
219 already_warned = PyDict_GetItem(registry, key);
220 if (already_warned != NULL) {
221 int rc = PyObject_IsTrue(already_warned);
222 if (rc != 0)
223 return rc;
224 }
Christian Heimes33fe8092008-04-13 13:53:33 +0000225 }
226
227 /* This warning wasn't found in the registry, set it. */
228 if (should_set)
229 return PyDict_SetItem(registry, key, Py_True);
230 return 0;
231}
232
233/* New reference. */
234static PyObject *
235normalize_module(PyObject *filename)
236{
237 PyObject *module;
Victor Stinnera4c704b2013-10-29 23:43:41 +0100238 int kind;
239 void *data;
Christian Heimes33fe8092008-04-13 13:53:33 +0000240 Py_ssize_t len;
241
Victor Stinner9e30aa52011-11-21 02:49:52 +0100242 len = PyUnicode_GetLength(filename);
Christian Heimes33fe8092008-04-13 13:53:33 +0000243 if (len < 0)
244 return NULL;
Victor Stinnera4c704b2013-10-29 23:43:41 +0100245
246 if (len == 0)
247 return PyUnicode_FromString("<unknown>");
248
249 kind = PyUnicode_KIND(filename);
250 data = PyUnicode_DATA(filename);
251
252 /* if filename.endswith(".py"): */
Christian Heimes33fe8092008-04-13 13:53:33 +0000253 if (len >= 3 &&
Victor Stinnera4c704b2013-10-29 23:43:41 +0100254 PyUnicode_READ(kind, data, len-3) == '.' &&
255 PyUnicode_READ(kind, data, len-2) == 'p' &&
256 PyUnicode_READ(kind, data, len-1) == 'y')
257 {
Victor Stinner9e30aa52011-11-21 02:49:52 +0100258 module = PyUnicode_Substring(filename, 0, len-3);
Christian Heimes33fe8092008-04-13 13:53:33 +0000259 }
260 else {
261 module = filename;
262 Py_INCREF(module);
263 }
264 return module;
265}
266
267static int
268update_registry(PyObject *registry, PyObject *text, PyObject *category,
269 int add_zero)
270{
271 PyObject *altkey, *zero = NULL;
272 int rc;
273
274 if (add_zero) {
275 zero = PyLong_FromLong(0);
276 if (zero == NULL)
277 return -1;
278 altkey = PyTuple_Pack(3, text, category, zero);
279 }
280 else
281 altkey = PyTuple_Pack(2, text, category);
282
283 rc = already_warned(registry, altkey, 1);
284 Py_XDECREF(zero);
285 Py_XDECREF(altkey);
286 return rc;
287}
288
289static void
Victor Stinner914cde82016-03-19 01:03:51 +0100290show_warning(PyObject *filename, int lineno, PyObject *text,
291 PyObject *category, PyObject *sourceline)
Christian Heimes33fe8092008-04-13 13:53:33 +0000292{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000293 PyObject *f_stderr;
294 PyObject *name;
Christian Heimes33fe8092008-04-13 13:53:33 +0000295 char lineno_str[128];
Martin v. Löwisbd928fe2011-10-14 10:20:37 +0200296 _Py_IDENTIFIER(__name__);
Christian Heimes33fe8092008-04-13 13:53:33 +0000297
298 PyOS_snprintf(lineno_str, sizeof(lineno_str), ":%d: ", lineno);
299
Martin v. Löwis1ee1b6f2011-10-10 18:11:30 +0200300 name = _PyObject_GetAttrId(category, &PyId___name__);
Christian Heimes33fe8092008-04-13 13:53:33 +0000301 if (name == NULL) /* XXX Can an object lack a '__name__' attribute? */
Victor Stinnerae233ea2013-10-31 14:51:38 +0100302 goto error;
Christian Heimes33fe8092008-04-13 13:53:33 +0000303
Victor Stinnerbd303c12013-11-07 23:07:29 +0100304 f_stderr = _PySys_GetObjectId(&PyId_stderr);
Christian Heimes33fe8092008-04-13 13:53:33 +0000305 if (f_stderr == NULL) {
306 fprintf(stderr, "lost sys.stderr\n");
Victor Stinnerae233ea2013-10-31 14:51:38 +0100307 goto error;
Christian Heimes33fe8092008-04-13 13:53:33 +0000308 }
309
310 /* Print "filename:lineno: category: text\n" */
Victor Stinnerae233ea2013-10-31 14:51:38 +0100311 if (PyFile_WriteObject(filename, f_stderr, Py_PRINT_RAW) < 0)
312 goto error;
313 if (PyFile_WriteString(lineno_str, f_stderr) < 0)
314 goto error;
315 if (PyFile_WriteObject(name, f_stderr, Py_PRINT_RAW) < 0)
316 goto error;
317 if (PyFile_WriteString(": ", f_stderr) < 0)
318 goto error;
319 if (PyFile_WriteObject(text, f_stderr, Py_PRINT_RAW) < 0)
320 goto error;
321 if (PyFile_WriteString("\n", f_stderr) < 0)
322 goto error;
323 Py_CLEAR(name);
Christian Heimes33fe8092008-04-13 13:53:33 +0000324
325 /* Print " source_line\n" */
Christian Heimes33fe8092008-04-13 13:53:33 +0000326 if (sourceline) {
Victor Stinnera4c704b2013-10-29 23:43:41 +0100327 int kind;
328 void *data;
329 Py_ssize_t i, len;
330 Py_UCS4 ch;
331 PyObject *truncated;
Christian Heimes33fe8092008-04-13 13:53:33 +0000332
Victor Stinnera4c704b2013-10-29 23:43:41 +0100333 if (PyUnicode_READY(sourceline) < 1)
334 goto error;
335
336 kind = PyUnicode_KIND(sourceline);
337 data = PyUnicode_DATA(sourceline);
338 len = PyUnicode_GET_LENGTH(sourceline);
339 for (i=0; i<len; i++) {
340 ch = PyUnicode_READ(kind, data, i);
341 if (ch != ' ' && ch != '\t' && ch != '\014')
342 break;
343 }
344
345 truncated = PyUnicode_Substring(sourceline, i, len);
346 if (truncated == NULL)
347 goto error;
348
349 PyFile_WriteObject(sourceline, f_stderr, Py_PRINT_RAW);
350 Py_DECREF(truncated);
Christian Heimes33fe8092008-04-13 13:53:33 +0000351 PyFile_WriteString("\n", f_stderr);
352 }
Victor Stinner78e2c982013-07-16 01:54:37 +0200353 else {
354 _Py_DisplaySourceLine(f_stderr, filename, lineno, 2);
355 }
Victor Stinnera4c704b2013-10-29 23:43:41 +0100356
357error:
Victor Stinnerae233ea2013-10-31 14:51:38 +0100358 Py_XDECREF(name);
Christian Heimes33fe8092008-04-13 13:53:33 +0000359 PyErr_Clear();
360}
361
Victor Stinner1231a462016-03-19 00:47:17 +0100362static int
363call_show_warning(PyObject *category, PyObject *text, PyObject *message,
364 PyObject *filename, int lineno, PyObject *lineno_obj,
Victor Stinner914cde82016-03-19 01:03:51 +0100365 PyObject *sourceline, PyObject *source)
Victor Stinner1231a462016-03-19 00:47:17 +0100366{
367 PyObject *show_fn, *msg, *res, *warnmsg_cls = NULL;
368
369 show_fn = get_warnings_attr("_showwarnmsg");
370 if (show_fn == NULL) {
371 if (PyErr_Occurred())
372 return -1;
373 show_warning(filename, lineno, text, category, sourceline);
374 return 0;
375 }
376
377 if (!PyCallable_Check(show_fn)) {
378 PyErr_SetString(PyExc_TypeError,
379 "warnings._showwarnmsg() must be set to a callable");
380 goto error;
381 }
382
383 warnmsg_cls = get_warnings_attr("WarningMessage");
384 if (warnmsg_cls == NULL) {
385 PyErr_SetString(PyExc_RuntimeError,
386 "unable to get warnings.WarningMessage");
387 goto error;
388 }
389
390 msg = PyObject_CallFunctionObjArgs(warnmsg_cls, message, category,
Victor Stinner914cde82016-03-19 01:03:51 +0100391 filename, lineno_obj, Py_None, Py_None, source,
Victor Stinner1231a462016-03-19 00:47:17 +0100392 NULL);
393 Py_DECREF(warnmsg_cls);
394 if (msg == NULL)
395 goto error;
396
397 res = PyObject_CallFunctionObjArgs(show_fn, msg, NULL);
398 Py_DECREF(show_fn);
399 Py_DECREF(msg);
400
401 if (res == NULL)
402 return -1;
403
404 Py_DECREF(res);
405 return 0;
406
407error:
408 Py_XDECREF(show_fn);
409 return -1;
410}
411
Christian Heimes33fe8092008-04-13 13:53:33 +0000412static PyObject *
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000413warn_explicit(PyObject *category, PyObject *message,
Christian Heimes33fe8092008-04-13 13:53:33 +0000414 PyObject *filename, int lineno,
Victor Stinner914cde82016-03-19 01:03:51 +0100415 PyObject *module, PyObject *registry, PyObject *sourceline,
416 PyObject *source)
Christian Heimes33fe8092008-04-13 13:53:33 +0000417{
418 PyObject *key = NULL, *text = NULL, *result = NULL, *lineno_obj = NULL;
Benjamin Petersondeff2b72015-05-03 11:23:37 -0400419 PyObject *item = NULL;
Victor Stinnera4c704b2013-10-29 23:43:41 +0100420 PyObject *action;
Christian Heimes33fe8092008-04-13 13:53:33 +0000421 int rc;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000422
Victor Stinnerdcdd05b2013-11-01 00:55:30 +0100423 /* module can be None if a warning is emitted late during Python shutdown.
424 In this case, the Python warnings module was probably unloaded, filters
425 are no more available to choose as action. It is safer to ignore the
426 warning and do nothing. */
427 if (module == Py_None)
428 Py_RETURN_NONE;
429
Brett Cannondb734912008-06-27 00:52:15 +0000430 if (registry && !PyDict_Check(registry) && (registry != Py_None)) {
431 PyErr_SetString(PyExc_TypeError, "'registry' must be a dict");
432 return NULL;
433 }
Christian Heimes33fe8092008-04-13 13:53:33 +0000434
435 /* Normalize module. */
436 if (module == NULL) {
437 module = normalize_module(filename);
438 if (module == NULL)
439 return NULL;
440 }
441 else
442 Py_INCREF(module);
443
444 /* Normalize message. */
445 Py_INCREF(message); /* DECREF'ed in cleanup. */
446 rc = PyObject_IsInstance(message, PyExc_Warning);
447 if (rc == -1) {
448 goto cleanup;
449 }
450 if (rc == 1) {
451 text = PyObject_Str(message);
Hirokazu Yamamoto1c0c0032009-07-17 06:55:42 +0000452 if (text == NULL)
453 goto cleanup;
Christian Heimes33fe8092008-04-13 13:53:33 +0000454 category = (PyObject*)message->ob_type;
455 }
456 else {
457 text = message;
458 message = PyObject_CallFunction(category, "O", message);
Brett Cannondb734912008-06-27 00:52:15 +0000459 if (message == NULL)
460 goto cleanup;
Christian Heimes33fe8092008-04-13 13:53:33 +0000461 }
462
463 lineno_obj = PyLong_FromLong(lineno);
464 if (lineno_obj == NULL)
465 goto cleanup;
466
467 /* Create key. */
468 key = PyTuple_Pack(3, text, category, lineno_obj);
469 if (key == NULL)
470 goto cleanup;
471
Brett Cannondb734912008-06-27 00:52:15 +0000472 if ((registry != NULL) && (registry != Py_None)) {
Christian Heimes33fe8092008-04-13 13:53:33 +0000473 rc = already_warned(registry, key, 0);
474 if (rc == -1)
475 goto cleanup;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000476 else if (rc == 1)
Christian Heimes33fe8092008-04-13 13:53:33 +0000477 goto return_none;
478 /* Else this warning hasn't been generated before. */
479 }
480
481 action = get_filter(category, text, lineno, module, &item);
482 if (action == NULL)
483 goto cleanup;
484
Victor Stinnera4c704b2013-10-29 23:43:41 +0100485 if (PyUnicode_CompareWithASCIIString(action, "error") == 0) {
Christian Heimes33fe8092008-04-13 13:53:33 +0000486 PyErr_SetObject(category, message);
487 goto cleanup;
488 }
489
490 /* Store in the registry that we've been here, *except* when the action
491 is "always". */
492 rc = 0;
Victor Stinnera4c704b2013-10-29 23:43:41 +0100493 if (PyUnicode_CompareWithASCIIString(action, "always") != 0) {
Brett Cannondb734912008-06-27 00:52:15 +0000494 if (registry != NULL && registry != Py_None &&
495 PyDict_SetItem(registry, key, Py_True) < 0)
Christian Heimes33fe8092008-04-13 13:53:33 +0000496 goto cleanup;
Victor Stinnera4c704b2013-10-29 23:43:41 +0100497 else if (PyUnicode_CompareWithASCIIString(action, "ignore") == 0)
Christian Heimes33fe8092008-04-13 13:53:33 +0000498 goto return_none;
Victor Stinnera4c704b2013-10-29 23:43:41 +0100499 else if (PyUnicode_CompareWithASCIIString(action, "once") == 0) {
Brett Cannondb734912008-06-27 00:52:15 +0000500 if (registry == NULL || registry == Py_None) {
Christian Heimes33fe8092008-04-13 13:53:33 +0000501 registry = get_once_registry();
502 if (registry == NULL)
503 goto cleanup;
504 }
505 /* _once_registry[(text, category)] = 1 */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000506 rc = update_registry(registry, text, category, 0);
Christian Heimes33fe8092008-04-13 13:53:33 +0000507 }
Victor Stinnera4c704b2013-10-29 23:43:41 +0100508 else if (PyUnicode_CompareWithASCIIString(action, "module") == 0) {
Christian Heimes33fe8092008-04-13 13:53:33 +0000509 /* registry[(text, category, 0)] = 1 */
Brett Cannondb734912008-06-27 00:52:15 +0000510 if (registry != NULL && registry != Py_None)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000511 rc = update_registry(registry, text, category, 0);
Christian Heimes33fe8092008-04-13 13:53:33 +0000512 }
Victor Stinnera4c704b2013-10-29 23:43:41 +0100513 else if (PyUnicode_CompareWithASCIIString(action, "default") != 0) {
Christian Heimes33fe8092008-04-13 13:53:33 +0000514 PyErr_Format(PyExc_RuntimeError,
Victor Stinnera4c704b2013-10-29 23:43:41 +0100515 "Unrecognized action (%R) in warnings.filters:\n %R",
516 action, item);
Christian Heimes33fe8092008-04-13 13:53:33 +0000517 goto cleanup;
518 }
519 }
520
Christian Heimes1a8501c2008-10-02 19:56:01 +0000521 if (rc == 1) /* Already warned for this module. */
Christian Heimes33fe8092008-04-13 13:53:33 +0000522 goto return_none;
523 if (rc == 0) {
Victor Stinner1231a462016-03-19 00:47:17 +0100524 if (call_show_warning(category, text, message, filename, lineno,
Victor Stinner914cde82016-03-19 01:03:51 +0100525 lineno_obj, sourceline, source) < 0)
Victor Stinner1231a462016-03-19 00:47:17 +0100526 goto cleanup;
Christian Heimes33fe8092008-04-13 13:53:33 +0000527 }
528 else /* if (rc == -1) */
529 goto cleanup;
530
531 return_none:
532 result = Py_None;
533 Py_INCREF(result);
534
535 cleanup:
Benjamin Petersondeff2b72015-05-03 11:23:37 -0400536 Py_XDECREF(item);
Christian Heimes33fe8092008-04-13 13:53:33 +0000537 Py_XDECREF(key);
538 Py_XDECREF(text);
539 Py_XDECREF(lineno_obj);
540 Py_DECREF(module);
Brett Cannondb734912008-06-27 00:52:15 +0000541 Py_XDECREF(message);
Christian Heimes33fe8092008-04-13 13:53:33 +0000542 return result; /* Py_None or NULL. */
543}
544
Larry Hastings714e4932015-09-06 00:39:37 -0700545static int
546is_internal_frame(PyFrameObject *frame)
547{
548 static PyObject *importlib_string = NULL;
549 static PyObject *bootstrap_string = NULL;
550 PyObject *filename;
551 int contains;
552
553 if (importlib_string == NULL) {
554 importlib_string = PyUnicode_FromString("importlib");
555 if (importlib_string == NULL) {
556 return 0;
557 }
558
559 bootstrap_string = PyUnicode_FromString("_bootstrap");
560 if (bootstrap_string == NULL) {
561 Py_DECREF(importlib_string);
562 return 0;
563 }
564 Py_INCREF(importlib_string);
565 Py_INCREF(bootstrap_string);
566 }
567
568 if (frame == NULL || frame->f_code == NULL ||
569 frame->f_code->co_filename == NULL) {
570 return 0;
571 }
572 filename = frame->f_code->co_filename;
573 if (!PyUnicode_Check(filename)) {
574 return 0;
575 }
576 contains = PyUnicode_Contains(filename, importlib_string);
577 if (contains < 0) {
578 return 0;
579 }
580 else if (contains > 0) {
581 contains = PyUnicode_Contains(filename, bootstrap_string);
582 if (contains < 0) {
583 return 0;
584 }
585 else if (contains > 0) {
586 return 1;
587 }
588 }
589
590 return 0;
591}
592
593static PyFrameObject *
594next_external_frame(PyFrameObject *frame)
595{
596 do {
597 frame = frame->f_back;
598 } while (frame != NULL && is_internal_frame(frame));
599
600 return frame;
601}
602
Christian Heimes33fe8092008-04-13 13:53:33 +0000603/* filename, module, and registry are new refs, globals is borrowed */
604/* Returns 0 on error (no new refs), 1 on success */
605static int
606setup_context(Py_ssize_t stack_level, PyObject **filename, int *lineno,
607 PyObject **module, PyObject **registry)
608{
609 PyObject *globals;
610
611 /* Setup globals and lineno. */
612 PyFrameObject *f = PyThreadState_GET()->frame;
Larry Hastings714e4932015-09-06 00:39:37 -0700613 // Stack level comparisons to Python code is off by one as there is no
614 // warnings-related stack level to avoid.
615 if (stack_level <= 0 || is_internal_frame(f)) {
616 while (--stack_level > 0 && f != NULL) {
617 f = f->f_back;
618 }
619 }
620 else {
621 while (--stack_level > 0 && f != NULL) {
622 f = next_external_frame(f);
623 }
624 }
Christian Heimes33fe8092008-04-13 13:53:33 +0000625
626 if (f == NULL) {
627 globals = PyThreadState_Get()->interp->sysdict;
628 *lineno = 1;
629 }
630 else {
631 globals = f->f_globals;
Alexandre Vassalotti7b82b402009-07-21 04:30:03 +0000632 *lineno = PyFrame_GetLineNumber(f);
Christian Heimes33fe8092008-04-13 13:53:33 +0000633 }
634
635 *module = NULL;
636
637 /* Setup registry. */
638 assert(globals != NULL);
639 assert(PyDict_Check(globals));
640 *registry = PyDict_GetItemString(globals, "__warningregistry__");
641 if (*registry == NULL) {
642 int rc;
643
644 *registry = PyDict_New();
645 if (*registry == NULL)
646 return 0;
647
648 rc = PyDict_SetItemString(globals, "__warningregistry__", *registry);
649 if (rc < 0)
650 goto handle_error;
651 }
652 else
653 Py_INCREF(*registry);
654
655 /* Setup module. */
656 *module = PyDict_GetItemString(globals, "__name__");
657 if (*module == NULL) {
658 *module = PyUnicode_FromString("<string>");
659 if (*module == NULL)
660 goto handle_error;
661 }
662 else
663 Py_INCREF(*module);
664
665 /* Setup filename. */
666 *filename = PyDict_GetItemString(globals, "__file__");
Victor Stinner8b0508e2011-07-04 02:43:09 +0200667 if (*filename != NULL && PyUnicode_Check(*filename)) {
Victor Stinnerb62a7b22011-10-06 02:34:51 +0200668 Py_ssize_t len;
669 int kind;
670 void *data;
671
672 if (PyUnicode_READY(*filename))
673 goto handle_error;
674
Victor Stinner9e30aa52011-11-21 02:49:52 +0100675 len = PyUnicode_GetLength(*filename);
Victor Stinnerb62a7b22011-10-06 02:34:51 +0200676 kind = PyUnicode_KIND(*filename);
677 data = PyUnicode_DATA(*filename);
Christian Heimes33fe8092008-04-13 13:53:33 +0000678
Benjamin Peterson21e0da22012-01-11 21:00:42 -0500679#define ascii_lower(c) ((c <= 127) ? Py_TOLOWER(c) : 0)
Brett Cannonf299abd2015-04-13 14:21:02 -0400680 /* if filename.lower().endswith(".pyc"): */
Christian Heimes33fe8092008-04-13 13:53:33 +0000681 if (len >= 4 &&
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200682 PyUnicode_READ(kind, data, len-4) == '.' &&
Benjamin Peterson21e0da22012-01-11 21:00:42 -0500683 ascii_lower(PyUnicode_READ(kind, data, len-3)) == 'p' &&
684 ascii_lower(PyUnicode_READ(kind, data, len-2)) == 'y' &&
Brett Cannonf299abd2015-04-13 14:21:02 -0400685 ascii_lower(PyUnicode_READ(kind, data, len-1)) == 'c')
Christian Heimes81ee3ef2008-05-04 22:42:01 +0000686 {
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200687 *filename = PyUnicode_Substring(*filename, 0,
688 PyUnicode_GET_LENGTH(*filename)-1);
Victor Stinner2e5f1172010-08-08 22:12:45 +0000689 if (*filename == NULL)
690 goto handle_error;
691 }
692 else
Christian Heimes33fe8092008-04-13 13:53:33 +0000693 Py_INCREF(*filename);
694 }
695 else {
Benjamin Petersonbb4a7472011-07-04 22:27:16 -0500696 *filename = NULL;
Victor Stinner856f45f2013-10-30 00:04:59 +0100697 if (*module != Py_None && PyUnicode_CompareWithASCIIString(*module, "__main__") == 0) {
Victor Stinnerbd303c12013-11-07 23:07:29 +0100698 PyObject *argv = _PySys_GetObjectId(&PyId_argv);
Victor Stinnerce5f4fb2013-10-28 18:47:22 +0100699 /* PyList_Check() is needed because sys.argv is set to None during
700 Python finalization */
701 if (argv != NULL && PyList_Check(argv) && PyList_Size(argv) > 0) {
Christian Heimes81ee3ef2008-05-04 22:42:01 +0000702 int is_true;
Christian Heimes33fe8092008-04-13 13:53:33 +0000703 *filename = PyList_GetItem(argv, 0);
704 Py_INCREF(*filename);
Christian Heimes81ee3ef2008-05-04 22:42:01 +0000705 /* If sys.argv[0] is false, then use '__main__'. */
706 is_true = PyObject_IsTrue(*filename);
707 if (is_true < 0) {
708 Py_DECREF(*filename);
709 goto handle_error;
710 }
711 else if (!is_true) {
Serhiy Storchaka5a57ade2015-12-24 10:35:59 +0200712 Py_SETREF(*filename, PyUnicode_FromString("__main__"));
Christian Heimes81ee3ef2008-05-04 22:42:01 +0000713 if (*filename == NULL)
714 goto handle_error;
715 }
Christian Heimes33fe8092008-04-13 13:53:33 +0000716 }
717 else {
718 /* embedded interpreters don't have sys.argv, see bug #839151 */
719 *filename = PyUnicode_FromString("__main__");
Victor Stinner856f45f2013-10-30 00:04:59 +0100720 if (*filename == NULL)
721 goto handle_error;
Christian Heimes33fe8092008-04-13 13:53:33 +0000722 }
723 }
724 if (*filename == NULL) {
725 *filename = *module;
726 Py_INCREF(*filename);
727 }
728 }
729
730 return 1;
731
732 handle_error:
733 /* filename not XDECREF'ed here as there is no way to jump here with a
734 dangling reference. */
735 Py_XDECREF(*registry);
736 Py_XDECREF(*module);
737 return 0;
738}
739
740static PyObject *
741get_category(PyObject *message, PyObject *category)
742{
743 int rc;
744
745 /* Get category. */
746 rc = PyObject_IsInstance(message, PyExc_Warning);
747 if (rc == -1)
748 return NULL;
749
750 if (rc == 1)
751 category = (PyObject*)message->ob_type;
Berker Peksagd8089e02014-07-11 19:50:25 +0300752 else if (category == NULL || category == Py_None)
Christian Heimes33fe8092008-04-13 13:53:33 +0000753 category = PyExc_UserWarning;
754
755 /* Validate category. */
756 rc = PyObject_IsSubclass(category, PyExc_Warning);
Berker Peksagd8089e02014-07-11 19:50:25 +0300757 /* category is not a subclass of PyExc_Warning or
758 PyObject_IsSubclass raised an error */
759 if (rc == -1 || rc == 0) {
760 PyErr_Format(PyExc_TypeError,
761 "category must be a Warning subclass, not '%s'",
762 Py_TYPE(category)->tp_name);
Christian Heimes33fe8092008-04-13 13:53:33 +0000763 return NULL;
764 }
765
766 return category;
767}
768
769static PyObject *
Victor Stinner914cde82016-03-19 01:03:51 +0100770do_warn(PyObject *message, PyObject *category, Py_ssize_t stack_level,
771 PyObject *source)
Christian Heimes33fe8092008-04-13 13:53:33 +0000772{
773 PyObject *filename, *module, *registry, *res;
774 int lineno;
775
776 if (!setup_context(stack_level, &filename, &lineno, &module, &registry))
777 return NULL;
778
Victor Stinnerdcdd05b2013-11-01 00:55:30 +0100779 res = warn_explicit(category, message, filename, lineno, module, registry,
Victor Stinner914cde82016-03-19 01:03:51 +0100780 NULL, source);
Christian Heimes33fe8092008-04-13 13:53:33 +0000781 Py_DECREF(filename);
782 Py_DECREF(registry);
783 Py_DECREF(module);
784 return res;
785}
786
787static PyObject *
788warnings_warn(PyObject *self, PyObject *args, PyObject *kwds)
789{
Victor Stinnere19558a2016-03-23 00:28:08 +0100790 static char *kw_list[] = {"message", "category", "stacklevel",
791 "source", NULL};
792 PyObject *message, *category = NULL, *source = NULL;
Christian Heimes33fe8092008-04-13 13:53:33 +0000793 Py_ssize_t stack_level = 1;
794
Victor Stinnere19558a2016-03-23 00:28:08 +0100795 if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|OnO:warn", kw_list,
796 &message, &category, &stack_level, &source))
Christian Heimes33fe8092008-04-13 13:53:33 +0000797 return NULL;
798
799 category = get_category(message, category);
800 if (category == NULL)
801 return NULL;
Victor Stinnere19558a2016-03-23 00:28:08 +0100802 return do_warn(message, category, stack_level, source);
Christian Heimes33fe8092008-04-13 13:53:33 +0000803}
804
805static PyObject *
806warnings_warn_explicit(PyObject *self, PyObject *args, PyObject *kwds)
807{
808 static char *kwd_list[] = {"message", "category", "filename", "lineno",
Victor Stinner914cde82016-03-19 01:03:51 +0100809 "module", "registry", "module_globals",
810 "source", 0};
Christian Heimes33fe8092008-04-13 13:53:33 +0000811 PyObject *message;
812 PyObject *category;
813 PyObject *filename;
814 int lineno;
815 PyObject *module = NULL;
816 PyObject *registry = NULL;
817 PyObject *module_globals = NULL;
Victor Stinner914cde82016-03-19 01:03:51 +0100818 PyObject *sourceobj = NULL;
Christian Heimes33fe8092008-04-13 13:53:33 +0000819
Victor Stinner914cde82016-03-19 01:03:51 +0100820 if (!PyArg_ParseTupleAndKeywords(args, kwds, "OOUi|OOOO:warn_explicit",
Christian Heimes33fe8092008-04-13 13:53:33 +0000821 kwd_list, &message, &category, &filename, &lineno, &module,
Victor Stinner914cde82016-03-19 01:03:51 +0100822 &registry, &module_globals, &sourceobj))
Christian Heimes33fe8092008-04-13 13:53:33 +0000823 return NULL;
824
825 if (module_globals) {
Martin v. Löwis1c67dd92011-10-14 15:16:45 +0200826 _Py_IDENTIFIER(get_source);
827 _Py_IDENTIFIER(splitlines);
828 PyObject *tmp;
Christian Heimes33fe8092008-04-13 13:53:33 +0000829 PyObject *loader;
830 PyObject *module_name;
831 PyObject *source;
832 PyObject *source_list;
833 PyObject *source_line;
834 PyObject *returned;
835
Martin v. Löwis1c67dd92011-10-14 15:16:45 +0200836 if ((tmp = _PyUnicode_FromId(&PyId_get_source)) == NULL)
837 return NULL;
Martin v. Löwis1c67dd92011-10-14 15:16:45 +0200838 if ((tmp = _PyUnicode_FromId(&PyId_splitlines)) == NULL)
839 return NULL;
Christian Heimes33fe8092008-04-13 13:53:33 +0000840
841 /* Check/get the requisite pieces needed for the loader. */
842 loader = PyDict_GetItemString(module_globals, "__loader__");
843 module_name = PyDict_GetItemString(module_globals, "__name__");
844
845 if (loader == NULL || module_name == NULL)
846 goto standard_call;
847
848 /* Make sure the loader implements the optional get_source() method. */
Martin v. Löwis1c67dd92011-10-14 15:16:45 +0200849 if (!_PyObject_HasAttrId(loader, &PyId_get_source))
Christian Heimes33fe8092008-04-13 13:53:33 +0000850 goto standard_call;
851 /* Call get_source() to get the source code. */
Martin v. Löwis1c67dd92011-10-14 15:16:45 +0200852 source = PyObject_CallMethodObjArgs(loader, PyId_get_source.object,
853 module_name, NULL);
Christian Heimes33fe8092008-04-13 13:53:33 +0000854 if (!source)
855 return NULL;
856 else if (source == Py_None) {
857 Py_DECREF(Py_None);
858 goto standard_call;
859 }
860
861 /* Split the source into lines. */
Victor Stinner9e30aa52011-11-21 02:49:52 +0100862 source_list = PyObject_CallMethodObjArgs(source,
Martin v. Löwis1c67dd92011-10-14 15:16:45 +0200863 PyId_splitlines.object,
864 NULL);
Christian Heimes33fe8092008-04-13 13:53:33 +0000865 Py_DECREF(source);
866 if (!source_list)
867 return NULL;
868
869 /* Get the source line. */
870 source_line = PyList_GetItem(source_list, lineno-1);
871 if (!source_line) {
872 Py_DECREF(source_list);
873 return NULL;
874 }
875
876 /* Handle the warning. */
877 returned = warn_explicit(category, message, filename, lineno, module,
Victor Stinner914cde82016-03-19 01:03:51 +0100878 registry, source_line, sourceobj);
Christian Heimes33fe8092008-04-13 13:53:33 +0000879 Py_DECREF(source_list);
880 return returned;
881 }
882
883 standard_call:
884 return warn_explicit(category, message, filename, lineno, module,
Victor Stinner914cde82016-03-19 01:03:51 +0100885 registry, NULL, sourceobj);
Christian Heimes33fe8092008-04-13 13:53:33 +0000886}
887
Antoine Pitroucb0a0062014-09-18 02:40:46 +0200888static PyObject *
889warnings_filters_mutated(PyObject *self, PyObject *args)
890{
891 _filters_version++;
892 Py_RETURN_NONE;
893}
894
Christian Heimes33fe8092008-04-13 13:53:33 +0000895
896/* Function to issue a warning message; may raise an exception. */
Victor Stinner4a2b7a12010-08-13 14:03:48 +0000897
898static int
899warn_unicode(PyObject *category, PyObject *message,
Victor Stinner914cde82016-03-19 01:03:51 +0100900 Py_ssize_t stack_level, PyObject *source)
Christian Heimes33fe8092008-04-13 13:53:33 +0000901{
902 PyObject *res;
Christian Heimes33fe8092008-04-13 13:53:33 +0000903
904 if (category == NULL)
905 category = PyExc_RuntimeWarning;
906
Victor Stinner914cde82016-03-19 01:03:51 +0100907 res = do_warn(message, category, stack_level, source);
Christian Heimes33fe8092008-04-13 13:53:33 +0000908 if (res == NULL)
909 return -1;
910 Py_DECREF(res);
911
912 return 0;
913}
914
Victor Stinner914cde82016-03-19 01:03:51 +0100915static int
916_PyErr_WarnFormatV(PyObject *source,
917 PyObject *category, Py_ssize_t stack_level,
918 const char *format, va_list vargs)
919{
920 PyObject *message;
921 int res;
922
923 message = PyUnicode_FromFormatV(format, vargs);
924 if (message == NULL)
925 return -1;
926
927 res = warn_unicode(category, message, stack_level, source);
928 Py_DECREF(message);
929 return res;
930}
931
Victor Stinner4a2b7a12010-08-13 14:03:48 +0000932int
933PyErr_WarnFormat(PyObject *category, Py_ssize_t stack_level,
934 const char *format, ...)
935{
Victor Stinner914cde82016-03-19 01:03:51 +0100936 int res;
Victor Stinner4a2b7a12010-08-13 14:03:48 +0000937 va_list vargs;
938
939#ifdef HAVE_STDARG_PROTOTYPES
940 va_start(vargs, format);
941#else
942 va_start(vargs);
943#endif
Victor Stinner914cde82016-03-19 01:03:51 +0100944 res = _PyErr_WarnFormatV(NULL, category, stack_level, format, vargs);
Victor Stinner4a2b7a12010-08-13 14:03:48 +0000945 va_end(vargs);
Victor Stinner914cde82016-03-19 01:03:51 +0100946 return res;
Victor Stinner4a2b7a12010-08-13 14:03:48 +0000947}
948
949int
Victor Stinner914cde82016-03-19 01:03:51 +0100950PyErr_ResourceWarning(PyObject *source, Py_ssize_t stack_level,
951 const char *format, ...)
952{
953 int res;
954 va_list vargs;
955
956#ifdef HAVE_STDARG_PROTOTYPES
957 va_start(vargs, format);
958#else
959 va_start(vargs);
960#endif
961 res = _PyErr_WarnFormatV(source, PyExc_ResourceWarning,
962 stack_level, format, vargs);
963 va_end(vargs);
964 return res;
965}
966
967
968int
Victor Stinner4a2b7a12010-08-13 14:03:48 +0000969PyErr_WarnEx(PyObject *category, const char *text, Py_ssize_t stack_level)
970{
971 int ret;
972 PyObject *message = PyUnicode_FromString(text);
973 if (message == NULL)
974 return -1;
Victor Stinner914cde82016-03-19 01:03:51 +0100975 ret = warn_unicode(category, message, stack_level, NULL);
Victor Stinner4a2b7a12010-08-13 14:03:48 +0000976 Py_DECREF(message);
977 return ret;
978}
979
Ezio Melotti42da6632011-03-15 05:18:48 +0200980/* PyErr_Warn is only for backwards compatibility and will be removed.
Christian Heimes33fe8092008-04-13 13:53:33 +0000981 Use PyErr_WarnEx instead. */
982
983#undef PyErr_Warn
984
985PyAPI_FUNC(int)
Serhiy Storchakaef1585e2015-12-25 20:01:53 +0200986PyErr_Warn(PyObject *category, const char *text)
Christian Heimes33fe8092008-04-13 13:53:33 +0000987{
988 return PyErr_WarnEx(category, text, 1);
989}
990
991/* Warning with explicit origin */
992int
Victor Stinner14e461d2013-08-26 22:28:21 +0200993PyErr_WarnExplicitObject(PyObject *category, PyObject *message,
994 PyObject *filename, int lineno,
995 PyObject *module, PyObject *registry)
996{
997 PyObject *res;
998 if (category == NULL)
999 category = PyExc_RuntimeWarning;
1000 res = warn_explicit(category, message, filename, lineno,
Victor Stinner914cde82016-03-19 01:03:51 +01001001 module, registry, NULL, NULL);
Victor Stinner14e461d2013-08-26 22:28:21 +02001002 if (res == NULL)
1003 return -1;
1004 Py_DECREF(res);
1005 return 0;
1006}
1007
1008int
Christian Heimes33fe8092008-04-13 13:53:33 +00001009PyErr_WarnExplicit(PyObject *category, const char *text,
1010 const char *filename_str, int lineno,
1011 const char *module_str, PyObject *registry)
1012{
Christian Heimes33fe8092008-04-13 13:53:33 +00001013 PyObject *message = PyUnicode_FromString(text);
Victor Stinnercb428f02010-12-27 20:10:36 +00001014 PyObject *filename = PyUnicode_DecodeFSDefault(filename_str);
Christian Heimes33fe8092008-04-13 13:53:33 +00001015 PyObject *module = NULL;
1016 int ret = -1;
1017
1018 if (message == NULL || filename == NULL)
1019 goto exit;
1020 if (module_str != NULL) {
1021 module = PyUnicode_FromString(module_str);
Antoine Pitrou070cb3c2013-05-08 13:23:25 +02001022 if (module == NULL)
1023 goto exit;
Christian Heimes33fe8092008-04-13 13:53:33 +00001024 }
1025
Victor Stinner14e461d2013-08-26 22:28:21 +02001026 ret = PyErr_WarnExplicitObject(category, message, filename, lineno,
1027 module, registry);
Christian Heimes33fe8092008-04-13 13:53:33 +00001028
1029 exit:
1030 Py_XDECREF(message);
1031 Py_XDECREF(module);
1032 Py_XDECREF(filename);
1033 return ret;
1034}
1035
Antoine Pitrou070cb3c2013-05-08 13:23:25 +02001036int
1037PyErr_WarnExplicitFormat(PyObject *category,
1038 const char *filename_str, int lineno,
1039 const char *module_str, PyObject *registry,
1040 const char *format, ...)
1041{
1042 PyObject *message;
1043 PyObject *module = NULL;
1044 PyObject *filename = PyUnicode_DecodeFSDefault(filename_str);
1045 int ret = -1;
1046 va_list vargs;
1047
1048 if (filename == NULL)
1049 goto exit;
1050 if (module_str != NULL) {
1051 module = PyUnicode_FromString(module_str);
1052 if (module == NULL)
1053 goto exit;
1054 }
1055
1056#ifdef HAVE_STDARG_PROTOTYPES
1057 va_start(vargs, format);
1058#else
1059 va_start(vargs);
1060#endif
1061 message = PyUnicode_FromFormatV(format, vargs);
1062 if (message != NULL) {
1063 PyObject *res;
1064 res = warn_explicit(category, message, filename, lineno,
Victor Stinner914cde82016-03-19 01:03:51 +01001065 module, registry, NULL, NULL);
Antoine Pitrou070cb3c2013-05-08 13:23:25 +02001066 Py_DECREF(message);
1067 if (res != NULL) {
1068 Py_DECREF(res);
1069 ret = 0;
1070 }
1071 }
1072 va_end(vargs);
1073exit:
1074 Py_XDECREF(module);
1075 Py_XDECREF(filename);
1076 return ret;
1077}
1078
Christian Heimes33fe8092008-04-13 13:53:33 +00001079
1080PyDoc_STRVAR(warn_doc,
1081"Issue a warning, or maybe ignore it or raise an exception.");
1082
1083PyDoc_STRVAR(warn_explicit_doc,
1084"Low-level inferface to warnings functionality.");
1085
1086static PyMethodDef warnings_functions[] = {
1087 {"warn", (PyCFunction)warnings_warn, METH_VARARGS | METH_KEYWORDS,
1088 warn_doc},
1089 {"warn_explicit", (PyCFunction)warnings_warn_explicit,
1090 METH_VARARGS | METH_KEYWORDS, warn_explicit_doc},
Antoine Pitroucb0a0062014-09-18 02:40:46 +02001091 {"_filters_mutated", (PyCFunction)warnings_filters_mutated, METH_NOARGS,
1092 NULL},
Christian Heimes1a8501c2008-10-02 19:56:01 +00001093 /* XXX(brett.cannon): add showwarning? */
1094 /* XXX(brett.cannon): Reasonable to add formatwarning? */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001095 {NULL, NULL} /* sentinel */
Christian Heimes33fe8092008-04-13 13:53:33 +00001096};
1097
1098
1099static PyObject *
1100create_filter(PyObject *category, const char *action)
1101{
1102 static PyObject *ignore_str = NULL;
1103 static PyObject *error_str = NULL;
1104 static PyObject *default_str = NULL;
Georg Brandl08be72d2010-10-24 15:11:22 +00001105 static PyObject *always_str = NULL;
Christian Heimes33fe8092008-04-13 13:53:33 +00001106 PyObject *action_obj = NULL;
1107 PyObject *lineno, *result;
1108
1109 if (!strcmp(action, "ignore")) {
1110 if (ignore_str == NULL) {
1111 ignore_str = PyUnicode_InternFromString("ignore");
1112 if (ignore_str == NULL)
1113 return NULL;
1114 }
1115 action_obj = ignore_str;
1116 }
1117 else if (!strcmp(action, "error")) {
1118 if (error_str == NULL) {
1119 error_str = PyUnicode_InternFromString("error");
1120 if (error_str == NULL)
1121 return NULL;
1122 }
1123 action_obj = error_str;
1124 }
1125 else if (!strcmp(action, "default")) {
1126 if (default_str == NULL) {
1127 default_str = PyUnicode_InternFromString("default");
1128 if (default_str == NULL)
1129 return NULL;
1130 }
1131 action_obj = default_str;
1132 }
Georg Brandl08be72d2010-10-24 15:11:22 +00001133 else if (!strcmp(action, "always")) {
1134 if (always_str == NULL) {
1135 always_str = PyUnicode_InternFromString("always");
1136 if (always_str == NULL)
1137 return NULL;
1138 }
1139 action_obj = always_str;
1140 }
Christian Heimes33fe8092008-04-13 13:53:33 +00001141 else {
1142 Py_FatalError("unknown action");
1143 }
1144
1145 /* This assumes the line number is zero for now. */
1146 lineno = PyLong_FromLong(0);
1147 if (lineno == NULL)
1148 return NULL;
1149 result = PyTuple_Pack(5, action_obj, Py_None, category, Py_None, lineno);
1150 Py_DECREF(lineno);
1151 return result;
1152}
1153
1154static PyObject *
1155init_filters(void)
1156{
Georg Brandl08be72d2010-10-24 15:11:22 +00001157 PyObject *filters = PyList_New(5);
Benjamin Peterson7ab4b8d2010-06-28 00:01:59 +00001158 unsigned int pos = 0; /* Post-incremented in each use. */
1159 unsigned int x;
Georg Brandl08be72d2010-10-24 15:11:22 +00001160 const char *bytes_action, *resource_action;
Benjamin Peterson7ab4b8d2010-06-28 00:01:59 +00001161
Christian Heimes33fe8092008-04-13 13:53:33 +00001162 if (filters == NULL)
1163 return NULL;
1164
Benjamin Peterson7ab4b8d2010-06-28 00:01:59 +00001165 PyList_SET_ITEM(filters, pos++,
1166 create_filter(PyExc_DeprecationWarning, "ignore"));
1167 PyList_SET_ITEM(filters, pos++,
Christian Heimes33fe8092008-04-13 13:53:33 +00001168 create_filter(PyExc_PendingDeprecationWarning, "ignore"));
Benjamin Peterson7ab4b8d2010-06-28 00:01:59 +00001169 PyList_SET_ITEM(filters, pos++,
1170 create_filter(PyExc_ImportWarning, "ignore"));
Christian Heimes33fe8092008-04-13 13:53:33 +00001171 if (Py_BytesWarningFlag > 1)
1172 bytes_action = "error";
1173 else if (Py_BytesWarningFlag)
1174 bytes_action = "default";
1175 else
1176 bytes_action = "ignore";
Benjamin Peterson7ab4b8d2010-06-28 00:01:59 +00001177 PyList_SET_ITEM(filters, pos++, create_filter(PyExc_BytesWarning,
Christian Heimes33fe8092008-04-13 13:53:33 +00001178 bytes_action));
Georg Brandl08be72d2010-10-24 15:11:22 +00001179 /* resource usage warnings are enabled by default in pydebug mode */
1180#ifdef Py_DEBUG
1181 resource_action = "always";
1182#else
1183 resource_action = "ignore";
1184#endif
1185 PyList_SET_ITEM(filters, pos++, create_filter(PyExc_ResourceWarning,
1186 resource_action));
Benjamin Peterson7ab4b8d2010-06-28 00:01:59 +00001187 for (x = 0; x < pos; x += 1) {
1188 if (PyList_GET_ITEM(filters, x) == NULL) {
1189 Py_DECREF(filters);
1190 return NULL;
1191 }
Christian Heimes33fe8092008-04-13 13:53:33 +00001192 }
1193
1194 return filters;
1195}
1196
Martin v. Löwis1a214512008-06-11 05:26:20 +00001197static struct PyModuleDef warningsmodule = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001198 PyModuleDef_HEAD_INIT,
1199 MODULE_NAME,
1200 warnings__doc__,
1201 0,
1202 warnings_functions,
1203 NULL,
1204 NULL,
1205 NULL,
1206 NULL
Martin v. Löwis1a214512008-06-11 05:26:20 +00001207};
1208
Christian Heimes33fe8092008-04-13 13:53:33 +00001209
1210PyMODINIT_FUNC
1211_PyWarnings_Init(void)
1212{
Brett Cannon0759dd62009-04-01 18:13:07 +00001213 PyObject *m;
Christian Heimes33fe8092008-04-13 13:53:33 +00001214
Martin v. Löwis1a214512008-06-11 05:26:20 +00001215 m = PyModule_Create(&warningsmodule);
Christian Heimes33fe8092008-04-13 13:53:33 +00001216 if (m == NULL)
Martin v. Löwis1a214512008-06-11 05:26:20 +00001217 return NULL;
Christian Heimes33fe8092008-04-13 13:53:33 +00001218
Antoine Pitrouaa5c5c62012-01-18 21:45:15 +01001219 if (_filters == NULL) {
1220 _filters = init_filters();
1221 if (_filters == NULL)
1222 return NULL;
1223 }
Christian Heimes33fe8092008-04-13 13:53:33 +00001224 Py_INCREF(_filters);
1225 if (PyModule_AddObject(m, "filters", _filters) < 0)
Martin v. Löwis1a214512008-06-11 05:26:20 +00001226 return NULL;
Christian Heimes33fe8092008-04-13 13:53:33 +00001227
Antoine Pitrouaa5c5c62012-01-18 21:45:15 +01001228 if (_once_registry == NULL) {
1229 _once_registry = PyDict_New();
1230 if (_once_registry == NULL)
1231 return NULL;
1232 }
Christian Heimes33fe8092008-04-13 13:53:33 +00001233 Py_INCREF(_once_registry);
Brett Cannonef0e6c32010-09-04 18:24:04 +00001234 if (PyModule_AddObject(m, "_onceregistry", _once_registry) < 0)
Martin v. Löwis1a214512008-06-11 05:26:20 +00001235 return NULL;
Christian Heimes33fe8092008-04-13 13:53:33 +00001236
Antoine Pitrouaa5c5c62012-01-18 21:45:15 +01001237 if (_default_action == NULL) {
1238 _default_action = PyUnicode_FromString("default");
1239 if (_default_action == NULL)
1240 return NULL;
1241 }
1242 Py_INCREF(_default_action);
Brett Cannonef0e6c32010-09-04 18:24:04 +00001243 if (PyModule_AddObject(m, "_defaultaction", _default_action) < 0)
Martin v. Löwis1a214512008-06-11 05:26:20 +00001244 return NULL;
Antoine Pitroucb0a0062014-09-18 02:40:46 +02001245
1246 _filters_version = 0;
Martin v. Löwis1a214512008-06-11 05:26:20 +00001247 return m;
Christian Heimes33fe8092008-04-13 13:53:33 +00001248}