LCOV - differential code coverage report
Current view: top level - src/backend/utils/cache - spccache.c (source / functions) Coverage Total Hit LBC UIC GIC GNC CBC EUB ECB DCB
Current: Differential Code Coverage HEAD vs 15 Lines: 90.2 % 61 55 2 4 36 1 18 6 32 3
Current Date: 2023-04-08 17:13:01 Functions: 100.0 % 6 6 6 6
Baseline: 15 Line coverage date bins:
Baseline Date: 2023-04-08 15:09:40 (60,120] days: 100.0 % 1 1 1
Legend: Lines: hit not hit (240..) days: 90.0 % 60 54 2 4 36 18 6 32
Function coverage date bins:
(240..) days: 50.0 % 12 6 6 6

 Age         Owner                  TLA  Line data    Source code
                                  1                 : /*-------------------------------------------------------------------------
                                  2                 :  *
                                  3                 :  * spccache.c
                                  4                 :  *    Tablespace cache management.
                                  5                 :  *
                                  6                 :  * We cache the parsed version of spcoptions for each tablespace to avoid
                                  7                 :  * needing to reparse on every lookup.  Right now, there doesn't appear to
                                  8                 :  * be a measurable performance gain from doing this, but that might change
                                  9                 :  * in the future as we add more options.
                                 10                 :  *
                                 11                 :  * Portions Copyright (c) 1996-2023, PostgreSQL Global Development Group
                                 12                 :  * Portions Copyright (c) 1994, Regents of the University of California
                                 13                 :  *
                                 14                 :  * IDENTIFICATION
                                 15                 :  *    src/backend/utils/cache/spccache.c
                                 16                 :  *
                                 17                 :  *-------------------------------------------------------------------------
                                 18                 :  */
                                 19                 : #include "postgres.h"
                                 20                 : 
                                 21                 : #include "access/reloptions.h"
                                 22                 : #include "catalog/pg_tablespace.h"
                                 23                 : #include "commands/tablespace.h"
                                 24                 : #include "miscadmin.h"
                                 25                 : #include "optimizer/optimizer.h"
                                 26                 : #include "storage/bufmgr.h"
                                 27                 : #include "utils/catcache.h"
                                 28                 : #include "utils/hsearch.h"
                                 29                 : #include "utils/inval.h"
                                 30                 : #include "utils/spccache.h"
                                 31                 : #include "utils/syscache.h"
                                 32                 : #include "varatt.h"
                                 33                 : 
                                 34                 : 
                                 35                 : /* Hash table for information about each tablespace */
                                 36                 : static HTAB *TableSpaceCacheHash = NULL;
                                 37                 : 
                                 38                 : typedef struct
                                 39                 : {
                                 40                 :     Oid         oid;            /* lookup key - must be first */
                                 41                 :     TableSpaceOpts *opts;       /* options, or NULL if none */
                                 42                 : } TableSpaceCacheEntry;
                                 43                 : 
                                 44                 : 
                                 45                 : /*
                                 46                 :  * InvalidateTableSpaceCacheCallback
                                 47                 :  *      Flush all cache entries when pg_tablespace is updated.
                                 48                 :  *
                                 49                 :  * When pg_tablespace is updated, we must flush the cache entry at least
                                 50                 :  * for that tablespace.  Currently, we just flush them all.  This is quick
                                 51                 :  * and easy and doesn't cost much, since there shouldn't be terribly many
                                 52                 :  * tablespaces, nor do we expect them to be frequently modified.
                                 53                 :  */
                                 54                 : static void
 4254 tgl                        55 GIC         166 : InvalidateTableSpaceCacheCallback(Datum arg, int cacheid, uint32 hashvalue)
 4842 rhaas                      56 ECB             : {
                                 57                 :     HASH_SEQ_STATUS status;
                                 58                 :     TableSpaceCacheEntry *spc;
                                 59                 : 
 4842 rhaas                      60 GIC         166 :     hash_seq_init(&status, TableSpaceCacheHash);
 4841 tgl                        61 CBC         262 :     while ((spc = (TableSpaceCacheEntry *) hash_seq_search(&status)) != NULL)
 4842 rhaas                      62 ECB             :     {
 4842 rhaas                      63 GIC          96 :         if (spc->opts)
 4842 rhaas                      64 CBC           3 :             pfree(spc->opts);
 4841 tgl                        65              96 :         if (hash_search(TableSpaceCacheHash,
   62 peter                      66 GNC          96 :                         &spc->oid,
 4841 tgl                        67 ECB             :                         HASH_REMOVE,
                                 68                 :                         NULL) == NULL)
 4841 tgl                        69 UIC           0 :             elog(ERROR, "hash table corrupted");
 4842 rhaas                      70 EUB             :     }
 4842 rhaas                      71 GIC         166 : }
 4842 rhaas                      72 ECB             : 
                                 73                 : /*
                                 74                 :  * InitializeTableSpaceCache
                                 75                 :  *      Initialize the tablespace cache.
                                 76                 :  */
                                 77                 : static void
 4842 rhaas                      78 GIC        3590 : InitializeTableSpaceCache(void)
 4842 rhaas                      79 ECB             : {
                                 80                 :     HASHCTL     ctl;
                                 81                 : 
                                 82                 :     /* Initialize the hash table. */
 4842 rhaas                      83 GIC        3590 :     ctl.keysize = sizeof(Oid);
 4841 tgl                        84 CBC        3590 :     ctl.entrysize = sizeof(TableSpaceCacheEntry);
 4842 rhaas                      85            3590 :     TableSpaceCacheHash =
                                 86            3590 :         hash_create("TableSpace cache", 16, &ctl,
 3034 tgl                        87 ECB             :                     HASH_ELEM | HASH_BLOBS);
                                 88                 : 
                                 89                 :     /* Make sure we've initialized CacheMemoryContext. */
 4842 rhaas                      90 GIC        3590 :     if (!CacheMemoryContext)
 4842 rhaas                      91 LBC           0 :         CreateCacheMemoryContext();
 4842 rhaas                      92 EUB             : 
                                 93                 :     /* Watch for invalidation events. */
 4842 rhaas                      94 GIC        3590 :     CacheRegisterSyscacheCallback(TABLESPACEOID,
 4842 rhaas                      95 ECB             :                                   InvalidateTableSpaceCacheCallback,
                                 96                 :                                   (Datum) 0);
 4842 rhaas                      97 GIC        3590 : }
 4842 rhaas                      98 ECB             : 
                                 99                 : /*
                                100                 :  * get_tablespace
                                101                 :  *      Fetch TableSpaceCacheEntry structure for a specified table OID.
                                102                 :  *
                                103                 :  * Pointers returned by this function should not be stored, since a cache
                                104                 :  * flush will invalidate them.
                                105                 :  */
                                106                 : static TableSpaceCacheEntry *
 4842 rhaas                     107 GIC      925360 : get_tablespace(Oid spcid)
 4842 rhaas                     108 ECB             : {
                                109                 :     TableSpaceCacheEntry *spc;
                                110                 :     HeapTuple   tp;
                                111                 :     TableSpaceOpts *opts;
                                112                 : 
                                113                 :     /*
                                114                 :      * Since spcid is always from a pg_class tuple, InvalidOid implies the
                                115                 :      * default.
                                116                 :      */
 4842 rhaas                     117 GIC      925360 :     if (spcid == InvalidOid)
 4842 rhaas                     118 CBC      893268 :         spcid = MyDatabaseTableSpace;
 4842 rhaas                     119 ECB             : 
                                120                 :     /* Find existing cache entry, if any. */
 4842 rhaas                     121 GIC      925360 :     if (!TableSpaceCacheHash)
 4842 rhaas                     122 CBC        3590 :         InitializeTableSpaceCache();
 4841 tgl                       123          925360 :     spc = (TableSpaceCacheEntry *) hash_search(TableSpaceCacheHash,
                                124                 :                                                &spcid,
                                125                 :                                                HASH_FIND,
                                126                 :                                                NULL);
 4841 tgl                       127 GIC      925360 :     if (spc)
 4842 rhaas                     128 CBC      921021 :         return spc;
 4842 rhaas                     129 ECB             : 
                                130                 :     /*
                                131                 :      * Not found in TableSpace cache.  Check catcache.  If we don't find a
                                132                 :      * valid HeapTuple, it must mean someone has managed to request tablespace
                                133                 :      * details for a non-existent tablespace.  We'll just treat that case as
                                134                 :      * if no options were specified.
                                135                 :      */
 4802 rhaas                     136 GIC        4339 :     tp = SearchSysCache1(TABLESPACEOID, ObjectIdGetDatum(spcid));
 4842 rhaas                     137 CBC        4339 :     if (!HeapTupleIsValid(tp))
 4841 tgl                       138 LBC           0 :         opts = NULL;
 4842 rhaas                     139 EUB             :     else
                                140                 :     {
                                141                 :         Datum       datum;
                                142                 :         bool        isNull;
                                143                 : 
 4842 rhaas                     144 GIC        4339 :         datum = SysCacheGetAttr(TABLESPACEOID,
 4842 rhaas                     145 ECB             :                                 tp,
                                146                 :                                 Anum_pg_tablespace_spcoptions,
                                147                 :                                 &isNull);
 4842 rhaas                     148 GIC        4339 :         if (isNull)
 4841 tgl                       149 CBC        4336 :             opts = NULL;
 4842 rhaas                     150 ECB             :         else
                                151                 :         {
 4790 bruce                     152 GIC           3 :             bytea      *bytea_opts = tablespace_reloptions(datum, false);
 4790 bruce                     153 ECB             : 
 4840 rhaas                     154 GIC           3 :             opts = MemoryContextAlloc(CacheMemoryContext, VARSIZE(bytea_opts));
 4840 rhaas                     155 CBC           3 :             memcpy(opts, bytea_opts, VARSIZE(bytea_opts));
 4842 rhaas                     156 ECB             :         }
 4842 rhaas                     157 GIC        4339 :         ReleaseSysCache(tp);
 4842 rhaas                     158 ECB             :     }
                                159                 : 
                                160                 :     /*
                                161                 :      * Now create the cache entry.  It's important to do this only after
                                162                 :      * reading the pg_tablespace entry, since doing so could cause a cache
                                163                 :      * flush.
                                164                 :      */
 4841 tgl                       165 GIC        4339 :     spc = (TableSpaceCacheEntry *) hash_search(TableSpaceCacheHash,
                                166                 :                                                &spcid,
                                167                 :                                                HASH_ENTER,
                                168                 :                                                NULL);
                                169            4339 :     spc->opts = opts;
 4842 rhaas                     170 CBC        4339 :     return spc;
 4842 rhaas                     171 ECB             : }
                                172                 : 
                                173                 : /*
                                174                 :  * get_tablespace_page_costs
                                175                 :  *      Return random and/or sequential page costs for a given tablespace.
                                176                 :  *
                                177                 :  *      This value is not locked by the transaction, so this value may
                                178                 :  *      be changed while a SELECT that has used these values for planning
                                179                 :  *      is still executing.
                                180                 :  */
                                181                 : void
 4841 tgl                       182 GIC      888690 : get_tablespace_page_costs(Oid spcid,
 4841 tgl                       183 ECB             :                           double *spc_random_page_cost,
                                184                 :                           double *spc_seq_page_cost)
                                185                 : {
 4841 tgl                       186 GIC      888690 :     TableSpaceCacheEntry *spc = get_tablespace(spcid);
 4842 rhaas                     187 ECB             : 
 4842 rhaas                     188 GIC      888690 :     Assert(spc != NULL);
 4842 rhaas                     189 ECB             : 
 4842 rhaas                     190 GIC      888690 :     if (spc_random_page_cost)
 4842 rhaas                     191 ECB             :     {
 4842 rhaas                     192 GIC      718659 :         if (!spc->opts || spc->opts->random_page_cost < 0)
 4842 rhaas                     193 CBC      718659 :             *spc_random_page_cost = random_page_cost;
 4842 rhaas                     194 ECB             :         else
 4842 rhaas                     195 UIC           0 :             *spc_random_page_cost = spc->opts->random_page_cost;
 4842 rhaas                     196 EUB             :     }
                                197                 : 
 4842 rhaas                     198 GIC      888690 :     if (spc_seq_page_cost)
 4842 rhaas                     199 ECB             :     {
 4842 rhaas                     200 GIC      625731 :         if (!spc->opts || spc->opts->seq_page_cost < 0)
 4842 rhaas                     201 CBC      625602 :             *spc_seq_page_cost = seq_page_cost;
 4842 rhaas                     202 ECB             :         else
 4842 rhaas                     203 GIC         129 :             *spc_seq_page_cost = spc->opts->seq_page_cost;
 4842 rhaas                     204 ECB             :     }
 4842 rhaas                     205 GIC      888690 : }
 2770 alvherre                  206 ECB             : 
                                207                 : /*
                                208                 :  * get_tablespace_io_concurrency
                                209                 :  *
                                210                 :  *      This value is not locked by the transaction, so this value may
                                211                 :  *      be changed while a SELECT that has used these values for planning
                                212                 :  *      is still executing.
                                213                 :  */
                                214                 : int
 2770 alvherre                  215 GIC       10598 : get_tablespace_io_concurrency(Oid spcid)
 2770 alvherre                  216 ECB             : {
 2770 alvherre                  217 GIC       10598 :     TableSpaceCacheEntry *spc = get_tablespace(spcid);
 2770 alvherre                  218 ECB             : 
 2770 alvherre                  219 GIC       10598 :     if (!spc->opts || spc->opts->effective_io_concurrency < 0)
 2770 alvherre                  220 CBC       10598 :         return effective_io_concurrency;
 2770 alvherre                  221 ECB             :     else
 2770 alvherre                  222 UIC           0 :         return spc->opts->effective_io_concurrency;
 2770 alvherre                  223 EUB             : }
                                224                 : 
                                225                 : /*
                                226                 :  * get_tablespace_maintenance_io_concurrency
                                227                 :  */
                                228                 : int
 1119 tmunro                    229 GIC       26072 : get_tablespace_maintenance_io_concurrency(Oid spcid)
 1119 tmunro                    230 ECB             : {
 1119 tmunro                    231 GIC       26072 :     TableSpaceCacheEntry *spc = get_tablespace(spcid);
 1119 tmunro                    232 ECB             : 
 1119 tmunro                    233 GIC       26072 :     if (!spc->opts || spc->opts->maintenance_io_concurrency < 0)
 1119 tmunro                    234 CBC       26072 :         return maintenance_io_concurrency;
 1119 tmunro                    235 ECB             :     else
 1119 tmunro                    236 UIC           0 :         return spc->opts->maintenance_io_concurrency;
 1119 tmunro                    237 EUB             : }
        

Generated by: LCOV version v1.16-55-g56c0a2a