Author: Armin Rigo <ar...@tunes.org>
Branch: rpython-error-to-systemerror
Changeset: r88163:9ceb823c232b
Date: 2016-11-06 20:06 +0100
http://bitbucket.org/pypy/pypy/changeset/9ceb823c232b/

Log:    Dump the RPython-level traceback up to the point where we caught it

diff --git a/pypy/interpreter/baseobjspace.py b/pypy/interpreter/baseobjspace.py
--- a/pypy/interpreter/baseobjspace.py
+++ b/pypy/interpreter/baseobjspace.py
@@ -3,7 +3,7 @@
 from rpython.rlib.cache import Cache
 from rpython.tool.uid import HUGEVAL_BYTES
 from rpython.rlib import jit, types
-from rpython.rlib.debug import make_sure_not_resized
+from rpython.rlib.debug import make_sure_not_resized, debug_print_traceback
 from rpython.rlib.objectmodel import (we_are_translated, newlist_hint,
      compute_unique_id, specialize)
 from rpython.rlib.signature import signature
@@ -1852,7 +1852,8 @@
 
     def _convert_unexpected_exception(self, e):
         if we_are_translated():
-            extra = ''
+            debug_print_traceback()
+            extra = '; internal traceback was dumped to stderr'
         else:
             extra = self._convert_unexpected_exception_extra(e)
         raise OperationError(self.w_SystemError, self.wrap(
diff --git a/rpython/rlib/debug.py b/rpython/rlib/debug.py
--- a/rpython/rlib/debug.py
+++ b/rpython/rlib/debug.py
@@ -11,7 +11,7 @@
 
 # Expose these here (public interface)
 from rpython.rtyper.debug import (
-    ll_assert, FatalError, fatalerror, fatalerror_notb)
+    ll_assert, FatalError, fatalerror, fatalerror_notb, debug_print_traceback)
 
 
 class DebugLog(list):
diff --git a/rpython/rlib/test/test_debug.py b/rpython/rlib/test/test_debug.py
--- a/rpython/rlib/test/test_debug.py
+++ b/rpython/rlib/test/test_debug.py
@@ -118,3 +118,30 @@
     finally:
         debug._log = None
     assert dlog == [("mycat", [('debug_print', 'foo', 2, 'bar', 3)])]
+
+
+def test_debug_print_traceback():
+    from rpython.translator.c.test.test_genc import compile
+    from rpython.rtyper.lltypesystem import lltype
+    from rpython.rtyper.lltypesystem.lloperation import llop
+
+    def ggg(n):
+        if n < 10:
+            ggg(n + 1)
+        else:
+            raise ValueError
+    def recovery():
+        llop.debug_print_traceback(lltype.Void)
+    recovery._dont_inline_ = True
+    def fff():
+        try:
+            ggg(0)
+        except:
+            recovery()
+
+    fn = compile(fff, [], return_stderr=True)
+    stderr = fn()
+    assert 'RPython traceback:\n' in stderr
+    assert stderr.count('entry_point') == 1
+    assert stderr.count('ggg') == 11
+    assert stderr.count('recovery') == 0
diff --git a/rpython/rtyper/debug.py b/rpython/rtyper/debug.py
--- a/rpython/rtyper/debug.py
+++ b/rpython/rtyper/debug.py
@@ -45,3 +45,12 @@
 fatalerror_notb._dont_inline_ = True
 fatalerror_notb._jit_look_inside_ = False
 fatalerror_notb._annenforceargs_ = [str]
+
+def debug_print_traceback():
+    # print to stderr the RPython traceback of the last caught exception,
+    # but without interrupting the program
+    from rpython.rtyper.lltypesystem import lltype
+    from rpython.rtyper.lltypesystem.lloperation import llop
+    llop.debug_print_traceback(lltype.Void)
+debug_print_traceback._dont_inline_ = True
+debug_print_traceback._jit_look_inside_ = False
diff --git a/rpython/translator/c/test/test_genc.py 
b/rpython/translator/c/test/test_genc.py
--- a/rpython/translator/c/test/test_genc.py
+++ b/rpython/translator/c/test/test_genc.py
@@ -53,7 +53,8 @@
                                            unsigned_ffffffff)
 
 def compile(fn, argtypes, view=False, gcpolicy="none", backendopt=True,
-            annotatorpolicy=None, thread=False, **kwds):
+            annotatorpolicy=None, thread=False,
+            return_stderr=False, **kwds):
     argtypes_unroll = unrolling_iterable(enumerate(argtypes))
 
     for argtype in argtypes:
@@ -139,7 +140,8 @@
 
         stdout = t.driver.cbuilder.cmdexec(
             " ".join([llrepr_in(arg) for arg in args]),
-            expect_crash=(expected_exception_name is not None))
+            expect_crash=(expected_exception_name is not None),
+            err=return_stderr)
         #
         if expected_exception_name is not None:
             stdout, stderr = stdout
@@ -154,6 +156,8 @@
             assert lastline == expected or prevline == expected
             return None
 
+        if return_stderr:
+            stdout, stderr = stdout
         output(stdout)
         stdout, lastline, empty = stdout.rsplit('\n', 2)
         assert empty == ''
@@ -168,6 +172,8 @@
         else:
             assert mallocs - frees in expected_extra_mallocs
         #
+        if return_stderr:
+            return stderr
         if ll_res in [lltype.Signed, lltype.Unsigned, lltype.SignedLongLong,
                       lltype.UnsignedLongLong]:
             return int(res)
_______________________________________________
pypy-commit mailing list
pypy-commit@python.org
https://mail.python.org/mailman/listinfo/pypy-commit

Reply via email to