while (cqe->phase != phase)
{
- vnet_dev_process_suspend (vm, suspend_time);
+ vlib_process_suspend (vm, suspend_time);
suspend_time *= 2;
if (suspend_time > 1e-3)
{
break;
if (i++ == 20)
return ena_err (dev, VNET_DEV_ERR_BUS, "failed to initiate reset");
- vnet_dev_process_suspend (vm, 0.001);
+ vlib_process_suspend (vm, 0.001);
}
ena_reg_write (dev, ENA_REG_DEV_CTL, &(ena_reg_dev_ctl_t){});
break;
if (i++ == 20)
return ena_err (dev, VNET_DEV_ERR_BUS, "failed to complete reset");
- vnet_dev_process_suspend (vm, 0.001);
+ vlib_process_suspend (vm, 0.001);
}
ena_reg_read (dev, ENA_REG_VERSION, &ver);
return VNET_DEV_ERR_TIMEOUT;
}
- vnet_dev_process_suspend (vm, suspend_time);
+ vlib_process_suspend (vm, suspend_time);
suspend_time *= 2;
}
}
if (vlib_time_now (vm) - t0 > timeout)
return 0;
- vnet_dev_process_suspend (vm, suspend_time);
+ vlib_process_suspend (vm, suspend_time);
suspend_time *= 2;
}
{
if (n_tries-- == 0)
return VNET_DEV_ERR_TIMEOUT;
- vnet_dev_process_suspend (vm, 0.02);
+ vlib_process_suspend (vm, 0.02);
}
while ((iavf_reg_read (ad, IAVF_VFGEN_RSTAT) & 3) != 2);
return err;
}
-static clib_error_t *
-devices_config (vlib_main_t *vm, unformat_input_t *input)
+uword
+dev_config_process_node_fn (vlib_main_t *vm, vlib_node_runtime_t *rt,
+ vlib_frame_t *f)
{
+ vnet_dev_main_t *dm = &vnet_dev_main;
vnet_dev_driver_name_t driver_name;
+ unformat_input_t input;
clib_error_t *err = 0;
+ u32 *i;
+
+ if (dm->startup_config == 0)
+ goto done;
- while (!err && unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
+ unformat_init_vector (&input, dm->startup_config);
+ dm->startup_config = 0;
+
+ while (!err && unformat_check_input (&input) != UNFORMAT_END_OF_INPUT)
{
unformat_input_t sub_input;
vnet_dev_device_id_t device_id;
- if (unformat (input, "dev %U %U", unformat_c_string_array, device_id,
+ if (unformat (&input, "dev %U %U", unformat_c_string_array, device_id,
sizeof (device_id), unformat_vlib_cli_sub_input,
&sub_input))
{
err = vnet_dev_config_one_device (vm, &sub_input, device_id);
unformat_free (&sub_input);
}
- else if (unformat (input, "dev %U", unformat_c_string_array, device_id,
+ else if (unformat (&input, "dev %U", unformat_c_string_array, device_id,
sizeof (device_id)))
{
unformat_input_t no_input = {};
err = vnet_dev_config_one_device (vm, &no_input, device_id);
unformat_free (&no_input);
}
- else if (unformat (input, "driver %U %U", unformat_c_string_array,
+ else if (unformat (&input, "driver %U %U", unformat_c_string_array,
driver_name, sizeof (driver_name),
unformat_vlib_cli_sub_input, &sub_input))
{
format_unformat_error, &input);
}
- unformat_free (input);
+ unformat_free (&input);
- return err;
+ if (err)
+ {
+ log_err (0, "%U", format_clib_error, err);
+ clib_error_free (err);
+ }
+
+done:
+ dm->startup_config_completed = 1;
+ vec_foreach (i, dm->process_nodes_waiting_for_startup_conf)
+ vlib_process_signal_event (vm, *i, 0, 0);
+ vec_free (dm->process_nodes_waiting_for_startup_conf);
+
+ vlib_node_set_state (vm, rt->node_index, VLIB_NODE_STATE_DISABLED);
+ vlib_node_rename (vm, rt->node_index, "deleted-%u", rt->node_index);
+ vec_add1 (dm->free_process_node_indices, rt->node_index);
+ return 0;
+}
+
+VLIB_REGISTER_NODE (dev_config_process_node) = {
+ .function = dev_config_process_node_fn,
+ .type = VLIB_NODE_TYPE_PROCESS,
+ .name = "dev-config",
+};
+
+static clib_error_t *
+devices_config (vlib_main_t *vm, unformat_input_t *input)
+{
+ vnet_dev_main_t *dm = &vnet_dev_main;
+ uword c;
+
+ while ((c = unformat_get_input (input)) != UNFORMAT_END_OF_INPUT)
+ vec_add1 (dm->startup_config, c);
+
+ return 0;
}
VLIB_CONFIG_FUNCTION (devices_config, "devices");
+
+void
+vnet_dev_wait_for_startup_config_complete (vlib_main_t *vm)
+{
+ vnet_dev_main_t *dm = &vnet_dev_main;
+ uword *event_data = 0;
+
+ if (dm->startup_config_completed)
+ return;
+
+ vec_add1 (dm->process_nodes_waiting_for_startup_conf,
+ vlib_get_current_process_node_index (vm));
+ vlib_process_wait_for_event (vm);
+ vlib_process_get_events (vm, &event_data);
+ vec_free (event_data);
+}
temp_space_sz = r->runtime_temp_space_sz;
}
+ if (dm->startup_config)
+ log_debug (0, "startup config: %v", dm->startup_config);
+
vec_free (drv);
if (temp_space_sz > 0)
u32 *free_rx_node_indices;
uword *device_index_by_id;
+ /* startup config */
+ u8 *startup_config;
+ u32 *process_nodes_waiting_for_startup_conf;
+ u8 startup_config_completed;
+
u16 next_rx_queue_thread;
u8 eth_port_rx_feature_arc_index;
- u8 main_loop_running;
} vnet_dev_main_t;
extern vnet_dev_main_t vnet_dev_main;
format_function_t format_vnet_dev_arg_value;
format_function_t format_vnet_dev_args;
+/* config.c */
+void vnet_dev_wait_for_startup_config_complete (vlib_main_t *);
+
/* dev.c */
vnet_dev_t *vnet_dev_alloc (vlib_main_t *, vnet_dev_device_id_t,
vnet_dev_driver_t *);
static_always_inline void
vnet_dev_validate (vlib_main_t *vm, vnet_dev_t *dev)
{
- vnet_dev_main_t *dm = &vnet_dev_main;
- ASSERT (!dm->main_loop_running ||
- dev->process_node_index == vlib_get_current_process_node_index (vm));
+ ASSERT (dev->process_node_index == vlib_get_current_process_node_index (vm));
ASSERT (vm->thread_index == 0);
}
static_always_inline void
vnet_dev_port_validate (vlib_main_t *vm, vnet_dev_port_t *port)
{
- vnet_dev_main_t *dm = &vnet_dev_main;
- ASSERT (!dm->main_loop_running ||
- port->dev->process_node_index ==
- vlib_get_current_process_node_index (vm));
+ ASSERT (port->dev->process_node_index ==
+ vlib_get_current_process_node_index (vm));
ASSERT (vm->thread_index == 0);
}
return arg->val_set ? arg->val.string : arg->default_val.string;
}
-static_always_inline void
-vnet_dev_process_suspend (vlib_main_t *vm, f64 t)
-{
- if (!vnet_dev_main.main_loop_running)
- {
- t += vlib_time_now (vm);
-
- while (vlib_time_now (vm) < t)
- CLIB_PAUSE ();
- }
- else
- vlib_process_suspend (vm, t);
-}
-
-static_always_inline void
-vnet_dev_process_yield (vlib_main_t *vm, f64 t)
-{
- if (vnet_dev_main.main_loop_running)
- vlib_process_yield (vm);
-}
-
#endif /* _VNET_DEV_FUNCS_H_ */
vnet_dev_process_event_send_and_wait (vlib_main_t *vm, vnet_dev_t *dev,
vnet_dev_event_data_t *ed)
{
- vnet_dev_main_t *dm = &vnet_dev_main;
+ ed->calling_process_index = vlib_get_current_process_node_index (vm);
vnet_dev_rv_t rv = VNET_DEV_ERR_PROCESS_REPLY;
ed->reply_needed = 1;
- if (!dm->main_loop_running)
- {
- vnet_dev_process_one_event (vm, dev, ed);
- rv = ed->rv;
- goto done;
- }
-
- ed->calling_process_index = vlib_get_current_process_node_index (vm);
-
if (ed->calling_process_index == dev->process_node_index)
{
vnet_dev_process_one_event (vm, dev, ed);
vnet_dev_process_event_send (vm, port->dev, ed);
}
-
-static clib_error_t *
-vnet_dev_main_loop_init (vlib_main_t *vm)
-{
- vnet_dev_main_t *dm = &vnet_dev_main;
- dm->main_loop_running = 1;
- return 0;
-}
-
-VLIB_MAIN_LOOP_ENTER_FUNCTION (vnet_dev_main_loop_init);