ReactOS 0.4.16-dev-1946-g52006dd
ndr_typelib.c
Go to the documentation of this file.
1/*
2 * Type library proxy/stub implementation
3 *
4 * Copyright 2018 Zebediah Figura
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 <assert.h>
22
23#define COBJMACROS
24#ifdef __REACTOS__
25#include "objbase.h"
26#endif
27#include "oaidl.h"
28#define USE_STUBLESS_PROXY
29#include "rpcproxy.h"
30#include "ndrtypes.h"
31#include "wine/debug.h"
32
33#include "cpsf.h"
34#include "initguid.h"
35#include "ndr_types.h"
36#include "ndr_stubless.h"
37
39
40static size_t write_type_tfs(ITypeInfo *typeinfo, unsigned char *str,
41 size_t *len, TYPEDESC *desc, BOOL toplevel, BOOL onstack);
42
43#define WRITE_CHAR(str, len, val) \
44 do { if ((str)) (str)[(len)] = (val); (len)++; } while (0)
45#define WRITE_SHORT(str, len, val) \
46 do { if ((str)) *((short *)((str) + (len))) = (val); (len) += 2; } while (0)
47#define WRITE_INT(str, len, val) \
48 do { if ((str)) *((int *)((str) + (len))) = (val); (len) += 4; } while (0)
49#define ROUND_SIZE(size, alignment) (((size) + ((alignment) - 1)) & ~((alignment) - 1))
50
52
54{
55 return ndr_types_ProxyFileInfo.pProxyVtblList[0]->header.pStublessProxyInfo;
56}
57
58static const NDR_PARAM_OIF *get_ndr_types_params( unsigned int *nb_params )
59{
61 const unsigned char *format = proxy->ProcFormatString + proxy->FormatStringOffset[3];
64
65 if (proc->Oi_flags & Oi_HAS_RPCFLAGS)
66 format += sizeof(NDR_PROC_HEADER_RPC);
67 else
68 format += sizeof(NDR_PROC_HEADER);
69
71 format += sizeof(*header);
72 if (header->Oi2Flags.HasExtensions)
73 {
75 format += ext->Size;
76 }
77 *nb_params = header->number_of_params;
78 return (const NDR_PARAM_OIF *)format;
79}
80
81static unsigned short get_tfs_offset( int param )
82{
83 unsigned int nb_params;
84 const NDR_PARAM_OIF *params = get_ndr_types_params( &nb_params );
85
86 assert( param < nb_params );
87 return params[param].u.type_offset;
88}
89
90static const unsigned char *get_type_format_string( size_t *size )
91{
92 unsigned int nb_params;
93 const NDR_PARAM_OIF *params = get_ndr_types_params( &nb_params );
94
95 *size = params[nb_params - 1].u.type_offset;
97}
98
99static unsigned short write_oleaut_tfs(VARTYPE vt)
100{
101 switch (vt)
102 {
103 case VT_BSTR: return get_tfs_offset( 0 );
104 case VT_UNKNOWN: return get_tfs_offset( 1 );
105 case VT_DISPATCH: return get_tfs_offset( 2 );
106 case VT_VARIANT: return get_tfs_offset( 3 );
107 case VT_SAFEARRAY: return get_tfs_offset( 4 );
108 }
109 return 0;
110}
111
112static unsigned char get_basetype(ITypeInfo *typeinfo, TYPEDESC *desc)
113{
114 ITypeInfo *refinfo;
115 unsigned char ret;
116 TYPEATTR *attr;
117
118 switch (desc->vt)
119 {
120 case VT_I1: return FC_SMALL;
121 case VT_BOOL:
122 case VT_I2: return FC_SHORT;
123 case VT_INT:
124 case VT_ERROR:
125 case VT_HRESULT:
126 case VT_I4: return FC_LONG;
127 case VT_I8:
128 case VT_UI8: return FC_HYPER;
129 case VT_UI1: return FC_USMALL;
130 case VT_UI2: return FC_USHORT;
131 case VT_UINT:
132 case VT_UI4: return FC_ULONG;
133 case VT_R4: return FC_FLOAT;
134 case VT_DATE:
135 case VT_R8: return FC_DOUBLE;
136 case VT_USERDEFINED:
137 ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
138 ITypeInfo_GetTypeAttr(refinfo, &attr);
139 if (attr->typekind == TKIND_ENUM)
140 ret = FC_ENUM32;
141 else if (attr->typekind == TKIND_ALIAS)
142 ret = get_basetype(refinfo, &attr->tdescAlias);
143 else
144 ret = 0;
145 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
146 ITypeInfo_Release(refinfo);
147 return ret;
148 default: return 0;
149 }
150}
151
152static unsigned int type_memsize(ITypeInfo *typeinfo, TYPEDESC *desc, unsigned int *align_ret)
153{
154 unsigned int size, align;
155
156 switch (desc->vt)
157 {
158 case VT_I1:
159 case VT_UI1:
160 size = align = 1;
161 break;
162 case VT_I2:
163 case VT_UI2:
164 case VT_BOOL:
165 size = align = 2;
166 break;
167 case VT_I4:
168 case VT_UI4:
169 case VT_R4:
170 case VT_INT:
171 case VT_UINT:
172 case VT_ERROR:
173 case VT_HRESULT:
174 size = align = 4;
175 break;
176 case VT_I8:
177 case VT_UI8:
178 case VT_R8:
179 case VT_DATE:
180 size = align = 8;
181 break;
182 case VT_BSTR:
183 case VT_SAFEARRAY:
184 case VT_PTR:
185 case VT_UNKNOWN:
186 case VT_DISPATCH:
187 size = align = sizeof(void *);
188 break;
189 case VT_VARIANT:
190 align = 8;
191 size = sizeof(VARIANT);
192 break;
193 case VT_CARRAY:
194 {
195 unsigned int i;
196 size = type_memsize(typeinfo, &desc->lpadesc->tdescElem, &align);
197 for (i = 0; i < desc->lpadesc->cDims; i++)
198 size *= desc->lpadesc->rgbounds[i].cElements;
199 break;
200 }
201 case VT_USERDEFINED:
202 {
203 ITypeInfo *refinfo;
204 TYPEATTR *attr;
205
206 ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
207 ITypeInfo_GetTypeAttr(refinfo, &attr);
208 size = attr->cbSizeInstance;
209 align = attr->cbAlignment;
210 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
211 ITypeInfo_Release(refinfo);
212 break;
213 }
214 default:
215 FIXME("unhandled type %u\n", desc->vt);
216 return 0;
217 }
218 if (align_ret) *align_ret = align;
219 return size;
220}
221
223{
224 ITypeInfo *refinfo;
225 BOOL ret = FALSE;
226 TYPEATTR *attr;
227
228 if (tdesc->vt == VT_USERDEFINED)
229 {
230 ITypeInfo_GetRefTypeInfo(typeinfo, tdesc->hreftype, &refinfo);
231 ITypeInfo_GetTypeAttr(refinfo, &attr);
232
233 if (attr->typekind == TKIND_INTERFACE
234 || attr->typekind == TKIND_DISPATCH
235 || attr->typekind == TKIND_COCLASS)
236 ret = TRUE;
237 else if (attr->typekind == TKIND_ALIAS)
238 ret = type_pointer_is_iface(refinfo, &attr->tdescAlias);
239
240 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
241 ITypeInfo_Release(refinfo);
242 }
243
244 return ret;
245}
246
247static unsigned char get_array_fc(ITypeInfo *typeinfo, TYPEDESC *desc);
248static unsigned char get_struct_fc(ITypeInfo *typeinfo, TYPEATTR *attr);
249
250static unsigned char get_struct_member_fc(ITypeInfo *typeinfo, TYPEDESC *tdesc)
251{
252 unsigned char fc;
253 ITypeInfo *refinfo;
254 TYPEATTR *attr;
255
256 switch (tdesc->vt)
257 {
258 case VT_BSTR:
259 case VT_SAFEARRAY:
260 return (sizeof(void *) == 4) ? FC_PSTRUCT : FC_BOGUS_STRUCT;
261 case VT_CY:
262 return FC_STRUCT;
263 case VT_VARIANT:
264 case VT_UNKNOWN:
265 case VT_DISPATCH:
266 return FC_BOGUS_STRUCT;
267 case VT_CARRAY:
268 if (get_array_fc(typeinfo, &tdesc->lpadesc->tdescElem) == FC_BOGUS_ARRAY)
269 return FC_BOGUS_STRUCT;
270 return FC_STRUCT;
271 case VT_PTR:
274 else
275 fc = (sizeof(void *) == 4) ? FC_PSTRUCT : FC_BOGUS_STRUCT;
276 break;
277 case VT_USERDEFINED:
278 ITypeInfo_GetRefTypeInfo(typeinfo, tdesc->hreftype, &refinfo);
279 ITypeInfo_GetTypeAttr(refinfo, &attr);
280
281 switch (attr->typekind)
282 {
283 case TKIND_ENUM:
284 fc = FC_STRUCT;
285 break;
286 case TKIND_RECORD:
287 fc = get_struct_fc(refinfo, attr);
288 break;
289 case TKIND_INTERFACE:
290 case TKIND_DISPATCH:
291 case TKIND_COCLASS:
293 break;
294 case TKIND_ALIAS:
295 fc = get_struct_member_fc(refinfo, &attr->tdescAlias);
296 break;
297 default:
298 FIXME("Unhandled kind %#x.\n", attr->typekind);
300 break;
301 }
302
303 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
304 ITypeInfo_Release(refinfo);
305 break;
306 default:
307 if (get_basetype(typeinfo, tdesc))
308 return FC_STRUCT;
309 else
310 {
311 FIXME("Unhandled type %u.\n", tdesc->vt);
312 return FC_BOGUS_STRUCT;
313 }
314 }
315
316 return fc;
317}
318
319static unsigned char get_struct_fc(ITypeInfo *typeinfo, TYPEATTR *attr)
320{
321 unsigned char fc = FC_STRUCT, member_fc;
322 VARDESC *desc;
323 WORD i;
324
325 for (i = 0; i < attr->cVars; i++)
326 {
327 ITypeInfo_GetVarDesc(typeinfo, i, &desc);
328
329 member_fc = get_struct_member_fc(typeinfo, &desc->elemdescVar.tdesc);
330 if (member_fc == FC_BOGUS_STRUCT)
332 else if (member_fc == FC_PSTRUCT && fc != FC_BOGUS_STRUCT)
333 fc = FC_PSTRUCT;
334
335 ITypeInfo_ReleaseVarDesc(typeinfo, desc);
336 }
337
338 return fc;
339}
340
341static unsigned char get_array_fc(ITypeInfo *typeinfo, TYPEDESC *desc)
342{
343 switch (desc->vt)
344 {
345 case VT_CY:
346 return FC_LGFARRAY;
347 case VT_CARRAY:
348 return get_array_fc(typeinfo, &desc->lpadesc->tdescElem);
349 case VT_USERDEFINED:
350 {
351 ITypeInfo *refinfo;
352 TYPEATTR *attr;
353 unsigned char fc;
354
355 ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
356 ITypeInfo_GetTypeAttr(refinfo, &attr);
357
358 if (attr->typekind == TKIND_ENUM)
359 fc = FC_LGFARRAY;
360 else if (attr->typekind == TKIND_RECORD && get_struct_fc(refinfo, attr) == FC_STRUCT)
361 fc = FC_LGFARRAY;
362 else if (attr->typekind == TKIND_ALIAS)
363 fc = get_array_fc(refinfo, &attr->tdescAlias);
364 else
366
367 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
368 ITypeInfo_Release(refinfo);
369
370 return fc;
371 }
372 default:
374 }
375}
376
378{
379 if (desc->vt == VT_PTR)
380 return !type_pointer_is_iface(typeinfo, desc->lptdesc);
381 else if (desc->vt == VT_USERDEFINED)
382 {
383 ITypeInfo *refinfo;
384 TYPEATTR *attr;
385 BOOL ret;
386
387 ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
388 ITypeInfo_GetTypeAttr(refinfo, &attr);
389
390 if (attr->typekind == TKIND_ALIAS)
391 ret = type_is_non_iface_pointer(refinfo, &attr->tdescAlias);
392 else
393 ret = FALSE;
394
395 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
396 ITypeInfo_Release(refinfo);
397
398 return ret;
399 }
400 else
401 return FALSE;
402}
403
404static void write_struct_members(ITypeInfo *typeinfo, unsigned char *str,
405 size_t *len, TYPEATTR *attr)
406{
407 unsigned int struct_offset = 0;
408 unsigned char basetype;
409 TYPEDESC *tdesc;
410 VARDESC *desc;
411 WORD i;
412
413 for (i = 0; i < attr->cVars; i++)
414 {
415 ITypeInfo_GetVarDesc(typeinfo, i, &desc);
416 tdesc = &desc->elemdescVar.tdesc;
417
418 if (struct_offset != desc->oInst)
419 WRITE_CHAR(str, *len, FC_STRUCTPAD1 + desc->oInst - struct_offset - 1);
420 struct_offset = desc->oInst + type_memsize(typeinfo, tdesc, NULL);
421
422 if ((basetype = get_basetype(typeinfo, tdesc)))
423 WRITE_CHAR(str, *len, basetype);
424 else if (type_is_non_iface_pointer(typeinfo, tdesc))
426 else
427 {
429 WRITE_CHAR(str, *len, 0);
430 WRITE_SHORT(str, *len, 0);
431 }
432
433 ITypeInfo_ReleaseVarDesc(typeinfo, desc);
434 }
435 if (!(*len & 1))
438}
439
440static void write_simple_struct_tfs(ITypeInfo *typeinfo, unsigned char *str,
441 size_t *len, TYPEATTR *attr)
442{
444}
445
447{
448 if (desc->vt == VT_PTR || desc->vt == VT_UNKNOWN || desc->vt == VT_DISPATCH)
449 return TRUE;
450 else if (desc->vt == VT_USERDEFINED)
451 {
452 ITypeInfo *refinfo;
453 BOOL ret = FALSE;
454 TYPEATTR *attr;
455
456 ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
457 ITypeInfo_GetTypeAttr(refinfo, &attr);
458
459 if (attr->typekind == TKIND_ALIAS)
460 ret = type_needs_pointer_deref(refinfo, &attr->tdescAlias);
461
462 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
463 ITypeInfo_Release(refinfo);
464
465 return ret;
466 }
467 else
468 return FALSE;
469}
470
472 TYPEDESC *desc, unsigned char *str, size_t *len)
473{
474 unsigned char basetype;
475
476 if (desc->vt == VT_PTR && !type_pointer_is_iface(typeinfo, desc->lptdesc))
477 {
479 if ((basetype = get_basetype(typeinfo, desc->lptdesc)))
480 {
482 WRITE_CHAR(str, *len, basetype);
484 }
485 else
486 {
489 else
490 WRITE_CHAR(str, *len, 0);
491 WRITE_SHORT(str, *len, 0);
492 }
493 }
494 else if (desc->vt == VT_USERDEFINED)
495 {
496 ITypeInfo *refinfo;
497 TYPEATTR *attr;
498
499 ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
500 ITypeInfo_GetTypeAttr(refinfo, &attr);
501
502 if (attr->typekind == TKIND_ALIAS)
503 write_complex_struct_pointer_layout(refinfo, &attr->tdescAlias, str, len);
504
505 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
506 ITypeInfo_Release(refinfo);
507 }
508}
509
511 TYPEDESC *desc, unsigned char *str, size_t *len)
512{
513 if (desc->vt == VT_PTR && !type_pointer_is_iface(typeinfo, desc->lptdesc)
514 && !get_basetype(typeinfo, desc->lptdesc))
515 {
516 return write_type_tfs(typeinfo, str, len, desc->lptdesc, FALSE, FALSE);
517 }
518 else if (desc->vt == VT_USERDEFINED)
519 {
520 ITypeInfo *refinfo;
521 TYPEATTR *attr;
522 size_t ret = 0;
523
524 ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
525 ITypeInfo_GetTypeAttr(refinfo, &attr);
526
527 if (attr->typekind == TKIND_ALIAS)
528 ret = write_complex_struct_pointer_ref(refinfo, &attr->tdescAlias, str, len);
529
530 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
531 ITypeInfo_Release(refinfo);
532
533 return ret;
534 }
535
536 return 0;
537}
538
539static void write_complex_struct_tfs(ITypeInfo *typeinfo, unsigned char *str,
540 size_t *len, TYPEATTR *attr)
541{
542 size_t pointer_layout_offset, pointer_layout, member_layout, ref;
543 unsigned int struct_offset = 0;
544 TYPEDESC *tdesc;
545 VARDESC *desc;
546 WORD i;
547
548 WRITE_SHORT(str, *len, 0); /* conformant array description */
549 pointer_layout_offset = *len;
550 WRITE_SHORT(str, *len, 0); /* pointer layout; will be filled in later */
551 member_layout = *len;
552
553 /* First pass: write the struct members and pointer layout, but do not yet
554 * write the offsets for embedded complexes and pointer refs. These must be
555 * handled after we write the whole struct description, since it must be
556 * contiguous. */
557
559
560 pointer_layout = *len;
561 if (str) *((short *)(str + pointer_layout_offset)) = pointer_layout - pointer_layout_offset;
562
563 for (i = 0; i < attr->cVars; i++)
564 {
565 ITypeInfo_GetVarDesc(typeinfo, i, &desc);
567 ITypeInfo_ReleaseVarDesc(typeinfo, desc);
568 }
569
570 /* Second pass: write types for embedded complexes and non-simple pointers. */
571
572 struct_offset = 0;
573
574 for (i = 0; i < attr->cVars; i++)
575 {
576 ITypeInfo_GetVarDesc(typeinfo, i, &desc);
577 tdesc = &desc->elemdescVar.tdesc;
578
579 if (struct_offset != desc->oInst)
580 member_layout++; /* alignment directive */
581 struct_offset = desc->oInst + type_memsize(typeinfo, tdesc, NULL);
582
583 if (get_basetype(typeinfo, tdesc))
584 member_layout++;
585 else if (type_is_non_iface_pointer(typeinfo, tdesc))
586 {
587 member_layout++;
589 {
590 if (str) *((short *)(str + pointer_layout + 2)) = ref - (pointer_layout + 2);
591 }
592 pointer_layout += 4;
593 }
594 else
595 {
597 if (str) *((short *)(str + member_layout + 2)) = ref - (member_layout + 2);
598 member_layout += 4;
599 }
600
601 ITypeInfo_ReleaseVarDesc(typeinfo, desc);
602 }
603}
604
605static size_t write_struct_tfs(ITypeInfo *typeinfo, unsigned char *str,
606 size_t *len, TYPEATTR *attr)
607{
608 unsigned char fc = get_struct_fc(typeinfo, attr);
609 size_t off = *len;
610
611 /* For the sake of simplicity, write pointer structs as complex structs. */
612 if (fc == FC_PSTRUCT)
614
615 WRITE_CHAR (str, *len, fc);
616 WRITE_CHAR (str, *len, attr->cbAlignment - 1);
617 WRITE_SHORT(str, *len, attr->cbSizeInstance);
618
619 if (fc == FC_STRUCT)
621 else if (fc == FC_BOGUS_STRUCT)
623
624 return off;
625}
626
627static size_t write_array_tfs(ITypeInfo *typeinfo, unsigned char *str,
628 size_t *len, ARRAYDESC *desc)
629{
630 unsigned char fc = get_array_fc(typeinfo, &desc->tdescElem);
631 unsigned char basetype;
632 size_t ref = 0, off;
633 ULONG size = 1;
634 USHORT i;
635
636 if (!(basetype = get_basetype(typeinfo, &desc->tdescElem)))
637 ref = write_type_tfs(typeinfo, str, len, &desc->tdescElem, FALSE, FALSE);
638
639 /* In theory arrays should be nested, but there's no reason not to marshal
640 * [x][y] as [x*y]. */
641 for (i = 0; i < desc->cDims; i++) size *= desc->rgbounds[i].cElements;
642
643 off = *len;
644
645 WRITE_CHAR(str, *len, fc);
646 WRITE_CHAR(str, *len, 0);
647 if (fc == FC_BOGUS_ARRAY)
648 {
650 WRITE_INT(str, *len, 0xffffffff); /* conformance */
651 WRITE_SHORT(str, *len, 0);
652 WRITE_INT(str, *len, 0xffffffff); /* variance */
653 WRITE_SHORT(str, *len, 0);
654 }
655 else
656 {
657 size *= type_memsize(typeinfo, &desc->tdescElem, NULL);
658 WRITE_INT(str, *len, size);
659 }
660
661 if (basetype)
662 WRITE_CHAR(str, *len, basetype);
663 else
664 {
666 WRITE_CHAR (str, *len, 0);
667 WRITE_SHORT(str, *len, ref - *len);
669 }
671
672 return off;
673}
674
675static size_t write_ip_tfs(unsigned char *str, size_t *len, const GUID *iid)
676{
677 size_t off = *len;
678
679 if (str)
680 {
681 str[*len] = FC_IP;
682 str[*len+1] = FC_CONSTANT_IID;
683 memcpy(str + *len + 2, iid, sizeof(*iid));
684 }
685 *len += 2 + sizeof(*iid);
686
687 return off;
688}
689
691{
692 ITypeInfo *refinfo;
693 HREFTYPE reftype;
694 TYPEATTR *attr;
695 int flags, i;
696
697 for (i = 0; i < count; ++i)
698 {
699 ITypeInfo_GetImplTypeFlags(typeinfo, i, &flags);
700 if (flags & IMPLTYPEFLAG_FDEFAULT)
701 break;
702 }
703
704 /* If no interface was explicitly marked default, choose the first one. */
705 if (i == count)
706 i = 0;
707
708 ITypeInfo_GetRefTypeOfImplType(typeinfo, i, &reftype);
709 ITypeInfo_GetRefTypeInfo(typeinfo, reftype, &refinfo);
710 ITypeInfo_GetTypeAttr(refinfo, &attr);
711 *iid = attr->guid;
712 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
713 ITypeInfo_Release(refinfo);
714}
715
716static size_t write_pointer_tfs(ITypeInfo *typeinfo, unsigned char *str,
717 size_t *len, TYPEDESC *desc, BOOL toplevel, BOOL onstack)
718{
719 unsigned char basetype, flags = 0;
720 size_t ref, off = *len;
721 ITypeInfo *refinfo;
722 TYPEATTR *attr;
723 GUID guid;
724
725 if (desc->vt == VT_USERDEFINED)
726 {
727 ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
728 ITypeInfo_GetTypeAttr(refinfo, &attr);
729
730 switch (attr->typekind)
731 {
732 case TKIND_ENUM:
733 assert(!toplevel); /* toplevel base-type pointers should use IsSimpleRef */
738 break;
739 case TKIND_RECORD:
740 assert(!toplevel); /* toplevel struct pointers should use IsSimpleRef */
741 ref = write_struct_tfs(refinfo, str, len, attr);
742 off = *len;
743 WRITE_CHAR (str, *len, FC_UP);
744 WRITE_CHAR (str, *len, 0);
745 WRITE_SHORT(str, *len, ref - *len);
746 break;
747 case TKIND_INTERFACE:
748 case TKIND_DISPATCH:
749 write_ip_tfs(str, len, &attr->guid);
750 break;
751 case TKIND_COCLASS:
752 get_default_iface(refinfo, attr->cImplTypes, &guid);
754 break;
755 case TKIND_ALIAS:
756 off = write_pointer_tfs(refinfo, str, len, &attr->tdescAlias, toplevel, onstack);
757 break;
758 default:
759 FIXME("unhandled kind %#x\n", attr->typekind);
760 WRITE_SHORT(str, *len, 0);
761 break;
762 }
763
764 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
765 ITypeInfo_Release(refinfo);
766 }
767 else if ((basetype = get_basetype(typeinfo, desc)))
768 {
769 assert(!toplevel); /* toplevel base-type pointers should use IsSimpleRef */
772 WRITE_CHAR(str, *len, basetype);
774 }
775 else
776 {
778
779 if (onstack) flags |= FC_ALLOCED_ON_STACK;
780 if (desc->vt == VT_PTR || desc->vt == VT_UNKNOWN || desc->vt == VT_DISPATCH)
782
783 off = *len;
784
786 WRITE_CHAR (str, *len, flags);
787 WRITE_SHORT(str, *len, ref - *len);
788 }
789
790 return off;
791}
792
793static size_t write_type_tfs(ITypeInfo *typeinfo, unsigned char *str,
794 size_t *len, TYPEDESC *desc, BOOL toplevel, BOOL onstack)
795{
796 ITypeInfo *refinfo;
797 TYPEATTR *attr;
798 size_t off;
799 GUID guid;
800
801 TRACE("vt %d%s\n", desc->vt, toplevel ? " (toplevel)" : "");
802
803 if ((off = write_oleaut_tfs(desc->vt)))
804 return off;
805
806 switch (desc->vt)
807 {
808 case VT_PTR:
809 return write_pointer_tfs(typeinfo, str, len, desc->lptdesc, toplevel, onstack);
810 case VT_CARRAY:
811 return write_array_tfs(typeinfo, str, len, desc->lpadesc);
812 case VT_USERDEFINED:
813 ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
814 ITypeInfo_GetTypeAttr(refinfo, &attr);
815
816 switch (attr->typekind)
817 {
818 case TKIND_RECORD:
819 off = write_struct_tfs(refinfo, str, len, attr);
820 break;
821 case TKIND_INTERFACE:
822 case TKIND_DISPATCH:
823 /* These are treated as if they were interface pointers. */
824 off = *len;
825 write_ip_tfs(str, len, &attr->guid);
826 break;
827 case TKIND_COCLASS:
828 off = *len;
829 get_default_iface(refinfo, attr->cImplTypes, &guid);
831 break;
832 case TKIND_ALIAS:
833 off = write_type_tfs(refinfo, str, len, &attr->tdescAlias, toplevel, onstack);
834 break;
835 default:
836 FIXME("unhandled kind %u\n", attr->typekind);
837 off = *len;
838 WRITE_SHORT(str, *len, 0);
839 break;
840 }
841
842 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
843 ITypeInfo_Release(refinfo);
844 break;
845 default:
846 /* base types are always embedded directly */
848 FIXME("unhandled type %u\n", desc->vt);
849 off = *len;
850 WRITE_SHORT(str, *len, 0);
851 break;
852 }
853
854 return off;
855}
856
857static unsigned int get_stack_size(ITypeInfo *typeinfo, TYPEDESC *desc, unsigned int *align, int *by_value)
858{
859 unsigned int size = *align = sizeof(void *);
860 int byval = 1;
861
862 switch (desc->vt)
863 {
864 case VT_R8:
865 case VT_I8:
866 case VT_UI8:
867 case VT_DATE:
868#ifdef __arm__
869 case VT_R4:
870 *align = 8;
871#endif
872 size = 8;
873 break;
874 case VT_PTR:
875 case VT_UNKNOWN:
876 case VT_DISPATCH:
877 case VT_CARRAY:
878 byval = 0;
879 break;
880 case VT_VARIANT:
881 case VT_USERDEFINED:
883 break;
884 default:
885 break;
886 }
887
888#ifdef __i386__
889 *align = sizeof(void *);
890#endif
891 if (byval)
892 {
893#ifdef __x86_64__
894 byval = (size == 1 || size == 2 || size == 4 || size == 8);
895#elif defined __aarch64__
896 byval = (size <= 16);
897#endif
898 }
899 if (!byval) size = *align = sizeof(void *);
900 else if (*align < sizeof(void *)) *align = sizeof(void *);
901 if (by_value) *by_value = byval;
902 return ROUND_SIZE( size, *align );
903}
904
905static const unsigned short MustSize = 0x0001;
906static const unsigned short MustFree = 0x0002;
907static const unsigned short IsIn = 0x0008;
908static const unsigned short IsOut = 0x0010;
909static const unsigned short IsReturn = 0x0020;
910static const unsigned short IsBasetype = 0x0040;
911static const unsigned short IsByValue = 0x0080;
912static const unsigned short IsSimpleRef = 0x0100;
913
914static HRESULT get_param_pointer_info(ITypeInfo *typeinfo, TYPEDESC *tdesc, int is_in,
915 int is_out, unsigned short *server_size, unsigned short *flags,
916 unsigned char *basetype, TYPEDESC **tfs_tdesc)
917{
918 ITypeInfo *refinfo;
919 HRESULT hr = S_OK;
920 TYPEATTR *attr;
921
922 switch (tdesc->vt)
923 {
924 case VT_UNKNOWN:
925 case VT_DISPATCH:
926 *flags |= MustFree;
927 if (is_in && is_out)
928 *server_size = sizeof(void *);
929 break;
930 case VT_PTR:
931 *flags |= MustFree;
932 if (type_pointer_is_iface(typeinfo, tdesc->lptdesc))
933 {
934 if (is_in && is_out)
935 *server_size = sizeof(void *);
936 }
937 else
938 *server_size = sizeof(void *);
939 break;
940 case VT_CARRAY:
942 *server_size = type_memsize(typeinfo, tdesc, NULL);
943 *tfs_tdesc = tdesc;
944 break;
945 case VT_USERDEFINED:
946 ITypeInfo_GetRefTypeInfo(typeinfo, tdesc->hreftype, &refinfo);
947 ITypeInfo_GetTypeAttr(refinfo, &attr);
948
949 switch (attr->typekind)
950 {
951 case TKIND_ENUM:
953 if (!is_in && is_out)
954 *server_size = sizeof(void *);
955 *basetype = FC_ENUM32;
956 break;
957 case TKIND_RECORD:
959 if (!is_in && is_out)
960 *server_size = attr->cbSizeInstance;
961 *tfs_tdesc = tdesc;
962 break;
963 case TKIND_INTERFACE:
964 case TKIND_DISPATCH:
965 case TKIND_COCLASS:
966 *flags |= MustFree;
967 break;
968 case TKIND_ALIAS:
969 hr = get_param_pointer_info(refinfo, &attr->tdescAlias, is_in,
970 is_out, server_size, flags, basetype, tfs_tdesc);
971 break;
972 default:
973 FIXME("unhandled kind %#x\n", attr->typekind);
974 hr = E_NOTIMPL;
975 break;
976 }
977
978 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
979 ITypeInfo_Release(refinfo);
980 break;
981 default:
982 *flags |= IsSimpleRef;
983 *tfs_tdesc = tdesc;
984 if (!is_in && is_out)
985 *server_size = type_memsize(typeinfo, tdesc, NULL);
986 if ((*basetype = get_basetype(typeinfo, tdesc)))
987 *flags |= IsBasetype;
988 else
989 *flags |= MustFree;
990 break;
991 }
992
993 return hr;
994}
995
996static HRESULT get_param_info(ITypeInfo *typeinfo, TYPEDESC *tdesc, int is_in,
997 int is_out, int by_val, unsigned short *server_size, unsigned short *flags,
998 unsigned char *basetype, TYPEDESC **tfs_tdesc)
999{
1000 ITypeInfo *refinfo;
1001 HRESULT hr = S_OK;
1002 TYPEATTR *attr;
1003
1004 *server_size = 0;
1005 *flags = MustSize;
1006 *basetype = 0;
1007 *tfs_tdesc = tdesc;
1008
1009 TRACE("vt %u\n", tdesc->vt);
1010
1011 switch (tdesc->vt)
1012 {
1013 case VT_VARIANT:
1014 case VT_BSTR:
1015 case VT_SAFEARRAY:
1016 case VT_CY:
1017 *flags |= (by_val ? IsByValue : IsSimpleRef) | MustFree;
1018 break;
1019 case VT_UNKNOWN:
1020 case VT_DISPATCH:
1021 case VT_CARRAY:
1022 *flags |= MustFree;
1023 break;
1024 case VT_PTR:
1025 return get_param_pointer_info(typeinfo, tdesc->lptdesc, is_in, is_out,
1026 server_size, flags, basetype, tfs_tdesc);
1027 case VT_USERDEFINED:
1028 ITypeInfo_GetRefTypeInfo(typeinfo, tdesc->hreftype, &refinfo);
1029 ITypeInfo_GetTypeAttr(refinfo, &attr);
1030
1031 switch (attr->typekind)
1032 {
1033 case TKIND_ENUM:
1034 *flags |= IsBasetype;
1035 *basetype = FC_ENUM32;
1036 break;
1037 case TKIND_RECORD:
1038 *flags |= (by_val ? IsByValue : IsSimpleRef) | MustFree;
1039 break;
1040 case TKIND_ALIAS:
1041 hr = get_param_info(refinfo, &attr->tdescAlias, is_in, is_out, 0,
1042 server_size, flags, basetype, tfs_tdesc);
1043 break;
1044
1045 case TKIND_INTERFACE:
1046 case TKIND_DISPATCH:
1047 case TKIND_COCLASS:
1048 /* These are treated as if they were interface pointers. */
1049 *flags |= MustFree;
1050 break;
1051
1052 default:
1053 FIXME("unhandled kind %#x\n", attr->typekind);
1054 hr = E_NOTIMPL;
1055 break;
1056 }
1057
1058 ITypeInfo_ReleaseTypeAttr(refinfo, attr);
1059 ITypeInfo_Release(refinfo);
1060 break;
1061 default:
1062 if ((*basetype = get_basetype(typeinfo, tdesc)))
1063 *flags |= IsBasetype;
1064 else
1065 {
1066 FIXME("unhandled type %u\n", tdesc->vt);
1067 return E_NOTIMPL;
1068 }
1069 break;
1070 }
1071
1072 return hr;
1073}
1074
1076 size_t *typelen, unsigned char *proc, size_t *proclen, ELEMDESC *desc,
1077 BOOL is_return, unsigned short *stack_offset)
1078{
1079 USHORT param_flags = desc->paramdesc.wParamFlags;
1080 TYPEDESC *tdesc = &desc->tdesc, *tfs_tdesc;
1081 unsigned short server_size;
1082 int byval;
1083 unsigned int align, stack_size = get_stack_size(typeinfo, tdesc, &align, &byval);
1084 unsigned char basetype;
1085 unsigned short flags;
1086 int is_in, is_out;
1087 size_t off = 0;
1088 HRESULT hr;
1089
1090 is_out = param_flags & PARAMFLAG_FOUT;
1091 is_in = (param_flags & PARAMFLAG_FIN) || (!is_out && !is_return);
1092
1093 hr = get_param_info(typeinfo, tdesc, is_in, is_out, byval, &server_size, &flags,
1094 &basetype, &tfs_tdesc);
1095
1096 if (is_in) flags |= IsIn;
1097 if (is_out) flags |= IsOut;
1098 if (is_return) flags |= IsOut | IsReturn;
1099
1100 server_size = (server_size + 7) / 8;
1101 if (server_size >= 8) server_size = 0;
1102 flags |= server_size << 13;
1103
1104 if (!basetype)
1105 off = write_type_tfs(typeinfo, type, typelen, tfs_tdesc, TRUE, server_size != 0);
1106
1107 if (SUCCEEDED(hr))
1108 {
1110
1111 WRITE_SHORT(proc, *proclen, flags);
1112 WRITE_SHORT(proc, *proclen, *stack_offset);
1113 WRITE_SHORT(proc, *proclen, basetype ? basetype : off);
1114
1115 *stack_offset += stack_size;
1116 }
1117
1118 return hr;
1119}
1120
1121#if defined __arm__ || defined __aarch64__
1122
1123/* replace consecutive params code by a repeat sequence: 0x9d code<1> repeat_count<2> */
1124static unsigned int compress_params_array( unsigned char *params, unsigned int count )
1125{
1126 unsigned int i, j;
1127
1128 for (i = 0; i + 4 <= count; i++)
1129 {
1130 for (j = 1; i + j < count; j++) if (params[i + j] != params[i]) break;
1131 if (j < 4) continue;
1132 params[i] = 0x9d;
1133 params[i + 2] = j & 0xff;
1134 params[i + 3] = j >> 8;
1135 memmove( params + i + 4, params + i + j, count - (i + j) );
1136 count -= j - 4;
1137 i += 3;
1138 }
1139 return count;
1140}
1141
1142/* fill the parameters array for the procedure extra data on ARM platforms */
1143static unsigned int fill_params_array( ITypeInfo *typeinfo, FUNCDESC *desc,
1144 unsigned char *params, unsigned int count )
1145{
1146 static const unsigned int pointer_size = sizeof(void *);
1147 unsigned int reg_count = 0, float_count = 0, double_count = 0, stack_pos = 0, offset = 0;
1148 unsigned int i, size, pos, align;
1149
1150 memset( params, 0x9f /* padding */, count );
1151
1152 /* This pointer */
1153 params[0] = 0x80 + reg_count++;
1155
1156 for (i = 0; i < desc->cParams; i++)
1157 {
1158 unsigned char basetype = get_basetype( typeinfo, &desc->lprgelemdescParam[i].tdesc );
1159
1160 size = get_stack_size( typeinfo, &desc->lprgelemdescParam[i].tdesc, &align, NULL );
1163
1164#ifdef __aarch64__
1165 switch (basetype)
1166 {
1167 case FC_FLOAT:
1168 case FC_DOUBLE:
1169 if (double_count >= 8) break;
1170 params[pos] = 0x88 + double_count++;
1171 offset += size;
1172 continue;
1173
1174 default:
1175 reg_count = ROUND_SIZE( reg_count, align / pointer_size );
1176 if (reg_count > 8 - size / pointer_size) break;
1177 while (size)
1178 {
1179 params[pos++] = 0x80 + reg_count++;
1181 size -= pointer_size;
1182 }
1183 continue;
1184 }
1185 (void)float_count; /* unused on arm64 */
1186#else
1187 switch (basetype)
1188 {
1189 case FC_FLOAT:
1190 if (!(float_count % 2)) float_count = max( float_count, double_count * 2 );
1191 if (float_count >= 16)
1192 {
1193 stack_pos = ROUND_SIZE( stack_pos, align );
1194 params[pos] = 0x100 - (offset - stack_pos) / pointer_size;
1195 stack_pos += size;
1196 }
1197 else
1198 {
1199 params[pos] = 0x84 + float_count++;
1200 }
1201 offset += size;
1202 continue;
1203
1204 case FC_DOUBLE:
1205 double_count = max( double_count, (float_count + 1) / 2 );
1206 if (double_count >= 8) break;
1207 params[pos] = 0x84 + 2 * double_count;
1208 params[pos + 1] = 0x84 + 2 * double_count + 1;
1209 double_count++;
1210 offset += size;
1211 continue;
1212
1213 default:
1214 reg_count = ROUND_SIZE( reg_count, align / pointer_size );
1215 if (reg_count <= 4 - size / pointer_size || !stack_pos)
1216 {
1217 while (size && reg_count < 4)
1218 {
1219 params[pos++] = 0x80 + reg_count++;
1221 size -= pointer_size;
1222 }
1223 }
1224 break;
1225 }
1226#endif
1227 stack_pos = ROUND_SIZE( stack_pos, align );
1228 memset( params + pos, 0x100 - (offset - stack_pos) / pointer_size, size / pointer_size );
1229 stack_pos += size;
1230 offset += size;
1231 }
1232
1233 while (count && params[count - 1] == 0x9f) count--;
1234 return count;
1235}
1236
1237#endif /* __arm__ || __aarch64__ */
1238
1240 WORD proc_idx, unsigned char *proc, size_t *proclen)
1241{
1242 unsigned int i, align, size, stack_size = sizeof(void *); /* This */
1243
1244 for (i = 0; i < desc->cParams; i++)
1245 {
1246 size = get_stack_size(typeinfo, &desc->lprgelemdescParam[i].tdesc, &align, NULL );
1247 stack_size = ROUND_SIZE( stack_size, align );
1248 stack_size += size;
1249 }
1250 stack_size += sizeof(void *); /* return */
1251
1252 WRITE_CHAR (proc, *proclen, FC_AUTO_HANDLE);
1254 WRITE_SHORT(proc, *proclen, proc_idx);
1255 WRITE_SHORT(proc, *proclen, stack_size);
1256
1257 WRITE_SHORT(proc, *proclen, 0); /* constant_client_buffer_size */
1258 WRITE_SHORT(proc, *proclen, 0); /* constant_server_buffer_size */
1259 WRITE_CHAR (proc, *proclen, 0x47); /* HasExtensions | HasReturn | ClientMustSize | ServerMustSize */
1260 WRITE_CHAR (proc, *proclen, desc->cParams + 1); /* incl. return value */
1261
1262#ifdef __i386__
1263 WRITE_CHAR (proc, *proclen, 8); /* extension size */
1264 WRITE_CHAR (proc, *proclen, 1); /* HasNewCorrDesc */
1265 WRITE_SHORT(proc, *proclen, 0); /* ClientCorrHint */
1266 WRITE_SHORT(proc, *proclen, 0); /* ServerCorrHint */
1267 WRITE_SHORT(proc, *proclen, 0); /* NotifyIndex */
1268#elif defined __x86_64__
1269 {
1270 unsigned short float_mask = 0;
1271
1272 for (i = 0; i < desc->cParams && i < 3; i++)
1273 {
1274 unsigned char basetype = get_basetype(typeinfo, &desc->lprgelemdescParam[i].tdesc);
1275 if (basetype == FC_FLOAT) float_mask |= (1 << ((i + 1) * 2));
1276 else if (basetype == FC_DOUBLE) float_mask |= (2 << ((i + 1) * 2));
1277 }
1278 WRITE_CHAR (proc, *proclen, 10); /* extension size */
1279 WRITE_CHAR (proc, *proclen, 1); /* HasNewCorrDesc */
1280 WRITE_SHORT(proc, *proclen, 0); /* ClientCorrHint */
1281 WRITE_SHORT(proc, *proclen, 0); /* ServerCorrHint */
1282 WRITE_SHORT(proc, *proclen, 0); /* NotifyIndex */
1283 WRITE_SHORT(proc, *proclen, float_mask);
1284 }
1285#else
1286 {
1287 unsigned int len, count = stack_size / sizeof(void *);
1288 unsigned char *params = malloc( count );
1289
1292 WRITE_CHAR (proc, *proclen, 8 + 3 + len + !(len % 2) ); /* extension size */
1293 WRITE_CHAR (proc, *proclen, 1); /* HasNewCorrDesc */
1294 WRITE_SHORT(proc, *proclen, 0); /* ClientCorrHint */
1295 WRITE_SHORT(proc, *proclen, 0); /* ServerCorrHint */
1296 WRITE_SHORT(proc, *proclen, 0); /* NotifyIndex */
1297 WRITE_SHORT(proc, *proclen, count);
1298 WRITE_CHAR (proc, *proclen, len);
1299 for (i = 0; i < len; i++) WRITE_CHAR (proc, *proclen, params[i]);
1300 if (!(len % 2)) WRITE_CHAR (proc, *proclen, 0);
1301 free( params );
1302 }
1303#endif
1304}
1305
1307 unsigned char *type, size_t *typelen, unsigned char *proc,
1308 size_t *proclen, unsigned short *offset)
1309{
1310 unsigned short stack_offset;
1311 WORD proc_idx, param_idx;
1312 FUNCDESC *desc;
1313 HRESULT hr;
1314
1315 for (proc_idx = 3; proc_idx < parentfuncs; proc_idx++)
1316 {
1317 if (offset)
1318 offset[proc_idx - 3] = -1;
1319 }
1320
1321 for (proc_idx = 0; proc_idx < funcs; proc_idx++)
1322 {
1323 TRACE("Writing procedure %d.\n", proc_idx);
1324
1325 hr = ITypeInfo_GetFuncDesc(typeinfo, proc_idx, &desc);
1326 if (FAILED(hr)) return hr;
1327
1328 if (offset)
1329 offset[proc_idx + parentfuncs - 3] = *proclen;
1330
1331 write_proc_func_header(typeinfo, desc, proc_idx + parentfuncs, proc, proclen);
1332
1333 stack_offset = sizeof(void *); /* This */
1334 for (param_idx = 0; param_idx < desc->cParams; param_idx++)
1335 {
1336 TRACE("Writing parameter %d.\n", param_idx);
1337 hr = write_param_fs(typeinfo, type, typelen, proc, proclen,
1338 &desc->lprgelemdescParam[param_idx], FALSE, &stack_offset);
1339 if (FAILED(hr))
1340 {
1341 ITypeInfo_ReleaseFuncDesc(typeinfo, desc);
1342 return hr;
1343 }
1344 }
1345
1346 hr = write_param_fs(typeinfo, type, typelen, proc, proclen,
1347 &desc->elemdescFunc, TRUE, &stack_offset);
1348 ITypeInfo_ReleaseFuncDesc(typeinfo, desc);
1349 if (FAILED(hr)) return hr;
1350 }
1351
1352 return S_OK;
1353}
1354
1356 WORD parentfuncs, const unsigned char **type_ret,
1357 const unsigned char **proc_ret, unsigned short **offset_ret)
1358{
1359 size_t tfs_size;
1360 const unsigned char *tfs = get_type_format_string( &tfs_size );
1361 size_t typelen = tfs_size, proclen = 0;
1362 unsigned char *type, *proc;
1363 unsigned short *offset;
1364 HRESULT hr;
1365
1366 hr = write_iface_fs(typeinfo, funcs, parentfuncs, NULL, &typelen, NULL, &proclen, NULL);
1367 if (FAILED(hr)) return hr;
1368
1369 type = malloc(typelen);
1370 proc = malloc(proclen);
1371 offset = malloc((parentfuncs + funcs - 3) * sizeof(*offset));
1372 if (!type || !proc || !offset)
1373 {
1374 ERR("Failed to allocate format strings.\n");
1375 hr = E_OUTOFMEMORY;
1376 goto err;
1377 }
1378
1379 memcpy(type, tfs, tfs_size);
1380 typelen = tfs_size;
1381 proclen = 0;
1382
1383 hr = write_iface_fs(typeinfo, funcs, parentfuncs, type, &typelen, proc, &proclen, offset);
1384 if (SUCCEEDED(hr))
1385 {
1386 *type_ret = type;
1387 *proc_ret = proc;
1388 *offset_ret = offset;
1389 return S_OK;
1390 }
1391
1392err:
1393 free(type);
1394 free(proc);
1395 free(offset);
1396 return hr;
1397}
1398
1399/* Common helper for Create{Proxy,Stub}FromTypeInfo(). */
1401 GUID *parentiid, ITypeInfo **real_typeinfo)
1402{
1403 ITypeInfo *parentinfo;
1404 TYPEATTR *typeattr;
1406 TLIBATTR *libattr;
1407 TYPEKIND typekind;
1408 HREFTYPE reftype;
1409 SYSKIND syskind;
1410 HRESULT hr;
1411
1412 /* Dual interfaces report their size to be sizeof(IDispatchVtbl) and their
1413 * implemented type to be IDispatch. We need to retrieve the underlying
1414 * interface to get that information. */
1415 hr = ITypeInfo_GetTypeAttr(typeinfo, &typeattr);
1416 if (FAILED(hr))
1417 return hr;
1418 typekind = typeattr->typekind;
1419 ITypeInfo_ReleaseTypeAttr(typeinfo, typeattr);
1420 if (typekind == TKIND_DISPATCH)
1421 {
1422 hr = ITypeInfo_GetRefTypeOfImplType(typeinfo, -1, &reftype);
1423 if (FAILED(hr))
1424 return hr;
1425
1426 hr = ITypeInfo_GetRefTypeInfo(typeinfo, reftype, real_typeinfo);
1427 if (FAILED(hr))
1428 return hr;
1429 }
1430 else
1431 ITypeInfo_AddRef(*real_typeinfo = typeinfo);
1432
1433 hr = ITypeInfo_GetContainingTypeLib(*real_typeinfo, &typelib, NULL);
1434 if (FAILED(hr))
1435 goto err;
1436
1437 hr = ITypeLib_GetLibAttr(typelib, &libattr);
1438 if (FAILED(hr))
1439 {
1440 ITypeLib_Release(typelib);
1441 goto err;
1442 }
1443 syskind = libattr->syskind;
1444 ITypeLib_ReleaseTLibAttr(typelib, libattr);
1445 ITypeLib_Release(typelib);
1446
1447 hr = ITypeInfo_GetTypeAttr(*real_typeinfo, &typeattr);
1448 if (FAILED(hr))
1449 goto err;
1450 *funcs = typeattr->cFuncs;
1451 *parentfuncs = typeattr->cbSizeVft / (syskind == SYS_WIN64 ? 8 : 4) - *funcs;
1452 ITypeInfo_ReleaseTypeAttr(*real_typeinfo, typeattr);
1453
1454 hr = ITypeInfo_GetRefTypeOfImplType(*real_typeinfo, 0, &reftype);
1455 if (FAILED(hr))
1456 goto err;
1457 hr = ITypeInfo_GetRefTypeInfo(*real_typeinfo, reftype, &parentinfo);
1458 if (FAILED(hr))
1459 goto err;
1460
1461 hr = ITypeInfo_GetTypeAttr(parentinfo, &typeattr);
1462 if (SUCCEEDED(hr))
1463 {
1464 *parentiid = typeattr->guid;
1465 ITypeInfo_ReleaseTypeAttr(parentinfo, typeattr);
1466 }
1467 ITypeInfo_Release(parentinfo);
1468 if (SUCCEEDED(hr))
1469 return hr;
1470
1471err:
1472 ITypeInfo_Release(*real_typeinfo);
1473 return hr;
1474}
1475
1477{
1478 desc->pfnAllocate = NdrOleAllocate;
1479 desc->pfnFree = NdrOleFree;
1480 desc->Version = 0x50002;
1481 desc->aUserMarshalQuadruple = get_ndr_types_proxy_info()->pStubDesc->aUserMarshalQuadruple;
1482 /* type format string is initialized with proc format string and offset table */
1483}
1484
1486{
1492 unsigned short *offset_table;
1493};
1494
1496{
1497 struct typelib_proxy *proxy = CONTAINING_RECORD(iface, struct typelib_proxy, proxy.IRpcProxyBuffer_iface);
1498 ULONG refcount = InterlockedDecrement(&proxy->proxy.RefCount);
1499
1500 TRACE("(%p) decreasing refs to %ld\n", proxy, refcount);
1501
1502 if (!refcount)
1503 {
1504 if (proxy->proxy.pChannel)
1505 IRpcProxyBuffer_Disconnect(&proxy->proxy.IRpcProxyBuffer_iface);
1506 if (proxy->proxy.base_object)
1507 IUnknown_Release(proxy->proxy.base_object);
1508 if (proxy->proxy.base_proxy)
1509 IRpcProxyBuffer_Release(proxy->proxy.base_proxy);
1510 free((void *)proxy->stub_desc.pFormatTypes);
1511 free((void *)proxy->proxy_info.ProcFormatString);
1512 free(proxy->offset_table);
1513 free(proxy->proxy_vtbl);
1514 free(proxy);
1515 }
1516 return refcount;
1517}
1518
1519static const IRpcProxyBufferVtbl typelib_proxy_vtbl =
1520{
1526};
1527
1529 ULONG count, const GUID *parentiid, IRpcProxyBuffer **proxy_buffer, void **out)
1530{
1531 if (!fill_stubless_table((IUnknownVtbl *)proxy->proxy_vtbl->Vtbl, count))
1532 return E_OUTOFMEMORY;
1533
1534 if (!outer) outer = (IUnknown *)&proxy->proxy;
1535
1536 proxy->proxy.IRpcProxyBuffer_iface.lpVtbl = &typelib_proxy_vtbl;
1537 proxy->proxy.PVtbl = proxy->proxy_vtbl->Vtbl;
1538 proxy->proxy.RefCount = 1;
1539 proxy->proxy.piid = proxy->proxy_vtbl->header.piid;
1540 proxy->proxy.pUnkOuter = outer;
1541
1542 if (!IsEqualGUID(parentiid, &IID_IUnknown))
1543 {
1544 HRESULT hr = create_proxy(parentiid, NULL, &proxy->proxy.base_proxy,
1545 (void **)&proxy->proxy.base_object);
1546 if (FAILED(hr)) return hr;
1547 }
1548
1549 *proxy_buffer = &proxy->proxy.IRpcProxyBuffer_iface;
1550 *out = &proxy->proxy.PVtbl;
1551 IUnknown_AddRef((IUnknown *)*out);
1552
1553 return S_OK;
1554}
1555
1557 REFIID iid, IRpcProxyBuffer **proxy_buffer, void **out)
1558{
1559 struct typelib_proxy *proxy;
1560 WORD funcs, parentfuncs, i;
1561 ITypeInfo *real_typeinfo;
1562 GUID parentiid;
1563 HRESULT hr;
1564
1565 TRACE("typeinfo %p, outer %p, iid %s, proxy_buffer %p, out %p.\n",
1566 typeinfo, outer, debugstr_guid(iid), proxy_buffer, out);
1567
1568 hr = get_iface_info(typeinfo, &funcs, &parentfuncs, &parentiid, &real_typeinfo);
1569 if (FAILED(hr))
1570 return hr;
1571
1572 if (!(proxy = calloc(1, sizeof(*proxy))))
1573 {
1574 ERR("Failed to allocate proxy object.\n");
1575 ITypeInfo_Release(real_typeinfo);
1576 return E_OUTOFMEMORY;
1577 }
1578
1579 init_stub_desc(&proxy->stub_desc);
1580 proxy->proxy_info.pStubDesc = &proxy->stub_desc;
1581
1582 proxy->proxy_vtbl = calloc(1, sizeof(proxy->proxy_vtbl->header) + (funcs + parentfuncs) * sizeof(void *));
1583 if (!proxy->proxy_vtbl)
1584 {
1585 ERR("Failed to allocate proxy vtbl.\n");
1586 free(proxy);
1587 ITypeInfo_Release(real_typeinfo);
1588 return E_OUTOFMEMORY;
1589 }
1590 proxy->proxy_vtbl->header.pStublessProxyInfo = &proxy->proxy_info;
1591 proxy->iid = *iid;
1592 proxy->proxy_vtbl->header.piid = &proxy->iid;
1593 fill_delegated_proxy_table((IUnknownVtbl *)proxy->proxy_vtbl->Vtbl, parentfuncs);
1594 for (i = 0; i < funcs; i++)
1595 proxy->proxy_vtbl->Vtbl[parentfuncs + i] = (void *)-1;
1596
1597 hr = build_format_strings(real_typeinfo, funcs, parentfuncs, &proxy->stub_desc.pFormatTypes,
1598 &proxy->proxy_info.ProcFormatString, &proxy->offset_table);
1599 ITypeInfo_Release(real_typeinfo);
1600 if (FAILED(hr))
1601 {
1602 free(proxy->proxy_vtbl);
1603 free(proxy);
1604 return hr;
1605 }
1606 proxy->proxy_info.FormatStringOffset = &proxy->offset_table[-3];
1607
1608 hr = typelib_proxy_init(proxy, outer, funcs + parentfuncs, &parentiid, proxy_buffer, out);
1609 if (FAILED(hr))
1610 {
1611 free((void *)proxy->stub_desc.pFormatTypes);
1612 free((void *)proxy->proxy_info.ProcFormatString);
1613 free((void *)proxy->offset_table);
1614 free(proxy->proxy_vtbl);
1615 free(proxy);
1616 }
1617
1618 return hr;
1619}
1620
1622{
1628 unsigned short *offset_table;
1630};
1631
1633{
1634 struct typelib_stub *stub = CONTAINING_RECORD(iface, struct typelib_stub, stub.stub_buffer);
1635 ULONG refcount = InterlockedDecrement(&stub->stub.stub_buffer.RefCount);
1636
1637 TRACE("(%p) decreasing refs to %ld\n", stub, refcount);
1638
1639 if (!refcount)
1640 {
1641 /* test_Release shows that native doesn't call Disconnect here.
1642 We'll leave it in for the time being. */
1643 IRpcStubBuffer_Disconnect(iface);
1644
1645 if (stub->stub.base_stub)
1646 {
1647 IRpcStubBuffer_Release(stub->stub.base_stub);
1648 free(stub->dispatch_table);
1649 }
1650
1651 free((void *)stub->stub_desc.pFormatTypes);
1652 free((void *)stub->server_info.ProcString);
1653 free(stub->offset_table);
1654 free(stub);
1655 }
1656
1657 return refcount;
1658}
1659
1661 const GUID *parentiid, IRpcStubBuffer **stub_buffer)
1662{
1663 HRESULT hr;
1664
1665 hr = IUnknown_QueryInterface(server, stub->stub_vtbl.header.piid,
1666 (void **)&stub->stub.stub_buffer.pvServerObject);
1667 if (FAILED(hr))
1668 {
1669 WARN("Failed to get interface %s, hr %#lx.\n",
1670 debugstr_guid(stub->stub_vtbl.header.piid), hr);
1671 stub->stub.stub_buffer.pvServerObject = server;
1672 IUnknown_AddRef(server);
1673 }
1674
1675 if (!IsEqualGUID(parentiid, &IID_IUnknown))
1676 {
1677 stub->stub.base_obj.lpVtbl = get_delegating_vtbl(stub->stub_vtbl.header.DispatchTableCount);
1678 hr = create_stub(parentiid, &stub->stub.base_obj, &stub->stub.base_stub);
1679 if (FAILED(hr))
1680 {
1681 IUnknown_Release(stub->stub.stub_buffer.pvServerObject);
1682 return hr;
1683 }
1684 }
1685
1686 stub->stub.stub_buffer.lpVtbl = &stub->stub_vtbl.Vtbl;
1687 stub->stub.stub_buffer.RefCount = 1;
1688
1689 *stub_buffer = (IRpcStubBuffer *)&stub->stub.stub_buffer;
1690 return S_OK;
1691}
1692
1694 IUnknown *server, IRpcStubBuffer **stub_buffer)
1695{
1696 WORD funcs, parentfuncs, i;
1697 struct typelib_stub *stub;
1698 ITypeInfo *real_typeinfo;
1699 GUID parentiid;
1700 HRESULT hr;
1701
1702 TRACE("typeinfo %p, iid %s, server %p, stub_buffer %p.\n",
1703 typeinfo, debugstr_guid(iid), server, stub_buffer);
1704
1705 hr = get_iface_info(typeinfo, &funcs, &parentfuncs, &parentiid, &real_typeinfo);
1706 if (FAILED(hr))
1707 return hr;
1708
1709 if (!(stub = calloc(1, sizeof(*stub))))
1710 {
1711 ERR("Failed to allocate stub object.\n");
1712 ITypeInfo_Release(real_typeinfo);
1713 return E_OUTOFMEMORY;
1714 }
1715
1716 init_stub_desc(&stub->stub_desc);
1717 stub->server_info.pStubDesc = &stub->stub_desc;
1718
1719 hr = build_format_strings(real_typeinfo, funcs, parentfuncs, &stub->stub_desc.pFormatTypes,
1720 &stub->server_info.ProcString, &stub->offset_table);
1721 ITypeInfo_Release(real_typeinfo);
1722 if (FAILED(hr))
1723 {
1724 free(stub);
1725 return hr;
1726 }
1727 stub->server_info.FmtStringOffset = &stub->offset_table[-3];
1728
1729 stub->iid = *iid;
1730 stub->stub_vtbl.header.piid = &stub->iid;
1731 stub->stub_vtbl.header.pServerInfo = &stub->server_info;
1732 stub->stub_vtbl.header.DispatchTableCount = funcs + parentfuncs;
1733
1734 if (!IsEqualGUID(&parentiid, &IID_IUnknown))
1735 {
1736 stub->dispatch_table = malloc((funcs + parentfuncs) * sizeof(void *));
1737 for (i = 3; i < parentfuncs; i++)
1738 stub->dispatch_table[i - 3] = NdrStubForwardingFunction;
1739 for (; i < funcs + parentfuncs; i++)
1740 stub->dispatch_table[i - 3] = (PRPC_STUB_FUNCTION)NdrStubCall2;
1741 stub->stub_vtbl.header.pDispatchTable = &stub->dispatch_table[-3];
1742 stub->stub_vtbl.Vtbl = CStdStubBuffer_Delegating_Vtbl;
1743 }
1744 else
1745 stub->stub_vtbl.Vtbl = CStdStubBuffer_Vtbl;
1746 stub->stub_vtbl.Vtbl.Release = typelib_stub_Release;
1747
1748 hr = typelib_stub_init(stub, server, &parentiid, stub_buffer);
1749 if (FAILED(hr))
1750 {
1751 free((void *)stub->stub_desc.pFormatTypes);
1752 free((void *)stub->server_info.ProcString);
1753 free(stub->offset_table);
1754 free(stub);
1755 }
1756
1757 return hr;
1758}
#define InterlockedDecrement
Definition: armddk.h:52
#define WINE_DEFAULT_DEBUG_CHANNEL(t)
Definition: precomp.h:23
#define FIXME(fmt,...)
Definition: precomp.h:53
#define WARN(fmt,...)
Definition: precomp.h:61
#define ERR(fmt,...)
Definition: precomp.h:57
PFOR_CONTEXT fc
Definition: for.c:57
const GUID IID_IUnknown
HRESULT WINAPI StdProxy_QueryInterface(IRpcProxyBuffer *iface, REFIID riid, void **obj)
Definition: cproxy.c:137
void WINAPI StdProxy_Disconnect(IRpcProxyBuffer *iface)
Definition: cproxy.c:199
HRESULT WINAPI StdProxy_Connect(IRpcProxyBuffer *iface, IRpcChannelBuffer *pChannel)
Definition: cproxy.c:188
BOOL fill_stubless_table(IUnknownVtbl *vtbl, DWORD num)
Definition: cproxy.c:56
ULONG WINAPI StdProxy_AddRef(IRpcProxyBuffer *iface)
Definition: cproxy.c:158
const IRpcStubBufferVtbl CStdStubBuffer_Delegating_Vtbl
Definition: cstub.c:397
HRESULT create_stub(REFIID iid, IUnknown *pUnk, IRpcStubBuffer **ppstub)
Definition: ndr_ole.c:430
BOOL fill_delegated_proxy_table(IUnknownVtbl *vtbl, DWORD num)
Definition: cstub.c:106
HRESULT create_proxy(REFIID iid, IUnknown *pUnkOuter, IRpcProxyBuffer **pproxy, void **ppv)
Definition: ndr_ole.c:408
const IUnknownVtbl * get_delegating_vtbl(DWORD num_methods)
Definition: cstub.c:124
const IRpcStubBufferVtbl CStdStubBuffer_Vtbl
Definition: cstub.c:348
#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
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
struct tagVARIANT VARIANT
Definition: compat.h:2377
unsigned short VARTYPE
Definition: compat.h:2254
@ VT_UI8
Definition: compat.h:2315
@ VT_BSTR
Definition: compat.h:2303
@ VT_INT
Definition: compat.h:2316
@ VT_R4
Definition: compat.h:2299
@ VT_UNKNOWN
Definition: compat.h:2308
@ VT_PTR
Definition: compat.h:2320
@ VT_UI2
Definition: compat.h:2312
@ VT_ERROR
Definition: compat.h:2305
@ VT_SAFEARRAY
Definition: compat.h:2321
@ VT_R8
Definition: compat.h:2300
@ VT_CY
Definition: compat.h:2301
@ 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_USERDEFINED
Definition: compat.h:2323
@ VT_HRESULT
Definition: compat.h:2319
@ VT_DATE
Definition: compat.h:2302
@ VT_BOOL
Definition: compat.h:2306
@ VT_I2
Definition: compat.h:2297
@ VT_UI4
Definition: compat.h:2313
@ VT_UINT
Definition: compat.h:2317
@ VT_CARRAY
Definition: compat.h:2322
@ VT_DISPATCH
Definition: compat.h:2304
@ VT_UI1
Definition: compat.h:2311
static const WCHAR *const ext[]
Definition: module.c:53
GUID guid
Definition: version.c:147
static REFPROPVARIANT PROPVAR_CHANGE_FLAGS VARTYPE vt
Definition: suminfo.c:91
void __RPC_STUB NdrStubForwardingFunction(IRpcStubBuffer *iface, IRpcChannelBuffer *pChannel, PRPC_MESSAGE pMsg, DWORD *pdwStubPhase)
Definition: cstub.c:421
#define assert(x)
Definition: debug.h:53
return ret
Definition: mutex.c:146
int align(int length, int align)
Definition: dsound8.c:36
unsigned short WORD
Definition: ntddk_ex.h:93
unsigned int BOOL
Definition: ntddk_ex.h:94
int proxy
Definition: main.c:67
jmp_buf toplevel
Definition: main.c:95
GLuint GLuint GLsizei count
Definition: gl.h:1545
GLuint GLuint GLsizei GLenum type
Definition: gl.h:1545
GLsizeiptr size
Definition: glext.h:5919
GLintptr offset
Definition: glext.h:5920
GLenum const GLfloat * params
Definition: glext.h:5645
GLbitfield flags
Definition: glext.h:7161
GLfloat param
Definition: glext.h:5796
GLenum GLsizei len
Definition: glext.h:6722
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 const GLfloat const GLdouble const GLfloat GLint GLint GLint j
Definition: glfuncs.h:250
#define S_OK
Definition: intsafe.h:52
#define SUCCEEDED(hr)
Definition: intsafe.h:50
#define FAILED(hr)
Definition: intsafe.h:51
#define debugstr_guid
Definition: kernel32.h:35
if(dx< 0)
Definition: linetemp.h:194
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
#define memmove(s1, s2, n)
Definition: mkisofs.h:881
#define for
Definition: utility.h:88
D3D11_SHADER_VARIABLE_DESC desc
Definition: reflection.c:1204
unsigned int float_count
Definition: shader.c:6188
static OLECHAR OLECHAR *static SYSKIND
Definition: typelib.c:80
void *WINAPI NdrOleAllocate(SIZE_T Size)
Definition: ndr_ole.c:391
void WINAPI NdrOleFree(void *NodeToFree)
Definition: ndr_ole.c:399
LONG WINAPI NdrStubCall2(struct IRpcStubBuffer *pThis, struct IRpcChannelBuffer *pChannel, PRPC_MESSAGE pRpcMsg, DWORD *pdwStubPhase)
struct _NDR_PROC_HEADER_RPC NDR_PROC_HEADER_RPC
struct _NDR_PROC_HEADER NDR_PROC_HEADER
static const unsigned short IsReturn
Definition: ndr_typelib.c:909
static ULONG WINAPI typelib_stub_Release(IRpcStubBuffer *iface)
Definition: ndr_typelib.c:1632
static HRESULT build_format_strings(ITypeInfo *typeinfo, WORD funcs, WORD parentfuncs, const unsigned char **type_ret, const unsigned char **proc_ret, unsigned short **offset_ret)
Definition: ndr_typelib.c:1355
static const IRpcProxyBufferVtbl typelib_proxy_vtbl
Definition: ndr_typelib.c:1519
static const unsigned short IsBasetype
Definition: ndr_typelib.c:910
#define WRITE_CHAR(str, len, val)
Definition: ndr_typelib.c:43
#define WRITE_SHORT(str, len, val)
Definition: ndr_typelib.c:45
static const MIDL_STUBLESS_PROXY_INFO * get_ndr_types_proxy_info(void)
Definition: ndr_typelib.c:53
static const unsigned short IsSimpleRef
Definition: ndr_typelib.c:912
static unsigned char get_array_fc(ITypeInfo *typeinfo, TYPEDESC *desc)
Definition: ndr_typelib.c:341
static const unsigned short IsOut
Definition: ndr_typelib.c:908
static size_t write_ip_tfs(unsigned char *str, size_t *len, const GUID *iid)
Definition: ndr_typelib.c:675
static const unsigned short MustSize
Definition: ndr_typelib.c:905
#define WRITE_INT(str, len, val)
Definition: ndr_typelib.c:47
static unsigned char get_struct_member_fc(ITypeInfo *typeinfo, TYPEDESC *tdesc)
Definition: ndr_typelib.c:250
static unsigned char get_basetype(ITypeInfo *typeinfo, TYPEDESC *desc)
Definition: ndr_typelib.c:112
static size_t write_complex_struct_pointer_ref(ITypeInfo *typeinfo, TYPEDESC *desc, unsigned char *str, size_t *len)
Definition: ndr_typelib.c:510
static void write_complex_struct_tfs(ITypeInfo *typeinfo, unsigned char *str, size_t *len, TYPEATTR *attr)
Definition: ndr_typelib.c:539
static const unsigned short MustFree
Definition: ndr_typelib.c:906
static void write_complex_struct_pointer_layout(ITypeInfo *typeinfo, TYPEDESC *desc, unsigned char *str, size_t *len)
Definition: ndr_typelib.c:471
static void write_simple_struct_tfs(ITypeInfo *typeinfo, unsigned char *str, size_t *len, TYPEATTR *attr)
Definition: ndr_typelib.c:440
static unsigned short get_tfs_offset(int param)
Definition: ndr_typelib.c:81
const ExtendedProxyFileInfo ndr_types_ProxyFileInfo
static unsigned int get_stack_size(ITypeInfo *typeinfo, TYPEDESC *desc, unsigned int *align, int *by_value)
Definition: ndr_typelib.c:857
static BOOL type_pointer_is_iface(ITypeInfo *typeinfo, TYPEDESC *tdesc)
Definition: ndr_typelib.c:222
static ULONG WINAPI typelib_proxy_Release(IRpcProxyBuffer *iface)
Definition: ndr_typelib.c:1495
static unsigned char get_struct_fc(ITypeInfo *typeinfo, TYPEATTR *attr)
Definition: ndr_typelib.c:319
static HRESULT get_param_info(ITypeInfo *typeinfo, TYPEDESC *tdesc, int is_in, int is_out, int by_val, unsigned short *server_size, unsigned short *flags, unsigned char *basetype, TYPEDESC **tfs_tdesc)
Definition: ndr_typelib.c:996
#define ROUND_SIZE(size, alignment)
Definition: ndr_typelib.c:49
static const unsigned short IsByValue
Definition: ndr_typelib.c:911
static HRESULT write_iface_fs(ITypeInfo *typeinfo, WORD funcs, WORD parentfuncs, unsigned char *type, size_t *typelen, unsigned char *proc, size_t *proclen, unsigned short *offset)
Definition: ndr_typelib.c:1306
HRESULT WINAPI CreateStubFromTypeInfo(ITypeInfo *typeinfo, REFIID iid, IUnknown *server, IRpcStubBuffer **stub_buffer)
Definition: ndr_typelib.c:1693
HRESULT WINAPI CreateProxyFromTypeInfo(ITypeInfo *typeinfo, IUnknown *outer, REFIID iid, IRpcProxyBuffer **proxy_buffer, void **out)
Definition: ndr_typelib.c:1556
static HRESULT write_param_fs(ITypeInfo *typeinfo, unsigned char *type, size_t *typelen, unsigned char *proc, size_t *proclen, ELEMDESC *desc, BOOL is_return, unsigned short *stack_offset)
Definition: ndr_typelib.c:1075
static unsigned short write_oleaut_tfs(VARTYPE vt)
Definition: ndr_typelib.c:99
static void write_proc_func_header(ITypeInfo *typeinfo, FUNCDESC *desc, WORD proc_idx, unsigned char *proc, size_t *proclen)
Definition: ndr_typelib.c:1239
static void init_stub_desc(MIDL_STUB_DESC *desc)
Definition: ndr_typelib.c:1476
static size_t write_struct_tfs(ITypeInfo *typeinfo, unsigned char *str, size_t *len, TYPEATTR *attr)
Definition: ndr_typelib.c:605
static const unsigned short IsIn
Definition: ndr_typelib.c:907
static size_t write_array_tfs(ITypeInfo *typeinfo, unsigned char *str, size_t *len, ARRAYDESC *desc)
Definition: ndr_typelib.c:627
static HRESULT get_param_pointer_info(ITypeInfo *typeinfo, TYPEDESC *tdesc, int is_in, int is_out, unsigned short *server_size, unsigned short *flags, unsigned char *basetype, TYPEDESC **tfs_tdesc)
Definition: ndr_typelib.c:914
static HRESULT get_iface_info(ITypeInfo *typeinfo, WORD *funcs, WORD *parentfuncs, GUID *parentiid, ITypeInfo **real_typeinfo)
Definition: ndr_typelib.c:1400
static void write_struct_members(ITypeInfo *typeinfo, unsigned char *str, size_t *len, TYPEATTR *attr)
Definition: ndr_typelib.c:404
static const NDR_PARAM_OIF * get_ndr_types_params(unsigned int *nb_params)
Definition: ndr_typelib.c:58
static size_t write_pointer_tfs(ITypeInfo *typeinfo, unsigned char *str, size_t *len, TYPEDESC *desc, BOOL toplevel, BOOL onstack)
Definition: ndr_typelib.c:716
static HRESULT typelib_stub_init(struct typelib_stub *stub, IUnknown *server, const GUID *parentiid, IRpcStubBuffer **stub_buffer)
Definition: ndr_typelib.c:1660
static void get_default_iface(ITypeInfo *typeinfo, WORD count, GUID *iid)
Definition: ndr_typelib.c:690
static BOOL type_needs_pointer_deref(ITypeInfo *typeinfo, TYPEDESC *desc)
Definition: ndr_typelib.c:446
static unsigned int type_memsize(ITypeInfo *typeinfo, TYPEDESC *desc, unsigned int *align_ret)
Definition: ndr_typelib.c:152
static size_t write_type_tfs(ITypeInfo *typeinfo, unsigned char *str, size_t *len, TYPEDESC *desc, BOOL toplevel, BOOL onstack)
Definition: ndr_typelib.c:793
static BOOL type_is_non_iface_pointer(ITypeInfo *typeinfo, TYPEDESC *desc)
Definition: ndr_typelib.c:377
static const unsigned char * get_type_format_string(size_t *size)
Definition: ndr_typelib.c:90
static HRESULT typelib_proxy_init(struct typelib_proxy *proxy, IUnknown *outer, ULONG count, const GUID *parentiid, IRpcProxyBuffer **proxy_buffer, void **out)
Definition: ndr_typelib.c:1528
static HANDLE proc()
Definition: pdb.c:34
unsigned short USHORT
Definition: pedump.c:61
#define IsEqualGUID(rguid1, rguid2)
Definition: guiddef.h:147
#define REFIID
Definition: guiddef.h:118
#define FC_POINTER_DEREF
Definition: ndrtypes.h:276
@ FC_USMALL
Definition: ndrtypes.h:138
@ FC_STRUCT
Definition: ndrtypes.h:157
@ FC_SMALL
Definition: ndrtypes.h:137
@ FC_BOGUS_STRUCT
Definition: ndrtypes.h:162
@ FC_DOUBLE
Definition: ndrtypes.h:146
@ FC_USHORT
Definition: ndrtypes.h:141
@ FC_LONG
Definition: ndrtypes.h:142
@ FC_HYPER
Definition: ndrtypes.h:145
@ FC_CONSTANT_IID
Definition: ndrtypes.h:251
@ FC_STRUCTPAD1
Definition: ndrtypes.h:210
@ FC_EMBEDDED_COMPLEX
Definition: ndrtypes.h:233
@ FC_BOGUS_ARRAY
Definition: ndrtypes.h:170
@ FC_ULONG
Definition: ndrtypes.h:143
@ FC_AUTO_HANDLE
Definition: ndrtypes.h:195
@ FC_UP
Definition: ndrtypes.h:153
@ FC_POINTER
Definition: ndrtypes.h:200
@ FC_PAD
Definition: ndrtypes.h:254
@ FC_RP
Definition: ndrtypes.h:152
@ FC_PSTRUCT
Definition: ndrtypes.h:158
@ FC_FLOAT
Definition: ndrtypes.h:144
@ FC_ENUM32
Definition: ndrtypes.h:148
@ FC_END
Definition: ndrtypes.h:253
@ FC_IP
Definition: ndrtypes.h:189
@ FC_LGFARRAY
Definition: ndrtypes.h:167
@ FC_SHORT
Definition: ndrtypes.h:140
#define FC_SIMPLE_POINTER
Definition: ndrtypes.h:275
#define Oi_OBJ_USE_V2_INTERPRETER
Definition: ndrtypes.h:294
#define Oi_HAS_RPCFLAGS
Definition: ndrtypes.h:293
#define FC_ALLOCED_ON_STACK
Definition: ndrtypes.h:274
#define Oi_OBJECT_PROC
Definition: ndrtypes.h:292
#define err(...)
#define calloc
Definition: rosglue.h:14
const WCHAR * str
void(__RPC_STUB * PRPC_STUB_FUNCTION)(IRpcStubBuffer *This, IRpcChannelBuffer *_pRpcChannelBuffer, PRPC_MESSAGE _pRpcMessage, DWORD *pdwStubPhase)
Definition: rpcproxy.h:83
static struct __wine_debug_functions funcs
Definition: debug.c:48
#define memset(x, y, z)
Definition: compat.h:39
HRESULT hr
Definition: shlfolder.c:183
#define TRACE(s)
Definition: solgame.cpp:4
PMIDL_STUB_DESC pStubDesc
Definition: rpcndr.h:463
const unsigned char * pFormatTypes
Definition: rpcndr.h:390
const USER_MARSHAL_ROUTINE_QUADRUPLE * aUserMarshalQuadruple
Definition: rpcndr.h:396
Definition: stubgen.c:11
Definition: cookie.c:202
Definition: format.c:58
Definition: send.c:48
CInterfaceProxyHeader header
Definition: rpcproxy.h:79
const PCInterfaceProxyVtblList * pProxyVtblList
Definition: rpcproxy.h:47
MIDL_STUB_DESC stub_desc
Definition: ndr_typelib.c:1489
CInterfaceProxyVtbl * proxy_vtbl
Definition: ndr_typelib.c:1491
StdProxyImpl proxy
Definition: ndr_typelib.c:1487
unsigned short * offset_table
Definition: ndr_typelib.c:1492
MIDL_STUBLESS_PROXY_INFO proxy_info
Definition: ndr_typelib.c:1490
MIDL_SERVER_INFO server_info
Definition: ndr_typelib.c:1626
PRPC_STUB_FUNCTION * dispatch_table
Definition: ndr_typelib.c:1629
CInterfaceStubVtbl stub_vtbl
Definition: ndr_typelib.c:1627
cstdstubbuffer_delegating_t stub
Definition: ndr_typelib.c:1623
unsigned short * offset_table
Definition: ndr_typelib.c:1628
MIDL_STUB_DESC stub_desc
Definition: ndr_typelib.c:1625
struct _stub stub
#define max(a, b)
Definition: svc.c:63
#define CONTAINING_RECORD(address, type, field)
Definition: typedefs.h:260
uint32_t ULONG
Definition: typedefs.h:59
static unsigned int compress_params_array(unsigned char *params, unsigned int count)
Definition: typegen.c:1380
static unsigned int fill_params_array(const type_t *iface, const var_t *func, unsigned char *params, unsigned int count)
Definition: typegen.c:1399
static unsigned stack_offset(compile_ctx_t *ctx)
Definition: compile.c:349
static rfbScreenInfoPtr server
Definition: vnc.c:74
wchar_t tm const _CrtWcstime_Writes_and_advances_ptr_ count wchar_t ** out
Definition: wcsftime.cpp:383
unsigned int pointer_size
Definition: widl.c:147
@ TKIND_COCLASS
Definition: widltypes.h:239
@ TKIND_RECORD
Definition: widltypes.h:235
@ TKIND_ENUM
Definition: widltypes.h:234
@ TKIND_ALIAS
Definition: widltypes.h:240
@ TKIND_DISPATCH
Definition: widltypes.h:238
@ TKIND_INTERFACE
Definition: widltypes.h:237
@ SYS_WIN64
Definition: widltypes.h:649
#define WINAPI
Definition: msvc.h:6