]> Cypherpunks repositories - gostls13.git/commitdiff
runtime: stack allocate Panic structure during runtime.panic
authorDave Cheney <dave@cheney.net>
Mon, 24 Feb 2014 16:09:19 +0000 (11:09 -0500)
committerRuss Cox <rsc@golang.org>
Mon, 24 Feb 2014 16:09:19 +0000 (11:09 -0500)
Update #7347

When runtime.panic is called the *Panic is malloced from the heap. This can lead to a gc cycle while panicing which can make a bad situation worse.

It appears to be possible to stack allocate the Panic and avoid malloc'ing during a panic.

Ref: https://groups.google.com/d/topic/golang-dev/OfxqpklGkh0/discussion

LGTM=minux.ma, dvyukov, rsc
R=r, minux.ma, gobot, rsc, dvyukov
CC=golang-codereviews
https://golang.org/cl/66830043

src/pkg/runtime/panic.c

index 73185273cbd911d88d6c2b0ee8967590c0d1a2f0..f4f2148d54f9e55dd5839a9bf124300c119bc431 100644 (file)
@@ -211,14 +211,14 @@ void
 runtime·panic(Eface e)
 {
        Defer *d;
-       Panic *p;
+       Panic p;
        void *pc, *argp;
-       
-       p = runtime·mal(sizeof *p);
-       p->arg = e;
-       p->link = g->panic;
-       p->stackbase = g->stackbase;
-       g->panic = p;
+
+       runtime·memclr((byte*)&p, sizeof p);
+       p.arg = e;
+       p.link = g->panic;
+       p.stackbase = g->stackbase;
+       g->panic = &p;
 
        for(;;) {
                d = g->defer;
@@ -231,11 +231,10 @@ runtime·panic(Eface e)
                pc = d->pc;
                runtime·newstackcall(d->fn, (byte*)d->args, d->siz);
                freedefer(d);
-               if(p->recovered) {
-                       g->panic = p->link;
+               if(p.recovered) {
+                       g->panic = p.link;
                        if(g->panic == nil)     // must be done with signal
                                g->sig = 0;
-                       runtime·free(p);
                        // Pass information about recovering frame to recovery.
                        g->sigcode0 = (uintptr)argp;
                        g->sigcode1 = (uintptr)pc;