@cryptotaxi247 / netdata-1 / commits / 62ea17c88

added checksum to detect corruption in netdev rename tasks (#20048)

Costa Tsaousis committed Apr 3, 2025 at 18:06 UTC 62ea17c887f0e3a7633517a723a0b13dcbb4f116
3 files changed +94 -49
src/collectors/proc.plugin/proc_net_dev.c
+53 -46
@@ -317,60 +317,65 @@ static void netdev_charts_release(struct netdev *d) {
317 }
318
319 static void netdev_free_chart_strings(struct netdev *d) {
320 - freez((void *)d->chart_type_net_bytes);
321 - freez((void *)d->chart_type_net_compressed);
322 - freez((void *)d->chart_type_net_drops);
323 - freez((void *)d->chart_type_net_errors);
324 - freez((void *)d->chart_type_net_events);
325 - freez((void *)d->chart_type_net_fifo);
326 - freez((void *)d->chart_type_net_packets);
327 - freez((void *)d->chart_type_net_speed);
328 - freez((void *)d->chart_type_net_duplex);
329 - freez((void *)d->chart_type_net_operstate);
330 - freez((void *)d->chart_type_net_carrier);
331 - freez((void *)d->chart_type_net_mtu);
332 -
333 - freez((void *)d->chart_id_net_bytes);
334 - freez((void *)d->chart_id_net_compressed);
335 - freez((void *)d->chart_id_net_drops);
336 - freez((void *)d->chart_id_net_errors);
337 - freez((void *)d->chart_id_net_events);
338 - freez((void *)d->chart_id_net_fifo);
339 - freez((void *)d->chart_id_net_packets);
340 - freez((void *)d->chart_id_net_speed);
341 - freez((void *)d->chart_id_net_duplex);
342 - freez((void *)d->chart_id_net_operstate);
343 - freez((void *)d->chart_id_net_carrier);
344 - freez((void *)d->chart_id_net_mtu);
345 -
346 - freez((void *)d->chart_ctx_net_bytes);
347 - freez((void *)d->chart_ctx_net_compressed);
348 - freez((void *)d->chart_ctx_net_drops);
349 - freez((void *)d->chart_ctx_net_errors);
350 - freez((void *)d->chart_ctx_net_events);
351 - freez((void *)d->chart_ctx_net_fifo);
352 - freez((void *)d->chart_ctx_net_packets);
353 - freez((void *)d->chart_ctx_net_speed);
354 - freez((void *)d->chart_ctx_net_duplex);
355 - freez((void *)d->chart_ctx_net_operstate);
356 - freez((void *)d->chart_ctx_net_carrier);
357 - freez((void *)d->chart_ctx_net_mtu);
358 -
359 - freez((void *)d->chart_family);
320 + freez_and_set_to_null(d->chart_type_net_bytes);
321 + freez_and_set_to_null(d->chart_type_net_compressed);
322 + freez_and_set_to_null(d->chart_type_net_drops);
323 + freez_and_set_to_null(d->chart_type_net_errors);
324 + freez_and_set_to_null(d->chart_type_net_events);
325 + freez_and_set_to_null(d->chart_type_net_fifo);
326 + freez_and_set_to_null(d->chart_type_net_packets);
327 + freez_and_set_to_null(d->chart_type_net_speed);
328 + freez_and_set_to_null(d->chart_type_net_duplex);
329 + freez_and_set_to_null(d->chart_type_net_operstate);
330 + freez_and_set_to_null(d->chart_type_net_carrier);
331 + freez_and_set_to_null(d->chart_type_net_mtu);
332 +
333 + freez_and_set_to_null(d->chart_id_net_bytes);
334 + freez_and_set_to_null(d->chart_id_net_compressed);
335 + freez_and_set_to_null(d->chart_id_net_drops);
336 + freez_and_set_to_null(d->chart_id_net_errors);
337 + freez_and_set_to_null(d->chart_id_net_events);
338 + freez_and_set_to_null(d->chart_id_net_fifo);
339 + freez_and_set_to_null(d->chart_id_net_packets);
340 + freez_and_set_to_null(d->chart_id_net_speed);
341 + freez_and_set_to_null(d->chart_id_net_duplex);
342 + freez_and_set_to_null(d->chart_id_net_operstate);
343 + freez_and_set_to_null(d->chart_id_net_carrier);
344 + freez_and_set_to_null(d->chart_id_net_mtu);
345 +
346 + freez_and_set_to_null(d->chart_ctx_net_bytes);
347 + freez_and_set_to_null(d->chart_ctx_net_compressed);
348 + freez_and_set_to_null(d->chart_ctx_net_drops);
349 + freez_and_set_to_null(d->chart_ctx_net_errors);
350 + freez_and_set_to_null(d->chart_ctx_net_events);
351 + freez_and_set_to_null(d->chart_ctx_net_fifo);
352 + freez_and_set_to_null(d->chart_ctx_net_packets);
353 + freez_and_set_to_null(d->chart_ctx_net_speed);
354 + freez_and_set_to_null(d->chart_ctx_net_duplex);
355 + freez_and_set_to_null(d->chart_ctx_net_operstate);
356 + freez_and_set_to_null(d->chart_ctx_net_carrier);
357 + freez_and_set_to_null(d->chart_ctx_net_mtu);
358 +
359 + freez_and_set_to_null(d->chart_family);
360 }
361
362 static void netdev_free(struct netdev *d) {
363 netdev_charts_release(d);
364 netdev_free_chart_strings(d);
365 +
366 rrdlabels_destroy(d->chart_labels);
367 + d->chart_labels = NULL;
368 +
369 cgroup_netdev_release(d->cgroup_netdev_link);
370 + d->cgroup_netdev_link = NULL;
371 +
372 + freez_and_set_to_null(d->name);
373 + freez_and_set_to_null(d->filename_speed);
374 + freez_and_set_to_null(d->filename_duplex);
375 + freez_and_set_to_null(d->filename_operstate);
376 + freez_and_set_to_null(d->filename_carrier);
377 + freez_and_set_to_null(d->filename_mtu);
378
368 - freez((void *)d->name);
369 - freez((void *)d->filename_speed);
370 - freez((void *)d->filename_duplex);
371 - freez((void *)d->filename_operstate);
372 - freez((void *)d->filename_carrier);
373 - freez((void *)d->filename_mtu);
379 freez((void *)d);
380 }
381
@@ -379,6 +384,8 @@ static netdata_mutex_t netdev_mutex = NETDATA_MUTEX_INITIALIZER;
384 // ----------------------------------------------------------------------------
385
386 static inline void netdev_rename(struct netdev *d, struct rename_task *r) {
387 + rename_task_verify_checksum(r);
388 +
389 collector_info("CGROUP: renaming network interface '%s' as '%s' under '%s'", d->name, r->container_device, r->container_name);
390
391 netdev_charts_release(d);
src/collectors/proc.plugin/proc_net_dev_renames.c
+33 -3
@@ -4,14 +4,40 @@
4
5 DICTIONARY *netdev_renames = NULL;
6
7 +static XXH64_hash_t rename_task_hash(struct rename_task *r) {
8 + struct rename_task local_copy = *r;
9 + local_copy.checksum = 0;
10 + return XXH3_64bits(&local_copy, sizeof(local_copy));
11 +}
12 +
13 +// Set the checksum for a rename_task
14 +static void rename_task_set_checksum(struct rename_task *r) {
15 + r->checksum = rename_task_hash(r);
16 +}
17 +
18 +// Verify the checksum for a rename_task
19 +void rename_task_verify_checksum(struct rename_task *r) {
20 + if(r->checksum != rename_task_hash(r))
21 + fatal("MEMORY CORRUPTION DETECTED in rename_task structure. "
22 + "Expected checksum: 0x%016" PRIx64 ", "
23 + "Calculated checksum: 0x%016" PRIx64,
24 + r->checksum, rename_task_hash(r));
25 +}
26 +
27 static void dictionary_netdev_rename_delete_cb(const DICTIONARY_ITEM *item __maybe_unused, void *value, void *data __maybe_unused) {
28 struct rename_task *r = value;
29
30 + rename_task_verify_checksum(r);
31 +
32 cgroup_netdev_release(r->cgroup_netdev_link);
33 + r->cgroup_netdev_link = NULL;
34 +
35 rrdlabels_destroy(r->chart_labels);
12 - freez((void *) r->container_name);
13 - freez((void *) r->container_device);
14 - freez((void *) r->ctx_prefix);
36 + r->chart_labels = NULL;
37 +
38 + freez_and_set_to_null(r->container_name);
39 + freez_and_set_to_null(r->container_device);
40 + freez_and_set_to_null(r->ctx_prefix);
41 }
42
43 void netdev_renames_init(void) {
@@ -41,8 +67,12 @@ void cgroup_rename_task_add(
67 .ctx_prefix = strdupz(ctx_prefix),
68 .chart_labels = rrdlabels_create(),
69 .cgroup_netdev_link = cgroup_netdev_link,
70 + .checksum = 0, // Will be set below
71 };
72 rrdlabels_migrate_to_these(tmp.chart_labels, labels);
73 +
74 + // Set the checksum after all fields are initialized
75 + rename_task_set_checksum(&tmp);
76
77 dictionary_set(netdev_renames, host_device, &tmp, sizeof(tmp));
78 }
src/collectors/proc.plugin/proc_net_dev_renames.h
+8
@@ -5,6 +5,11 @@
5
6 #include "plugin_proc.h"
7
8 +#define freez_and_set_to_null(p) do { \
9 + freez((void *)p); \
10 + p = NULL; \
11 +} while(0)
12 +
13 extern DICTIONARY *netdev_renames;
14
15 struct rename_task {
@@ -13,10 +18,13 @@ struct rename_task {
18 const char *ctx_prefix;
19 RRDLABELS *chart_labels;
20 const DICTIONARY_ITEM *cgroup_netdev_link;
21 + XXH64_hash_t checksum;
22 };
23
24 void netdev_renames_init(void);
25
26 +void rename_task_verify_checksum(struct rename_task *r);
27 +
28 void cgroup_netdev_reset_all(void);
29 void cgroup_netdev_release(const DICTIONARY_ITEM *link);
30 const void *cgroup_netdev_dup(const DICTIONARY_ITEM *link);