ReactOS  0.4.14-dev-583-g2a1ba2c
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 #include "wine/heap.h"
33 
34 #include "cpsf.h"
35 #include "initguid.h"
36 #include "ndr_types.h"
37 #include "ndr_stubless.h"
38 
40 
41 static size_t write_type_tfs(ITypeInfo *typeinfo, unsigned char *str,
42  size_t *len, TYPEDESC *desc, BOOL toplevel, BOOL onstack);
43 
44 #define WRITE_CHAR(str, len, val) \
45  do { if ((str)) (str)[(len)] = (val); (len)++; } while (0)
46 #define WRITE_SHORT(str, len, val) \
47  do { if ((str)) *((short *)((str) + (len))) = (val); (len) += 2; } while (0)
48 #define WRITE_INT(str, len, val) \
49  do { if ((str)) *((int *)((str) + (len))) = (val); (len) += 4; } while (0)
50 
52 
54 {
55  return ndr_types_ProxyFileInfo.pProxyVtblList[0]->header.pStublessProxyInfo;
56 }
57 
58 static const NDR_PARAM_OIF *get_ndr_types_params( unsigned int *nb_params )
59 {
61  const unsigned char *format = proxy->ProcFormatString + proxy->FormatStringOffset[3];
62  const NDR_PROC_HEADER *proc = (const NDR_PROC_HEADER *)format;
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 
81 static 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 
90 static 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 
99 static 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 
112 static 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 
152 static unsigned int type_memsize(ITypeInfo *typeinfo, TYPEDESC *desc)
153 {
154  switch (desc->vt)
155  {
156  case VT_I1:
157  case VT_UI1:
158  return 1;
159  case VT_I2:
160  case VT_UI2:
161  case VT_BOOL:
162  return 2;
163  case VT_I4:
164  case VT_UI4:
165  case VT_R4:
166  case VT_INT:
167  case VT_UINT:
168  case VT_ERROR:
169  case VT_HRESULT:
170  return 4;
171  case VT_I8:
172  case VT_UI8:
173  case VT_R8:
174  case VT_DATE:
175  return 8;
176  case VT_BSTR:
177  case VT_SAFEARRAY:
178  case VT_PTR:
179  case VT_UNKNOWN:
180  case VT_DISPATCH:
181  return sizeof(void *);
182  case VT_VARIANT:
183  return sizeof(VARIANT);
184  case VT_CARRAY:
185  {
186  unsigned int size = type_memsize(typeinfo, &desc->lpadesc->tdescElem);
187  unsigned int i;
188  for (i = 0; i < desc->lpadesc->cDims; i++)
189  size *= desc->lpadesc->rgbounds[i].cElements;
190  return size;
191  }
192  case VT_USERDEFINED:
193  {
194  unsigned int size = 0;
195  ITypeInfo *refinfo;
196  TYPEATTR *attr;
197 
198  ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
199  ITypeInfo_GetTypeAttr(refinfo, &attr);
200  size = attr->cbSizeInstance;
201  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
202  ITypeInfo_Release(refinfo);
203  return size;
204  }
205  default:
206  FIXME("unhandled type %u\n", desc->vt);
207  return 0;
208  }
209 }
210 
211 static BOOL type_pointer_is_iface(ITypeInfo *typeinfo, TYPEDESC *tdesc)
212 {
213  ITypeInfo *refinfo;
214  BOOL ret = FALSE;
215  TYPEATTR *attr;
216 
217  if (tdesc->vt == VT_USERDEFINED)
218  {
219  ITypeInfo_GetRefTypeInfo(typeinfo, tdesc->hreftype, &refinfo);
220  ITypeInfo_GetTypeAttr(refinfo, &attr);
221 
222  if (attr->typekind == TKIND_INTERFACE
223  || attr->typekind == TKIND_DISPATCH
224  || attr->typekind == TKIND_COCLASS)
225  ret = TRUE;
226  else if (attr->typekind == TKIND_ALIAS)
227  ret = type_pointer_is_iface(refinfo, &attr->tdescAlias);
228 
229  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
230  ITypeInfo_Release(refinfo);
231  }
232 
233  return ret;
234 }
235 
236 static unsigned char get_array_fc(ITypeInfo *typeinfo, TYPEDESC *desc);
237 static unsigned char get_struct_fc(ITypeInfo *typeinfo, TYPEATTR *attr);
238 
239 static unsigned char get_struct_member_fc(ITypeInfo *typeinfo, TYPEDESC *tdesc)
240 {
241  unsigned char fc;
242  ITypeInfo *refinfo;
243  TYPEATTR *attr;
244 
245  switch (tdesc->vt)
246  {
247  case VT_BSTR:
248  case VT_SAFEARRAY:
249  return (sizeof(void *) == 4) ? FC_PSTRUCT : FC_BOGUS_STRUCT;
250  case VT_CY:
251  return FC_STRUCT;
252  case VT_VARIANT:
253  case VT_UNKNOWN:
254  case VT_DISPATCH:
255  return FC_BOGUS_STRUCT;
256  case VT_CARRAY:
257  if (get_array_fc(typeinfo, &tdesc->lpadesc->tdescElem) == FC_BOGUS_ARRAY)
258  return FC_BOGUS_STRUCT;
259  return FC_STRUCT;
260  case VT_PTR:
261  if (type_pointer_is_iface(typeinfo, tdesc))
263  else
264  fc = (sizeof(void *) == 4) ? FC_PSTRUCT : FC_BOGUS_STRUCT;
265  break;
266  case VT_USERDEFINED:
267  ITypeInfo_GetRefTypeInfo(typeinfo, tdesc->hreftype, &refinfo);
268  ITypeInfo_GetTypeAttr(refinfo, &attr);
269 
270  switch (attr->typekind)
271  {
272  case TKIND_ENUM:
273  fc = FC_STRUCT;
274  break;
275  case TKIND_RECORD:
276  fc = get_struct_fc(refinfo, attr);
277  break;
278  case TKIND_INTERFACE:
279  case TKIND_DISPATCH:
280  case TKIND_COCLASS:
282  break;
283  case TKIND_ALIAS:
284  fc = get_struct_member_fc(refinfo, &attr->tdescAlias);
285  break;
286  default:
287  FIXME("Unhandled kind %#x.\n", attr->typekind);
289  break;
290  }
291 
292  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
293  ITypeInfo_Release(refinfo);
294  break;
295  default:
296  if (get_basetype(typeinfo, tdesc))
297  return FC_STRUCT;
298  else
299  {
300  FIXME("Unhandled type %u.\n", tdesc->vt);
301  return FC_BOGUS_STRUCT;
302  }
303  }
304 
305  return fc;
306 }
307 
308 static unsigned char get_struct_fc(ITypeInfo *typeinfo, TYPEATTR *attr)
309 {
310  unsigned char fc = FC_STRUCT, member_fc;
311  VARDESC *desc;
312  WORD i;
313 
314  for (i = 0; i < attr->cVars; i++)
315  {
316  ITypeInfo_GetVarDesc(typeinfo, i, &desc);
317 
318  member_fc = get_struct_member_fc(typeinfo, &desc->elemdescVar.tdesc);
319  if (member_fc == FC_BOGUS_STRUCT)
321  else if (member_fc == FC_PSTRUCT && fc != FC_BOGUS_STRUCT)
322  fc = FC_PSTRUCT;
323 
324  ITypeInfo_ReleaseVarDesc(typeinfo, desc);
325  }
326 
327  return fc;
328 }
329 
330 static unsigned char get_array_fc(ITypeInfo *typeinfo, TYPEDESC *desc)
331 {
332  switch (desc->vt)
333  {
334  case VT_CY:
335  return FC_LGFARRAY;
336  case VT_CARRAY:
337  return get_array_fc(typeinfo, &desc->lpadesc->tdescElem);
338  case VT_USERDEFINED:
339  {
340  ITypeInfo *refinfo;
341  TYPEATTR *attr;
342  unsigned char fc;
343 
344  ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
345  ITypeInfo_GetTypeAttr(refinfo, &attr);
346 
347  if (attr->typekind == TKIND_ENUM)
348  fc = FC_LGFARRAY;
349  else if (attr->typekind == TKIND_RECORD && get_struct_fc(refinfo, attr) == FC_STRUCT)
350  fc = FC_LGFARRAY;
351  else if (attr->typekind == TKIND_ALIAS)
352  fc = get_array_fc(refinfo, &attr->tdescAlias);
353  else
354  fc = FC_BOGUS_ARRAY;
355 
356  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
357  ITypeInfo_Release(refinfo);
358 
359  return fc;
360  }
361  default:
363  }
364 }
365 
367 {
368  if (desc->vt == VT_PTR)
369  return !type_pointer_is_iface(typeinfo, desc->lptdesc);
370  else if (desc->vt == VT_USERDEFINED)
371  {
372  ITypeInfo *refinfo;
373  TYPEATTR *attr;
374  BOOL ret;
375 
376  ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
377  ITypeInfo_GetTypeAttr(refinfo, &attr);
378 
379  if (attr->typekind == TKIND_ALIAS)
380  ret = type_is_non_iface_pointer(refinfo, &attr->tdescAlias);
381  else
382  ret = FALSE;
383 
384  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
385  ITypeInfo_Release(refinfo);
386 
387  return ret;
388  }
389  else
390  return FALSE;
391 }
392 
393 static void write_struct_members(ITypeInfo *typeinfo, unsigned char *str,
394  size_t *len, TYPEATTR *attr)
395 {
396  unsigned int struct_offset = 0;
397  unsigned char basetype;
398  TYPEDESC *tdesc;
399  VARDESC *desc;
400  WORD i;
401 
402  for (i = 0; i < attr->cVars; i++)
403  {
404  ITypeInfo_GetVarDesc(typeinfo, i, &desc);
405  tdesc = &desc->elemdescVar.tdesc;
406 
407  /* This may not match the intended alignment, but we don't have enough
408  * information to determine that. This should always give the correct
409  * layout. */
410  if ((struct_offset & 7) && !(desc->oInst & 7))
412  else if ((struct_offset & 3) && !(desc->oInst & 3))
414  else if ((struct_offset & 1) && !(desc->oInst & 1))
416  struct_offset = desc->oInst + type_memsize(typeinfo, tdesc);
417 
418  if ((basetype = get_basetype(typeinfo, tdesc)))
419  WRITE_CHAR(str, *len, basetype);
420  else if (type_is_non_iface_pointer(typeinfo, tdesc))
422  else
423  {
425  WRITE_CHAR(str, *len, 0);
426  WRITE_SHORT(str, *len, 0);
427  }
428 
429  ITypeInfo_ReleaseVarDesc(typeinfo, desc);
430  }
431  if (!(*len & 1))
432  WRITE_CHAR (str, *len, FC_PAD);
433  WRITE_CHAR (str, *len, FC_END);
434 }
435 
436 static void write_simple_struct_tfs(ITypeInfo *typeinfo, unsigned char *str,
437  size_t *len, TYPEATTR *attr)
438 {
440 }
441 
443 {
444  if (desc->vt == VT_PTR || desc->vt == VT_UNKNOWN || desc->vt == VT_DISPATCH)
445  return TRUE;
446  else if (desc->vt == VT_USERDEFINED)
447  {
448  ITypeInfo *refinfo;
449  BOOL ret = FALSE;
450  TYPEATTR *attr;
451 
452  ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
453  ITypeInfo_GetTypeAttr(refinfo, &attr);
454 
455  if (attr->typekind == TKIND_ALIAS)
456  ret = type_needs_pointer_deref(refinfo, &attr->tdescAlias);
457 
458  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
459  ITypeInfo_Release(refinfo);
460 
461  return ret;
462  }
463  else
464  return FALSE;
465 }
466 
468  TYPEDESC *desc, unsigned char *str, size_t *len)
469 {
470  unsigned char basetype;
471 
472  if (desc->vt == VT_PTR && !type_pointer_is_iface(typeinfo, desc->lptdesc))
473  {
474  WRITE_CHAR(str, *len, FC_UP);
475  if ((basetype = get_basetype(typeinfo, desc->lptdesc)))
476  {
478  WRITE_CHAR(str, *len, basetype);
479  WRITE_CHAR(str, *len, FC_PAD);
480  }
481  else
482  {
483  if (type_needs_pointer_deref(typeinfo, desc->lptdesc))
485  else
486  WRITE_CHAR(str, *len, 0);
487  WRITE_SHORT(str, *len, 0);
488  }
489  }
490  else if (desc->vt == VT_USERDEFINED)
491  {
492  ITypeInfo *refinfo;
493  TYPEATTR *attr;
494 
495  ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
496  ITypeInfo_GetTypeAttr(refinfo, &attr);
497 
498  if (attr->typekind == TKIND_ALIAS)
499  write_complex_struct_pointer_layout(refinfo, &attr->tdescAlias, str, len);
500 
501  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
502  ITypeInfo_Release(refinfo);
503  }
504 }
505 
507  TYPEDESC *desc, unsigned char *str, size_t *len)
508 {
509  if (desc->vt == VT_PTR && !type_pointer_is_iface(typeinfo, desc->lptdesc)
510  && !get_basetype(typeinfo, desc->lptdesc))
511  {
512  return write_type_tfs(typeinfo, str, len, desc->lptdesc, FALSE, FALSE);
513  }
514  else if (desc->vt == VT_USERDEFINED)
515  {
516  ITypeInfo *refinfo;
517  TYPEATTR *attr;
518  size_t ret = 0;
519 
520  ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
521  ITypeInfo_GetTypeAttr(refinfo, &attr);
522 
523  if (attr->typekind == TKIND_ALIAS)
524  ret = write_complex_struct_pointer_ref(refinfo, &attr->tdescAlias, str, len);
525 
526  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
527  ITypeInfo_Release(refinfo);
528 
529  return ret;
530  }
531 
532  return 0;
533 }
534 
535 static void write_complex_struct_tfs(ITypeInfo *typeinfo, unsigned char *str,
536  size_t *len, TYPEATTR *attr)
537 {
538  size_t pointer_layout_offset, pointer_layout, member_layout, ref;
539  unsigned int struct_offset = 0;
540  TYPEDESC *tdesc;
541  VARDESC *desc;
542  WORD i;
543 
544  WRITE_SHORT(str, *len, 0); /* conformant array description */
545  pointer_layout_offset = *len;
546  WRITE_SHORT(str, *len, 0); /* pointer layout; will be filled in later */
547  member_layout = *len;
548 
549  /* First pass: write the struct members and pointer layout, but do not yet
550  * write the offsets for embedded complexes and pointer refs. These must be
551  * handled after we write the whole struct description, since it must be
552  * contiguous. */
553 
555 
556  pointer_layout = *len;
557  if (str) *((short *)(str + pointer_layout_offset)) = pointer_layout - pointer_layout_offset;
558 
559  for (i = 0; i < attr->cVars; i++)
560  {
561  ITypeInfo_GetVarDesc(typeinfo, i, &desc);
562  write_complex_struct_pointer_layout(typeinfo, &desc->elemdescVar.tdesc, str, len);
563  ITypeInfo_ReleaseVarDesc(typeinfo, desc);
564  }
565 
566  /* Second pass: write types for embedded complexes and non-simple pointers. */
567 
568  struct_offset = 0;
569 
570  for (i = 0; i < attr->cVars; i++)
571  {
572  ITypeInfo_GetVarDesc(typeinfo, i, &desc);
573  tdesc = &desc->elemdescVar.tdesc;
574 
575  if (struct_offset != desc->oInst)
576  member_layout++; /* alignment directive */
577  struct_offset = desc->oInst + type_memsize(typeinfo, tdesc);
578 
579  if (get_basetype(typeinfo, tdesc))
580  member_layout++;
581  else if (type_is_non_iface_pointer(typeinfo, tdesc))
582  {
583  member_layout++;
585  {
586  if (str) *((short *)(str + pointer_layout + 2)) = ref - (pointer_layout + 2);
587  }
588  pointer_layout += 4;
589  }
590  else
591  {
592  ref = write_type_tfs(typeinfo, str, len, tdesc, FALSE, FALSE);
593  if (str) *((short *)(str + member_layout + 2)) = ref - (member_layout + 2);
594  member_layout += 4;
595  }
596 
597  ITypeInfo_ReleaseVarDesc(typeinfo, desc);
598  }
599 }
600 
601 static size_t write_struct_tfs(ITypeInfo *typeinfo, unsigned char *str,
602  size_t *len, TYPEATTR *attr)
603 {
604  unsigned char fc = get_struct_fc(typeinfo, attr);
605  size_t off = *len;
606 
607  /* For the sake of simplicity, write pointer structs as complex structs. */
608  if (fc == FC_PSTRUCT)
610 
611  WRITE_CHAR (str, *len, fc);
612  WRITE_CHAR (str, *len, attr->cbAlignment - 1);
613  WRITE_SHORT(str, *len, attr->cbSizeInstance);
614 
615  if (fc == FC_STRUCT)
617  else if (fc == FC_BOGUS_STRUCT)
619 
620  return off;
621 }
622 
623 static size_t write_array_tfs(ITypeInfo *typeinfo, unsigned char *str,
624  size_t *len, ARRAYDESC *desc)
625 {
626  unsigned char fc = get_array_fc(typeinfo, &desc->tdescElem);
627  unsigned char basetype;
628  size_t ref = 0, off;
629  ULONG size = 1;
630  USHORT i;
631 
632  if (!(basetype = get_basetype(typeinfo, &desc->tdescElem)))
633  ref = write_type_tfs(typeinfo, str, len, &desc->tdescElem, FALSE, FALSE);
634 
635  /* In theory arrays should be nested, but there's no reason not to marshal
636  * [x][y] as [x*y]. */
637  for (i = 0; i < desc->cDims; i++) size *= desc->rgbounds[i].cElements;
638 
639  off = *len;
640 
641  WRITE_CHAR(str, *len, fc);
642  WRITE_CHAR(str, *len, 0);
643  if (fc == FC_BOGUS_ARRAY)
644  {
645  WRITE_SHORT(str, *len, size);
646  WRITE_INT(str, *len, 0xffffffff); /* conformance */
647  WRITE_INT(str, *len, 0xffffffff); /* variance */
648  }
649  else
650  {
651  size *= type_memsize(typeinfo, &desc->tdescElem);
652  WRITE_INT(str, *len, size);
653  }
654 
655  if (basetype)
656  WRITE_CHAR(str, *len, basetype);
657  else
658  {
660  WRITE_CHAR (str, *len, 0);
661  WRITE_SHORT(str, *len, ref - *len);
662  WRITE_CHAR (str, *len, FC_PAD);
663  }
664  WRITE_CHAR(str, *len, FC_END);
665 
666  return off;
667 }
668 
669 static size_t write_ip_tfs(unsigned char *str, size_t *len, const GUID *iid)
670 {
671  size_t off = *len;
672 
673  if (str)
674  {
675  str[*len] = FC_IP;
676  str[*len+1] = FC_CONSTANT_IID;
677  memcpy(str + *len + 2, iid, sizeof(*iid));
678  }
679  *len += 2 + sizeof(*iid);
680 
681  return off;
682 }
683 
685 {
686  ITypeInfo *refinfo;
687  HREFTYPE reftype;
688  TYPEATTR *attr;
689  int flags, i;
690 
691  for (i = 0; i < count; ++i)
692  {
693  ITypeInfo_GetImplTypeFlags(typeinfo, i, &flags);
694  if (flags & IMPLTYPEFLAG_FDEFAULT)
695  break;
696  }
697 
698  /* If no interface was explicitly marked default, choose the first one. */
699  if (i == count)
700  i = 0;
701 
702  ITypeInfo_GetRefTypeOfImplType(typeinfo, i, &reftype);
703  ITypeInfo_GetRefTypeInfo(typeinfo, reftype, &refinfo);
704  ITypeInfo_GetTypeAttr(refinfo, &attr);
705  *iid = attr->guid;
706  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
707  ITypeInfo_Release(refinfo);
708 }
709 
710 static size_t write_pointer_tfs(ITypeInfo *typeinfo, unsigned char *str,
711  size_t *len, TYPEDESC *desc, BOOL toplevel, BOOL onstack)
712 {
713  unsigned char basetype, flags = 0;
714  size_t ref, off = *len;
715  ITypeInfo *refinfo;
716  TYPEATTR *attr;
717  GUID guid;
718 
719  if (desc->vt == VT_USERDEFINED)
720  {
721  ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
722  ITypeInfo_GetTypeAttr(refinfo, &attr);
723 
724  switch (attr->typekind)
725  {
726  case TKIND_ENUM:
727  assert(!toplevel); /* toplevel base-type pointers should use IsSimpleRef */
728  WRITE_CHAR(str, *len, FC_UP);
731  WRITE_CHAR(str, *len, FC_PAD);
732  break;
733  case TKIND_RECORD:
734  assert(!toplevel); /* toplevel struct pointers should use IsSimpleRef */
735  ref = write_struct_tfs(refinfo, str, len, attr);
736  off = *len;
737  WRITE_CHAR (str, *len, FC_UP);
738  WRITE_CHAR (str, *len, 0);
739  WRITE_SHORT(str, *len, ref - *len);
740  break;
741  case TKIND_INTERFACE:
742  case TKIND_DISPATCH:
743  write_ip_tfs(str, len, &attr->guid);
744  break;
745  case TKIND_COCLASS:
746  get_default_iface(refinfo, attr->cImplTypes, &guid);
747  write_ip_tfs(str, len, &guid);
748  break;
749  case TKIND_ALIAS:
750  off = write_pointer_tfs(refinfo, str, len, &attr->tdescAlias, toplevel, onstack);
751  break;
752  default:
753  FIXME("unhandled kind %#x\n", attr->typekind);
754  WRITE_SHORT(str, *len, 0);
755  break;
756  }
757 
758  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
759  ITypeInfo_Release(refinfo);
760  }
761  else if ((basetype = get_basetype(typeinfo, desc)))
762  {
763  assert(!toplevel); /* toplevel base-type pointers should use IsSimpleRef */
764  WRITE_CHAR(str, *len, FC_UP);
766  WRITE_CHAR(str, *len, basetype);
767  WRITE_CHAR(str, *len, FC_PAD);
768  }
769  else
770  {
772 
773  if (onstack) flags |= FC_ALLOCED_ON_STACK;
774  if (desc->vt == VT_PTR || desc->vt == VT_UNKNOWN || desc->vt == VT_DISPATCH)
776 
777  off = *len;
778 
780  WRITE_CHAR (str, *len, flags);
781  WRITE_SHORT(str, *len, ref - *len);
782  }
783 
784  return off;
785 }
786 
787 static size_t write_type_tfs(ITypeInfo *typeinfo, unsigned char *str,
788  size_t *len, TYPEDESC *desc, BOOL toplevel, BOOL onstack)
789 {
790  ITypeInfo *refinfo;
791  TYPEATTR *attr;
792  size_t off;
793 
794  TRACE("vt %d%s\n", desc->vt, toplevel ? " (toplevel)" : "");
795 
796  if ((off = write_oleaut_tfs(desc->vt)))
797  return off;
798 
799  switch (desc->vt)
800  {
801  case VT_PTR:
802  return write_pointer_tfs(typeinfo, str, len, desc->lptdesc, toplevel, onstack);
803  case VT_CARRAY:
804  return write_array_tfs(typeinfo, str, len, desc->lpadesc);
805  case VT_USERDEFINED:
806  ITypeInfo_GetRefTypeInfo(typeinfo, desc->hreftype, &refinfo);
807  ITypeInfo_GetTypeAttr(refinfo, &attr);
808 
809  switch (attr->typekind)
810  {
811  case TKIND_RECORD:
812  off = write_struct_tfs(refinfo, str, len, attr);
813  break;
814  case TKIND_INTERFACE:
815  case TKIND_DISPATCH:
816  case TKIND_COCLASS:
817  assert(0);
818  break;
819  case TKIND_ALIAS:
820  off = write_type_tfs(refinfo, str, len, &attr->tdescAlias, toplevel, onstack);
821  break;
822  default:
823  FIXME("unhandled kind %u\n", attr->typekind);
824  off = *len;
825  WRITE_SHORT(str, *len, 0);
826  break;
827  }
828 
829  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
830  ITypeInfo_Release(refinfo);
831  break;
832  default:
833  /* base types are always embedded directly */
835  FIXME("unhandled type %u\n", desc->vt);
836  off = *len;
837  WRITE_SHORT(str, *len, 0);
838  break;
839  }
840 
841  return off;
842 }
843 
844 static unsigned short get_stack_size(ITypeInfo *typeinfo, TYPEDESC *desc)
845 {
846 #if defined(__i386__) || defined(__arm__)
847  if (desc->vt == VT_CARRAY)
848  return sizeof(void *);
849  return (type_memsize(typeinfo, desc) + 3) & ~3;
850 #else
851  return sizeof(void *);
852 #endif
853 }
854 
855 static const unsigned short MustSize = 0x0001;
856 static const unsigned short MustFree = 0x0002;
857 static const unsigned short IsIn = 0x0008;
858 static const unsigned short IsOut = 0x0010;
859 static const unsigned short IsReturn = 0x0020;
860 static const unsigned short IsBasetype = 0x0040;
861 static const unsigned short IsByValue = 0x0080;
862 static const unsigned short IsSimpleRef = 0x0100;
863 
864 static HRESULT get_param_pointer_info(ITypeInfo *typeinfo, TYPEDESC *tdesc, int is_in,
865  int is_out, unsigned short *server_size, unsigned short *flags,
866  unsigned char *basetype, TYPEDESC **tfs_tdesc)
867 {
868  ITypeInfo *refinfo;
869  HRESULT hr = S_OK;
870  TYPEATTR *attr;
871 
872  switch (tdesc->vt)
873  {
874  case VT_UNKNOWN:
875  case VT_DISPATCH:
876  *flags |= MustFree;
877  if (is_in && is_out)
878  *server_size = sizeof(void *);
879  break;
880  case VT_PTR:
881  *flags |= MustFree;
882  if (type_pointer_is_iface(typeinfo, tdesc->lptdesc))
883  {
884  if (is_in && is_out)
885  *server_size = sizeof(void *);
886  }
887  else
888  *server_size = sizeof(void *);
889  break;
890  case VT_CARRAY:
891  *flags |= IsSimpleRef | MustFree;
892  *server_size = type_memsize(typeinfo, tdesc);
893  *tfs_tdesc = tdesc;
894  break;
895  case VT_USERDEFINED:
896  ITypeInfo_GetRefTypeInfo(typeinfo, tdesc->hreftype, &refinfo);
897  ITypeInfo_GetTypeAttr(refinfo, &attr);
898 
899  switch (attr->typekind)
900  {
901  case TKIND_ENUM:
903  if (!is_in && is_out)
904  *server_size = sizeof(void *);
905  *basetype = FC_ENUM32;
906  break;
907  case TKIND_RECORD:
908  *flags |= IsSimpleRef | MustFree;
909  if (!is_in && is_out)
910  *server_size = attr->cbSizeInstance;
911  *tfs_tdesc = tdesc;
912  break;
913  case TKIND_INTERFACE:
914  case TKIND_DISPATCH:
915  case TKIND_COCLASS:
916  *flags |= MustFree;
917  break;
918  case TKIND_ALIAS:
919  hr = get_param_pointer_info(refinfo, &attr->tdescAlias, is_in,
920  is_out, server_size, flags, basetype, tfs_tdesc);
921  break;
922  default:
923  FIXME("unhandled kind %#x\n", attr->typekind);
924  hr = E_NOTIMPL;
925  break;
926  }
927 
928  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
929  ITypeInfo_Release(refinfo);
930  break;
931  default:
932  *flags |= IsSimpleRef;
933  *tfs_tdesc = tdesc;
934  if (!is_in && is_out)
935  *server_size = type_memsize(typeinfo, tdesc);
936  if ((*basetype = get_basetype(typeinfo, tdesc)))
937  *flags |= IsBasetype;
938  break;
939  }
940 
941  return hr;
942 }
943 
944 static HRESULT get_param_info(ITypeInfo *typeinfo, TYPEDESC *tdesc, int is_in,
945  int is_out, unsigned short *server_size, unsigned short *flags,
946  unsigned char *basetype, TYPEDESC **tfs_tdesc)
947 {
948  ITypeInfo *refinfo;
949  HRESULT hr = S_OK;
950  TYPEATTR *attr;
951 
952  *server_size = 0;
953  *flags = MustSize;
954  *basetype = 0;
955  *tfs_tdesc = tdesc;
956 
957  TRACE("vt %u\n", tdesc->vt);
958 
959  switch (tdesc->vt)
960  {
961  case VT_VARIANT:
962 #if !defined(__i386__) && !defined(__arm__)
963  *flags |= IsSimpleRef | MustFree;
964  break;
965 #endif
966  /* otherwise fall through */
967  case VT_BSTR:
968  case VT_SAFEARRAY:
969  case VT_CY:
970  *flags |= IsByValue | MustFree;
971  break;
972  case VT_UNKNOWN:
973  case VT_DISPATCH:
974  case VT_CARRAY:
975  *flags |= MustFree;
976  break;
977  case VT_PTR:
978  return get_param_pointer_info(typeinfo, tdesc->lptdesc, is_in, is_out,
979  server_size, flags, basetype, tfs_tdesc);
980  case VT_USERDEFINED:
981  ITypeInfo_GetRefTypeInfo(typeinfo, tdesc->hreftype, &refinfo);
982  ITypeInfo_GetTypeAttr(refinfo, &attr);
983 
984  switch (attr->typekind)
985  {
986  case TKIND_ENUM:
987  *flags |= IsBasetype;
988  *basetype = FC_ENUM32;
989  break;
990  case TKIND_RECORD:
991 #if defined(__i386__) || defined(__arm__)
992  *flags |= IsByValue | MustFree;
993 #else
994  if (attr->cbSizeInstance <= 8)
995  *flags |= IsByValue | MustFree;
996  else
997  *flags |= IsSimpleRef | MustFree;
998 #endif
999  break;
1000  case TKIND_ALIAS:
1001  hr = get_param_info(refinfo, &attr->tdescAlias, is_in, is_out,
1002  server_size, flags, basetype, tfs_tdesc);
1003  break;
1004  default:
1005  FIXME("unhandled kind %#x\n", attr->typekind);
1006  hr = E_NOTIMPL;
1007  break;
1008  }
1009 
1010  ITypeInfo_ReleaseTypeAttr(refinfo, attr);
1011  ITypeInfo_Release(refinfo);
1012  break;
1013  default:
1014  if ((*basetype = get_basetype(typeinfo, tdesc)))
1015  *flags |= IsBasetype;
1016  else
1017  {
1018  FIXME("unhandled type %u\n", tdesc->vt);
1019  return E_NOTIMPL;
1020  }
1021  break;
1022  }
1023 
1024  return hr;
1025 }
1026 
1028  size_t *typelen, unsigned char *proc, size_t *proclen, ELEMDESC *desc,
1029  BOOL is_return, unsigned short *stack_offset)
1030 {
1031  USHORT param_flags = desc->paramdesc.wParamFlags;
1032  int is_in = param_flags & PARAMFLAG_FIN;
1033  int is_out = param_flags & PARAMFLAG_FOUT;
1034  TYPEDESC *tdesc = &desc->tdesc, *tfs_tdesc;
1035  unsigned short server_size;
1036  unsigned short stack_size = get_stack_size(typeinfo, tdesc);
1037  unsigned char basetype;
1038  unsigned short flags;
1039  size_t off = 0;
1040  HRESULT hr;
1041 
1042  hr = get_param_info(typeinfo, tdesc, is_in, is_out, &server_size, &flags,
1043  &basetype, &tfs_tdesc);
1044 
1045  if (is_in) flags |= IsIn;
1046  if (is_out) flags |= IsOut;
1047  if (is_return) flags |= IsOut | IsReturn;
1048 
1049  server_size = (server_size + 7) / 8;
1050  if (server_size >= 8) server_size = 0;
1051  flags |= server_size << 13;
1052 
1053  if (!basetype)
1054  off = write_type_tfs(typeinfo, type, typelen, tfs_tdesc, TRUE, server_size != 0);
1055 
1056  if (SUCCEEDED(hr))
1057  {
1058  WRITE_SHORT(proc, *proclen, flags);
1059  WRITE_SHORT(proc, *proclen, *stack_offset);
1060  WRITE_SHORT(proc, *proclen, basetype ? basetype : off);
1061 
1062  *stack_offset += stack_size;
1063  }
1064 
1065  return hr;
1066 }
1067 
1069  WORD proc_idx, unsigned char *proc, size_t *proclen)
1070 {
1071  unsigned short stack_size = 2 * sizeof(void *); /* This + return */
1072 #ifdef __x86_64__
1073  unsigned short float_mask = 0;
1074  unsigned char basetype;
1075 #endif
1076  WORD param_idx;
1077 
1078  WRITE_CHAR (proc, *proclen, FC_AUTO_HANDLE);
1080  WRITE_SHORT(proc, *proclen, proc_idx);
1081  for (param_idx = 0; param_idx < desc->cParams; param_idx++)
1082  stack_size += get_stack_size(typeinfo, &desc->lprgelemdescParam[param_idx].tdesc);
1083  WRITE_SHORT(proc, *proclen, stack_size);
1084 
1085  WRITE_SHORT(proc, *proclen, 0); /* constant_client_buffer_size */
1086  WRITE_SHORT(proc, *proclen, 0); /* constant_server_buffer_size */
1087 #ifdef __x86_64__
1088  WRITE_CHAR (proc, *proclen, 0x47); /* HasExtensions | HasReturn | ClientMustSize | ServerMustSize */
1089 #else
1090  WRITE_CHAR (proc, *proclen, 0x07); /* HasReturn | ClientMustSize | ServerMustSize */
1091 #endif
1092  WRITE_CHAR (proc, *proclen, desc->cParams + 1); /* incl. return value */
1093 #ifdef __x86_64__
1094  WRITE_CHAR (proc, *proclen, 10); /* extension size */
1095  WRITE_CHAR (proc, *proclen, 0); /* INTERPRETER_OPT_FLAGS2 */
1096  WRITE_SHORT(proc, *proclen, 0); /* ClientCorrHint */
1097  WRITE_SHORT(proc, *proclen, 0); /* ServerCorrHint */
1098  WRITE_SHORT(proc, *proclen, 0); /* NotifyIndex */
1099  for (param_idx = 0; param_idx < desc->cParams && param_idx < 3; param_idx++)
1100  {
1101  basetype = get_basetype(typeinfo, &desc->lprgelemdescParam[param_idx].tdesc);
1102  if (basetype == FC_FLOAT)
1103  float_mask |= (1 << ((param_idx + 1) * 2));
1104  else if (basetype == FC_DOUBLE)
1105  float_mask |= (2 << ((param_idx + 1) * 2));
1106  }
1107  WRITE_SHORT(proc, *proclen, float_mask);
1108 #endif
1109 }
1110 
1112  unsigned char *type, size_t *typelen, unsigned char *proc,
1113  size_t *proclen, unsigned short *offset)
1114 {
1115  unsigned short stack_offset;
1116  WORD proc_idx, param_idx;
1117  FUNCDESC *desc;
1118  HRESULT hr;
1119 
1120  for (proc_idx = 3; proc_idx < parentfuncs; proc_idx++)
1121  {
1122  if (offset)
1123  offset[proc_idx - 3] = -1;
1124  }
1125 
1126  for (proc_idx = 0; proc_idx < funcs; proc_idx++)
1127  {
1128  TRACE("Writing procedure %d.\n", proc_idx);
1129 
1130  hr = ITypeInfo_GetFuncDesc(typeinfo, proc_idx, &desc);
1131  if (FAILED(hr)) return hr;
1132 
1133  if (offset)
1134  offset[proc_idx + parentfuncs - 3] = *proclen;
1135 
1136  write_proc_func_header(typeinfo, desc, proc_idx + parentfuncs, proc, proclen);
1137 
1138  stack_offset = sizeof(void *); /* This */
1139  for (param_idx = 0; param_idx < desc->cParams; param_idx++)
1140  {
1141  TRACE("Writing parameter %d.\n", param_idx);
1142  hr = write_param_fs(typeinfo, type, typelen, proc, proclen,
1143  &desc->lprgelemdescParam[param_idx], FALSE, &stack_offset);
1144  if (FAILED(hr))
1145  {
1146  ITypeInfo_ReleaseFuncDesc(typeinfo, desc);
1147  return hr;
1148  }
1149  }
1150 
1151  hr = write_param_fs(typeinfo, type, typelen, proc, proclen,
1152  &desc->elemdescFunc, TRUE, &stack_offset);
1153  ITypeInfo_ReleaseFuncDesc(typeinfo, desc);
1154  if (FAILED(hr)) return hr;
1155  }
1156 
1157  return S_OK;
1158 }
1159 
1161  WORD parentfuncs, const unsigned char **type_ret,
1162  const unsigned char **proc_ret, unsigned short **offset_ret)
1163 {
1164  size_t tfs_size;
1165  const unsigned char *tfs = get_type_format_string( &tfs_size );
1166  size_t typelen = tfs_size, proclen = 0;
1167  unsigned char *type, *proc;
1168  unsigned short *offset;
1169  HRESULT hr;
1170 
1171  hr = write_iface_fs(typeinfo, funcs, parentfuncs, NULL, &typelen, NULL, &proclen, NULL);
1172  if (FAILED(hr)) return hr;
1173 
1174  type = heap_alloc(typelen);
1175  proc = heap_alloc(proclen);
1176  offset = heap_alloc((parentfuncs + funcs - 3) * sizeof(*offset));
1177  if (!type || !proc || !offset)
1178  {
1179  ERR("Failed to allocate format strings.\n");
1180  hr = E_OUTOFMEMORY;
1181  goto err;
1182  }
1183 
1184  memcpy(type, tfs, tfs_size);
1185  typelen = tfs_size;
1186  proclen = 0;
1187 
1188  hr = write_iface_fs(typeinfo, funcs, parentfuncs, type, &typelen, proc, &proclen, offset);
1189  if (SUCCEEDED(hr))
1190  {
1191  *type_ret = type;
1192  *proc_ret = proc;
1193  *offset_ret = offset;
1194  return S_OK;
1195  }
1196 
1197 err:
1198  heap_free(type);
1199  heap_free(proc);
1200  heap_free(offset);
1201  return hr;
1202 }
1203 
1204 /* Common helper for Create{Proxy,Stub}FromTypeInfo(). */
1206  GUID *parentiid)
1207 {
1208  ITypeInfo *real_typeinfo, *parentinfo;
1209  TYPEATTR *typeattr;
1210  ITypeLib *typelib;
1211  TLIBATTR *libattr;
1212  TYPEKIND typekind;
1213  HREFTYPE reftype;
1214  SYSKIND syskind;
1215  HRESULT hr;
1216 
1217  /* Dual interfaces report their size to be sizeof(IDispatchVtbl) and their
1218  * implemented type to be IDispatch. We need to retrieve the underlying
1219  * interface to get that information. */
1220  hr = ITypeInfo_GetTypeAttr(*typeinfo, &typeattr);
1221  if (FAILED(hr))
1222  return hr;
1223  typekind = typeattr->typekind;
1224  ITypeInfo_ReleaseTypeAttr(*typeinfo, typeattr);
1225  if (typekind == TKIND_DISPATCH)
1226  {
1227  hr = ITypeInfo_GetRefTypeOfImplType(*typeinfo, -1, &reftype);
1228  if (FAILED(hr))
1229  return hr;
1230 
1231  hr = ITypeInfo_GetRefTypeInfo(*typeinfo, reftype, &real_typeinfo);
1232  if (FAILED(hr))
1233  return hr;
1234 
1235  ITypeInfo_Release(*typeinfo);
1236  *typeinfo = real_typeinfo;
1237  }
1238 
1239  hr = ITypeInfo_GetContainingTypeLib(*typeinfo, &typelib, NULL);
1240  if (FAILED(hr))
1241  return hr;
1242 
1243  hr = ITypeLib_GetLibAttr(typelib, &libattr);
1244  if (FAILED(hr))
1245  {
1246  ITypeLib_Release(typelib);
1247  return hr;
1248  }
1249  syskind = libattr->syskind;
1250  ITypeLib_ReleaseTLibAttr(typelib, libattr);
1251  ITypeLib_Release(typelib);
1252 
1253  hr = ITypeInfo_GetTypeAttr(*typeinfo, &typeattr);
1254  if (FAILED(hr))
1255  return hr;
1256  *funcs = typeattr->cFuncs;
1257  *parentfuncs = typeattr->cbSizeVft / (syskind == SYS_WIN64 ? 8 : 4) - *funcs;
1258  ITypeInfo_ReleaseTypeAttr(*typeinfo, typeattr);
1259 
1260  hr = ITypeInfo_GetRefTypeOfImplType(*typeinfo, 0, &reftype);
1261  if (FAILED(hr))
1262  return hr;
1263  hr = ITypeInfo_GetRefTypeInfo(*typeinfo, reftype, &parentinfo);
1264  if (FAILED(hr))
1265  return hr;
1266  hr = ITypeInfo_GetTypeAttr(parentinfo, &typeattr);
1267  if (FAILED(hr))
1268  return hr;
1269  *parentiid = typeattr->guid;
1270  ITypeInfo_ReleaseTypeAttr(parentinfo, typeattr);
1271  ITypeInfo_Release(parentinfo);
1272 
1273  return hr;
1274 }
1275 
1277 {
1278  desc->pfnAllocate = NdrOleAllocate;
1279  desc->pfnFree = NdrOleFree;
1280  desc->Version = 0x50002;
1281  desc->aUserMarshalQuadruple = get_ndr_types_proxy_info()->pStubDesc->aUserMarshalQuadruple;
1282  /* type format string is initialized with proc format string and offset table */
1283 }
1284 
1286 {
1292  unsigned short *offset_table;
1293 };
1294 
1296 {
1297  struct typelib_proxy *proxy = CONTAINING_RECORD(iface, struct typelib_proxy, proxy.IRpcProxyBuffer_iface);
1298  ULONG refcount = InterlockedDecrement(&proxy->proxy.RefCount);
1299 
1300  TRACE("(%p) decreasing refs to %d\n", proxy, refcount);
1301 
1302  if (!refcount)
1303  {
1304  if (proxy->proxy.pChannel)
1305  IRpcProxyBuffer_Disconnect(&proxy->proxy.IRpcProxyBuffer_iface);
1306  if (proxy->proxy.base_object)
1307  IUnknown_Release(proxy->proxy.base_object);
1308  if (proxy->proxy.base_proxy)
1309  IRpcProxyBuffer_Release(proxy->proxy.base_proxy);
1310  heap_free((void *)proxy->stub_desc.pFormatTypes);
1311  heap_free((void *)proxy->proxy_info.ProcFormatString);
1312  heap_free(proxy->offset_table);
1313  heap_free(proxy->proxy_vtbl);
1314  heap_free(proxy);
1315  }
1316  return refcount;
1317 }
1318 
1319 static const IRpcProxyBufferVtbl typelib_proxy_vtbl =
1320 {
1326 };
1327 
1329  ULONG count, const GUID *parentiid, IRpcProxyBuffer **proxy_buffer, void **out)
1330 {
1331  if (!fill_stubless_table((IUnknownVtbl *)proxy->proxy_vtbl->Vtbl, count))
1332  return E_OUTOFMEMORY;
1333 
1334  if (!outer) outer = (IUnknown *)&proxy->proxy;
1335 
1336  proxy->proxy.IRpcProxyBuffer_iface.lpVtbl = &typelib_proxy_vtbl;
1337  proxy->proxy.PVtbl = proxy->proxy_vtbl->Vtbl;
1338  proxy->proxy.RefCount = 1;
1339  proxy->proxy.piid = proxy->proxy_vtbl->header.piid;
1340  proxy->proxy.pUnkOuter = outer;
1341 
1342  if (!IsEqualGUID(parentiid, &IID_IUnknown))
1343  {
1344  HRESULT hr = create_proxy(parentiid, NULL, &proxy->proxy.base_proxy,
1345  (void **)&proxy->proxy.base_object);
1346  if (FAILED(hr)) return hr;
1347  }
1348 
1349  *proxy_buffer = &proxy->proxy.IRpcProxyBuffer_iface;
1350  *out = &proxy->proxy.PVtbl;
1351  IUnknown_AddRef((IUnknown *)*out);
1352 
1353  return S_OK;
1354 }
1355 
1357  REFIID iid, IRpcProxyBuffer **proxy_buffer, void **out)
1358 {
1359  struct typelib_proxy *proxy;
1360  WORD funcs, parentfuncs, i;
1361  GUID parentiid;
1362  HRESULT hr;
1363 
1364  TRACE("typeinfo %p, outer %p, iid %s, proxy_buffer %p, out %p.\n",
1365  typeinfo, outer, debugstr_guid(iid), proxy_buffer, out);
1366 
1367  hr = get_iface_info(&typeinfo, &funcs, &parentfuncs, &parentiid);
1368  if (FAILED(hr))
1369  return hr;
1370 
1371  if (!(proxy = heap_alloc_zero(sizeof(*proxy))))
1372  {
1373  ERR("Failed to allocate proxy object.\n");
1374  return E_OUTOFMEMORY;
1375  }
1376 
1377  init_stub_desc(&proxy->stub_desc);
1378  proxy->proxy_info.pStubDesc = &proxy->stub_desc;
1379 
1380  proxy->proxy_vtbl = heap_alloc_zero(sizeof(proxy->proxy_vtbl->header) + (funcs + parentfuncs) * sizeof(void *));
1381  if (!proxy->proxy_vtbl)
1382  {
1383  ERR("Failed to allocate proxy vtbl.\n");
1384  heap_free(proxy);
1385  return E_OUTOFMEMORY;
1386  }
1387  proxy->proxy_vtbl->header.pStublessProxyInfo = &proxy->proxy_info;
1388  proxy->iid = *iid;
1389  proxy->proxy_vtbl->header.piid = &proxy->iid;
1390  fill_delegated_proxy_table((IUnknownVtbl *)proxy->proxy_vtbl->Vtbl, parentfuncs);
1391  for (i = 0; i < funcs; i++)
1392  proxy->proxy_vtbl->Vtbl[parentfuncs + i] = (void *)-1;
1393 
1394  hr = build_format_strings(typeinfo, funcs, parentfuncs, &proxy->stub_desc.pFormatTypes,
1395  &proxy->proxy_info.ProcFormatString, &proxy->offset_table);
1396  if (FAILED(hr))
1397  {
1398  heap_free(proxy->proxy_vtbl);
1399  heap_free(proxy);
1400  return hr;
1401  }
1402  proxy->proxy_info.FormatStringOffset = &proxy->offset_table[-3];
1403 
1404  hr = typelib_proxy_init(proxy, outer, funcs + parentfuncs, &parentiid, proxy_buffer, out);
1405  if (FAILED(hr))
1406  {
1407  heap_free((void *)proxy->stub_desc.pFormatTypes);
1408  heap_free((void *)proxy->proxy_info.ProcFormatString);
1409  heap_free((void *)proxy->offset_table);
1410  heap_free(proxy->proxy_vtbl);
1411  heap_free(proxy);
1412  }
1413 
1414  return hr;
1415 }
1416 
1418 {
1424  unsigned short *offset_table;
1426 };
1427 
1429 {
1430  struct typelib_stub *stub = CONTAINING_RECORD(iface, struct typelib_stub, stub.stub_buffer);
1431  ULONG refcount = InterlockedDecrement(&stub->stub.stub_buffer.RefCount);
1432 
1433  TRACE("(%p) decreasing refs to %d\n", stub, refcount);
1434 
1435  if (!refcount)
1436  {
1437  /* test_Release shows that native doesn't call Disconnect here.
1438  We'll leave it in for the time being. */
1439  IRpcStubBuffer_Disconnect(iface);
1440 
1441  if (stub->stub.base_stub)
1442  {
1443  IRpcStubBuffer_Release(stub->stub.base_stub);
1444  release_delegating_vtbl(stub->stub.base_obj);
1445  heap_free(stub->dispatch_table);
1446  }
1447 
1448  heap_free((void *)stub->stub_desc.pFormatTypes);
1449  heap_free((void *)stub->server_info.ProcString);
1450  heap_free(stub->offset_table);
1451  heap_free(stub);
1452  }
1453 
1454  return refcount;
1455 }
1456 
1458  const GUID *parentiid, IRpcStubBuffer **stub_buffer)
1459 {
1460  HRESULT hr;
1461 
1462  hr = IUnknown_QueryInterface(server, stub->stub_vtbl.header.piid,
1463  (void **)&stub->stub.stub_buffer.pvServerObject);
1464  if (FAILED(hr))
1465  {
1466  WARN("Failed to get interface %s, hr %#x.\n",
1467  debugstr_guid(stub->stub_vtbl.header.piid), hr);
1468  stub->stub.stub_buffer.pvServerObject = server;
1469  IUnknown_AddRef(server);
1470  }
1471 
1472  if (!IsEqualGUID(parentiid, &IID_IUnknown))
1473  {
1474  stub->stub.base_obj = get_delegating_vtbl(stub->stub_vtbl.header.DispatchTableCount);
1475  hr = create_stub(parentiid, (IUnknown *)&stub->stub.base_obj, &stub->stub.base_stub);
1476  if (FAILED(hr))
1477  {
1478  release_delegating_vtbl(stub->stub.base_obj);
1479  IUnknown_Release(stub->stub.stub_buffer.pvServerObject);
1480  return hr;
1481  }
1482  }
1483 
1484  stub->stub.stub_buffer.lpVtbl = &stub->stub_vtbl.Vtbl;
1485  stub->stub.stub_buffer.RefCount = 1;
1486 
1487  *stub_buffer = (IRpcStubBuffer *)&stub->stub.stub_buffer;
1488  return S_OK;
1489 }
1490 
1492  IUnknown *server, IRpcStubBuffer **stub_buffer)
1493 {
1494  WORD funcs, parentfuncs, i;
1495  struct typelib_stub *stub;
1496  GUID parentiid;
1497  HRESULT hr;
1498 
1499  TRACE("typeinfo %p, iid %s, server %p, stub_buffer %p.\n",
1500  typeinfo, debugstr_guid(iid), server, stub_buffer);
1501 
1502  hr = get_iface_info(&typeinfo, &funcs, &parentfuncs, &parentiid);
1503  if (FAILED(hr))
1504  return hr;
1505 
1506  if (!(stub = heap_alloc_zero(sizeof(*stub))))
1507  {
1508  ERR("Failed to allocate stub object.\n");
1509  return E_OUTOFMEMORY;
1510  }
1511 
1512  init_stub_desc(&stub->stub_desc);
1513  stub->server_info.pStubDesc = &stub->stub_desc;
1514 
1515  hr = build_format_strings(typeinfo, funcs, parentfuncs, &stub->stub_desc.pFormatTypes,
1516  &stub->server_info.ProcString, &stub->offset_table);
1517  if (FAILED(hr))
1518  {
1519  heap_free(stub);
1520  return hr;
1521  }
1522  stub->server_info.FmtStringOffset = &stub->offset_table[-3];
1523 
1524  stub->iid = *iid;
1525  stub->stub_vtbl.header.piid = &stub->iid;
1526  stub->stub_vtbl.header.pServerInfo = &stub->server_info;
1527  stub->stub_vtbl.header.DispatchTableCount = funcs + parentfuncs;
1528 
1529  if (!IsEqualGUID(&parentiid, &IID_IUnknown))
1530  {
1531  stub->dispatch_table = heap_alloc((funcs + parentfuncs) * sizeof(void *));
1532  for (i = 3; i < parentfuncs; i++)
1533  stub->dispatch_table[i - 3] = NdrStubForwardingFunction;
1534  for (; i < funcs + parentfuncs; i++)
1535  stub->dispatch_table[i - 3] = (PRPC_STUB_FUNCTION)NdrStubCall2;
1536  stub->stub_vtbl.header.pDispatchTable = &stub->dispatch_table[-3];
1537  stub->stub_vtbl.Vtbl = CStdStubBuffer_Delegating_Vtbl;
1538  }
1539  else
1540  stub->stub_vtbl.Vtbl = CStdStubBuffer_Vtbl;
1541  stub->stub_vtbl.Vtbl.Release = typelib_stub_Release;
1542 
1543  hr = typelib_stub_init(stub, server, &parentiid, stub_buffer);
1544  if (FAILED(hr))
1545  {
1546  heap_free((void *)stub->stub_desc.pFormatTypes);
1547  heap_free((void *)stub->server_info.ProcString);
1548  heap_free(stub->offset_table);
1549  heap_free(stub);
1550  }
1551 
1552  return hr;
1553 }
static BOOL type_needs_pointer_deref(ITypeInfo *typeinfo, TYPEDESC *desc)
Definition: ndr_typelib.c:442
static const unsigned short MustSize
Definition: ndr_typelib.c:855
struct tagVARIANT VARIANT
Definition: compat.h:2026
LONG WINAPI NdrStubCall2(struct IRpcStubBuffer *pThis, struct IRpcChannelBuffer *pChannel, PRPC_MESSAGE pRpcMsg, DWORD *pdwStubPhase)
static void write_simple_struct_tfs(ITypeInfo *typeinfo, unsigned char *str, size_t *len, TYPEATTR *attr)
Definition: ndr_typelib.c:436
int proxy
Definition: main.c:67
#define REFIID
Definition: guiddef.h:118
#define TRUE
Definition: types.h:120
#define FC_POINTER_DEREF
Definition: ndrtypes.h:276
static size_t write_type_tfs(ITypeInfo *typeinfo, unsigned char *str, size_t *len, TYPEDESC *desc, BOOL toplevel, BOOL onstack)
Definition: ndr_typelib.c:787
Definition: compat.h:1947
static rfbScreenInfoPtr server
Definition: vnc.c:74
static HRESULT get_iface_info(ITypeInfo **typeinfo, WORD *funcs, WORD *parentfuncs, GUID *parentiid)
Definition: ndr_typelib.c:1205
BOOL fill_delegated_proxy_table(IUnknownVtbl *vtbl, DWORD num) DECLSPEC_HIDDEN
Definition: cstub.c:266
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:1160
Definition: compat.h:1963
HRESULT hr
Definition: shlfolder.c:183
Definition: compat.h:1959
static ULONG WINAPI typelib_stub_Release(IRpcStubBuffer *iface)
Definition: ndr_typelib.c:1428
GLuint GLuint GLsizei count
Definition: gl.h:1545
cstdstubbuffer_delegating_t stub
Definition: ndr_typelib.c:1419
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:1027
#define WARN(fmt,...)
Definition: debug.h:111
static size_t write_array_tfs(ITypeInfo *typeinfo, unsigned char *str, size_t *len, ARRAYDESC *desc)
Definition: ndr_typelib.c:623
GLintptr offset
Definition: glext.h:5920
static void init_stub_desc(MIDL_STUB_DESC *desc)
Definition: ndr_typelib.c:1276
Definition: stubgen.c:11
static ITypeLib * typelib
Definition: apps.c:108
unsigned short * offset_table
Definition: ndr_typelib.c:1292
GLuint GLuint GLsizei GLenum type
Definition: gl.h:1545
#define assert(x)
Definition: debug.h:53
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:1328
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:1111
MIDL_STUB_DESC stub_desc
Definition: ndr_typelib.c:1421
static HANDLE proc()
Definition: pdb.c:32
static const unsigned char * get_type_format_string(size_t *size)
Definition: ndr_typelib.c:90
void(__RPC_STUB * PRPC_STUB_FUNCTION)(IRpcStubBuffer *This, IRpcChannelBuffer *_pRpcChannelBuffer, PRPC_MESSAGE _pRpcMessage, DWORD *pdwStubPhase)
Definition: rpcproxy.h:88
#define WRITE_CHAR(str, len, val)
Definition: ndr_typelib.c:44
static const unsigned short IsBasetype
Definition: ndr_typelib.c:860
Definition: send.c:47
GLint GLint GLsizei GLsizei GLsizei GLint GLenum format
Definition: gl.h:1546
static void * heap_alloc(size_t len)
Definition: appwiz.h:65
void WINAPI StdProxy_Disconnect(IRpcProxyBuffer *iface)
Definition: cproxy.c:431
StdProxyImpl proxy
Definition: ndr_typelib.c:1287
static const NDR_PARAM_OIF * get_ndr_types_params(unsigned int *nb_params)
Definition: ndr_typelib.c:58
IUnknownVtbl * get_delegating_vtbl(DWORD num_methods) DECLSPEC_HIDDEN
Definition: cstub.c:289
struct _stub stub
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
const GUID * guid
#define E_OUTOFMEMORY
Definition: ddrawi.h:100
GLenum const GLfloat * params
Definition: glext.h:5645
MIDL_STUB_DESC stub_desc
Definition: ndr_typelib.c:1289
unsigned int BOOL
Definition: ntddk_ex.h:94
static const WCHAR desc[]
Definition: protectdata.c:36
HRESULT WINAPI CreateProxyFromTypeInfo(ITypeInfo *typeinfo, IUnknown *outer, REFIID iid, IRpcProxyBuffer **proxy_buffer, void **out)
Definition: ndr_typelib.c:1356
GLenum GLint ref
Definition: glext.h:6028
#define FIXME(fmt,...)
Definition: debug.h:110
PRPC_STUB_FUNCTION * dispatch_table
Definition: ndr_typelib.c:1425
static unsigned char get_struct_member_fc(ITypeInfo *typeinfo, TYPEDESC *tdesc)
Definition: ndr_typelib.c:239
const WCHAR * str
jmp_buf toplevel
Definition: main.c:95
smooth NULL
Definition: ftsmooth.c:416
unsigned short * offset_table
Definition: ndr_typelib.c:1424
char ext[3]
Definition: mkdosfs.c:358
ULONG WINAPI StdProxy_AddRef(IRpcProxyBuffer *iface)
Definition: cproxy.c:390
#define WRITE_SHORT(str, len, val)
Definition: ndr_typelib.c:46
static const unsigned short MustFree
Definition: ndr_typelib.c:856
#define FC_ALLOCED_ON_STACK
Definition: ndrtypes.h:274
BOOL fill_stubless_table(IUnknownVtbl *vtbl, DWORD num)
Definition: cproxy.c:285
static HRESULT get_param_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:944
HRESULT WINAPI StdProxy_Connect(IRpcProxyBuffer *iface, IRpcChannelBuffer *pChannel)
Definition: cproxy.c:420
static size_t write_pointer_tfs(ITypeInfo *typeinfo, unsigned char *str, size_t *len, TYPEDESC *desc, BOOL toplevel, BOOL onstack)
Definition: ndr_typelib.c:710
#define debugstr_guid
Definition: kernel32.h:35
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
CInterfaceProxyHeader header
Definition: rpcproxy.h:80
static ULONG WINAPI typelib_proxy_Release(IRpcProxyBuffer *iface)
Definition: ndr_typelib.c:1295
#define TRACE(s)
Definition: solgame.cpp:4
GLsizeiptr size
Definition: glext.h:5919
struct _NDR_PROC_HEADER NDR_PROC_HEADER
static unsigned stack_offset(compile_ctx_t *ctx)
Definition: compile.c:349
if(!(yy_init))
Definition: macro.lex.yy.c:714
const IRpcStubBufferVtbl CStdStubBuffer_Vtbl
Definition: cstub.c:552
LONG HRESULT
Definition: typedefs.h:77
const GUID IID_IUnknown
static HRESULT typelib_stub_init(struct typelib_stub *stub, IUnknown *server, const GUID *parentiid, IRpcStubBuffer **stub_buffer)
Definition: ndr_typelib.c:1457
GLfloat param
Definition: glext.h:5796
MIDL_SERVER_INFO server_info
Definition: ndr_typelib.c:1422
static unsigned short get_tfs_offset(int param)
Definition: ndr_typelib.c:81
#define WINAPI
Definition: msvc.h:6
static unsigned char get_basetype(ITypeInfo *typeinfo, TYPEDESC *desc)
Definition: ndr_typelib.c:112
static struct __wine_debug_functions funcs
Definition: debug.c:59
static void get_default_iface(ITypeInfo *typeinfo, WORD count, GUID *iid)
Definition: ndr_typelib.c:684
unsigned short WORD
Definition: ntddk_ex.h:93
static FILE * out
Definition: regtests2xml.c:44
static BOOL type_pointer_is_iface(ITypeInfo *typeinfo, TYPEDESC *tdesc)
Definition: ndr_typelib.c:211
#define for
Definition: utility.h:88
LPFOR_CONTEXT fc
Definition: for.c:53
Definition: cookie.c:201
const unsigned char * pFormatTypes
Definition: rpcndr.h:374
static REFPROPVARIANT PROPVAR_CHANGE_FLAGS VARTYPE vt
Definition: suminfo.c:85
#define Oi_HAS_RPCFLAGS
Definition: ndrtypes.h:293
#define Oi_OBJ_USE_V2_INTERPRETER
Definition: ndrtypes.h:294
GLbitfield flags
Definition: glext.h:7161
static const IRpcProxyBufferVtbl typelib_proxy_vtbl
Definition: ndr_typelib.c:1319
int ret
#define FC_SIMPLE_POINTER
Definition: ndrtypes.h:275
static size_t write_complex_struct_pointer_ref(ITypeInfo *typeinfo, TYPEDESC *desc, unsigned char *str, size_t *len)
Definition: ndr_typelib.c:506
void __RPC_STUB NdrStubForwardingFunction(IRpcStubBuffer *iface, IRpcChannelBuffer *pChannel, PRPC_MESSAGE pMsg, DWORD *pdwStubPhase)
Definition: cstub.c:624
Definition: compat.h:1948
__u8 attr
Definition: mkdosfs.c:359
#define InterlockedDecrement
Definition: armddk.h:52
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
GLenum GLsizei len
Definition: glext.h:6722
void *WINAPI NdrOleAllocate(SIZE_T Size)
Definition: ndr_ole.c:423
static unsigned short write_oleaut_tfs(VARTYPE vt)
Definition: ndr_typelib.c:99
#define err(...)
Definition: compat.h:1950
static const unsigned short IsByValue
Definition: ndr_typelib.c:861
static size_t write_ip_tfs(unsigned char *str, size_t *len, const GUID *iid)
Definition: ndr_typelib.c:669
const ExtendedProxyFileInfo ndr_types_ProxyFileInfo
static const unsigned short IsReturn
Definition: ndr_typelib.c:859
static BOOL type_is_non_iface_pointer(ITypeInfo *typeinfo, TYPEDESC *desc)
Definition: ndr_typelib.c:366
#define ERR(fmt,...)
Definition: debug.h:109
const PCInterfaceProxyVtblList * pProxyVtblList
Definition: rpcproxy.h:48
#define S_OK
Definition: intsafe.h:59
static const MIDL_STUBLESS_PROXY_INFO * get_ndr_types_proxy_info(void)
Definition: ndr_typelib.c:53
unsigned short USHORT
Definition: pedump.c:61
struct _NDR_PROC_HEADER_RPC NDR_PROC_HEADER_RPC
HRESULT create_proxy(REFIID iid, IUnknown *pUnkOuter, IRpcProxyBuffer **pproxy, void **ppv) DECLSPEC_HIDDEN
Definition: ndr_ole.c:442
void WINAPI NdrOleFree(void *NodeToFree)
Definition: ndr_ole.c:432
#define WRITE_INT(str, len, val)
Definition: ndr_typelib.c:48
static const unsigned short IsIn
Definition: ndr_typelib.c:857
#define Oi_OBJECT_PROC
Definition: ndrtypes.h:292
#define E_NOTIMPL
Definition: ddrawi.h:99
CInterfaceStubVtbl stub_vtbl
Definition: ndr_typelib.c:1423
unsigned short VARTYPE
Definition: compat.h:1903
BOOL WINAPI IsEqualGUID(REFGUID rguid1, REFGUID rguid2)
Definition: compobj.c:4112
static size_t write_struct_tfs(ITypeInfo *typeinfo, unsigned char *str, size_t *len, TYPEATTR *attr)
Definition: ndr_typelib.c:601
WINE_DEFAULT_DEBUG_CHANNEL(ole)
static void write_proc_func_header(ITypeInfo *typeinfo, FUNCDESC *desc, WORD proc_idx, unsigned char *proc, size_t *proclen)
Definition: ndr_typelib.c:1068
static void write_struct_members(ITypeInfo *typeinfo, unsigned char *str, size_t *len, TYPEATTR *attr)
Definition: ndr_typelib.c:393
static unsigned int type_memsize(ITypeInfo *typeinfo, TYPEDESC *desc)
Definition: ndr_typelib.c:152
static const unsigned short IsOut
Definition: ndr_typelib.c:858
static unsigned char get_array_fc(ITypeInfo *typeinfo, TYPEDESC *desc)
Definition: ndr_typelib.c:330
unsigned int ULONG
Definition: retypes.h:1
HRESULT WINAPI StdProxy_QueryInterface(IRpcProxyBuffer *iface, REFIID riid, void **obj)
Definition: cproxy.c:369
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:864
static unsigned short get_stack_size(ITypeInfo *typeinfo, TYPEDESC *desc)
Definition: ndr_typelib.c:844
void release_delegating_vtbl(IUnknownVtbl *vtbl) DECLSPEC_HIDDEN
Definition: cstub.c:325
static void write_complex_struct_pointer_layout(ITypeInfo *typeinfo, TYPEDESC *desc, unsigned char *str, size_t *len)
Definition: ndr_typelib.c:467
PMIDL_STUB_DESC pStubDesc
Definition: rpcndr.h:433
static unsigned char get_struct_fc(ITypeInfo *typeinfo, TYPEATTR *attr)
Definition: ndr_typelib.c:308
const USER_MARSHAL_ROUTINE_QUADRUPLE * aUserMarshalQuadruple
Definition: rpcndr.h:380
static OLECHAR OLECHAR *static SYSKIND
Definition: typelib.c:80
MIDL_STUBLESS_PROXY_INFO proxy_info
Definition: ndr_typelib.c:1290
struct CFHEADER header
Definition: fdi.c:101
CInterfaceProxyVtbl * proxy_vtbl
Definition: ndr_typelib.c:1291
Definition: compat.h:1949
HRESULT WINAPI CreateStubFromTypeInfo(ITypeInfo *typeinfo, REFIID iid, IUnknown *server, IRpcStubBuffer **stub_buffer)
Definition: ndr_typelib.c:1491
Definition: compat.h:1946
#define SUCCEEDED(hr)
Definition: intsafe.h:57
static void write_complex_struct_tfs(ITypeInfo *typeinfo, unsigned char *str, size_t *len, TYPEATTR *attr)
Definition: ndr_typelib.c:535
const IRpcStubBufferVtbl CStdStubBuffer_Delegating_Vtbl
Definition: cstub.c:601
static const unsigned short IsSimpleRef
Definition: ndr_typelib.c:862
static BOOL heap_free(void *mem)
Definition: appwiz.h:75
HRESULT create_stub(REFIID iid, IUnknown *pUnk, IRpcStubBuffer **ppstub) DECLSPEC_HIDDEN
Definition: ndr_ole.c:466
off
Definition: i386-dis.c:3909