aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMichael Paquier <michael@paquier.xyz>2023-11-01 14:54:13 +0900
committerMichael Paquier <michael@paquier.xyz>2023-11-01 14:54:13 +0900
commitfe705ef6fc1d1b4b48aea94a1dd2835a6630dacf (patch)
tree95cd1f6ec9722d2fb073bb0a02370d773bd329cc
parent6ec62b779907e2fa49283a7d1dbd761fb64675f1 (diff)
downloadpostgresql-fe705ef6fc1d1b4b48aea94a1dd2835a6630dacf.tar.gz
postgresql-fe705ef6fc1d1b4b48aea94a1dd2835a6630dacf.zip
doc: Expand section related to LWLocks and shared memory
The documentation includes a section describing how to define custom LWLocks in extensions using the shmem hooks. However, it has never mentioned the second, more flexible method based on the following routines: - LWLockNewTrancheId() to allocate a tranche ID. - LWLockRegisterTranche() to associate a name to a tranche ID. - LWLockInitialize() to initialize a LWLock with a tranche ID. autoprewarm.c is the only example of extension in the tree that allocates a LWLock this way. This commit adds some documentation about all that. While on it, a comment is added about the need of AddinShmemInitLock. This is required especially for EXEC_BACKEND builds (aka Windows, normally), as per a remark from Alexander, because backends can execute shmem initialization paths concurrently. Author: Aleksander Alekseev, Michael Paquier Discussion: https://postgr.es/m/CAJ7c6TPKhFgL+54cdTD9yGpG4+sNcyJ+N1GvQqAxgWENAOa3VA@mail.gmail.com
-rw-r--r--doc/src/sgml/xfunc.sgml30
1 files changed, 30 insertions, 0 deletions
diff --git a/doc/src/sgml/xfunc.sgml b/doc/src/sgml/xfunc.sgml
index 96ba95818c2..89116ae74c2 100644
--- a/doc/src/sgml/xfunc.sgml
+++ b/doc/src/sgml/xfunc.sgml
@@ -3429,6 +3429,29 @@ void RequestNamedLWLockTranche(const char *tranche_name, int num_lwlocks)
<productname>PostgreSQL</productname> source tree.
</para>
<para>
+ There is another, more flexible method of obtaining LWLocks. First,
+ allocate a <literal>tranche_id</literal> from a shared counter by
+ calling:
+<programlisting>
+int LWLockNewTrancheId(void)
+</programlisting>
+ Next, each individual process using the <literal>tranche_id</literal>
+ should associate it with a <literal>tranche_name</literal> by calling:
+<programlisting>
+void LWLockRegisterTranche(int tranche_id, const char *tranche_name)
+</programlisting>
+ It is also required to call <function>LWLockInitialize</function> once
+ per LWLock, passing the <literal>tranche_id</literal> as argument:
+<programlisting>
+void LWLockInitialize(LWLock *lock, int tranche_id)
+</programlisting>
+ A complete usage example of <function>LWLockNewTrancheId</function>,
+ <function>LWLockInitialize</function> and
+ <function>LWLockRegisterTranche</function> can be found in
+ <filename>contrib/pg_prewarm/autoprewarm.c</filename> in the
+ <productname>PostgreSQL</productname> source tree.
+ </para>
+ <para>
To avoid possible race-conditions, each backend should use the LWLock
<function>AddinShmemInitLock</function> when connecting to and initializing
its allocation of shared memory, as shown here:
@@ -3451,6 +3474,13 @@ if (!ptr)
}
</programlisting>
</para>
+ <para>
+ It is convenient to use <literal>shmem_startup_hook</literal> which allows
+ placing all the code responsible for initializing shared memory in one
+ place. When using <literal>shmem_startup_hook</literal> the extension
+ still needs to acquire <function>AddinShmemInitLock</function> in order to
+ work properly on all the supported platforms.
+ </para>
</sect2>
<sect2 id="xfunc-addin-wait-events">