Commit 0eb59ccf authored by Auke Kok's avatar Auke Kok Committed by Lennart Poettering

SMACK: Add configuration options. (v3)

This adds SMACK label configuration options to socket units.

SMACK labels should be applied to most objects on disk well before
execution time, but two items remain that are generated dynamically
at run time that require SMACK labels to be set in order to enforce
MAC on all objects.

Files on disk can be labelled using package management.

For device nodes, simple udev rules are sufficient to add SMACK labels
at boot/insertion time.

Sockets can be created at run time and systemd does just that for
several services. In order to protect FIFO's and UNIX domain sockets,
we must instruct systemd to apply SMACK labels at runtime.

This patch adds the following options:

Smack - applicable to FIFO's.
SmackIpIn/SmackIpOut - applicable to sockets.

No external dependencies are required to support SMACK, as setting
the labels is done using fsetxattr(). The labels can be set on a
kernel that does not have SMACK enabled either, so there is no need
to #ifdef any of this code out.

For more information about SMACK, please see Documentation/Smack.txt
in the kernel source code.

v3 of this patch changes the config options to be CamelCased.
parent 978cf3c7
......@@ -484,6 +484,26 @@
for details.</para></listitem>
<listitem><para>Takes a string
value. Controls the extended
respectively, i.e. the security label
of the FIFO, or the security label for
the incoming or outgoing connections
of the socket, respectively. See
for details.</para></listitem>
<listitem><para>Takes an integer
......@@ -63,6 +63,9 @@
" <property name=\"MessageQueueMaxMessages\" type=\"x\" access=\"read\"/>\n" \
" <property name=\"MessageQueueMessageSize\" type=\"x\" access=\"read\"/>\n" \
" <property name=\"Result\" type=\"s\" access=\"read\"/>\n" \
" <property name=\"SmackLabel\" type=\"s\" access=\"read\"/>\n" \
" <property name=\"SmackLabelIPIn\" type=\"s\" access=\"read\"/>\n" \
" <property name=\"SmackLabelIPOut\" type=\"s\" access=\"read\"/>\n" \
" </interface>\n" \
......@@ -126,6 +129,9 @@ static const BusProperty bus_socket_properties[] = {
{ "MessageQueueMaxMessages", bus_property_append_long, "x", offsetof(Socket, mq_maxmsg) },
{ "MessageQueueMessageSize", bus_property_append_long, "x", offsetof(Socket, mq_msgsize) },
{ "Result", bus_socket_append_socket_result, "s", offsetof(Socket, result) },
{ "SmackLabel", bus_property_append_string, "s", offsetof(Socket, smack), true },
{ "SmackLabelIPIn", bus_property_append_string, "s", offsetof(Socket, smack_ip_in), true },
{ "SmackLabelIPOut",bus_property_append_string, "s", offsetof(Socket, smack_ip_out), true },
{ NULL, }
......@@ -208,6 +208,9 @@ Socket.TCPCongestion, config_parse_string, 0,
Socket.MessageQueueMaxMessages, config_parse_long, 0, offsetof(Socket, mq_maxmsg)
Socket.MessageQueueMessageSize, config_parse_long, 0, offsetof(Socket, mq_msgsize)
Socket.Service, config_parse_socket_service, 0, 0
Socket.SmackLabel, config_parse_string, 0, offsetof(Socket, smack)
Socket.SmackLabelIPIn, config_parse_string, 0, offsetof(Socket, smack_ip_in)
Socket.SmackLabelIPOut, config_parse_string, 0, offsetof(Socket, smack_ip_out)
......@@ -28,6 +28,7 @@
#include <signal.h>
#include <arpa/inet.h>
#include <mqueue.h>
#include <attr/xattr.h>
#include "unit.h"
#include "socket.h"
......@@ -131,6 +132,10 @@ static void socket_done(Unit *u) {
s->bind_to_device = NULL;
unit_unwatch_timer(u, &s->timer_watch);
......@@ -508,6 +513,21 @@ static void socket_dump(Unit *u, FILE *f, const char *prefix) {
"%sMessageQueueMessageSize: %li\n",
prefix, s->mq_msgsize);
if (s->smack)
"%sSmackLabel: %s\n",
prefix, s->smack);
if (s->smack_ip_in)
"%sSmackLabelIPIn: %s\n",
prefix, s->smack_ip_in);
if (s->smack_ip_out)
"%sSmackLabelIPOut: %s\n",
prefix, s->smack_ip_out);
LIST_FOREACH(port, p, s->ports) {
if (p->type == SOCKET_SOCKET) {
......@@ -747,6 +767,14 @@ static void socket_apply_socket_options(Socket *s, int fd) {
if (s->tcp_congestion)
if (setsockopt(fd, SOL_TCP, TCP_CONGESTION, s->tcp_congestion, strlen(s->tcp_congestion)+1) < 0)
log_warning("TCP_CONGESTION failed: %m");
if (s->smack_ip_in)
if (fsetxattr(fd, "security.SMACK64IPIN", s->smack_ip_in, strlen(s->smack_ip_in), 0) < 0)
log_error("fsetxattr(\"security.SMACK64IPIN\"): %m");
if (s->smack_ip_out)
if (fsetxattr(fd, "security.SMACK64IPOUT", s->smack_ip_out, strlen(s->smack_ip_out), 0) < 0)
log_error("fsetxattr(\"security.SMACK64IPOUT\"): %m");
static void socket_apply_fifo_options(Socket *s, int fd) {
......@@ -756,6 +784,10 @@ static void socket_apply_fifo_options(Socket *s, int fd) {
if (s->pipe_size > 0)
if (fcntl(fd, F_SETPIPE_SZ, s->pipe_size) < 0)
log_warning("F_SETPIPE_SZ: %m");
if (s->smack)
if (fsetxattr(fd, "security.SMACK64", s->smack, strlen(s->smack), 0) < 0)
log_error("fsetxattr(\"security.SMACK64\"): %m");
static int fifo_address_create(
......@@ -144,6 +144,10 @@ struct Socket {
/* Only for INET6 sockets: issue IPV6_V6ONLY sockopt */
SocketAddressBindIPv6Only bind_ipv6_only;
char *smack;
char *smack_ip_in;
char *smack_ip_out;
/* Called from the service code when collecting fds */
Markdown is supported
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment