mirror of
https://github.com/percona/pg_stat_monitor.git
synced 2026-02-04 14:06:20 +00:00
PG-286: Reduce calls to pgstat_fetch_stat_numbackends().
After couple CPU profiling sessions with perf, it was detected that the function pgstat_fetch_stat_numbackends() is very expensive, reading the implementation on PostgreSQL's backend_status.c just confirmed that. We use that function on pg_stat_monitor to retrieve the application name and IP address of the client, we now cache the results in order to avoid calling it for every query being processed.
This commit is contained in:
committed by
Hamid Akhtar
parent
8c61e24f95
commit
b798ffd461
@@ -104,12 +104,11 @@ PG_FUNCTION_INFO_V1(pg_stat_monitor_settings);
|
||||
PG_FUNCTION_INFO_V1(get_histogram_timings);
|
||||
PG_FUNCTION_INFO_V1(pg_stat_monitor_hook_stats);
|
||||
|
||||
static uint pg_get_client_addr(void);
|
||||
static int pg_get_application_name(char* application_name);
|
||||
static uint pg_get_client_addr(bool *ok);
|
||||
static int pg_get_application_name(char *application_name, bool *ok);
|
||||
static PgBackendStatus *pg_get_backend_status(void);
|
||||
static Datum intarray_get_datum(int32 arr[], int len);
|
||||
|
||||
|
||||
#if PG_VERSION_NUM < 140000
|
||||
DECLARE_HOOK(void pgss_post_parse_analyze, ParseState *pstate, Query *query);
|
||||
#else
|
||||
@@ -1132,46 +1131,44 @@ pg_get_backend_status(void)
|
||||
}
|
||||
|
||||
static int
|
||||
pg_get_application_name(char *application_name)
|
||||
pg_get_application_name(char *application_name, bool *ok)
|
||||
{
|
||||
PgBackendStatus *beentry = pg_get_backend_status();
|
||||
if (!beentry)
|
||||
return snprintf(application_name, APPLICATIONNAME_LEN, "%s", "postmaster");
|
||||
|
||||
if (!beentry)
|
||||
return snprintf(application_name, APPLICATIONNAME_LEN, "%s", "unknown");
|
||||
|
||||
*ok = true;
|
||||
|
||||
return snprintf(application_name, APPLICATIONNAME_LEN, "%s", beentry->st_appname);
|
||||
}
|
||||
|
||||
static uint
|
||||
pg_get_client_addr(void)
|
||||
pg_get_client_addr(bool *ok)
|
||||
{
|
||||
PgBackendStatus *beentry = pg_get_backend_status();
|
||||
char remote_host[NI_MAXHOST];
|
||||
int ret;
|
||||
static uint localhost = 0;
|
||||
|
||||
remote_host[0] = '\0';
|
||||
|
||||
if (!beentry)
|
||||
return ntohl(inet_addr("127.0.0.1"));
|
||||
|
||||
*ok = true;
|
||||
|
||||
ret = pg_getnameinfo_all(&beentry->st_clientaddr.addr,
|
||||
beentry->st_clientaddr.salen,
|
||||
remote_host, sizeof(remote_host),
|
||||
NULL, 0,
|
||||
NI_NUMERICHOST | NI_NUMERICSERV);
|
||||
if (ret != 0)
|
||||
{
|
||||
if (localhost == 0)
|
||||
localhost = ntohl(inet_addr("127.0.0.1"));
|
||||
return localhost;
|
||||
}
|
||||
return ntohl(inet_addr("127.0.0.1"));
|
||||
|
||||
if (strcmp(remote_host, "[local]") == 0)
|
||||
{
|
||||
if (localhost == 0)
|
||||
localhost = ntohl(inet_addr("127.0.0.1"));
|
||||
return localhost;
|
||||
}
|
||||
return ntohl(inet_addr("127.0.0.1"));
|
||||
|
||||
return ntohl(inet_addr(remote_host));
|
||||
}
|
||||
@@ -1191,11 +1188,11 @@ pgss_update_entry(pgssEntry *entry,
|
||||
BufferUsage *bufusage,
|
||||
WalUsage *walusage,
|
||||
bool reset,
|
||||
pgssStoreKind kind)
|
||||
pgssStoreKind kind,
|
||||
const char *app_name,
|
||||
size_t app_name_len)
|
||||
{
|
||||
int index;
|
||||
char application_name[APPLICATIONNAME_LEN];
|
||||
int application_name_len = pg_get_application_name(application_name);
|
||||
double old_mean;
|
||||
int message_len = error_info ? strlen (error_info->message) : 0;
|
||||
int comments_len = comments ? strlen (comments) : 0;
|
||||
@@ -1264,11 +1261,11 @@ pgss_update_entry(pgssEntry *entry,
|
||||
e->counters.resp_calls[index]++;
|
||||
}
|
||||
|
||||
if (plan_text_len > 0)
|
||||
if (plan_text_len > 0 && !e->counters.planinfo.plan_text[0])
|
||||
_snprintf(e->counters.planinfo.plan_text, plan_info->plan_text, plan_text_len + 1, PLAN_TEXT_LEN);
|
||||
|
||||
if (application_name_len > 0)
|
||||
_snprintf(e->counters.info.application_name, application_name, application_name_len + 1, APPLICATIONNAME_LEN);
|
||||
if (app_name_len > 0 && !e->counters.info.application_name[0])
|
||||
_snprintf(e->counters.info.application_name, app_name, app_name_len + 1, APPLICATIONNAME_LEN);
|
||||
|
||||
e->counters.info.num_relations = num_relations;
|
||||
_snprintf2(e->counters.info.relations, relations, num_relations, REL_LEN);
|
||||
@@ -1465,8 +1462,8 @@ pgss_store(uint64 queryid,
|
||||
pgssHashKey key;
|
||||
pgssEntry *entry;
|
||||
pgssSharedState *pgss = pgsm_get_ss();
|
||||
char application_name[APPLICATIONNAME_LEN];
|
||||
int application_name_len;
|
||||
static char application_name[APPLICATIONNAME_LEN] = "";
|
||||
static int application_name_len = 0;
|
||||
bool reset = false;
|
||||
uint64 bucketid;
|
||||
uint64 prev_bucket_id;
|
||||
@@ -1474,6 +1471,9 @@ pgss_store(uint64 queryid,
|
||||
uint64 planid;
|
||||
uint64 appid;
|
||||
char comments[512] = "";
|
||||
static bool found_app_name = false;
|
||||
static bool found_client_addr = false;
|
||||
static uint client_addr = 0;
|
||||
|
||||
/* Monitoring is disabled */
|
||||
if (!PGSM_ENABLED)
|
||||
@@ -1492,7 +1492,12 @@ pgss_store(uint64 queryid,
|
||||
else
|
||||
userid = GetUserId();
|
||||
|
||||
application_name_len = pg_get_application_name(application_name);
|
||||
if (!found_app_name)
|
||||
application_name_len = pg_get_application_name(application_name, &found_app_name);
|
||||
|
||||
if (!found_client_addr)
|
||||
client_addr = pg_get_client_addr(&found_client_addr);
|
||||
|
||||
planid = plan_info ? plan_info->planid : 0;
|
||||
appid = djb2_hash((unsigned char *)application_name, application_name_len);
|
||||
|
||||
@@ -1508,7 +1513,7 @@ pgss_store(uint64 queryid,
|
||||
key.userid = userid;
|
||||
key.dbid = MyDatabaseId;
|
||||
key.queryid = queryid;
|
||||
key.ip = pg_get_client_addr();
|
||||
key.ip = client_addr;
|
||||
key.planid = planid;
|
||||
key.appid = appid;
|
||||
#if PG_VERSION_NUM < 140000
|
||||
@@ -1597,7 +1602,9 @@ pgss_store(uint64 queryid,
|
||||
bufusage, /* bufusage */
|
||||
walusage, /* walusage */
|
||||
reset, /* reset */
|
||||
kind); /* kind */
|
||||
kind, /* kind */
|
||||
application_name,
|
||||
application_name_len);
|
||||
|
||||
LWLockRelease(pgss->lock);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user