// SPDX-License-Identifier: GPL-3.0-or-later
#include "internal.h"
#define QUERY_TARGET_MAX_REALLOC_INCREASE 500
#define query_target_realloc_size(size, start) \
(size) ? ((size) < QUERY_TARGET_MAX_REALLOC_INCREASE ? (size) * 2 : (size) + QUERY_TARGET_MAX_REALLOC_INCREASE) : (start);
static void query_metric_release(QUERY_TARGET *qt, QUERY_METRIC *qm);
static void query_dimension_release(QUERY_DIMENSION *qd);
static void query_instance_release(QUERY_INSTANCE *qi);
static void query_context_release(QUERY_CONTEXT *qc);
static void query_node_release(QUERY_NODE *qn);
static __thread QUERY_TARGET thread_query_target = {};
// ----------------------------------------------------------------------------
// query API
typedef struct query_target_locals {
time_t start_s;
QUERY_TARGET *qt;
RRDSET *st;
const char *scope_nodes;
const char *scope_contexts;
const char *nodes;
const char *contexts;
const char *instances;
const char *dimensions;
const char *chart_label_key;
const char *labels;
const char *alerts;
long long after;
long long before;
bool match_ids;
bool match_names;
size_t metrics_skipped_due_to_not_matching_timeframe;
char host_uuid_buffer[UUID_STR_LEN];
QUERY_NODE *qn; // temp to pass on callbacks, ignore otherwise - no need to free
} QUERY_TARGET_LOCALS;
void query_target_release(QUERY_TARGET *qt) {
if(unlikely(!qt || !qt->used)) return;
simple_pattern_free(qt->nodes.scope_pattern);
qt->nodes.scope_pattern = NULL;
simple_pattern_free(qt->nodes.pattern);
qt->nodes.pattern = NULL;
simple_pattern_free(qt->contexts.scope_pattern);
qt->contexts.scope_pattern = NULL;
simple_pattern_free(qt->contexts.pattern);
qt->contexts.pattern = NULL;
simple_pattern_free(qt->instances.pattern);
qt->instances.pattern = NULL;
simple_pattern_free(qt->instances.chart_label_key_pattern);
qt->instances.chart_label_key_pattern = NULL;
simple_pattern_free(qt->instances.labels_pattern);
qt->instances.labels_pattern = NULL;
simple_pattern_free(qt->query.pattern);
qt->query.pattern = NULL;
// release the query
for(size_t i = 0, used = qt->query.used; i < used ;i++) {
QUERY_METRIC *qm = query_metric(qt, i);
query_metric_release(qt, qm);
}
qt->query.used = 0;
// release the dimensions
for(size_t i = 0, used = qt->dimensions.used; i