secint.xml revision 5eeb4e8f
1<?xml version="1.0" encoding="UTF-8" ?>
2<!DOCTYPE book PUBLIC "-//OASIS//DTD DocBook XML V4.3//EN"
3                   "http://www.oasis-open.org/docbook/xml/4.3/docbookx.dtd"
4[
5<!ENTITY % defs SYSTEM "defs.ent"> %defs;
6]>
7
8
9<!--translated from secint.tex, on 2010-06-27 15:38:00,
10by TeX4ht (http://www.cse.ohio-state.edu/~gurari/TeX4ht/)
11xhtml,docbook,html,refcaption -->
12
13<book id="secint">
14
15<bookinfo>
16   <title>Security Extension Server Design Draft</title>
17   <subtitle>X Consortium Standard</subtitle>
18   <authorgroup>
19      <author>
20         <firstname>David</firstname><othername>P.</othername><surname>Wiggins</surname>
21         <affiliation><orgname>X Consortium</orgname></affiliation>
22      </author>
23   </authorgroup>
24   <releaseinfo>X Version 11, Release &fullrelvers;</releaseinfo>
25   <releaseinfo>Version 3.0</releaseinfo>
26   <copyright><year>1996</year><holder>X Consortium</holder></copyright>
27
28<legalnotice>
29<para>
30Permission is hereby granted, free of charge, to any person obtaining
31a copy of this software and associated documentation files (the
32"Software"), to deal in the Software without restriction, including
33without limitation the rights to use, copy, modify, merge, publish,
34distribute, sublicense, and/or sell copies of the Software, and to
35permit persons to whom the Software is furnished to do so, subject to
36the following conditions:
37</para>
38<para>
39The above copyright notice and this permission notice shall be included
40in all copies or substantial portions of the Software.
41</para>
42<para>
43THE SOFTWARE IS PROVIDED &ldquo;AS IS&rdquo;, WITHOUT WARRANTY OF ANY KIND, EXPRESS
44OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
45MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
46IN NO EVENT SHALL THE X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR
47OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
48ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
49OTHER DEALINGS IN THE SOFTWARE.
50</para>
51<para>
52Except as contained in this notice, the name of the X Consortium shall
53not be used in advertising or otherwise to promote the sale, use or
54other dealings in this Software without prior written authorization
55from the X Consortium.
56</para>
57<para>X Window System is a trademark of The Open Group.</para>
58</legalnotice>
59<pubdate>June 27, 2010</pubdate>
60
61<abstract>
62<para>This paper describes the implementation strategy used to implement
63     various pieces of the SECURITY Extension.
64</para>
65</abstract>
66
67</bookinfo>
68
69
70<chapter id='Generate_Authorization_Request'>
71<title>Generate Authorization Request</title>
72
73<para>
74The major steps taken to execute this request are as follows.
75</para>
76
77<para>
78Sanity check arguments. The interesting one is the group, which must be
79checked by some other module(s), initially just the embedding extension.
80Use a new callback for this. The callback functions will be passed a small
81structure containing the group ID and a Boolean value which is initially
82false. If any of the callbacks recognize the ID, they should set the boolean
83to true. If after the callbacks have been called the boolean is false, return
84an error, since nobody recognized it.
85</para>
86
87<para>
88Use the existing Xkey library function XkeyGenerateAuthorization to generate
89the new authorization.
90</para>
91
92<para>
93Use the existing os layer function AddAuthorization to add the new
94authorization to the server's internal database.
95</para>
96
97<para>
98Use the existing os layer function AuthorizationToID to retrieve
99the authorization ID that the os layer assigned to the new authorization.
100</para>
101
102<para>Change the os layer to use authorization IDs allocated from the
103server's ID range via FakeClientID(0) instead of using a simple incrementing
104integer. This lets us use the resource database to attach additional
105information to an authorization without needing any changes to os
106data structures.
107</para>
108
109<para>
110Add the authorization ID as a server resource. The structure for an
111authorization resource will contain the timeout, trust-level, and group
112sent in the request, a reference count of how many clients are connected
113with this authorization, a timer pointer, and time-remaining counter.
114</para>
115
116<para>
117Return the authorization ID and generated auth data to the client.
118</para>
119
120</chapter>
121<chapter id='Client_Connection'>
122<title>Client Connection</title>
123
124<para>
125The Security extension needs to be aware of new client connections
126primarily so that it copy the trust-level of the authorization that was
127used to the client structure.  The trust-level is needed in the client
128structure because it will be accessed frequently to make access control
129decisions for the client. We will use the existing ClientStateCallback
130to catch new client connections.
131</para>
132
133<para>
134We also need to copy the authorization ID into the client structure. The
135authorization ID is already stored in an os private hung from the client,
136and we will add a new os function AuthorizationIDOfClient to retrieve it.
137However, when a client disconnects, this os private is already gone before
138ClientStateCallbacks are called. We need the authorization ID at client
139disconnect time for reasons described below.
140</para>
141
142<para>
143Now that we know what needs to be done and why, let's walk through the
144sequence of events.
145</para>
146
147<para>
148When a new client connects, get the authorization ID with
149AuthorizationIDOfClient, store it in the client, then pass that ID to
150LookupIDByType to find the authorization. If we get a non-NULL pointer
151back, this is a generated authorization, not one of the predefined ones in
152the server's authority file. In this case, increment the authorization's
153reference count. If the reference count is now 1, cancel the timer
154for this authorization using the trivial new os layer function TimerCancel.
155Lastly, copy the trust-level of this authorization into the client structure
156so that it can be reached quickly for future access control decisions.
157</para>
158
159<para>
160The embedding extension can determine the group to use for a new client in
161the same way that we determined the trust level: get the authorization ID,
162look it up, and if that succeeds, pluck the group out of the returned
163authorization structure.
164</para>
165</chapter>
166
167<chapter id='Client_disconnection'>
168<title>Client disconnection</title>
169
170<para>
171Use the existing ClientStateCallback to catch client disconnections. If the
172client was using a generated authorization, decrement its reference count.
173If the reference count is now zero, use the existing os layer function
174TimerSet to start a timer to count down the timeout period for this
175authorization. Record the timer ID for this authorization. When the timer
176fires, the authorization should be freed, removing all
177traces of it from the server.
178</para>
179
180<para>
181There is a slight complication regarding the timeout because the timer
182interface in the server allows for 32 bits worth of milliseconds, while
183the timeout specified in GenerateAuthorization has 32 bits worth of seconds.
184To handle this, if the specified time is more than the timer interface can
185handle, the maximum possible timeout will be set, and time-remaining counter
186for this authorization will be used to track the leftover part. When the
187timer fires, it should first check to see if there is any leftover
188time to wait. If there is, it should set another timer to the minimum of (the
189maximum possible timeout) and the time remaining, and not do the revocation
190yet.
191</para>
192</chapter>
193
194<chapter id='Resource_ID_Security'>
195<title>Resource ID Security</title>
196
197<para>
198To implement the restriction that untrusted clients cannot access resources
199of trusted clients, we add two new functions to dix: SecurityLookupIDByType
200and SecurityLookupIDByClass. Hereafter we will use SecurityLookupID to refer
201to both functions. In addition to the parameters of the existing LookupID
202functions, these functions also take a pointer to the client doing the lookup,
203and an access mode that conveys a high-level idea of what the client intends
204to do with the resource (currently just read, write, destroy, and unknown).
205Passing NullClient for the client turns off access checks. SecurityLookupID can
206return NULL for two reasons: the resource doesn't exist, or it does but the
207client isn't allowed to access it. The caller cannot tell the difference. Most
208places in dix call these new lookup functions instead of the old LookupID,
209which continue to do no access checking. Extension "Proc" functions should
210probably use SecurityLookupID, not LookupID. Ddxen can continue to use
211LookupID.
212</para>
213
214<para>
215Inside SecurityLookupID, the function client -&gt; CheckAccess is called
216passing the client, resource id, resource type/class, resource value, and
217access mode. CheckAccess returns the resource value if access is allowed,
218else it returns NULL. The entire resource ID security policy of the Security
219extension can be replaced by plugging in your own access decision function
220here. This in combination with the access mode parameter should be enough to
221implement a more traditional DAC (discretionary access control) policy.
222</para>
223
224<para>
225Since we need client and access mode information to do access controlled
226resource lookups, we add (and use) several other macros and functions that
227parallel existing ones with the addition of the missing information. The list
228includes SECURITY_VERIFY_GC, SECURITY_VERIFY_DRAWABLE,
229SECURITY_VERIFY_GEOMETRABLE, SecurityLookupWindow,
230SecurityLookupDrawable, and dixChangeGC. The dixChangeGC interface is
231worth mentioning because in addition to a client parameter, we introduce a
232pointer-to-union parameter that should let us eliminate the warnings that some
233compilers give when you assign small integers to pointers, as the DoChangeGC
234interface required. For more details, see the comment preceding dixChangeGC in
235;&lt;dix/gc.c;&gt;.
236</para>
237
238<para>
239If XCSECURITY is not defined (the Security extension is not being built),
240the server uses essentially the same code as before for resource lookups.
241</para>
242
243</chapter>
244<chapter id='Extension_Security'>
245<title>Extension Security</title>
246
247<para>
248A new field in the ExtensionEntry structure, Bool secure, tells whether the
249extension is considered secure. It is initialized to FALSE by AddExtension.
250The following new dix function can be used to set the secure field:
251</para>
252
253<funcsynopsis id='DeclareExtensionSecurity'>
254<funcprototype>
255  <funcdef>void <function>DeclareExtensionSecurity</function></funcdef>
256    <paramdef>char <parameter> *extname</parameter></paramdef>
257    <paramdef>Bool <parameter>secure</parameter></paramdef>
258</funcprototype>
259</funcsynopsis>
260
261<para>
262The name of the extension and the desired value of the secure field are
263passed. If an extension is secure, a call to this function with
264secure = TRUE will typically appear right after the call to
265<function>AddExtension</function>.
266<xref linkend='DeclareExtensionSecurity' xrefstyle='select: title'/>
267should be called during server reset. It should not
268be called after the first client has connected. Passing the name of an
269extension that has not been initialized has no effect (the secure value will
270not be remembered in case the extension is later initialized).
271</para>
272
273<para>
274For untrusted clients, <function>ProcListExtensions</function> omits
275extensions that have secure = FALSE, and
276<function>ProcQueryExtension</function> reports that such
277extensions don't exist.
278</para>
279
280<para>
281To prevent untrusted clients from using extensions by guessing their major
282opcode, one of two new Proc vectors are used by untrusted clients,
283<function>UntrusedProcVector</function> and
284<function>SwappedUntrustedProcVector</function>. These have the same contents
285as <function>ProcVector</function> and
286<function>SwappedProcVector</function> respectively for the first 128
287entries. Entries 128 through 255 are initialized to ProcBadRequest. If
288<xref linkend='DeclareExtensionSecurity' xrefstyle='select: title'/> is called with secure =
289TRUE, that extension's dispatch function is plugged into the appropriate entry
290so that the extension can be used. If
291<xref linkend='DeclareExtensionSecurity' xrefstyle='select: title'/> is called with secure =
292FALSE, the appropriate entry is reset to ProcBadRequest.
293</para>
294
295<para>
296Now we can explain why <xref linkend='DeclareExtensionSecurity' xrefstyle='select: title'/>
297should not be called after the first client connects. In some cases,
298the Record extension gives clients a private copy of the proc vector,
299which it then changes to intercept certain requests. Changing entries in
300<function>UntrusedProcVector</function> and
301<function>SwappedUntrustedProcVector</function> will have no effect on these
302copied proc vectors. If we get to the point of needing an extension request
303to control which extensions are secure, we'll need to invent a way to
304get those copied proc vectors changed.
305</para>
306</chapter>
307</book>
308
309
310