Skip to content

Commit 4215453

Browse files
LorenzoBianconialmusil
authored andcommitted
lib: inc-proc-eng: Add more debug info to recompute events.
Introduce the get_compute_failure_info callback used to report info about the input node that triggers the parent node recompute. This patch sets the callback just for DB nodes dumping the table name and the row UUID that triggers the recompute when the parent node does not support incremental processing for this input. Following patches will specify get_compute_failure_info callback even for non-DB nodes. Reported-at: https://issues.redhat.com/browse/FDP-1396 Signed-off-by: Lorenzo Bianconi <lorenzo.bianconi@redhat.com> Signed-off-by: Ales Musil <amusil@redhat.com>
1 parent 670f98c commit 4215453

2 files changed

Lines changed: 84 additions & 9 deletions

File tree

lib/inc-proc-eng.c

Lines changed: 34 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -192,6 +192,12 @@ engine_set_log_timeout_cmd(struct unixctl_conn *conn, int argc OVS_UNUSED,
192192
unixctl_command_reply(conn, NULL);
193193
}
194194

195+
static void
196+
engine_get_compute_failure_info(struct engine_node *node)
197+
{
198+
VLOG_DBG("Node \"%s\" is missing compute failure debug info.", node->name);
199+
}
200+
195201
void
196202
engine_init(struct engine_node *node, struct engine_arg *arg)
197203
{
@@ -204,6 +210,11 @@ engine_init(struct engine_node *node, struct engine_arg *arg)
204210
} else {
205211
sorted_node->data = NULL;
206212
}
213+
if (!sorted_node->get_compute_failure_info) {
214+
/* Provide default get_compute_failure_info implementation. */
215+
sorted_node->get_compute_failure_info =
216+
engine_get_compute_failure_info;
217+
}
207218
}
208219

209220
unixctl_command_register("inc-engine/show-stats", "", 0, 2,
@@ -264,6 +275,17 @@ engine_add_input(struct engine_node *node, struct engine_node *input,
264275
node->n_inputs ++;
265276
}
266277

278+
void
279+
engine_add_input_with_compute_debug(
280+
struct engine_node *node, struct engine_node *input,
281+
enum engine_input_handler_result (*change_handler)
282+
(struct engine_node *, void *),
283+
void (*get_compute_failure_info)(struct engine_node *))
284+
{
285+
engine_add_input(node, input, change_handler);
286+
node->get_compute_failure_info = get_compute_failure_info;
287+
}
288+
267289
struct ovsdb_idl_index *
268290
engine_ovsdb_node_get_index(struct engine_node *node, const char *name)
269291
{
@@ -440,8 +462,10 @@ static bool
440462
engine_compute(struct engine_node *node, bool recompute_allowed)
441463
{
442464
for (size_t i = 0; i < node->n_inputs; i++) {
465+
struct engine_node *input_node = node->inputs[i].node;
466+
443467
/* If the input node data changed call its change handler. */
444-
if (node->inputs[i].node->state == EN_UPDATED) {
468+
if (input_node->state == EN_UPDATED) {
445469
/* If the input change can't be handled incrementally, run
446470
* the node handler.
447471
*/
@@ -453,25 +477,24 @@ engine_compute(struct engine_node *node, bool recompute_allowed)
453477
static struct vlog_rate_limit rl =
454478
VLOG_RATE_LIMIT_INIT(20, 10);
455479
VLOG_INFO_RL(&rl, "node: %s, handler for input %s took %lldms",
456-
node->name, node->inputs[i].node->name,
457-
delta_time);
480+
node->name, input_node->name, delta_time);
458481
} else {
459482
VLOG_DBG("node: %s, handler for input %s took %lldms",
460-
node->name, node->inputs[i].node->name, delta_time);
483+
node->name, input_node->name, delta_time);
461484
}
462485
if (handled == EN_UNHANDLED) {
486+
input_node->get_compute_failure_info(input_node);
463487
engine_recompute(node, recompute_allowed,
464488
"failed handler for input %s",
465-
node->inputs[i].node->name);
489+
input_node->name);
466490
return (node->state != EN_CANCELED);
467491
} else if (!engine_node_changed(node)) {
468492
/* We only want to update the state if the node is unchanged.
469493
* Otherwise, handlers might change the state from EN_UPDATED
470494
* back to EN_UNCHANGED.
471495
*/
472496
engine_set_node_state(node, (enum engine_node_state) handled,
473-
"input %s updated",
474-
node->inputs[i].node->name);
497+
"input %s updated", input_node->name);
475498
}
476499
}
477500
}
@@ -501,14 +524,16 @@ engine_run_node(struct engine_node *node, bool recompute_allowed)
501524
*/
502525
bool need_compute = false;
503526
for (size_t i = 0; i < node->n_inputs; i++) {
504-
if (node->inputs[i].node->state == EN_UPDATED) {
527+
struct engine_node *input_node = node->inputs[i].node;
528+
if (input_node->state == EN_UPDATED) {
505529
need_compute = true;
506530

507531
/* Trigger a recompute if we don't have a change handler. */
508532
if (!node->inputs[i].change_handler) {
509533
engine_recompute(node, recompute_allowed,
510534
"missing handler for input %s",
511-
node->inputs[i].node->name);
535+
input_node->name);
536+
input_node->get_compute_failure_info(input_node);
512537
return;
513538
}
514539
}

lib/inc-proc-eng.h

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -265,6 +265,11 @@ struct engine_node {
265265
* engine 'data'. It may be NULL. */
266266
void (*clear_tracked_data)(void *tracked_data);
267267

268+
/* Method used to dump info about node input compute failues. It may be
269+
* NULL.
270+
*/
271+
void (*get_compute_failure_info)(struct engine_node *);
272+
268273
/* Engine stats. */
269274
struct engine_stats stats;
270275
};
@@ -308,6 +313,11 @@ void *engine_get_input_data(const char *input_name, struct engine_node *);
308313
void engine_add_input(struct engine_node *node, struct engine_node *input,
309314
enum engine_input_handler_result (*change_handler)
310315
(struct engine_node *, void *));
316+
void engine_add_input_with_compute_debug(
317+
struct engine_node *node, struct engine_node *input,
318+
enum engine_input_handler_result (*change_handler)
319+
(struct engine_node *, void *),
320+
void (*get_compute_failure_info)(struct engine_node *));
311321

312322
/* Force the engine to recompute everything. It is used
313323
* in circumstances when we are not sure there is change or not, or
@@ -422,6 +432,9 @@ void engine_ovsdb_node_add_index(struct engine_node *, const char *name,
422432
#define IS_VALID(NAME) \
423433
.is_valid = en_##NAME##_is_valid
424434

435+
#define COMPUTE_FAIL_INFO(NAME) \
436+
.get_compute_failure_info = en_##NAME##_compute_failure_info,
437+
425438
#define ENGINE_NODE2(NAME, ARG1) \
426439
ENGINE_NODE_DEF_START(NAME, #NAME) \
427440
ARG1(NAME), \
@@ -460,6 +473,42 @@ static void *en_##DB_NAME##_##TBL_NAME##_init( \
460473
} \
461474
static void en_##DB_NAME##_##TBL_NAME##_cleanup(void *data OVS_UNUSED) \
462475
{ \
476+
} \
477+
static void \
478+
en_##DB_NAME##_##TBL_NAME##_compute_failure_info(struct engine_node *node) \
479+
{ \
480+
if (!VLOG_IS_DBG_ENABLED()) { \
481+
return; \
482+
} \
483+
const struct ovsdb_idl *table = EN_OVSDB_GET(node); \
484+
const struct ovsdb_idl_row *row; \
485+
struct ds s = DS_EMPTY_INITIALIZER; \
486+
ds_put_format(&s, "Node \"%s\" compute failure info:\n", node->name); \
487+
for ((row) = ovsdb_idl_track_get_first(table, \
488+
&DB_NAME##rec_table_##TBL_NAME); \
489+
(row); (row) = ovsdb_idl_track_get_next(row)) { \
490+
if (ovsdb_idl_row_get_seqno((row), OVSDB_IDL_CHANGE_INSERT) > 0) { \
491+
ds_put_format(&s, "%s (New) "UUID_FMT"\n", \
492+
#DB_NAME"_"#TBL_NAME, UUID_ARGS(&row->uuid)); \
493+
} else if (ovsdb_idl_row_get_seqno((row), \
494+
OVSDB_IDL_CHANGE_DELETE) > 0) { \
495+
ds_put_format(&s, "%s (Deleted) "UUID_FMT"\n", \
496+
#DB_NAME"_"#TBL_NAME, UUID_ARGS(&row->uuid)); \
497+
} else { \
498+
ds_put_format(&s, "%s (Updated) "UUID_FMT" columns:", \
499+
#DB_NAME"_"#TBL_NAME, UUID_ARGS(&row->uuid)); \
500+
for (size_t i = 0; i < row->table->class_->n_columns; i++) { \
501+
struct ovsdb_idl_column *col = \
502+
&DB_NAME##rec_##TBL_NAME##_columns[i]; \
503+
if (ovsdb_idl_track_is_updated(row, col)) { \
504+
ds_put_format(&s, " %s,", col->name); \
505+
} \
506+
} \
507+
ds_chomp(&s, ','); \
508+
} \
509+
} \
510+
VLOG_DBG("%s", ds_cstr(&s)); \
511+
ds_destroy(&s); \
463512
}
464513

465514
/* Macro to define member functions of an engine node which represents
@@ -480,6 +529,7 @@ static void en_##DB_NAME##_##TBL_NAME##_cleanup(void *data OVS_UNUSED) \
480529
/* Macro to define an engine node which represents a table of OVSDB */
481530
#define ENGINE_NODE_OVSDB(DB_NAME, DB_NAME_STR, TBL_NAME, TBL_NAME_STR) \
482531
ENGINE_NODE_DEF_START(DB_NAME##_##TBL_NAME, DB_NAME_STR"_"TBL_NAME_STR) \
532+
COMPUTE_FAIL_INFO(DB_NAME##_##TBL_NAME) \
483533
ENGINE_NODE_DEF_END
484534

485535
/* Macro to define an engine node which represents a table of OVN SB DB */

0 commit comments

Comments
 (0)