]> granicus.if.org Git - jq/commitdiff
Remove the is_backtrack_frame special case hack.
authorStephen Dolan <mu@netsoc.tcd.ie>
Mon, 13 May 2013 14:37:57 +0000 (15:37 +0100)
committerStephen Dolan <mu@netsoc.tcd.ie>
Mon, 13 May 2013 14:37:57 +0000 (15:37 +0100)
execute.c
frame_layout.h

index 77b8574d3b925cb6f6725d0e54a1f2ae9a4cf98e..9062f116147581ac8cf9e5032617b674e8c419c2 100644 (file)
--- a/execute.c
+++ b/execute.c
@@ -56,16 +56,18 @@ struct forkpoint {
   struct forkable_stack_state saved_data_stack;
   struct forkable_stack_state saved_call_stack;
   int path_len, subexp_nest;
+  uint16_t* return_address;
 };
 
 
-void stack_save(jq_state *jq){
+void stack_save(jq_state *jq, uint16_t* retaddr){
   struct forkpoint* fork = forkable_stack_push(&jq->fork_stk, sizeof(struct forkpoint));
   forkable_stack_save(&jq->data_stk, &fork->saved_data_stack);
   forkable_stack_save(&jq->frame_stk, &fork->saved_call_stack);
   fork->path_len = 
     jv_get_kind(jq->path) == JV_KIND_ARRAY ? jv_array_length(jv_copy(jq->path)) : 0;
   fork->subexp_nest = jq->subexp_nest;
+  fork->return_address = retaddr;
 }
 
 void stack_switch(jq_state *jq) {
@@ -85,7 +87,7 @@ void path_append(jq_state* jq, jv component) {
   }
 }
 
-int stack_restore(jq_state *jq){
+uint16_t* stack_restore(jq_state *jq){
   while (!forkable_stack_empty(&jq->data_stk) && 
          forkable_stack_pop_will_free(&jq->data_stk)) {
     jv_free(stack_pop(jq));
@@ -100,6 +102,7 @@ int stack_restore(jq_state *jq){
   }
 
   struct forkpoint* fork = forkable_stack_peek(&jq->fork_stk);
+  uint16_t* retaddr = fork->return_address;
   forkable_stack_restore(&jq->data_stk, &fork->saved_data_stack);
   forkable_stack_restore(&jq->frame_stk, &fork->saved_call_stack);
   int path_len = fork->path_len;
@@ -111,7 +114,7 @@ int stack_restore(jq_state *jq){
   }
   jq->subexp_nest = fork->subexp_nest;
   forkable_stack_pop(&jq->fork_stk);
-  return 1;
+  return retaddr;
 }
 
 
@@ -143,11 +146,8 @@ void print_error(jv value) {
 jv jq_next(jq_state *jq) {
   jv cfunc_input[MAX_CFUNCTION_ARGS];
 
-  assert(!forkable_stack_empty(&jq->frame_stk));
-  uint16_t* pc = *frame_current_retaddr(&jq->frame_stk);
-  frame_pop(&jq->frame_stk);
-  
-  assert(!forkable_stack_empty(&jq->frame_stk));
+  uint16_t* pc = stack_restore(jq);
+  assert(pc);
 
   int backtracking = 0;
   while (1) {
@@ -293,8 +293,7 @@ jv jq_next(jq_state *jq) {
       jv v = stack_pop(jq);
       stack_push(jq, jq->path);
 
-      stack_save(jq);
-      frame_push_backtrack(&jq->frame_stk, pc - 1);
+      stack_save(jq, pc - 1);
       stack_switch(jq);
 
       stack_push(jq, jv_number(jq->subexp_nest));
@@ -314,9 +313,8 @@ jv jq_next(jq_state *jq) {
       jv path = jq->path;
       jq->path = stack_pop(jq);
 
-      stack_save(jq);
+      stack_save(jq, pc - 1);
       stack_push(jq, jv_copy(path));
-      frame_push_backtrack(&jq->frame_stk, pc - 1);
       stack_switch(jq);
 
       stack_push(jq, path);
@@ -399,10 +397,9 @@ jv jq_next(jq_state *jq) {
         jv_free(container);
         goto do_backtrack;
       } else {
-        stack_save(jq);
+        stack_save(jq, pc - 1);
         stack_push(jq, container);
         stack_push(jq, jv_number(idx));
-        frame_push_backtrack(&jq->frame_stk, pc - 1);
         stack_switch(jq);
         path_append(jq, key);
         stack_push(jq, value);
@@ -412,18 +409,16 @@ jv jq_next(jq_state *jq) {
 
     do_backtrack:
     case BACKTRACK: {
-      if (!stack_restore(jq)) {
+      pc = stack_restore(jq);
+      if (!pc) {
         return jv_invalid();
       }
-      pc = *frame_current_retaddr(&jq->frame_stk);
-      frame_pop(&jq->frame_stk);
       backtracking = 1;
       break;
     }
 
     case FORK: {
-      stack_save(jq);
-      frame_push_backtrack(&jq->frame_stk, pc - 1);
+      stack_save(jq, pc - 1);
       stack_switch(jq);
       pc++; // skip offset this time
       break;
@@ -437,7 +432,8 @@ jv jq_next(jq_state *jq) {
 
     case YIELD: {
       jv value = stack_pop(jq);
-      frame_push_backtrack(&jq->frame_stk, pc);
+      stack_save(jq, pc);
+      stack_switch(jq);
       return value;
     }
       
@@ -499,7 +495,8 @@ void jq_init(struct bytecode* bc, jv input, jq_state **jq, int flags) {
   stack_push(new_jq, input);
   struct closure top = {bc, -1};
   frame_push(&new_jq->frame_stk, top, 0);
-  frame_push_backtrack(&new_jq->frame_stk, bc->code);
+  stack_save(new_jq, bc->code);
+  stack_switch(new_jq);
   if (flags & JQ_DEBUG_TRACE) {
     new_jq->debug_trace_enabled = 1;
   } else {
index f098272ec0148d5ba4b2af621b7f27921be38b3d..dbbe3000aabacfa313857b483c78fafe82425b78 100644 (file)
@@ -11,8 +11,6 @@ struct continuation {
   struct bytecode* bc;
   stack_idx env;
   uint16_t* retaddr;
-  // FIXME: probably not necessary as a separate field
-  int is_backtrack_frame;
 };
 
 typedef union frame_elem {
@@ -86,27 +84,15 @@ static frame_ptr frame_push(struct forkable_stack* stk, struct closure cl, uint1
   cc->bc = cl.bc;
   cc->env = cl.env;
   cc->retaddr = retaddr;
-  cc->is_backtrack_frame = 0;
   for (int i=0; i<cl.bc->nlocals; i++) {
     *frame_local_var(fp, i) = jv_invalid();
   }
   return fp;
 }
 
-static frame_ptr frame_push_backtrack(struct forkable_stack* stk, uint16_t* retaddr) {
-  struct continuation cc = *frame_self(frame_current(stk));
-  frame_ptr fp = forkable_stack_push(stk, sizeof(union frame_elem) * 2);
-  assert(!cc.is_backtrack_frame);
-  cc.is_backtrack_frame = 1;
-  cc.retaddr = retaddr;
-  *frame_self(fp) = cc;
-  return fp;
-}
-
 static void frame_pop(struct forkable_stack* stk) {
   frame_ptr fp = frame_current(stk);
-  if (forkable_stack_pop_will_free(stk) && 
-      !frame_self(fp)->is_backtrack_frame) {
+  if (forkable_stack_pop_will_free(stk)) {
     int nlocals = frame_self(fp)->bc->nlocals;
     for (int i=0; i<nlocals; i++) {
       jv_free(*frame_local_var(fp, i));