1996-08-28 03:59:28 +02:00
|
|
|
/*-------------------------------------------------------------------------
|
|
|
|
*
|
1999-02-14 00:22:53 +01:00
|
|
|
* catcache.h
|
1997-09-07 07:04:48 +02:00
|
|
|
* Low-level catalog cache definitions.
|
1996-08-28 03:59:28 +02:00
|
|
|
*
|
2000-11-10 01:33:12 +01:00
|
|
|
* NOTE: every catalog cache must have a corresponding unique index on
|
|
|
|
* the system table that it caches --- ie, the index must match the keys
|
|
|
|
* used to do lookups in this cache. All cache fetches are done with
|
|
|
|
* indexscans (under normal conditions). The index should be unique to
|
|
|
|
* guarantee that there can only be one matching row for a key combination.
|
|
|
|
*
|
1996-08-28 03:59:28 +02:00
|
|
|
*
|
2021-01-02 19:06:25 +01:00
|
|
|
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
|
2000-01-26 06:58:53 +01:00
|
|
|
* Portions Copyright (c) 1994, Regents of the University of California
|
1996-08-28 03:59:28 +02:00
|
|
|
*
|
2010-09-20 22:08:53 +02:00
|
|
|
* src/include/utils/catcache.h
|
1996-08-28 03:59:28 +02:00
|
|
|
*
|
|
|
|
*-------------------------------------------------------------------------
|
|
|
|
*/
|
1997-09-07 07:04:48 +02:00
|
|
|
#ifndef CATCACHE_H
|
1996-08-28 03:59:28 +02:00
|
|
|
#define CATCACHE_H
|
|
|
|
|
1999-07-16 01:04:24 +02:00
|
|
|
#include "access/htup.h"
|
2003-11-09 22:30:38 +01:00
|
|
|
#include "access/skey.h"
|
2012-10-16 22:36:30 +02:00
|
|
|
#include "lib/ilist.h"
|
2008-06-19 02:46:06 +02:00
|
|
|
#include "utils/relcache.h"
|
1996-08-28 03:59:28 +02:00
|
|
|
|
2000-06-17 06:56:39 +02:00
|
|
|
/*
|
2000-11-10 01:33:12 +01:00
|
|
|
* struct catctup: individual tuple in the cache.
|
2002-04-06 08:59:25 +02:00
|
|
|
* struct catclist: list of tuples matching a partial key.
|
1997-09-07 07:04:48 +02:00
|
|
|
* struct catcache: information for managing a cache.
|
2001-06-18 05:35:07 +02:00
|
|
|
* struct catcacheheader: information for managing all the caches.
|
1996-08-28 03:59:28 +02:00
|
|
|
*/
|
|
|
|
|
2010-02-14 19:42:19 +01:00
|
|
|
#define CATCACHE_MAXKEYS 4
|
|
|
|
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
|
|
|
|
/* function computing a datum's hash */
|
|
|
|
typedef uint32 (*CCHashFN) (Datum datum);
|
|
|
|
|
|
|
|
/* function computing equality of two datums */
|
|
|
|
typedef bool (*CCFastEqualFN) (Datum a, Datum b);
|
|
|
|
|
2001-06-18 05:35:07 +02:00
|
|
|
typedef struct catcache
|
|
|
|
{
|
|
|
|
int id; /* cache identifier --- see syscache.h */
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
int cc_nbuckets; /* # of hash buckets in this cache */
|
|
|
|
TupleDesc cc_tupdesc; /* tuple descriptor (copied from reldesc) */
|
|
|
|
dlist_head *cc_bucket; /* hash buckets */
|
|
|
|
CCHashFN cc_hashfunc[CATCACHE_MAXKEYS]; /* hash function for each key */
|
|
|
|
CCFastEqualFN cc_fastequal[CATCACHE_MAXKEYS]; /* fast equal function for
|
|
|
|
* each key */
|
|
|
|
int cc_keyno[CATCACHE_MAXKEYS]; /* AttrNumber of each key */
|
|
|
|
dlist_head cc_lists; /* list of CatCList structs */
|
|
|
|
int cc_ntup; /* # of tuples currently in this cache */
|
|
|
|
int cc_nkeys; /* # of keys (1..CATCACHE_MAXKEYS) */
|
2002-03-26 20:17:02 +01:00
|
|
|
const char *cc_relname; /* name of relation the tuples come from */
|
2002-03-03 18:47:56 +01:00
|
|
|
Oid cc_reloid; /* OID of relation the tuples come from */
|
2005-04-14 22:03:27 +02:00
|
|
|
Oid cc_indexoid; /* OID of index matching cache keys */
|
2002-04-06 08:59:25 +02:00
|
|
|
bool cc_relisshared; /* is relation shared across databases? */
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
slist_node cc_next; /* list link */
|
Phase 2 of pgindent updates.
Change pg_bsd_indent to follow upstream rules for placement of comments
to the right of code, and remove pgindent hack that caused comments
following #endif to not obey the general rule.
Commit e3860ffa4dd0dad0dd9eea4be9cc1412373a8c89 wasn't actually using
the published version of pg_bsd_indent, but a hacked-up version that
tried to minimize the amount of movement of comments to the right of
code. The situation of interest is where such a comment has to be
moved to the right of its default placement at column 33 because there's
code there. BSD indent has always moved right in units of tab stops
in such cases --- but in the previous incarnation, indent was working
in 8-space tab stops, while now it knows we use 4-space tabs. So the
net result is that in about half the cases, such comments are placed
one tab stop left of before. This is better all around: it leaves
more room on the line for comment text, and it means that in such
cases the comment uniformly starts at the next 4-space tab stop after
the code, rather than sometimes one and sometimes two tabs after.
Also, ensure that comments following #endif are indented the same
as comments following other preprocessor commands such as #else.
That inconsistency turns out to have been self-inflicted damage
from a poorly-thought-through post-indent "fixup" in pgindent.
This patch is much less interesting than the first round of indent
changes, but also bulkier, so I thought it best to separate the effects.
Discussion: https://postgr.es/m/E1dAmxK-0006EE-1r@gemulon.postgresql.org
Discussion: https://postgr.es/m/30527.1495162840@sss.pgh.pa.us
2017-06-21 21:18:54 +02:00
|
|
|
ScanKeyData cc_skey[CATCACHE_MAXKEYS]; /* precomputed key info for heap
|
|
|
|
* scans */
|
2017-01-13 00:59:46 +01:00
|
|
|
|
|
|
|
/*
|
|
|
|
* Keep these at the end, so that compiling catcache.c with CATCACHE_STATS
|
|
|
|
* doesn't break ABI for other modules
|
|
|
|
*/
|
2002-02-19 21:11:20 +01:00
|
|
|
#ifdef CATCACHE_STATS
|
|
|
|
long cc_searches; /* total # searches against this cache */
|
|
|
|
long cc_hits; /* # of matches against existing entry */
|
2002-03-03 18:47:56 +01:00
|
|
|
long cc_neg_hits; /* # of matches against negative entry */
|
2002-02-19 21:11:20 +01:00
|
|
|
long cc_newloads; /* # of successful loads of new entry */
|
2002-09-04 22:31:48 +02:00
|
|
|
|
2002-03-03 18:47:56 +01:00
|
|
|
/*
|
2005-10-15 04:49:52 +02:00
|
|
|
* cc_searches - (cc_hits + cc_neg_hits + cc_newloads) is number of failed
|
|
|
|
* searches, each of which will result in loading a negative entry
|
2002-03-03 18:47:56 +01:00
|
|
|
*/
|
|
|
|
long cc_invals; /* # of entries invalidated from cache */
|
2002-04-06 08:59:25 +02:00
|
|
|
long cc_lsearches; /* total # list-searches */
|
|
|
|
long cc_lhits; /* # of matches against existing lists */
|
2002-02-19 21:11:20 +01:00
|
|
|
#endif
|
2013-09-05 18:47:56 +02:00
|
|
|
} CatCache;
|
2001-06-18 05:35:07 +02:00
|
|
|
|
|
|
|
|
1997-09-07 07:04:48 +02:00
|
|
|
typedef struct catctup
|
|
|
|
{
|
2002-04-06 08:59:25 +02:00
|
|
|
int ct_magic; /* for identifying CatCTup entries */
|
2000-11-16 23:30:52 +01:00
|
|
|
#define CT_MAGIC 0x57261502
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
|
|
|
|
uint32 hash_value; /* hash value for this tuple's keys */
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Lookup keys for the entry. By-reference datums point into the tuple for
|
|
|
|
* positive cache entries, and are separately allocated for negative ones.
|
|
|
|
*/
|
|
|
|
Datum keys[CATCACHE_MAXKEYS];
|
2001-10-25 07:50:21 +02:00
|
|
|
|
2000-04-12 19:17:23 +02:00
|
|
|
/*
|
2012-10-16 22:36:30 +02:00
|
|
|
* Each tuple in a cache is a member of a dlist that stores the elements
|
2014-05-06 18:12:18 +02:00
|
|
|
* of its hash bucket. We keep each dlist in LRU order to speed repeated
|
2006-06-15 04:08:09 +02:00
|
|
|
* lookups.
|
2005-08-14 00:18:07 +02:00
|
|
|
*/
|
2012-10-16 22:36:30 +02:00
|
|
|
dlist_node cache_elem; /* list member of per-bucket list */
|
2005-08-14 00:18:07 +02:00
|
|
|
|
2002-04-06 08:59:25 +02:00
|
|
|
/*
|
2000-11-16 23:30:52 +01:00
|
|
|
* A tuple marked "dead" must not be returned by subsequent searches.
|
|
|
|
* However, it won't be physically deleted from the cache until its
|
2005-08-14 00:18:07 +02:00
|
|
|
* refcount goes to zero. (If it's a member of a CatCList, the list's
|
2005-10-15 04:49:52 +02:00
|
|
|
* refcount must go to zero, too; also, remember to mark the list dead at
|
|
|
|
* the same time the tuple is marked.)
|
2002-03-03 18:47:56 +01:00
|
|
|
*
|
2005-11-22 19:17:34 +01:00
|
|
|
* A negative cache entry is an assertion that there is no tuple matching
|
|
|
|
* a particular key. This is just as useful as a normal entry so far as
|
2014-05-06 18:12:18 +02:00
|
|
|
* avoiding catalog searches is concerned. Management of positive and
|
2005-10-15 04:49:52 +02:00
|
|
|
* negative entries is identical.
|
1999-06-04 04:19:47 +02:00
|
|
|
*/
|
2000-11-16 23:30:52 +01:00
|
|
|
int refcount; /* number of active references */
|
|
|
|
bool dead; /* dead but not yet removed? */
|
2002-03-03 18:47:56 +01:00
|
|
|
bool negative; /* negative cache entry? */
|
2000-11-16 23:30:52 +01:00
|
|
|
HeapTupleData tuple; /* tuple management header */
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
|
|
|
|
/*
|
|
|
|
* The tuple may also be a member of at most one CatCList. (If a single
|
|
|
|
* catcache is list-searched with varying numbers of keys, we may have to
|
|
|
|
* make multiple entries for the same tuple because of this restriction.
|
|
|
|
* Currently, that's not expected to be common, so we accept the potential
|
|
|
|
* inefficiency.)
|
|
|
|
*/
|
|
|
|
struct catclist *c_list; /* containing CatCList, or NULL if none */
|
|
|
|
|
|
|
|
CatCache *my_cache; /* link to owning catcache */
|
|
|
|
/* properly aligned tuple data follows, unless a negative entry */
|
1997-09-08 23:56:23 +02:00
|
|
|
} CatCTup;
|
1996-08-28 03:59:28 +02:00
|
|
|
|
2000-11-16 23:30:52 +01:00
|
|
|
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
/*
|
|
|
|
* A CatCList describes the result of a partial search, ie, a search using
|
|
|
|
* only the first K key columns of an N-key cache. We store the keys used
|
|
|
|
* into the keys attribute to represent the stored key set. The CatCList
|
|
|
|
* object contains links to cache entries for all the table rows satisfying
|
|
|
|
* the partial key. (Note: none of these will be negative cache entries.)
|
|
|
|
*
|
|
|
|
* A CatCList is only a member of a per-cache list; we do not currently
|
|
|
|
* divide them into hash buckets.
|
|
|
|
*
|
|
|
|
* A list marked "dead" must not be returned by subsequent searches.
|
|
|
|
* However, it won't be physically deleted from the cache until its
|
|
|
|
* refcount goes to zero. (A list should be marked dead if any of its
|
|
|
|
* member entries are dead.)
|
|
|
|
*
|
|
|
|
* If "ordered" is true then the member tuples appear in the order of the
|
|
|
|
* cache's underlying index. This will be true in normal operation, but
|
|
|
|
* might not be true during bootstrap or recovery operations. (namespace.c
|
|
|
|
* is able to save some cycles when it is true.)
|
|
|
|
*/
|
2002-04-06 08:59:25 +02:00
|
|
|
typedef struct catclist
|
|
|
|
{
|
|
|
|
int cl_magic; /* for identifying CatCList entries */
|
|
|
|
#define CL_MAGIC 0x52765103
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
|
|
|
|
uint32 hash_value; /* hash value for lookup keys */
|
|
|
|
|
|
|
|
dlist_node cache_elem; /* list member of per-catcache list */
|
2002-04-06 08:59:25 +02:00
|
|
|
|
|
|
|
/*
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
* Lookup keys for the entry, with the first nkeys elements being valid.
|
|
|
|
* All by-reference are separately allocated.
|
2002-04-06 08:59:25 +02:00
|
|
|
*/
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
Datum keys[CATCACHE_MAXKEYS];
|
|
|
|
|
2002-04-06 08:59:25 +02:00
|
|
|
int refcount; /* number of active references */
|
|
|
|
bool dead; /* dead but not yet removed? */
|
|
|
|
bool ordered; /* members listed in index order? */
|
|
|
|
short nkeys; /* number of lookup keys specified */
|
|
|
|
int n_members; /* number of member tuples */
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
CatCache *my_cache; /* link to owning catcache */
|
2015-02-20 06:11:42 +01:00
|
|
|
CatCTup *members[FLEXIBLE_ARRAY_MEMBER]; /* members */
|
|
|
|
} CatCList;
|
2002-04-06 08:59:25 +02:00
|
|
|
|
|
|
|
|
2001-06-18 05:35:07 +02:00
|
|
|
typedef struct catcacheheader
|
1997-09-07 07:04:48 +02:00
|
|
|
{
|
2012-10-16 22:36:30 +02:00
|
|
|
slist_head ch_caches; /* head of list of CatCache structs */
|
2001-06-18 05:35:07 +02:00
|
|
|
int ch_ntup; /* # of tuples in all caches */
|
|
|
|
} CatCacheHeader;
|
1996-08-28 03:59:28 +02:00
|
|
|
|
|
|
|
|
2000-06-28 05:33:33 +02:00
|
|
|
/* this extern duplicates utils/memutils.h... */
|
2007-07-25 14:22:54 +02:00
|
|
|
extern PGDLLIMPORT MemoryContext CacheMemoryContext;
|
1996-08-28 03:59:28 +02:00
|
|
|
|
2000-06-28 05:33:33 +02:00
|
|
|
extern void CreateCacheMemoryContext(void);
|
2000-11-10 01:33:12 +01:00
|
|
|
|
2005-04-14 22:03:27 +02:00
|
|
|
extern CatCache *InitCatCache(int id, Oid reloid, Oid indexoid,
|
2019-05-22 19:04:48 +02:00
|
|
|
int nkeys, const int *key,
|
|
|
|
int nbuckets);
|
2006-10-06 20:23:35 +02:00
|
|
|
extern void InitCatCachePhase2(CatCache *cache, bool touch_index);
|
2000-11-16 23:30:52 +01:00
|
|
|
|
|
|
|
extern HeapTuple SearchCatCache(CatCache *cache,
|
2019-05-22 19:04:48 +02:00
|
|
|
Datum v1, Datum v2, Datum v3, Datum v4);
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
extern HeapTuple SearchCatCache1(CatCache *cache,
|
2019-05-22 19:04:48 +02:00
|
|
|
Datum v1);
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
extern HeapTuple SearchCatCache2(CatCache *cache,
|
2019-05-22 19:04:48 +02:00
|
|
|
Datum v1, Datum v2);
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
extern HeapTuple SearchCatCache3(CatCache *cache,
|
2019-05-22 19:04:48 +02:00
|
|
|
Datum v1, Datum v2, Datum v3);
|
Improve sys/catcache performance.
The following are the individual improvements:
1) Avoidance of FunctionCallInfo based function calls, replaced by
more efficient functions with a native C argument interface.
2) Don't extract columns from a cache entry's tuple whenever matching
entries - instead store them as a Datum array. This also allows to
get rid of having to build dummy tuples for negative & list
entries, and of a hack for dealing with cstring vs. text weirdness.
3) Reorder members of catcache.h struct, so imortant entries are more
likely to be on one cacheline.
4) Allowing the compiler to specialize critical SearchCatCache for a
specific number of attributes allows to unroll loops and avoid
other nkeys dependant initialization.
5) Only initializing the ScanKey when necessary, i.e. catcache misses,
greatly reduces cache unnecessary cpu cache misses.
6) Split of the cache-miss case from the hash lookup, reducing stack
allocations etc in the common case.
7) CatCTup and their corresponding heaptuple are allocated in one
piece.
This results in making cache lookups themselves roughly three times as
fast - full-system benchmarks obviously improve less than that.
I've also evaluated further techniques:
- replace open coded hash with simplehash - the list walk right now
shows up in profiles. Unfortunately it's not easy to do so safely as
an entry's memory location can change at various times, which
doesn't work well with the refcounting and cache invalidation.
- Cacheline-aligning CatCTup entries - helps some with performance,
but the win isn't big and the code for it is ugly, because the
tuples have to be freed as well.
- add more proper functions, rather than macros for
SearchSysCacheCopyN etc., but right now they don't show up in
profiles.
The reason the macro wrapper for syscache.c/h have to be changed,
rather than just catcache, is that doing otherwise would require
exposing the SysCache array to the outside. That might be a good idea
anyway, but it's for another day.
Author: Andres Freund
Reviewed-By: Robert Haas
Discussion: https://postgr.es/m/20170914061207.zxotvyopetm7lrrp@alap3.anarazel.de
2017-10-13 22:16:50 +02:00
|
|
|
extern HeapTuple SearchCatCache4(CatCache *cache,
|
2019-05-22 19:04:48 +02:00
|
|
|
Datum v1, Datum v2, Datum v3, Datum v4);
|
2000-11-16 23:30:52 +01:00
|
|
|
extern void ReleaseCatCache(HeapTuple tuple);
|
2000-11-10 01:33:12 +01:00
|
|
|
|
2012-03-07 20:51:13 +01:00
|
|
|
extern uint32 GetCatCacheHashValue(CatCache *cache,
|
2019-05-22 19:04:48 +02:00
|
|
|
Datum v1, Datum v2,
|
|
|
|
Datum v3, Datum v4);
|
2012-03-07 20:51:13 +01:00
|
|
|
|
2002-04-06 08:59:25 +02:00
|
|
|
extern CatCList *SearchCatCacheList(CatCache *cache, int nkeys,
|
2019-05-22 19:04:48 +02:00
|
|
|
Datum v1, Datum v2,
|
|
|
|
Datum v3);
|
2002-04-06 08:59:25 +02:00
|
|
|
extern void ReleaseCatCacheList(CatCList *list);
|
|
|
|
|
2001-06-18 05:35:07 +02:00
|
|
|
extern void ResetCatalogCaches(void);
|
2010-02-07 21:48:13 +01:00
|
|
|
extern void CatalogCacheFlushCatalog(Oid catId);
|
2017-05-13 00:17:29 +02:00
|
|
|
extern void CatCacheInvalidate(CatCache *cache, uint32 hashValue);
|
2001-01-05 23:54:37 +01:00
|
|
|
extern void PrepareToInvalidateCacheTuple(Relation relation,
|
2019-05-22 19:04:48 +02:00
|
|
|
HeapTuple tuple,
|
|
|
|
HeapTuple newtuple,
|
|
|
|
void (*function) (int, uint32, Oid));
|
2001-10-28 07:26:15 +01:00
|
|
|
|
2005-03-25 19:30:28 +01:00
|
|
|
extern void PrintCatCacheLeakWarning(HeapTuple tuple);
|
|
|
|
extern void PrintCatCacheListLeakWarning(CatCList *list);
|
|
|
|
|
Phase 2 of pgindent updates.
Change pg_bsd_indent to follow upstream rules for placement of comments
to the right of code, and remove pgindent hack that caused comments
following #endif to not obey the general rule.
Commit e3860ffa4dd0dad0dd9eea4be9cc1412373a8c89 wasn't actually using
the published version of pg_bsd_indent, but a hacked-up version that
tried to minimize the amount of movement of comments to the right of
code. The situation of interest is where such a comment has to be
moved to the right of its default placement at column 33 because there's
code there. BSD indent has always moved right in units of tab stops
in such cases --- but in the previous incarnation, indent was working
in 8-space tab stops, while now it knows we use 4-space tabs. So the
net result is that in about half the cases, such comments are placed
one tab stop left of before. This is better all around: it leaves
more room on the line for comment text, and it means that in such
cases the comment uniformly starts at the next 4-space tab stop after
the code, rather than sometimes one and sometimes two tabs after.
Also, ensure that comments following #endif are indented the same
as comments following other preprocessor commands such as #else.
That inconsistency turns out to have been self-inflicted damage
from a poorly-thought-through post-indent "fixup" in pgindent.
This patch is much less interesting than the first round of indent
changes, but also bulkier, so I thought it best to separate the effects.
Discussion: https://postgr.es/m/E1dAmxK-0006EE-1r@gemulon.postgresql.org
Discussion: https://postgr.es/m/30527.1495162840@sss.pgh.pa.us
2017-06-21 21:18:54 +02:00
|
|
|
#endif /* CATCACHE_H */
|