mirror of
https://github.com/timescale/timescaledb.git
synced 2025-05-23 22:41:34 +08:00
Merged in enordstr/backend-database/enordstr/no-storage-for-negative-cache-entries (pull request #119)
Avoid allocating hypertable cache storage for negative entries. Approved-by: Olof Rensfelt Approved-by: ci-vast
This commit is contained in:
commit
5f4b158c83
@ -17,18 +17,18 @@
|
|||||||
#include "scanner.h"
|
#include "scanner.h"
|
||||||
#include "partitioning.h"
|
#include "partitioning.h"
|
||||||
|
|
||||||
static void *hypertable_cache_create_entry(Cache *cache, CacheQueryCtx *ctx);
|
static void *hypertable_cache_create_entry(Cache * cache, CacheQueryCtx * ctx);
|
||||||
|
|
||||||
typedef struct HypertableCacheQueryCtx
|
typedef struct HypertableCacheQueryCtx
|
||||||
{
|
{
|
||||||
CacheQueryCtx cctx;
|
CacheQueryCtx cctx;
|
||||||
Oid main_table_relid;
|
Oid main_table_relid;
|
||||||
char *schema;
|
const char *schema;
|
||||||
char *table_name;
|
const char *table;
|
||||||
} HypertableCacheQueryCtx;
|
} HypertableCacheQueryCtx;
|
||||||
|
|
||||||
static void *
|
static void *
|
||||||
hypertable_cache_get_key(CacheQueryCtx *ctx)
|
hypertable_cache_get_key(CacheQueryCtx * ctx)
|
||||||
{
|
{
|
||||||
return &((HypertableCacheQueryCtx *) ctx)->main_table_relid;
|
return &((HypertableCacheQueryCtx *) ctx)->main_table_relid;
|
||||||
}
|
}
|
||||||
@ -36,9 +36,8 @@ hypertable_cache_get_key(CacheQueryCtx *ctx)
|
|||||||
typedef struct
|
typedef struct
|
||||||
{
|
{
|
||||||
Oid main_table_relid;
|
Oid main_table_relid;
|
||||||
bool negative; /* true if no such hypertable exists */
|
Hypertable *hypertable;
|
||||||
Hypertable entry;
|
} HypertableNameCacheEntry;
|
||||||
} HypertableNameCacheEntry;
|
|
||||||
|
|
||||||
|
|
||||||
static Cache *
|
static Cache *
|
||||||
@ -77,15 +76,18 @@ static Cache *hypertable_cache_current = NULL;
|
|||||||
/* Column numbers for 'hypertable' table in sql/common/tables.sql */
|
/* Column numbers for 'hypertable' table in sql/common/tables.sql */
|
||||||
|
|
||||||
static bool
|
static bool
|
||||||
hypertable_tuple_found(TupleInfo *ti, void *data)
|
hypertable_tuple_found(TupleInfo * ti, void *data)
|
||||||
{
|
{
|
||||||
Hypertable *he = data;
|
HypertableNameCacheEntry *entry = data;
|
||||||
|
Hypertable *he;
|
||||||
Datum values[Natts_hypertable];
|
Datum values[Natts_hypertable];
|
||||||
bool isnull[Natts_hypertable];
|
bool isnull[Natts_hypertable];
|
||||||
char *root_table_name;
|
char *root_table_name;
|
||||||
char *root_table_schema;
|
char *root_table_schema;
|
||||||
int32 id;
|
int32 id;
|
||||||
|
|
||||||
|
he = palloc(sizeof(Hypertable));
|
||||||
|
|
||||||
heap_deform_tuple(ti->tuple, ti->desc, values, isnull);
|
heap_deform_tuple(ti->tuple, ti->desc, values, isnull);
|
||||||
|
|
||||||
id = DatumGetInt32(DATUM_GET(values, Anum_hypertable_id));
|
id = DatumGetInt32(DATUM_GET(values, Anum_hypertable_id));
|
||||||
@ -109,58 +111,58 @@ hypertable_tuple_found(TupleInfo *ti, void *data)
|
|||||||
he->chunk_size_bytes = DatumGetInt64(DATUM_GET(values, Anum_hypertable_chunk_size_bytes));
|
he->chunk_size_bytes = DatumGetInt64(DATUM_GET(values, Anum_hypertable_chunk_size_bytes));
|
||||||
he->num_replicas = DatumGetInt16(DATUM_GET(values, Anum_hypertable_replication_factor));
|
he->num_replicas = DatumGetInt16(DATUM_GET(values, Anum_hypertable_replication_factor));
|
||||||
|
|
||||||
|
entry->hypertable = he;
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void *
|
static void *
|
||||||
hypertable_cache_create_entry(Cache *cache, CacheQueryCtx *ctx)
|
hypertable_cache_create_entry(Cache * cache, CacheQueryCtx * ctx)
|
||||||
{
|
{
|
||||||
HypertableCacheQueryCtx *hctx = (HypertableCacheQueryCtx *) ctx;
|
HypertableCacheQueryCtx *hctx = (HypertableCacheQueryCtx *) ctx;
|
||||||
Catalog *catalog = catalog_get();
|
Catalog *catalog = catalog_get();
|
||||||
HypertableNameCacheEntry *cache_entry = hctx->cctx.entry;
|
HypertableNameCacheEntry *cache_entry = ctx->entry;
|
||||||
Hypertable *he = &cache_entry->entry;
|
|
||||||
int number_found;
|
int number_found;
|
||||||
char *schema = hctx->schema;
|
|
||||||
char *table_name = hctx->table_name;
|
|
||||||
ScanKeyData scankey[2];
|
ScanKeyData scankey[2];
|
||||||
|
|
||||||
ScannerCtx scanCtx = {
|
ScannerCtx scanCtx = {
|
||||||
.table = catalog->tables[HYPERTABLE].id,
|
.table = catalog->tables[HYPERTABLE].id,
|
||||||
.index = catalog->tables[HYPERTABLE].index_ids[HYPERTABLE_NAME_INDEX],
|
.index = catalog->tables[HYPERTABLE].index_ids[HYPERTABLE_NAME_INDEX],
|
||||||
.scantype = ScannerTypeIndex,
|
.scantype = ScannerTypeIndex,
|
||||||
.nkeys = 2,
|
.nkeys = 2,
|
||||||
.scankey = scankey,
|
.scankey = scankey,
|
||||||
.data = he,
|
.data = ctx->entry,
|
||||||
.tuple_found = hypertable_tuple_found,
|
.tuple_found = hypertable_tuple_found,
|
||||||
.lockmode = AccessShareLock,
|
.lockmode = AccessShareLock,
|
||||||
.scandirection = ForwardScanDirection,
|
.scandirection = ForwardScanDirection,
|
||||||
};
|
};
|
||||||
|
|
||||||
if (NULL == schema)
|
if (NULL == hctx->schema)
|
||||||
{
|
{
|
||||||
schema = get_namespace_name(get_rel_namespace(hctx->main_table_relid));
|
hctx->schema = get_namespace_name(get_rel_namespace(hctx->main_table_relid));
|
||||||
}
|
}
|
||||||
if (NULL == table_name)
|
|
||||||
|
if (NULL == hctx->table)
|
||||||
{
|
{
|
||||||
table_name = get_rel_name(hctx->main_table_relid);
|
hctx->table = get_rel_name(hctx->main_table_relid);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Perform an index scan on schema and table. */
|
/* Perform an index scan on schema and table. */
|
||||||
ScanKeyInit(&scankey[0], Anum_hypertable_name_idx_schema,
|
ScanKeyInit(&scankey[0], Anum_hypertable_name_idx_schema,
|
||||||
BTEqualStrategyNumber, F_NAMEEQ, NameGetDatum(schema));
|
BTEqualStrategyNumber, F_NAMEEQ, NameGetDatum(hctx->schema));
|
||||||
ScanKeyInit(&scankey[1], Anum_hypertable_name_idx_table,
|
ScanKeyInit(&scankey[1], Anum_hypertable_name_idx_table,
|
||||||
BTEqualStrategyNumber, F_NAMEEQ, NameGetDatum(table_name));
|
BTEqualStrategyNumber, F_NAMEEQ, NameGetDatum(hctx->table));
|
||||||
|
|
||||||
number_found = scanner_scan(&scanCtx);
|
number_found = scanner_scan(&scanCtx);
|
||||||
|
|
||||||
switch (number_found)
|
switch (number_found)
|
||||||
{
|
{
|
||||||
case 0:
|
case 0:
|
||||||
cache_entry->negative = true;
|
/* Negative cache entry: table is not a hypertable */
|
||||||
|
cache_entry->hypertable = NULL;
|
||||||
break;
|
break;
|
||||||
case 1:
|
case 1:
|
||||||
cache_entry->negative = false;
|
Assert(strncmp(cache_entry->hypertable->schema, hctx->schema, NAMEDATALEN) == 0);
|
||||||
Assert(strncmp(he->schema, get_namespace_name(get_rel_namespace(hctx->main_table_relid)), NAMEDATALEN) == 0);
|
Assert(strncmp(cache_entry->hypertable->table, hctx->table, NAMEDATALEN) == 0);
|
||||||
Assert(strncmp(he->table, get_rel_name(hctx->main_table_relid), NAMEDATALEN) == 0);
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
elog(ERROR, "Got an unexpected number of records: %d", number_found);
|
elog(ERROR, "Got an unexpected number of records: %d", number_found);
|
||||||
@ -180,30 +182,22 @@ hypertable_cache_invalidate_callback(void)
|
|||||||
|
|
||||||
/* Get hypertable cache entry. If the entry is not in the cache, add it. */
|
/* Get hypertable cache entry. If the entry is not in the cache, add it. */
|
||||||
Hypertable *
|
Hypertable *
|
||||||
hypertable_cache_get_entry(Cache *cache, Oid main_table_relid)
|
hypertable_cache_get_entry(Cache * cache, Oid main_table_relid)
|
||||||
{
|
{
|
||||||
return hypertable_cache_get_entry_with_table(cache, main_table_relid, NULL, NULL);
|
return hypertable_cache_get_entry_with_table(cache, main_table_relid, NULL, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
Hypertable *
|
Hypertable *
|
||||||
hypertable_cache_get_entry_with_table(Cache *cache, Oid main_table_relid, char *schema, char *table_name)
|
hypertable_cache_get_entry_with_table(Cache * cache, Oid main_table_relid, const char *schema, const char *table)
|
||||||
{
|
{
|
||||||
HypertableCacheQueryCtx ctx = {
|
HypertableCacheQueryCtx ctx = {
|
||||||
.main_table_relid = main_table_relid,
|
.main_table_relid = main_table_relid,
|
||||||
.schema = schema,
|
.schema = schema,
|
||||||
.table_name = table_name,
|
.table = table,
|
||||||
};
|
};
|
||||||
|
|
||||||
HypertableNameCacheEntry *entry = cache_fetch(cache, &ctx.cctx);
|
HypertableNameCacheEntry *entry = cache_fetch(cache, &ctx.cctx);
|
||||||
|
|
||||||
if (entry->negative)
|
return entry->hypertable;
|
||||||
{
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
return &entry->entry;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* function to compare epochs */
|
/* function to compare epochs */
|
||||||
@ -227,7 +221,7 @@ cmp_epochs(const void *time_pt_pointer, const void *test)
|
|||||||
}
|
}
|
||||||
|
|
||||||
PartitionEpoch *
|
PartitionEpoch *
|
||||||
hypertable_cache_get_partition_epoch(Cache *cache, Hypertable * hce, int64 time_pt, Oid relid)
|
hypertable_cache_get_partition_epoch(Cache * cache, Hypertable * hce, int64 time_pt, Oid relid)
|
||||||
{
|
{
|
||||||
MemoryContext old;
|
MemoryContext old;
|
||||||
PartitionEpoch *epoch,
|
PartitionEpoch *epoch,
|
||||||
|
@ -30,16 +30,15 @@ typedef struct Hypertable
|
|||||||
|
|
||||||
|
|
||||||
extern Hypertable *hypertable_cache_get_entry(Cache * cache, Oid main_table_relid);
|
extern Hypertable *hypertable_cache_get_entry(Cache * cache, Oid main_table_relid);
|
||||||
extern Hypertable *
|
extern Hypertable *hypertable_cache_get_entry_with_table(Cache * cache, Oid main_table_relid, const char *schema, const char *table);
|
||||||
hypertable_cache_get_entry_with_table(Cache *cache, Oid main_table_relid, char *schema, char *table_name);
|
|
||||||
|
|
||||||
PartitionEpoch *hypertable_cache_get_partition_epoch(Cache * cache, Hypertable * hce, int64 time_pt, Oid relid);
|
extern PartitionEpoch *hypertable_cache_get_partition_epoch(Cache * cache, Hypertable * hce, int64 time_pt, Oid relid);
|
||||||
|
|
||||||
void hypertable_cache_invalidate_callback(void);
|
extern void hypertable_cache_invalidate_callback(void);
|
||||||
|
|
||||||
extern Cache *hypertable_cache_pin(void);
|
extern Cache *hypertable_cache_pin(void);
|
||||||
|
|
||||||
void _hypertable_cache_init(void);
|
extern void _hypertable_cache_init(void);
|
||||||
void _hypertable_cache_fini(void);
|
extern void _hypertable_cache_fini(void);
|
||||||
|
|
||||||
#endif /* TIMESCALEDB_HYPERTABLE_CACHE_H */
|
#endif /* TIMESCALEDB_HYPERTABLE_CACHE_H */
|
||||||
|
Loading…
x
Reference in New Issue
Block a user