advapi32/tests: Test SystemFunction036.
[wine] / dlls / secur32 / tests / main.c
1 /*
2  * Miscellaneous secur32 tests
3  *
4  * Copyright 2005, 2006 Kai Blin
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 #define SECURITY_WIN32
22
23 #include <stdarg.h>
24 #include <stdio.h>
25 #include <assert.h>
26 #include <windef.h>
27 #include <winbase.h>
28 #include <sspi.h>
29
30 #include "wine/test.h"
31
32 static HMODULE secdll;
33 static PSecurityFunctionTableA (SEC_ENTRY * pInitSecurityInterfaceA)(void);
34 static SECURITY_STATUS (SEC_ENTRY * pEnumerateSecurityPackagesA)(PULONG, PSecPkgInfoA*);
35 static SECURITY_STATUS (SEC_ENTRY * pFreeContextBuffer)(PVOID pv);
36 static SECURITY_STATUS (SEC_ENTRY * pQuerySecurityPackageInfoA)(SEC_CHAR*, PSecPkgInfoA*);
37 static SECURITY_STATUS (SEC_ENTRY * pAcquireCredentialsHandleA)(SEC_CHAR*, SEC_CHAR*,
38                             ULONG, PLUID, PVOID, SEC_GET_KEY_FN, PVOID, PCredHandle, PTimeStamp);
39 static SECURITY_STATUS (SEC_ENTRY * pInitializeSecurityContextA)(PCredHandle, PCtxtHandle,
40                             SEC_CHAR*, ULONG, ULONG, ULONG, PSecBufferDesc, ULONG, 
41                             PCtxtHandle, PSecBufferDesc, PULONG, PTimeStamp);
42 static SECURITY_STATUS (SEC_ENTRY * pCompleteAuthToken)(PCtxtHandle, PSecBufferDesc);
43 static SECURITY_STATUS (SEC_ENTRY * pAcceptSecurityContext)(PCredHandle, PCtxtHandle,
44                             PSecBufferDesc, ULONG, ULONG, PCtxtHandle, PSecBufferDesc,
45                             PULONG, PTimeStamp);
46 static SECURITY_STATUS (SEC_ENTRY * pFreeCredentialsHandle)(PCredHandle);
47 static SECURITY_STATUS (SEC_ENTRY * pDeleteSecurityContext)(PCtxtHandle);
48 static SECURITY_STATUS (SEC_ENTRY * pQueryContextAttributesA)(PCtxtHandle, ULONG, PVOID);
49
50 static void InitFunctionPtrs(void)
51 {
52     secdll = LoadLibraryA("secur32.dll");
53     if(!secdll)
54         secdll = LoadLibraryA("security.dll");
55     if(secdll)
56     {
57         pInitSecurityInterfaceA = (PVOID)GetProcAddress(secdll, "InitSecurityInterfaceA");
58         pEnumerateSecurityPackagesA = (PVOID)GetProcAddress(secdll, "EnumerateSecurityPackagesA");
59         pFreeContextBuffer = (PVOID)GetProcAddress(secdll, "FreeContextBuffer");
60         pQuerySecurityPackageInfoA = (PVOID)GetProcAddress(secdll, "QuerySecurityPackageInfoA");
61         pAcquireCredentialsHandleA = (PVOID)GetProcAddress(secdll, "AcquireCredentialsHandleA");
62         pInitializeSecurityContextA = (PVOID)GetProcAddress(secdll, "InitializeSecurityContextA");
63         pCompleteAuthToken = (PVOID)GetProcAddress(secdll, "CompleteAuthToken");
64         pAcceptSecurityContext = (PVOID)GetProcAddress(secdll, "AcceptSecurityContext");
65         pFreeCredentialsHandle = (PVOID)GetProcAddress(secdll, "FreeCredentialsHandle");
66         pDeleteSecurityContext = (PVOID)GetProcAddress(secdll, "DeleteSecurityContext");
67         pQueryContextAttributesA = (PVOID)GetProcAddress(secdll, "QueryContextAttributesA");
68     }
69 }
70
71 /*---------------------------------------------------------*/
72 /* General helper functions */
73
74 static const char* getSecError(SECURITY_STATUS status)
75 {
76     static char buf[20];
77
78 #define _SEC_ERR(x) case (x): return #x;
79     switch(status)
80     {
81         _SEC_ERR(SEC_E_OK);
82         _SEC_ERR(SEC_E_INSUFFICIENT_MEMORY);
83         _SEC_ERR(SEC_E_INVALID_HANDLE);
84         _SEC_ERR(SEC_E_UNSUPPORTED_FUNCTION);
85         _SEC_ERR(SEC_E_TARGET_UNKNOWN);
86         _SEC_ERR(SEC_E_INTERNAL_ERROR);
87         _SEC_ERR(SEC_E_SECPKG_NOT_FOUND);
88         _SEC_ERR(SEC_E_NOT_OWNER);
89         _SEC_ERR(SEC_E_CANNOT_INSTALL);
90         _SEC_ERR(SEC_E_INVALID_TOKEN);
91         _SEC_ERR(SEC_E_CANNOT_PACK);
92         _SEC_ERR(SEC_E_QOP_NOT_SUPPORTED);
93         _SEC_ERR(SEC_E_NO_IMPERSONATION);
94         _SEC_ERR(SEC_I_CONTINUE_NEEDED);
95         _SEC_ERR(SEC_E_BUFFER_TOO_SMALL);
96         _SEC_ERR(SEC_E_ILLEGAL_MESSAGE);
97         _SEC_ERR(SEC_E_LOGON_DENIED);
98         _SEC_ERR(SEC_E_NO_CREDENTIALS);
99         _SEC_ERR(SEC_E_OUT_OF_SEQUENCE);
100         default:
101             sprintf(buf, "%08x\n", status);
102             return buf;
103     }
104 #undef _SEC_ERR
105 }
106
107 /*---------------------------------------------------------*/
108 /* Helper for testQuerySecurityPagageInfo */
109
110 static SECURITY_STATUS setupPackageA(SEC_CHAR *p_package_name, 
111         PSecPkgInfo *p_pkg_info)
112 {
113     SECURITY_STATUS ret;
114     
115     ret = pQuerySecurityPackageInfoA( p_package_name, p_pkg_info);
116     return ret;
117 }
118
119 /*--------------------------------------------------------- */
120 /* The test functions */
121
122 static void testInitSecurityInterface(void)
123 {
124     PSecurityFunctionTable sec_fun_table = NULL;
125
126     sec_fun_table = pInitSecurityInterfaceA();
127     ok(sec_fun_table != NULL, "InitSecurityInterface() returned NULL.\n");
128
129 }
130
131 static void testEnumerateSecurityPackages(void)
132 {
133
134     SECURITY_STATUS sec_status;
135     ULONG           num_packages, i;
136     PSecPkgInfo     pkg_info = NULL;
137
138     trace("Running testEnumerateSecurityPackages\n");
139     
140     sec_status = pEnumerateSecurityPackagesA(&num_packages, &pkg_info);
141
142     ok(sec_status == SEC_E_OK, 
143             "EnumerateSecurityPackages() should return %d, not %08x\n",
144             SEC_E_OK, sec_status);
145
146     if (num_packages == 0)
147     {
148         todo_wine
149         ok(num_packages > 0, "Number of sec packages should be > 0 ,but is %d\n",
150                 num_packages);
151         skip("no sec packages to check\n");
152         return;
153     }
154     else
155         ok(num_packages > 0, "Number of sec packages should be > 0 ,but is %d\n",
156                 num_packages);
157
158     ok(pkg_info != NULL, 
159             "pkg_info should not be NULL after EnumerateSecurityPackages\n");
160     
161     trace("Number of packages: %d\n", num_packages);
162     for(i = 0; i < num_packages; ++i){
163         trace("%d: Package \"%s\"\n", i, pkg_info[i].Name);
164         trace("Supported flags:\n");
165         if(pkg_info[i].fCapabilities & SECPKG_FLAG_INTEGRITY)
166             trace("\tSECPKG_FLAG_INTEGRITY\n");
167         if(pkg_info[i].fCapabilities & SECPKG_FLAG_PRIVACY)
168             trace("\tSECPKG_FLAG_PRIVACY\n");
169         if(pkg_info[i].fCapabilities & SECPKG_FLAG_TOKEN_ONLY)
170             trace("\tSECPKG_FLAG_TOKEN_ONLY\n");
171         if(pkg_info[i].fCapabilities & SECPKG_FLAG_DATAGRAM)
172             trace("\tSECPKG_FLAG_DATAGRAM\n");
173         if(pkg_info[i].fCapabilities & SECPKG_FLAG_CONNECTION)
174             trace("\tSECPKG_FLAG_CONNECTION\n");
175         if(pkg_info[i].fCapabilities & SECPKG_FLAG_MULTI_REQUIRED)
176             trace("\tSECPKG_FLAG_MULTI_REQUIRED\n");
177         if(pkg_info[i].fCapabilities & SECPKG_FLAG_CLIENT_ONLY)
178             trace("\tSECPKG_FLAG_CLIENT_ONLY\n");
179         if(pkg_info[i].fCapabilities & SECPKG_FLAG_EXTENDED_ERROR)
180             trace("\tSECPKG_FLAG_EXTENDED_ERROR\n");
181         if(pkg_info[i].fCapabilities & SECPKG_FLAG_IMPERSONATION)
182             trace("\tSECPKG_FLAG_IMPERSONATION\n");
183         if(pkg_info[i].fCapabilities & SECPKG_FLAG_ACCEPT_WIN32_NAME)
184             trace("\tSECPKG_FLAG_ACCEPT_WIN32_NAME\n");
185         if(pkg_info[i].fCapabilities & SECPKG_FLAG_STREAM)
186             trace("\tSECPKG_FLAG_STREAM\n");
187         if(pkg_info[i].fCapabilities & SECPKG_FLAG_READONLY_WITH_CHECKSUM)
188             trace("\tSECPKG_FLAG_READONLY_WITH_CHECKSUM\n");
189         trace("Comment: %s\n", pkg_info[i].Comment);
190         trace("\n");
191     }
192
193     pFreeContextBuffer(pkg_info);
194 }
195
196
197 static void testQuerySecurityPackageInfo(void)
198 {
199     SECURITY_STATUS     sec_status;
200     PSecPkgInfo         pkg_info;
201     static SEC_CHAR     ntlm[]     = "NTLM",
202                         winetest[] = "Winetest";
203
204     trace("Running testQuerySecurityPackageInfo\n");
205
206     /* Test with an existing package. Test should pass */
207
208     pkg_info = (void *)0xdeadbeef;
209     sec_status = setupPackageA(ntlm, &pkg_info);
210
211     ok((sec_status == SEC_E_OK) || (sec_status == SEC_E_SECPKG_NOT_FOUND) ||
212        broken(sec_status == SEC_E_UNSUPPORTED_FUNCTION), /* win95 */
213        "Return value of QuerySecurityPackageInfo() shouldn't be %s\n",
214        getSecError(sec_status) );
215
216     if (sec_status == SEC_E_OK)
217     {
218         ok(pkg_info != (void *)0xdeadbeef, "wrong pkg_info address %p\n", pkg_info);
219         ok(pkg_info->wVersion == 1, "wVersion always should be 1, but is %d\n", pkg_info->wVersion);
220         /* there is no point in testing pkg_info->cbMaxToken since it varies
221          * between implementations.
222          */
223
224         sec_status = pFreeContextBuffer(pkg_info);
225         ok( sec_status == SEC_E_OK,
226             "Return value of FreeContextBuffer() shouldn't be %s\n",
227             getSecError(sec_status) );
228     }
229
230     /* Test with a nonexistent package, test should fail */
231
232     pkg_info = (void *)0xdeadbeef;
233     sec_status = pQuerySecurityPackageInfoA(winetest, &pkg_info);
234
235     ok( sec_status == SEC_E_SECPKG_NOT_FOUND,
236         "Return value of QuerySecurityPackageInfo() should be %s for a nonexistent package\n",
237         getSecError(SEC_E_SECPKG_NOT_FOUND));
238
239     ok(pkg_info == (void *)0xdeadbeef, "wrong pkg_info address %p\n", pkg_info);
240 }
241
242 START_TEST(main)
243 {
244     InitFunctionPtrs();
245     if(pInitSecurityInterfaceA)
246         testInitSecurityInterface();
247     if(pFreeContextBuffer)
248     {
249         if(pEnumerateSecurityPackagesA)
250             testEnumerateSecurityPackages();
251         if(pQuerySecurityPackageInfoA)
252         {
253             testQuerySecurityPackageInfo();
254         }
255     }
256     if(secdll)
257         FreeLibrary(secdll);
258 }