Set proper label for notification sockets 90/154090/7
authorKrzysztof Jackiewicz <k.jackiewicz@samsung.com>
Thu, 5 Oct 2017 14:26:49 +0000 (16:26 +0200)
committerKrzysztof Jackiewicz <k.jackiewicz@samsung.com>
Fri, 13 Oct 2017 15:45:16 +0000 (17:45 +0200)
When a client registers for notification it receives a socket to wait on. The
socket descriptor is transferred using ancillary data. In such cases Smack
checks if Smack rules allow the process that is about to receive it to write to
socket's IPOUT (System::Privileged) and if socket IPIN is allowed to write the
process. CAP_MAC_OVERRIDE is ignored (this may be a bug in Smack). As a result
any process not having System::Privileged label (including ode-admin-cli and UI
apps) is not able to receive the notification socket.

By default notification sockets receive the server's label that is
System::Privileged. This patch sets the IPOUT socket label to '@' so that all
processes can write it and receive the notification socket.

Change-Id: I473099f48e253c4bfe3cebee1a21857d9ea2b963

packaging/ode.spec
server/CMakeLists.txt
server/server.cpp

index b5e0d57..4c82c3d 100755 (executable)
@@ -19,6 +19,7 @@ BuildRequires: pkgconfig(key-manager)
 BuildRequires: pkgconfig(cynara-client)
 BuildRequires: pkgconfig(cynara-session)
 BuildRequires: pkgconfig(openssl)
+BuildRequires: pkgconfig(libsmack)
 Requires: cryptsetup
 
 %description
index ee73f4c..9258da2 100644 (file)
@@ -47,6 +47,7 @@ SET(DEPENDENCY        klay
                                cynara-client
                                cynara-session
                                openssl
+                               libsmack
 )
 
 SET(SERVER_NAME ${PROJECT_NAME}d)
index e3ff24f..e69d3ea 100644 (file)
@@ -15,6 +15,7 @@
  */
 #include <cynara-client.h>
 #include <cynara-session.h>
+#include <sys/smack.h>
 
 #include <klay/audit/dlog-sink.h>
 
@@ -94,7 +95,18 @@ runtime::FileDescriptor ServerContext::registerNotificationSubscriber(const std:
 {
        INFO(SINK, "registerNotificationSubscriber");
        INFO(SINK, name);
-       return runtime::FileDescriptor(subscribeNotification(name), true);
+       int fd = subscribeNotification(name);
+
+       /**
+        *  Set @ label so that smack_file_receive() in kernel succeeds in checking
+        *  'w' access between the client and the IPOUT of the socket.
+        */
+       if (smack_fsetlabel(fd, "@", SMACK_LABEL_IPOUT) != 0) {
+               ERROR(SINK, "Setting IPOUT label failed");
+               throw runtime::Exception("Setting IPOUT label failed");
+       }
+
+       return runtime::FileDescriptor(fd, true);
 }
 
 int ServerContext::unregisterNotificationSubscriber(const std::string& name, int id)