/* Copyright (c) 2017-2018 Dovecot authors, see the included COPYING file */
#include "lib.h"
#include "str.h"
#include "strescape.h"
#include "ostream.h"
#include "time-util.h"
#include "lib-event-private.h"
#include "event-filter.h"
#include "connection.h"
#include "stats-client.h"
struct stats_client {
bool handshaked;
bool silent_notfound_errors;
};
static int
const char **error_r)
{
*error_r = "Expected FILTER";
return -1;
}
*filter_r = event_filter_create();
return -1;
}
return 0;
}
static int
{
const char *error;
i_error("stats: Received invalid handshake: %s (input: %s)",
return -1;
}
/* Filter is already set. It becomes a bit complicated to
change it. Since it's most likely exactly the same filter
anyway, just keep the old one. */
return 1;
}
if (event_get_global_debug_send_filter() != NULL) {
/* merge into the global debug send filter */
} else {
/* no global filter yet - use this */
}
return 1;
}
static int
{
if (!client->handshaked)
i_error("stats: Received unexpected input: %s",
return 0;
}
{
}
{
/* after reconnection the IDs need to be re-sent */
/* waiting for stats handshake to finish */
int msecs_since_connected =
&conn->connect_finished);
/* reconnect immdiately */
reconnect_msecs = 0;
} else {
/* wait for reconnect interval since we last
were connected. */
}
}
}
}
.service_name_in = "stats-server",
.service_name_out = "stats-client",
.major_version = 2,
.minor_version = 0,
};
};
{
unsigned int count;
return parent;
/* avoid sending unnecessary events that don't add anything */
if (count > 0)
return parent;
if (count > 0)
return parent;
return stats_event_get_parent(parent);
}
{
/* FIXME: we could use create-timestamp of the events to figure out
whether to use BEGIN or to just merge the categories and fields
to the same EVENT. If the parent's timestamp is the same as ours,
don't bother using BEGIN for parent. */
if (parent_event != NULL) {
if (!parent_event->id_sent_to_stats)
}
if (begin) {
} else {
}
}
static void
{
return;
}
static void
{
if (!event->id_sent_to_stats)
return;
}
static bool
{
return TRUE;
return TRUE;
switch (type) {
break;
case EVENT_CALLBACK_TYPE_FREE:
break;
}
return TRUE;
}
static void
{
}
}
{
return;
return;
}
static void stats_global_init(void)
{
}
static void stats_global_deinit(void)
{
}
{
}
{
unsigned int i, count;
for (i = 0; i < count; i++)
}
{
/* read the handshake so the global debug filter is updated */
} else if (!client->silent_notfound_errors ||
}
}
struct stats_client *
{
if (stats_clients == NULL)
return client;
}
{
}