Skip to content

Commit 0ded5c0

Browse files
committed
clonesetup: add support to clone devices via /etc/clonetab
Adds dm-clone device setup at boot via a new /etc/clonetab config file, following the crypttab/veritytab pattern. - Add systemd-clonesetup-generator to parse /etc/clonetab and generate units. - Add systemd-clonesetup binary to create/remove dm-clone devices via ioctl. - Add clonesetup.target for ordering dm-clone activation at boot. - Add region_size= option in clonetab to configure dm-clone hydration granularity. - Add clonetab(5) and systemd-clonesetup-generator(8) man pages. Fixes: systemd#39500
1 parent af4e2a9 commit 0ded5c0

16 files changed

Lines changed: 986 additions & 0 deletions

docs/ENVIRONMENT.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,10 @@ All tools:
7272
`/etc/veritytab`. Only useful for debugging. Currently only supported by
7373
`systemd-veritysetup-generator`.
7474

75+
* `$SYSTEMD_CLONETAB` — if set, use this path instead of
76+
`/etc/clonetab`. Only useful for debugging. Currently only supported by
77+
`systemd-clonesetup-generator`.
78+
7579
* `$SYSTEMD_DEFAULT_HOSTNAME` — override the compiled-in fallback hostname
7680
(relevant in particular for the system manager and `systemd-hostnamed`).
7781
Must be a valid hostname (either a single label or a FQDN).

man/clonetab.xml

Lines changed: 119 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,119 @@
1+
<?xml version="1.0"?>
2+
<!--*-nxml-*-->
3+
<!DOCTYPE refentry PUBLIC "-//OASIS//DTD DocBook XML V4.5//EN"
4+
"http://www.oasis-open.org/docbook/xml/4.5/docbookx.dtd">
5+
<!--
6+
SPDX-License-Identifier: LGPL-2.1-or-later
7+
-->
8+
<refentry id="clonetab" xmlns:xi="http://www.w3.org/2001/XInclude">
9+
10+
<refentryinfo>
11+
<title>clonetab</title>
12+
<productname>systemd</productname>
13+
</refentryinfo>
14+
15+
<refmeta>
16+
<refentrytitle>clonetab</refentrytitle>
17+
<manvolnum>5</manvolnum>
18+
</refmeta>
19+
20+
<refnamediv>
21+
<refname>clonetab</refname>
22+
<refpurpose>Configuration for dm-clone block devices</refpurpose>
23+
</refnamediv>
24+
25+
<refsynopsisdiv>
26+
<para><filename>/etc/clonetab</filename></para>
27+
</refsynopsisdiv>
28+
29+
<refsect1>
30+
<title>Description</title>
31+
32+
<para>The <filename>/etc/clonetab</filename> file describes
33+
dm-clone block devices that are set up during system boot.</para>
34+
35+
<para>Empty lines and lines starting with the <literal>#</literal>
36+
character are ignored. Each of the remaining lines describes one
37+
dm-clone device. Fields are delimited by white space.</para>
38+
39+
<para>Each line is in the form<programlisting><replaceable>name</replaceable> <replaceable>source-device</replaceable> <replaceable>destination-device</replaceable> <replaceable>metadata-device</replaceable> [<replaceable>options</replaceable>]</programlisting>
40+
The first four fields are mandatory, the fifth is optional.</para>
41+
42+
<para>The four fields of <filename>/etc/clonetab</filename> are defined as follows:</para>
43+
44+
<orderedlist>
45+
46+
<listitem><para>The first field contains the name of the resulting dm-clone device; its
47+
block device is set up below <filename>/dev/mapper/</filename>.</para></listitem>
48+
49+
<listitem><para>The second field contains a path to the read-only source block device.
50+
This is the device whose data is cloned to the destination device. Reads to regions not
51+
yet hydrated are served directly from this device.</para></listitem>
52+
53+
<listitem><para>The third field contains a path to the writable destination block device.
54+
The source device's data is copied here in the background. It must be at least as
55+
large as the source device.</para></listitem>
56+
57+
<listitem><para>The fourth field contains a path to the metadata block device. This
58+
small device tracks which regions of the destination have been hydrated and is managed
59+
exclusively by dm-clone.</para></listitem>
60+
61+
<listitem><para>The fifth field, if present, contains comma-separated <literal>key=value</literal>
62+
options. The following option is supported:</para>
63+
64+
<variablelist>
65+
<varlistentry>
66+
<term><option>region_size=<replaceable>N</replaceable></option></term>
67+
<listitem><para>Controls the granularity of background hydration copying — how much
68+
data is copied at a time. Region size is specified in 512-byte sectors, so
69+
<literal>region_size=8</literal> means 8 × 512 = 4KB per region. One region is the
70+
atomic unit dm-clone tracks: it is either fully hydrated (copied to the destination)
71+
or not, never partially. If a copy is interrupted mid-region, that whole region is
72+
retried from scratch on next boot. Smaller regions mean finer progress tracking;
73+
larger regions reduce metadata overhead. Must be a power of two between
74+
<literal>8</literal> and <literal>2097152</literal> sectors. Defaults to
75+
<literal>8</literal> (4KB). For background, see
76+
<ulink url="https://www.kernel.org/doc/html/latest/admin-guide/device-mapper/dm-clone.html">dm-clone kernel documentation</ulink>.
77+
Device mapper sectors are always 512 bytes regardless of physical block size
78+
(<filename>include/linux/blk_types.h</filename>: <literal>SECTOR_SIZE = 1 &lt;&lt; 9</literal>).
79+
</para></listitem>
80+
</varlistentry>
81+
</variablelist>
82+
83+
<para>If no options are needed, the field may be omitted entirely,
84+
<literal>-</literal> may be used as a placeholder, or a quoted empty string
85+
<literal>""</literal> may be used (it is silently ignored).</para></listitem>
86+
87+
</orderedlist>
88+
89+
<para>At early boot and when the system manager configuration is reloaded, this file is
90+
translated into native systemd units by
91+
<citerefentry><refentrytitle>systemd-clonesetup-generator</refentrytitle><manvolnum>8</manvolnum></citerefentry>.</para>
92+
</refsect1>
93+
94+
<refsect1>
95+
<title>Examples</title>
96+
97+
<example>
98+
<title>/etc/clonetab</title>
99+
<para>Clone a source device to a destination, using a separate metadata device:</para>
100+
<programlisting>mydevice /dev/sdb /dev/sdc /dev/sdd</programlisting>
101+
</example>
102+
103+
<example>
104+
<title>/etc/clonetab</title>
105+
<para>Clone a source device to a destination, using a separate metadata device:</para>
106+
<programlisting>mydevice /dev/sdb /dev/sdc /dev/sdd region_size=16</programlisting>
107+
</example>
108+
</refsect1>
109+
110+
<refsect1>
111+
<title>See Also</title>
112+
<para><simplelist type="inline">
113+
<member><citerefentry><refentrytitle>systemd</refentrytitle><manvolnum>1</manvolnum></citerefentry></member>
114+
<member><citerefentry><refentrytitle>systemd-clonesetup-generator</refentrytitle><manvolnum>8</manvolnum></citerefentry></member>
115+
<member><citerefentry project='die-net'><refentrytitle>dmsetup</refentrytitle><manvolnum>8</manvolnum></citerefentry></member>
116+
</simplelist></para>
117+
</refsect1>
118+
119+
</refentry>

man/rules/meson.build

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ manpages = [
1818
['coredump.conf', '5', ['coredump.conf.d'], 'ENABLE_COREDUMP'],
1919
['coredumpctl', '1', [], 'ENABLE_COREDUMP'],
2020
['crypttab', '5', [], 'HAVE_LIBCRYPTSETUP'],
21+
['clonetab', '5', [], ''],
2122
['daemon', '7', [], ''],
2223
['dnssec-trust-anchors.d',
2324
'5',
@@ -1018,6 +1019,7 @@ manpages = [
10181019
['systemd-creds', '1', [], ''],
10191020
['systemd-cryptenroll', '1', [], 'HAVE_LIBCRYPTSETUP'],
10201021
['systemd-cryptsetup-generator', '8', [], 'HAVE_LIBCRYPTSETUP'],
1022+
['systemd-clonesetup-generator', '8', [], ''],
10211023
['systemd-cryptsetup',
10221024
'8',
10231025
['systemd-cryptsetup@.service'],
Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
<?xml version="1.0"?>
2+
<!--*-nxml-*-->
3+
<!DOCTYPE refentry PUBLIC "-//OASIS//DTD DocBook XML V4.5//EN"
4+
"http://www.oasis-open.org/docbook/xml/4.5/docbookx.dtd">
5+
<!-- SPDX-License-Identifier: LGPL-2.1-or-later -->
6+
<refentry id="systemd-clonesetup-generator" xmlns:xi="http://www.w3.org/2001/XInclude">
7+
8+
<refentryinfo>
9+
<title>systemd-clonesetup-generator</title>
10+
<productname>systemd</productname>
11+
</refentryinfo>
12+
13+
<refmeta>
14+
<refentrytitle>systemd-clonesetup-generator</refentrytitle>
15+
<manvolnum>8</manvolnum>
16+
</refmeta>
17+
18+
<refnamediv>
19+
<refname>systemd-clonesetup-generator</refname>
20+
<refpurpose>Unit generator for <filename>/etc/clonetab</filename></refpurpose>
21+
</refnamediv>
22+
23+
<refsynopsisdiv>
24+
<para><filename>/usr/lib/systemd/system-generators/systemd-clonesetup-generator</filename></para>
25+
</refsynopsisdiv>
26+
27+
<refsect1>
28+
<title>Description</title>
29+
30+
<para><filename>systemd-clonesetup-generator</filename> is a generator that translates
31+
<filename>/etc/clonetab</filename> into native systemd units early at boot and when
32+
configuration of the system manager is reloaded. This will create
33+
<citerefentry><refentrytitle>systemd-clonesetup@.service</refentrytitle><manvolnum>8</manvolnum></citerefentry>
34+
units as necessary.</para>
35+
36+
<para><filename>systemd-clonesetup-generator</filename> implements
37+
<citerefentry><refentrytitle>systemd.generator</refentrytitle><manvolnum>7</manvolnum></citerefentry>.</para>
38+
</refsect1>
39+
40+
<refsect1>
41+
<title>See Also</title>
42+
<para><simplelist type="inline">
43+
<member><citerefentry><refentrytitle>systemd</refentrytitle><manvolnum>1</manvolnum></citerefentry></member>
44+
<member><citerefentry><refentrytitle>clonetab</refentrytitle><manvolnum>5</manvolnum></citerefentry></member>
45+
<member><citerefentry><refentrytitle>systemd-clonesetup@.service</refentrytitle><manvolnum>8</manvolnum></citerefentry></member>
46+
<member><citerefentry project='die-net'><refentrytitle>dmsetup</refentrytitle><manvolnum>8</manvolnum></citerefentry></member>
47+
</simplelist></para>
48+
</refsect1>
49+
50+
</refentry>

meson.build

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -292,6 +292,7 @@ conf.set_quoted('SYSTEMD_USERWORK_PATH', libexecdir / 'syst
292292
conf.set_quoted('SYSTEMD_MOUNTWORK_PATH', libexecdir / 'systemd-mountwork')
293293
conf.set_quoted('SYSTEMD_NSRESOURCEWORK_PATH', libexecdir / 'systemd-nsresourcework')
294294
conf.set_quoted('SYSTEMD_VERITYSETUP_PATH', libexecdir / 'systemd-veritysetup')
295+
conf.set_quoted('SYSTEMD_CLONESETUP_PATH', bindir / 'systemd-clonesetup')
295296
conf.set_quoted('SYSTEM_CONFIG_UNIT_DIR', pkgsysconfdir / 'system')
296297
conf.set_quoted('SYSTEM_DATA_UNIT_DIR', systemunitdir)
297298
conf.set_quoted('SYSTEM_ENV_GENERATOR_DIR', systemenvgeneratordir)
@@ -1981,6 +1982,7 @@ subdir('src/debug-generator')
19811982
subdir('src/delta')
19821983
subdir('src/detect-virt')
19831984
subdir('src/dissect')
1985+
subdir('src/clonesetup')
19841986
subdir('src/environment-d-generator')
19851987
subdir('src/escape')
19861988
subdir('src/factory-reset')

src/basic/special.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,7 @@
9797
#define SPECIAL_PCRFS_ROOT_SERVICE "systemd-pcrfs-root.service"
9898
#define SPECIAL_VALIDATEFS_SERVICE "systemd-validatefs@.service"
9999
#define SPECIAL_HIBERNATE_RESUME_SERVICE "systemd-hibernate-resume.service"
100+
#define SPECIAL_CLONESETUP_TARGET "clonesetup.target"
100101

101102
/* Services systemd relies on */
102103
#define SPECIAL_DBUS_SERVICE "dbus.service"

0 commit comments

Comments
 (0)