~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~ [ freetext search ] ~ [ file search ] ~

Wine Cross Reference
wine/dlls/ole32/usrmarshal.c

Version: ~ [ wine-1.1.24 ] ~ [ wine-1.1.23 ] ~ [ wine-1.1.22 ] ~ [ wine-1.1.21 ] ~ [ wine-1.1.20 ] ~ [ wine-1.1.19 ] ~ [ wine-1.1.18 ] ~ [ wine-1.1.17 ] ~ [ wine-1.1.16 ] ~ [ wine-1.1.15 ] ~ [ wine-1.1.14 ] ~ [ wine-1.1.13 ] ~ [ wine-1.1.12 ] ~ [ wine-1.1.11 ] ~ [ wine-1.1.10 ] ~ [ wine-1.1.9 ] ~ [ wine-1.1.8 ] ~ [ wine-1.1.7 ] ~ [ wine-1.0.1 ] ~ [ wine-1.1.6 ] ~ [ wine-1.1.5 ] ~ [ wine-1.1.4 ] ~ [ wine-1.1.3 ] ~ [ wine-1.1.2 ] ~ [ wine-1.1.1 ] ~ [ wine-1.1.0 ] ~ [ wine-1.0 ] ~

  1 /*
  2  * Miscellaneous Marshaling Routines
  3  *
  4  * Copyright 2005 Robert Shearman
  5  *
  6  * This library is free software; you can redistribute it and/or
  7  * modify it under the terms of the GNU Lesser General Public
  8  * License as published by the Free Software Foundation; either
  9  * version 2.1 of the License, or (at your option) any later version.
 10  *
 11  * This library is distributed in the hope that it will be useful,
 12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
 13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 14  * Lesser General Public License for more details.
 15  *
 16  * You should have received a copy of the GNU Lesser General Public
 17  * License along with this library; if not, write to the Free Software
 18  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
 19  */
 20 
 21 #include <stdio.h>
 22 #include <stdarg.h>
 23 #include <string.h>
 24 
 25 #define COBJMACROS
 26 #define NONAMELESSUNION
 27 #define NONAMELESSSTRUCT
 28 
 29 #include "windef.h"
 30 #include "winbase.h"
 31 #include "wingdi.h"
 32 #include "winuser.h"
 33 #include "winerror.h"
 34 
 35 #include "ole2.h"
 36 #include "oleauto.h"
 37 #include "rpcproxy.h"
 38 
 39 #include "wine/unicode.h"
 40 #include "wine/debug.h"
 41 
 42 WINE_DEFAULT_DEBUG_CHANNEL(ole);
 43 
 44 #define ALIGNED_LENGTH(_Len, _Align) (((_Len)+(_Align))&~(_Align))
 45 #define ALIGNED_POINTER(_Ptr, _Align) ((LPVOID)ALIGNED_LENGTH((ULONG_PTR)(_Ptr), _Align))
 46 #define ALIGN_LENGTH(_Len, _Align) _Len = ALIGNED_LENGTH(_Len, _Align)
 47 #define ALIGN_POINTER(_Ptr, _Align) _Ptr = ALIGNED_POINTER(_Ptr, _Align)
 48 
 49 #define USER_MARSHAL_PTR_PREFIX \
 50   ( (DWORD)'U'         | ( (DWORD)'s' << 8 ) | \
 51   ( (DWORD)'e' << 16 ) | ( (DWORD)'r' << 24 ) )
 52 
 53 static const char* debugstr_user_flags(ULONG *pFlags)
 54 {
 55     char buf[12];
 56     const char* loword;
 57     switch (LOWORD(*pFlags))
 58     {
 59     case MSHCTX_LOCAL:
 60         loword="MSHCTX_LOCAL";
 61         break;
 62     case MSHCTX_NOSHAREDMEM:
 63         loword="MSHCTX_NOSHAREDMEM";
 64         break;
 65     case MSHCTX_DIFFERENTMACHINE:
 66         loword="MSHCTX_DIFFERENTMACHINE";
 67         break;
 68     case MSHCTX_INPROC:
 69         loword="MSHCTX_INPROC";
 70         break;
 71     default:
 72         sprintf(buf, "%d", LOWORD(*pFlags));
 73         loword=buf;
 74     }
 75 
 76     if (HIWORD(*pFlags) == NDR_LOCAL_DATA_REPRESENTATION)
 77         return wine_dbg_sprintf("MAKELONG(NDR_LOCAL_REPRESENTATION, %s)", loword);
 78     else
 79         return wine_dbg_sprintf("MAKELONG(0x%04x, %s)", HIWORD(*pFlags), loword);
 80 }
 81 
 82 /******************************************************************************
 83  *           CLIPFORMAT_UserSize [OLE32.@]
 84  *
 85  * Calculates the buffer size required to marshal a clip format.
 86  *
 87  * PARAMS
 88  *  pFlags       [I] Flags. See notes.
 89  *  StartingSize [I] Starting size of the buffer. This value is added on to
 90  *                   the buffer size required for the clip format.
 91  *  pCF          [I] Clip format to size.
 92  *
 93  * RETURNS
 94  *  The buffer size required to marshal a clip format plus the starting size.
 95  *
 96  * NOTES
 97  *  Even though the function is documented to take a pointer to an unsigned
 98  *  long in pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
 99  *  the first parameter is an unsigned long.
100  *  This function is only intended to be called by the RPC runtime.
101  */
102 ULONG __RPC_USER CLIPFORMAT_UserSize(ULONG *pFlags, ULONG StartingSize, CLIPFORMAT *pCF)
103 {
104     ULONG size = StartingSize;
105 
106     TRACE("(%s, %d, %p\n", debugstr_user_flags(pFlags), StartingSize, pCF);
107 
108     size += 8;
109 
110     /* only need to marshal the name if it is not a pre-defined type and
111      * we are going remote */
112     if ((*pCF >= 0xc000) && (LOWORD(*pFlags) == MSHCTX_DIFFERENTMACHINE))
113     {
114         WCHAR format[255];
115         INT ret;
116         size += 3 * sizeof(UINT);
117         /* urg! this function is badly designed because it won't tell us how
118          * much space is needed without doing a dummy run of storing the
119          * name into a buffer */
120         ret = GetClipboardFormatNameW(*pCF, format, sizeof(format)/sizeof(format[0])-1);
121         if (!ret)
122             RaiseException(DV_E_CLIPFORMAT, 0, 0, NULL);
123         size += (ret + 1) * sizeof(WCHAR);
124     }
125     return size;
126 }
127 
128 /******************************************************************************
129  *           CLIPFORMAT_UserMarshal [OLE32.@]
130  *
131  * Marshals a clip format into a buffer.
132  *
133  * PARAMS
134  *  pFlags  [I] Flags. See notes.
135  *  pBuffer [I] Buffer to marshal the clip format into.
136  *  pCF     [I] Clip format to marshal.
137  *
138  * RETURNS
139  *  The end of the marshaled data in the buffer.
140  *
141  * NOTES
142  *  Even though the function is documented to take a pointer to an unsigned
143  *  long in pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
144  *  the first parameter is an unsigned long.
145  *  This function is only intended to be called by the RPC runtime.
146  */
147 unsigned char * __RPC_USER CLIPFORMAT_UserMarshal(ULONG *pFlags, unsigned char *pBuffer, CLIPFORMAT *pCF)
148 {
149     TRACE("(%s, %p, &0x%04x\n", debugstr_user_flags(pFlags), pBuffer, *pCF);
150 
151     /* only need to marshal the name if it is not a pre-defined type and
152      * we are going remote */
153     if ((*pCF >= 0xc000) && (LOWORD(*pFlags) == MSHCTX_DIFFERENTMACHINE))
154     {
155         WCHAR format[255];
156         UINT len;
157 
158         *(DWORD *)pBuffer = WDT_REMOTE_CALL;
159         pBuffer += 4;
160         *(DWORD *)pBuffer = *pCF;
161         pBuffer += 4;
162 
163         len = GetClipboardFormatNameW(*pCF, format, sizeof(format)/sizeof(format[0])-1);
164         if (!len)
165             RaiseException(DV_E_CLIPFORMAT, 0, 0, NULL);
166         len += 1;
167         *(UINT *)pBuffer = len;
168         pBuffer += sizeof(UINT);
169         *(UINT *)pBuffer = 0;
170         pBuffer += sizeof(UINT);
171         *(UINT *)pBuffer = len;
172         pBuffer += sizeof(UINT);
173         TRACE("marshaling format name %s\n", debugstr_wn(format, len-1));
174         lstrcpynW((LPWSTR)pBuffer, format, len);
175         pBuffer += len * sizeof(WCHAR);
176         *(WCHAR *)pBuffer = '\0';
177         pBuffer += sizeof(WCHAR);
178     }
179     else
180     {
181         *(DWORD *)pBuffer = WDT_INPROC_CALL;
182         pBuffer += 4;
183         *(DWORD *)pBuffer = *pCF;
184         pBuffer += 4;
185     }
186 
187     return pBuffer;
188 }
189 
190 /******************************************************************************
191  *           CLIPFORMAT_UserUnmarshal [OLE32.@]
192  *
193  * Unmarshals a clip format from a buffer.
194  *
195  * PARAMS
196  *  pFlags  [I] Flags. See notes.
197  *  pBuffer [I] Buffer to marshal the clip format from.
198  *  pCF     [O] Address that receive the unmarshaled clip format.
199  *
200  * RETURNS
201  *  The end of the marshaled data in the buffer.
202  *
203  * NOTES
204  *  Even though the function is documented to take a pointer to an unsigned
205  *  long in pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
206  *  the first parameter is an unsigned long.
207  *  This function is only intended to be called by the RPC runtime.
208  */
209 unsigned char * __RPC_USER CLIPFORMAT_UserUnmarshal(ULONG *pFlags, unsigned char *pBuffer, CLIPFORMAT *pCF)
210 {
211     LONG fContext;
212 
213     TRACE("(%s, %p, %p\n", debugstr_user_flags(pFlags), pBuffer, pCF);
214 
215     fContext = *(DWORD *)pBuffer;
216     pBuffer += 4;
217 
218     if (fContext == WDT_INPROC_CALL)
219     {
220         *pCF = *(CLIPFORMAT *)pBuffer;
221         pBuffer += 4;
222     }
223     else if (fContext == WDT_REMOTE_CALL)
224     {
225         CLIPFORMAT cf;
226         UINT len;
227 
228         /* pointer ID for registered clip format string */
229         if (*(DWORD *)pBuffer == 0)
230             RaiseException(RPC_S_INVALID_BOUND, 0, 0, NULL);
231         pBuffer += 4;
232 
233         len = *(UINT *)pBuffer;
234         pBuffer += sizeof(UINT);
235         if (*(UINT *)pBuffer != 0)
236             RaiseException(RPC_S_INVALID_BOUND, 0, 0, NULL);
237         pBuffer += sizeof(UINT);
238         if (*(UINT *)pBuffer != len)
239             RaiseException(RPC_S_INVALID_BOUND, 0, 0, NULL);
240         pBuffer += sizeof(UINT);
241         if (((WCHAR *)pBuffer)[len] != '\0')
242             RaiseException(RPC_S_INVALID_BOUND, 0, 0, NULL);
243         TRACE("unmarshaling clip format %s\n", debugstr_w((LPCWSTR)pBuffer));
244         cf = RegisterClipboardFormatW((LPCWSTR)pBuffer);
245         pBuffer += (len + 1) * sizeof(WCHAR);
246         if (!cf)
247             RaiseException(DV_E_CLIPFORMAT, 0, 0, NULL);
248         *pCF = cf;
249     }
250     else
251         /* code not really appropriate, but nearest I can find */
252         RaiseException(RPC_S_INVALID_TAG, 0, 0, NULL);
253     return pBuffer;
254 }
255 
256 /******************************************************************************
257  *           CLIPFORMAT_UserFree [OLE32.@]
258  *
259  * Frees an unmarshaled clip format.
260  *
261  * PARAMS
262  *  pFlags  [I] Flags. See notes.
263  *  pCF     [I] Clip format to free.
264  *
265  * RETURNS
266  *  The end of the marshaled data in the buffer.
267  *
268  * NOTES
269  *  Even though the function is documented to take a pointer to an unsigned
270  *  long in pFlags, it actually takes a pointer to a USER_MARSHAL_CB
271  *  structure, of which the first parameter is an unsigned long.
272  *  This function is only intended to be called by the RPC runtime.
273  */
274 void __RPC_USER CLIPFORMAT_UserFree(ULONG *pFlags, CLIPFORMAT *pCF)
275 {
276     /* there is no inverse of the RegisterClipboardFormat function,
277      * so nothing to do */
278 }
279 
280 static ULONG handle_UserSize(ULONG *pFlags, ULONG StartingSize, HANDLE *handle)
281 {
282     if (LOWORD(*pFlags) == MSHCTX_DIFFERENTMACHINE)
283     {
284         ERR("can't remote a local handle\n");
285         RaiseException(RPC_S_INVALID_TAG, 0, 0, NULL);
286         return StartingSize;
287     }
288     return StartingSize + sizeof(RemotableHandle);
289 }
290 
291 static unsigned char * handle_UserMarshal(ULONG *pFlags, unsigned char *pBuffer, HANDLE *handle)
292 {
293     RemotableHandle *remhandle = (RemotableHandle *)pBuffer;
294     if (LOWORD(*pFlags) == MSHCTX_DIFFERENTMACHINE)
295     {
296         ERR("can't remote a local handle\n");
297         RaiseException(RPC_S_INVALID_TAG, 0, 0, NULL);
298         return pBuffer;
299     }
300     remhandle->fContext = WDT_INPROC_CALL;
301     remhandle->u.hInproc = (LONG_PTR)*handle;
302     return pBuffer + sizeof(RemotableHandle);
303 }
304 
305 static unsigned char * handle_UserUnmarshal(ULONG *pFlags, unsigned char *pBuffer, HANDLE *handle)
306 {
307     RemotableHandle *remhandle = (RemotableHandle *)pBuffer;
308     if (remhandle->fContext != WDT_INPROC_CALL)
309         RaiseException(RPC_X_BAD_STUB_DATA, 0, 0, NULL);
310     *handle = (HANDLE)(LONG_PTR)remhandle->u.hInproc;
311     return pBuffer + sizeof(RemotableHandle);
312 }
313 
314 static void handle_UserFree(ULONG *pFlags, HANDLE *phMenu)
315 {
316     /* nothing to do */
317 }
318 
319 #define IMPL_WIREM_HANDLE(type) \
320     ULONG __RPC_USER type##_UserSize(ULONG *pFlags, ULONG StartingSize, type *handle) \
321     { \
322         TRACE("(%s, %d, %p\n", debugstr_user_flags(pFlags), StartingSize, handle); \
323         return handle_UserSize(pFlags, StartingSize, (HANDLE *)handle); \
324     } \
325     \
326     unsigned char * __RPC_USER type##_UserMarshal(ULONG *pFlags, unsigned char *pBuffer, type *handle) \
327     { \
328         TRACE("(%s, %p, &%p\n", debugstr_user_flags(pFlags), pBuffer, *handle); \
329         return handle_UserMarshal(pFlags, pBuffer, (HANDLE *)handle); \
330     } \
331     \
332     unsigned char * __RPC_USER type##_UserUnmarshal(ULONG *pFlags, unsigned char *pBuffer, type *handle) \
333     { \
334         TRACE("(%s, %p, %p\n", debugstr_user_flags(pFlags), pBuffer, handle); \
335         return handle_UserUnmarshal(pFlags, pBuffer, (HANDLE *)handle); \
336     } \
337     \
338     void __RPC_USER type##_UserFree(ULONG *pFlags, type *handle) \
339     { \
340         TRACE("(%s, &%p\n", debugstr_user_flags(pFlags), *handle); \
341         handle_UserFree(pFlags, (HANDLE *)handle); \
342     }
343 
344 IMPL_WIREM_HANDLE(HACCEL)
345 IMPL_WIREM_HANDLE(HMENU)
346 IMPL_WIREM_HANDLE(HWND)
347 
348 /******************************************************************************
349  *           HGLOBAL_UserSize [OLE32.@]
350  *
351  * Calculates the buffer size required to marshal an HGLOBAL.
352  *
353  * PARAMS
354  *  pFlags       [I] Flags. See notes.
355  *  StartingSize [I] Starting size of the buffer. This value is added on to
356  *                   the buffer size required for the clip format.
357  *  phGlobal     [I] HGLOBAL to size.
358  *
359  * RETURNS
360  *  The buffer size required to marshal an HGLOBAL plus the starting size.
361  *
362  * NOTES
363  *  Even though the function is documented to take a pointer to a ULONG in
364  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
365  *  the first parameter is a ULONG.
366  *  This function is only intended to be called by the RPC runtime.
367  */
368 ULONG __RPC_USER HGLOBAL_UserSize(ULONG *pFlags, ULONG StartingSize, HGLOBAL *phGlobal)
369 {
370     ULONG size = StartingSize;
371 
372     TRACE("(%s, %d, %p\n", debugstr_user_flags(pFlags), StartingSize, phGlobal);
373 
374     ALIGN_LENGTH(size, 3);
375 
376     size += sizeof(ULONG);
377 
378     if (LOWORD(*pFlags == MSHCTX_INPROC))
379         size += sizeof(HGLOBAL);
380     else
381     {
382         size += sizeof(ULONG);
383         if (*phGlobal)
384         {
385             SIZE_T ret;
386             size += 3 * sizeof(ULONG);
387             ret = GlobalSize(*phGlobal);
388             size += (ULONG)ret;
389         }
390     }
391     
392     return size;
393 }
394 
395 /******************************************************************************
396  *           HGLOBAL_UserMarshal [OLE32.@]
397  *
398  * Marshals an HGLOBAL into a buffer.
399  *
400  * PARAMS
401  *  pFlags   [I] Flags. See notes.
402  *  pBuffer  [I] Buffer to marshal the clip format into.
403  *  phGlobal [I] HGLOBAL to marshal.
404  *
405  * RETURNS
406  *  The end of the marshaled data in the buffer.
407  *
408  * NOTES
409  *  Even though the function is documented to take a pointer to a ULONG in
410  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
411  *  the first parameter is a ULONG.
412  *  This function is only intended to be called by the RPC runtime.
413  */
414 unsigned char * __RPC_USER HGLOBAL_UserMarshal(ULONG *pFlags, unsigned char *pBuffer, HGLOBAL *phGlobal)
415 {
416     TRACE("(%s, %p, &%p\n", debugstr_user_flags(pFlags), pBuffer, *phGlobal);
417 
418     ALIGN_POINTER(pBuffer, 3);
419 
420     if (LOWORD(*pFlags == MSHCTX_INPROC))
421     {
422         if (sizeof(*phGlobal) == 8)
423             *(ULONG *)pBuffer = WDT_INPROC64_CALL;
424         else
425             *(ULONG *)pBuffer = WDT_INPROC_CALL;
426         pBuffer += sizeof(ULONG);
427         *(HGLOBAL *)pBuffer = *phGlobal;
428         pBuffer += sizeof(HGLOBAL);
429     }
430     else
431     {
432         *(ULONG *)pBuffer = WDT_REMOTE_CALL;
433         pBuffer += sizeof(ULONG);
434         *(ULONG *)pBuffer = (ULONG)*phGlobal;
435         pBuffer += sizeof(ULONG);
436         if (*phGlobal)
437         {
438             const unsigned char *memory;
439             SIZE_T size = GlobalSize(*phGlobal);
440             *(ULONG *)pBuffer = (ULONG)size;
441             pBuffer += sizeof(ULONG);
442             *(ULONG *)pBuffer = (ULONG)*phGlobal;
443             pBuffer += sizeof(ULONG);
444             *(ULONG *)pBuffer = (ULONG)size;
445             pBuffer += sizeof(ULONG);
446 
447             memory = GlobalLock(*phGlobal);
448             memcpy(pBuffer, memory, size);
449             pBuffer += size;
450             GlobalUnlock(*phGlobal);
451         }
452     }
453 
454     return pBuffer;
455 }
456 
457 /******************************************************************************
458  *           HGLOBAL_UserUnmarshal [OLE32.@]
459  *
460  * Unmarshals an HGLOBAL from a buffer.
461  *
462  * PARAMS
463  *  pFlags   [I] Flags. See notes.
464  *  pBuffer  [I] Buffer to marshal the clip format from.
465  *  phGlobal [O] Address that receive the unmarshaled HGLOBAL.
466  *
467  * RETURNS
468  *  The end of the marshaled data in the buffer.
469  *
470  * NOTES
471  *  Even though the function is documented to take a pointer to an ULONG in
472  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
473  *  the first parameter is an ULONG.
474  *  This function is only intended to be called by the RPC runtime.
475  */
476 unsigned char * __RPC_USER HGLOBAL_UserUnmarshal(ULONG *pFlags, unsigned char *pBuffer, HGLOBAL *phGlobal)
477 {
478     ULONG fContext;
479 
480     TRACE("(%s, %p, &%p\n", debugstr_user_flags(pFlags), pBuffer, *phGlobal);
481 
482     ALIGN_POINTER(pBuffer, 3);
483 
484     fContext = *(ULONG *)pBuffer;
485     pBuffer += sizeof(ULONG);
486 
487     if (((fContext == WDT_INPROC_CALL) && (sizeof(*phGlobal) < 8)) ||
488         ((fContext == WDT_INPROC64_CALL) && (sizeof(*phGlobal) == 8)))
489     {
490         *phGlobal = *(HGLOBAL *)pBuffer;
491         pBuffer += sizeof(*phGlobal);
492     }
493     else if (fContext == WDT_REMOTE_CALL)
494     {
495         ULONG handle;
496 
497         handle = *(ULONG *)pBuffer;
498         pBuffer += sizeof(ULONG);
499 
500         if (handle)
501         {
502             ULONG size;
503             void *memory;
504 
505             size = *(ULONG *)pBuffer;
506             pBuffer += sizeof(ULONG);
507             /* redundancy is bad - it means you have to check consistency like
508              * this: */
509             if (*(ULONG *)pBuffer != handle)
510             {
511                 RaiseException(RPC_X_BAD_STUB_DATA, 0, 0, NULL);
512                 return pBuffer;
513             }
514             pBuffer += sizeof(ULONG);
515             /* redundancy is bad - it means you have to check consistency like
516              * this: */
517             if (*(ULONG *)pBuffer != size)
518             {
519                 RaiseException(RPC_X_BAD_STUB_DATA, 0, 0, NULL);
520                 return pBuffer;
521             }
522             pBuffer += sizeof(ULONG);
523 
524             /* FIXME: check size is not too big */
525 
526             *phGlobal = GlobalAlloc(GMEM_MOVEABLE, size);
527             memory = GlobalLock(*phGlobal);
528             memcpy(memory, pBuffer, size);
529             pBuffer += size;
530             GlobalUnlock(*phGlobal);
531         }
532         else
533             *phGlobal = NULL;
534     }
535     else
536         RaiseException(RPC_S_INVALID_TAG, 0, 0, NULL);
537 
538     return pBuffer;
539 }
540 
541 /******************************************************************************
542  *           HGLOBAL_UserFree [OLE32.@]
543  *
544  * Frees an unmarshaled HGLOBAL.
545  *
546  * PARAMS
547  *  pFlags   [I] Flags. See notes.
548  *  phGlobal [I] HGLOBAL to free.
549  *
550  * RETURNS
551  *  The end of the marshaled data in the buffer.
552  *
553  * NOTES
554  *  Even though the function is documented to take a pointer to a ULONG in
555  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of
556  *  which the first parameter is a ULONG.
557  *  This function is only intended to be called by the RPC runtime.
558  */
559 void __RPC_USER HGLOBAL_UserFree(ULONG *pFlags, HGLOBAL *phGlobal)
560 {
561     TRACE("(%s, &%p\n", debugstr_user_flags(pFlags), *phGlobal);
562 
563     if (LOWORD(*pFlags != MSHCTX_INPROC) && *phGlobal)
564         GlobalFree(*phGlobal);
565 }
566 
567 /******************************************************************************
568  *           HBITMAP_UserSize [OLE32.@]
569  *
570  * Calculates the buffer size required to marshal a bitmap.
571  *
572  * PARAMS
573  *  pFlags       [I] Flags. See notes.
574  *  StartingSize [I] Starting size of the buffer. This value is added on to
575  *                   the buffer size required for the clip format.
576  *  phBmp        [I] Bitmap to size.
577  *
578  * RETURNS
579  *  The buffer size required to marshal an bitmap plus the starting size.
580  *
581  * NOTES
582  *  Even though the function is documented to take a pointer to a ULONG in
583  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
584  *  the first parameter is a ULONG.
585  *  This function is only intended to be called by the RPC runtime.
586  */
587 ULONG __RPC_USER HBITMAP_UserSize(ULONG *pFlags, ULONG StartingSize, HBITMAP *phBmp)
588 {
589     FIXME(":stub\n");
590     return StartingSize;
591 }
592 
593 /******************************************************************************
594 *           HBITMAP_UserMarshal [OLE32.@]
595 *
596 * Marshals a bitmap into a buffer.
597 *
598 * PARAMS
599 *  pFlags  [I] Flags. See notes.
600 *  pBuffer [I] Buffer to marshal the clip format into.
601 *  phBmp   [I] Bitmap to marshal.
602 *
603 * RETURNS
604 *  The end of the marshaled data in the buffer.
605 *
606 * NOTES
607 *  Even though the function is documented to take a pointer to a ULONG in
608 *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
609 *  the first parameter is a ULONG.
610 *  This function is only intended to be called by the RPC runtime.
611 */
612 unsigned char * __RPC_USER HBITMAP_UserMarshal(ULONG *pFlags, unsigned char *pBuffer, HBITMAP *phBmp)
613 {
614     FIXME(":stub\n");
615     return pBuffer;
616 }
617 
618 /******************************************************************************
619  *           HBITMAP_UserUnmarshal [OLE32.@]
620  *
621  * Unmarshals a bitmap from a buffer.
622  *
623  * PARAMS
624  *  pFlags   [I] Flags. See notes.
625  *  pBuffer  [I] Buffer to marshal the clip format from.
626  *  phBmp    [O] Address that receive the unmarshaled bitmap.
627  *
628  * RETURNS
629  *  The end of the marshaled data in the buffer.
630  *
631  * NOTES
632  *  Even though the function is documented to take a pointer to an ULONG in
633  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
634  *  the first parameter is an ULONG.
635  *  This function is only intended to be called by the RPC runtime.
636  */
637 unsigned char * __RPC_USER HBITMAP_UserUnmarshal(ULONG *pFlags, unsigned char *pBuffer, HBITMAP *phBmp)
638 {
639     FIXME(":stub\n");
640     return pBuffer;
641 }
642 
643 /******************************************************************************
644  *           HBITMAP_UserFree [OLE32.@]
645  *
646  * Frees an unmarshaled bitmap.
647  *
648  * PARAMS
649  *  pFlags   [I] Flags. See notes.
650  *  phBmp    [I] Bitmap to free.
651  *
652  * RETURNS
653  *  The end of the marshaled data in the buffer.
654  *
655  * NOTES
656  *  Even though the function is documented to take a pointer to a ULONG in
657  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of
658  *  which the first parameter is a ULONG.
659  *  This function is only intended to be called by the RPC runtime.
660  */
661 void __RPC_USER HBITMAP_UserFree(ULONG *pFlags, HBITMAP *phBmp)
662 {
663     FIXME(":stub\n");
664 }
665 
666 /******************************************************************************
667  *           HICON_UserSize [OLE32.@]
668  *
669  * Calculates the buffer size required to marshal an icon.
670  *
671  * PARAMS
672  *  pFlags       [I] Flags. See notes.
673  *  StartingSize [I] Starting size of the buffer. This value is added on to
674  *                   the buffer size required for the icon.
675  *  phIcon       [I] Icon to size.
676  *
677  * RETURNS
678  *  The buffer size required to marshal an icon plus the starting size.
679  *
680  * NOTES
681  *  Even though the function is documented to take a pointer to a ULONG in
682  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
683  *  the first parameter is a ULONG.
684  *  This function is only intended to be called by the RPC runtime.
685  */
686 ULONG __RPC_USER HICON_UserSize(ULONG *pFlags, ULONG StartingSize, HICON *phIcon)
687 {
688     FIXME(":stub\n");
689     return StartingSize;
690 }
691 
692 /******************************************************************************
693 *           HICON_UserMarshal [OLE32.@]
694 *
695 * Marshals an icon into a buffer.
696 *
697 * PARAMS
698 *  pFlags  [I] Flags. See notes.
699 *  pBuffer [I] Buffer to marshal the icon into.
700 *  phIcon  [I] Icon to marshal.
701 *
702 * RETURNS
703 *  The end of the marshaled data in the buffer.
704 *
705 * NOTES
706 *  Even though the function is documented to take a pointer to a ULONG in
707 *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
708 *  the first parameter is a ULONG.
709 *  This function is only intended to be called by the RPC runtime.
710 */
711 unsigned char * __RPC_USER HICON_UserMarshal(ULONG *pFlags, unsigned char *pBuffer, HICON *phIcon)
712 {
713     FIXME(":stub\n");
714     return pBuffer;
715 }
716 
717 /******************************************************************************
718  *           HICON_UserUnmarshal [OLE32.@]
719  *
720  * Unmarshals an icon from a buffer.
721  *
722  * PARAMS
723  *  pFlags   [I] Flags. See notes.
724  *  pBuffer  [I] Buffer to marshal the icon from.
725  *  phIcon   [O] Address that receive the unmarshaled icon.
726  *
727  * RETURNS
728  *  The end of the marshaled data in the buffer.
729  *
730  * NOTES
731  *  Even though the function is documented to take a pointer to an ULONG in
732  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
733  *  the first parameter is an ULONG.
734  *  This function is only intended to be called by the RPC runtime.
735  */
736 unsigned char * __RPC_USER HICON_UserUnmarshal(ULONG *pFlags, unsigned char *pBuffer, HICON *phIcon)
737 {
738     FIXME(":stub\n");
739     return pBuffer;
740 }
741 
742 /******************************************************************************
743  *           HICON_UserFree [OLE32.@]
744  *
745  * Frees an unmarshaled icon.
746  *
747  * PARAMS
748  *  pFlags   [I] Flags. See notes.
749  *  phIcon   [I] Icon to free.
750  *
751  * RETURNS
752  *  The end of the marshaled data in the buffer.
753  *
754  * NOTES
755  *  Even though the function is documented to take a pointer to a ULONG in
756  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of
757  *  which the first parameter is a ULONG.
758  *  This function is only intended to be called by the RPC runtime.
759  */
760 void __RPC_USER HICON_UserFree(ULONG *pFlags, HICON *phIcon)
761 {
762     FIXME(":stub\n");
763 }
764 
765 /******************************************************************************
766  *           HDC_UserSize [OLE32.@]
767  *
768  * Calculates the buffer size required to marshal an HDC.
769  *
770  * PARAMS
771  *  pFlags       [I] Flags. See notes.
772  *  StartingSize [I] Starting size of the buffer. This value is added on to
773  *                   the buffer size required for the clip format.
774  *  phGlobal     [I] HDC to size.
775  *
776  * RETURNS
777  *  The buffer size required to marshal an HDC plus the starting size.
778  *
779  * NOTES
780  *  Even though the function is documented to take a pointer to a ULONG in
781  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
782  *  the first parameter is a ULONG.
783  *  This function is only intended to be called by the RPC runtime.
784  */
785 ULONG __RPC_USER HDC_UserSize(ULONG *pFlags, ULONG StartingSize, HDC *phdc)
786 {
787     FIXME(":stub\n");
788     return StartingSize;
789 }
790 
791 /******************************************************************************
792  *           HDC_UserMarshal [OLE32.@]
793  *
794  * Marshals an HDC into a buffer.
795  *
796  * PARAMS
797  *  pFlags  [I] Flags. See notes.
798  *  pBuffer [I] Buffer to marshal the clip format into.
799  *  phdc    [I] HDC to marshal.
800  *
801  * RETURNS
802  *  The end of the marshaled data in the buffer.
803  *
804  * NOTES
805  *  Even though the function is documented to take a pointer to a ULONG in
806  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
807  *  the first parameter is a ULONG.
808  *  This function is only intended to be called by the RPC runtime.
809  */
810 unsigned char * __RPC_USER HDC_UserMarshal(ULONG *pFlags, unsigned char *pBuffer, HDC *phdc)
811 {
812     FIXME(":stub\n");
813     return pBuffer;
814 }
815 
816 /******************************************************************************
817  *           HDC_UserUnmarshal [OLE32.@]
818  *
819  * Unmarshals an HDC from a buffer.
820  *
821  * PARAMS
822  *  pFlags   [I] Flags. See notes.
823  *  pBuffer  [I] Buffer to marshal the clip format from.
824  *  phdc     [O] Address that receive the unmarshaled HDC.
825  *
826  * RETURNS
827  *  The end of the marshaled data in the buffer.
828  *
829  * NOTES
830  *  Even though the function is documented to take a pointer to an ULONG in
831  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
832  *  the first parameter is an ULONG.
833  *  This function is only intended to be called by the RPC runtime.
834  */
835 unsigned char * __RPC_USER HDC_UserUnmarshal(ULONG *pFlags, unsigned char *pBuffer, HDC *phdc)
836 {
837     FIXME(":stub\n");
838     return pBuffer;
839 }
840 
841 /******************************************************************************
842  *           HDC_UserFree [OLE32.@]
843  *
844  * Frees an unmarshaled HDC.
845  *
846  * PARAMS
847  *  pFlags   [I] Flags. See notes.
848  *  phdc     [I] HDC to free.
849  *
850  * RETURNS
851  *  The end of the marshaled data in the buffer.
852  *
853  * NOTES
854  *  Even though the function is documented to take a pointer to a ULONG in
855  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of
856  *  which the first parameter is a ULONG.
857  *  This function is only intended to be called by the RPC runtime.
858  */
859 void __RPC_USER HDC_UserFree(ULONG *pFlags, HDC *phdc)
860 {
861     FIXME(":stub\n");
862 }
863 
864 /******************************************************************************
865  *           HPALETTE_UserSize [OLE32.@]
866  *
867  * Calculates the buffer size required to marshal a palette.
868  *
869  * PARAMS
870  *  pFlags       [I] Flags. See notes.
871  *  StartingSize [I] Starting size of the buffer. This value is added on to
872  *                   the buffer size required for the clip format.
873  *  phPal        [I] Palette to size.
874  *
875  * RETURNS
876  *  The buffer size required to marshal a palette plus the starting size.
877  *
878  * NOTES
879  *  Even though the function is documented to take a pointer to a ULONG in
880  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
881  *  the first parameter is a ULONG.
882  *  This function is only intended to be called by the RPC runtime.
883  */
884 ULONG __RPC_USER HPALETTE_UserSize(ULONG *pFlags, ULONG StartingSize, HPALETTE *phPal)
885 {
886     FIXME(":stub\n");
887     return StartingSize;
888 }
889 
890 /******************************************************************************
891  *           HPALETTE_UserMarshal [OLE32.@]
892  *
893  * Marshals a palette into a buffer.
894  *
895  * PARAMS
896  *  pFlags  [I] Flags. See notes.
897  *  pBuffer [I] Buffer to marshal the clip format into.
898  *  phPal   [I] Palette to marshal.
899  *
900  * RETURNS
901  *  The end of the marshaled data in the buffer.
902  *
903  * NOTES
904  *  Even though the function is documented to take a pointer to a ULONG in
905  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
906  *  the first parameter is a ULONG.
907  *  This function is only intended to be called by the RPC runtime.
908  */
909 unsigned char * __RPC_USER HPALETTE_UserMarshal(ULONG *pFlags, unsigned char *pBuffer, HPALETTE *phPal)
910 {
911     FIXME(":stub\n");
912     return pBuffer;
913 }
914 
915 /******************************************************************************
916  *           HPALETTE_UserUnmarshal [OLE32.@]
917  *
918  * Unmarshals a palette from a buffer.
919  *
920  * PARAMS
921  *  pFlags   [I] Flags. See notes.
922  *  pBuffer  [I] Buffer to marshal the clip format from.
923  *  phPal    [O] Address that receive the unmarshaled palette.
924  *
925  * RETURNS
926  *  The end of the marshaled data in the buffer.
927  *
928  * NOTES
929  *  Even though the function is documented to take a pointer to an ULONG in
930  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
931  *  the first parameter is an ULONG.
932  *  This function is only intended to be called by the RPC runtime.
933  */
934 unsigned char * __RPC_USER HPALETTE_UserUnmarshal(ULONG *pFlags, unsigned char *pBuffer, HPALETTE *phPal)
935 {
936     FIXME(":stub\n");
937     return pBuffer;
938 }
939 
940 /******************************************************************************
941  *           HPALETTE_UserFree [OLE32.@]
942  *
943  * Frees an unmarshaled palette.
944  *
945  * PARAMS
946  *  pFlags   [I] Flags. See notes.
947  *  phPal    [I] Palette to free.
948  *
949  * RETURNS
950  *  The end of the marshaled data in the buffer.
951  *
952  * NOTES
953  *  Even though the function is documented to take a pointer to a ULONG in
954  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of
955  *  which the first parameter is a ULONG.
956  *  This function is only intended to be called by the RPC runtime.
957  */
958 void __RPC_USER HPALETTE_UserFree(ULONG *pFlags, HPALETTE *phPal)
959 {
960     FIXME(":stub\n");
961 }
962 
963 
964 /******************************************************************************
965  *           HMETAFILE_UserSize [OLE32.@]
966  *
967  * Calculates the buffer size required to marshal a metafile.
968  *
969  * PARAMS
970  *  pFlags       [I] Flags. See notes.
971  *  StartingSize [I] Starting size of the buffer. This value is added on to
972  *                   the buffer size required for the clip format.
973  *  phmf         [I] Metafile to size.
974  *
975  * RETURNS
976  *  The buffer size required to marshal a metafile plus the starting size.
977  *
978  * NOTES
979  *  Even though the function is documented to take a pointer to a ULONG in
980  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
981  *  the first parameter is a ULONG.
982  *  This function is only intended to be called by the RPC runtime.
983  */
984 ULONG __RPC_USER HMETAFILE_UserSize(ULONG *pFlags, ULONG StartingSize, HMETAFILE *phmf)
985 {
986     ULONG size = StartingSize;
987 
988     TRACE("(%s, %d, &%p\n", debugstr_user_flags(pFlags), StartingSize, *phmf);
989 
990     ALIGN_LENGTH(size, 3);
991 
992     size += sizeof(ULONG);
993     if (LOWORD(*pFlags) == MSHCTX_INPROC)
994         size += sizeof(ULONG_PTR);
995     else
996     {
997         size += sizeof(ULONG);
998 
999         if (*phmf)
1000         {
1001             UINT mfsize;
1002 
1003             size += 2 * sizeof(ULONG);
1004             mfsize = GetMetaFileBitsEx(*phmf, 0, NULL);
1005             size += mfsize;
1006         }
1007     }
1008 
1009     return size;
1010 }
1011 
1012 /******************************************************************************
1013  *           HMETAFILE_UserMarshal [OLE32.@]
1014  *
1015  * Marshals a metafile into a buffer.
1016  *
1017  * PARAMS
1018  *  pFlags  [I] Flags. See notes.
1019  *  pBuffer [I] Buffer to marshal the clip format into.
1020  *  phEmf   [I] Metafile to marshal.
1021  *
1022  * RETURNS
1023  *  The end of the marshaled data in the buffer.
1024  *
1025  * NOTES
1026  *  Even though the function is documented to take a pointer to a ULONG in
1027  *  pFlags, it actually takes a pointer to a USER_MARSHAL_CB structure, of which
1028  *  the first parameter is a ULONG.
1029  *  This function is only intended to be called by the RPC runtime.
1030  */
1031 unsigned char * __RPC_USER HMETAFILE_UserMarshal(ULONG *pFlags, unsigned char *pBuffer, HMETAFILE *phmf)
1032 {
1033     TRACE("(%s, %p, &%p\n", debugstr_user_flags(pFlags), pBuffer, *phmf);
1034 
1035     ALIGN_POINTER(pBuffer, 3);
1036 
1037     if (LOWORD(*pFlags) == MSHCTX_INPROC)
1038     {
1039         if (sizeof(*phmf) == 8)
1040             *(ULONG *)pBuffer = WDT_INPROC64_CALL;
1041         else
1042             *(ULONG *)pBuffer = WDT_INPROC_CALL;
1043         pBuffer += sizeof(ULONG);
1044         *(HMETAFILE *)pBuffer = *phmf;
1045         pBuffer += sizeof(HMETAFILE);
1046     }
1047     else
1048     {
1049         *(ULONG *)pBuffer = WDT_REMOTE_CALL;
1050         pBuffer += sizeof(ULONG);
1051         *(ULONG *)pBuffer = (ULONG)(ULONG_PTR)*phmf;
1052         pBuffer += sizeof(ULONG);
1053 
1054         if (*phmf)
1055         {
1056             UINT mfsize = GetMetaFileBitsEx(*phmf, 0, NULL);
1057 
1058             *(ULONG *)pBuffer = mfsize;
1059             pBuffer += sizeof(ULONG);
1060             *(ULONG *)pBuffer = mfsize;
1061             pBuffer += sizeof(ULONG);
1062             GetMetaFileBitsEx(*phmf, mfsize, pBuffe