ReactOS 0.4.17-dev-966-gf06eace
dictionary.c
Go to the documentation of this file.
1/*
2 * Copyright (C) 2012 Alistair Leslie-Hughes
3 * Copyright 2015 Nikolay Sivov for CodeWeavers
4 *
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Lesser General Public
7 * License as published by the Free Software Foundation; either
8 * version 2.1 of the License, or (at your option) any later version.
9 *
10 * This library is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * Lesser General Public License for more details.
14 *
15 * You should have received a copy of the GNU Lesser General Public
16 * License along with this library; if not, write to the Free Software
17 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
18 */
19#define COBJMACROS
20
21#ifdef __REACTOS__
22#include <wine/config.h>
23#include <wine/port.h>
24#endif
25#include <stdarg.h>
26#include <math.h>
27
28#include "windef.h"
29#include "winbase.h"
30#include "ole2.h"
31#include "olectl.h"
32#include "dispex.h"
33#include "scrrun.h"
34#include "scrrun_private.h"
35
36#include "wine/debug.h"
37#include "wine/list.h"
38
40
41#define BUCKET_COUNT 509
42#define DICT_HASH_MOD 1201
43
44/* Implementation details
45
46 Dictionary contains one list that links all pairs, this way
47 order in which they were added is preserved. Each bucket has
48 its own list to hold all pairs in this bucket. Initially all
49 bucket lists are zeroed and we init them once we about to add
50 first pair.
51
52 When pair is removed it's unlinked from both lists; if it was
53 a last pair in a bucket list it stays empty in initialized state.
54
55 Preserving pair order is important for enumeration, so far testing
56 indicates that pairs are not reordered basing on hash value.
57 */
58
60{
61 struct list entry;
62 struct list bucket;
66};
67
68struct dictionary
69{
71 IDictionary IDictionary_iface;
73
74 CompareMethod method;
76 struct list pairs;
78 struct list notifier;
79};
80
82{
85
87 struct list *cur;
88 struct list notify;
89};
90
91static inline struct dictionary *impl_from_IDictionary(IDictionary *iface)
92{
93 return CONTAINING_RECORD(iface, struct dictionary, IDictionary_iface);
94}
95
97{
99}
100
101static inline struct list *get_bucket_head(struct dictionary *dict, DWORD hash)
102{
103 return &dict->buckets[hash % BUCKET_COUNT];
104}
105
106static inline BOOL is_string_key(const VARIANT *key)
107{
108 return V_VT(key) == VT_BSTR;
109}
110
111static inline BOOL is_ptr_key(const VARIANT *key)
112{
113 return V_VT(key) == VT_UNKNOWN || V_VT(key) == VT_DISPATCH;
114}
115
116static inline BOOL is_numeric_key(const VARIANT *key)
117{
118 switch (V_VT(key))
119 {
120 case VT_UI1:
121 case VT_I2:
122 case VT_I4:
123 case VT_DATE:
124 case VT_R4:
125 case VT_R8:
126 return TRUE;
127 default:
128 return FALSE;
129 }
130}
131
132/* Only for VT_BSTR or VT_BSTR|VT_BYREF types */
133static inline WCHAR *get_key_strptr(const VARIANT *key)
134{
135 if (V_VT(key) == VT_BSTR)
136 return V_BSTR(key);
137
138 if (V_BSTRREF(key))
139 return *V_BSTRREF(key);
140
141 return NULL;
142}
143
144/* should be used only when both keys are of string type, it's not checked */
145static inline int strcmp_key(const struct dictionary *dict, const VARIANT *key1, const VARIANT *key2)
146{
147 const WCHAR *str1, *str2;
148
150 str2 = get_key_strptr(key2);
151 return dict->method == BinaryCompare ? wcscmp(str1, str2) : wcsicmp(str1, str2);
152}
153
154static inline BOOL numeric_key_eq(const VARIANT *key1, const VARIANT *key2)
155{
156 VARIANT v1, v2;
157
158 VariantInit(&v1);
160 return FALSE;
161
162 VariantInit(&v2);
163 if (FAILED(VariantChangeType(&v2, key2, 0, VT_R4)))
164 return FALSE;
165
166 return V_R4(&v1) == V_R4(&v2);
167}
168
169static BOOL is_matching_key(const struct dictionary *dict, const struct keyitem_pair *pair, const VARIANT *key, DWORD hash)
170{
171 if (is_string_key(key) != is_string_key(&pair->key))
172 {
173 return FALSE;
174 }
175 else if (is_string_key(key) && is_string_key(&pair->key))
176 {
177 return hash == pair->hash && !strcmp_key(dict, key, &pair->key);
178 }
179 else if (is_ptr_key(key) != is_ptr_key(&pair->key))
180 {
181 return FALSE;
182 }
183 else if (is_ptr_key(key) && is_ptr_key(&pair->key))
184 {
185 return hash == pair->hash && V_UNKNOWN(key) == V_UNKNOWN(&pair->key);
186 }
187 else if (is_numeric_key(key) != is_numeric_key(&pair->key))
188 {
189 return FALSE;
190 }
191 else if (is_numeric_key(key) && is_numeric_key(&pair->key))
192 {
193 return hash == pair->hash && numeric_key_eq(key, &pair->key);
194 }
195 else if (V_VT(&pair->key) == VT_EMPTY || V_VT(&pair->key) == VT_NULL)
196 {
197 return V_VT(&pair->key) == V_VT(key);
198 }
199 else
200 {
201 WARN("Unexpected key type %#x.\n", V_VT(key));
202 return FALSE;
203 }
204}
205
206static struct keyitem_pair *get_keyitem_pair(struct dictionary *dict, VARIANT *key)
207{
208 struct keyitem_pair *pair;
209 struct list *head, *entry;
210 VARIANT hash, v;
211 HRESULT hr;
212
213 hr = IDictionary_get_HashVal(&dict->IDictionary_iface, key, &hash);
214 if (FAILED(hr))
215 return NULL;
216
217 head = get_bucket_head(dict, V_I4(&hash));
218 if (!head->next || list_empty(head))
219 return NULL;
220
221 VariantInit(&v);
222 if (FAILED(VariantCopyInd(&v, key)))
223 return NULL;
224
226 do
227 {
228 pair = LIST_ENTRY(entry, struct keyitem_pair, bucket);
229 if (is_matching_key(dict, pair, &v, V_I4(&hash)))
230 {
231 VariantClear(&v);
232 return pair;
233 }
234 } while ((entry = list_next(head, entry)));
235
236 VariantClear(&v);
237
238 return NULL;
239}
240
242{
243 struct keyitem_pair *pair;
244 struct list *head;
246 HRESULT hr;
247
248 hr = IDictionary_get_HashVal(&dict->IDictionary_iface, key, &hash);
249 if (FAILED(hr))
250 return hr;
251
252 if (!(pair = malloc(sizeof(*pair))))
253 return E_OUTOFMEMORY;
254
255 pair->hash = V_I4(&hash);
256 VariantInit(&pair->key);
257 VariantInit(&pair->item);
258
259 hr = VariantCopyInd(&pair->key, key);
260 if (FAILED(hr))
261 goto failed;
262
263 hr = VariantCopyInd(&pair->item, item);
264 if (FAILED(hr))
265 goto failed;
266
267 head = get_bucket_head(dict, pair->hash);
268 if (!head->next)
269 /* this only happens once per bucket */
271
272 /* link to bucket list and to full list */
273 list_add_tail(head, &pair->bucket);
274 list_add_tail(&dict->pairs, &pair->entry);
275 dict->count++;
276 return S_OK;
277
278failed:
279 VariantClear(&pair->key);
280 VariantClear(&pair->item);
281 free(pair);
282 return hr;
283}
284
286{
287 VariantClear(&pair->key);
288 VariantClear(&pair->item);
289 free(pair);
290}
291
293{
295
296 TRACE("(%p)->(%s, %p)\n", This, debugstr_guid(riid), obj);
297
298 if (IsEqualIID(riid, &IID_IEnumVARIANT) || IsEqualIID(riid, &IID_IUnknown)) {
299 *obj = iface;
300 IEnumVARIANT_AddRef(iface);
301 return S_OK;
302 }
303 else {
304 WARN("interface not supported %s\n", debugstr_guid(riid));
305 *obj = NULL;
306 return E_NOINTERFACE;
307 }
308}
309
311{
314 TRACE("%p, refcount %lu.\n", iface, ref);
315 return ref;
316}
317
319{
322
323 TRACE("%p, refcount %lu.\n", iface, ref);
324
325 if (!ref)
326 {
327 list_remove(&This->notify);
328 IDictionary_Release(&This->dict->IDictionary_iface);
329 free(This);
330 }
331
332 return ref;
333}
334
336{
338 struct keyitem_pair *pair;
339 ULONG i = 0;
340
341 TRACE("%p, %lu, %p, %p.\n", iface, count, keys, fetched);
342
343 if (fetched)
344 *fetched = 0;
345
346 if (!count)
347 return S_OK;
348
349 while (This->cur && i < count) {
350 pair = LIST_ENTRY(This->cur, struct keyitem_pair, entry);
351 VariantCopy(&keys[i], &pair->key);
352 This->cur = list_next(&This->dict->pairs, This->cur);
353 i++;
354 }
355
356 if (fetched)
357 *fetched = i;
358
359 return i < count ? S_FALSE : S_OK;
360}
361
363{
365
366 TRACE("%p, %lu.\n", iface, count);
367
368 if (!count)
369 return S_OK;
370
371 if (!This->cur)
372 return S_FALSE;
373
374 while (count--) {
375 This->cur = list_next(&This->dict->pairs, This->cur);
376 if (!This->cur) break;
377 }
378
379 return count == 0 ? S_OK : S_FALSE;
380}
381
383{
385
386 TRACE("(%p)\n", This);
387
388 This->cur = list_head(&This->dict->pairs);
389 return S_OK;
390}
391
392static HRESULT create_dict_enum(struct dictionary *, IUnknown**);
393
395{
397 TRACE("(%p)->(%p)\n", This, cloned);
398 return create_dict_enum(This->dict, (IUnknown**)cloned);
399}
400
401static const IEnumVARIANTVtbl dictenumvtbl = {
409};
410
412{
413 struct dictionary_enum *object;
414
415 *ret = NULL;
416
417 if (!(object = calloc(1, sizeof(*object))))
418 return E_OUTOFMEMORY;
419
420 object->IEnumVARIANT_iface.lpVtbl = &dictenumvtbl;
421 object->ref = 1;
422 object->cur = list_head(&dict->pairs);
423 list_add_tail(&dict->notifier, &object->notify);
424 object->dict = dict;
425 IDictionary_AddRef(&dict->IDictionary_iface);
426
427 *ret = (IUnknown *)&object->IEnumVARIANT_iface;
428
429 return S_OK;
430}
431
432static void notify_remove_pair(struct list *notifier, struct list *pair)
433{
434 struct dictionary_enum *dict_enum;
435 struct list *cur;
436
437 LIST_FOR_EACH(cur, notifier) {
438 dict_enum = LIST_ENTRY(cur, struct dictionary_enum, notify);
439 if (!pair)
440 dict_enum->cur = list_head(&dict_enum->dict->pairs);
441 else if (dict_enum->cur == pair) {
442 dict_enum->cur = list_next(&dict_enum->dict->pairs, dict_enum->cur);
443 }
444 }
445}
446
447static HRESULT WINAPI dictionary_QueryInterface(IDictionary *iface, REFIID riid, void **obj)
448{
450
451 TRACE("%p, %s, %p.\n", iface, debugstr_guid(riid), obj);
452
453 *obj = NULL;
454
457 IsEqualIID(riid, &IID_IDictionary))
458 {
460 }
462 {
463 *obj = &dictionary->classinfo.IProvideClassInfo_iface;
464 }
465 else if ( IsEqualGUID( riid, &IID_IDispatchEx ))
466 {
467 TRACE("Interface IDispatchEx not supported - returning NULL\n");
468 *obj = NULL;
469 return E_NOINTERFACE;
470 }
471 else if ( IsEqualGUID( riid, &IID_IObjectWithSite ))
472 {
473 TRACE("Interface IObjectWithSite not supported - returning NULL\n");
474 *obj = NULL;
475 return E_NOINTERFACE;
476 }
477 else
478 {
479 WARN("interface %s not implemented\n", debugstr_guid(riid));
480 return E_NOINTERFACE;
481 }
482
483 IUnknown_AddRef((IUnknown*)*obj);
484 return S_OK;
485}
486
487static ULONG WINAPI dictionary_AddRef(IDictionary *iface)
488{
491
492 TRACE("%p, refcount %lu.\n", iface, ref);
493
494 return ref;
495}
496
497static ULONG WINAPI dictionary_Release(IDictionary *iface)
498{
501
502 TRACE("%p, refcount %lu.\n", iface, ref);
503
504 if (!ref)
505 {
506 IDictionary_RemoveAll(iface);
508 }
509
510 return ref;
511}
512
513static HRESULT WINAPI dictionary_GetTypeInfoCount(IDictionary *iface, UINT *pctinfo)
514{
515 TRACE("%p, %p.\n", iface, pctinfo);
516
517 *pctinfo = 1;
518 return S_OK;
519}
520
521static HRESULT WINAPI dictionary_GetTypeInfo(IDictionary *iface, UINT iTInfo, LCID lcid, ITypeInfo **ppTInfo)
522{
523 TRACE("%p, %u, %lx, %p.\n", iface, iTInfo, lcid, ppTInfo);
524
525 return get_typeinfo(IDictionary_tid, ppTInfo);
526}
527
528static HRESULT WINAPI dictionary_GetIDsOfNames(IDictionary *iface, REFIID riid, LPOLESTR *rgszNames,
529 UINT cNames, LCID lcid, DISPID *rgDispId)
530{
532 HRESULT hr;
533
534 TRACE("%p, %s, %p, %u, %lx, %p.\n", iface, debugstr_guid(riid), rgszNames, cNames, lcid, rgDispId);
535
537 if(SUCCEEDED(hr))
538 {
539 hr = ITypeInfo_GetIDsOfNames(typeinfo, rgszNames, cNames, rgDispId);
540 ITypeInfo_Release(typeinfo);
541 }
542
543 return hr;
544}
545
546static HRESULT WINAPI dictionary_Invoke(IDictionary *iface, DISPID dispIdMember, REFIID riid,
547 LCID lcid, WORD wFlags, DISPPARAMS *pDispParams, VARIANT *pVarResult,
548 EXCEPINFO *pExcepInfo, UINT *puArgErr)
549{
551 HRESULT hr;
552
553 TRACE("%p, %ld, %s, %lx, %d, %p, %p, %p, %p.\n", iface, dispIdMember, debugstr_guid(riid),
554 lcid, wFlags, pDispParams, pVarResult, pExcepInfo, puArgErr);
555
557 if(SUCCEEDED(hr))
558 {
559 hr = ITypeInfo_Invoke(typeinfo, iface, dispIdMember, wFlags, pDispParams, pVarResult, pExcepInfo, puArgErr);
560 ITypeInfo_Release(typeinfo);
561 }
562
563 return hr;
564}
565
567{
569 struct keyitem_pair *pair;
570
571 TRACE("%p, %s, %s.\n", iface, debugstr_variant(key), debugstr_variant(item));
572
574 return VariantCopyInd(&pair->item, item);
575
577}
578
580{
582 struct keyitem_pair *pair;
583
584 TRACE("%p, %s, %s.\n", iface, debugstr_variant(key), debugstr_variant(item));
585
587 return VariantCopyInd(&pair->item, item);
588
590}
591
593{
595 struct keyitem_pair *pair;
596
597 TRACE("%p, %s, %p.\n", iface, debugstr_variant(key), item);
598
600 VariantCopy(item, &pair->item);
601 else {
603 return IDictionary_Add(iface, key, item);
604 }
605
606 return S_OK;
607}
608
609static HRESULT WINAPI dictionary_Add(IDictionary *iface, VARIANT *key, VARIANT *item)
610{
612
613 TRACE("%p, %s, %s.\n", iface, debugstr_variant(key), debugstr_variant(item));
614
616 return CTL_E_KEY_ALREADY_EXISTS;
617
619}
620
621static HRESULT WINAPI dictionary_get_Count(IDictionary *iface, LONG *count)
622{
624
625 TRACE("%p, %p.\n", iface, count);
626
628 return S_OK;
629}
630
631static HRESULT WINAPI dictionary_Exists(IDictionary *iface, VARIANT *key, VARIANT_BOOL *exists)
632{
634
635 TRACE("%p, %s, %p.\n", iface, debugstr_variant(key), exists);
636
637 if (!exists)
639
640 *exists = get_keyitem_pair(dictionary, key) != NULL ? VARIANT_TRUE : VARIANT_FALSE;
641 return S_OK;
642}
643
644static HRESULT WINAPI dictionary_Items(IDictionary *iface, VARIANT *items)
645{
647 struct keyitem_pair *pair;
648 SAFEARRAYBOUND bound;
649 SAFEARRAY *sa;
650 VARIANT *v;
651 HRESULT hr;
652 LONG i;
653
654 TRACE("%p, %p.\n", iface, items);
655
656 if (!items)
657 return S_OK;
658
659 bound.lLbound = 0;
660 bound.cElements = dictionary->count;
661 sa = SafeArrayCreate(VT_VARIANT, 1, &bound);
662 if (!sa)
663 return E_OUTOFMEMORY;
664
665 hr = SafeArrayAccessData(sa, (void**)&v);
666 if (FAILED(hr)) {
668 return hr;
669 }
670
671 i = 0;
673 {
674 VariantCopy(&v[i], &pair->item);
675 i++;
676 }
678
680 V_ARRAY(items) = sa;
681 return S_OK;
682}
683
684static HRESULT WINAPI dictionary_put_Key(IDictionary *iface, VARIANT *key, VARIANT *newkey)
685{
687 struct keyitem_pair *pair;
689 HRESULT hr;
690
691 TRACE("%p, %s, %s.\n", iface, debugstr_variant(key), debugstr_variant(newkey));
692
694 {
695 /* found existing pair for a key, add new pair with new key
696 and old item and remove old pair after that */
697
698 hr = IDictionary_Add(iface, newkey, &pair->item);
699 if (FAILED(hr))
700 return hr;
701
702 return IDictionary_Remove(iface, key);
703 }
704
706 return IDictionary_Add(iface, newkey, &empty);
707}
708
709static HRESULT WINAPI dictionary_Keys(IDictionary *iface, VARIANT *keys)
710{
712 struct keyitem_pair *pair;
713 SAFEARRAYBOUND bound;
714 SAFEARRAY *sa;
715 VARIANT *v;
716 HRESULT hr;
717 LONG i;
718
719 TRACE("%p, %p.\n", iface, keys);
720
721 if (!keys)
722 return S_OK;
723
724 bound.lLbound = 0;
725 bound.cElements = dictionary->count;
726 sa = SafeArrayCreate(VT_VARIANT, 1, &bound);
727 if (!sa)
728 return E_OUTOFMEMORY;
729
730 hr = SafeArrayAccessData(sa, (void**)&v);
731 if (FAILED(hr)) {
733 return hr;
734 }
735
736 i = 0;
738 {
739 VariantCopy(&v[i], &pair->key);
740 i++;
741 }
743
745 V_ARRAY(keys) = sa;
746 return S_OK;
747}
748
749static HRESULT WINAPI dictionary_Remove(IDictionary *iface, VARIANT *key)
750{
752 struct keyitem_pair *pair;
753
754 TRACE("%p, %s.\n", iface, debugstr_variant(key));
755
757 return CTL_E_ELEMENT_NOT_FOUND;
758
760 list_remove(&pair->entry);
761 list_remove(&pair->bucket);
762 dictionary->count--;
763
765 return S_OK;
766}
767
768static HRESULT WINAPI dictionary_RemoveAll(IDictionary *iface)
769{
771 struct keyitem_pair *pair, *pair2;
772
773 TRACE("%p.\n", iface);
774
775 if (!dictionary->count)
776 return S_OK;
777
780 {
781 list_remove(&pair->entry);
782 list_remove(&pair->bucket);
784 }
785 dictionary->count = 0;
786
787 return S_OK;
788}
789
790static HRESULT WINAPI dictionary_put_CompareMode(IDictionary *iface, CompareMethod method)
791{
793
794 TRACE("%p, %d.\n", iface, method);
795
796 if (dictionary->count)
798
800 return S_OK;
801}
802
803static HRESULT WINAPI dictionary_get_CompareMode(IDictionary *iface, CompareMethod *method)
804{
806
807 TRACE("%p, %p.\n", iface, method);
808
810 return S_OK;
811}
812
813static HRESULT WINAPI dictionary__NewEnum(IDictionary *iface, IUnknown **ret)
814{
816
817 TRACE("%p, %p.\n", iface, ret);
818
820}
821
822static DWORD get_str_hash(const WCHAR *str, CompareMethod method)
823{
824 DWORD hash = 0;
825
826 if (str) {
827 while (*str) {
828 WCHAR ch;
829
830 ch = (method == TextCompare || method == DatabaseCompare) ? towlower(*str) : *str;
831
832 hash += (hash << 4) + ch;
833 str++;
834 }
835 }
836
837 return hash % DICT_HASH_MOD;
838}
839
841{
842 return (*((DWORD*)&num)) % DICT_HASH_MOD;
843}
844
846{
847 if (isinf(flt)) {
848 *hash = 0;
849 return S_OK;
850 }
851 else if (!isnan(flt)) {
852 *hash = get_num_hash(flt);
853 return S_OK;
854 }
855
856 /* NaN case */
857 *hash = ~0u;
859}
860
861static DWORD get_ptr_hash(void *ptr)
862{
864#ifdef _WIN64
865 hash ^= (ULONG_PTR)ptr >> 32;
866#endif
867 return hash % 1201;
868}
869
871{
873
874 TRACE("%p, %s, %p.\n", iface, debugstr_variant(key), hash);
875
876 V_VT(hash) = VT_I4;
877 switch (V_VT(key))
878 {
879 case VT_BSTR|VT_BYREF:
880 case VT_BSTR:
882 break;
883 case VT_UI1|VT_BYREF:
884 case VT_UI1:
886 break;
887 case VT_I2|VT_BYREF:
888 case VT_I2:
890 break;
891 case VT_I4|VT_BYREF:
892 case VT_I4:
894 break;
895 case VT_UNKNOWN|VT_BYREF:
897 case VT_UNKNOWN:
898 case VT_DISPATCH:
899 {
901 IUnknown *unk = NULL;
902
903 if (!src) {
904 V_I4(hash) = 0;
905 return S_OK;
906 }
907
908 IUnknown_QueryInterface(src, &IID_IUnknown, (void**)&unk);
909 if (!unk) {
910 V_I4(hash) = ~0u;
912 }
913 V_I4(hash) = get_ptr_hash(unk);
914 IUnknown_Release(unk);
915 break;
916 }
917 case VT_DATE|VT_BYREF:
918 case VT_DATE:
920 case VT_R4|VT_BYREF:
921 case VT_R4:
922 return get_flt_hash(V_VT(key) & VT_BYREF ? *V_R4REF(key) : V_R4(key), &V_I4(hash));
923 case VT_R8|VT_BYREF:
924 case VT_R8:
925 return get_flt_hash(V_VT(key) & VT_BYREF ? *V_R8REF(key) : V_R8(key), &V_I4(hash));
926 case VT_EMPTY:
927 case VT_NULL:
928 V_I4(hash) = 0;
929 return S_OK;
930 case VT_INT:
931 case VT_UINT:
932 case VT_I1:
933 case VT_I8:
934 case VT_UI2:
935 case VT_UI4:
936 V_I4(hash) = ~0u;
938 default:
939 FIXME("not implemented for type %d\n", V_VT(key));
940 return E_NOTIMPL;
941 }
942
943 return S_OK;
944}
945
946static const struct IDictionaryVtbl dictionary_vtbl =
947{
970};
971
973{
974 struct dictionary *object;
975
976 TRACE("(%p, %p, %s, %p)\n", factory, outer, debugstr_guid(riid), ret);
977
978 *ret = NULL;
979
980 if (!(object = calloc(1, sizeof(*object))))
981 return E_OUTOFMEMORY;
982
983 object->IDictionary_iface.lpVtbl = &dictionary_vtbl;
984 object->ref = 1;
985 object->method = BinaryCompare;
986 list_init(&object->pairs);
987 list_init(&object->notifier);
988
989 init_classinfo(&CLSID_Dictionary, (IUnknown *)&object->IDictionary_iface, &object->classinfo);
990
991 *ret = &object->IDictionary_iface;
992
993 return S_OK;
994}
static struct sockaddr_in sa
Definition: adnsresfilter.c:69
struct outqueuenode * head
Definition: adnsresfilter.c:66
HRESULT get_typeinfo(enum type_id tid, ITypeInfo **ret)
Definition: apps.c:125
#define InterlockedIncrement
Definition: armddk.h:53
#define InterlockedDecrement
Definition: armddk.h:52
#define WINE_DEFAULT_DEBUG_CHANNEL(t)
Definition: precomp.h:23
#define TextCompare
Definition: text.h:19
static void list_remove(struct list_entry *entry)
Definition: list.h:90
static int list_empty(struct list_entry *head)
Definition: list.h:58
static void list_add_tail(struct list_entry *head, struct list_entry *entry)
Definition: list.h:83
static void list_init(struct list_entry *head)
Definition: list.h:51
#define FIXME(fmt,...)
Definition: precomp.h:53
#define WARN(fmt,...)
Definition: precomp.h:61
const GUID IID_IUnknown
Definition: list.h:39
#define E_OUTOFMEMORY
Definition: ddrawi.h:100
#define E_NOTIMPL
Definition: ddrawi.h:99
#define free
Definition: debug_ros.c:5
#define malloc
Definition: debug_ros.c:4
HRESULT hr
Definition: delayimp.cpp:582
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
static const WCHAR empty[1]
Definition: string.c:47
short VARIANT_BOOL
Definition: compat.h:2290
@ VT_BSTR
Definition: compat.h:2303
@ VT_INT
Definition: compat.h:2316
@ VT_R4
Definition: compat.h:2299
@ VT_NULL
Definition: compat.h:2296
@ VT_UNKNOWN
Definition: compat.h:2308
@ VT_BYREF
Definition: compat.h:2342
@ VT_UI2
Definition: compat.h:2312
@ VT_ARRAY
Definition: compat.h:2341
@ VT_R8
Definition: compat.h:2300
@ VT_VARIANT
Definition: compat.h:2307
@ VT_I8
Definition: compat.h:2314
@ VT_I1
Definition: compat.h:2310
@ VT_I4
Definition: compat.h:2298
@ VT_DATE
Definition: compat.h:2302
@ VT_I2
Definition: compat.h:2297
@ VT_UI4
Definition: compat.h:2313
@ VT_UINT
Definition: compat.h:2317
@ VT_EMPTY
Definition: compat.h:2295
@ VT_DISPATCH
Definition: compat.h:2304
@ VT_UI1
Definition: compat.h:2311
#define wcsicmp
Definition: compat.h:15
LCID lcid
Definition: locale.c:5660
const UINT * keys
Definition: locale.c:418
unsigned char ch[4][2]
Definition: console.c:118
_ACRTIMP int __cdecl wcscmp(const wchar_t *, const wchar_t *)
Definition: wcs.c:1977
#define isinf(x)
Definition: math.h:359
#define isnan(x)
Definition: math.h:360
HRESULT WINAPI SafeArrayAccessData(SAFEARRAY *psa, void **ppvData)
Definition: safearray.c:1137
HRESULT WINAPI SafeArrayUnaccessData(SAFEARRAY *psa)
Definition: safearray.c:1168
HRESULT WINAPI SafeArrayDestroy(SAFEARRAY *psa)
Definition: safearray.c:1347
SAFEARRAY *WINAPI SafeArrayCreate(VARTYPE vt, UINT cDims, SAFEARRAYBOUND *rgsabound)
Definition: safearray.c:600
static HRESULT create_dict_enum(struct dictionary *, IUnknown **)
Definition: dictionary.c:411
#define BUCKET_COUNT
Definition: dictionary.c:41
static void notify_remove_pair(struct list *notifier, struct list *pair)
Definition: dictionary.c:432
static BOOL is_ptr_key(const VARIANT *key)
Definition: dictionary.c:111
static HRESULT WINAPI dict_enum_Skip(IEnumVARIANT *iface, ULONG count)
Definition: dictionary.c:362
static HRESULT WINAPI dictionary_QueryInterface(IDictionary *iface, REFIID riid, void **obj)
Definition: dictionary.c:447
static HRESULT WINAPI dictionary_GetIDsOfNames(IDictionary *iface, REFIID riid, LPOLESTR *rgszNames, UINT cNames, LCID lcid, DISPID *rgDispId)
Definition: dictionary.c:528
static ULONG WINAPI dict_enum_AddRef(IEnumVARIANT *iface)
Definition: dictionary.c:310
static DWORD get_str_hash(const WCHAR *str, CompareMethod method)
Definition: dictionary.c:822
static HRESULT WINAPI dictionary_get_HashVal(IDictionary *iface, VARIANT *key, VARIANT *hash)
Definition: dictionary.c:870
static WCHAR * get_key_strptr(const VARIANT *key)
Definition: dictionary.c:133
static struct dictionary * impl_from_IDictionary(IDictionary *iface)
Definition: dictionary.c:91
static HRESULT WINAPI dictionary__NewEnum(IDictionary *iface, IUnknown **ret)
Definition: dictionary.c:813
static HRESULT WINAPI dict_enum_QueryInterface(IEnumVARIANT *iface, REFIID riid, void **obj)
Definition: dictionary.c:292
static HRESULT WINAPI dictionary_GetTypeInfo(IDictionary *iface, UINT iTInfo, LCID lcid, ITypeInfo **ppTInfo)
Definition: dictionary.c:521
static const struct IDictionaryVtbl dictionary_vtbl
Definition: dictionary.c:946
static HRESULT WINAPI dictionary_get_Item(IDictionary *iface, VARIANT *key, VARIANT *item)
Definition: dictionary.c:592
static ULONG WINAPI dictionary_AddRef(IDictionary *iface)
Definition: dictionary.c:487
static HRESULT WINAPI dictionary_Items(IDictionary *iface, VARIANT *items)
Definition: dictionary.c:644
static int strcmp_key(const struct dictionary *dict, const VARIANT *key1, const VARIANT *key2)
Definition: dictionary.c:145
HRESULT WINAPI Dictionary_CreateInstance(IClassFactory *factory, IUnknown *outer, REFIID riid, void **ret)
Definition: dictionary.c:972
static struct keyitem_pair * get_keyitem_pair(struct dictionary *dict, VARIANT *key)
Definition: dictionary.c:206
static void free_keyitem_pair(struct keyitem_pair *pair)
Definition: dictionary.c:285
static BOOL is_matching_key(const struct dictionary *dict, const struct keyitem_pair *pair, const VARIANT *key, DWORD hash)
Definition: dictionary.c:169
static const IEnumVARIANTVtbl dictenumvtbl
Definition: dictionary.c:401
static DWORD get_num_hash(FLOAT num)
Definition: dictionary.c:840
static HRESULT get_flt_hash(FLOAT flt, LONG *hash)
Definition: dictionary.c:845
static HRESULT WINAPI dict_enum_Clone(IEnumVARIANT *iface, IEnumVARIANT **cloned)
Definition: dictionary.c:394
static ULONG WINAPI dictionary_Release(IDictionary *iface)
Definition: dictionary.c:497
static BOOL is_string_key(const VARIANT *key)
Definition: dictionary.c:106
static HRESULT WINAPI dictionary_Remove(IDictionary *iface, VARIANT *key)
Definition: dictionary.c:749
static HRESULT WINAPI dict_enum_Next(IEnumVARIANT *iface, ULONG count, VARIANT *keys, ULONG *fetched)
Definition: dictionary.c:335
static HRESULT WINAPI dictionary_putref_Item(IDictionary *iface, VARIANT *key, VARIANT *item)
Definition: dictionary.c:566
static struct list * get_bucket_head(struct dictionary *dict, DWORD hash)
Definition: dictionary.c:101
static HRESULT WINAPI dictionary_Invoke(IDictionary *iface, DISPID dispIdMember, REFIID riid, LCID lcid, WORD wFlags, DISPPARAMS *pDispParams, VARIANT *pVarResult, EXCEPINFO *pExcepInfo, UINT *puArgErr)
Definition: dictionary.c:546
static HRESULT WINAPI dictionary_put_Item(IDictionary *iface, VARIANT *key, VARIANT *item)
Definition: dictionary.c:579
static HRESULT WINAPI dictionary_Add(IDictionary *iface, VARIANT *key, VARIANT *item)
Definition: dictionary.c:609
static HRESULT WINAPI dictionary_put_Key(IDictionary *iface, VARIANT *key, VARIANT *newkey)
Definition: dictionary.c:684
#define DICT_HASH_MOD
Definition: dictionary.c:42
static BOOL is_numeric_key(const VARIANT *key)
Definition: dictionary.c:116
static HRESULT WINAPI dictionary_Keys(IDictionary *iface, VARIANT *keys)
Definition: dictionary.c:709
static HRESULT add_keyitem_pair(struct dictionary *dict, VARIANT *key, VARIANT *item)
Definition: dictionary.c:241
static DWORD get_ptr_hash(void *ptr)
Definition: dictionary.c:861
static BOOL numeric_key_eq(const VARIANT *key1, const VARIANT *key2)
Definition: dictionary.c:154
static ULONG WINAPI dict_enum_Release(IEnumVARIANT *iface)
Definition: dictionary.c:318
static HRESULT WINAPI dictionary_Exists(IDictionary *iface, VARIANT *key, VARIANT_BOOL *exists)
Definition: dictionary.c:631
static HRESULT WINAPI dictionary_RemoveAll(IDictionary *iface)
Definition: dictionary.c:768
static HRESULT WINAPI dict_enum_Reset(IEnumVARIANT *iface)
Definition: dictionary.c:382
static HRESULT WINAPI dictionary_put_CompareMode(IDictionary *iface, CompareMethod method)
Definition: dictionary.c:790
static HRESULT WINAPI dictionary_GetTypeInfoCount(IDictionary *iface, UINT *pctinfo)
Definition: dictionary.c:513
static HRESULT WINAPI dictionary_get_CompareMode(IDictionary *iface, CompareMethod *method)
Definition: dictionary.c:803
static struct dictionary_enum * impl_from_IEnumVARIANT(IEnumVARIANT *iface)
Definition: dictionary.c:96
static HRESULT WINAPI dictionary_get_Count(IDictionary *iface, LONG *count)
Definition: dictionary.c:621
static const char * debugstr_variant(const VARIANT *var)
Definition: dom.c:505
method
Definition: dragdrop.c:54
return ret
Definition: mutex.c:147
#define ULONG_PTR
Definition: config.h:101
#define PtrToUlong(u)
Definition: config.h:107
unsigned short WORD
Definition: ntddk_ex.h:93
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned long DWORD
Definition: ntddk_ex.h:95
FxCollectionEntry * cur
const GLdouble * v
Definition: gl.h:2040
GLuint GLuint GLsizei count
Definition: gl.h:1545
GLenum src
Definition: glext.h:6340
GLuint64EXT GLuint GLuint GLenum GLenum GLuint GLuint GLenum GLuint GLuint key1
Definition: glext.h:10608
GLuint GLuint num
Definition: glext.h:9618
GLfloat GLfloat v1
Definition: glext.h:6062
GLfloat GLfloat GLfloat v2
Definition: glext.h:6063
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble * u
Definition: glfuncs.h:240
unsigned int UINT
Definition: sysinfo.c:13
REFIID riid
Definition: atlbase.h:39
#define S_OK
Definition: intsafe.h:52
#define SUCCEEDED(hr)
Definition: intsafe.h:50
#define FAILED(hr)
Definition: intsafe.h:51
uint32_t entry
Definition: isohybrid.c:63
#define debugstr_guid
Definition: kernel32.h:35
static PVOID ptr
Definition: dispmode.c:27
const IID IID_IObjectWithSite
static IUnknown * outer
Definition: compobj.c:82
static VARIANTARG static DISPID
Definition: ordinal.c:49
int notify
Definition: msacm.c:1366
#define V_UI1(A)
Definition: oleauto.h:266
#define V_ARRAY(A)
Definition: oleauto.h:222
#define V_BSTRREF(A)
Definition: oleauto.h:227
#define V_R4REF(A)
Definition: oleauto.h:261
#define V_UNKNOWN(A)
Definition: oleauto.h:281
#define V_UNKNOWNREF(A)
Definition: oleauto.h:282
#define V_VT(A)
Definition: oleauto.h:211
#define V_BSTR(A)
Definition: oleauto.h:226
#define V_DATEREF(A)
Definition: oleauto.h:232
#define V_I4(A)
Definition: oleauto.h:247
#define V_R4(A)
Definition: oleauto.h:260
#define V_R8(A)
Definition: oleauto.h:262
#define V_I2REF(A)
Definition: oleauto.h:246
#define V_DATE(A)
Definition: oleauto.h:231
#define V_UI1REF(A)
Definition: oleauto.h:267
#define V_R8REF(A)
Definition: oleauto.h:263
#define V_I2(A)
Definition: oleauto.h:245
#define V_I4REF(A)
Definition: oleauto.h:248
#define CTL_E_ILLEGALFUNCTIONCALL
Definition: olectl.h:267
const GUID IID_IProvideClassInfo
const GUID IID_IDispatch
static TCHAR * items[]
Definition: page1.c:45
short WCHAR
Definition: pedump.c:58
long LONG
Definition: pedump.c:60
#define IsEqualGUID(rguid1, rguid2)
Definition: guiddef.h:147
#define IsEqualIID(riid1, riid2)
Definition: guiddef.h:95
#define REFIID
Definition: guiddef.h:118
#define calloc
Definition: rosglue.h:14
const WCHAR * str
void init_classinfo(const GUID *guid, IUnknown *outer, struct provideclassinfo *classinfo)
Definition: scrrun.c:230
@ IDictionary_tid
DWORD LCID
Definition: nls.h:13
#define LIST_FOR_EACH_ENTRY(elem, list, type, field)
Definition: list.h:236
#define LIST_FOR_EACH_ENTRY_SAFE(cursor, cursor2, list, type, field)
Definition: list.h:242
__WINE_SERVER_LIST_INLINE struct list * list_next(const struct list *list, const struct list *elem)
Definition: list.h:117
#define LIST_FOR_EACH(cursor, list)
Definition: list.h:226
XML_HIDDEN void xmlParserErrors const char const xmlChar const xmlChar * str2
Definition: parser.h:35
XML_HIDDEN void xmlParserErrors const char const xmlChar * str1
Definition: parser.h:35
#define towlower(c)
Definition: wctype.h:97
#define TRACE(s)
Definition: solgame.cpp:4
IEnumVARIANT IEnumVARIANT_iface
Definition: dictionary.c:83
struct dictionary * dict
Definition: dictionary.c:86
struct list notify
Definition: dictionary.c:88
struct list * cur
Definition: dictionary.c:87
struct list pairs
Definition: dictionary.c:76
struct list buckets[BUCKET_COUNT]
Definition: dictionary.c:77
LONG ref
Definition: dictionary.c:72
struct list notifier
Definition: dictionary.c:78
struct provideclassinfo classinfo
Definition: dictionary.c:70
LONG count
Definition: dictionary.c:75
IDictionary IDictionary_iface
Definition: dictionary.c:71
CompareMethod method
Definition: dictionary.c:74
Definition: main.c:439
Definition: copy.c:22
VARIANT item
Definition: dictionary.c:65
struct list entry
Definition: dictionary.c:61
DWORD hash
Definition: dictionary.c:63
VARIANT key
Definition: dictionary.c:64
struct list bucket
Definition: dictionary.c:62
Definition: list.h:15
Definition: _pair.h:47
Definition: send.c:48
#define LIST_ENTRY(type)
Definition: queue.h:175
float FLOAT
Definition: typedefs.h:69
#define CONTAINING_RECORD(address, type, field)
Definition: typedefs.h:260
uint32_t ULONG
Definition: typedefs.h:59
HRESULT WINAPI VariantCopy(VARIANTARG *pvargDest, const VARIANTARG *pvargSrc)
Definition: variant.c:724
HRESULT WINAPI DECLSPEC_HOTPATCH VariantChangeType(VARIANTARG *pvargDest, const VARIANTARG *pvargSrc, USHORT wFlags, VARTYPE vt)
Definition: variant.c:939
HRESULT WINAPI DECLSPEC_HOTPATCH VariantClear(VARIANTARG *pVarg)
Definition: variant.c:626
HRESULT WINAPI VariantCopyInd(VARIANT *pvargDest, const VARIANTARG *pvargSrc)
Definition: variant.c:823
void WINAPI VariantInit(VARIANTARG *pVarg)
Definition: variant.c:547
WINBASEAPI _In_ DWORD _Out_ _In_ WORD wFlags
Definition: wincon_undoc.h:337
#define WINAPI
Definition: msvc.h:6
#define S_FALSE
Definition: winerror.h:3451
#define E_NOINTERFACE
Definition: winerror.h:3479