vlib: don't leak node frames on refork
[vpp.git] / src / vlib / main.c
index a9efe7e..964bc4a 100644 (file)
@@ -106,6 +106,7 @@ vlib_frame_alloc_to_node (vlib_main_t * vm, u32 to_node_index,
   f->vector_offset = to_node->vector_offset;
   f->aux_offset = to_node->aux_offset;
   f->flags = 0;
+  f->frame_size_index = to_node->frame_size_index;
 
   fs->n_alloc_frames += 1;
 
@@ -186,17 +187,15 @@ vlib_put_frame_to_node (vlib_main_t * vm, u32 to_node_index, vlib_frame_t * f)
 
 /* Free given frame. */
 void
-vlib_frame_free (vlib_main_t * vm, vlib_node_runtime_t * r, vlib_frame_t * f)
+vlib_frame_free (vlib_main_t *vm, vlib_frame_t *f)
 {
   vlib_node_main_t *nm = &vm->node_main;
-  vlib_node_t *node;
   vlib_frame_size_t *fs;
 
   ASSERT (vm == vlib_get_main ());
   ASSERT (f->frame_flags & VLIB_FRAME_IS_ALLOCATED);
 
-  node = vlib_get_node (vm, r->node_index);
-  fs = vec_elt_at_index (nm->frame_sizes, node->frame_size_index);
+  fs = vec_elt_at_index (nm->frame_sizes, f->frame_size_index);
 
   ASSERT (f->frame_flags & VLIB_FRAME_IS_ALLOCATED);
 
@@ -208,6 +207,7 @@ vlib_frame_free (vlib_main_t * vm, vlib_node_runtime_t * r, vlib_frame_t * f)
     }
 
   f->frame_flags &= ~(VLIB_FRAME_IS_ALLOCATED | VLIB_FRAME_NO_APPEND);
+  f->flags = 0;
 
   vec_add1 (fs->free_frames, f);
   ASSERT (fs->n_alloc_frames > 0);
@@ -1163,13 +1163,14 @@ dispatch_pending_node (vlib_main_t * vm, uword pending_frame_index,
          /* no new frame has been assigned to this node, use the saved one */
          nf->frame = restore_frame;
          f->n_vectors = 0;
+         f->flags = 0;
        }
       else
        {
          /* The node has gained a frame, implying packets from the current frame
             were re-queued to this same node. we don't need the saved one
             anymore */
-         vlib_frame_free (vm, n, f);
+         vlib_frame_free (vm, f);
        }
     }
   else
@@ -1177,7 +1178,7 @@ dispatch_pending_node (vlib_main_t * vm, uword pending_frame_index,
       if (f->frame_flags & VLIB_FRAME_FREE_AFTER_DISPATCH)
        {
          ASSERT (!(n->flags & VLIB_NODE_FLAG_FRAME_NO_FREE_AFTER_DISPATCH));
-         vlib_frame_free (vm, n, f);
+         vlib_frame_free (vm, f);
        }
     }
 
@@ -1517,8 +1518,7 @@ vlib_main_or_worker_loop (vlib_main_t * vm, int is_main)
       if (PREDICT_FALSE (vm->check_frame_queues + frame_queue_check_counter))
        {
          u32 processed = 0;
-         vlib_frame_queue_dequeue_fn_t *fn =
-           vlib_buffer_func_main.frame_queue_dequeue_fn;
+         vlib_frame_queue_dequeue_fn_t *fn;
 
          if (vm->check_frame_queues)
            {
@@ -1527,7 +1527,10 @@ vlib_main_or_worker_loop (vlib_main_t * vm, int is_main)
            }
 
          vec_foreach (fqm, tm->frame_queue_mains)
-           processed += (fn) (vm, fqm);
+           {
+             fn = fqm->frame_queue_dequeue_fn;
+             processed += (fn) (vm, fqm);
+           }
 
          /* No handoff queue work found? */
          if (processed)