• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

systemd / systemd / 12940458095

23 Jan 2025 10:34PM UTC coverage: 71.463% (+0.02%) from 71.444%
12940458095

push

github

web-flow
nspawn: support unpriv directory-tree containers (#35685)

So far nspawn supported unpriv containers only if backed by a DDI. This
adds dir-based unpriv containers too.

To make this work this introduces a new UID concept to systemd: the
"foreign UID range". This is a high UID range of size 64K. The idea is
that disk images that are "foreign" to the local system can use that,
and when a container or similar is invoked from it, a transiently
allocated dynamic UID range is mapped from that foreign UID range via id
mapped mounts.

This means the fully dynamic, transient UID ranges never hit the disk,
which should vastly simplify management, and does not require that uid
"subranges" are persistently delegated to any users.

The mountfsd daemon gained a new method call for acquiring an idmapped
mount fd for an mount tree owned by the foreign UID range. Access is
permitted to unpriv clients – as long as the referenced inode is located
within a dir owned by client's own uid range.

166 of 349 new or added lines in 6 files covered. (47.56%)

2432 existing lines in 65 files now uncovered.

291664 of 408131 relevant lines covered (71.46%)

709262.54 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

97.92
/src/basic/hash-funcs.c
1
/* SPDX-License-Identifier: LGPL-2.1-or-later */
2

3
#include <string.h>
4

5
#include "hash-funcs.h"
6
#include "path-util.h"
7
#include "strv.h"
8

9
void string_hash_func(const char *p, struct siphash *state) {
92,550,457✔
10
        siphash24_compress(p, strlen(p) + 1, state);
92,550,457✔
11
}
92,550,457✔
12

13
DEFINE_HASH_OPS(string_hash_ops,
14
                char, string_hash_func, string_compare_func);
15
DEFINE_HASH_OPS_WITH_KEY_DESTRUCTOR(
444,197✔
16
                string_hash_ops_free,
17
                char, string_hash_func, string_compare_func, free);
18
DEFINE_HASH_OPS_WITH_VALUE_DESTRUCTOR(
27,489✔
19
                string_hash_ops_value_free,
20
                char, string_hash_func, string_compare_func,
21
                void, free);
22
DEFINE_HASH_OPS_FULL(
22,463,122✔
23
                string_hash_ops_free_free,
24
                char, string_hash_func, string_compare_func, free,
25
                void, free);
26
DEFINE_HASH_OPS_FULL(
7,216✔
27
                string_hash_ops_free_strv_free,
28
                char, string_hash_func, string_compare_func, free,
29
                char*, strv_free);
30

31
void path_hash_func(const char *q, struct siphash *state) {
20,637,523✔
32
        bool add_slash = false;
20,637,523✔
33

34
        assert(q);
20,637,523✔
35
        assert(state);
20,637,523✔
36

37
        /* Calculates a hash for a path in a way this duplicate inner slashes don't make a differences, and also
38
         * whether there's a trailing slash or not. This fits well with the semantics of path_compare(), which does
39
         * similar checks and also doesn't care for trailing slashes. Note that relative and absolute paths (i.e. those
40
         * which begin in a slash or not) will hash differently though. */
41

42
        /* if path is absolute, add one "/" to the hash. */
43
        if (path_is_absolute(q))
20,637,523✔
44
                siphash24_compress_byte('/', state);
16,375,656✔
45

46
        for (;;) {
193,012,513✔
47
                const char *e;
106,825,018✔
48
                int r;
106,825,018✔
49

50
                r = path_find_first_component(&q, true, &e);
106,825,018✔
51
                if (r == 0)
106,825,018✔
52
                        return;
20,637,523✔
53

54
                if (add_slash)
86,187,687✔
55
                        siphash24_compress_byte('/', state);
65,605,835✔
56

57
                if (r < 0) {
86,187,687✔
58
                        /* if a component is invalid, then add remaining part as a string. */
59
                        string_hash_func(q, state);
192✔
60
                        return;
192✔
61
                }
62

63
                /* Add this component to the hash. */
64
                siphash24_compress(e, r, state);
86,187,495✔
65

66
                add_slash = true;
86,187,495✔
67
        }
68
}
69

70
DEFINE_HASH_OPS(path_hash_ops,
71
                char, path_hash_func, path_compare);
72
DEFINE_HASH_OPS_WITH_KEY_DESTRUCTOR(
1,066,444✔
73
                path_hash_ops_free,
74
                char, path_hash_func, path_compare, free);
75
DEFINE_HASH_OPS_FULL(
99,808✔
76
                path_hash_ops_free_free,
77
                char, path_hash_func, path_compare, free,
78
                void, free);
79

80
void trivial_hash_func(const void *p, struct siphash *state) {
29,833,711✔
81
        siphash24_compress_typesafe(p, state);
29,833,711✔
82
}
29,833,711✔
83

84
int trivial_compare_func(const void *a, const void *b) {
18,415,748✔
85
        return CMP(a, b);
18,415,748✔
86
}
87

88
DEFINE_HASH_OPS(trivial_hash_ops,
89
                void, trivial_hash_func, trivial_compare_func);
90
DEFINE_HASH_OPS_WITH_KEY_DESTRUCTOR(
11,591✔
91
                trivial_hash_ops_free,
92
                void, trivial_hash_func, trivial_compare_func, free);
93
DEFINE_HASH_OPS_WITH_VALUE_DESTRUCTOR(
3,867✔
94
                trivial_hash_ops_value_free,
95
                void, trivial_hash_func, trivial_compare_func,
96
                void, free);
97
DEFINE_HASH_OPS_FULL(
3,288✔
98
                trivial_hash_ops_free_free,
99
                void, trivial_hash_func, trivial_compare_func, free,
100
                void, free);
101

102
void uint64_hash_func(const uint64_t *p, struct siphash *state) {
27,005,900✔
103
        siphash24_compress_typesafe(*p, state);
27,005,900✔
104
}
27,005,900✔
105

106
int uint64_compare_func(const uint64_t *a, const uint64_t *b) {
24,404,939✔
107
        return CMP(*a, *b);
24,404,939✔
108
}
109

110
DEFINE_HASH_OPS(uint64_hash_ops,
111
                uint64_t, uint64_hash_func, uint64_compare_func);
112
DEFINE_HASH_OPS_WITH_VALUE_DESTRUCTOR(
31,744✔
113
                uint64_hash_ops_value_free,
114
                uint64_t, uint64_hash_func, uint64_compare_func,
115
                void, free);
116

117
#if SIZEOF_DEV_T != 8
118
void devt_hash_func(const dev_t *p, struct siphash *state) {
119
        siphash24_compress_typesafe(*p, state);
120
}
121
#endif
122

123
int devt_compare_func(const dev_t *a, const dev_t *b) {
22✔
124
        int r;
22✔
125

126
        r = CMP(major(*a), major(*b));
22✔
127
        if (r != 0)
22✔
UNCOV
128
                return r;
×
129

130
        return CMP(minor(*a), minor(*b));
22✔
131
}
132

133
DEFINE_HASH_OPS(devt_hash_ops, dev_t, devt_hash_func, devt_compare_func);
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc