Author: jilles
Date: Sat May 11 20:51:00 2013
New Revision: 250527
URL: http://svnweb.freebsd.org/changeset/base/250527

Log:
  sh: Remove linked list of stack marks.
  
  The linked list of stack marks may cause problems if the allocation stack is
  used between an exception and a higher-level popstackmark(), as it may then
  touch a stack mark that is local to a function which has returned.
  
  Also, the adjustment compares to a pointer passed to realloc(), which is
  undefined behaviour.
  
  Instead of adjusting stack marks when reallocating stack blocks, ensure that
  such an adjustment is never necessary by fixing a small piece of memory in
  place at a stack mark. This also simplifies the code.
  
  To avoid the problems reported in bin/175922, it remains necessary to call
  setstackmark() after popstackmark() if the stack mark remains in use.

Modified:
  head/bin/sh/memalloc.c
  head/bin/sh/memalloc.h

Modified: head/bin/sh/memalloc.c
==============================================================================
--- head/bin/sh/memalloc.c      Sat May 11 19:46:15 2013        (r250526)
+++ head/bin/sh/memalloc.c      Sat May 11 20:51:00 2013        (r250527)
@@ -124,7 +124,6 @@ struct stack_block {
 #define SPACE(sp)      ((char*)(sp) + ALIGN(sizeof(struct stack_block)))
 
 static struct stack_block *stackp;
-static struct stackmark *markp;
 char *stacknxt;
 int stacknleft;
 char *sstrend;
@@ -186,8 +185,9 @@ setstackmark(struct stackmark *mark)
        mark->stackp = stackp;
        mark->stacknxt = stacknxt;
        mark->stacknleft = stacknleft;
-       mark->marknext = markp;
-       markp = mark;
+       /* Ensure this block stays in place. */
+       if (stackp != NULL && stacknxt == SPACE(stackp))
+               stalloc(1);
 }
 
 
@@ -197,7 +197,6 @@ popstackmark(struct stackmark *mark)
        struct stack_block *sp;
 
        INTOFF;
-       markp = mark->marknext;
        while (stackp != mark->stackp) {
                sp = stackp;
                stackp = sp->prev;
@@ -229,7 +228,6 @@ growstackblock(int min)
        int oldlen;
        struct stack_block *sp;
        struct stack_block *oldstackp;
-       struct stackmark *xmark;
 
        if (min < stacknleft)
                min = stacknleft;
@@ -254,18 +252,6 @@ growstackblock(int min)
                stacknxt = SPACE(sp);
                stacknleft = newlen - (stacknxt - (char*)sp);
                sstrend = stacknxt + stacknleft;
-
-               /*
-                * Stack marks pointing to the start of the old block
-                * must be relocated to point to the new block
-                */
-               xmark = markp;
-               while (xmark != NULL && xmark->stackp == oldstackp) {
-                       xmark->stackp = stackp;
-                       xmark->stacknxt = stacknxt;
-                       xmark->stacknleft = stacknleft;
-                       xmark = xmark->marknext;
-               }
                INTON;
        } else {
                newlen -= ALIGN(sizeof(struct stack_block));

Modified: head/bin/sh/memalloc.h
==============================================================================
--- head/bin/sh/memalloc.h      Sat May 11 19:46:15 2013        (r250526)
+++ head/bin/sh/memalloc.h      Sat May 11 20:51:00 2013        (r250527)
@@ -39,7 +39,6 @@ struct stackmark {
        struct stack_block *stackp;
        char *stacknxt;
        int stacknleft;
-        struct stackmark *marknext;
 };
 
 
_______________________________________________
svn-src-head@freebsd.org mailing list
http://lists.freebsd.org/mailman/listinfo/svn-src-head
To unsubscribe, send any mail to "svn-src-head-unsubscr...@freebsd.org"

Reply via email to