PostgreSQL Source Code git master
test_dsa.c
Go to the documentation of this file.
1/*--------------------------------------------------------------------------
2 *
3 * test_dsa.c
4 * Test dynamic shared memory areas (DSAs)
5 *
6 * Copyright (c) 2022-2025, PostgreSQL Global Development Group
7 *
8 * IDENTIFICATION
9 * src/test/modules/test_dsa/test_dsa.c
10 *
11 * -------------------------------------------------------------------------
12 */
13#include "postgres.h"
14
15#include "fmgr.h"
16#include "storage/lwlock.h"
17#include "utils/dsa.h"
18#include "utils/resowner.h"
19
21
22/* Test basic DSA functionality */
26{
27 int tranche_id;
28 dsa_area *a;
29 dsa_pointer p[100];
30
31 /* XXX: this tranche is leaked */
32 tranche_id = LWLockNewTrancheId();
33 LWLockRegisterTranche(tranche_id, "test_dsa");
34
35 a = dsa_create(tranche_id);
36 for (int i = 0; i < 100; i++)
37 {
38 p[i] = dsa_allocate(a, 1000);
39 snprintf(dsa_get_address(a, p[i]), 1000, "foobar%d", i);
40 }
41
42 for (int i = 0; i < 100; i++)
43 {
44 char buf[100];
45
46 snprintf(buf, 100, "foobar%d", i);
47 if (strcmp(dsa_get_address(a, p[i]), buf) != 0)
48 elog(ERROR, "no match");
49 }
50
51 for (int i = 0; i < 100; i++)
52 {
53 dsa_free(a, p[i]);
54 }
55
57
59}
60
61/* Test using DSA across different resource owners */
65{
66 int tranche_id;
67 dsa_area *a;
68 dsa_pointer p[10000];
69 ResourceOwner oldowner;
70 ResourceOwner childowner;
71
72 /* XXX: this tranche is leaked */
73 tranche_id = LWLockNewTrancheId();
74 LWLockRegisterTranche(tranche_id, "test_dsa");
75
76 /* Create DSA in parent resource owner */
77 a = dsa_create(tranche_id);
78
79 /*
80 * Switch to child resource owner, and do a bunch of allocations in the
81 * DSA
82 */
83 oldowner = CurrentResourceOwner;
84 childowner = ResourceOwnerCreate(oldowner, "test_dsa temp owner");
85 CurrentResourceOwner = childowner;
86
87 for (int i = 0; i < 10000; i++)
88 {
89 p[i] = dsa_allocate(a, 1000);
90 snprintf(dsa_get_address(a, p[i]), 1000, "foobar%d", i);
91 }
92
93 /* Also test freeing, by freeing some of the allocations. */
94 for (int i = 0; i < 500; i++)
95 dsa_free(a, p[i]);
96
97 /* Release the child resource owner */
98 CurrentResourceOwner = oldowner;
99 ResourceOwnerRelease(childowner,
101 true, false);
102 ResourceOwnerRelease(childowner,
104 true, false);
105 ResourceOwnerRelease(childowner,
107 true, false);
108 ResourceOwnerDelete(childowner);
109
110 dsa_detach(a);
111
113}
void * dsa_get_address(dsa_area *area, dsa_pointer dp)
Definition: dsa.c:942
void dsa_detach(dsa_area *area)
Definition: dsa.c:1952
void dsa_free(dsa_area *area, dsa_pointer dp)
Definition: dsa.c:826
uint64 dsa_pointer
Definition: dsa.h:62
#define dsa_allocate(area, size)
Definition: dsa.h:109
#define dsa_create(tranch_id)
Definition: dsa.h:117
#define ERROR
Definition: elog.h:39
#define elog(elevel,...)
Definition: elog.h:225
#define PG_RETURN_VOID()
Definition: fmgr.h:349
#define PG_FUNCTION_ARGS
Definition: fmgr.h:193
int a
Definition: isn.c:68
int i
Definition: isn.c:72
void LWLockRegisterTranche(int tranche_id, const char *tranche_name)
Definition: lwlock.c:628
int LWLockNewTrancheId(void)
Definition: lwlock.c:603
static char * buf
Definition: pg_test_fsync.c:72
#define snprintf
Definition: port.h:239
uintptr_t Datum
Definition: postgres.h:69
ResourceOwner ResourceOwnerCreate(ResourceOwner parent, const char *name)
Definition: resowner.c:413
ResourceOwner CurrentResourceOwner
Definition: resowner.c:165
void ResourceOwnerRelease(ResourceOwner owner, ResourceReleasePhase phase, bool isCommit, bool isTopLevel)
Definition: resowner.c:648
void ResourceOwnerDelete(ResourceOwner owner)
Definition: resowner.c:854
@ RESOURCE_RELEASE_LOCKS
Definition: resowner.h:55
@ RESOURCE_RELEASE_BEFORE_LOCKS
Definition: resowner.h:54
@ RESOURCE_RELEASE_AFTER_LOCKS
Definition: resowner.h:56
Definition: dsa.c:348
Datum test_dsa_basic(PG_FUNCTION_ARGS)
Definition: test_dsa.c:25
PG_MODULE_MAGIC
Definition: test_dsa.c:20
Datum test_dsa_resowners(PG_FUNCTION_ARGS)
Definition: test_dsa.c:64
PG_FUNCTION_INFO_V1(test_dsa_basic)