Additional checks during metric page list retrieval (#21575)
Add null check for UUID and improve metric list size validation in journal v2 processing
Stelios Fragkakis committed
Jan 16, 2026 at 10:48 UTC
28ca505ece86e0b866dc1cab272045cc0959b49c
1 file changed
+13
-4
src/database/engine/pagecache.c
+13
-4
@@ -485,8 +485,15 @@ static ALWAYS_INLINE_HOT size_t list_has_time_gaps(
485
// ----------------------------------------------------------------------------
486
487
typedef void (*page_found_callback_t)(PGC_PAGE *page, void *data);
488
-static NOT_INLINE_HOT size_t get_page_list_from_journal_v2(struct rrdengine_instance *ctx, METRIC *metric, usec_t start_time_ut, usec_t end_time_ut, page_found_callback_t callback, void *callback_data) {
488
+
489
+static NOT_INLINE_HOT size_t get_page_list_from_journal_v2(struct rrdengine_instance *ctx, METRIC *metric,
490
+ usec_t start_time_ut, usec_t end_time_ut,
491
+ page_found_callback_t callback, void *callback_data)
492
+{
493
nd_uuid_t *uuid = mrg_metric_uuid(main_mrg, metric);
494
+ if (unlikely(!uuid))
495
+ return 0;
496
+
497
Word_t metric_id = mrg_metric_id(main_mrg, metric);
498
499
time_t wanted_start_time_s = (time_t)(start_time_ut / USEC_PER_SEC);
@@ -523,11 +530,13 @@ static NOT_INLINE_HOT size_t get_page_list_from_journal_v2(struct rrdengine_inst
530
struct journal_metric_list *uuid_list =
531
(struct journal_metric_list *)((uint8_t *)j2_header + j2_header->metric_offset);
532
size_t metric_offset = (uint8_t *)uuid_list - (uint8_t *)j2_header;
526
- if (metric_offset >= journal_v2_file_size) {
533
+
534
+ size_t metric_list_size = journal_metric_count * sizeof(*uuid_list);
535
+ if (metric_offset + metric_list_size > journal_v2_file_size) {
536
nd_log_limit_static_thread_var(erl, 60, 0);
537
nd_log_limit(&erl, NDLS_DAEMON, NDLP_ERR,
529
- "DBENGINE: Invalid metric list header in journalfile %u of tier %u",
530
- datafile->fileno, datafile->tier);
538
+ "DBENGINE: Metric list exceeds journal file size in journalfile %u of tier %u (metric_offset=%zu, list_size=%zu, file_size=%zu)",
539
+ datafile->fileno, datafile->tier, metric_offset, metric_list_size, journal_v2_file_size);
540
journalfile_v2_data_release(datafile->journalfile);
541
continue;
542
}