dmsynth: Add stubbed IKsControl interface to DirectMusicSynth object.
[wine] / dlls / schannel / tests / main.c
1 /*
2  * Schannel tests
3  *
4  * Copyright 2006 Yuval Fledel
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 <stdio.h>
22 #include <stdarg.h>
23 #include "ntstatus.h"
24 #define WIN32_NO_STATUS
25 #include <windef.h>
26 #include <winbase.h>
27 #define SECURITY_WIN32
28 #include <security.h>
29 #include <schannel.h>
30 #include <ntsecapi.h>
31 #include <ntsecpkg.h>
32
33 #include "wine/test.h"
34
35 /* Helper macros to find the size of SECPKG_FUNCTION_TABLE */
36 #define SECPKG_FUNCTION_TABLE_SIZE_1 FIELD_OFFSET(SECPKG_FUNCTION_TABLE, \
37     SetContextAttributes)
38 #define SECPKG_FUNCTION_TABLE_SIZE_2 FIELD_OFFSET(SECPKG_FUNCTION_TABLE, \
39     SetCredentialsAttributes)
40 #define SECPKG_FUNCTION_TABLE_SIZE_3 FIELD_OFFSET(SECPKG_FUNCTION_TABLE, \
41     ChangeAccountPassword)
42 #define SECPKG_FUNCTION_TABLE_SIZE_4 FIELD_OFFSET(SECPKG_FUNCTION_TABLE, \
43     QueryMetaData)
44 #define SECPKG_FUNCTION_TABLE_SIZE_5 FIELD_OFFSET(SECPKG_FUNCTION_TABLE, \
45     ValidateTargetInfo)
46 #define SECPKG_FUNCTION_TABLE_SIZE_6 sizeof(SECPKG_FUNCTION_TABLE)
47
48 static NTSTATUS (NTAPI *pSpLsaModeInitialize)(ULONG, PULONG,
49     PSECPKG_FUNCTION_TABLE*, PULONG);
50 static NTSTATUS (NTAPI *pSpUserModeInitialize)(ULONG, PULONG,
51     PSECPKG_USER_FUNCTION_TABLE*, PULONG);
52
53 static void testInitialize(void)
54 {
55     PSECPKG_USER_FUNCTION_TABLE pUserTables, pUserTables2;
56     PSECPKG_FUNCTION_TABLE pTables, pTables2;
57     ULONG cTables = 0, cUserTables = 0, Version = 0;
58     NTSTATUS status;
59
60     /* Passing NULL into one of the parameters of SpLsaModeInitialize or
61        SpUserModeInitialize causes a crash. */
62
63     /* SpLsaModeInitialize does not care about the LSA version. */
64     status = pSpLsaModeInitialize(0, &Version, &pTables2, &cTables);
65     ok(status == STATUS_SUCCESS, "status: 0x%x\n", status);
66     ok(cTables == 2 ||
67        broken(cTables == 1), /* Win2k */
68        "cTables: %d\n", cTables);
69     ok(pTables2 != NULL,"pTables: %p\n", pTables2);
70
71     /* We can call it as many times we want. */
72     status = pSpLsaModeInitialize(0x10000, &Version, &pTables, &cTables);
73     ok(status == STATUS_SUCCESS, "status: 0x%x\n", status);
74     ok(cTables == 2 ||
75        broken(cTables == 1), /* Win2k */
76        "cTables: %d\n", cTables);
77     ok(pTables != NULL, "pTables: %p\n", pTables);
78     /* It will always return the same pointer. */
79     ok(pTables == pTables2, "pTables: %p, pTables2: %p\n", pTables, pTables2);
80
81     status = pSpLsaModeInitialize(0x23456, &Version, &pTables, &cTables);
82     ok(status == STATUS_SUCCESS, "status: 0x%x\n", status);
83     ok(cTables == 2 ||
84        broken(cTables == 1), /* Win2k */
85        "cTables: %d\n", cTables);
86     ok(pTables != NULL, "pTables: %p\n", pTables);
87     ok(pTables == pTables2, "pTables: %p, pTables2: %p\n", pTables, pTables2);
88
89     /* Bad versions to SpUserModeInitialize. Parameters unchanged */
90     Version = 0xdead;
91     cUserTables = 0xdead;
92     pUserTables = NULL;
93     status = pSpUserModeInitialize(0, &Version, &pUserTables, &cUserTables);
94     ok(status == STATUS_INVALID_PARAMETER, "status: 0x%x\n", status);
95     ok(Version == 0xdead, "Version: 0x%x\n", Version);
96     ok(cUserTables == 0xdead, "cTables: %d\n", cUserTables);
97     ok(pUserTables == NULL, "pUserTables: %p\n", pUserTables);
98
99     status = pSpUserModeInitialize(0x20000, &Version, &pUserTables,
100                                    &cUserTables);
101     ok(status == STATUS_INVALID_PARAMETER, "status: 0x%x\n", status);
102     ok(Version == 0xdead, "Version: 0x%x\n", Version);
103     ok(cUserTables == 0xdead, "cTables: %d\n", cUserTables);
104     ok(pUserTables == NULL, "pUserTables: %p\n", pUserTables);
105
106     /* Good version to SpUserModeInitialize */
107     status = pSpUserModeInitialize(SECPKG_INTERFACE_VERSION, &Version,
108                                    &pUserTables, &cUserTables);
109     ok(status == STATUS_SUCCESS, "status: 0x%x\n", status);
110     ok(Version == SECPKG_INTERFACE_VERSION, "Version: 0x%x\n", Version);
111     ok(cUserTables == 2 ||
112        broken(cUserTables == 4), /* Win2k */
113        "cUserTables: %d\n", cUserTables);
114     ok(pUserTables != NULL, "pUserTables: %p\n", pUserTables);
115
116     /* Initializing user again */
117     status = pSpUserModeInitialize(SECPKG_INTERFACE_VERSION, &Version,
118                                    &pUserTables2, &cTables);
119     ok(status == STATUS_SUCCESS, "status: 0x%x\n", status);
120     ok(pUserTables == pUserTables2, "pUserTables: %p, pUserTables2: %p\n",
121        pUserTables, pUserTables2);
122 }
123
124 /* A helper function to find the dispatch table of the next package.
125    Needed because SECPKG_FUNCTION_TABLE's size depend on the version */
126 static PSECPKG_FUNCTION_TABLE getNextSecPkgTable(PSECPKG_FUNCTION_TABLE pTable,
127                                                  ULONG Version)
128 {
129     size_t size;
130     PSECPKG_FUNCTION_TABLE pNextTable;
131
132     if (Version == SECPKG_INTERFACE_VERSION)
133         size = SECPKG_FUNCTION_TABLE_SIZE_1;
134     else if (Version == SECPKG_INTERFACE_VERSION_2)
135         size = SECPKG_FUNCTION_TABLE_SIZE_2;
136     else if (Version == SECPKG_INTERFACE_VERSION_3)
137         size = SECPKG_FUNCTION_TABLE_SIZE_3;
138     else if (Version == SECPKG_INTERFACE_VERSION_4)
139         size = SECPKG_FUNCTION_TABLE_SIZE_4;
140     else if (Version == SECPKG_INTERFACE_VERSION_5)
141         size = SECPKG_FUNCTION_TABLE_SIZE_5;
142     else if (Version == SECPKG_INTERFACE_VERSION_6)
143         size = SECPKG_FUNCTION_TABLE_SIZE_6;
144     else {
145         ok(FALSE, "Unknown package version 0x%x\n", Version);
146         return NULL;
147     }
148
149     pNextTable = (PSECPKG_FUNCTION_TABLE)((PBYTE)pTable + size);
150     /* Win7 function tables appear to be SECPKG_INTERFACE_VERSION_6 format,
151        but unfortunately SpLsaModeInitialize returns SECPKG_INTERFACE_VERSION_3.
152        We detect that by comparing the "Initialize" pointer from the old table
153        to the "FreeCredentialsHandle" pointer of the new table. These functions
154        have different numbers of arguments, so they can't possibly point to the
155        same implementation */
156     if (broken((void *) pTable->Initialize == (void *) pNextTable->FreeCredentialsHandle &&
157                pNextTable->FreeCredentialsHandle != NULL))
158     {
159         win_skip("Invalid function pointers for next package\n");
160         return NULL;
161     }
162
163     return pNextTable;
164 }
165
166 static void testGetInfo(void)
167 {
168     PSECPKG_FUNCTION_TABLE pTables;
169     SecPkgInfoW PackageInfo;
170     ULONG cTables, Version;
171     NTSTATUS status;
172
173     /* Get the dispatch table */
174     status = pSpLsaModeInitialize(0, &Version, &pTables, &cTables);
175     ok(status == STATUS_SUCCESS, "status: 0x%x\n", status);
176
177     /* Passing NULL into ->GetInfo causes a crash. */
178
179     /* First package: Unified */
180     status = pTables->GetInfo(&PackageInfo);
181     ok(status == STATUS_SUCCESS, "status: 0x%x\n", status);
182     ok(PackageInfo.fCapabilities == 0x107b3, "fCapabilities: 0x%x\n",
183        PackageInfo.fCapabilities);
184     ok(PackageInfo.wVersion == 1, "wVersion: %d\n", PackageInfo.wVersion);
185     ok(PackageInfo.wRPCID == 14, "wRPCID: %d\n", PackageInfo.wRPCID);
186     ok(PackageInfo.cbMaxToken == 0x4000 ||
187        PackageInfo.cbMaxToken == 0x6000, /* Vista */
188        "cbMaxToken: 0x%x\n",
189        PackageInfo.cbMaxToken);
190
191     /* Second package */
192     if (cTables == 1)
193     {
194         win_skip("Second package missing\n");
195         return;
196     }
197     pTables = getNextSecPkgTable(pTables, Version);
198     if (!pTables)
199         return;
200     status = pTables->GetInfo(&PackageInfo);
201     ok(status == STATUS_SUCCESS ||
202        status == SEC_E_UNSUPPORTED_FUNCTION, /* win2k3 */
203        "status: 0x%x\n", status);
204
205     if (status == STATUS_SUCCESS)
206     {
207         ok(PackageInfo.fCapabilities == 0x107b3, "fCapabilities: 0x%x\n",
208            PackageInfo.fCapabilities);
209         ok(PackageInfo.wVersion == 1, "wVersion: %d\n", PackageInfo.wVersion);
210         ok(PackageInfo.wRPCID == 14, "wRPCID: %d\n", PackageInfo.wRPCID);
211         ok(PackageInfo.cbMaxToken == 0x4000 ||
212            PackageInfo.cbMaxToken == 0x6000, /* Win7 */
213            "cbMaxToken: 0x%x\n",
214            PackageInfo.cbMaxToken);
215     }
216 }
217
218 START_TEST(main)
219 {
220     HMODULE hMod = LoadLibraryA("schannel.dll");
221     if (!hMod) {
222         win_skip("schannel.dll not available\n");
223         return;
224     }
225
226     pSpLsaModeInitialize  = (void *)GetProcAddress(hMod, "SpLsaModeInitialize");
227     pSpUserModeInitialize = (void *)GetProcAddress(hMod, "SpUserModeInitialize");
228
229     if (pSpLsaModeInitialize && pSpUserModeInitialize)
230     {
231         testInitialize();
232         testGetInfo();
233     }
234     else win_skip( "schannel functions not found\n" );
235
236     FreeLibrary(hMod);
237 }