summaryrefslogtreecommitdiff
path: root/man/sd_event_add_memory_pressure.xml
diff options
context:
space:
mode:
authorLennart Poettering <lennart@poettering.net>2023-02-16 17:24:28 +0100
committerLennart Poettering <lennart@poettering.net>2023-02-22 13:16:34 +0100
commitf8a32e679eec7173db5f7ccfb63a2e3841ded1e1 (patch)
treee7dfd45caaafa696368d13c4b97b2dc4bd1dd153 /man/sd_event_add_memory_pressure.xml
parentb7dc40e66317b0d389537d7e3d1cde7d84cac01a (diff)
downloadsystemd-f8a32e679eec7173db5f7ccfb63a2e3841ded1e1.tar.gz
man: document the new sd_event_add_memory_pressure() API
Diffstat (limited to 'man/sd_event_add_memory_pressure.xml')
-rw-r--r--man/sd_event_add_memory_pressure.xml270
1 files changed, 270 insertions, 0 deletions
diff --git a/man/sd_event_add_memory_pressure.xml b/man/sd_event_add_memory_pressure.xml
new file mode 100644
index 0000000000..46cae0d16d
--- /dev/null
+++ b/man/sd_event_add_memory_pressure.xml
@@ -0,0 +1,270 @@
+<?xml version='1.0'?>
+<!DOCTYPE refentry PUBLIC "-//OASIS//DTD DocBook XML V4.5//EN"
+ "http://www.oasis-open.org/docbook/xml/4.2/docbookx.dtd">
+<!-- SPDX-License-Identifier: LGPL-2.1-or-later -->
+
+<refentry id="sd_event_add_memory_pressure" xmlns:xi="http://www.w3.org/2001/XInclude">
+
+ <refentryinfo>
+ <title>sd_event_add_memory_pressure</title>
+ <productname>systemd</productname>
+ </refentryinfo>
+
+ <refmeta>
+ <refentrytitle>sd_event_add_memory_pressure</refentrytitle>
+ <manvolnum>3</manvolnum>
+ </refmeta>
+
+ <refnamediv>
+ <refname>sd_event_add_memory_pressure</refname>
+ <refname>sd_event_source_set_memory_pressure_type</refname>
+ <refname>sd_event_source_set_memory_pressure_period</refname>
+ <refname>sd_event_trim_memory</refname>
+
+ <refpurpose>Add and configure an event source run as result of memory pressure</refpurpose>
+ </refnamediv>
+
+ <refsynopsisdiv>
+ <funcsynopsis>
+ <funcsynopsisinfo>#include &lt;systemd/sd-event.h&gt;</funcsynopsisinfo>
+
+ <funcsynopsisinfo><token>typedef</token> struct sd_event_source sd_event_source;</funcsynopsisinfo>
+
+ <funcprototype>
+ <funcdef>int <function>sd_event_add_memory_pressure</function></funcdef>
+ <paramdef>sd_event *<parameter>event</parameter></paramdef>
+ <paramdef>sd_event_source **<parameter>ret_source</parameter></paramdef>
+ <paramdef>sd_event_handler_t <parameter>handler</parameter></paramdef>
+ <paramdef>void *<parameter>userdata</parameter></paramdef>
+ </funcprototype>
+
+ <funcprototype>
+ <funcdef>int <function>sd_event_source_set_memory_pressure_type</function></funcdef>
+ <paramdef>sd_event_source *<parameter>source</parameter></paramdef>
+ <paramdef>const char *<parameter>type</parameter></paramdef>
+ </funcprototype>
+
+ <funcprototype>
+ <funcdef>int <function>sd_event_source_set_memory_pressure_period</function></funcdef>
+ <paramdef>sd_event_source *<parameter>source</parameter></paramdef>
+ <paramdef>uint64_t <parameter>threshold_usec</parameter></paramdef>
+ <paramdef>uint64_t <parameter>window_usec</parameter></paramdef>
+ </funcprototype>
+
+ <funcprototype>
+ <funcdef>int <function>sd_event_trim_memory</function></funcdef>
+ <paramdef>void</paramdef>
+ </funcprototype>
+ </funcsynopsis>
+ </refsynopsisdiv>
+
+ <refsect1>
+ <title>Description</title>
+
+ <para><function>sd_event_add_memory_pressure()</function> adds a new event source that is triggered
+ whenever memory pressure is seen. This functionality is built around the Linux kernel's <ulink
+ url="https://docs.kernel.org/accounting/psi.html">Pressure Stall Information (PSI)</ulink> logic.</para>
+
+ <para>Expects an event loop object as first parameter, and returns the allocated event source object in
+ the second parameter, on success. The <parameter>handler</parameter> parameter is a function to call when
+ memory pressure is seen, or <constant>NULL</constant>. The handler function will be passed the
+ <parameter>userdata</parameter> pointer, which may be chosen freely by the caller. The handler may return
+ negative to signal an error (see below), other return values are ignored. If
+ <parameter>handler</parameter> is <constant>NULL</constant>, a default handler that compacts allocation
+ caches maintained by <filename>libsystemd</filename> as well as glibc (via <citerefentry
+ project='man-pages'><refentrytitle>malloc_trim</refentrytitle><manvolnum>3</manvolnum></citerefentry>)
+ will be used.</para>
+
+ <para>To destroy an event source object use
+ <citerefentry><refentrytitle>sd_event_source_unref</refentrytitle><manvolnum>3</manvolnum></citerefentry>,
+ but note that the event source is only removed from the event loop when all references to the event
+ source are dropped. To make sure an event source does not fire anymore, even if it is still referenced,
+ disable the event source using
+ <citerefentry><refentrytitle>sd_event_source_set_enabled</refentrytitle><manvolnum>3</manvolnum></citerefentry>
+ with <constant>SD_EVENT_OFF</constant>.</para>
+
+ <para>If the second parameter of <function>sd_event_add_memory_pressure()</function> is
+ <constant>NULL</constant> no reference to the event source object is returned. In this case the event
+ source is considered "floating", and will be destroyed implicitly when the event loop itself is
+ destroyed.</para>
+
+ <para>The event source will fire according to the following logic:</para>
+
+ <orderedlist>
+ <listitem><para>If the
+ <varname>$MEMORY_PRESSURE_WATCH</varname>/<varname>$MEMORY_PRESSURE_WRITE</varname> environment
+ variables are set at the time the event source is established, it will watch the file, FIFO or AF_UNIX
+ socket specified via <varname>$MEMORY_PRESSURE_WATCH</varname> (which must contain an absolute path
+ name) for <constant>POLLPRI</constant> (in case it is a regular file) or <constant>POLLIN</constant>
+ events (otherwise). After opening the inode, it will write the (decoded) Base64 data provided via
+ <varname>$MEMORY_PRESSURE_WRITE</varname> into it before it starts polling on it (the variable may be
+ unset in which case this is skipped). Typically, if used, <varname>$MEMORY_PRESSURE_WATCH</varname>
+ will contain a path such as <filename>/proc/pressure/memory</filename> or a path to a specific
+ <filename>memory.pressure</filename> file in the control group file system
+ (cgroupfs).</para></listitem>
+
+ <listitem><para>If these environment variables are not set, the local PSI interface file
+ <filename>memory.pressure</filename> of the control group the invoking process is running in is
+ used.</para></listitem>
+
+ <listitem><para>If that file does not exist, the system-wide PSI interface file
+ <filename>/proc/pressure/memory</filename> is watched instead.</para></listitem>
+ </orderedlist>
+
+ <para>Or in other words: preferably any explicit configuration passed in by an invoking service manager
+ (or similar) is used as notification source, before falling back to local notifications of the service,
+ and finally to global notifications of the system.</para>
+
+ <para>Well-behaving services and applications are recommended to react to memory pressure events by
+ executing one or more of the following operations, in order to ensure optimal behaviour even on loaded
+ and resource-constrained systems:</para>
+
+ <itemizedlist>
+ <listitem><para>Release allocation caches such as <function>malloc_trim()</function> or similar, both
+ implemented in the libraries consumed by the program and in private allocation caches of the program
+ itself.</para></listitem>
+
+ <listitem><para>Release any other form of in-memory caches that can easily be recovered if
+ needed (e.g. browser caches).</para></listitem>
+
+ <listitem><para>Terminate idle worker threads or processes, or similar.</para></listitem>
+
+ <listitem><para>Even exit entirely from the program if it is idle and can be automatically started when
+ needed (for example via socket or bus activation).</para></listitem>
+ </itemizedlist>
+
+ <para>Any of the suggested operations should help easing memory pressure situations and allowing the
+ system to make progress by reclaiming the memory for other purposes.</para>
+
+ <para>This event source typically fires on memory pressure stalls, i.e. when operational latency above a
+ configured threshold already has been seen. This should be taken into consideration when discussing
+ whether later latency to re-aquire any released resources is acceptable: it's usually more important to
+ think of the latencies that already happened than those coming up in future.</para>
+
+ <para>The <function>sd_event_source_set_memory_pressure_type()</function> and
+ <function>sd_event_source_set_memory_pressure_period()</function> functions can be used to fine-tune the
+ PSI parameters for pressure notifications. The former takes either <literal>some</literal>,
+ <literal>full</literal> as second parameter, the latter takes threshold and period times in microseconds
+ as parameters. For details about these three parameters see the PSI documentation. Note that these two
+ calls must be invoked immediately after allocating the event source, as they must be configured before
+ polling begins. Also note that these calls will fail if memory pressure paramterization has been passed
+ in via the <varname>$MEMORY_PRESSURE_WATCH</varname>/<varname>$MEMORY_PRESSURE_WRITE</varname>
+ environment variables (or in other words: configuration supplied by a service manager wins over internal
+ settings).</para>
+
+ <para>The <function>sd_event_trim_memory()</function> function releases various internal allocation
+ caches maintained by <filename>libsystemd</filename> and then invokes glibc's <citerefentry
+ project='man-pages'><refentrytitle>malloc_trim</refentrytitle><manvolnum>3</manvolnum></citerefentry>. This
+ makes the operation executed when the handler function parameter of
+ <function>sd_event_add_memory_pressure</function> is passed as <constant>NULL</constant> directly
+ accessible for invocation at any time (see above). This function will log a structured log message at
+ <constant>LOG_DEBUG</constant> level (with message ID f9b0be465ad540d0850ad32172d57c21) about the memory
+ pressure operation.</para>
+ </refsect1>
+
+ <refsect1>
+ <title>Return Value</title>
+
+ <para>On success, these functions return 0 or a positive
+ integer. On failure, they return a negative errno-style error
+ code.</para>
+
+ <refsect2>
+ <title>Errors</title>
+
+ <para>Returned errors may indicate the following problems:</para>
+
+ <variablelist>
+ <varlistentry>
+ <term><constant>-ENOMEM</constant></term>
+
+ <listitem><para>Not enough memory to allocate an object.</para></listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><constant>-EINVAL</constant></term>
+
+ <listitem><para>An invalid argument has been passed.</para></listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><constant>-EHOSTDOWN</constant></term>
+
+ <listitem><para>The <varname>$MEMORY_PRESSURE_WATCH</varname> variable has been set to the literal
+ string <filename>/dev/null</filename>, in order to explicitly disable memory pressure
+ handling.</para></listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><constant>-EBADMSG</constant></term>
+
+ <listitem><para>The <varname>$MEMORY_PRESSURE_WATCH</varname> variable has been set to an invalid
+ string, for example a relative rather than an absolute path.</para></listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><constant>-ENOTTY</constant></term>
+
+ <listitem><para>The <varname>$MEMORY_PRESSURE_WATCH</varname> variable points to a regular file
+ outside of the procfs or cgroupfs file systems.</para></listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><constant>-EOPNOTSUPP</constant></term>
+
+ <listitem><para>No configuration via <varname>$MEMORY_PRESSURE_WATCH</varname> has been specified
+ and the local kernel does not support the PSI interface.</para></listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><constant>-EBUSY</constant></term>
+
+ <listitem><para>This is returned by <function>sd_event_source_set_memory_pressure_type()</function>
+ and <function>sd_event_source_set_memory_pressure_period()</function> if invoked on event sources
+ at a time later than immediately after allocting them.</para></listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><constant>-ESTALE</constant></term>
+
+ <listitem><para>The event loop is already terminated.</para></listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><constant>-ECHILD</constant></term>
+
+ <listitem><para>The event loop has been created in a different process.</para></listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><constant>-EDOM</constant></term>
+
+ <listitem><para>The passed event source is not a signal event source.</para></listitem>
+ </varlistentry>
+
+ </variablelist>
+ </refsect2>
+ </refsect1>
+
+ <xi:include href="libsystemd-pkgconfig.xml" />
+
+ <refsect1>
+ <title>See Also</title>
+
+ <para>
+ <citerefentry><refentrytitle>systemd</refentrytitle><manvolnum>1</manvolnum></citerefentry>,
+ <citerefentry><refentrytitle>sd-event</refentrytitle><manvolnum>3</manvolnum></citerefentry>,
+ <citerefentry><refentrytitle>sd_event_new</refentrytitle><manvolnum>3</manvolnum></citerefentry>,
+ <citerefentry><refentrytitle>sd_event_add_io</refentrytitle><manvolnum>3</manvolnum></citerefentry>,
+ <citerefentry><refentrytitle>sd_event_add_time</refentrytitle><manvolnum>3</manvolnum></citerefentry>,
+ <citerefentry><refentrytitle>sd_event_add_child</refentrytitle><manvolnum>3</manvolnum></citerefentry>,
+ <citerefentry><refentrytitle>sd_event_add_inotify</refentrytitle><manvolnum>3</manvolnum></citerefentry>,
+ <citerefentry><refentrytitle>sd_event_add_defer</refentrytitle><manvolnum>3</manvolnum></citerefentry>,
+ <citerefentry><refentrytitle>sd_event_source_set_enabled</refentrytitle><manvolnum>3</manvolnum></citerefentry>,
+ <citerefentry><refentrytitle>sd_event_source_set_description</refentrytitle><manvolnum>3</manvolnum></citerefentry>,
+ <citerefentry><refentrytitle>sd_event_source_set_userdata</refentrytitle><manvolnum>3</manvolnum></citerefentry>,
+ <citerefentry><refentrytitle>sd_event_source_set_floating</refentrytitle><manvolnum>3</manvolnum></citerefentry>
+ </para>
+ </refsect1>
+
+</refentry>