aboutsummaryrefslogtreecommitdiffstats
path: root/extras/selinux/selinux_doc.md
blob: e71bd6582869c746b993cdfb1daa1a55cf3aac6e (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
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
# SELinux - VPP Custom SELinux Policy    {#selinux_doc}

## Overview

Security-enhanced Linux (SELinux) is a security feature in the Linux kernel. At
a very high level, SELinux implements mandatory access controls (MAC), as
opposed to discretionary access control (DAC) implemented in standard Linux. MAC
defines how processes can interact with other system components (Files,
Directories, Other Processes, Pipes, Sockets, Network Ports). Each system
component is assigned a label, and then the SELinux Policy defines which labels
and which actions on each label a process is able to perform. The VPP Custom
SELinux Policy defines the actions VPP is allowed to perform on which labels.

The VPP Custom SELinux Policy is intended to be installed on RPM based platforms
(tested on CentOS 7 and RHEL 7). Though SELinux can run on Debian platforms, it
typically is not and therefore is not currently being built for Debian.

The VPP Custom SELinux Policy does not enable or disable SELinux, only allows
VPP to run when SELinux is enabled. A fresh install of either Fedora, CentOS or
RHEL will have SELinux enabled by default. To determine if SELinux is enabled on
a given system and enable it if needed, run:

```
   $ getenforce
   Permissive

   $ sudo setenforce 1

   $ getenforce
   Enforcing
```

To make the change persistent, modify the following file to set
`SELINUX=enforcing`:

```
   $ sudo vi /etc/selinux/config
   :
   # This file controls the state of SELinux on the system.
   # SELINUX= can take one of these three values:
   #     enforcing - SELinux security policy is enforced.
   #     permissive - SELinux prints warnings instead of enforcing.
   #     disabled - No SELinux policy is loaded.
   SELINUX=enforcing
   :
```

## Installation

To install VPP, see the installation instructions on the VPP Wiki
(https://wiki.fd.io/view/VPP/Installing_VPP_binaries_from_packages). The VPP
Custom SELinux Policy is packaged in its own RPM starting in 18.04,
`vpp-selinux-policy-<VERSION>-<RELEASE>.rpm`. It is packaged and installed along
with the other VPP RPMs.

### Fresh Install of VPP

If VPP has never been installed on a system, then starting in 18.04, the VPP
Custom SELinux Policy will be installed with the other RPMs and all the system
components managed by VPP will be labeled properly.

### Fix SELinux Labels for VPP
In the case where the VPP Custom Policy is being installed for the first time,
either because VPP has been upgraded or packages were removed and then
reinstalled, several directories and files will not not be properly labeled. The
labels on these files will need to be fixed for VPP to run properly with SELinux
enabled. After the VPP Custom SELinux Policy is installed, run the following
commands to fix the labels. If VPP is already running, make sure to restart
VPP after the labels are fixed. This change is persistent for the life of the
file. Once the VPP Custom Policy is installed on the system, subsequent files
created by VPP will be labeled properly. This is only to fix files created by
VPP prior to the VPP Custom Policy being installed.

```
  $ sudo restorecon -Rv /etc/vpp/
  $ sudo restorecon -Rv /usr/lib/vpp_api_test_plugins/
  $ sudo restorecon -Rv /usr/lib/vpp_plugins/
  $ sudo restorecon -Rv /usr/share/vpp/
  $ sudo restorecon -Rv /var/run/vpp/

  $ sudo chcon -t vpp_tmp_t /tmp/vpp_*
  $ sudo chcon -t vpp_var_run_t /var/run/.vpp_*
```

**NOTE:** Because the VPP APIs allow custom filenames in certain scenarios, the
above commands may not handle all files. Inspect your system and correct any
files that are mislabeled. For example, to verify all VPP files in `/tmp/` are
labeled properly, run:

```
  $ sudo ls -alZ /tmp/
```

Any files not properly labeled with `vpp_tmp_t`, run:

```
  $ sudo chcon -t vpp_tmp_t /tmp/<filename>
```

## VPP Files

### Recommended Default File Directories

Documentation in the VPP Wiki (https://wiki.fd.io/view/VPP/) and doxygen
generated documentation have examples with files located in certain directories.
Some of the recommend file locations have been moved to satisfy SELinux. Most of
the documentation has been updated, but links to older documentation still exist
and there may have been instances that were missed. Use the file locations
described below to allow SELinux to properly label the given files.

File locations that have changed:
* VPP Debug CLI Script Files
* vHost Sockets
* VPP Log Files

#### VPP Debug CLI Script Files

The VPP Debug CLI, `vppctl`, allows a sequence of CLI commands to be read from a
file and executed. To avoid from having to grant VPP access to all of `/tmp/` and
possibly `/home/` sub-directories, it is recommended that any VPP Debug CLI script
files be placed in a common directory such as `/usr/share/vpp/`.

For example:
```
$ cat /usr/share/vpp/scripts/gigup.txt
set interface state GigabitEthernet0/8/0 up
set interface state GigabitEthernet0/9/0 up
```

To execute:
```
$ vppctl exec /usr/share/vpp/scripts/gigup.txt
```
Or
```
$ vppctl
    _______    _        _   _____  ___
 __/ __/ _ \  (_)__    | | / / _ \/ _ \
 _/ _// // / / / _ \   | |/ / ___/ ___/
 /_/ /____(_)_/\___/   |___/_/  /_/

vpp# exec /usr/share/vpp/scripts/gigup.txt
vpp# quit

```

If the file is not labeled properly, you will see something similar to:
```
$ vppctl exec /home/<user>/dev/vpp/scripts/vppctl/gigup.txt
exec: failed to open `/home/<user>/dev/vpp/scripts/vppctl/gigup.txt': Permission denied

$ ls -alZ
drwxrwxr-x. <user> <user> unconfined_u:object_r:user_home_t:s0 .
drwxrwxr-x. <user> <user> unconfined_u:object_r:user_home_t:s0 ..
-rw-r--r--. <user> <user> unconfined_u:object_r:user_home_t:s0 gigup.txt
```

##### Original Documentation

Some of the original documentation showed script files being executed out of
`/tmp/`. Convenience also may lead to script files being placed in
`/home/<user>/` subdirectories. If a file is generated by the VPP process in
`/tmp/`, for example a trace file or pcap file, it will get properly labeled
with the SELinux label `vpp_tmp_t`. When a file is created, unless a rule is in
place for the process that created it, the file will inherit the SELinux label
of the parent directory. So if a user creates a file themselves in `/tmp/`, it
will get the SELinux label `tmp_t`, which VPP does not have permission to
access. Therefore it is recommended that script files are located as described
above.

#### vHost Sockets

vHost sockets are created from VPP perspective in either Server or Client mode.
In Server mode, the socket name is provided to VPP and VPP creates the socket.
In Client mode, the socket name is provided to VPP and the hypervisor creates
the socket. In order for VPP and hypervisor to share the socket resource with
SELinux enabled, a rule in the VPP Custom SELinux Policy has been added. This
rules allows processes with the `svirt_t` label (the hypervisor) to access
sockets with the `vpp_var_run_t` label. As such, when SELinux is enabled,
vHost sockets should be created in the directory `/var/run/vpp/`.

##### Original Documentation

Some of the original documentation showed vHost sockets being created in the
directory `/tmp/`. To work properly with SELinux enabled, vHost sockets should be
created as described above.

#### VPP Log Files

The VPP log file location is set by updating the `/etc/vpp/startup.conf` file:

```
vi /etc/vpp/startup.conf
unix {
:
  log /var/log/vpp/vpp.log
:
}

```

By moving the log file to `/var/log/vpp/`, it will get the label `vpp_log_t`,
which indicates that the files are log files so they benefit from the
associated rules (for example granting rights to logrotate so that it can
manipulate them).

##### Original Documentation

The default `startup.conf` file creates the VPP log file in `/tmp/vpp.log`. By
leaving the log file in `/tmp/`, it will get the label `vpp_tmp_t`. Moving it
to `/var/log/vpp/`, it will get the label `vpp_log_t`.

### Use of Non-default File Directories

VPP installs multiple files on the system.
Some files have fixed directory and file names:
- /etc/bash_completion.d/vppctl_completion
- /etc/sysctl.d/80-vpp.conf
- /usr/lib/systemd/system/vpp.service

Others files have default directory and file names but the default can be
overwritten:
- /etc/vpp/startup.conf
  - Can be changed via the `/usr/lib/systemd/system/vpp.service` file by
    changing the -c option on the VPP command line:

```
ExecStart=/usr/bin/vpp -c /etc/vpp/startup.conf
```

- /run/vpp/cli.sock
  - Can be changed via the `/etc/vpp/startup.conf` file by changing the
    cli-listen setting:

```
unix {
:
  cli-listen /run/vpp/cli.sock
:
}
```


- /var/log/vpp/vpp.log
  - Can be changed via the `/etc/vpp/startup.conf` file by changing the log
    setting:

```
unix {
  :
  log /var/log/vpp/vpp.log
  :
}

```

If the directory of any VPP installed files is changed from the default, ensure
that the proper SELiunx label is applied. The SELinux label can be determined by
passing the -Z option to many common Linux commands:

```
ls -alZ /run/vpp/
drwxr-xr-x. root vpp  system_u:object_r:vpp_var_run_t:s0 .
drwxr-xr-x. root root system_u:object_r:var_run_t:s0     ..
srwxrwxr-x. root vpp  system_u:object_r:vpp_var_run_t:s0 cli.sock
```

### VPP SELinux Types ###

The following SELinux types are created by the VPP Custom SELinux Policy:
- `vpp_t` - Applied to:
  - VPP process and spawned threads.

- `vpp_config_rw_t` - Applied to:
  - `/etc/vpp/*`

- `vpp_tmp_t` - Applied to:
  - `/tmp/*`

- `vpp_exec_t` - Applied to:
  - `/usr/bin/*`

- `vpp_lib_t` - Applied to:
  - `/usr/lib/vpp_api_test_plugins/*`
  - `/usr/lib/vpp_plugins/*`

- `vpp_unit_file_t` - Applied to:
  - `/usr/lib/systemd/system/vpp.*`

- `vpp_log_t` - Applied to:
  - `/var/log/vpp/*`

- `vpp_var_run_t` - Applied to:
  - `/var/run/vpp/*`