xref: /reactos/dll/win32/wbemprox/security.c (revision c2c66aff)
1 /*
2  * __SystemSecurity implementation
3  *
4  * Copyright 2014 Vincent Povirk for CodeWeavers
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19  */
20 
21 #include "wbemprox_private.h"
22 
23 #include <iads.h>
24 
25 static HRESULT to_byte_array( void *data, DWORD size, VARIANT *var )
26 {
27     SAFEARRAY *sa;
28     void *sadata;
29     HRESULT hr;
30 
31     if (!(sa = SafeArrayCreateVector( VT_UI1, 0, size ))) return E_OUTOFMEMORY;
32 
33     hr = SafeArrayAccessData( sa, &sadata );
34 
35     if (SUCCEEDED(hr))
36     {
37         memcpy( sadata, data, size );
38 
39         SafeArrayUnaccessData( sa );
40     }
41     else
42     {
43         SafeArrayDestroy( sa );
44         return hr;
45     }
46 
47     set_variant( VT_UI1|VT_ARRAY, 0, sa, var );
48     return S_OK;
49 }
50 
51 static HRESULT get_sd( SECURITY_DESCRIPTOR **sd, DWORD *size )
52 {
53     BYTE sid_admin_buffer[SECURITY_MAX_SID_SIZE];
54     SID *sid_admin = (SID*)sid_admin_buffer;
55     BYTE sid_network_buffer[SECURITY_MAX_SID_SIZE];
56     SID *sid_network = (SID*)sid_network_buffer;
57     BYTE sid_local_buffer[SECURITY_MAX_SID_SIZE];
58     SID *sid_local = (SID*)sid_local_buffer;
59     BYTE sid_users_buffer[SECURITY_MAX_SID_SIZE];
60     SID *sid_users = (SID*)sid_users_buffer;
61     BYTE acl_buffer[sizeof(ACL) + 4 * (sizeof(ACCESS_ALLOWED_ACE) - sizeof(DWORD) + SECURITY_MAX_SID_SIZE)];
62     ACL *acl = (ACL*)acl_buffer;
63     DWORD sid_size;
64     SECURITY_DESCRIPTOR absolute_sd;
65     HRESULT hr = S_OK;
66 
67     sid_size = sizeof(sid_admin_buffer);
68     CreateWellKnownSid( WinBuiltinAdministratorsSid, NULL, sid_admin, &sid_size );
69 
70     sid_size = sizeof(sid_network_buffer);
71     CreateWellKnownSid( WinNetworkServiceSid, NULL, sid_network, &sid_size );
72 
73     sid_size = sizeof(sid_local_buffer);
74     CreateWellKnownSid( WinLocalServiceSid, NULL, sid_local, &sid_size );
75 
76     sid_size = sizeof(sid_users_buffer);
77     CreateWellKnownSid( WinAuthenticatedUserSid, NULL, sid_users, &sid_size );
78 
79     InitializeAcl( acl, sizeof(acl_buffer), ACL_REVISION );
80 
81     AddAccessAllowedAceEx( acl, ACL_REVISION, CONTAINER_INHERIT_ACE|INHERITED_ACE,
82         ADS_RIGHT_DS_CREATE_CHILD|ADS_RIGHT_DS_DELETE_CHILD|ADS_RIGHT_ACTRL_DS_LIST|ADS_RIGHT_DS_SELF|
83         ADS_RIGHT_DS_READ_PROP|ADS_RIGHT_DS_WRITE_PROP|READ_CONTROL|WRITE_DAC,
84         sid_admin );
85 
86     AddAccessAllowedAceEx( acl, ACL_REVISION, CONTAINER_INHERIT_ACE|INHERITED_ACE,
87         ADS_RIGHT_DS_CREATE_CHILD|ADS_RIGHT_DS_DELETE_CHILD|ADS_RIGHT_DS_READ_PROP,
88         sid_network );
89 
90     AddAccessAllowedAceEx( acl, ACL_REVISION, CONTAINER_INHERIT_ACE|INHERITED_ACE,
91         ADS_RIGHT_DS_CREATE_CHILD|ADS_RIGHT_DS_DELETE_CHILD|ADS_RIGHT_DS_READ_PROP,
92         sid_local );
93 
94     AddAccessAllowedAceEx( acl, ACL_REVISION, CONTAINER_INHERIT_ACE|INHERITED_ACE,
95         ADS_RIGHT_DS_CREATE_CHILD|ADS_RIGHT_DS_DELETE_CHILD|ADS_RIGHT_DS_READ_PROP,
96         sid_users );
97 
98     InitializeSecurityDescriptor( &absolute_sd, SECURITY_DESCRIPTOR_REVISION );
99 
100     SetSecurityDescriptorOwner( &absolute_sd, sid_admin, TRUE );
101     SetSecurityDescriptorGroup( &absolute_sd, sid_admin, TRUE );
102     SetSecurityDescriptorDacl( &absolute_sd, TRUE, acl, TRUE );
103 
104     *size = GetSecurityDescriptorLength( &absolute_sd );
105 
106     *sd = HeapAlloc( GetProcessHeap(), 0, *size );
107     if (!*sd)
108         hr = E_OUTOFMEMORY;
109 
110     if (SUCCEEDED(hr))
111     {
112         if (!MakeSelfRelativeSD(&absolute_sd, *sd, size)) {
113             HeapFree( GetProcessHeap(), 0, *sd );
114 	    *sd = NULL;
115             hr = E_FAIL;
116         }
117     }
118 
119     return hr;
120 }
121 
122 HRESULT security_get_sd( IWbemClassObject *obj, IWbemClassObject *in, IWbemClassObject **out )
123 {
124     VARIANT var_sd, retval;
125     IWbemClassObject *sig, *out_params = NULL;
126     HRESULT hr, ret;
127     SECURITY_DESCRIPTOR *sd;
128     DWORD sd_size;
129 
130     TRACE("%p, %p\n", in, out);
131 
132     hr = create_signature( class_systemsecurityW, method_getsdW, PARAM_OUT, &sig );
133 
134     if (SUCCEEDED(hr))
135     {
136         hr = IWbemClassObject_SpawnInstance( sig, 0, &out_params );
137 
138         IWbemClassObject_Release( sig );
139     }
140 
141     if (SUCCEEDED(hr))
142     {
143         ret = get_sd( &sd, &sd_size );
144 
145         if (SUCCEEDED(ret))
146         {
147             VariantInit( &var_sd );
148 
149             hr = to_byte_array( sd, sd_size, &var_sd );
150 
151             if (SUCCEEDED(hr))
152                 hr = IWbemClassObject_Put( out_params, param_sdW, 0, &var_sd, CIM_UINT8|CIM_FLAG_ARRAY );
153 
154             HeapFree( GetProcessHeap(), 0, sd );
155             VariantClear( &var_sd );
156         }
157 
158         if (SUCCEEDED(hr))
159         {
160             set_variant( VT_UI4, ret, NULL, &retval );
161             hr = IWbemClassObject_Put( out_params, param_returnvalueW, 0, &retval, CIM_UINT32 );
162         }
163 
164         if (SUCCEEDED(hr) && out)
165         {
166             *out = out_params;
167             IWbemClassObject_AddRef( out_params );
168         }
169 
170         IWbemClassObject_Release( out_params );
171     }
172 
173     return hr;
174 }
175 
176 
177 HRESULT security_set_sd( IWbemClassObject *obj, IWbemClassObject *in, IWbemClassObject **out )
178 {
179     VARIANT retval;
180     IWbemClassObject *sig, *out_params = NULL;
181     HRESULT hr;
182 
183     FIXME("stub\n");
184 
185     hr = create_signature( class_systemsecurityW, method_setsdW, PARAM_OUT, &sig );
186 
187     if (SUCCEEDED(hr))
188     {
189         hr = IWbemClassObject_SpawnInstance( sig, 0, &out_params );
190 
191         IWbemClassObject_Release( sig );
192     }
193 
194     if (SUCCEEDED(hr))
195     {
196         set_variant( VT_UI4, S_OK, NULL, &retval );
197         hr = IWbemClassObject_Put( out_params, param_returnvalueW, 0, &retval, CIM_UINT32 );
198 
199         if (SUCCEEDED(hr) && out)
200         {
201             *out = out_params;
202             IWbemClassObject_AddRef( out_params );
203         }
204 
205         IWbemClassObject_Release( out_params );
206     }
207 
208     return hr;
209 }
210