comparison cos/python/Python/errors.c @ 27:7f74363f4c82

Added some files for the python port
author windel
date Tue, 27 Dec 2011 18:59:02 +0100
parents
children
comparison
equal deleted inserted replaced
26:dcce92b1efbc 27:7f74363f4c82
1
2 /* Error handling */
3
4 #include "Python.h"
5
6 #ifndef __STDC__
7 #ifndef MS_WINDOWS
8 extern char *strerror(int);
9 #endif
10 #endif
11
12 #ifdef MS_WINDOWS
13 #include <windows.h>
14 #include <winbase.h>
15 #endif
16
17 #include <ctype.h>
18
19 #ifdef __cplusplus
20 extern "C" {
21 #endif
22
23
24 void
25 PyErr_Restore(PyObject *type, PyObject *value, PyObject *traceback)
26 {
27 PyThreadState *tstate = PyThreadState_GET();
28 PyObject *oldtype, *oldvalue, *oldtraceback;
29
30 if (traceback != NULL && !PyTraceBack_Check(traceback)) {
31 /* XXX Should never happen -- fatal error instead? */
32 /* Well, it could be None. */
33 Py_DECREF(traceback);
34 traceback = NULL;
35 }
36
37 /* Save these in locals to safeguard against recursive
38 invocation through Py_XDECREF */
39 oldtype = tstate->curexc_type;
40 oldvalue = tstate->curexc_value;
41 oldtraceback = tstate->curexc_traceback;
42
43 tstate->curexc_type = type;
44 tstate->curexc_value = value;
45 tstate->curexc_traceback = traceback;
46
47 Py_XDECREF(oldtype);
48 Py_XDECREF(oldvalue);
49 Py_XDECREF(oldtraceback);
50 }
51
52 void
53 PyErr_SetObject(PyObject *exception, PyObject *value)
54 {
55 PyThreadState *tstate = PyThreadState_GET();
56 PyObject *exc_value;
57 PyObject *tb = NULL;
58
59 if (exception != NULL &&
60 !PyExceptionClass_Check(exception)) {
61 PyErr_Format(PyExc_SystemError,
62 "exception %R not a BaseException subclass",
63 exception);
64 return;
65 }
66 Py_XINCREF(value);
67 exc_value = tstate->exc_value;
68 if (exc_value != NULL && exc_value != Py_None) {
69 /* Implicit exception chaining */
70 Py_INCREF(exc_value);
71 if (value == NULL || !PyExceptionInstance_Check(value)) {
72 /* We must normalize the value right now */
73 PyObject *args, *fixed_value;
74 if (value == NULL || value == Py_None)
75 args = PyTuple_New(0);
76 else if (PyTuple_Check(value)) {
77 Py_INCREF(value);
78 args = value;
79 }
80 else
81 args = PyTuple_Pack(1, value);
82 fixed_value = args ?
83 PyEval_CallObject(exception, args) : NULL;
84 Py_XDECREF(args);
85 Py_XDECREF(value);
86 if (fixed_value == NULL)
87 return;
88 value = fixed_value;
89 }
90 /* Avoid reference cycles through the context chain.
91 This is O(chain length) but context chains are
92 usually very short. Sensitive readers may try
93 to inline the call to PyException_GetContext. */
94 if (exc_value != value) {
95 PyObject *o = exc_value, *context;
96 while ((context = PyException_GetContext(o))) {
97 Py_DECREF(context);
98 if (context == value) {
99 PyException_SetContext(o, NULL);
100 break;
101 }
102 o = context;
103 }
104 PyException_SetContext(value, exc_value);
105 } else {
106 Py_DECREF(exc_value);
107 }
108 }
109 if (value != NULL && PyExceptionInstance_Check(value))
110 tb = PyException_GetTraceback(value);
111 Py_XINCREF(exception);
112 PyErr_Restore(exception, value, tb);
113 }
114
115 void
116 PyErr_SetNone(PyObject *exception)
117 {
118 PyErr_SetObject(exception, (PyObject *)NULL);
119 }
120
121 void
122 PyErr_SetString(PyObject *exception, const char *string)
123 {
124 PyObject *value = PyUnicode_FromString(string);
125 PyErr_SetObject(exception, value);
126 Py_XDECREF(value);
127 }
128
129
130 PyObject *
131 PyErr_Occurred(void)
132 {
133 /* If there is no thread state, PyThreadState_GET calls
134 Py_FatalError, which calls PyErr_Occurred. To avoid the
135 resulting infinite loop, we inline PyThreadState_GET here and
136 treat no thread as no error. */
137 PyThreadState *tstate =
138 ((PyThreadState*)_Py_atomic_load_relaxed(&_PyThreadState_Current));
139
140 return tstate == NULL ? NULL : tstate->curexc_type;
141 }
142
143
144 int
145 PyErr_GivenExceptionMatches(PyObject *err, PyObject *exc)
146 {
147 if (err == NULL || exc == NULL) {
148 /* maybe caused by "import exceptions" that failed early on */
149 return 0;
150 }
151 if (PyTuple_Check(exc)) {
152 Py_ssize_t i, n;
153 n = PyTuple_Size(exc);
154 for (i = 0; i < n; i++) {
155 /* Test recursively */
156 if (PyErr_GivenExceptionMatches(
157 err, PyTuple_GET_ITEM(exc, i)))
158 {
159 return 1;
160 }
161 }
162 return 0;
163 }
164 /* err might be an instance, so check its class. */
165 if (PyExceptionInstance_Check(err))
166 err = PyExceptionInstance_Class(err);
167
168 if (PyExceptionClass_Check(err) && PyExceptionClass_Check(exc)) {
169 int res = 0;
170 PyObject *exception, *value, *tb;
171 PyErr_Fetch(&exception, &value, &tb);
172 /* PyObject_IsSubclass() can recurse and therefore is
173 not safe (see test_bad_getattr in test.pickletester). */
174 res = PyType_IsSubtype((PyTypeObject *)err, (PyTypeObject *)exc);
175 /* This function must not fail, so print the error here */
176 if (res == -1) {
177 PyErr_WriteUnraisable(err);
178 res = 0;
179 }
180 PyErr_Restore(exception, value, tb);
181 return res;
182 }
183
184 return err == exc;
185 }
186
187
188 int
189 PyErr_ExceptionMatches(PyObject *exc)
190 {
191 return PyErr_GivenExceptionMatches(PyErr_Occurred(), exc);
192 }
193
194
195 /* Used in many places to normalize a raised exception, including in
196 eval_code2(), do_raise(), and PyErr_Print()
197
198 XXX: should PyErr_NormalizeException() also call
199 PyException_SetTraceback() with the resulting value and tb?
200 */
201 void
202 PyErr_NormalizeException(PyObject **exc, PyObject **val, PyObject **tb)
203 {
204 PyObject *type = *exc;
205 PyObject *value = *val;
206 PyObject *inclass = NULL;
207 PyObject *initial_tb = NULL;
208 PyThreadState *tstate = NULL;
209
210 if (type == NULL) {
211 /* There was no exception, so nothing to do. */
212 return;
213 }
214
215 /* If PyErr_SetNone() was used, the value will have been actually
216 set to NULL.
217 */
218 if (!value) {
219 value = Py_None;
220 Py_INCREF(value);
221 }
222
223 if (PyExceptionInstance_Check(value))
224 inclass = PyExceptionInstance_Class(value);
225
226 /* Normalize the exception so that if the type is a class, the
227 value will be an instance.
228 */
229 if (PyExceptionClass_Check(type)) {
230 /* if the value was not an instance, or is not an instance
231 whose class is (or is derived from) type, then use the
232 value as an argument to instantiation of the type
233 class.
234 */
235 if (!inclass || !PyObject_IsSubclass(inclass, type)) {
236 PyObject *args, *res;
237
238 if (value == Py_None)
239 args = PyTuple_New(0);
240 else if (PyTuple_Check(value)) {
241 Py_INCREF(value);
242 args = value;
243 }
244 else
245 args = PyTuple_Pack(1, value);
246
247 if (args == NULL)
248 goto finally;
249 res = PyEval_CallObject(type, args);
250 Py_DECREF(args);
251 if (res == NULL)
252 goto finally;
253 Py_DECREF(value);
254 value = res;
255 }
256 /* if the class of the instance doesn't exactly match the
257 class of the type, believe the instance
258 */
259 else if (inclass != type) {
260 Py_DECREF(type);
261 type = inclass;
262 Py_INCREF(type);
263 }
264 }
265 *exc = type;
266 *val = value;
267 return;
268 finally:
269 Py_DECREF(type);
270 Py_DECREF(value);
271 /* If the new exception doesn't set a traceback and the old
272 exception had a traceback, use the old traceback for the
273 new exception. It's better than nothing.
274 */
275 initial_tb = *tb;
276 PyErr_Fetch(exc, val, tb);
277 if (initial_tb != NULL) {
278 if (*tb == NULL)
279 *tb = initial_tb;
280 else
281 Py_DECREF(initial_tb);
282 }
283 /* normalize recursively */
284 tstate = PyThreadState_GET();
285 if (++tstate->recursion_depth > Py_GetRecursionLimit()) {
286 --tstate->recursion_depth;
287 /* throw away the old exception... */
288 Py_DECREF(*exc);
289 Py_DECREF(*val);
290 /* ... and use the recursion error instead */
291 *exc = PyExc_RuntimeError;
292 *val = PyExc_RecursionErrorInst;
293 Py_INCREF(*exc);
294 Py_INCREF(*val);
295 /* just keeping the old traceback */
296 return;
297 }
298 PyErr_NormalizeException(exc, val, tb);
299 --tstate->recursion_depth;
300 }
301
302
303 void
304 PyErr_Fetch(PyObject **p_type, PyObject **p_value, PyObject **p_traceback)
305 {
306 PyThreadState *tstate = PyThreadState_GET();
307
308 *p_type = tstate->curexc_type;
309 *p_value = tstate->curexc_value;
310 *p_traceback = tstate->curexc_traceback;
311
312 tstate->curexc_type = NULL;
313 tstate->curexc_value = NULL;
314 tstate->curexc_traceback = NULL;
315 }
316
317 void
318 PyErr_Clear(void)
319 {
320 PyErr_Restore(NULL, NULL, NULL);
321 }
322
323 /* Convenience functions to set a type error exception and return 0 */
324
325 int
326 PyErr_BadArgument(void)
327 {
328 PyErr_SetString(PyExc_TypeError,
329 "bad argument type for built-in operation");
330 return 0;
331 }
332
333 PyObject *
334 PyErr_NoMemory(void)
335 {
336 PyErr_SetNone(PyExc_MemoryError);
337 return NULL;
338 }
339
340 PyObject *
341 PyErr_SetFromErrnoWithFilenameObject(PyObject *exc, PyObject *filenameObject)
342 {
343 PyObject *message;
344 PyObject *v, *args;
345 int i = errno;
346 #ifdef MS_WINDOWS
347 WCHAR *s_buf = NULL;
348 #endif /* Unix/Windows */
349
350 #ifdef EINTR
351 if (i == EINTR && PyErr_CheckSignals())
352 return NULL;
353 #endif
354
355 #ifndef MS_WINDOWS
356 if (i != 0) {
357 char *s = strerror(i);
358 message = PyUnicode_DecodeLocale(s, "surrogateescape");
359 }
360 else {
361 /* Sometimes errno didn't get set */
362 message = PyUnicode_FromString("Error");
363 }
364 #else
365 if (i == 0)
366 message = PyUnicode_FromString("Error"); /* Sometimes errno didn't get set */
367 else
368 {
369 /* Note that the Win32 errors do not lineup with the
370 errno error. So if the error is in the MSVC error
371 table, we use it, otherwise we assume it really _is_
372 a Win32 error code
373 */
374 if (i > 0 && i < _sys_nerr) {
375 message = PyUnicode_FromString(_sys_errlist[i]);
376 }
377 else {
378 int len = FormatMessageW(
379 FORMAT_MESSAGE_ALLOCATE_BUFFER |
380 FORMAT_MESSAGE_FROM_SYSTEM |
381 FORMAT_MESSAGE_IGNORE_INSERTS,
382 NULL, /* no message source */
383 i,
384 MAKELANGID(LANG_NEUTRAL,
385 SUBLANG_DEFAULT),
386 /* Default language */
387 (LPWSTR) &s_buf,
388 0, /* size not used */
389 NULL); /* no args */
390 if (len==0) {
391 /* Only ever seen this in out-of-mem
392 situations */
393 s_buf = NULL;
394 message = PyUnicode_FromFormat("Windows Error 0x%X", i);
395 } else {
396 /* remove trailing cr/lf and dots */
397 while (len > 0 && (s_buf[len-1] <= L' ' || s_buf[len-1] == L'.'))
398 s_buf[--len] = L'\0';
399 message = PyUnicode_FromWideChar(s_buf, len);
400 }
401 }
402 }
403 #endif /* Unix/Windows */
404
405 if (message == NULL)
406 {
407 #ifdef MS_WINDOWS
408 LocalFree(s_buf);
409 #endif
410 return NULL;
411 }
412
413 if (filenameObject != NULL)
414 args = Py_BuildValue("(iOO)", i, message, filenameObject);
415 else
416 args = Py_BuildValue("(iO)", i, message);
417 Py_DECREF(message);
418
419 if (args != NULL) {
420 v = PyObject_Call(exc, args, NULL);
421 Py_DECREF(args);
422 if (v != NULL) {
423 PyErr_SetObject((PyObject *) Py_TYPE(v), v);
424 Py_DECREF(v);
425 }
426 }
427 #ifdef MS_WINDOWS
428 LocalFree(s_buf);
429 #endif
430 return NULL;
431 }
432
433
434 PyObject *
435 PyErr_SetFromErrnoWithFilename(PyObject *exc, const char *filename)
436 {
437 PyObject *name = filename ? PyUnicode_DecodeFSDefault(filename) : NULL;
438 PyObject *result = PyErr_SetFromErrnoWithFilenameObject(exc, name);
439 Py_XDECREF(name);
440 return result;
441 }
442
443 #ifdef MS_WINDOWS
444 PyObject *
445 PyErr_SetFromErrnoWithUnicodeFilename(PyObject *exc, const Py_UNICODE *filename)
446 {
447 PyObject *name = filename ?
448 PyUnicode_FromUnicode(filename, wcslen(filename)) :
449 NULL;
450 PyObject *result = PyErr_SetFromErrnoWithFilenameObject(exc, name);
451 Py_XDECREF(name);
452 return result;
453 }
454 #endif /* MS_WINDOWS */
455
456 PyObject *
457 PyErr_SetFromErrno(PyObject *exc)
458 {
459 return PyErr_SetFromErrnoWithFilenameObject(exc, NULL);
460 }
461
462 #ifdef MS_WINDOWS
463 /* Windows specific error code handling */
464 PyObject *PyErr_SetExcFromWindowsErrWithFilenameObject(
465 PyObject *exc,
466 int ierr,
467 PyObject *filenameObject)
468 {
469 int len;
470 WCHAR *s_buf = NULL; /* Free via LocalFree */
471 PyObject *message;
472 PyObject *args, *v;
473 DWORD err = (DWORD)ierr;
474 if (err==0) err = GetLastError();
475 len = FormatMessageW(
476 /* Error API error */
477 FORMAT_MESSAGE_ALLOCATE_BUFFER |
478 FORMAT_MESSAGE_FROM_SYSTEM |
479 FORMAT_MESSAGE_IGNORE_INSERTS,
480 NULL, /* no message source */
481 err,
482 MAKELANGID(LANG_NEUTRAL,
483 SUBLANG_DEFAULT), /* Default language */
484 (LPWSTR) &s_buf,
485 0, /* size not used */
486 NULL); /* no args */
487 if (len==0) {
488 /* Only seen this in out of mem situations */
489 message = PyUnicode_FromFormat("Windows Error 0x%X", err);
490 s_buf = NULL;
491 } else {
492 /* remove trailing cr/lf and dots */
493 while (len > 0 && (s_buf[len-1] <= L' ' || s_buf[len-1] == L'.'))
494 s_buf[--len] = L'\0';
495 message = PyUnicode_FromWideChar(s_buf, len);
496 }
497
498 if (message == NULL)
499 {
500 LocalFree(s_buf);
501 return NULL;
502 }
503
504 if (filenameObject == NULL)
505 filenameObject = Py_None;
506 /* This is the constructor signature for passing a Windows error code.
507 The POSIX translation will be figured out by the constructor. */
508 args = Py_BuildValue("(iOOi)", 0, message, filenameObject, err);
509 Py_DECREF(message);
510
511 if (args != NULL) {
512 v = PyObject_Call(exc, args, NULL);
513 Py_DECREF(args);
514 if (v != NULL) {
515 PyErr_SetObject((PyObject *) Py_TYPE(v), v);
516 Py_DECREF(v);
517 }
518 }
519 LocalFree(s_buf);
520 return NULL;
521 }
522
523 PyObject *PyErr_SetExcFromWindowsErrWithFilename(
524 PyObject *exc,
525 int ierr,
526 const char *filename)
527 {
528 PyObject *name = filename ? PyUnicode_DecodeFSDefault(filename) : NULL;
529 PyObject *ret = PyErr_SetExcFromWindowsErrWithFilenameObject(exc,
530 ierr,
531 name);
532 Py_XDECREF(name);
533 return ret;
534 }
535
536 PyObject *PyErr_SetExcFromWindowsErrWithUnicodeFilename(
537 PyObject *exc,
538 int ierr,
539 const Py_UNICODE *filename)
540 {
541 PyObject *name = filename ?
542 PyUnicode_FromUnicode(filename, wcslen(filename)) :
543 NULL;
544 PyObject *ret = PyErr_SetExcFromWindowsErrWithFilenameObject(exc,
545 ierr,
546 name);
547 Py_XDECREF(name);
548 return ret;
549 }
550
551 PyObject *PyErr_SetExcFromWindowsErr(PyObject *exc, int ierr)
552 {
553 return PyErr_SetExcFromWindowsErrWithFilename(exc, ierr, NULL);
554 }
555
556 PyObject *PyErr_SetFromWindowsErr(int ierr)
557 {
558 return PyErr_SetExcFromWindowsErrWithFilename(PyExc_WindowsError,
559 ierr, NULL);
560 }
561 PyObject *PyErr_SetFromWindowsErrWithFilename(
562 int ierr,
563 const char *filename)
564 {
565 PyObject *name = filename ? PyUnicode_DecodeFSDefault(filename) : NULL;
566 PyObject *result = PyErr_SetExcFromWindowsErrWithFilenameObject(
567 PyExc_WindowsError,
568 ierr, name);
569 Py_XDECREF(name);
570 return result;
571 }
572
573 PyObject *PyErr_SetFromWindowsErrWithUnicodeFilename(
574 int ierr,
575 const Py_UNICODE *filename)
576 {
577 PyObject *name = filename ?
578 PyUnicode_FromUnicode(filename, wcslen(filename)) :
579 NULL;
580 PyObject *result = PyErr_SetExcFromWindowsErrWithFilenameObject(
581 PyExc_WindowsError,
582 ierr, name);
583 Py_XDECREF(name);
584 return result;
585 }
586 #endif /* MS_WINDOWS */
587
588 void
589 _PyErr_BadInternalCall(const char *filename, int lineno)
590 {
591 PyErr_Format(PyExc_SystemError,
592 "%s:%d: bad argument to internal function",
593 filename, lineno);
594 }
595
596 /* Remove the preprocessor macro for PyErr_BadInternalCall() so that we can
597 export the entry point for existing object code: */
598 #undef PyErr_BadInternalCall
599 void
600 PyErr_BadInternalCall(void)
601 {
602 PyErr_Format(PyExc_SystemError,
603 "bad argument to internal function");
604 }
605 #define PyErr_BadInternalCall() _PyErr_BadInternalCall(__FILE__, __LINE__)
606
607
608
609 PyObject *
610 PyErr_Format(PyObject *exception, const char *format, ...)
611 {
612 va_list vargs;
613 PyObject* string;
614
615 #ifdef HAVE_STDARG_PROTOTYPES
616 va_start(vargs, format);
617 #else
618 va_start(vargs);
619 #endif
620
621 string = PyUnicode_FromFormatV(format, vargs);
622 PyErr_SetObject(exception, string);
623 Py_XDECREF(string);
624 va_end(vargs);
625 return NULL;
626 }
627
628
629
630 PyObject *
631 PyErr_NewException(const char *name, PyObject *base, PyObject *dict)
632 {
633 const char *dot;
634 PyObject *modulename = NULL;
635 PyObject *classname = NULL;
636 PyObject *mydict = NULL;
637 PyObject *bases = NULL;
638 PyObject *result = NULL;
639 dot = strrchr(name, '.');
640 if (dot == NULL) {
641 PyErr_SetString(PyExc_SystemError,
642 "PyErr_NewException: name must be module.class");
643 return NULL;
644 }
645 if (base == NULL)
646 base = PyExc_Exception;
647 if (dict == NULL) {
648 dict = mydict = PyDict_New();
649 if (dict == NULL)
650 goto failure;
651 }
652 if (PyDict_GetItemString(dict, "__module__") == NULL) {
653 modulename = PyUnicode_FromStringAndSize(name,
654 (Py_ssize_t)(dot-name));
655 if (modulename == NULL)
656 goto failure;
657 if (PyDict_SetItemString(dict, "__module__", modulename) != 0)
658 goto failure;
659 }
660 if (PyTuple_Check(base)) {
661 bases = base;
662 /* INCREF as we create a new ref in the else branch */
663 Py_INCREF(bases);
664 } else {
665 bases = PyTuple_Pack(1, base);
666 if (bases == NULL)
667 goto failure;
668 }
669 /* Create a real class. */
670 result = PyObject_CallFunction((PyObject *)&PyType_Type, "sOO",
671 dot+1, bases, dict);
672 failure:
673 Py_XDECREF(bases);
674 Py_XDECREF(mydict);
675 Py_XDECREF(classname);
676 Py_XDECREF(modulename);
677 return result;
678 }
679
680
681 /* Create an exception with docstring */
682 PyObject *
683 PyErr_NewExceptionWithDoc(const char *name, const char *doc,
684 PyObject *base, PyObject *dict)
685 {
686 int result;
687 PyObject *ret = NULL;
688 PyObject *mydict = NULL; /* points to the dict only if we create it */
689 PyObject *docobj;
690
691 if (dict == NULL) {
692 dict = mydict = PyDict_New();
693 if (dict == NULL) {
694 return NULL;
695 }
696 }
697
698 if (doc != NULL) {
699 docobj = PyUnicode_FromString(doc);
700 if (docobj == NULL)
701 goto failure;
702 result = PyDict_SetItemString(dict, "__doc__", docobj);
703 Py_DECREF(docobj);
704 if (result < 0)
705 goto failure;
706 }
707
708 ret = PyErr_NewException(name, base, dict);
709 failure:
710 Py_XDECREF(mydict);
711 return ret;
712 }
713
714
715 /* Call when an exception has occurred but there is no way for Python
716 to handle it. Examples: exception in __del__ or during GC. */
717 void
718 PyErr_WriteUnraisable(PyObject *obj)
719 {
720 _Py_IDENTIFIER(__module__);
721 PyObject *f, *t, *v, *tb;
722 PyErr_Fetch(&t, &v, &tb);
723 f = PySys_GetObject("stderr");
724 if (f != NULL && f != Py_None) {
725 PyFile_WriteString("Exception ", f);
726 if (t) {
727 PyObject* moduleName;
728 char* className;
729 assert(PyExceptionClass_Check(t));
730 className = PyExceptionClass_Name(t);
731 if (className != NULL) {
732 char *dot = strrchr(className, '.');
733 if (dot != NULL)
734 className = dot+1;
735 }
736
737 moduleName = _PyObject_GetAttrId(t, &PyId___module__);
738 if (moduleName == NULL)
739 PyFile_WriteString("<unknown>", f);
740 else {
741 char* modstr = _PyUnicode_AsString(moduleName);
742 if (modstr &&
743 strcmp(modstr, "builtins") != 0)
744 {
745 PyFile_WriteString(modstr, f);
746 PyFile_WriteString(".", f);
747 }
748 }
749 if (className == NULL)
750 PyFile_WriteString("<unknown>", f);
751 else
752 PyFile_WriteString(className, f);
753 if (v && v != Py_None) {
754 PyFile_WriteString(": ", f);
755 PyFile_WriteObject(v, f, 0);
756 }
757 Py_XDECREF(moduleName);
758 }
759 if (obj) {
760 PyFile_WriteString(" in ", f);
761 PyFile_WriteObject(obj, f, 0);
762 }
763 PyFile_WriteString(" ignored\n", f);
764 PyErr_Clear(); /* Just in case */
765 }
766 Py_XDECREF(t);
767 Py_XDECREF(v);
768 Py_XDECREF(tb);
769 }
770
771 extern PyObject *PyModule_GetWarningsModule(void);
772
773
774 void
775 PyErr_SyntaxLocation(const char *filename, int lineno) {
776 PyErr_SyntaxLocationEx(filename, lineno, -1);
777 }
778
779
780 /* Set file and line information for the current exception.
781 If the exception is not a SyntaxError, also sets additional attributes
782 to make printing of exceptions believe it is a syntax error. */
783
784 void
785 PyErr_SyntaxLocationEx(const char *filename, int lineno, int col_offset)
786 {
787 PyObject *exc, *v, *tb, *tmp;
788 _Py_IDENTIFIER(filename);
789 _Py_IDENTIFIER(lineno);
790 _Py_IDENTIFIER(msg);
791 _Py_IDENTIFIER(offset);
792 _Py_IDENTIFIER(print_file_and_line);
793 _Py_IDENTIFIER(text);
794
795 /* add attributes for the line number and filename for the error */
796 PyErr_Fetch(&exc, &v, &tb);
797 PyErr_NormalizeException(&exc, &v, &tb);
798 /* XXX check that it is, indeed, a syntax error. It might not
799 * be, though. */
800 tmp = PyLong_FromLong(lineno);
801 if (tmp == NULL)
802 PyErr_Clear();
803 else {
804 if (_PyObject_SetAttrId(v, &PyId_lineno, tmp))
805 PyErr_Clear();
806 Py_DECREF(tmp);
807 }
808 if (col_offset >= 0) {
809 tmp = PyLong_FromLong(col_offset);
810 if (tmp == NULL)
811 PyErr_Clear();
812 else {
813 if (_PyObject_SetAttrId(v, &PyId_offset, tmp))
814 PyErr_Clear();
815 Py_DECREF(tmp);
816 }
817 }
818 if (filename != NULL) {
819 tmp = PyUnicode_DecodeFSDefault(filename);
820 if (tmp == NULL)
821 PyErr_Clear();
822 else {
823 if (_PyObject_SetAttrId(v, &PyId_filename, tmp))
824 PyErr_Clear();
825 Py_DECREF(tmp);
826 }
827
828 tmp = PyErr_ProgramText(filename, lineno);
829 if (tmp) {
830 if (_PyObject_SetAttrId(v, &PyId_text, tmp))
831 PyErr_Clear();
832 Py_DECREF(tmp);
833 }
834 }
835 if (_PyObject_SetAttrId(v, &PyId_offset, Py_None)) {
836 PyErr_Clear();
837 }
838 if (exc != PyExc_SyntaxError) {
839 if (!_PyObject_HasAttrId(v, &PyId_msg)) {
840 tmp = PyObject_Str(v);
841 if (tmp) {
842 if (_PyObject_SetAttrId(v, &PyId_msg, tmp))
843 PyErr_Clear();
844 Py_DECREF(tmp);
845 } else {
846 PyErr_Clear();
847 }
848 }
849 if (!_PyObject_HasAttrId(v, &PyId_print_file_and_line)) {
850 if (_PyObject_SetAttrId(v, &PyId_print_file_and_line,
851 Py_None))
852 PyErr_Clear();
853 }
854 }
855 PyErr_Restore(exc, v, tb);
856 }
857
858 /* Attempt to load the line of text that the exception refers to. If it
859 fails, it will return NULL but will not set an exception.
860
861 XXX The functionality of this function is quite similar to the
862 functionality in tb_displayline() in traceback.c. */
863
864 PyObject *
865 PyErr_ProgramText(const char *filename, int lineno)
866 {
867 FILE *fp;
868 int i;
869 char linebuf[1000];
870
871 if (filename == NULL || *filename == '\0' || lineno <= 0)
872 return NULL;
873 fp = fopen(filename, "r" PY_STDIOTEXTMODE);
874 if (fp == NULL)
875 return NULL;
876 for (i = 0; i < lineno; i++) {
877 char *pLastChar = &linebuf[sizeof(linebuf) - 2];
878 do {
879 *pLastChar = '\0';
880 if (Py_UniversalNewlineFgets(linebuf, sizeof linebuf,
881 fp, NULL) == NULL)
882 break;
883 /* fgets read *something*; if it didn't get as
884 far as pLastChar, it must have found a newline
885 or hit the end of the file; if pLastChar is \n,
886 it obviously found a newline; else we haven't
887 yet seen a newline, so must continue */
888 } while (*pLastChar != '\0' && *pLastChar != '\n');
889 }
890 fclose(fp);
891 if (i == lineno) {
892 char *p = linebuf;
893 PyObject *res;
894 while (*p == ' ' || *p == '\t' || *p == '\014')
895 p++;
896 res = PyUnicode_FromString(p);
897 if (res == NULL)
898 PyErr_Clear();
899 return res;
900 }
901 return NULL;
902 }
903
904 #ifdef __cplusplus
905 }
906 #endif