xref: /reactos/dll/win32/aclui/aclui.c (revision 43d6fdf2)
1c2c66affSColin Finck /*
2c2c66affSColin Finck  * ReactOS Access Control List Editor
3c2c66affSColin Finck  * Copyright (C) 2004-2005 ReactOS Team
4c2c66affSColin Finck  *
5c2c66affSColin Finck  * This library is free software; you can redistribute it and/or
6c2c66affSColin Finck  * modify it under the terms of the GNU Lesser General Public
7c2c66affSColin Finck  * License as published by the Free Software Foundation; either
8c2c66affSColin Finck  * version 2.1 of the License, or (at your option) any later version.
9c2c66affSColin Finck  *
10c2c66affSColin Finck  * This library is distributed in the hope that it will be useful,
11c2c66affSColin Finck  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12c2c66affSColin Finck  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13c2c66affSColin Finck  * Lesser General Public License for more details.
14c2c66affSColin Finck  *
15c2c66affSColin Finck  * You should have received a copy of the GNU Lesser General Public
16c2c66affSColin Finck  * License along with this library; if not, write to the Free Software
17c2c66affSColin Finck  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
18c2c66affSColin Finck  */
19c2c66affSColin Finck /*
20c2c66affSColin Finck  * PROJECT:         ReactOS Access Control List Editor
21c2c66affSColin Finck  * FILE:            lib/aclui/aclui.c
22c2c66affSColin Finck  * PURPOSE:         Access Control List Editor
23c2c66affSColin Finck  * PROGRAMMER:      Thomas Weidenmueller <w3seek@reactos.com>
24c2c66affSColin Finck  *
25c2c66affSColin Finck  * UPDATE HISTORY:
26c2c66affSColin Finck  *      08/10/2004  Created
27c2c66affSColin Finck  */
28c2c66affSColin Finck 
29c2c66affSColin Finck #include "precomp.h"
30c2c66affSColin Finck 
31c2c66affSColin Finck #include <sddl.h>
32c2c66affSColin Finck 
33c2c66affSColin Finck #define NDEBUG
34c2c66affSColin Finck #include <debug.h>
35c2c66affSColin Finck 
36c2c66affSColin Finck #include "resource.h"
37c2c66affSColin Finck 
38c2c66affSColin Finck HINSTANCE hDllInstance;
39c2c66affSColin Finck 
40c2c66affSColin Finck #define SIDN_LOOKUPSUCCEEDED    (0x101)
41c2c66affSColin Finck typedef struct _SIDLOOKUPNOTIFYINFO
42c2c66affSColin Finck {
43c2c66affSColin Finck     NMHDR nmh;
44c2c66affSColin Finck     PSID Sid;
45c2c66affSColin Finck     PSIDREQRESULT SidRequestResult;
46c2c66affSColin Finck } SIDLOOKUPNOTIFYINFO, *PSIDLOOKUPNOTIFYINFO;
47c2c66affSColin Finck 
48c2c66affSColin Finck static PSID
AceHeaderToSID(IN PACE_HEADER AceHeader)49c2c66affSColin Finck AceHeaderToSID(IN PACE_HEADER AceHeader)
50c2c66affSColin Finck {
51c2c66affSColin Finck     PSID Sid = NULL;
52c2c66affSColin Finck     switch (AceHeader->AceType)
53c2c66affSColin Finck     {
54c2c66affSColin Finck         case ACCESS_ALLOWED_ACE_TYPE:
55c2c66affSColin Finck             Sid = (PSID)&((PACCESS_ALLOWED_ACE)AceHeader)->SidStart;
56c2c66affSColin Finck             break;
57c2c66affSColin Finck #if 0
58c2c66affSColin Finck         case ACCESS_ALLOWED_CALLBACK_ACE_TYPE:
59c2c66affSColin Finck             Sid = (PSID)&((PACCESS_ALLOWED_CALLBACK_ACE)AceHeader)->SidStart;
60c2c66affSColin Finck             break;
61c2c66affSColin Finck         case ACCESS_ALLOWED_CALLBACK_OBJECT_ACE_TYPE:
62c2c66affSColin Finck             Sid = (PSID)&((PACCESS_ALLOWED_CALLBACK_OBJECT_ACE)AceHeader)->SidStart;
63c2c66affSColin Finck             break;
64c2c66affSColin Finck #endif
65c2c66affSColin Finck         case ACCESS_ALLOWED_OBJECT_ACE_TYPE:
66c2c66affSColin Finck             Sid = (PSID)&((PACCESS_ALLOWED_OBJECT_ACE)AceHeader)->SidStart;
67c2c66affSColin Finck             break;
68c2c66affSColin Finck         case ACCESS_DENIED_ACE_TYPE:
69c2c66affSColin Finck             Sid = (PSID)&((PACCESS_DENIED_ACE)AceHeader)->SidStart;
70c2c66affSColin Finck             break;
71c2c66affSColin Finck #if 0
72c2c66affSColin Finck         case ACCESS_DENIED_CALLBACK_ACE_TYPE:
73c2c66affSColin Finck             Sid = (PSID)&((PACCESS_DENIED_CALLBACK_ACE)AceHeader)->SidStart;
74c2c66affSColin Finck             break;
75c2c66affSColin Finck         case ACCESS_DENIED_CALLBACK_OBJECT_ACE_TYPE:
76c2c66affSColin Finck             Sid = (PSID)&((PACCESS_DENIED_CALLBACK_OBJECT_ACE)AceHeader)->SidStart;
77c2c66affSColin Finck             break;
78c2c66affSColin Finck #endif
79c2c66affSColin Finck         case SYSTEM_AUDIT_OBJECT_ACE_TYPE:
80c2c66affSColin Finck             Sid = (PSID)&((PACCESS_DENIED_OBJECT_ACE)AceHeader)->SidStart;
81c2c66affSColin Finck             break;
82c2c66affSColin Finck     }
83c2c66affSColin Finck 
84c2c66affSColin Finck     return Sid;
85c2c66affSColin Finck }
86c2c66affSColin Finck 
87c2c66affSColin Finck static VOID
DestroySecurityPage(IN PSECURITY_PAGE sp)88c2c66affSColin Finck DestroySecurityPage(IN PSECURITY_PAGE sp)
89c2c66affSColin Finck {
90c2c66affSColin Finck     DestroySidCacheMgr(sp->SidCacheMgr);
91c2c66affSColin Finck 
92c2c66affSColin Finck     if (sp->OwnerSid != NULL)
93c2c66affSColin Finck         LocalFree((HLOCAL)sp->OwnerSid);
94c2c66affSColin Finck 
95c2c66affSColin Finck     HeapFree(GetProcessHeap(),
96c2c66affSColin Finck              0,
97c2c66affSColin Finck              sp);
98c2c66affSColin Finck 
99c2c66affSColin Finck     CoUninitialize();
100c2c66affSColin Finck }
101c2c66affSColin Finck 
102c2c66affSColin Finck static VOID
FreePrincipalsList(IN PSECURITY_PAGE sp,IN PPRINCIPAL_LISTITEM * PrincipalsListHead)103c2c66affSColin Finck FreePrincipalsList(IN PSECURITY_PAGE sp,
104c2c66affSColin Finck                    IN PPRINCIPAL_LISTITEM *PrincipalsListHead)
105c2c66affSColin Finck {
106c2c66affSColin Finck     PPRINCIPAL_LISTITEM CurItem, NextItem;
107c2c66affSColin Finck     PACE_ENTRY AceEntry, NextAceEntry;
108c2c66affSColin Finck 
109c2c66affSColin Finck     CurItem = *PrincipalsListHead;
110c2c66affSColin Finck     while (CurItem != NULL)
111c2c66affSColin Finck     {
112c2c66affSColin Finck         /* Free all ACEs */
113c2c66affSColin Finck         AceEntry = CurItem->ACEs;
114c2c66affSColin Finck         while (AceEntry != NULL)
115c2c66affSColin Finck         {
116c2c66affSColin Finck             NextAceEntry = AceEntry->Next;
117c2c66affSColin Finck             HeapFree(GetProcessHeap(),
118c2c66affSColin Finck                      0,
119c2c66affSColin Finck                      AceEntry);
120c2c66affSColin Finck             AceEntry = NextAceEntry;
121c2c66affSColin Finck         }
122c2c66affSColin Finck 
123c2c66affSColin Finck         /* free the SID string if present */
124c2c66affSColin Finck         if (CurItem->SidReqResult != NULL)
125c2c66affSColin Finck         {
126c2c66affSColin Finck             DereferenceSidReqResult(sp->SidCacheMgr,
127c2c66affSColin Finck                                     CurItem->SidReqResult);
128c2c66affSColin Finck         }
129c2c66affSColin Finck 
130c2c66affSColin Finck         if (CurItem->DisplayString != NULL)
131c2c66affSColin Finck         {
132c2c66affSColin Finck             LocalFree((HLOCAL)CurItem->DisplayString);
133c2c66affSColin Finck         }
134c2c66affSColin Finck 
135c2c66affSColin Finck         /* free the ACE list item */
136c2c66affSColin Finck         NextItem = CurItem->Next;
137c2c66affSColin Finck         HeapFree(GetProcessHeap(),
138c2c66affSColin Finck                  0,
139c2c66affSColin Finck                  CurItem);
140c2c66affSColin Finck         CurItem = NextItem;
141c2c66affSColin Finck     }
142c2c66affSColin Finck 
143c2c66affSColin Finck     *PrincipalsListHead = NULL;
144c2c66affSColin Finck }
145c2c66affSColin Finck 
146c2c66affSColin Finck static PACE_ENTRY
AddAceToPrincipal(IN PPRINCIPAL_LISTITEM Principal,IN PACE_HEADER AceHeader)147c2c66affSColin Finck AddAceToPrincipal(IN PPRINCIPAL_LISTITEM Principal,
148c2c66affSColin Finck                   IN PACE_HEADER AceHeader)
149c2c66affSColin Finck {
150c2c66affSColin Finck     PACE_ENTRY AceEntry, *AceLink;
151c2c66affSColin Finck 
152c2c66affSColin Finck     AceEntry = HeapAlloc(GetProcessHeap(),
153c2c66affSColin Finck                          0,
154c2c66affSColin Finck                          sizeof(ACE_ENTRY) + AceHeader->AceSize);
155c2c66affSColin Finck     if (AceEntry != NULL)
156c2c66affSColin Finck     {
157c2c66affSColin Finck         AceEntry->Next = NULL;
158c2c66affSColin Finck 
159c2c66affSColin Finck         /* copy the ACE */
160c2c66affSColin Finck         CopyMemory(AceEntry + 1,
161c2c66affSColin Finck                    AceHeader,
162c2c66affSColin Finck                    AceHeader->AceSize);
163c2c66affSColin Finck 
164c2c66affSColin Finck         /* append it to the list */
165c2c66affSColin Finck         AceLink = &Principal->ACEs;
166c2c66affSColin Finck         while (*AceLink != NULL)
167c2c66affSColin Finck         {
168c2c66affSColin Finck             AceLink = &(*AceLink)->Next;
169c2c66affSColin Finck         }
170c2c66affSColin Finck         *AceLink = AceEntry;
171c2c66affSColin Finck     }
172c2c66affSColin Finck 
173c2c66affSColin Finck     return AceEntry;
174c2c66affSColin Finck }
175c2c66affSColin Finck 
176c2c66affSColin Finck static PPRINCIPAL_LISTITEM
FindSidInPrincipalsListAddAce(IN PPRINCIPAL_LISTITEM PrincipalsListHead,IN PSID Sid,IN PACE_HEADER AceHeader)177c2c66affSColin Finck FindSidInPrincipalsListAddAce(IN PPRINCIPAL_LISTITEM PrincipalsListHead,
178c2c66affSColin Finck                               IN PSID Sid,
179c2c66affSColin Finck                               IN PACE_HEADER AceHeader)
180c2c66affSColin Finck {
181c2c66affSColin Finck     PPRINCIPAL_LISTITEM CurItem;
182c2c66affSColin Finck 
183c2c66affSColin Finck     for (CurItem = PrincipalsListHead;
184c2c66affSColin Finck          CurItem != NULL;
185c2c66affSColin Finck          CurItem = CurItem->Next)
186c2c66affSColin Finck     {
187c2c66affSColin Finck         if (EqualSid((PSID)(CurItem + 1),
188c2c66affSColin Finck                      Sid))
189c2c66affSColin Finck         {
190c2c66affSColin Finck             if (AddAceToPrincipal(CurItem,
191c2c66affSColin Finck                                   AceHeader) != NULL)
192c2c66affSColin Finck             {
193c2c66affSColin Finck                 return CurItem;
194c2c66affSColin Finck             }
195c2c66affSColin Finck 
196c2c66affSColin Finck             /* unable to add the ACE to the principal */
197c2c66affSColin Finck             break;
198c2c66affSColin Finck         }
199c2c66affSColin Finck     }
200c2c66affSColin Finck 
201c2c66affSColin Finck     return NULL;
202c2c66affSColin Finck }
203c2c66affSColin Finck 
204c2c66affSColin Finck static VOID
SidLookupCompletion(IN HANDLE SidCacheMgr,IN PSID Sid,IN PSIDREQRESULT SidRequestResult,IN PVOID Context)205c2c66affSColin Finck SidLookupCompletion(IN HANDLE SidCacheMgr,
206c2c66affSColin Finck                     IN PSID Sid,
207c2c66affSColin Finck                     IN PSIDREQRESULT SidRequestResult,
208c2c66affSColin Finck                     IN PVOID Context)
209c2c66affSColin Finck {
210c2c66affSColin Finck     PSECURITY_PAGE sp = (PSECURITY_PAGE)Context;
211c2c66affSColin Finck 
212c2c66affSColin Finck     /* NOTE: this routine may be executed in a different thread
213c2c66affSColin Finck              than the GUI! */
214c2c66affSColin Finck 
215c2c66affSColin Finck     if (SidRequestResult != NULL)
216c2c66affSColin Finck     {
217c2c66affSColin Finck         SIDLOOKUPNOTIFYINFO LookupInfo;
218c2c66affSColin Finck 
219c2c66affSColin Finck         LookupInfo.nmh.hwndFrom = sp->hWnd;
220c2c66affSColin Finck         LookupInfo.nmh.idFrom = 0;
221c2c66affSColin Finck         LookupInfo.nmh.code = SIDN_LOOKUPSUCCEEDED;
222c2c66affSColin Finck         LookupInfo.Sid = Sid;
223c2c66affSColin Finck         LookupInfo.SidRequestResult = SidRequestResult;
224c2c66affSColin Finck 
225c2c66affSColin Finck         /* notify the page that the sid lookup succeeded */
226c2c66affSColin Finck         SendMessage(sp->hWnd,
227c2c66affSColin Finck                     WM_NOTIFY,
228c2c66affSColin Finck                     (WPARAM)LookupInfo.nmh.idFrom,
229c2c66affSColin Finck                     (LPARAM)&LookupInfo.nmh);
230c2c66affSColin Finck     }
231c2c66affSColin Finck }
232c2c66affSColin Finck 
233c2c66affSColin Finck static PPRINCIPAL_LISTITEM
AddPrincipalToList(IN PSECURITY_PAGE sp,IN PSID Sid,IN PACE_HEADER AceHeader,OUT BOOL * LookupDeferred OPTIONAL)234c2c66affSColin Finck AddPrincipalToList(IN PSECURITY_PAGE sp,
235c2c66affSColin Finck                    IN PSID Sid,
236c2c66affSColin Finck                    IN PACE_HEADER AceHeader,
237c2c66affSColin Finck                    OUT BOOL *LookupDeferred  OPTIONAL)
238c2c66affSColin Finck {
239c2c66affSColin Finck     PPRINCIPAL_LISTITEM PrincipalListItem = NULL, *PrincipalLink;
240c2c66affSColin Finck     PACE_ENTRY AceEntry;
241c2c66affSColin Finck     BOOL Deferred = FALSE;
242c2c66affSColin Finck 
243c2c66affSColin Finck     if (!FindSidInPrincipalsListAddAce(sp->PrincipalsListHead,
244c2c66affSColin Finck                                        Sid,
245c2c66affSColin Finck                                        AceHeader))
246c2c66affSColin Finck     {
247c2c66affSColin Finck         DWORD SidLength;
248c2c66affSColin Finck 
249c2c66affSColin Finck         PrincipalLink = &sp->PrincipalsListHead;
250c2c66affSColin Finck         while (*PrincipalLink != NULL)
251c2c66affSColin Finck         {
252c2c66affSColin Finck             PrincipalLink = &(*PrincipalLink)->Next;
253c2c66affSColin Finck         }
254c2c66affSColin Finck 
255c2c66affSColin Finck         SidLength = GetLengthSid(Sid);
256c2c66affSColin Finck 
257c2c66affSColin Finck         /* allocate the principal */
258c2c66affSColin Finck         PrincipalListItem = HeapAlloc(GetProcessHeap(),
259c2c66affSColin Finck                                       0,
260c2c66affSColin Finck                                       sizeof(PRINCIPAL_LISTITEM) + SidLength);
261c2c66affSColin Finck         if (PrincipalListItem != NULL)
262c2c66affSColin Finck         {
263c2c66affSColin Finck             PrincipalListItem->DisplayString = NULL;
264c2c66affSColin Finck             PrincipalListItem->SidReqResult = NULL;
265c2c66affSColin Finck 
266c2c66affSColin Finck             CopySid(SidLength,
267c2c66affSColin Finck                     (PSID)(PrincipalListItem + 1),
268c2c66affSColin Finck                     Sid);
269c2c66affSColin Finck 
270c2c66affSColin Finck             /* allocate some memory for the ACE and copy it */
271c2c66affSColin Finck             AceEntry = HeapAlloc(GetProcessHeap(),
272c2c66affSColin Finck                                  0,
273c2c66affSColin Finck                                  sizeof(ACE_ENTRY) + AceHeader->AceSize);
274c2c66affSColin Finck             if (AceEntry != NULL)
275c2c66affSColin Finck             {
276c2c66affSColin Finck                 AceEntry->Next = NULL;
277c2c66affSColin Finck                 CopyMemory(AceEntry + 1,
278c2c66affSColin Finck                            AceHeader,
279c2c66affSColin Finck                            AceHeader->AceSize);
280c2c66affSColin Finck 
281c2c66affSColin Finck                 /* add the ACE to the list */
282c2c66affSColin Finck                 PrincipalListItem->ACEs = AceEntry;
283c2c66affSColin Finck 
284c2c66affSColin Finck                 PrincipalListItem->Next = NULL;
285c2c66affSColin Finck 
286c2c66affSColin Finck                 /* append item to the principals list */
287c2c66affSColin Finck                 *PrincipalLink = PrincipalListItem;
288c2c66affSColin Finck 
289c2c66affSColin Finck                 /* lookup the SID now */
290c2c66affSColin Finck                 Deferred = !LookupSidCache(sp->SidCacheMgr,
291c2c66affSColin Finck                                            Sid,
292c2c66affSColin Finck                                            SidLookupCompletion,
293c2c66affSColin Finck                                            sp);
294c2c66affSColin Finck             }
295c2c66affSColin Finck             else
296c2c66affSColin Finck             {
297c2c66affSColin Finck                 HeapFree(GetProcessHeap(),
298c2c66affSColin Finck                          0,
299c2c66affSColin Finck                          PrincipalListItem);
300c2c66affSColin Finck                 PrincipalListItem = NULL;
301c2c66affSColin Finck             }
302c2c66affSColin Finck         }
303c2c66affSColin Finck     }
304c2c66affSColin Finck 
305c2c66affSColin Finck     if (PrincipalListItem != NULL && LookupDeferred != NULL)
306c2c66affSColin Finck     {
307c2c66affSColin Finck         *LookupDeferred = Deferred;
308c2c66affSColin Finck     }
309c2c66affSColin Finck 
310c2c66affSColin Finck     return PrincipalListItem;
311c2c66affSColin Finck }
312c2c66affSColin Finck 
313c2c66affSColin Finck static LPWSTR
GetDisplayStringFromSidRequestResult(IN PSIDREQRESULT SidReqResult)314c2c66affSColin Finck GetDisplayStringFromSidRequestResult(IN PSIDREQRESULT SidReqResult)
315c2c66affSColin Finck {
316c2c66affSColin Finck     LPWSTR lpDisplayString = NULL;
317c2c66affSColin Finck 
318c2c66affSColin Finck     if (SidReqResult->SidNameUse == SidTypeUser ||
319c2c66affSColin Finck         SidReqResult->SidNameUse == SidTypeGroup)
320c2c66affSColin Finck     {
321c2c66affSColin Finck         LoadAndFormatString(hDllInstance,
322c2c66affSColin Finck                             IDS_USERDOMAINFORMAT,
323c2c66affSColin Finck                             &lpDisplayString,
324c2c66affSColin Finck                             SidReqResult->AccountName,
325c2c66affSColin Finck                             SidReqResult->DomainName,
326c2c66affSColin Finck                             SidReqResult->AccountName);
327c2c66affSColin Finck     }
328c2c66affSColin Finck     else
329c2c66affSColin Finck     {
330c2c66affSColin Finck         LoadAndFormatString(hDllInstance,
331c2c66affSColin Finck                             IDS_USERFORMAT,
332c2c66affSColin Finck                             &lpDisplayString,
333c2c66affSColin Finck                             SidReqResult->AccountName);
334c2c66affSColin Finck     }
335c2c66affSColin Finck 
336c2c66affSColin Finck     return lpDisplayString;
337c2c66affSColin Finck }
338c2c66affSColin Finck 
339c2c66affSColin Finck static LPWSTR
GetPrincipalDisplayString(IN PPRINCIPAL_LISTITEM PrincipalListItem)340c2c66affSColin Finck GetPrincipalDisplayString(IN PPRINCIPAL_LISTITEM PrincipalListItem)
341c2c66affSColin Finck {
342c2c66affSColin Finck     LPWSTR lpDisplayString = NULL;
343c2c66affSColin Finck 
344c2c66affSColin Finck     if (PrincipalListItem->SidReqResult != NULL)
345c2c66affSColin Finck     {
346c2c66affSColin Finck         lpDisplayString = GetDisplayStringFromSidRequestResult(PrincipalListItem->SidReqResult);
347c2c66affSColin Finck     }
348c2c66affSColin Finck     else
349c2c66affSColin Finck     {
350c2c66affSColin Finck         ConvertSidToStringSidW((PSID)(PrincipalListItem + 1),
351c2c66affSColin Finck                                &lpDisplayString);
352c2c66affSColin Finck     }
353c2c66affSColin Finck 
354c2c66affSColin Finck     return lpDisplayString;
355c2c66affSColin Finck }
356c2c66affSColin Finck 
357c2c66affSColin Finck static LPWSTR
GetPrincipalAccountNameString(IN PPRINCIPAL_LISTITEM PrincipalListItem)358c2c66affSColin Finck GetPrincipalAccountNameString(IN PPRINCIPAL_LISTITEM PrincipalListItem)
359c2c66affSColin Finck {
360c2c66affSColin Finck     LPWSTR lpDisplayString = NULL;
361c2c66affSColin Finck 
362c2c66affSColin Finck     if (PrincipalListItem->SidReqResult != NULL)
363c2c66affSColin Finck     {
364c2c66affSColin Finck         LoadAndFormatString(hDllInstance,
365c2c66affSColin Finck                             IDS_USERFORMAT,
366c2c66affSColin Finck                             &lpDisplayString,
367c2c66affSColin Finck                             PrincipalListItem->SidReqResult->AccountName);
368c2c66affSColin Finck     }
369c2c66affSColin Finck     else
370c2c66affSColin Finck     {
371c2c66affSColin Finck         ConvertSidToStringSid((PSID)(PrincipalListItem + 1),
372c2c66affSColin Finck                               &lpDisplayString);
373c2c66affSColin Finck     }
374c2c66affSColin Finck 
375c2c66affSColin Finck     return lpDisplayString;
376c2c66affSColin Finck }
377c2c66affSColin Finck 
378c2c66affSColin Finck static VOID
CreatePrincipalListItem(OUT LVITEM * li,IN PSECURITY_PAGE sp,IN PPRINCIPAL_LISTITEM PrincipalListItem,IN INT Index,IN BOOL Selected)379c2c66affSColin Finck CreatePrincipalListItem(OUT LVITEM *li,
380c2c66affSColin Finck                         IN PSECURITY_PAGE sp,
381c2c66affSColin Finck                         IN PPRINCIPAL_LISTITEM PrincipalListItem,
382c2c66affSColin Finck                         IN INT Index,
383c2c66affSColin Finck                         IN BOOL Selected)
384c2c66affSColin Finck {
385c2c66affSColin Finck     INT ImageIndex = 2;
386c2c66affSColin Finck 
387c2c66affSColin Finck     if (PrincipalListItem->SidReqResult != NULL)
388c2c66affSColin Finck     {
389c2c66affSColin Finck         switch (PrincipalListItem->SidReqResult->SidNameUse)
390c2c66affSColin Finck         {
391c2c66affSColin Finck             case SidTypeUser:
392c2c66affSColin Finck                 ImageIndex = 0;
393c2c66affSColin Finck                 break;
394c2c66affSColin Finck             case SidTypeWellKnownGroup:
395c2c66affSColin Finck             case SidTypeGroup:
396c2c66affSColin Finck                 ImageIndex = 1;
397c2c66affSColin Finck                 break;
398c2c66affSColin Finck             default:
399c2c66affSColin Finck                 break;
400c2c66affSColin Finck         }
401c2c66affSColin Finck     }
402c2c66affSColin Finck 
403c2c66affSColin Finck     li->mask = LVIF_IMAGE | LVIF_PARAM | LVIF_STATE | LVIF_TEXT;
404c2c66affSColin Finck     li->iItem = Index;
405c2c66affSColin Finck     li->iSubItem = 0;
406c2c66affSColin Finck     li->state = (Selected ? LVIS_SELECTED : 0);
407c2c66affSColin Finck     li->stateMask = LVIS_SELECTED;
408c2c66affSColin Finck     li->pszText = PrincipalListItem->DisplayString;
409c2c66affSColin Finck     li->iImage = ImageIndex;
410c2c66affSColin Finck     li->lParam = (LPARAM)PrincipalListItem;
411c2c66affSColin Finck }
412c2c66affSColin Finck 
413c2c66affSColin Finck static INT
AddPrincipalListEntry(IN PSECURITY_PAGE sp,IN PPRINCIPAL_LISTITEM PrincipalListItem,IN INT Index,IN BOOL Selected)414c2c66affSColin Finck AddPrincipalListEntry(IN PSECURITY_PAGE sp,
415c2c66affSColin Finck                       IN PPRINCIPAL_LISTITEM PrincipalListItem,
416c2c66affSColin Finck                       IN INT Index,
417c2c66affSColin Finck                       IN BOOL Selected)
418c2c66affSColin Finck {
419c2c66affSColin Finck     LVITEM li;
420c2c66affSColin Finck     INT Ret;
421c2c66affSColin Finck 
422c2c66affSColin Finck     if (PrincipalListItem->DisplayString != NULL)
423c2c66affSColin Finck     {
424c2c66affSColin Finck         LocalFree((HLOCAL)PrincipalListItem->DisplayString);
425c2c66affSColin Finck     }
426c2c66affSColin Finck     PrincipalListItem->DisplayString = GetPrincipalDisplayString(PrincipalListItem);
427c2c66affSColin Finck 
428c2c66affSColin Finck     CreatePrincipalListItem(&li,
429c2c66affSColin Finck                             sp,
430c2c66affSColin Finck                             PrincipalListItem,
431c2c66affSColin Finck                             Index,
432c2c66affSColin Finck                             Selected);
433c2c66affSColin Finck 
434c2c66affSColin Finck     Ret = ListView_InsertItem(sp->hWndPrincipalsList,
435c2c66affSColin Finck                               &li);
436c2c66affSColin Finck 
437c2c66affSColin Finck     return Ret;
438c2c66affSColin Finck }
439c2c66affSColin Finck 
440c2c66affSColin Finck static int CALLBACK
PrincipalCompare(IN LPARAM lParam1,IN LPARAM lParam2,IN LPARAM lParamSort)441c2c66affSColin Finck PrincipalCompare(IN LPARAM lParam1,
442c2c66affSColin Finck                  IN LPARAM lParam2,
443c2c66affSColin Finck                  IN LPARAM lParamSort)
444c2c66affSColin Finck {
445c2c66affSColin Finck     PPRINCIPAL_LISTITEM Item1 = (PPRINCIPAL_LISTITEM)lParam1;
446c2c66affSColin Finck     PPRINCIPAL_LISTITEM Item2 = (PPRINCIPAL_LISTITEM)lParam2;
447c2c66affSColin Finck 
448c2c66affSColin Finck     if (Item1->DisplayString != NULL && Item2->DisplayString != NULL)
449c2c66affSColin Finck     {
450c2c66affSColin Finck         return wcscmp(Item1->DisplayString,
451c2c66affSColin Finck                       Item2->DisplayString);
452c2c66affSColin Finck     }
453c2c66affSColin Finck 
454c2c66affSColin Finck     return 0;
455c2c66affSColin Finck }
456c2c66affSColin Finck 
457c2c66affSColin Finck static VOID
UpdatePrincipalListItem(IN PSECURITY_PAGE sp,IN INT PrincipalIndex,IN PPRINCIPAL_LISTITEM PrincipalListItem,IN PSIDREQRESULT SidReqResult)458c2c66affSColin Finck UpdatePrincipalListItem(IN PSECURITY_PAGE sp,
459c2c66affSColin Finck                         IN INT PrincipalIndex,
460c2c66affSColin Finck                         IN PPRINCIPAL_LISTITEM PrincipalListItem,
461c2c66affSColin Finck                         IN PSIDREQRESULT SidReqResult)
462c2c66affSColin Finck {
463c2c66affSColin Finck     LVITEM li;
464c2c66affSColin Finck 
465c2c66affSColin Finck     /* replace the request result structure */
466c2c66affSColin Finck     if (PrincipalListItem->SidReqResult != NULL)
467c2c66affSColin Finck     {
468c2c66affSColin Finck         DereferenceSidReqResult(sp->SidCacheMgr,
469c2c66affSColin Finck                                 PrincipalListItem->SidReqResult);
470c2c66affSColin Finck     }
471c2c66affSColin Finck 
472c2c66affSColin Finck     ReferenceSidReqResult(sp->SidCacheMgr,
473c2c66affSColin Finck                           SidReqResult);
474c2c66affSColin Finck     PrincipalListItem->SidReqResult = SidReqResult;
475c2c66affSColin Finck 
476c2c66affSColin Finck     /* update the display string */
477c2c66affSColin Finck     if (PrincipalListItem->DisplayString != NULL)
478c2c66affSColin Finck     {
479c2c66affSColin Finck         LocalFree((HLOCAL)PrincipalListItem->DisplayString);
480c2c66affSColin Finck     }
481c2c66affSColin Finck     PrincipalListItem->DisplayString = GetPrincipalDisplayString(PrincipalListItem);
482c2c66affSColin Finck 
483c2c66affSColin Finck     /* update the list item */
484c2c66affSColin Finck     CreatePrincipalListItem(&li,
485c2c66affSColin Finck                             sp,
486c2c66affSColin Finck                             PrincipalListItem,
487c2c66affSColin Finck                             PrincipalIndex,
488c2c66affSColin Finck                             FALSE);
489c2c66affSColin Finck 
490c2c66affSColin Finck     /* don't change the list item state */
491c2c66affSColin Finck     li.mask &= ~(LVIF_STATE | LVIF_PARAM);
492c2c66affSColin Finck 
493c2c66affSColin Finck     (void)ListView_SetItem(sp->hWndPrincipalsList,
494c2c66affSColin Finck                            &li);
495c2c66affSColin Finck 
496c2c66affSColin Finck     /* sort the principals list view again */
497c2c66affSColin Finck     (void)ListView_SortItems(sp->hWndPrincipalsList,
498c2c66affSColin Finck                              PrincipalCompare,
499c2c66affSColin Finck                              (LPARAM)sp);
500c2c66affSColin Finck }
501c2c66affSColin Finck 
502c2c66affSColin Finck static VOID
ReloadPrincipalsList(IN PSECURITY_PAGE sp)503c2c66affSColin Finck ReloadPrincipalsList(IN PSECURITY_PAGE sp)
504c2c66affSColin Finck {
505c2c66affSColin Finck     PSECURITY_DESCRIPTOR SecurityDescriptor;
506c2c66affSColin Finck     BOOL DaclPresent, DaclDefaulted, OwnerDefaulted;
507c2c66affSColin Finck     PACL Dacl = NULL;
508c2c66affSColin Finck     PSID OwnerSid = NULL;
509c2c66affSColin Finck     LPTSTR OwnerSidString;
510c2c66affSColin Finck     DWORD SidLen;
511c2c66affSColin Finck     HRESULT hRet;
512c2c66affSColin Finck 
513c2c66affSColin Finck     /* delete the cached ACL */
514c2c66affSColin Finck     FreePrincipalsList(sp,
515c2c66affSColin Finck                        &sp->PrincipalsListHead);
516c2c66affSColin Finck 
517c2c66affSColin Finck     /* query the ACL */
518c2c66affSColin Finck     hRet = sp->psi->lpVtbl->GetSecurity(sp->psi,
519c2c66affSColin Finck                                         DACL_SECURITY_INFORMATION | OWNER_SECURITY_INFORMATION,
520c2c66affSColin Finck                                         &SecurityDescriptor,
521c2c66affSColin Finck                                         FALSE);
522c2c66affSColin Finck     if (SUCCEEDED(hRet) && SecurityDescriptor != NULL)
523c2c66affSColin Finck     {
524c2c66affSColin Finck         if (GetSecurityDescriptorOwner(SecurityDescriptor,
525c2c66affSColin Finck                                        &OwnerSid,
526c2c66affSColin Finck                                        &OwnerDefaulted))
527c2c66affSColin Finck         {
528c2c66affSColin Finck             sp->OwnerDefaulted = OwnerDefaulted;
529c2c66affSColin Finck             if (sp->OwnerSid != NULL)
530c2c66affSColin Finck             {
531c2c66affSColin Finck                 LocalFree((HLOCAL)sp->OwnerSid);
532c2c66affSColin Finck                 sp->OwnerSid = NULL;
533c2c66affSColin Finck             }
534c2c66affSColin Finck 
535c2c66affSColin Finck             SidLen = GetLengthSid(OwnerSid);
536c2c66affSColin Finck             if (SidLen == 0)
537c2c66affSColin Finck                 goto ClearOwner;
538c2c66affSColin Finck 
539c2c66affSColin Finck             sp->OwnerSid = (PSID)LocalAlloc(LMEM_FIXED,
540c2c66affSColin Finck                                             SidLen);
541c2c66affSColin Finck             if (sp->OwnerSid != NULL)
542c2c66affSColin Finck             {
543c2c66affSColin Finck                 if (CopySid(SidLen,
544c2c66affSColin Finck                             sp->OwnerSid,
545c2c66affSColin Finck                             OwnerSid))
546c2c66affSColin Finck                 {
547c2c66affSColin Finck                     /* Lookup the SID now */
548c2c66affSColin Finck                     if (!LookupSidCache(sp->SidCacheMgr,
549c2c66affSColin Finck                                         sp->OwnerSid,
550c2c66affSColin Finck                                         SidLookupCompletion,
551c2c66affSColin Finck                                         sp))
552c2c66affSColin Finck                     {
553c2c66affSColin Finck                         /* Lookup was deferred */
554c2c66affSColin Finck                         if (ConvertSidToStringSid(sp->OwnerSid,
555c2c66affSColin Finck                                                   &OwnerSidString))
556c2c66affSColin Finck                         {
557c2c66affSColin Finck                             SetDlgItemText(sp->hWnd,
558c2c66affSColin Finck                                            IDC_OWNER,
559c2c66affSColin Finck                                            OwnerSidString);
560c2c66affSColin Finck                             LocalFree((HLOCAL)OwnerSidString);
561c2c66affSColin Finck                         }
562c2c66affSColin Finck                         else
563c2c66affSColin Finck                             goto ClearOwner;
564c2c66affSColin Finck                     }
565c2c66affSColin Finck                 }
566c2c66affSColin Finck                 else
567c2c66affSColin Finck                     goto ClearOwner;
568c2c66affSColin Finck             }
569c2c66affSColin Finck             else
570c2c66affSColin Finck                 goto ClearOwner;
571c2c66affSColin Finck         }
572c2c66affSColin Finck         else
573c2c66affSColin Finck         {
574c2c66affSColin Finck ClearOwner:
575c2c66affSColin Finck             SetDlgItemText(sp->hWnd,
576c2c66affSColin Finck                            IDC_OWNER,
577c2c66affSColin Finck                            NULL);
578c2c66affSColin Finck         }
579c2c66affSColin Finck 
580c2c66affSColin Finck         if (GetSecurityDescriptorDacl(SecurityDescriptor,
581c2c66affSColin Finck                                       &DaclPresent,
582c2c66affSColin Finck                                       &Dacl,
583c2c66affSColin Finck                                       &DaclDefaulted) &&
584c2c66affSColin Finck             DaclPresent && Dacl != NULL)
585c2c66affSColin Finck         {
586c2c66affSColin Finck             PSID Sid;
587c2c66affSColin Finck             PACE_HEADER AceHeader;
588c2c66affSColin Finck             ULONG AceIndex;
589c2c66affSColin Finck 
590c2c66affSColin Finck             for (AceIndex = 0;
591c2c66affSColin Finck                  AceIndex < Dacl->AceCount;
592c2c66affSColin Finck                  AceIndex++)
593c2c66affSColin Finck             {
594c2c66affSColin Finck                 if (GetAce(Dacl,
595c2c66affSColin Finck                            AceIndex,
596c2c66affSColin Finck                            (LPVOID*)&AceHeader) &&
597c2c66affSColin Finck                     AceHeader != NULL)
598c2c66affSColin Finck                 {
599c2c66affSColin Finck                     BOOL LookupDeferred;
600c2c66affSColin Finck                     PPRINCIPAL_LISTITEM PrincipalListItem;
601c2c66affSColin Finck 
602c2c66affSColin Finck                     Sid = AceHeaderToSID(AceHeader);
603c2c66affSColin Finck 
604c2c66affSColin Finck                     PrincipalListItem = AddPrincipalToList(sp,
605c2c66affSColin Finck                                                            Sid,
606c2c66affSColin Finck                                                            AceHeader,
607c2c66affSColin Finck                                                            &LookupDeferred);
608c2c66affSColin Finck 
609c2c66affSColin Finck                     if (PrincipalListItem != NULL && LookupDeferred)
610c2c66affSColin Finck                     {
611c2c66affSColin Finck                         AddPrincipalListEntry(sp,
612c2c66affSColin Finck                                               PrincipalListItem,
613c2c66affSColin Finck                                               -1,
614c2c66affSColin Finck                                               FALSE);
615c2c66affSColin Finck                     }
616c2c66affSColin Finck                 }
617c2c66affSColin Finck             }
618c2c66affSColin Finck         }
619c2c66affSColin Finck         LocalFree((HLOCAL)SecurityDescriptor);
620c2c66affSColin Finck     }
621c2c66affSColin Finck }
622c2c66affSColin Finck 
623c2c66affSColin Finck static VOID
UpdateControlStates(IN PSECURITY_PAGE sp)624c2c66affSColin Finck UpdateControlStates(IN PSECURITY_PAGE sp)
625c2c66affSColin Finck {
626c2c66affSColin Finck     PPRINCIPAL_LISTITEM Selected = (PPRINCIPAL_LISTITEM)ListViewGetSelectedItemData(sp->hWndPrincipalsList);
627c2c66affSColin Finck 
628c2c66affSColin Finck     EnableWindow(sp->hBtnRemove,
629c2c66affSColin Finck                  Selected != NULL);
630c2c66affSColin Finck     EnableWindow(sp->hAceCheckList,
631c2c66affSColin Finck                  Selected != NULL);
632c2c66affSColin Finck 
633c2c66affSColin Finck     if (Selected != NULL)
634c2c66affSColin Finck     {
635c2c66affSColin Finck         LPWSTR szLabel;
636c2c66affSColin Finck         LPWSTR szDisplayString;
637c2c66affSColin Finck 
638c2c66affSColin Finck         szDisplayString = GetPrincipalAccountNameString(Selected);
639c2c66affSColin Finck         if (LoadAndFormatString(hDllInstance,
640c2c66affSColin Finck                                 IDS_PERMISSIONS_FOR,
641c2c66affSColin Finck                                 &szLabel,
642c2c66affSColin Finck                                 szDisplayString))
643c2c66affSColin Finck         {
644c2c66affSColin Finck             SetWindowText(sp->hPermissionsForLabel,
645c2c66affSColin Finck                           szLabel);
646c2c66affSColin Finck 
647c2c66affSColin Finck             LocalFree((HLOCAL)szLabel);
648c2c66affSColin Finck         }
649c2c66affSColin Finck 
650c2c66affSColin Finck         LocalFree((HLOCAL)szDisplayString);
651c2c66affSColin Finck 
652c2c66affSColin Finck         /* FIXME - update the checkboxes */
653c2c66affSColin Finck     }
654c2c66affSColin Finck     else
655c2c66affSColin Finck     {
656c2c66affSColin Finck         WCHAR szPermissions[255];
657c2c66affSColin Finck 
658c2c66affSColin Finck         if (LoadString(hDllInstance,
659c2c66affSColin Finck                        IDS_PERMISSIONS,
660c2c66affSColin Finck                        szPermissions,
661c2c66affSColin Finck                        sizeof(szPermissions) / sizeof(szPermissions[0])))
662c2c66affSColin Finck         {
663c2c66affSColin Finck             SetWindowText(sp->hPermissionsForLabel,
664c2c66affSColin Finck                           szPermissions);
665c2c66affSColin Finck         }
666c2c66affSColin Finck 
667c2c66affSColin Finck         SendMessage(sp->hAceCheckList,
668c2c66affSColin Finck                     CLM_CLEARCHECKBOXES,
669c2c66affSColin Finck                     0,
670c2c66affSColin Finck                     0);
671c2c66affSColin Finck     }
672c2c66affSColin Finck }
673c2c66affSColin Finck 
674c2c66affSColin Finck static void
UpdatePrincipalInfo(IN PSECURITY_PAGE sp,IN PSIDLOOKUPNOTIFYINFO LookupInfo)675c2c66affSColin Finck UpdatePrincipalInfo(IN PSECURITY_PAGE sp,
676c2c66affSColin Finck                     IN PSIDLOOKUPNOTIFYINFO LookupInfo)
677c2c66affSColin Finck {
678c2c66affSColin Finck     PPRINCIPAL_LISTITEM CurItem;
679c2c66affSColin Finck     LPWSTR DisplayName;
680c2c66affSColin Finck 
681c2c66affSColin Finck     if (sp->OwnerSid != NULL &&
682c2c66affSColin Finck         EqualSid(sp->OwnerSid,
683c2c66affSColin Finck                  LookupInfo->Sid))
684c2c66affSColin Finck     {
685c2c66affSColin Finck         if (LookupInfo->SidRequestResult != NULL)
686c2c66affSColin Finck             DisplayName = GetDisplayStringFromSidRequestResult(LookupInfo->SidRequestResult);
687c2c66affSColin Finck         else if (!ConvertSidToStringSidW(LookupInfo->Sid,
688c2c66affSColin Finck                                          &DisplayName))
689c2c66affSColin Finck         {
690c2c66affSColin Finck             DisplayName = NULL;
691c2c66affSColin Finck         }
692c2c66affSColin Finck 
693c2c66affSColin Finck         if (DisplayName != NULL)
694c2c66affSColin Finck         {
695c2c66affSColin Finck             SetDlgItemTextW(sp->hWnd,
696c2c66affSColin Finck                             IDC_OWNER,
697c2c66affSColin Finck                             DisplayName);
698c2c66affSColin Finck 
699c2c66affSColin Finck             LocalFree((HLOCAL)DisplayName);
700c2c66affSColin Finck         }
701c2c66affSColin Finck     }
702c2c66affSColin Finck 
703c2c66affSColin Finck     for (CurItem = sp->PrincipalsListHead;
704c2c66affSColin Finck          CurItem != NULL;
705c2c66affSColin Finck          CurItem = CurItem->Next)
706c2c66affSColin Finck     {
707c2c66affSColin Finck         if (EqualSid((PSID)(CurItem + 1),
708c2c66affSColin Finck                      LookupInfo->Sid))
709c2c66affSColin Finck         {
710c2c66affSColin Finck             INT PrincipalIndex;
711c2c66affSColin Finck             LVFINDINFO lvfi;
712c2c66affSColin Finck 
713c2c66affSColin Finck             /* find the principal in the list */
714c2c66affSColin Finck             lvfi.flags = LVFI_PARAM;
715c2c66affSColin Finck             lvfi.lParam = (LPARAM)CurItem;
716c2c66affSColin Finck             PrincipalIndex = ListView_FindItem(sp->hWndPrincipalsList,
717c2c66affSColin Finck                                                -1,
718c2c66affSColin Finck                                                &lvfi);
719c2c66affSColin Finck 
720c2c66affSColin Finck             if (PrincipalIndex != -1)
721c2c66affSColin Finck             {
722c2c66affSColin Finck                 /* update the principal in the list view control */
723c2c66affSColin Finck                 UpdatePrincipalListItem(sp,
724c2c66affSColin Finck                                         PrincipalIndex,
725c2c66affSColin Finck                                         CurItem,
726c2c66affSColin Finck                                         LookupInfo->SidRequestResult);
727c2c66affSColin Finck 
728c2c66affSColin Finck                 if (ListViewGetSelectedItemData(sp->hWndPrincipalsList) == (LPARAM)CurItem)
729c2c66affSColin Finck                 {
730c2c66affSColin Finck                     UpdateControlStates(sp);
731c2c66affSColin Finck                 }
732c2c66affSColin Finck             }
733c2c66affSColin Finck             else
734c2c66affSColin Finck             {
735c2c66affSColin Finck                 AddPrincipalListEntry(sp,
736c2c66affSColin Finck                                       CurItem,
737c2c66affSColin Finck                                       -1,
738c2c66affSColin Finck                                       FALSE);
739c2c66affSColin Finck             }
740c2c66affSColin Finck             break;
741c2c66affSColin Finck         }
742c2c66affSColin Finck     }
743c2c66affSColin Finck }
744c2c66affSColin Finck 
745c2c66affSColin Finck static UINT CALLBACK
SecurityPageCallback(IN HWND hwnd,IN UINT uMsg,IN LPPROPSHEETPAGE ppsp)746c2c66affSColin Finck SecurityPageCallback(IN HWND hwnd,
747c2c66affSColin Finck                      IN UINT uMsg,
748c2c66affSColin Finck                      IN LPPROPSHEETPAGE ppsp)
749c2c66affSColin Finck {
750c2c66affSColin Finck     PSECURITY_PAGE sp = (PSECURITY_PAGE)ppsp->lParam;
751c2c66affSColin Finck 
752c2c66affSColin Finck     switch (uMsg)
753c2c66affSColin Finck     {
754c2c66affSColin Finck         case PSPCB_CREATE:
755c2c66affSColin Finck         {
756c2c66affSColin Finck             return TRUE;
757c2c66affSColin Finck         }
758c2c66affSColin Finck         case PSPCB_RELEASE:
759c2c66affSColin Finck         {
760c2c66affSColin Finck             DestroySecurityPage(sp);
761c2c66affSColin Finck             return FALSE;
762c2c66affSColin Finck         }
763c2c66affSColin Finck     }
764c2c66affSColin Finck 
765c2c66affSColin Finck     return FALSE;
766c2c66affSColin Finck }
767c2c66affSColin Finck 
768c2c66affSColin Finck static VOID
SetAceCheckListColumns(IN HWND hAceCheckList,IN UINT Button,IN HWND hLabel)769c2c66affSColin Finck SetAceCheckListColumns(IN HWND hAceCheckList,
770c2c66affSColin Finck                        IN UINT Button,
771c2c66affSColin Finck                        IN HWND hLabel)
772c2c66affSColin Finck {
773c2c66affSColin Finck     POINT pt;
774c2c66affSColin Finck     RECT rcLabel;
775c2c66affSColin Finck 
776c2c66affSColin Finck     GetWindowRect(hLabel,
777c2c66affSColin Finck                   &rcLabel);
778c2c66affSColin Finck     pt.y = 0;
779c2c66affSColin Finck     pt.x = (rcLabel.right - rcLabel.left) / 2;
780c2c66affSColin Finck     MapWindowPoints(hLabel,
781c2c66affSColin Finck                     hAceCheckList,
782c2c66affSColin Finck                     &pt,
783c2c66affSColin Finck                     1);
784c2c66affSColin Finck 
785c2c66affSColin Finck     SendMessage(hAceCheckList,
786c2c66affSColin Finck                 CLM_SETCHECKBOXCOLUMN,
787c2c66affSColin Finck                 Button,
788c2c66affSColin Finck                 pt.x);
789c2c66affSColin Finck }
790c2c66affSColin Finck 
791c2c66affSColin Finck static VOID
LoadPermissionsList(IN PSECURITY_PAGE sp,IN GUID * GuidObjectType,IN DWORD dwFlags,OUT SI_ACCESS * DefaultAccess)792c2c66affSColin Finck LoadPermissionsList(IN PSECURITY_PAGE sp,
793c2c66affSColin Finck                     IN GUID *GuidObjectType,
794c2c66affSColin Finck                     IN DWORD dwFlags,
795c2c66affSColin Finck                     OUT SI_ACCESS *DefaultAccess)
796c2c66affSColin Finck {
797c2c66affSColin Finck     HRESULT hRet;
798c2c66affSColin Finck     PSI_ACCESS AccessList;
799c2c66affSColin Finck     ULONG nAccessList, DefaultAccessIndex;
800c2c66affSColin Finck     WCHAR szSpecialPermissions[255];
801c2c66affSColin Finck     BOOLEAN SpecialPermissionsPresent = FALSE;
802c2c66affSColin Finck     ACCESS_MASK SpecialPermissionsMask = 0;
803c2c66affSColin Finck 
804c2c66affSColin Finck     /* clear the permissions list */
805c2c66affSColin Finck 
806c2c66affSColin Finck     SendMessage(sp->hAceCheckList,
807c2c66affSColin Finck                 CLM_CLEAR,
808c2c66affSColin Finck                 0,
809c2c66affSColin Finck                 0);
810c2c66affSColin Finck 
811c2c66affSColin Finck     /* query the access rights from the server */
812c2c66affSColin Finck     hRet = sp->psi->lpVtbl->GetAccessRights(sp->psi,
813c2c66affSColin Finck                                             GuidObjectType,
814c2c66affSColin Finck                                             dwFlags, /* FIXME */
815c2c66affSColin Finck                                             &AccessList,
816c2c66affSColin Finck                                             &nAccessList,
817c2c66affSColin Finck                                             &DefaultAccessIndex);
818c2c66affSColin Finck     if (SUCCEEDED(hRet) && nAccessList != 0)
819c2c66affSColin Finck     {
820c2c66affSColin Finck         LPCWSTR NameStr;
821c2c66affSColin Finck         PSI_ACCESS CurAccess, LastAccess;
822c2c66affSColin Finck         WCHAR NameBuffer[MAX_PATH];
823c2c66affSColin Finck 
824c2c66affSColin Finck         /* save the default access rights to be used when adding ACEs later */
825c2c66affSColin Finck         if (DefaultAccess != NULL)
826c2c66affSColin Finck         {
827c2c66affSColin Finck             *DefaultAccess = AccessList[DefaultAccessIndex];
828c2c66affSColin Finck         }
829c2c66affSColin Finck 
830c2c66affSColin Finck         LastAccess = AccessList + nAccessList;
831c2c66affSColin Finck         for (CurAccess = &AccessList[0];
832c2c66affSColin Finck              CurAccess != LastAccess;
833c2c66affSColin Finck              CurAccess++)
834c2c66affSColin Finck         {
835c2c66affSColin Finck             if (CurAccess->dwFlags & dwFlags)
836c2c66affSColin Finck             {
837c2c66affSColin Finck                 /* get the permission name, load it from a string table if necessary */
838c2c66affSColin Finck                 if (IS_INTRESOURCE(CurAccess->pszName))
839c2c66affSColin Finck                 {
840c2c66affSColin Finck                     if (!LoadString(sp->ObjectInfo.hInstance,
841c2c66affSColin Finck                                     (UINT)((ULONG_PTR)CurAccess->pszName),
842c2c66affSColin Finck                                     NameBuffer,
843c2c66affSColin Finck                                     sizeof(NameBuffer) / sizeof(NameBuffer[0])))
844c2c66affSColin Finck                     {
845c2c66affSColin Finck                         LoadString(hDllInstance,
846c2c66affSColin Finck                                    IDS_UNKNOWN,
847c2c66affSColin Finck                                    NameBuffer,
848c2c66affSColin Finck                                    sizeof(NameBuffer) / sizeof(NameBuffer[0]));
849c2c66affSColin Finck                     }
850c2c66affSColin Finck                     NameStr = NameBuffer;
851c2c66affSColin Finck                 }
852c2c66affSColin Finck                 else
853c2c66affSColin Finck                 {
854c2c66affSColin Finck                     NameStr = CurAccess->pszName;
855c2c66affSColin Finck                 }
856c2c66affSColin Finck 
857c2c66affSColin Finck                 SendMessage(sp->hAceCheckList,
858c2c66affSColin Finck                             CLM_ADDITEM,
859c2c66affSColin Finck                             (WPARAM)CurAccess->mask,
860c2c66affSColin Finck                             (LPARAM)NameStr);
861c2c66affSColin Finck             }
862c2c66affSColin Finck             else if (CurAccess->dwFlags & SI_ACCESS_SPECIFIC)
863c2c66affSColin Finck             {
864c2c66affSColin Finck                 SpecialPermissionsPresent = TRUE;
865c2c66affSColin Finck                 SpecialPermissionsMask |= CurAccess->mask;
866c2c66affSColin Finck             }
867c2c66affSColin Finck         }
868c2c66affSColin Finck     }
869c2c66affSColin Finck 
870c2c66affSColin Finck     /* add the special permissions check item in case the specific access rights
871c2c66affSColin Finck        aren't displayed */
872c2c66affSColin Finck     if (SpecialPermissionsPresent &&
873c2c66affSColin Finck         LoadString(hDllInstance,
874c2c66affSColin Finck                    IDS_SPECIAL_PERMISSIONS,
875c2c66affSColin Finck                    szSpecialPermissions,
876c2c66affSColin Finck                    sizeof(szSpecialPermissions) / sizeof(szSpecialPermissions[0])))
877c2c66affSColin Finck     {
878c2c66affSColin Finck         /* add the special permissions check item */
879c2c66affSColin Finck         sp->SpecialPermCheckIndex = (INT)SendMessage(sp->hAceCheckList,
880c2c66affSColin Finck                                                      CLM_ADDITEM,
881c2c66affSColin Finck                                                      (WPARAM)SpecialPermissionsMask,
882c2c66affSColin Finck                                                      (LPARAM)szSpecialPermissions);
883c2c66affSColin Finck         if (sp->SpecialPermCheckIndex != -1)
884c2c66affSColin Finck         {
885c2c66affSColin Finck             SendMessage(sp->hAceCheckList,
886c2c66affSColin Finck                         CLM_SETITEMSTATE,
887c2c66affSColin Finck                         (WPARAM)sp->SpecialPermCheckIndex,
888c2c66affSColin Finck                         CIS_ALLOWDISABLED | CIS_DENYDISABLED | CIS_NONE);
889c2c66affSColin Finck         }
890c2c66affSColin Finck     }
891c2c66affSColin Finck }
892c2c66affSColin Finck 
893c2c66affSColin Finck static VOID
ResizeControls(IN PSECURITY_PAGE sp,IN INT Width,IN INT Height)894c2c66affSColin Finck ResizeControls(IN PSECURITY_PAGE sp,
895c2c66affSColin Finck                IN INT Width,
896c2c66affSColin Finck                IN INT Height)
897c2c66affSColin Finck {
898c2c66affSColin Finck     HWND hWndAllow, hWndDeny, hWndOwnerEdit;
899c2c66affSColin Finck     RECT rcControl, rcControl2, rcControl3, rcWnd;
900c2c66affSColin Finck     INT cxWidth, cxEdge, btnSpacing;
901c2c66affSColin Finck     POINT pt, pt2;
902c2c66affSColin Finck     HDWP dwp;
903c2c66affSColin Finck     INT nControls = 8;
904c2c66affSColin Finck     LVCOLUMN lvc;
905c2c66affSColin Finck 
906c2c66affSColin Finck     hWndAllow = GetDlgItem(sp->hWnd,
907c2c66affSColin Finck                            IDC_LABEL_ALLOW);
908c2c66affSColin Finck     hWndDeny = GetDlgItem(sp->hWnd,
909c2c66affSColin Finck                           IDC_LABEL_DENY);
910c2c66affSColin Finck 
911c2c66affSColin Finck     GetWindowRect(sp->hWnd,
912c2c66affSColin Finck                   &rcWnd);
913c2c66affSColin Finck 
914c2c66affSColin Finck     cxEdge = GetSystemMetrics(SM_CXEDGE);
915c2c66affSColin Finck 
916c2c66affSColin Finck     /* use the left margin of the principal list view control for all control
917c2c66affSColin Finck        margins */
918c2c66affSColin Finck     pt.x = 0;
919c2c66affSColin Finck     pt.y = 0;
920c2c66affSColin Finck     MapWindowPoints(sp->hWndPrincipalsList,
921c2c66affSColin Finck                     sp->hWnd,
922c2c66affSColin Finck                     &pt,
923c2c66affSColin Finck                     1);
924c2c66affSColin Finck     cxWidth = Width - (2 * pt.x);
925c2c66affSColin Finck 
926c2c66affSColin Finck     if (sp->ObjectInfo.dwFlags & SI_ADVANCED)
927c2c66affSColin Finck     {
928c2c66affSColin Finck         nControls += 2;
929c2c66affSColin Finck     }
930c2c66affSColin Finck 
931c2c66affSColin Finck     if ((dwp = BeginDeferWindowPos(nControls)))
932c2c66affSColin Finck     {
933c2c66affSColin Finck         /* resize the owner edit field */
934c2c66affSColin Finck         hWndOwnerEdit = GetDlgItem(sp->hWnd,
935c2c66affSColin Finck                                    IDC_OWNER);
936c2c66affSColin Finck         GetWindowRect(hWndOwnerEdit,
937c2c66affSColin Finck                       &rcControl);
938c2c66affSColin Finck         pt2.x = 0;
939c2c66affSColin Finck         pt2.y = 0;
940c2c66affSColin Finck         MapWindowPoints(hWndOwnerEdit,
941c2c66affSColin Finck                         sp->hWnd,
942c2c66affSColin Finck                         &pt2,
943c2c66affSColin Finck                         1);
944c2c66affSColin Finck         if (!(dwp = DeferWindowPos(dwp,
945c2c66affSColin Finck                                    hWndOwnerEdit,
946c2c66affSColin Finck                                    NULL,
947c2c66affSColin Finck                                    0,
948c2c66affSColin Finck                                    0,
949c2c66affSColin Finck                                    Width - pt.x - pt2.x,
950c2c66affSColin Finck                                    rcControl.bottom - rcControl.top,
951c2c66affSColin Finck                                    SWP_NOMOVE | SWP_NOZORDER)))
952c2c66affSColin Finck         {
953c2c66affSColin Finck             goto EndDeferWnds;
954c2c66affSColin Finck         }
955c2c66affSColin Finck 
956c2c66affSColin Finck         /* resize the Principal list view */
957c2c66affSColin Finck         GetWindowRect(sp->hWndPrincipalsList,
958c2c66affSColin Finck                       &rcControl);
959c2c66affSColin Finck         if (!(dwp = DeferWindowPos(dwp,
960c2c66affSColin Finck                                    sp->hWndPrincipalsList,
961c2c66affSColin Finck                                    NULL,
962c2c66affSColin Finck                                    0,
963c2c66affSColin Finck                                    0,
964c2c66affSColin Finck                                    cxWidth,
965c2c66affSColin Finck                                    rcControl.bottom - rcControl.top,
966c2c66affSColin Finck                                    SWP_NOMOVE | SWP_NOZORDER)))
967c2c66affSColin Finck         {
968c2c66affSColin Finck             goto EndDeferWnds;
969c2c66affSColin Finck         }
970c2c66affSColin Finck 
971c2c66affSColin Finck         /* move the Add Principal button */
972c2c66affSColin Finck         GetWindowRect(sp->hBtnAdd,
973c2c66affSColin Finck                       &rcControl);
974c2c66affSColin Finck         GetWindowRect(sp->hBtnRemove,
975c2c66affSColin Finck                       &rcControl2);
976c2c66affSColin Finck         btnSpacing = rcControl2.left - rcControl.right;
977c2c66affSColin Finck         pt2.x = 0;
978c2c66affSColin Finck         pt2.y = 0;
979c2c66affSColin Finck         MapWindowPoints(sp->hBtnAdd,
980c2c66affSColin Finck                         sp->hWnd,
981c2c66affSColin Finck                         &pt2,
982c2c66affSColin Finck                         1);
983c2c66affSColin Finck         if (!(dwp = DeferWindowPos(dwp,
984c2c66affSColin Finck                                    sp->hBtnAdd,
985c2c66affSColin Finck                                    NULL,
986c2c66affSColin Finck                                    pt.x + cxWidth - (rcControl2.right - rcControl2.left) -
987c2c66affSColin Finck                                        (rcControl.right - rcControl.left) -
988c2c66affSColin Finck                                        btnSpacing - cxEdge,
989c2c66affSColin Finck                                    pt2.y,
990c2c66affSColin Finck                                    0,
991c2c66affSColin Finck                                    0,
992c2c66affSColin Finck                                    SWP_NOSIZE | SWP_NOZORDER)))
993c2c66affSColin Finck         {
994c2c66affSColin Finck             goto EndDeferWnds;
995c2c66affSColin Finck         }
996c2c66affSColin Finck 
997c2c66affSColin Finck         /* move the Delete Principal button */
998c2c66affSColin Finck         pt2.x = 0;
999c2c66affSColin Finck         pt2.y = 0;
1000c2c66affSColin Finck         MapWindowPoints(sp->hBtnRemove,
1001c2c66affSColin Finck                         sp->hWnd,
1002c2c66affSColin Finck                         &pt2,
1003c2c66affSColin Finck                         1);
1004c2c66affSColin Finck         if (!(dwp = DeferWindowPos(dwp,
1005c2c66affSColin Finck                                    sp->hBtnRemove,
1006c2c66affSColin Finck                                    NULL,
1007c2c66affSColin Finck                                    pt.x + cxWidth - (rcControl2.right - rcControl2.left) - cxEdge,
1008c2c66affSColin Finck                                    pt2.y,
1009c2c66affSColin Finck                                    0,
1010c2c66affSColin Finck                                    0,
1011c2c66affSColin Finck                                    SWP_NOSIZE | SWP_NOZORDER)))
1012c2c66affSColin Finck         {
1013c2c66affSColin Finck             goto EndDeferWnds;
1014c2c66affSColin Finck         }
1015c2c66affSColin Finck 
1016c2c66affSColin Finck         /* move the Permissions For label */
1017c2c66affSColin Finck         GetWindowRect(hWndAllow,
1018c2c66affSColin Finck                       &rcControl);
1019c2c66affSColin Finck         GetWindowRect(hWndDeny,
1020c2c66affSColin Finck                       &rcControl2);
1021c2c66affSColin Finck         GetWindowRect(sp->hPermissionsForLabel,
1022c2c66affSColin Finck                       &rcControl3);
1023c2c66affSColin Finck         pt2.x = 0;
1024c2c66affSColin Finck         pt2.y = 0;
1025c2c66affSColin Finck         MapWindowPoints(sp->hPermissionsForLabel,
1026c2c66affSColin Finck                         sp->hWnd,
1027c2c66affSColin Finck                         &pt2,
1028c2c66affSColin Finck                         1);
1029c2c66affSColin Finck         if (!(dwp = DeferWindowPos(dwp,
1030c2c66affSColin Finck                                    sp->hPermissionsForLabel,
1031c2c66affSColin Finck                                    NULL,
1032c2c66affSColin Finck                                    0,
1033c2c66affSColin Finck                                    0,
1034c2c66affSColin Finck                                    cxWidth - (rcControl2.right - rcControl2.left) -
1035c2c66affSColin Finck                                        (rcControl.right - rcControl.left) -
1036c2c66affSColin Finck                                        (2 * btnSpacing) - cxEdge,
1037c2c66affSColin Finck                                    rcControl3.bottom - rcControl3.top,
1038c2c66affSColin Finck                                    SWP_NOMOVE | SWP_NOZORDER)))
1039c2c66affSColin Finck         {
1040c2c66affSColin Finck             goto EndDeferWnds;
1041c2c66affSColin Finck         }
1042c2c66affSColin Finck 
1043c2c66affSColin Finck         /* move the Allow label */
1044c2c66affSColin Finck         pt2.x = 0;
1045c2c66affSColin Finck         pt2.y = 0;
1046c2c66affSColin Finck         MapWindowPoints(hWndAllow,
1047c2c66affSColin Finck                         sp->hWnd,
1048c2c66affSColin Finck                         &pt2,
1049c2c66affSColin Finck                         1);
1050c2c66affSColin Finck         if (!(dwp = DeferWindowPos(dwp,
1051c2c66affSColin Finck                                    hWndAllow,
1052c2c66affSColin Finck                                    NULL,
1053c2c66affSColin Finck                                    cxWidth - (rcControl2.right - rcControl2.left) -
1054c2c66affSColin Finck                                        (rcControl.right - rcControl.left) -
1055c2c66affSColin Finck                                        btnSpacing - cxEdge,
1056c2c66affSColin Finck                                    pt2.y,
1057c2c66affSColin Finck                                    0,
1058c2c66affSColin Finck                                    0,
1059c2c66affSColin Finck                                    SWP_NOSIZE | SWP_NOZORDER)))
1060c2c66affSColin Finck         {
1061c2c66affSColin Finck             goto EndDeferWnds;
1062c2c66affSColin Finck         }
1063c2c66affSColin Finck 
1064c2c66affSColin Finck         /* move the Deny label */
1065c2c66affSColin Finck         pt2.x = 0;
1066c2c66affSColin Finck         pt2.y = 0;
1067c2c66affSColin Finck         MapWindowPoints(hWndDeny,
1068c2c66affSColin Finck                         sp->hWnd,
1069c2c66affSColin Finck                         &pt2,
1070c2c66affSColin Finck                         1);
1071c2c66affSColin Finck         if (!(dwp = DeferWindowPos(dwp,
1072c2c66affSColin Finck                                    hWndDeny,
1073c2c66affSColin Finck                                    NULL,
1074c2c66affSColin Finck                                    cxWidth - (rcControl2.right - rcControl2.left) - cxEdge,
1075c2c66affSColin Finck                                    pt2.y,
1076c2c66affSColin Finck                                    0,
1077c2c66affSColin Finck                                    0,
1078c2c66affSColin Finck                                    SWP_NOSIZE | SWP_NOZORDER)))
1079c2c66affSColin Finck         {
1080c2c66affSColin Finck             goto EndDeferWnds;
1081c2c66affSColin Finck         }
1082c2c66affSColin Finck 
1083c2c66affSColin Finck         /* resize the Permissions check list box */
1084c2c66affSColin Finck         GetWindowRect(sp->hAceCheckList,
1085c2c66affSColin Finck                       &rcControl);
1086c2c66affSColin Finck         GetWindowRect(sp->hBtnAdvanced,
1087c2c66affSColin Finck                       &rcControl2);
1088c2c66affSColin Finck         GetWindowRect(GetDlgItem(sp->hWnd,
1089c2c66affSColin Finck                                  IDC_LABEL_ADVANCED),
1090c2c66affSColin Finck                       &rcControl3);
1091c2c66affSColin Finck         if (!(dwp = DeferWindowPos(dwp,
1092c2c66affSColin Finck                                    sp->hAceCheckList,
1093c2c66affSColin Finck                                    NULL,
1094c2c66affSColin Finck                                    0,
1095c2c66affSColin Finck                                    0,
1096c2c66affSColin Finck                                    cxWidth,
1097c2c66affSColin Finck                                    ((sp->ObjectInfo.dwFlags & SI_ADVANCED) ?
1098c2c66affSColin Finck                                        Height - (rcControl.top - rcWnd.top) -
1099c2c66affSColin Finck                                            (rcControl3.bottom - rcControl3.top) - pt.x - btnSpacing :
1100c2c66affSColin Finck                                        Height - (rcControl.top - rcWnd.top) - pt.x),
1101c2c66affSColin Finck                                    SWP_NOMOVE | SWP_NOZORDER)))
1102c2c66affSColin Finck         {
1103c2c66affSColin Finck             goto EndDeferWnds;
1104c2c66affSColin Finck         }
1105c2c66affSColin Finck 
1106c2c66affSColin Finck         if (sp->ObjectInfo.dwFlags & SI_ADVANCED)
1107c2c66affSColin Finck         {
1108c2c66affSColin Finck             /* move and resize the Advanced label */
1109c2c66affSColin Finck             if (!(dwp = DeferWindowPos(dwp,
1110c2c66affSColin Finck                                        GetDlgItem(sp->hWnd,
1111c2c66affSColin Finck                                                   IDC_LABEL_ADVANCED),
1112c2c66affSColin Finck                                        NULL,
1113c2c66affSColin Finck                                        pt.x,
1114c2c66affSColin Finck                                        Height - (rcControl3.bottom - rcControl3.top) - pt.x,
1115c2c66affSColin Finck                                        cxWidth - (rcControl2.right - rcControl2.left) - cxEdge,
1116c2c66affSColin Finck                                        rcControl3.bottom - rcControl3.top,
1117c2c66affSColin Finck                                        SWP_NOZORDER)))
1118c2c66affSColin Finck             {
1119c2c66affSColin Finck                 goto EndDeferWnds;
1120c2c66affSColin Finck             }
1121c2c66affSColin Finck 
1122c2c66affSColin Finck             /* move and resize the Advanced button */
1123c2c66affSColin Finck             if (!(dwp = DeferWindowPos(dwp,
1124c2c66affSColin Finck                                        sp->hBtnAdvanced,
1125c2c66affSColin Finck                                        NULL,
1126c2c66affSColin Finck                                        cxWidth - (rcControl2.right - rcControl2.left) + pt.x,
1127c2c66affSColin Finck                                        Height - (rcControl2.bottom - rcControl2.top) - pt.x,
1128c2c66affSColin Finck                                        0,
1129c2c66affSColin Finck                                        0,
1130c2c66affSColin Finck                                        SWP_NOSIZE | SWP_NOZORDER)))
1131c2c66affSColin Finck             {
1132c2c66affSColin Finck                 goto EndDeferWnds;
1133c2c66affSColin Finck             }
1134c2c66affSColin Finck         }
1135c2c66affSColin Finck 
1136c2c66affSColin Finck         EndDeferWindowPos(dwp);
1137c2c66affSColin Finck     }
1138c2c66affSColin Finck 
1139c2c66affSColin Finck EndDeferWnds:
1140c2c66affSColin Finck     /* update the width of the principal list view column */
1141c2c66affSColin Finck     GetClientRect(sp->hWndPrincipalsList,
1142c2c66affSColin Finck                   &rcControl);
1143c2c66affSColin Finck     lvc.mask = LVCF_WIDTH;
1144c2c66affSColin Finck     lvc.cx = rcControl.right;
1145c2c66affSColin Finck     (void)ListView_SetColumn(sp->hWndPrincipalsList,
1146c2c66affSColin Finck                              0,
1147c2c66affSColin Finck                              &lvc);
1148c2c66affSColin Finck 
1149c2c66affSColin Finck     /* calculate the columns of the allow/deny checkboxes */
1150c2c66affSColin Finck     SetAceCheckListColumns(sp->hAceCheckList,
1151c2c66affSColin Finck                            CLB_ALLOW,
1152c2c66affSColin Finck                            hWndAllow);
1153c2c66affSColin Finck     SetAceCheckListColumns(sp->hAceCheckList,
1154c2c66affSColin Finck                            CLB_DENY,
1155c2c66affSColin Finck                            hWndDeny);
1156c2c66affSColin Finck }
1157c2c66affSColin Finck 
1158c2c66affSColin Finck static PACE_HEADER
BuildDefaultPrincipalAce(IN PSECURITY_PAGE sp,IN PSID pSid)1159c2c66affSColin Finck BuildDefaultPrincipalAce(IN PSECURITY_PAGE sp,
1160c2c66affSColin Finck                          IN PSID pSid)
1161c2c66affSColin Finck {
1162c2c66affSColin Finck     PACCESS_ALLOWED_ACE Ace;
1163c2c66affSColin Finck     DWORD SidLen;
1164c2c66affSColin Finck     WORD AceSize;
1165c2c66affSColin Finck 
1166c2c66affSColin Finck     SidLen = GetLengthSid(pSid);
1167c2c66affSColin Finck     AceSize = FIELD_OFFSET(ACCESS_ALLOWED_ACE,
1168c2c66affSColin Finck                            SidStart) + (WORD)SidLen;
1169c2c66affSColin Finck     Ace = HeapAlloc(GetProcessHeap(),
1170c2c66affSColin Finck                     0,
1171c2c66affSColin Finck                     AceSize);
1172c2c66affSColin Finck     if (Ace != NULL)
1173c2c66affSColin Finck     {
1174c2c66affSColin Finck         Ace->Header.AceType = ACCESS_ALLOWED_ACE_TYPE;
1175c2c66affSColin Finck         Ace->Header.AceFlags = 0; /* FIXME */
1176c2c66affSColin Finck         Ace->Header.AceSize = AceSize;
1177c2c66affSColin Finck         Ace->Mask = sp->DefaultAccess.mask;
1178c2c66affSColin Finck 
1179c2c66affSColin Finck         if (CopySid(SidLen,
1180c2c66affSColin Finck                     (PSID)&Ace->SidStart,
1181c2c66affSColin Finck                     pSid))
1182c2c66affSColin Finck         {
1183c2c66affSColin Finck             return &Ace->Header;
1184c2c66affSColin Finck         }
1185c2c66affSColin Finck 
1186c2c66affSColin Finck         HeapFree(GetProcessHeap(),
1187c2c66affSColin Finck                  0,
1188c2c66affSColin Finck                  Ace);
1189c2c66affSColin Finck     }
1190c2c66affSColin Finck 
1191c2c66affSColin Finck     return NULL;
1192c2c66affSColin Finck }
1193c2c66affSColin Finck 
1194c2c66affSColin Finck static BOOL
AddSelectedPrincipal(IN IDsObjectPicker * pDsObjectPicker,IN HWND hwndParent OPTIONAL,IN PSID pSid,IN PVOID Context OPTIONAL)1195c2c66affSColin Finck AddSelectedPrincipal(IN IDsObjectPicker *pDsObjectPicker,
1196c2c66affSColin Finck                      IN HWND hwndParent  OPTIONAL,
1197c2c66affSColin Finck                      IN PSID pSid,
1198c2c66affSColin Finck                      IN PVOID Context  OPTIONAL)
1199c2c66affSColin Finck {
1200c2c66affSColin Finck     PACE_HEADER AceHeader;
1201c2c66affSColin Finck     PSECURITY_PAGE sp = (PSECURITY_PAGE)Context;
1202c2c66affSColin Finck 
1203c2c66affSColin Finck     AceHeader = BuildDefaultPrincipalAce(sp,
1204c2c66affSColin Finck                                          pSid);
1205c2c66affSColin Finck     if (AceHeader != NULL)
1206c2c66affSColin Finck     {
1207c2c66affSColin Finck         PPRINCIPAL_LISTITEM PrincipalListItem;
1208c2c66affSColin Finck         BOOL LookupDeferred;
1209c2c66affSColin Finck 
1210c2c66affSColin Finck         PrincipalListItem = AddPrincipalToList(sp,
1211c2c66affSColin Finck                                                pSid,
1212c2c66affSColin Finck                                                AceHeader,
1213c2c66affSColin Finck                                                &LookupDeferred);
1214c2c66affSColin Finck 
1215c2c66affSColin Finck         if (PrincipalListItem != NULL && LookupDeferred)
1216c2c66affSColin Finck         {
1217c2c66affSColin Finck             AddPrincipalListEntry(sp,
1218c2c66affSColin Finck                                   PrincipalListItem,
1219c2c66affSColin Finck                                   -1,
1220c2c66affSColin Finck                                   FALSE);
1221c2c66affSColin Finck         }
1222c2c66affSColin Finck 
1223c2c66affSColin Finck         HeapFree(GetProcessHeap(),
1224c2c66affSColin Finck                  0,
1225c2c66affSColin Finck                  AceHeader);
1226c2c66affSColin Finck     }
1227c2c66affSColin Finck 
1228c2c66affSColin Finck     return TRUE;
1229c2c66affSColin Finck }
1230c2c66affSColin Finck 
1231c2c66affSColin Finck static INT_PTR CALLBACK
SecurityPageProc(IN HWND hwndDlg,IN UINT uMsg,IN WPARAM wParam,IN LPARAM lParam)1232c2c66affSColin Finck SecurityPageProc(IN HWND hwndDlg,
1233c2c66affSColin Finck                  IN UINT uMsg,
1234c2c66affSColin Finck                  IN WPARAM wParam,
1235c2c66affSColin Finck                  IN LPARAM lParam)
1236c2c66affSColin Finck {
1237c2c66affSColin Finck     PSECURITY_PAGE sp;
1238c2c66affSColin Finck     INT_PTR Ret = FALSE;
1239c2c66affSColin Finck 
1240*0182dcd7STimo Kreuzer     sp = (PSECURITY_PAGE)GetWindowLongPtr(hwndDlg, DWLP_USER);
1241c2c66affSColin Finck     if (sp != NULL || uMsg == WM_INITDIALOG)
1242c2c66affSColin Finck     {
1243c2c66affSColin Finck         switch (uMsg)
1244c2c66affSColin Finck         {
1245c2c66affSColin Finck             case WM_NOTIFY:
1246c2c66affSColin Finck             {
1247c2c66affSColin Finck                 NMHDR *pnmh = (NMHDR*)lParam;
1248c2c66affSColin Finck 
1249c2c66affSColin Finck                 if (pnmh->hwndFrom == sp->hWndPrincipalsList)
1250c2c66affSColin Finck                 {
1251c2c66affSColin Finck                     switch (pnmh->code)
1252c2c66affSColin Finck                     {
1253c2c66affSColin Finck                         case LVN_ITEMCHANGED:
1254c2c66affSColin Finck                         {
1255c2c66affSColin Finck                             LPNMLISTVIEW pnmv = (LPNMLISTVIEW)lParam;
1256c2c66affSColin Finck 
1257c2c66affSColin Finck                             if ((pnmv->uChanged & LVIF_STATE) &&
1258c2c66affSColin Finck                                 ((pnmv->uOldState & (LVIS_FOCUSED | LVIS_SELECTED)) ||
1259c2c66affSColin Finck                                  (pnmv->uNewState & (LVIS_FOCUSED | LVIS_SELECTED))))
1260c2c66affSColin Finck                             {
1261c2c66affSColin Finck                                 UpdateControlStates(sp);
1262c2c66affSColin Finck                             }
1263c2c66affSColin Finck                             break;
1264c2c66affSColin Finck                         }
1265c2c66affSColin Finck                     }
1266c2c66affSColin Finck                 }
1267c2c66affSColin Finck                 else if (pnmh->hwndFrom == sp->hAceCheckList)
1268c2c66affSColin Finck                 {
1269c2c66affSColin Finck                     switch (pnmh->code)
1270c2c66affSColin Finck                     {
1271c2c66affSColin Finck                         case CLN_CHANGINGITEMCHECKBOX:
1272c2c66affSColin Finck                         {
1273c2c66affSColin Finck                             PNMCHANGEITEMCHECKBOX pcicb = (PNMCHANGEITEMCHECKBOX)lParam;
1274c2c66affSColin Finck 
1275c2c66affSColin Finck                             /* make sure only one of both checkboxes is only checked
1276c2c66affSColin Finck                                at the same time */
1277c2c66affSColin Finck                             if (pcicb->Checked)
1278c2c66affSColin Finck                             {
1279c2c66affSColin Finck                                 pcicb->NewState &= ~((pcicb->CheckBox != CLB_DENY) ? CIS_DENY : CIS_ALLOW);
1280c2c66affSColin Finck                             }
1281c2c66affSColin Finck                             break;
1282c2c66affSColin Finck                         }
1283c2c66affSColin Finck                     }
1284c2c66affSColin Finck                 }
1285c2c66affSColin Finck                 else if (pnmh->hwndFrom == sp->hWnd)
1286c2c66affSColin Finck                 {
1287c2c66affSColin Finck                     switch(pnmh->code)
1288c2c66affSColin Finck                     {
1289c2c66affSColin Finck                         case SIDN_LOOKUPSUCCEEDED:
1290c2c66affSColin Finck                         {
1291c2c66affSColin Finck                             PSIDLOOKUPNOTIFYINFO LookupInfo = CONTAINING_RECORD(lParam,
1292c2c66affSColin Finck                                                                                 SIDLOOKUPNOTIFYINFO,
1293c2c66affSColin Finck                                                                                 nmh);
1294c2c66affSColin Finck 
1295c2c66affSColin Finck                             /* a SID lookup succeeded, update the information */
1296c2c66affSColin Finck                             UpdatePrincipalInfo(sp,
1297c2c66affSColin Finck                                                 LookupInfo);
1298c2c66affSColin Finck                             break;
1299c2c66affSColin Finck                         }
1300c2c66affSColin Finck                     }
1301c2c66affSColin Finck                 }
1302c2c66affSColin Finck                 break;
1303c2c66affSColin Finck             }
1304c2c66affSColin Finck 
1305c2c66affSColin Finck             case WM_COMMAND:
1306c2c66affSColin Finck             {
1307c2c66affSColin Finck                 switch (LOWORD(wParam))
1308c2c66affSColin Finck                 {
1309c2c66affSColin Finck                     case IDC_ADD_PRINCIPAL:
1310c2c66affSColin Finck                     {
1311c2c66affSColin Finck                         HRESULT hRet;
1312c2c66affSColin Finck 
1313c2c66affSColin Finck                         hRet = InitializeObjectPicker(sp->ServerName,
1314c2c66affSColin Finck                                                       &sp->ObjectInfo,
1315c2c66affSColin Finck                                                       &sp->pDsObjectPicker);
1316c2c66affSColin Finck                         if (SUCCEEDED(hRet))
1317c2c66affSColin Finck                         {
1318c2c66affSColin Finck                             hRet = InvokeObjectPickerDialog(sp->pDsObjectPicker,
1319c2c66affSColin Finck                                                             hwndDlg,
1320c2c66affSColin Finck                                                             AddSelectedPrincipal,
1321c2c66affSColin Finck                                                             sp);
1322c2c66affSColin Finck                             if (FAILED(hRet))
1323c2c66affSColin Finck                             {
1324c2c66affSColin Finck                                 MessageBox(hwndDlg, L"InvokeObjectPickerDialog failed!\n", NULL, 0);
1325c2c66affSColin Finck                             }
1326c2c66affSColin Finck 
1327c2c66affSColin Finck                             /* delete the instance */
1328c2c66affSColin Finck                             FreeObjectPicker(sp->pDsObjectPicker);
1329c2c66affSColin Finck                         }
1330c2c66affSColin Finck                         else
1331c2c66affSColin Finck                         {
1332c2c66affSColin Finck                             MessageBox(hwndDlg, L"InitializeObjectPicker failed!\n", NULL, 0);
1333c2c66affSColin Finck                         }
1334c2c66affSColin Finck                         break;
1335c2c66affSColin Finck                     }
1336c2c66affSColin Finck 
1337c2c66affSColin Finck                     case IDC_REMOVE_PRINCIPAL:
1338c2c66affSColin Finck                     {
1339c2c66affSColin Finck                         PPRINCIPAL_LISTITEM SelectedPrincipal;
1340c2c66affSColin Finck 
1341c2c66affSColin Finck                         SelectedPrincipal = (PPRINCIPAL_LISTITEM)ListViewGetSelectedItemData(sp->hWndPrincipalsList);
1342c2c66affSColin Finck                         if (SelectedPrincipal != NULL)
1343c2c66affSColin Finck                         {
1344c2c66affSColin Finck                             /* FIXME */
1345c2c66affSColin Finck                         }
1346c2c66affSColin Finck                         break;
1347c2c66affSColin Finck                     }
1348c2c66affSColin Finck                 }
1349c2c66affSColin Finck                 break;
1350c2c66affSColin Finck             }
1351c2c66affSColin Finck 
1352c2c66affSColin Finck             case WM_SIZE:
1353c2c66affSColin Finck             {
1354c2c66affSColin Finck                 ResizeControls(sp,
1355c2c66affSColin Finck                                (INT)LOWORD(lParam),
1356c2c66affSColin Finck                                (INT)HIWORD(lParam));
1357c2c66affSColin Finck                 break;
1358c2c66affSColin Finck             }
1359c2c66affSColin Finck 
1360c2c66affSColin Finck             case WM_INITDIALOG:
1361c2c66affSColin Finck             {
1362c2c66affSColin Finck                 sp = (PSECURITY_PAGE)((LPPROPSHEETPAGE)lParam)->lParam;
1363c2c66affSColin Finck                 if(sp != NULL)
1364c2c66affSColin Finck                 {
1365c2c66affSColin Finck                     LV_COLUMN lvc;
1366c2c66affSColin Finck                     RECT rcLvClient;
1367c2c66affSColin Finck 
1368c2c66affSColin Finck                     sp->hWnd = hwndDlg;
1369c2c66affSColin Finck                     sp->hWndPrincipalsList = GetDlgItem(hwndDlg, IDC_PRINCIPALS);
1370c2c66affSColin Finck                     sp->hBtnAdd = GetDlgItem(hwndDlg, IDC_ADD_PRINCIPAL);
1371c2c66affSColin Finck                     sp->hBtnRemove = GetDlgItem(hwndDlg, IDC_REMOVE_PRINCIPAL);
1372c2c66affSColin Finck                     sp->hBtnAdvanced = GetDlgItem(hwndDlg, IDC_ADVANCED);
1373c2c66affSColin Finck                     sp->hAceCheckList = GetDlgItem(hwndDlg, IDC_ACE_CHECKLIST);
1374c2c66affSColin Finck                     sp->hPermissionsForLabel = GetDlgItem(hwndDlg, IDC_LABEL_PERMISSIONS_FOR);
1375c2c66affSColin Finck 
1376c2c66affSColin Finck                     sp->SpecialPermCheckIndex = -1;
1377c2c66affSColin Finck 
1378c2c66affSColin Finck                     /* save the pointer to the structure */
1379*0182dcd7STimo Kreuzer                     SetWindowLongPtr(hwndDlg, DWLP_USER, (DWORD_PTR)sp);
1380c2c66affSColin Finck 
1381c2c66affSColin Finck                     (void)ListView_SetExtendedListViewStyleEx(sp->hWndPrincipalsList,
1382c2c66affSColin Finck                                                               LVS_EX_FULLROWSELECT,
1383c2c66affSColin Finck                                                               LVS_EX_FULLROWSELECT);
1384c2c66affSColin Finck 
1385c2c66affSColin Finck                     sp->hiPrincipals = ImageList_Create(16,
1386c2c66affSColin Finck                                                         16,
1387c2c66affSColin Finck                                                         ILC_COLOR32 | ILC_MASK,
1388c2c66affSColin Finck                                                         0,
1389c2c66affSColin Finck                                                         3);
1390c2c66affSColin Finck                     if (sp->hiPrincipals != NULL)
1391c2c66affSColin Finck                     {
1392c2c66affSColin Finck                         HBITMAP hbmImages;
1393c2c66affSColin Finck 
1394c2c66affSColin Finck                         hbmImages = LoadBitmap(hDllInstance,
1395c2c66affSColin Finck                                                MAKEINTRESOURCE(IDB_USRGRPIMAGES));
1396c2c66affSColin Finck                         if (hbmImages != NULL)
1397c2c66affSColin Finck                         {
1398c2c66affSColin Finck                             ImageList_AddMasked(sp->hiPrincipals,
1399c2c66affSColin Finck                                                 hbmImages,
1400c2c66affSColin Finck                                                 RGB(255,
1401c2c66affSColin Finck                                                     0,
1402c2c66affSColin Finck                                                     255));
1403c2c66affSColin Finck 
1404c2c66affSColin Finck                             DeleteObject(hbmImages);
1405c2c66affSColin Finck                         }
1406c2c66affSColin Finck                     }
1407c2c66affSColin Finck 
1408c2c66affSColin Finck                     /* setup the listview control */
1409c2c66affSColin Finck                     if (sp->hiPrincipals != NULL)
1410c2c66affSColin Finck                     {
1411c2c66affSColin Finck                         (void)ListView_SetImageList(sp->hWndPrincipalsList,
1412c2c66affSColin Finck                                                     sp->hiPrincipals,
1413c2c66affSColin Finck                                                     LVSIL_SMALL);
1414c2c66affSColin Finck                     }
1415c2c66affSColin Finck 
1416c2c66affSColin Finck                     GetClientRect(sp->hWndPrincipalsList,
1417c2c66affSColin Finck                                   &rcLvClient);
1418c2c66affSColin Finck 
1419c2c66affSColin Finck                     /* add a column to the list view */
1420c2c66affSColin Finck                     lvc.mask = LVCF_FMT | LVCF_WIDTH;
1421c2c66affSColin Finck                     lvc.fmt = LVCFMT_LEFT;
1422c2c66affSColin Finck                     lvc.cx = rcLvClient.right;
1423c2c66affSColin Finck                     (void)ListView_InsertColumn(sp->hWndPrincipalsList,
1424c2c66affSColin Finck                                                 0,
1425c2c66affSColin Finck                                                 &lvc);
1426c2c66affSColin Finck 
1427c2c66affSColin Finck                     ReloadPrincipalsList(sp);
1428c2c66affSColin Finck 
1429c2c66affSColin Finck                     ListViewSelectItem(sp->hWndPrincipalsList,
1430c2c66affSColin Finck                                        0);
1431c2c66affSColin Finck 
1432c2c66affSColin Finck                     /* calculate the columns of the allow/deny checkboxes */
1433c2c66affSColin Finck                     SetAceCheckListColumns(sp->hAceCheckList,
1434c2c66affSColin Finck                                            CLB_ALLOW,
1435c2c66affSColin Finck                                            GetDlgItem(hwndDlg, IDC_LABEL_ALLOW));
1436c2c66affSColin Finck                     SetAceCheckListColumns(sp->hAceCheckList,
1437c2c66affSColin Finck                                            CLB_DENY,
1438c2c66affSColin Finck                                            GetDlgItem(hwndDlg, IDC_LABEL_DENY));
1439c2c66affSColin Finck 
1440c2c66affSColin Finck                     LoadPermissionsList(sp,
1441c2c66affSColin Finck                                         NULL,
1442c2c66affSColin Finck                                         SI_ACCESS_GENERAL |
1443c2c66affSColin Finck                                         ((sp->ObjectInfo.dwFlags & SI_CONTAINER) ? SI_ACCESS_CONTAINER : 0),
1444c2c66affSColin Finck                                         &sp->DefaultAccess);
1445c2c66affSColin Finck 
1446c2c66affSColin Finck                     /* hide controls in case the flags aren't present */
1447c2c66affSColin Finck                     if (sp->ObjectInfo.dwFlags & SI_ADVANCED)
1448c2c66affSColin Finck                     {
1449c2c66affSColin Finck                         /* editing the permissions is least the user can do when
1450c2c66affSColin Finck                            the advanced button is showed */
1451c2c66affSColin Finck                         sp->ObjectInfo.dwFlags |= SI_EDIT_PERMS;
1452c2c66affSColin Finck                     }
1453c2c66affSColin Finck                     else
1454c2c66affSColin Finck                     {
1455c2c66affSColin Finck                         ShowWindow(sp->hBtnAdvanced,
1456c2c66affSColin Finck                                    SW_HIDE);
1457c2c66affSColin Finck                         ShowWindow(GetDlgItem(hwndDlg, IDC_LABEL_ADVANCED),
1458c2c66affSColin Finck                                    SW_HIDE);
1459c2c66affSColin Finck                     }
1460c2c66affSColin Finck 
1461c2c66affSColin Finck                     /* enable quicksearch for the permissions checklist control */
1462c2c66affSColin Finck                     SendMessage(sp->hAceCheckList,
1463c2c66affSColin Finck                                 CLM_ENABLEQUICKSEARCH,
1464c2c66affSColin Finck                                 TRUE,
1465c2c66affSColin Finck                                 0);
1466c2c66affSColin Finck 
1467c2c66affSColin Finck                     UpdateControlStates(sp);
1468c2c66affSColin Finck                 }
1469c2c66affSColin Finck 
1470c2c66affSColin Finck                 Ret = TRUE;
1471c2c66affSColin Finck                 break;
1472c2c66affSColin Finck             }
1473c2c66affSColin Finck         }
1474c2c66affSColin Finck     }
1475c2c66affSColin Finck     return Ret;
1476c2c66affSColin Finck }
1477c2c66affSColin Finck 
1478c2c66affSColin Finck 
1479c2c66affSColin Finck /*
1480c2c66affSColin Finck  * CreateSecurityPage							EXPORTED
1481c2c66affSColin Finck  *
1482c2c66affSColin Finck  * @implemented
1483c2c66affSColin Finck  */
1484c2c66affSColin Finck HPROPSHEETPAGE
1485c2c66affSColin Finck WINAPI
CreateSecurityPage(IN LPSECURITYINFO psi)1486c2c66affSColin Finck CreateSecurityPage(IN LPSECURITYINFO psi)
1487c2c66affSColin Finck {
1488c2c66affSColin Finck     PROPSHEETPAGE psp = {0};
1489c2c66affSColin Finck     PSECURITY_PAGE sPage;
1490c2c66affSColin Finck     SI_OBJECT_INFO ObjectInfo = {0};
1491c2c66affSColin Finck     HANDLE SidCacheMgr;
1492c2c66affSColin Finck     LPCWSTR SystemName = NULL;
1493c2c66affSColin Finck     HRESULT hRet;
1494c2c66affSColin Finck 
1495c2c66affSColin Finck     if (psi == NULL)
1496c2c66affSColin Finck     {
1497c2c66affSColin Finck         SetLastError(ERROR_INVALID_PARAMETER);
1498c2c66affSColin Finck 
1499c2c66affSColin Finck         DPRINT("No ISecurityInformation class passed!\n");
1500c2c66affSColin Finck         return NULL;
1501c2c66affSColin Finck     }
1502c2c66affSColin Finck 
1503c2c66affSColin Finck     /* get the object information from the server. Zero the structure before
1504c2c66affSColin Finck        because some applications seem to return SUCCESS but only seem to set the
1505c2c66affSColin Finck        fields they care about. */
1506c2c66affSColin Finck     hRet = psi->lpVtbl->GetObjectInformation(psi,
1507c2c66affSColin Finck                                              &ObjectInfo);
1508c2c66affSColin Finck 
1509c2c66affSColin Finck     if (FAILED(hRet))
1510c2c66affSColin Finck     {
1511c2c66affSColin Finck         SetLastError(hRet);
1512c2c66affSColin Finck 
1513c2c66affSColin Finck         DPRINT("CreateSecurityPage() failed! Failed to query the object information!\n");
1514c2c66affSColin Finck         return NULL;
1515c2c66affSColin Finck     }
1516c2c66affSColin Finck 
1517c2c66affSColin Finck     if ((ObjectInfo.dwFlags & SI_SERVER_IS_DC) &&
1518c2c66affSColin Finck          ObjectInfo.pszServerName != NULL &&
1519c2c66affSColin Finck          ObjectInfo.pszServerName[0] != L'\0')
1520c2c66affSColin Finck     {
1521c2c66affSColin Finck         SystemName = ObjectInfo.pszServerName;
1522c2c66affSColin Finck     }
1523c2c66affSColin Finck 
1524c2c66affSColin Finck     SidCacheMgr = CreateSidCacheMgr(GetProcessHeap(),
1525c2c66affSColin Finck                                     SystemName);
1526c2c66affSColin Finck     if (SidCacheMgr == NULL)
1527c2c66affSColin Finck     {
1528c2c66affSColin Finck         DPRINT("Creating the SID cache failed!\n");
1529c2c66affSColin Finck         return NULL;
1530c2c66affSColin Finck     }
1531c2c66affSColin Finck 
1532c2c66affSColin Finck     hRet = CoInitialize(NULL);
1533c2c66affSColin Finck     if (FAILED(hRet))
1534c2c66affSColin Finck     {
1535c2c66affSColin Finck         DestroySidCacheMgr(SidCacheMgr);
1536c2c66affSColin Finck         DPRINT("CoInitialize failed!\n");
1537c2c66affSColin Finck         return NULL;
1538c2c66affSColin Finck     }
1539c2c66affSColin Finck 
1540c2c66affSColin Finck     sPage = HeapAlloc(GetProcessHeap(),
1541c2c66affSColin Finck                       HEAP_ZERO_MEMORY,
1542c2c66affSColin Finck                       sizeof(SECURITY_PAGE));
1543c2c66affSColin Finck     if (sPage == NULL)
1544c2c66affSColin Finck     {
1545c2c66affSColin Finck         DestroySidCacheMgr(SidCacheMgr);
1546c2c66affSColin Finck         CoUninitialize();
1547c2c66affSColin Finck 
1548c2c66affSColin Finck         SetLastError(ERROR_NOT_ENOUGH_MEMORY);
1549c2c66affSColin Finck 
1550c2c66affSColin Finck         DPRINT("Not enough memory to allocate a SECURITY_PAGE!\n");
1551c2c66affSColin Finck         return NULL;
1552c2c66affSColin Finck     }
1553c2c66affSColin Finck 
1554c2c66affSColin Finck     ZeroMemory(sPage,
1555c2c66affSColin Finck                sizeof(*sPage));
1556c2c66affSColin Finck 
1557c2c66affSColin Finck     sPage->psi = psi;
1558c2c66affSColin Finck     sPage->ObjectInfo = ObjectInfo;
1559c2c66affSColin Finck     sPage->ServerName = SystemName;
1560c2c66affSColin Finck     sPage->SidCacheMgr = SidCacheMgr;
1561c2c66affSColin Finck 
1562c2c66affSColin Finck     psp.dwSize = sizeof(PROPSHEETPAGE);
1563c2c66affSColin Finck     psp.dwFlags = PSP_USECALLBACK;
1564c2c66affSColin Finck     psp.hInstance = hDllInstance;
1565c2c66affSColin Finck     psp.pszTemplate = MAKEINTRESOURCE(IDD_SECPAGE);
1566c2c66affSColin Finck     psp.pfnDlgProc = SecurityPageProc;
1567c2c66affSColin Finck     psp.lParam = (LPARAM)sPage;
1568c2c66affSColin Finck     psp.pfnCallback = SecurityPageCallback;
1569c2c66affSColin Finck 
1570c2c66affSColin Finck     if (ObjectInfo.dwFlags & SI_PAGE_TITLE)
1571c2c66affSColin Finck     {
1572c2c66affSColin Finck         psp.pszTitle = ObjectInfo.pszPageTitle;
1573c2c66affSColin Finck 
1574c2c66affSColin Finck         if (psp.pszTitle != NULL)
1575c2c66affSColin Finck         {
1576c2c66affSColin Finck             psp.dwFlags |= PSP_USETITLE;
1577c2c66affSColin Finck         }
1578c2c66affSColin Finck     }
1579c2c66affSColin Finck     else
1580c2c66affSColin Finck     {
1581c2c66affSColin Finck         psp.pszTitle = NULL;
1582c2c66affSColin Finck     }
1583c2c66affSColin Finck 
1584c2c66affSColin Finck     /* NOTE: the SECURITY_PAGE structure will be freed by the property page
1585c2c66affSColin Finck              callback! */
1586c2c66affSColin Finck 
1587c2c66affSColin Finck     return CreatePropertySheetPage(&psp);
1588c2c66affSColin Finck }
1589c2c66affSColin Finck 
1590c2c66affSColin Finck 
1591c2c66affSColin Finck /*
1592c2c66affSColin Finck  * EditSecurity								EXPORTED
1593c2c66affSColin Finck  *
1594c2c66affSColin Finck  * @implemented
1595c2c66affSColin Finck  */
1596c2c66affSColin Finck BOOL
1597c2c66affSColin Finck WINAPI
EditSecurity(IN HWND hwndOwner,IN LPSECURITYINFO psi)1598c2c66affSColin Finck EditSecurity(IN HWND hwndOwner,
1599c2c66affSColin Finck              IN LPSECURITYINFO psi)
1600c2c66affSColin Finck {
1601c2c66affSColin Finck     HRESULT hRet;
1602c2c66affSColin Finck     SI_OBJECT_INFO ObjectInfo = {0};
1603c2c66affSColin Finck     PROPSHEETHEADER psh;
1604c2c66affSColin Finck     HPROPSHEETPAGE hPages[1];
1605c2c66affSColin Finck     LPWSTR lpCaption = NULL;
1606c2c66affSColin Finck     BOOL Ret;
1607c2c66affSColin Finck 
1608c2c66affSColin Finck     if (psi == NULL)
1609c2c66affSColin Finck     {
1610c2c66affSColin Finck         SetLastError(ERROR_INVALID_PARAMETER);
1611c2c66affSColin Finck 
1612c2c66affSColin Finck         DPRINT("No ISecurityInformation class passed!\n");
1613c2c66affSColin Finck         return FALSE;
1614c2c66affSColin Finck     }
1615c2c66affSColin Finck 
1616c2c66affSColin Finck     /* get the object information from the server. Zero the structure before
1617c2c66affSColin Finck        because some applications seem to return SUCCESS but only seem to set the
1618c2c66affSColin Finck        fields they care about. */
1619c2c66affSColin Finck     hRet = psi->lpVtbl->GetObjectInformation(psi,
1620c2c66affSColin Finck                                              &ObjectInfo);
1621c2c66affSColin Finck 
1622c2c66affSColin Finck     if (FAILED(hRet))
1623c2c66affSColin Finck     {
1624c2c66affSColin Finck         SetLastError(hRet);
1625c2c66affSColin Finck 
1626c2c66affSColin Finck         DPRINT("GetObjectInformation() failed!\n");
1627c2c66affSColin Finck         return FALSE;
1628c2c66affSColin Finck     }
1629c2c66affSColin Finck 
1630c2c66affSColin Finck     /* create the page */
1631c2c66affSColin Finck     hPages[0] = CreateSecurityPage(psi);
1632c2c66affSColin Finck     if (hPages[0] == NULL)
1633c2c66affSColin Finck     {
1634c2c66affSColin Finck         DPRINT("CreateSecurityPage(), couldn't create property sheet!\n");
1635c2c66affSColin Finck         return FALSE;
1636c2c66affSColin Finck     }
1637c2c66affSColin Finck 
1638c2c66affSColin Finck     psh.dwSize = sizeof(PROPSHEETHEADER);
1639c2c66affSColin Finck     psh.dwFlags = PSH_DEFAULT;
1640c2c66affSColin Finck     psh.hwndParent = hwndOwner;
1641c2c66affSColin Finck     psh.hInstance = hDllInstance;
1642c2c66affSColin Finck 
1643c2c66affSColin Finck     /* Set the page title to the object name, make sure the format string
1644c2c66affSColin Finck        has "%1" NOT "%s" because it uses FormatMessage() to automatically
1645c2c66affSColin Finck        allocate the right amount of memory. */
1646c2c66affSColin Finck     if (LoadAndFormatString(hDllInstance,
1647c2c66affSColin Finck                             IDS_PSP_TITLE,
1648c2c66affSColin Finck                             &lpCaption,
1649c2c66affSColin Finck                             ObjectInfo.pszObjectName))
1650c2c66affSColin Finck     {
1651c2c66affSColin Finck         psh.pszCaption = lpCaption;
1652c2c66affSColin Finck     }
1653c2c66affSColin Finck     else
1654c2c66affSColin Finck     {
1655c2c66affSColin Finck         psh.pszCaption = ObjectInfo.pszObjectName;
1656c2c66affSColin Finck     }
1657c2c66affSColin Finck 
1658c2c66affSColin Finck     psh.nPages = sizeof(hPages) / sizeof(HPROPSHEETPAGE);
1659c2c66affSColin Finck     psh.nStartPage = 0;
1660c2c66affSColin Finck     psh.phpage = hPages;
1661c2c66affSColin Finck 
1662c2c66affSColin Finck     Ret = (PropertySheet(&psh) != -1);
1663c2c66affSColin Finck 
1664c2c66affSColin Finck     if (lpCaption != NULL)
1665c2c66affSColin Finck     {
1666c2c66affSColin Finck         LocalFree((HLOCAL)lpCaption);
1667c2c66affSColin Finck     }
1668c2c66affSColin Finck 
1669c2c66affSColin Finck     return Ret;
1670c2c66affSColin Finck }
1671c2c66affSColin Finck 
1672c2c66affSColin Finck BOOL
1673c2c66affSColin Finck WINAPI
DllMain(IN HINSTANCE hinstDLL,IN DWORD dwReason,IN LPVOID lpvReserved)1674c2c66affSColin Finck DllMain(IN HINSTANCE hinstDLL,
1675c2c66affSColin Finck         IN DWORD dwReason,
1676c2c66affSColin Finck         IN LPVOID lpvReserved)
1677c2c66affSColin Finck {
1678c2c66affSColin Finck     switch (dwReason)
1679c2c66affSColin Finck     {
1680c2c66affSColin Finck         case DLL_PROCESS_ATTACH:
1681c2c66affSColin Finck             hDllInstance = hinstDLL;
1682c2c66affSColin Finck 
1683c2c66affSColin Finck             DisableThreadLibraryCalls(hinstDLL);
1684c2c66affSColin Finck 
1685c2c66affSColin Finck             if (!RegisterCheckListControl(hinstDLL))
1686c2c66affSColin Finck             {
1687c2c66affSColin Finck                 DPRINT("Registering the CHECKLIST_ACLUI class failed!\n");
1688c2c66affSColin Finck                 return FALSE;
1689c2c66affSColin Finck             }
1690c2c66affSColin Finck             break;
1691c2c66affSColin Finck 
1692c2c66affSColin Finck         case DLL_PROCESS_DETACH:
1693c2c66affSColin Finck             UnregisterCheckListControl(hinstDLL);
1694c2c66affSColin Finck             break;
1695c2c66affSColin Finck     }
1696c2c66affSColin Finck 
1697c2c66affSColin Finck     return TRUE;
1698c2c66affSColin Finck }
1699c2c66affSColin Finck 
1700