aboutsummaryrefslogtreecommitdiffstats
path: root/meta-oe/recipes-core/dbus/dbus-broker/0003-dbus-socket-treat-MSG_CTRUNC-gracefully.patch
blob: 53f9e71aab491530b52e7a5e8464f7aaf28f7592 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
From 520c47c53deeb893e03194fefaf3c5b9223ede27 Mon Sep 17 00:00:00 2001
From: David Rheinsberg <david.rheinsberg@gmail.com>
Date: Fri, 10 May 2019 10:58:06 +0200
Subject: [PATCH] dbus/socket: treat MSG_CTRUNC gracefully

As it turns out, LSMs allow clients to trigger a MSG_CTRUNC on the
remote side of a unix socket. Whenever LSMs reject the transmission of
an FD, they will simply drop the FD and set MSG_CTRUNC, without any
other error notification.

Therefore, we must assume any occurance of MSG_CTRUNC is trigger by a
client. This makes it impossible to consider MSG_CTRUNC for any other
error handling, and as such we are left to disconnecting the client and
ignoring the flag.

Luckily, MSG_CTRUNC is expected for any other event, so we only used it
for diagnostics so far.

Signed-off-by: David Rheinsberg <david.rheinsberg@gmail.com>
Upstream-Status: dbus-broker@520c47c53deeb893e03194fefaf3c5b9223ede27
---
 src/dbus/socket.c | 44 +++++++++++++++++++++++++++++++++-----------
 1 file changed, 33 insertions(+), 11 deletions(-)

diff --git a/src/dbus/socket.c b/src/dbus/socket.c
index cacdff2..6e6ba10 100644
--- a/src/dbus/socket.c
+++ b/src/dbus/socket.c
@@ -593,18 +593,40 @@ static int socket_recvmsg(Socket *socket,
 
         if (msg.msg_flags & MSG_CTRUNC) {
                 /*
-                 * This flag means the control-buffer was too small to retrieve
-                 * all data. If this can be triggered remotely, it means a peer
-                 * can cause us to miss FDs. Hence, we really must protect
-                 * against this.
-                 * We do provide suitably sized buffers to be prepared for any
-                 * possible scenario. So if this happens, something is fishy
-                 * and we better report it.
-                 * Note that this is also reported by the kernel if we exceeded
-                 * our NOFILE limit. Since this implies resource
-                 * misconfiguration as well, we treat it the same way.
+                 * Our control-buffer-size is carefully calculated to be big
+                 * enough for any possible ancillary data we expect. Therefore,
+                 * the kernel should never be required to truncate it, and thus
+                 * MSG_CTRUNC will never be set. This is also foward compatible
+                 * to future extensions to the ancillary data, since these must
+                 * be enabled explicitly before the kernel considers forwarding
+                 * them.
+                 *
+                 * Unfortunately, the SCM_RIGHTS implementation might set this
+                 * flag as well. In particular, if not all FDs can be returned
+                 * to user-space, MSG_CTRUNC will be set (signalling that the
+                 * FD-set is non-complete). No other error is returned or
+                 * signalled, though. There are several reasons why the FD
+                 * transmission can fail. Most importantly, if we exhaust our
+                 * FD limit, further FDs will simply be discarded. We are
+                 * protected against this by our accounting-quotas, but we
+                 * would still like to catch this condition and warn loudly.
+                 * However, FDs are also dropped if the security layer refused
+                 * the transmission of the FD in question. This means, if an
+                 * LSM refuses the D-Bus client to send us an FD, the FD is
+                 * just dropped and MSG_CTRUNC will be set. This can be
+                 * triggered by clients.
+                 *
+                 * To summarize: In an ideal world, we would expect this flag
+                 * to never be set, and we would just use
+                 * `error_origin(-ENOTRECOVERABLE)` to provide diagnostics.
+                 * Unfortunately, the gross misuse of this flag for LSM
+                 * security enforcements means we have to assume any occurence
+                 * of MSG_CTRUNC means the client was refused to send a
+                 * specific message. Our only possible way to deal with this is
+                 * to disconnect the client.
                  */
-                r = error_origin(-ENOTRECOVERABLE);
+                socket_close(socket);
+                r = SOCKET_E_LOST_INTEREST;
                 goto error;
         }
 
-- 
2.21.0