Index: third_party/cython/src/Cython/Compiler/Errors.py |
diff --git a/third_party/cython/src/Cython/Compiler/Errors.py b/third_party/cython/src/Cython/Compiler/Errors.py |
new file mode 100644 |
index 0000000000000000000000000000000000000000..046ab531196ac25656d1c25039e586d6b342e695 |
--- /dev/null |
+++ b/third_party/cython/src/Cython/Compiler/Errors.py |
@@ -0,0 +1,235 @@ |
+# |
+# Errors |
+# |
+ |
+import sys |
+from Cython.Utils import open_new_file |
+import DebugFlags |
+import Options |
+ |
+ |
+class PyrexError(Exception): |
+ pass |
+ |
+class PyrexWarning(Exception): |
+ pass |
+ |
+ |
+def context(position): |
+ source = position[0] |
+ assert not (isinstance(source, unicode) or isinstance(source, str)), ( |
+ "Please replace filename strings with Scanning.FileSourceDescriptor instances %r" % source) |
+ try: |
+ F = source.get_lines() |
+ except UnicodeDecodeError: |
+ # file has an encoding problem |
+ s = u"[unprintable code]\n" |
+ else: |
+ s = u''.join(F[max(0, position[1]-6):position[1]]) |
+ s = u'...\n%s%s^\n' % (s, u' '*(position[2]-1)) |
+ s = u'%s\n%s%s\n' % (u'-'*60, s, u'-'*60) |
+ return s |
+ |
+def format_position(position): |
+ if position: |
+ return u"%s:%d:%d: " % (position[0].get_error_description(), |
+ position[1], position[2]) |
+ return u'' |
+ |
+def format_error(message, position): |
+ if position: |
+ pos_str = format_position(position) |
+ cont = context(position) |
+ message = u'\nError compiling Cython file:\n%s\n%s%s' % (cont, pos_str, message or u'') |
+ return message |
+ |
+class CompileError(PyrexError): |
+ |
+ def __init__(self, position = None, message = u""): |
+ self.position = position |
+ self.message_only = message |
+ self.formatted_message = format_error(message, position) |
+ self.reported = False |
+ # Deprecated and withdrawn in 2.6: |
+ # self.message = message |
+ Exception.__init__(self, self.formatted_message) |
+ # Python Exception subclass pickling is broken, |
+ # see http://bugs.python.org/issue1692335 |
+ self.args = (position, message) |
+ |
+ def __str__(self): |
+ return self.formatted_message |
+ |
+class CompileWarning(PyrexWarning): |
+ |
+ def __init__(self, position = None, message = ""): |
+ self.position = position |
+ # Deprecated and withdrawn in 2.6: |
+ # self.message = message |
+ Exception.__init__(self, format_position(position) + message) |
+ |
+class InternalError(Exception): |
+ # If this is ever raised, there is a bug in the compiler. |
+ |
+ def __init__(self, message): |
+ self.message_only = message |
+ Exception.__init__(self, u"Internal compiler error: %s" |
+ % message) |
+ |
+class AbortError(Exception): |
+ # Throw this to stop the compilation immediately. |
+ |
+ def __init__(self, message): |
+ self.message_only = message |
+ Exception.__init__(self, u"Abort error: %s" % message) |
+ |
+class CompilerCrash(CompileError): |
+ # raised when an unexpected exception occurs in a transform |
+ def __init__(self, pos, context, message, cause, stacktrace=None): |
+ if message: |
+ message = u'\n' + message |
+ else: |
+ message = u'\n' |
+ self.message_only = message |
+ if context: |
+ message = u"Compiler crash in %s%s" % (context, message) |
+ if stacktrace: |
+ import traceback |
+ message += ( |
+ u'\n\nCompiler crash traceback from this point on:\n' + |
+ u''.join(traceback.format_tb(stacktrace))) |
+ if cause: |
+ if not stacktrace: |
+ message += u'\n' |
+ message += u'%s: %s' % (cause.__class__.__name__, cause) |
+ CompileError.__init__(self, pos, message) |
+ # Python Exception subclass pickling is broken, |
+ # see http://bugs.python.org/issue1692335 |
+ self.args = (pos, context, message, cause, stacktrace) |
+ |
+class NoElementTreeInstalledException(PyrexError): |
+ """raised when the user enabled options.gdb_debug but no ElementTree |
+ implementation was found |
+ """ |
+ |
+listing_file = None |
+num_errors = 0 |
+echo_file = None |
+ |
+def open_listing_file(path, echo_to_stderr = 1): |
+ # Begin a new error listing. If path is None, no file |
+ # is opened, the error counter is just reset. |
+ global listing_file, num_errors, echo_file |
+ if path is not None: |
+ listing_file = open_new_file(path) |
+ else: |
+ listing_file = None |
+ if echo_to_stderr: |
+ echo_file = sys.stderr |
+ else: |
+ echo_file = None |
+ num_errors = 0 |
+ |
+def close_listing_file(): |
+ global listing_file |
+ if listing_file: |
+ listing_file.close() |
+ listing_file = None |
+ |
+def report_error(err): |
+ if error_stack: |
+ error_stack[-1].append(err) |
+ else: |
+ global num_errors |
+ # See Main.py for why dual reporting occurs. Quick fix for now. |
+ if err.reported: return |
+ err.reported = True |
+ try: line = u"%s\n" % err |
+ except UnicodeEncodeError: |
+ # Python <= 2.5 does this for non-ASCII Unicode exceptions |
+ line = format_error(getattr(err, 'message_only', "[unprintable exception message]"), |
+ getattr(err, 'position', None)) + u'\n' |
+ if listing_file: |
+ try: listing_file.write(line) |
+ except UnicodeEncodeError: |
+ listing_file.write(line.encode('ASCII', 'replace')) |
+ if echo_file: |
+ try: echo_file.write(line) |
+ except UnicodeEncodeError: |
+ echo_file.write(line.encode('ASCII', 'replace')) |
+ num_errors = num_errors + 1 |
+ if Options.fast_fail: |
+ raise AbortError("fatal errors") |
+ |
+def error(position, message): |
+ #print "Errors.error:", repr(position), repr(message) ### |
+ if position is None: |
+ raise InternalError(message) |
+ err = CompileError(position, message) |
+ if DebugFlags.debug_exception_on_error: raise Exception(err) # debug |
+ report_error(err) |
+ return err |
+ |
+LEVEL=1 # warn about all errors level 1 or higher |
+ |
+def message(position, message, level=1): |
+ if level < LEVEL: |
+ return |
+ warn = CompileWarning(position, message) |
+ line = "note: %s\n" % warn |
+ if listing_file: |
+ listing_file.write(line) |
+ if echo_file: |
+ echo_file.write(line) |
+ return warn |
+ |
+def warning(position, message, level=0): |
+ if level < LEVEL: |
+ return |
+ if Options.warning_errors and position: |
+ return error(position, message) |
+ warn = CompileWarning(position, message) |
+ line = "warning: %s\n" % warn |
+ if listing_file: |
+ listing_file.write(line) |
+ if echo_file: |
+ echo_file.write(line) |
+ return warn |
+ |
+_warn_once_seen = {} |
+def warn_once(position, message, level=0): |
+ if level < LEVEL or message in _warn_once_seen: |
+ return |
+ warn = CompileWarning(position, message) |
+ line = "warning: %s\n" % warn |
+ if listing_file: |
+ listing_file.write(line) |
+ if echo_file: |
+ echo_file.write(line) |
+ _warn_once_seen[message] = True |
+ return warn |
+ |
+ |
+# These functions can be used to momentarily suppress errors. |
+ |
+error_stack = [] |
+ |
+def hold_errors(): |
+ error_stack.append([]) |
+ |
+def release_errors(ignore=False): |
+ held_errors = error_stack.pop() |
+ if not ignore: |
+ for err in held_errors: |
+ report_error(err) |
+ |
+def held_errors(): |
+ return error_stack[-1] |
+ |
+ |
+# this module needs a redesign to support parallel cythonisation, but |
+# for now, the following works at least in sequential compiler runs |
+ |
+def reset(): |
+ _warn_once_seen.clear() |
+ del error_stack[:] |