LCOV - code coverage report
Current view: top level - src/test/modules/test_dsm_registry - test_dsm_registry.c (source / functions) Coverage Total Hit
Test: PostgreSQL 20devel Lines: 92.6 % 54 50
Test Date: 2026-07-25 22:15:46 Functions: 100.0 % 11 11
Legend: Lines:     hit not hit
Branches: + taken - not taken # not executed
Branches: 50.0 % 16 8

             Branch data     Line data    Source code
       1                 :             : /*--------------------------------------------------------------------------
       2                 :             :  *
       3                 :             :  * test_dsm_registry.c
       4                 :             :  *    Test the dynamic shared memory registry.
       5                 :             :  *
       6                 :             :  * Copyright (c) 2024-2026, PostgreSQL Global Development Group
       7                 :             :  *
       8                 :             :  * IDENTIFICATION
       9                 :             :  *      src/test/modules/test_dsm_registry/test_dsm_registry.c
      10                 :             :  *
      11                 :             :  * -------------------------------------------------------------------------
      12                 :             :  */
      13                 :             : #include "postgres.h"
      14                 :             : 
      15                 :             : #include "fmgr.h"
      16                 :             : #include "storage/dsm_registry.h"
      17                 :             : #include "storage/lwlock.h"
      18                 :             : #include "utils/builtins.h"
      19                 :             : 
      20                 :           2 : PG_MODULE_MAGIC;
      21                 :             : 
      22                 :             : typedef struct TestDSMRegistryStruct
      23                 :             : {
      24                 :             :     int         val;
      25                 :             :     LWLock      lck;
      26                 :             : } TestDSMRegistryStruct;
      27                 :             : 
      28                 :             : typedef struct TestDSMRegistryHashEntry
      29                 :             : {
      30                 :             :     char        key[64];
      31                 :             :     dsa_pointer val;
      32                 :             : } TestDSMRegistryHashEntry;
      33                 :             : 
      34                 :             : static TestDSMRegistryStruct *tdr_dsm;
      35                 :             : static dsa_area *tdr_dsa;
      36                 :             : static dshash_table *tdr_hash;
      37                 :             : 
      38                 :             : static const dshash_parameters dsh_params = {
      39                 :             :     offsetof(TestDSMRegistryHashEntry, val),
      40                 :             :     sizeof(TestDSMRegistryHashEntry),
      41                 :             :     dshash_strcmp,
      42                 :             :     dshash_strhash,
      43                 :             :     dshash_strcpy
      44                 :             : };
      45                 :             : 
      46                 :             : static void
      47                 :           1 : init_tdr_dsm(void *ptr, void *arg)
      48                 :             : {
      49                 :           1 :     TestDSMRegistryStruct *dsm = (TestDSMRegistryStruct *) ptr;
      50                 :             : 
      51         [ -  + ]:           1 :     if ((int) (intptr_t) arg != 5432)
      52         [ #  # ]:           0 :         elog(ERROR, "unexpected arg value %d", (int) (intptr_t) arg);
      53                 :             : 
      54                 :           1 :     LWLockInitialize(&dsm->lck, LWLockNewTrancheId("test_dsm_registry"));
      55                 :           1 :     dsm->val = 0;
      56                 :           1 : }
      57                 :             : 
      58                 :             : static void
      59                 :           4 : tdr_attach_shmem(void)
      60                 :             : {
      61                 :             :     bool        found;
      62                 :             : 
      63                 :           4 :     tdr_dsm = GetNamedDSMSegment("test_dsm_registry_dsm",
      64                 :             :                                  sizeof(TestDSMRegistryStruct),
      65                 :             :                                  init_tdr_dsm,
      66                 :             :                                  &found, (void *) (intptr_t) 5432);
      67                 :             : 
      68         [ +  + ]:           4 :     if (tdr_dsa == NULL)
      69                 :           2 :         tdr_dsa = GetNamedDSA("test_dsm_registry_dsa", &found);
      70                 :             : 
      71         [ +  + ]:           4 :     if (tdr_hash == NULL)
      72                 :           2 :         tdr_hash = GetNamedDSHash("test_dsm_registry_hash", &dsh_params, &found);
      73                 :           4 : }
      74                 :             : 
      75                 :           2 : PG_FUNCTION_INFO_V1(set_val_in_shmem);
      76                 :             : Datum
      77                 :           1 : set_val_in_shmem(PG_FUNCTION_ARGS)
      78                 :             : {
      79                 :           1 :     tdr_attach_shmem();
      80                 :             : 
      81                 :           1 :     LWLockAcquire(&tdr_dsm->lck, LW_EXCLUSIVE);
      82                 :           1 :     tdr_dsm->val = PG_GETARG_INT32(0);
      83                 :           1 :     LWLockRelease(&tdr_dsm->lck);
      84                 :             : 
      85                 :           1 :     PG_RETURN_VOID();
      86                 :             : }
      87                 :             : 
      88                 :           2 : PG_FUNCTION_INFO_V1(get_val_in_shmem);
      89                 :             : Datum
      90                 :           1 : get_val_in_shmem(PG_FUNCTION_ARGS)
      91                 :             : {
      92                 :             :     int         ret;
      93                 :             : 
      94                 :           1 :     tdr_attach_shmem();
      95                 :             : 
      96                 :           1 :     LWLockAcquire(&tdr_dsm->lck, LW_SHARED);
      97                 :           1 :     ret = tdr_dsm->val;
      98                 :           1 :     LWLockRelease(&tdr_dsm->lck);
      99                 :             : 
     100                 :           1 :     PG_RETURN_INT32(ret);
     101                 :             : }
     102                 :             : 
     103                 :           2 : PG_FUNCTION_INFO_V1(set_val_in_hash);
     104                 :             : Datum
     105                 :           1 : set_val_in_hash(PG_FUNCTION_ARGS)
     106                 :             : {
     107                 :             :     TestDSMRegistryHashEntry *entry;
     108                 :           1 :     char       *key = TextDatumGetCString(PG_GETARG_DATUM(0));
     109                 :           1 :     char       *val = TextDatumGetCString(PG_GETARG_DATUM(1));
     110                 :             :     bool        found;
     111                 :             : 
     112         [ -  + ]:           1 :     if (strlen(key) >= offsetof(TestDSMRegistryHashEntry, val))
     113         [ #  # ]:           0 :         ereport(ERROR,
     114                 :             :                 (errmsg("key too long")));
     115                 :             : 
     116                 :           1 :     tdr_attach_shmem();
     117                 :             : 
     118                 :           1 :     entry = dshash_find_or_insert(tdr_hash, key, &found);
     119         [ -  + ]:           1 :     if (found)
     120                 :           0 :         dsa_free(tdr_dsa, entry->val);
     121                 :             : 
     122                 :           1 :     entry->val = dsa_allocate(tdr_dsa, strlen(val) + 1);
     123                 :           1 :     strcpy(dsa_get_address(tdr_dsa, entry->val), val);
     124                 :             : 
     125                 :           1 :     dshash_release_lock(tdr_hash, entry);
     126                 :             : 
     127                 :           1 :     PG_RETURN_VOID();
     128                 :             : }
     129                 :             : 
     130                 :           2 : PG_FUNCTION_INFO_V1(get_val_in_hash);
     131                 :             : Datum
     132                 :           1 : get_val_in_hash(PG_FUNCTION_ARGS)
     133                 :             : {
     134                 :             :     TestDSMRegistryHashEntry *entry;
     135                 :           1 :     char       *key = TextDatumGetCString(PG_GETARG_DATUM(0));
     136                 :           1 :     text       *val = NULL;
     137                 :             : 
     138                 :           1 :     tdr_attach_shmem();
     139                 :             : 
     140                 :           1 :     entry = dshash_find(tdr_hash, key, false);
     141         [ -  + ]:           1 :     if (entry == NULL)
     142                 :           0 :         PG_RETURN_NULL();
     143                 :             : 
     144                 :           1 :     val = cstring_to_text(dsa_get_address(tdr_dsa, entry->val));
     145                 :             : 
     146                 :           1 :     dshash_release_lock(tdr_hash, entry);
     147                 :             : 
     148                 :           1 :     PG_RETURN_TEXT_P(val);
     149                 :             : }
        

Generated by: LCOV version 2.0-1