vlib_frame_t *f;
u32 n_vectors_in_frame;
- if (vm->buffer_main->callbacks_registered == 0 && CLIB_DEBUG > 0)
+ if (buffer_main.callbacks_registered == 0 && CLIB_DEBUG > 0)
vlib_put_next_frame_validate (vm, r, next_index, n_vectors_left);
nf = vlib_node_runtime_get_next_frame (vm, r, next_index);
/* data to log */ n_vectors);
}
+#if VLIB_BUFFER_TRACE_TRAJECTORY > 0
+void (*vlib_buffer_trace_trajectory_cb) (vlib_buffer_t * b, u32 node_index);
+void (*vlib_buffer_trace_trajectory_init_cb) (vlib_buffer_t * b);
+
void
-vlib_dump_context_trace (vlib_main_t * vm, u32 bi)
+vlib_buffer_trace_trajectory_init (vlib_buffer_t * b)
{
- vlib_node_main_t *vnm = &vm->node_main;
- vlib_buffer_t *b;
- u8 i, n;
-
- if (VLIB_BUFFER_TRACE_TRAJECTORY)
+ if (PREDICT_TRUE (vlib_buffer_trace_trajectory_init_cb != 0))
{
- b = vlib_get_buffer (vm, bi);
- n = b->pre_data[0];
-
- fformat (stderr, "Context trace for bi %d b 0x%llx, visited %d\n",
- bi, b, n);
-
- if (n == 0 || n > 20)
- {
- fformat (stderr, "n is unreasonable\n");
- return;
- }
-
-
- for (i = 0; i < n; i++)
- {
- u32 node_index;
-
- node_index = b->pre_data[i + 1];
+ (*vlib_buffer_trace_trajectory_init_cb) (b);
+ }
+}
- if (node_index > vec_len (vnm->nodes))
- {
- fformat (stderr, "Skip bogus node index %d\n", node_index);
- continue;
- }
+#endif
- fformat (stderr, "%v (%d)\n", vnm->nodes[node_index]->name,
- node_index);
- }
- }
- else
+static inline void
+add_trajectory_trace (vlib_buffer_t * b, u32 node_index)
+{
+#if VLIB_BUFFER_TRACE_TRAJECTORY > 0
+ if (PREDICT_TRUE (vlib_buffer_trace_trajectory_cb != 0))
{
- fformat (stderr,
- "in vlib/buffers.h, #define VLIB_BUFFER_TRACE_TRAJECTORY 1\n");
+ (*vlib_buffer_trace_trajectory_cb) (b, node_index);
}
+#endif
}
-
static_always_inline u64
dispatch_node (vlib_main_t * vm,
vlib_node_runtime_t * node,
if (VLIB_BUFFER_TRACE_TRAJECTORY && frame)
{
int i;
- int log_index;
u32 *from;
from = vlib_frame_vector_args (frame);
for (i = 0; i < frame->n_vectors; i++)
{
vlib_buffer_t *b = vlib_get_buffer (vm, from[i]);
- ASSERT (b->pre_data[0] < 32);
- log_index = b->pre_data[0]++ + 1;
- b->pre_data[log_index] = node->node_index;
+ add_trajectory_trace (b, node->node_index);
}
n = node->function (vm, node, frame);
}
vlib_node_main_t *nm = &vm->node_main;
vlib_node_runtime_t *node_runtime = &p->node_runtime;
vlib_node_t *node = vlib_get_node (vm, node_runtime->node_index);
+ u32 old_process_index;
u64 t;
uword n_vectors, is_suspend;
f ? f->n_vectors : 0, /* is_after */ 0);
/* Save away current process for suspend. */
+ old_process_index = nm->current_process_index;
nm->current_process_index = node->runtime_index;
n_vectors = vlib_process_startup (vm, p, f);
- nm->current_process_index = ~0;
+ nm->current_process_index = old_process_index;
ASSERT (n_vectors != VLIB_PROCESS_RETURN_LONGJMP_RETURN);
is_suspend = n_vectors == VLIB_PROCESS_RETURN_LONGJMP_SUSPEND;
return t;
}
+void vl_api_send_pending_rpc_requests (vlib_main_t *) __attribute__ ((weak));
+void
+vl_api_send_pending_rpc_requests (vlib_main_t * vm)
+{
+}
+
+
static_always_inline void
vlib_main_or_worker_loop (vlib_main_t * vm, int is_main)
{
{
vlib_node_runtime_t *n;
+ if (PREDICT_FALSE (_vec_len (vm->pending_rpc_requests) > 0))
+ vl_api_send_pending_rpc_requests (vm);
+
if (!is_main)
{
vlib_worker_thread_barrier_check ();
}
/* Process pre-input nodes. */
- if (is_main)
- vec_foreach (n, nm->nodes_by_type[VLIB_NODE_TYPE_PRE_INPUT])
- cpu_time_now = dispatch_node (vm, n,
- VLIB_NODE_TYPE_PRE_INPUT,
- VLIB_NODE_STATE_POLLING,
- /* frame */ 0,
- cpu_time_now);
+ vec_foreach (n, nm->nodes_by_type[VLIB_NODE_TYPE_PRE_INPUT])
+ cpu_time_now = dispatch_node (vm, n,
+ VLIB_NODE_TYPE_PRE_INPUT,
+ VLIB_NODE_STATE_POLLING,
+ /* frame */ 0,
+ cpu_time_now);
/* Next process input nodes. */
vec_foreach (n, nm->nodes_by_type[VLIB_NODE_TYPE_INPUT])
/* Next handle interrupts. */
{
+ /* unlocked read, for performance */
uword l = _vec_len (nm->pending_interrupt_node_runtime_indices);
uword i;
- if (l > 0)
+ if (PREDICT_FALSE (l > 0))
{
u32 *tmp;
if (!is_main)
- clib_spinlock_lock (&nm->pending_interrupt_lock);
+ {
+ clib_spinlock_lock (&nm->pending_interrupt_lock);
+ /* Re-read w/ lock held, in case another thread added an item */
+ l = _vec_len (nm->pending_interrupt_node_runtime_indices);
+ }
+
tmp = nm->pending_interrupt_node_runtime_indices;
nm->pending_interrupt_node_runtime_indices =
last_node_runtime_indices;
if (!vm->name)
vm->name = "VLIB";
- vec_validate (vm->buffer_main, 0);
- if (vlib_buffer_callbacks)
+ if ((error = unix_physmem_init (vm)))
{
- /* external plugin has registered own buffer callbacks
- so we just copy them */
- vlib_buffer_main_t *bm = vm->buffer_main;
- clib_memcpy (&bm->cb, vlib_buffer_callbacks,
- sizeof (vlib_buffer_callbacks_t));
- bm->callbacks_registered = 1;
+ clib_error_report (error);
+ goto done;
}
- else
+
+ if ((error = vlib_buffer_main_init (vm)))
{
- vlib_physmem_main_t *vpm = &vm->physmem_main;
- vlib_buffer_cb_init (vm);
- unix_physmem_init (vm, 0 /* fail_if_physical_memory_not_present */ );
- vlib_buffer_add_mem_range (vm, vpm->virtual.start, vpm->virtual.size);
+ clib_error_report (error);
+ goto done;
}
if ((error = vlib_thread_init (vm)))
goto done;
/* Create default buffer free list. */
- vlib_buffer_get_or_create_free_list (vm,
- VLIB_BUFFER_DEFAULT_FREE_LIST_BYTES,
- "default");
+ vlib_buffer_create_free_list (vm, VLIB_BUFFER_DEFAULT_FREE_LIST_BYTES,
+ "default");
nm->timing_wheel = clib_mem_alloc_aligned (sizeof (TWT (tw_timer_wheel)),
CLIB_CACHE_LINE_BYTES);
10e-6 /* timer period 10us */ ,
~0 /* max expirations per call */ );
+ vec_validate (vm->pending_rpc_requests, 0);
+ _vec_len (vm->pending_rpc_requests) = 0;
+
switch (clib_setjmp (&vm->main_loop_exit, VLIB_MAIN_LOOP_EXIT_NONE))
{
case VLIB_MAIN_LOOP_EXIT_NONE: