Commit | Line | Data |
---|---|---|
986b33d1 RS |
1 | /* |
2 | * MSXML3 self-registerable dll functions | |
3 | * | |
4 | * Copyright (C) 2003 John K. Hohm | |
5 | * Copyright (C) 2006 Robert Shearman | |
a1cce928 | 6 | * Copyright (C) 2008 Alistair Leslie-Hughes |
986b33d1 RS |
7 | * |
8 | * This library is free software; you can redistribute it and/or | |
9 | * modify it under the terms of the GNU Lesser General Public | |
10 | * License as published by the Free Software Foundation; either | |
11 | * version 2.1 of the License, or (at your option) any later version. | |
12 | * | |
13 | * This library is distributed in the hope that it will be useful, | |
14 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
16 | * Lesser General Public License for more details. | |
17 | * | |
18 | * You should have received a copy of the GNU Lesser General Public | |
19 | * License along with this library; if not, write to the Free Software | |
20 | * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA | |
21 | */ | |
22 | ||
45e8e360 BJY |
23 | #include "config.h" |
24 | ||
986b33d1 RS |
25 | #include <stdarg.h> |
26 | #include <string.h> | |
27 | ||
a1cce928 ALH |
28 | #define COBJMACROS |
29 | ||
986b33d1 RS |
30 | #include "windef.h" |
31 | #include "winbase.h" | |
32 | #include "winuser.h" | |
33 | #include "winreg.h" | |
34 | #include "winerror.h" | |
35 | #include "ole2.h" | |
36 | #include "msxml.h" | |
37 | #include "xmldom.h" | |
38 | #include "xmldso.h" | |
46964179 HD |
39 | #include "msxml2.h" |
40 | ||
41 | /* undef the #define in msxml2 so that we can access the v.2 version | |
42 | independent CLSID as well as the v.3 one. */ | |
43 | #undef CLSID_DOMDocument | |
986b33d1 RS |
44 | |
45 | #include "msxml_private.h" | |
46 | ||
47 | #include "wine/debug.h" | |
8bd9a3aa | 48 | #include "wine/unicode.h" |
986b33d1 | 49 | |
d3aacce6 | 50 | WINE_DEFAULT_DEBUG_CHANNEL(msxml); |
986b33d1 RS |
51 | |
52 | /* | |
53 | * Near the bottom of this file are the exported DllRegisterServer and | |
54 | * DllUnregisterServer, which make all this worthwhile. | |
55 | */ | |
56 | ||
57 | /*********************************************************************** | |
58 | * interface for self-registering | |
59 | */ | |
60 | struct regsvr_interface | |
61 | { | |
62 | IID const *iid; /* NULL for end of list */ | |
63 | LPCSTR name; /* can be NULL to omit */ | |
64 | IID const *base_iid; /* can be NULL to omit */ | |
65 | int num_methods; /* can be <0 to omit */ | |
66 | CLSID const *ps_clsid; /* can be NULL to omit */ | |
67 | CLSID const *ps_clsid32; /* can be NULL to omit */ | |
68 | }; | |
69 | ||
70 | static HRESULT register_interfaces(struct regsvr_interface const *list); | |
71 | static HRESULT unregister_interfaces(struct regsvr_interface const *list); | |
72 | ||
73 | struct regsvr_coclass | |
74 | { | |
75 | CLSID const *clsid; /* NULL for end of list */ | |
76 | LPCSTR name; /* can be NULL to omit */ | |
77 | LPCSTR ips; /* can be NULL to omit */ | |
78 | LPCSTR ips32; /* can be NULL to omit */ | |
79 | LPCSTR ips32_tmodel; /* can be NULL to omit */ | |
986b33d1 | 80 | LPCSTR progid; /* can be NULL to omit */ |
1933135f | 81 | LPCSTR version; /* can be NULL to omit */ |
986b33d1 RS |
82 | }; |
83 | ||
84 | static HRESULT register_coclasses(struct regsvr_coclass const *list); | |
85 | static HRESULT unregister_coclasses(struct regsvr_coclass const *list); | |
86 | ||
1933135f RS |
87 | struct progid |
88 | { | |
89 | LPCSTR name; /* NULL for end of list */ | |
90 | LPCSTR description; /* can be NULL to omit */ | |
91 | CLSID const *clsid; | |
92 | LPCSTR curver; /* can be NULL to omit */ | |
93 | }; | |
94 | ||
95 | static HRESULT register_progids(struct progid const *list); | |
96 | static HRESULT unregister_progids(struct progid const *list); | |
97 | ||
986b33d1 RS |
98 | /*********************************************************************** |
99 | * static string constants | |
100 | */ | |
101 | static WCHAR const interface_keyname[10] = { | |
102 | 'I', 'n', 't', 'e', 'r', 'f', 'a', 'c', 'e', 0 }; | |
103 | static WCHAR const base_ifa_keyname[14] = { | |
104 | 'B', 'a', 's', 'e', 'I', 'n', 't', 'e', 'r', 'f', 'a', 'c', | |
105 | 'e', 0 }; | |
106 | static WCHAR const num_methods_keyname[11] = { | |
107 | 'N', 'u', 'm', 'M', 'e', 't', 'h', 'o', 'd', 's', 0 }; | |
108 | static WCHAR const ps_clsid_keyname[15] = { | |
109 | 'P', 'r', 'o', 'x', 'y', 'S', 't', 'u', 'b', 'C', 'l', 's', | |
110 | 'i', 'd', 0 }; | |
111 | static WCHAR const ps_clsid32_keyname[17] = { | |
112 | 'P', 'r', 'o', 'x', 'y', 'S', 't', 'u', 'b', 'C', 'l', 's', | |
113 | 'i', 'd', '3', '2', 0 }; | |
114 | static WCHAR const clsid_keyname[6] = { | |
115 | 'C', 'L', 'S', 'I', 'D', 0 }; | |
116 | static WCHAR const ips_keyname[13] = { | |
117 | 'I', 'n', 'P', 'r', 'o', 'c', 'S', 'e', 'r', 'v', 'e', 'r', | |
118 | 0 }; | |
119 | static WCHAR const ips32_keyname[15] = { | |
120 | 'I', 'n', 'P', 'r', 'o', 'c', 'S', 'e', 'r', 'v', 'e', 'r', | |
121 | '3', '2', 0 }; | |
122 | static WCHAR const progid_keyname[7] = { | |
123 | 'P', 'r', 'o', 'g', 'I', 'D', 0 }; | |
1933135f RS |
124 | static WCHAR const versionindependentprogid_keyname[] = { |
125 | 'V', 'e', 'r', 's', 'i', 'o', 'n', | |
126 | 'I', 'n', 'd', 'e', 'p', 'e', 'n', 'd', 'e', 'n', 't', | |
127 | 'P', 'r', 'o', 'g', 'I', 'D', 0 }; | |
128 | static WCHAR const version_keyname[] = { | |
129 | 'V', 'e', 'r', 's', 'i', 'o', 'n', 0 }; | |
130 | static WCHAR const curver_keyname[] = { | |
131 | 'C', 'u', 'r', 'V', 'e', 'r', 0 }; | |
986b33d1 RS |
132 | static char const tmodel_valuename[] = "ThreadingModel"; |
133 | ||
134 | /*********************************************************************** | |
135 | * static helper functions | |
136 | */ | |
137 | static LONG register_key_guid(HKEY base, WCHAR const *name, GUID const *guid); | |
138 | static LONG register_key_defvalueW(HKEY base, WCHAR const *name, | |
139 | WCHAR const *value); | |
140 | static LONG register_key_defvalueA(HKEY base, WCHAR const *name, | |
141 | char const *value); | |
986b33d1 RS |
142 | |
143 | /*********************************************************************** | |
144 | * register_interfaces | |
145 | */ | |
146 | static HRESULT register_interfaces(struct regsvr_interface const *list) | |
147 | { | |
148 | LONG res = ERROR_SUCCESS; | |
149 | HKEY interface_key; | |
150 | ||
151 | res = RegCreateKeyExW(HKEY_CLASSES_ROOT, interface_keyname, 0, NULL, 0, | |
152 | KEY_READ | KEY_WRITE, NULL, &interface_key, NULL); | |
153 | if (res != ERROR_SUCCESS) goto error_return; | |
154 | ||
155 | for (; res == ERROR_SUCCESS && list->iid; ++list) { | |
156 | WCHAR buf[39]; | |
157 | HKEY iid_key; | |
158 | ||
159 | StringFromGUID2(list->iid, buf, 39); | |
160 | res = RegCreateKeyExW(interface_key, buf, 0, NULL, 0, | |
161 | KEY_READ | KEY_WRITE, NULL, &iid_key, NULL); | |
162 | if (res != ERROR_SUCCESS) goto error_close_interface_key; | |
163 | ||
164 | if (list->name) { | |
165 | res = RegSetValueExA(iid_key, NULL, 0, REG_SZ, | |
166 | (CONST BYTE*)(list->name), | |
167 | strlen(list->name) + 1); | |
168 | if (res != ERROR_SUCCESS) goto error_close_iid_key; | |
169 | } | |
170 | ||
171 | if (list->base_iid) { | |
172 | res = register_key_guid(iid_key, base_ifa_keyname, list->base_iid); | |
173 | if (res != ERROR_SUCCESS) goto error_close_iid_key; | |
174 | } | |
175 | ||
176 | if (0 <= list->num_methods) { | |
177 | static WCHAR const fmt[3] = { '%', 'd', 0 }; | |
178 | HKEY key; | |
179 | ||
180 | res = RegCreateKeyExW(iid_key, num_methods_keyname, 0, NULL, 0, | |
181 | KEY_READ | KEY_WRITE, NULL, &key, NULL); | |
182 | if (res != ERROR_SUCCESS) goto error_close_iid_key; | |
183 | ||
8bd9a3aa | 184 | sprintfW(buf, fmt, list->num_methods); |
986b33d1 RS |
185 | res = RegSetValueExW(key, NULL, 0, REG_SZ, |
186 | (CONST BYTE*)buf, | |
187 | (lstrlenW(buf) + 1) * sizeof(WCHAR)); | |
188 | RegCloseKey(key); | |
189 | ||
190 | if (res != ERROR_SUCCESS) goto error_close_iid_key; | |
191 | } | |
192 | ||
193 | if (list->ps_clsid) { | |
194 | res = register_key_guid(iid_key, ps_clsid_keyname, list->ps_clsid); | |
195 | if (res != ERROR_SUCCESS) goto error_close_iid_key; | |
196 | } | |
197 | ||
198 | if (list->ps_clsid32) { | |
199 | res = register_key_guid(iid_key, ps_clsid32_keyname, list->ps_clsid32); | |
200 | if (res != ERROR_SUCCESS) goto error_close_iid_key; | |
201 | } | |
202 | ||
203 | error_close_iid_key: | |
204 | RegCloseKey(iid_key); | |
205 | } | |
206 | ||
207 | error_close_interface_key: | |
208 | RegCloseKey(interface_key); | |
209 | error_return: | |
210 | return res != ERROR_SUCCESS ? HRESULT_FROM_WIN32(res) : S_OK; | |
211 | } | |
212 | ||
213 | /*********************************************************************** | |
214 | * unregister_interfaces | |
215 | */ | |
216 | static HRESULT unregister_interfaces(struct regsvr_interface const *list) | |
217 | { | |
218 | LONG res = ERROR_SUCCESS; | |
219 | HKEY interface_key; | |
220 | ||
221 | res = RegOpenKeyExW(HKEY_CLASSES_ROOT, interface_keyname, 0, | |
222 | KEY_READ | KEY_WRITE, &interface_key); | |
223 | if (res == ERROR_FILE_NOT_FOUND) return S_OK; | |
224 | if (res != ERROR_SUCCESS) goto error_return; | |
225 | ||
226 | for (; res == ERROR_SUCCESS && list->iid; ++list) { | |
227 | WCHAR buf[39]; | |
228 | ||
229 | StringFromGUID2(list->iid, buf, 39); | |
5987d3a3 SL |
230 | res = RegDeleteTreeW(interface_key, buf); |
231 | if (res == ERROR_FILE_NOT_FOUND) res = ERROR_SUCCESS; | |
986b33d1 RS |
232 | } |
233 | ||
234 | RegCloseKey(interface_key); | |
235 | error_return: | |
236 | return res != ERROR_SUCCESS ? HRESULT_FROM_WIN32(res) : S_OK; | |
237 | } | |
238 | ||
239 | /*********************************************************************** | |
240 | * register_coclasses | |
241 | */ | |
242 | static HRESULT register_coclasses(struct regsvr_coclass const *list) | |
243 | { | |
244 | LONG res = ERROR_SUCCESS; | |
245 | HKEY coclass_key; | |
246 | ||
247 | res = RegCreateKeyExW(HKEY_CLASSES_ROOT, clsid_keyname, 0, NULL, 0, | |
248 | KEY_READ | KEY_WRITE, NULL, &coclass_key, NULL); | |
249 | if (res != ERROR_SUCCESS) goto error_return; | |
250 | ||
251 | for (; res == ERROR_SUCCESS && list->clsid; ++list) { | |
252 | WCHAR buf[39]; | |
253 | HKEY clsid_key; | |
254 | ||
255 | StringFromGUID2(list->clsid, buf, 39); | |
256 | res = RegCreateKeyExW(coclass_key, buf, 0, NULL, 0, | |
257 | KEY_READ | KEY_WRITE, NULL, &clsid_key, NULL); | |
258 | if (res != ERROR_SUCCESS) goto error_close_coclass_key; | |
259 | ||
260 | if (list->name) { | |
261 | res = RegSetValueExA(clsid_key, NULL, 0, REG_SZ, | |
262 | (CONST BYTE*)(list->name), | |
263 | strlen(list->name) + 1); | |
264 | if (res != ERROR_SUCCESS) goto error_close_clsid_key; | |
265 | } | |
266 | ||
267 | if (list->ips) { | |
268 | res = register_key_defvalueA(clsid_key, ips_keyname, list->ips); | |
269 | if (res != ERROR_SUCCESS) goto error_close_clsid_key; | |
270 | } | |
271 | ||
272 | if (list->ips32) { | |
273 | HKEY ips32_key; | |
274 | ||
275 | res = RegCreateKeyExW(clsid_key, ips32_keyname, 0, NULL, 0, | |
276 | KEY_READ | KEY_WRITE, NULL, | |
277 | &ips32_key, NULL); | |
278 | if (res != ERROR_SUCCESS) goto error_close_clsid_key; | |
279 | ||
280 | res = RegSetValueExA(ips32_key, NULL, 0, REG_SZ, | |
281 | (CONST BYTE*)list->ips32, | |
282 | lstrlenA(list->ips32) + 1); | |
283 | if (res == ERROR_SUCCESS && list->ips32_tmodel) | |
284 | res = RegSetValueExA(ips32_key, tmodel_valuename, 0, REG_SZ, | |
285 | (CONST BYTE*)list->ips32_tmodel, | |
286 | strlen(list->ips32_tmodel) + 1); | |
287 | RegCloseKey(ips32_key); | |
288 | if (res != ERROR_SUCCESS) goto error_close_clsid_key; | |
289 | } | |
290 | ||
986b33d1 | 291 | if (list->progid) { |
1933135f RS |
292 | char *buffer = NULL; |
293 | LPCSTR progid; | |
294 | ||
295 | if (list->version) { | |
296 | buffer = HeapAlloc(GetProcessHeap(), 0, strlen(list->progid) + strlen(list->version) + 2); | |
297 | if (!buffer) { | |
298 | res = ERROR_OUTOFMEMORY; | |
299 | goto error_close_clsid_key; | |
300 | } | |
301 | strcpy(buffer, list->progid); | |
302 | strcat(buffer, "."); | |
303 | strcat(buffer, list->version); | |
304 | progid = buffer; | |
305 | } else | |
306 | progid = list->progid; | |
986b33d1 | 307 | res = register_key_defvalueA(clsid_key, progid_keyname, |
1933135f RS |
308 | progid); |
309 | HeapFree(GetProcessHeap(), 0, buffer); | |
986b33d1 RS |
310 | if (res != ERROR_SUCCESS) goto error_close_clsid_key; |
311 | ||
1933135f RS |
312 | if (list->version) { |
313 | res = register_key_defvalueA(clsid_key, versionindependentprogid_keyname, | |
314 | list->progid); | |
315 | if (res != ERROR_SUCCESS) goto error_close_clsid_key; | |
316 | } | |
317 | } | |
986b33d1 | 318 | |
1933135f RS |
319 | if (list->version) { |
320 | res = register_key_defvalueA(clsid_key, version_keyname, | |
321 | list->version); | |
986b33d1 RS |
322 | if (res != ERROR_SUCCESS) goto error_close_clsid_key; |
323 | } | |
324 | ||
325 | error_close_clsid_key: | |
326 | RegCloseKey(clsid_key); | |
327 | } | |
328 | ||
329 | error_close_coclass_key: | |
330 | RegCloseKey(coclass_key); | |
331 | error_return: | |
332 | return res != ERROR_SUCCESS ? HRESULT_FROM_WIN32(res) : S_OK; | |
333 | } | |
334 | ||
335 | /*********************************************************************** | |
336 | * unregister_coclasses | |
337 | */ | |
338 | static HRESULT unregister_coclasses(struct regsvr_coclass const *list) | |
339 | { | |
340 | LONG res = ERROR_SUCCESS; | |
341 | HKEY coclass_key; | |
342 | ||
343 | res = RegOpenKeyExW(HKEY_CLASSES_ROOT, clsid_keyname, 0, | |
344 | KEY_READ | KEY_WRITE, &coclass_key); | |
345 | if (res == ERROR_FILE_NOT_FOUND) return S_OK; | |
346 | if (res != ERROR_SUCCESS) goto error_return; | |
347 | ||
348 | for (; res == ERROR_SUCCESS && list->clsid; ++list) { | |
349 | WCHAR buf[39]; | |
350 | ||
351 | StringFromGUID2(list->clsid, buf, 39); | |
5987d3a3 SL |
352 | res = RegDeleteTreeW(coclass_key, buf); |
353 | if (res == ERROR_FILE_NOT_FOUND) res = ERROR_SUCCESS; | |
986b33d1 | 354 | if (res != ERROR_SUCCESS) goto error_close_coclass_key; |
986b33d1 RS |
355 | } |
356 | ||
357 | error_close_coclass_key: | |
358 | RegCloseKey(coclass_key); | |
359 | error_return: | |
360 | return res != ERROR_SUCCESS ? HRESULT_FROM_WIN32(res) : S_OK; | |
361 | } | |
362 | ||
1933135f RS |
363 | /*********************************************************************** |
364 | * register_progids | |
365 | */ | |
366 | static HRESULT register_progids(struct progid const *list) | |
367 | { | |
368 | LONG res = ERROR_SUCCESS; | |
369 | ||
370 | for (; res == ERROR_SUCCESS && list->name; ++list) { | |
371 | WCHAR buf[39]; | |
372 | HKEY progid_key; | |
373 | ||
374 | res = RegCreateKeyExA(HKEY_CLASSES_ROOT, list->name, 0, | |
375 | NULL, 0, KEY_READ | KEY_WRITE, NULL, | |
376 | &progid_key, NULL); | |
377 | if (res != ERROR_SUCCESS) goto error_close_clsid_key; | |
378 | ||
379 | res = RegSetValueExA(progid_key, NULL, 0, REG_SZ, | |
380 | (CONST BYTE*)list->description, | |
381 | strlen(list->description) + 1); | |
382 | if (res != ERROR_SUCCESS) goto error_close_clsid_key; | |
383 | ||
384 | StringFromGUID2(list->clsid, buf, 39); | |
385 | ||
386 | res = register_key_defvalueW(progid_key, clsid_keyname, buf); | |
387 | if (res != ERROR_SUCCESS) goto error_close_clsid_key; | |
388 | ||
389 | if (list->curver) { | |
390 | res = register_key_defvalueA(progid_key, curver_keyname, list->curver); | |
391 | if (res != ERROR_SUCCESS) goto error_close_clsid_key; | |
392 | } | |
393 | ||
394 | error_close_clsid_key: | |
395 | RegCloseKey(progid_key); | |
396 | } | |
397 | ||
398 | return res != ERROR_SUCCESS ? HRESULT_FROM_WIN32(res) : S_OK; | |
399 | } | |
400 | ||
401 | /*********************************************************************** | |
402 | * unregister_progids | |
403 | */ | |
404 | static HRESULT unregister_progids(struct progid const *list) | |
405 | { | |
406 | LONG res = ERROR_SUCCESS; | |
407 | ||
408 | for (; res == ERROR_SUCCESS && list->name; ++list) { | |
5987d3a3 SL |
409 | res = RegDeleteTreeA(HKEY_CLASSES_ROOT, list->name); |
410 | if (res == ERROR_FILE_NOT_FOUND) res = ERROR_SUCCESS; | |
1933135f RS |
411 | } |
412 | ||
413 | return res != ERROR_SUCCESS ? HRESULT_FROM_WIN32(res) : S_OK; | |
414 | } | |
415 | ||
986b33d1 RS |
416 | /*********************************************************************** |
417 | * regsvr_key_guid | |
418 | */ | |
419 | static LONG register_key_guid(HKEY base, WCHAR const *name, GUID const *guid) | |
420 | { | |
421 | WCHAR buf[39]; | |
422 | ||
423 | StringFromGUID2(guid, buf, 39); | |
424 | return register_key_defvalueW(base, name, buf); | |
425 | } | |
426 | ||
427 | /*********************************************************************** | |
428 | * regsvr_key_defvalueW | |
429 | */ | |
430 | static LONG register_key_defvalueW( | |
431 | HKEY base, | |
432 | WCHAR const *name, | |
433 | WCHAR const *value) | |
434 | { | |
435 | LONG res; | |
436 | HKEY key; | |
437 | ||
438 | res = RegCreateKeyExW(base, name, 0, NULL, 0, | |
439 | KEY_READ | KEY_WRITE, NULL, &key, NULL); | |
440 | if (res != ERROR_SUCCESS) return res; | |
441 | res = RegSetValueExW(key, NULL, 0, REG_SZ, (CONST BYTE*)value, | |
442 | (lstrlenW(value) + 1) * sizeof(WCHAR)); | |
443 | RegCloseKey(key); | |
444 | return res; | |
445 | } | |
446 | ||
447 | /*********************************************************************** | |
448 | * regsvr_key_defvalueA | |
449 | */ | |
450 | static LONG register_key_defvalueA( | |
451 | HKEY base, | |
452 | WCHAR const *name, | |
453 | char const *value) | |
454 | { | |
455 | LONG res; | |
456 | HKEY key; | |
457 | ||
458 | res = RegCreateKeyExW(base, name, 0, NULL, 0, | |
459 | KEY_READ | KEY_WRITE, NULL, &key, NULL); | |
460 | if (res != ERROR_SUCCESS) return res; | |
461 | res = RegSetValueExA(key, NULL, 0, REG_SZ, (CONST BYTE*)value, | |
462 | lstrlenA(value) + 1); | |
463 | RegCloseKey(key); | |
464 | return res; | |
465 | } | |
466 | ||
986b33d1 RS |
467 | /*********************************************************************** |
468 | * coclass list | |
469 | */ | |
470 | static struct regsvr_coclass const coclass_list[] = { | |
471 | { &CLSID_DOMDocument, | |
472 | "XML DOM Document", | |
473 | NULL, | |
474 | "msxml3.dll", | |
475 | "Both", | |
1933135f RS |
476 | "Microsoft.XMLDOM", |
477 | "1.0" | |
986b33d1 | 478 | }, |
46964179 HD |
479 | { &CLSID_DOMDocument2, |
480 | "XML DOM Document", | |
481 | NULL, | |
482 | "msxml3.dll", | |
483 | "Both", | |
484 | "Msxml2.DOMDocument", | |
485 | "3.0" | |
486 | }, | |
487 | { &CLSID_DOMDocument30, | |
488 | "XML DOM Document 3.0", | |
489 | NULL, | |
490 | "msxml3.dll", | |
491 | "Both", | |
492 | "Msxml2.DOMDocument", | |
493 | "3.0" | |
494 | }, | |
986b33d1 RS |
495 | { &CLSID_DOMFreeThreadedDocument, |
496 | "Free threaded XML DOM Document", | |
497 | NULL, | |
498 | "msxml3.dll", | |
b28f6e52 | 499 | "Both", |
1933135f RS |
500 | "Microsoft.FreeThreadedXMLDOM", |
501 | "1.0" | |
986b33d1 | 502 | }, |
b2add094 ALH |
503 | { &CLSID_DOMFreeThreadedDocument, |
504 | "Free threaded XML DOM Document", | |
505 | NULL, | |
506 | "msxml3.dll", | |
507 | "Both", | |
508 | "Microsoft.FreeThreadedXMLDOM", | |
509 | NULL | |
510 | }, | |
511 | { &CLSID_FreeThreadedDOMDocument, | |
512 | "Free Threaded XML DOM Document", | |
513 | NULL, | |
514 | "msxml3.dll", | |
515 | "Both", | |
516 | "Microsoft.FreeThreadedXMLDOM.1.0", | |
517 | "1.0" | |
8248040d ALH |
518 | }, |
519 | { &CLSID_FreeThreadedDOMDocument26, | |
520 | "Free Threaded XML DOM Document 2.6", | |
521 | NULL, | |
522 | "msxml3.dll", | |
523 | "Both", | |
524 | "Microsoft.FreeThreadedXMLDOM.1.0", | |
525 | "1.0" | |
526 | }, | |
527 | { &CLSID_FreeThreadedDOMDocument30, | |
528 | "Free Threaded XML DOM Document 3.0", | |
529 | NULL, | |
530 | "msxml3.dll", | |
531 | "Both", | |
532 | "Microsoft.FreeThreadedDOMDocument.1.0", | |
533 | "1.0" | |
b2add094 | 534 | }, |
986b33d1 RS |
535 | { &CLSID_XMLHTTPRequest, |
536 | "XML HTTP Request", | |
537 | NULL, | |
538 | "msxml3.dll", | |
539 | "Apartment", | |
1933135f RS |
540 | "Microsoft.XMLHTTP", |
541 | "1.0" | |
986b33d1 RS |
542 | }, |
543 | { &CLSID_XMLDSOControl, | |
544 | "XML Data Source Object", | |
545 | NULL, | |
546 | "msxml3.dll", | |
547 | "Apartment", | |
1933135f RS |
548 | "Microsoft.XMLDSO", |
549 | "1.0" | |
986b33d1 RS |
550 | }, |
551 | { &CLSID_XMLDocument, | |
552 | "Msxml", | |
553 | NULL, | |
554 | "msxml3.dll", | |
555 | "Both", | |
986b33d1 RS |
556 | "Msxml" |
557 | }, | |
cdac075e HD |
558 | { &CLSID_XMLSchemaCache, |
559 | "XML Schema Cache", | |
560 | NULL, | |
561 | "msxml3.dll", | |
562 | "Both", | |
563 | "Msxml2.XMLSchemaCache", | |
564 | "3.0" | |
565 | }, | |
8248040d ALH |
566 | { &CLSID_XMLSchemaCache26, |
567 | "XML Schema Cache 2.6", | |
568 | NULL, | |
569 | "msxml3.dll", | |
570 | "Both", | |
571 | "Msxml2.XMLSchemaCache", | |
572 | "2.6" | |
573 | }, | |
cdac075e HD |
574 | { &CLSID_XMLSchemaCache30, |
575 | "XML Schema Cache 3.0", | |
576 | NULL, | |
577 | "msxml3.dll", | |
578 | "Both", | |
579 | "Msxml2.XMLSchemaCache", | |
580 | "3.0" | |
581 | }, | |
c1f33395 PC |
582 | { &CLSID_SAXXMLReader, |
583 | "SAX XML Reader", | |
584 | NULL, | |
585 | "msxml3.dll", | |
586 | "Both", | |
587 | "Msxml2.SAXXMLReader", | |
588 | "3.0" | |
589 | }, | |
ceed55a4 ALH |
590 | { &CLSID_SAXXMLReader30, |
591 | "SAX XML Reader 3.0", | |
592 | NULL, | |
593 | "msxml3.dll", | |
594 | "Both", | |
595 | "Msxml2.SAXXMLReader", | |
596 | "3.0" | |
597 | }, | |
489c1a8d ALH |
598 | { &CLSID_MXXMLWriter, |
599 | "IMXWriter interface", | |
600 | NULL, | |
601 | "msxml3.dll", | |
602 | "Both", | |
603 | "Msxml2.MXXMLWriter", | |
604 | "3.0" | |
605 | }, | |
606 | { &CLSID_MXXMLWriter30, | |
607 | "IMXWriter interface 3.0", | |
608 | NULL, | |
609 | "msxml3.dll", | |
610 | "Both", | |
611 | "Msxml2.MXXMLWriter", | |
612 | "3.0" | |
613 | }, | |
8248040d ALH |
614 | { &CLSID_SAXAttributes, |
615 | "SAX Attribute", | |
616 | NULL, | |
617 | "msxml3.dll", | |
618 | "Both", | |
619 | "Msxml2.SAXAttributes", | |
620 | NULL | |
621 | }, | |
622 | { &CLSID_SAXAttributes30, | |
623 | "SAX Attribute 3.0", | |
624 | NULL, | |
625 | "msxml3.dll", | |
626 | "Both", | |
627 | "Msxml2.SAXAttributes", | |
628 | "3.0" | |
629 | }, | |
986b33d1 RS |
630 | { NULL } /* list terminator */ |
631 | }; | |
632 | ||
633 | /*********************************************************************** | |
634 | * interface list | |
635 | */ | |
636 | static struct regsvr_interface const interface_list[] = { | |
637 | { NULL } /* list terminator */ | |
638 | }; | |
639 | ||
1933135f RS |
640 | /*********************************************************************** |
641 | * progid list | |
642 | */ | |
643 | static struct progid const progid_list[] = { | |
644 | { "Microsoft.XMLDOM", | |
645 | "XML DOM Document", | |
646 | &CLSID_DOMDocument, | |
647 | "Microsoft.XMLDOM.1.0" | |
648 | }, | |
649 | { "Microsoft.XMLDOM.1.0", | |
650 | "XML DOM Document", | |
651 | &CLSID_DOMDocument, | |
652 | NULL | |
653 | }, | |
2afa6020 RS |
654 | { "MSXML.DOMDocument", |
655 | "XML DOM Document", | |
656 | &CLSID_DOMDocument, | |
657 | "Microsoft.XMLDOM.1.0" | |
658 | }, | |
46964179 HD |
659 | { "Msxml2.DOMDocument", |
660 | "XML DOM Document", | |
661 | &CLSID_DOMDocument2, | |
662 | "Msxml2.DOMDocument.3.0" | |
663 | }, | |
664 | { "Msxml2.DOMDocument.3.0", | |
665 | "XML DOM Document 3.0", | |
666 | &CLSID_DOMDocument30, | |
667 | NULL | |
668 | }, | |
1933135f RS |
669 | { "Microsoft.FreeThreadedXMLDOM", |
670 | "Free threaded XML DOM Document", | |
671 | &CLSID_DOMFreeThreadedDocument, | |
672 | "Microsoft.FreeThreadedXMLDOM.1.0" | |
673 | }, | |
674 | { "Microsoft.FreeThreadedXMLDOM.1.0", | |
675 | "Free threaded XML DOM Document", | |
676 | &CLSID_DOMFreeThreadedDocument, | |
677 | NULL | |
678 | }, | |
2afa6020 RS |
679 | { "MSXML.FreeThreadedDOMDocument", |
680 | "Free threaded XML DOM Document", | |
681 | &CLSID_DOMFreeThreadedDocument, | |
682 | "Microsoft.FreeThreadedXMLDOM.1.0" | |
683 | }, | |
8248040d ALH |
684 | { "MSXML.FreeThreadedDOMDocument26", |
685 | "Free threaded XML DOM Document 2.6", | |
686 | &CLSID_FreeThreadedDOMDocument26, | |
687 | NULL | |
688 | }, | |
689 | { "MSXML.FreeThreadedDOMDocument30", | |
690 | "Free threaded XML DOM Document 3.0", | |
691 | &CLSID_FreeThreadedDOMDocument30, | |
692 | NULL | |
693 | }, | |
1933135f RS |
694 | { "Microsoft.XMLHTTP", |
695 | "XML HTTP Request", | |
696 | &CLSID_XMLHTTPRequest, | |
697 | "Microsoft.XMLHTTP.1.0" | |
698 | }, | |
699 | { "Microsoft.XMLHTTP.1.0", | |
700 | "XML HTTP Request", | |
701 | &CLSID_XMLHTTPRequest, | |
702 | NULL | |
703 | }, | |
704 | { "Microsoft.XMLDSO", | |
705 | "XML Data Source Object", | |
706 | &CLSID_XMLDSOControl, | |
707 | "Microsoft.XMLDSO.1.0" | |
708 | }, | |
709 | { "Microsoft.XMLDSO.1.0", | |
710 | "XML Data Source Object", | |
711 | &CLSID_XMLDSOControl, | |
712 | NULL | |
713 | }, | |
714 | { "Msxml", | |
715 | "Msxml", | |
716 | &CLSID_XMLDocument, | |
717 | NULL | |
718 | }, | |
cdac075e HD |
719 | { "Msxml2.XMLSchemaCache", |
720 | "XML Schema Cache", | |
721 | &CLSID_XMLSchemaCache, | |
722 | "Msxml2.XMLSchemaCache.3.0" | |
723 | }, | |
8248040d ALH |
724 | { "Msxml2.XMLSchemaCache.2.6", |
725 | "XML Schema Cache 2.6", | |
726 | &CLSID_XMLSchemaCache26, | |
727 | "Msxml2.XMLSchemaCache.2.6" | |
728 | }, | |
cdac075e HD |
729 | { "Msxml2.XMLSchemaCache.3.0", |
730 | "XML Schema Cache 3.0", | |
731 | &CLSID_XMLSchemaCache30, | |
732 | NULL | |
733 | }, | |
ceed55a4 ALH |
734 | { "Msxml2.SAXXMLReader", |
735 | "SAX XML Reader", | |
736 | &CLSID_SAXXMLReader, | |
737 | "Msxml2.SAXXMLReader.3.0" | |
738 | }, | |
739 | { "Msxml2.SAXXMLReader.3.0", | |
740 | "SAX XML Reader 3.0", | |
741 | &CLSID_SAXXMLReader30, | |
742 | NULL | |
743 | }, | |
489c1a8d ALH |
744 | { "Msxml2.MXXMLWriter", |
745 | "MXXMLWriter", | |
746 | &CLSID_MXXMLWriter, | |
747 | "Msxml2.MXXMLWriter.3.0" | |
748 | }, | |
749 | { "Msxml2.MXXMLWriter.3.0", | |
750 | "MXXMLWriter 3.0", | |
751 | &CLSID_MXXMLWriter30, | |
752 | NULL | |
753 | }, | |
8248040d ALH |
754 | { "Msxml2.SAXAttributes", |
755 | "SAX Attribute", | |
756 | &CLSID_SAXAttributes, | |
757 | NULL | |
758 | }, | |
759 | { "Msxml2.SAXAttributes.3.0", | |
760 | "SAX Attribute 3.0", | |
761 | &CLSID_SAXAttributes30, | |
762 | NULL | |
763 | }, | |
1933135f RS |
764 | { NULL } /* list terminator */ |
765 | }; | |
766 | ||
986b33d1 | 767 | /*********************************************************************** |
d3aacce6 | 768 | * DllRegisterServer (MSXML3.@) |
986b33d1 RS |
769 | */ |
770 | HRESULT WINAPI DllRegisterServer(void) | |
771 | { | |
772 | HRESULT hr; | |
a1cce928 | 773 | ITypeLib *tl; |
379e543b | 774 | static const WCHAR wszMsXml3[] = {'m','s','x','m','l','3','.','d','l','l',0}; |
986b33d1 RS |
775 | |
776 | TRACE("\n"); | |
777 | ||
778 | hr = register_coclasses(coclass_list); | |
779 | if (SUCCEEDED(hr)) | |
780 | hr = register_interfaces(interface_list); | |
1933135f RS |
781 | if (SUCCEEDED(hr)) |
782 | hr = register_progids(progid_list); | |
a1cce928 | 783 | |
379e543b PC |
784 | if(SUCCEEDED(hr)) { |
785 | ||
786 | hr = LoadTypeLibEx(wszMsXml3, REGKIND_REGISTER, &tl); | |
787 | if(SUCCEEDED(hr)) | |
788 | ITypeLib_Release(tl); | |
a1cce928 | 789 | } |
a1cce928 | 790 | |
986b33d1 RS |
791 | return hr; |
792 | } | |
793 | ||
794 | /*********************************************************************** | |
d3aacce6 | 795 | * DllUnregisterServer (MSXML3.@) |
986b33d1 RS |
796 | */ |
797 | HRESULT WINAPI DllUnregisterServer(void) | |
798 | { | |
799 | HRESULT hr; | |
800 | ||
801 | TRACE("\n"); | |
802 | ||
803 | hr = unregister_coclasses(coclass_list); | |
804 | if (SUCCEEDED(hr)) | |
805 | hr = unregister_interfaces(interface_list); | |
1933135f RS |
806 | if (SUCCEEDED(hr)) |
807 | hr = unregister_progids(progid_list); | |
379e543b PC |
808 | if (SUCCEEDED(hr)) |
809 | hr = UnRegisterTypeLib(&LIBID_MSXML2, 3, 0, LOCALE_SYSTEM_DEFAULT, SYS_WIN32); | |
a1cce928 | 810 | |
986b33d1 RS |
811 | return hr; |
812 | } |