aboutsummaryrefslogtreecommitdiff
path: root/libgo/runtime/panic.c
diff options
context:
space:
mode:
Diffstat (limited to 'libgo/runtime/panic.c')
-rw-r--r--libgo/runtime/panic.c12
1 files changed, 11 insertions, 1 deletions
diff --git a/libgo/runtime/panic.c b/libgo/runtime/panic.c
index 7b9b578..7d79256 100644
--- a/libgo/runtime/panic.c
+++ b/libgo/runtime/panic.c
@@ -3,6 +3,7 @@
// license that can be found in the LICENSE file.
#include "runtime.h"
+#include "malloc.h"
#include "go-defer.h"
#include "go-panic.h"
@@ -37,6 +38,11 @@ runtime_startpanic(void)
M *m;
m = runtime_m();
+ if(runtime_mheap == 0 || runtime_mheap->cachealloc.size == 0) { // very early
+ runtime_printf("runtime: panic before malloc heap initialized\n");
+ m->mallocing = 1; // tell rest of panic not to try to malloc
+ } else if(m->mcache == nil) // can happen if called from signal handler or throw
+ m->mcache = runtime_allocmcache();
if(m->dying) {
runtime_printf("panic during panic\n");
runtime_exit(3);
@@ -51,13 +57,14 @@ runtime_dopanic(int32 unused __attribute__ ((unused)))
{
G *g;
static bool didothers;
+ bool crash;
g = runtime_g();
if(g->sig != 0)
runtime_printf("[signal %x code=%p addr=%p]\n",
g->sig, (void*)g->sigcode0, (void*)g->sigcode1);
- if(runtime_gotraceback()){
+ if(runtime_gotraceback(&crash)){
if(g != runtime_m()->g0) {
runtime_printf("\n");
runtime_goroutineheader(g);
@@ -79,6 +86,9 @@ runtime_dopanic(int32 unused __attribute__ ((unused)))
runtime_lock(&deadlock);
runtime_lock(&deadlock);
}
+
+ if(crash)
+ runtime_crash();
runtime_exit(2);
}