1 |
62 |
marcus.erl |
|
2 |
|
|
|
3 |
|
|
"http://www.oasis-open.org/docbook/xml/4.1.2/docbookx.dtd" []>
|
4 |
|
|
|
5 |
|
|
|
6 |
|
|
|
7 |
|
|
Linux Security Modules: General Security Hooks for Linux
|
8 |
|
|
|
9 |
|
|
|
10 |
|
|
Stephen
|
11 |
|
|
Smalley
|
12 |
|
|
|
13 |
|
|
NAI Labs
|
14 |
|
|
ssmalley@nai.com
|
15 |
|
|
|
16 |
|
|
|
17 |
|
|
|
18 |
|
|
Timothy
|
19 |
|
|
Fraser
|
20 |
|
|
|
21 |
|
|
NAI Labs
|
22 |
|
|
tfraser@nai.com
|
23 |
|
|
|
24 |
|
|
|
25 |
|
|
|
26 |
|
|
Chris
|
27 |
|
|
Vance
|
28 |
|
|
|
29 |
|
|
NAI Labs
|
30 |
|
|
cvance@nai.com
|
31 |
|
|
|
32 |
|
|
|
33 |
|
|
|
34 |
|
|
|
35 |
|
|
|
36 |
|
|
Introduction
|
37 |
|
|
|
38 |
|
|
|
39 |
|
|
In March 2001, the National Security Agency (NSA) gave a presentation
|
40 |
|
|
about Security-Enhanced Linux (SELinux) at the 2.5 Linux Kernel
|
41 |
|
|
Summit. SELinux is an implementation of flexible and fine-grained
|
42 |
|
|
nondiscretionary access controls in the Linux kernel, originally
|
43 |
|
|
implemented as its own particular kernel patch. Several other
|
44 |
|
|
security projects (e.g. RSBAC, Medusa) have also developed flexible
|
45 |
|
|
access control architectures for the Linux kernel, and various
|
46 |
|
|
projects have developed particular access control models for Linux
|
47 |
|
|
(e.g. LIDS, DTE, SubDomain). Each project has developed and
|
48 |
|
|
maintained its own kernel patch to support its security needs.
|
49 |
|
|
|
50 |
|
|
|
51 |
|
|
|
52 |
|
|
In response to the NSA presentation, Linus Torvalds made a set of
|
53 |
|
|
remarks that described a security framework he would be willing to
|
54 |
|
|
consider for inclusion in the mainstream Linux kernel. He described a
|
55 |
|
|
general framework that would provide a set of security hooks to
|
56 |
|
|
control operations on kernel objects and a set of opaque security
|
57 |
|
|
fields in kernel data structures for maintaining security attributes.
|
58 |
|
|
This framework could then be used by loadable kernel modules to
|
59 |
|
|
implement any desired model of security. Linus also suggested the
|
60 |
|
|
possibility of migrating the Linux capabilities code into such a
|
61 |
|
|
module.
|
62 |
|
|
|
63 |
|
|
|
64 |
|
|
|
65 |
|
|
The Linux Security Modules (LSM) project was started by WireX to
|
66 |
|
|
develop such a framework. LSM is a joint development effort by
|
67 |
|
|
several security projects, including Immunix, SELinux, SGI and Janus,
|
68 |
|
|
and several individuals, including Greg Kroah-Hartman and James
|
69 |
|
|
Morris, to develop a Linux kernel patch that implements this
|
70 |
|
|
framework. The patch is currently tracking the 2.4 series and is
|
71 |
|
|
targeted for integration into the 2.5 development series. This
|
72 |
|
|
technical report provides an overview of the framework and the example
|
73 |
|
|
capabilities security module provided by the LSM kernel patch.
|
74 |
|
|
|
75 |
|
|
|
76 |
|
|
|
77 |
|
|
|
78 |
|
|
LSM Framework
|
79 |
|
|
|
80 |
|
|
|
81 |
|
|
The LSM kernel patch provides a general kernel framework to support
|
82 |
|
|
security modules. In particular, the LSM framework is primarily
|
83 |
|
|
focused on supporting access control modules, although future
|
84 |
|
|
development is likely to address other security needs such as
|
85 |
|
|
auditing. By itself, the framework does not provide any additional
|
86 |
|
|
security; it merely provides the infrastructure to support security
|
87 |
|
|
modules. The LSM kernel patch also moves most of the capabilities
|
88 |
|
|
logic into an optional security module, with the system defaulting
|
89 |
|
|
to the traditional superuser logic. This capabilities module
|
90 |
|
|
is discussed further in .
|
91 |
|
|
|
92 |
|
|
|
93 |
|
|
|
94 |
|
|
The LSM kernel patch adds security fields to kernel data structures
|
95 |
|
|
and inserts calls to hook functions at critical points in the kernel
|
96 |
|
|
code to manage the security fields and to perform access control. It
|
97 |
|
|
also adds functions for registering and unregistering security
|
98 |
|
|
modules, and adds a general security system call
|
99 |
|
|
to support new system calls for security-aware applications.
|
100 |
|
|
|
101 |
|
|
|
102 |
|
|
|
103 |
|
|
The LSM security fields are simply void* pointers. For
|
104 |
|
|
process and program execution security information, security fields
|
105 |
|
|
were added to struct task_struct and
|
106 |
|
|
struct linux_binprm. For filesystem security
|
107 |
|
|
information, a security field was added to
|
108 |
|
|
struct super_block. For pipe, file, and socket
|
109 |
|
|
security information, security fields were added to
|
110 |
|
|
struct inode and
|
111 |
|
|
struct file. For packet and network device security
|
112 |
|
|
information, security fields were added to
|
113 |
|
|
struct sk_buff and
|
114 |
|
|
struct net_device. For System V IPC security
|
115 |
|
|
information, security fields were added to
|
116 |
|
|
struct kern_ipc_perm and
|
117 |
|
|
struct msg_msg; additionally, the definitions
|
118 |
|
|
for struct msg_msg, struct
|
119 |
|
|
msg_queue, and struct
|
120 |
|
|
shmid_kernel were moved to header files
|
121 |
|
|
(include/linux/msg.h and
|
122 |
|
|
include/linux/shm.h as appropriate) to allow
|
123 |
|
|
the security modules to use these definitions.
|
124 |
|
|
|
125 |
|
|
|
126 |
|
|
|
127 |
|
|
Each LSM hook is a function pointer in a global table,
|
128 |
|
|
security_ops. This table is a
|
129 |
|
|
security_operations structure as defined by
|
130 |
|
|
include/linux/security.h. Detailed documentation
|
131 |
|
|
for each hook is included in this header file. At present, this
|
132 |
|
|
structure consists of a collection of substructures that group related
|
133 |
|
|
hooks based on the kernel object (e.g. task, inode, file, sk_buff,
|
134 |
|
|
etc) as well as some top-level hook function pointers for system
|
135 |
|
|
operations. This structure is likely to be flattened in the future
|
136 |
|
|
for performance. The placement of the hook calls in the kernel code
|
137 |
|
|
is described by the "called:" lines in the per-hook documentation in
|
138 |
|
|
the header file. The hook calls can also be easily found in the
|
139 |
|
|
kernel code by looking for the string "security_ops->".
|
140 |
|
|
|
141 |
|
|
|
142 |
|
|
|
143 |
|
|
|
144 |
|
|
Linus mentioned per-process security hooks in his original remarks as a
|
145 |
|
|
possible alternative to global security hooks. However, if LSM were
|
146 |
|
|
to start from the perspective of per-process hooks, then the base
|
147 |
|
|
framework would have to deal with how to handle operations that
|
148 |
|
|
involve multiple processes (e.g. kill), since each process might have
|
149 |
|
|
its own hook for controlling the operation. This would require a
|
150 |
|
|
general mechanism for composing hooks in the base framework.
|
151 |
|
|
Additionally, LSM would still need global hooks for operations that
|
152 |
|
|
have no process context (e.g. network input operations).
|
153 |
|
|
Consequently, LSM provides global security hooks, but a security
|
154 |
|
|
module is free to implement per-process hooks (where that makes sense)
|
155 |
|
|
by storing a security_ops table in each process' security field and
|
156 |
|
|
then invoking these per-process hooks from the global hooks.
|
157 |
|
|
The problem of composition is thus deferred to the module.
|
158 |
|
|
|
159 |
|
|
|
160 |
|
|
|
161 |
|
|
The global security_ops table is initialized to a set of hook
|
162 |
|
|
functions provided by a dummy security module that provides
|
163 |
|
|
traditional superuser logic. A register_security
|
164 |
|
|
function (in security/security.c) is provided to
|
165 |
|
|
allow a security module to set security_ops to refer to its own hook
|
166 |
|
|
functions, and an unregister_security function is
|
167 |
|
|
provided to revert security_ops to the dummy module hooks. This
|
168 |
|
|
mechanism is used to set the primary security module, which is
|
169 |
|
|
responsible for making the final decision for each hook.
|
170 |
|
|
|
171 |
|
|
|
172 |
|
|
|
173 |
|
|
LSM also provides a simple mechanism for stacking additional security
|
174 |
|
|
modules with the primary security module. It defines
|
175 |
|
|
register_security and
|
176 |
|
|
unregister_security hooks in the
|
177 |
|
|
security_operations structure and provides
|
178 |
|
|
mod_reg_security and
|
179 |
|
|
mod_unreg_security functions that invoke these
|
180 |
|
|
hooks after performing some sanity checking. A security module can
|
181 |
|
|
call these functions in order to stack with other modules. However,
|
182 |
|
|
the actual details of how this stacking is handled are deferred to the
|
183 |
|
|
module, which can implement these hooks in any way it wishes
|
184 |
|
|
(including always returning an error if it does not wish to support
|
185 |
|
|
stacking). In this manner, LSM again defers the problem of
|
186 |
|
|
composition to the module.
|
187 |
|
|
|
188 |
|
|
|
189 |
|
|
|
190 |
|
|
Although the LSM hooks are organized into substructures based on
|
191 |
|
|
kernel object, all of the hooks can be viewed as falling into two
|
192 |
|
|
major categories: hooks that are used to manage the security fields
|
193 |
|
|
and hooks that are used to perform access control. Examples of the
|
194 |
|
|
first category of hooks include the
|
195 |
|
|
alloc_security and
|
196 |
|
|
free_security hooks defined for each kernel data
|
197 |
|
|
structure that has a security field. These hooks are used to allocate
|
198 |
|
|
and free security structures for kernel objects. The first category
|
199 |
|
|
of hooks also includes hooks that set information in the security
|
200 |
|
|
field after allocation, such as the post_lookup
|
201 |
|
|
hook in struct inode_security_ops. This hook
|
202 |
|
|
is used to set security information for inodes after successful lookup
|
203 |
|
|
operations. An example of the second category of hooks is the
|
204 |
|
|
permission hook in
|
205 |
|
|
struct inode_security_ops. This hook checks
|
206 |
|
|
permission when accessing an inode.
|
207 |
|
|
|
208 |
|
|
|
209 |
|
|
|
210 |
|
|
|
211 |
|
|
LSM Capabilities Module
|
212 |
|
|
|
213 |
|
|
|
214 |
|
|
The LSM kernel patch moves most of the existing POSIX.1e capabilities
|
215 |
|
|
logic into an optional security module stored in the file
|
216 |
|
|
security/capability.c. This change allows
|
217 |
|
|
users who do not want to use capabilities to omit this code entirely
|
218 |
|
|
from their kernel, instead using the dummy module for traditional
|
219 |
|
|
superuser logic or any other module that they desire. This change
|
220 |
|
|
also allows the developers of the capabilities logic to maintain and
|
221 |
|
|
enhance their code more freely, without needing to integrate patches
|
222 |
|
|
back into the base kernel.
|
223 |
|
|
|
224 |
|
|
|
225 |
|
|
|
226 |
|
|
In addition to moving the capabilities logic, the LSM kernel patch
|
227 |
|
|
could move the capability-related fields from the kernel data
|
228 |
|
|
structures into the new security fields managed by the security
|
229 |
|
|
modules. However, at present, the LSM kernel patch leaves the
|
230 |
|
|
capability fields in the kernel data structures. In his original
|
231 |
|
|
remarks, Linus suggested that this might be preferable so that other
|
232 |
|
|
security modules can be easily stacked with the capabilities module
|
233 |
|
|
without needing to chain multiple security structures on the security field.
|
234 |
|
|
It also avoids imposing extra overhead on the capabilities module
|
235 |
|
|
to manage the security fields. However, the LSM framework could
|
236 |
|
|
certainly support such a move if it is determined to be desirable,
|
237 |
|
|
with only a few additional changes described below.
|
238 |
|
|
|
239 |
|
|
|
240 |
|
|
|
241 |
|
|
At present, the capabilities logic for computing process capabilities
|
242 |
|
|
on execve and set*uid,
|
243 |
|
|
checking capabilities for a particular process, saving and checking
|
244 |
|
|
capabilities for netlink messages, and handling the
|
245 |
|
|
capget and capset system
|
246 |
|
|
calls have been moved into the capabilities module. There are still a
|
247 |
|
|
few locations in the base kernel where capability-related fields are
|
248 |
|
|
directly examined or modified, but the current version of the LSM
|
249 |
|
|
patch does allow a security module to completely replace the
|
250 |
|
|
assignment and testing of capabilities. These few locations would
|
251 |
|
|
need to be changed if the capability-related fields were moved into
|
252 |
|
|
the security field. The following is a list of known locations that
|
253 |
|
|
still perform such direct examination or modification of
|
254 |
|
|
capability-related fields:
|
255 |
|
|
|
256 |
|
|
fs/open.c:sys_access
|
257 |
|
|
fs/lockd/host.c:nlm_bind_host
|
258 |
|
|
fs/nfsd/auth.c:nfsd_setuser
|
259 |
|
|
fs/proc/array.c:task_cap
|
260 |
|
|
|
261 |
|
|
|
262 |
|
|
|
263 |
|
|
|
264 |
|
|
|
265 |
|
|
|