xref: /reactos/dll/win32/rpcrt4/ndr_es.c (revision b6fdb56b)
1 /*
2  * NDR Serialization Services
3  *
4  * Copyright (c) 2007 Robert Shearman for CodeWeavers
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 <stdarg.h>
22 #include <stdio.h>
23 
24 #include "windef.h"
25 #include "winbase.h"
26 #include "winerror.h"
27 #include "rpc.h"
28 #include "midles.h"
29 #include "ndrtypes.h"
30 
31 #include "ndr_misc.h"
32 #include "ndr_stubless.h"
33 
34 #include "wine/debug.h"
35 
36 WINE_DEFAULT_DEBUG_CHANNEL(ole);
37 
init_MIDL_ES_MESSAGE(MIDL_ES_MESSAGE * pEsMsg)38 static inline void init_MIDL_ES_MESSAGE(MIDL_ES_MESSAGE *pEsMsg)
39 {
40     memset(pEsMsg, 0, sizeof(*pEsMsg));
41     /* even if we are unmarshalling, as we don't want pointers to be pointed
42      * to buffer memory */
43     pEsMsg->StubMsg.IsClient = TRUE;
44     pEsMsg->MesVersion = 1;
45 }
46 
47 /***********************************************************************
48  *            MesEncodeIncrementalHandleCreate [RPCRT4.@]
49  */
MesEncodeIncrementalHandleCreate(void * UserState,MIDL_ES_ALLOC AllocFn,MIDL_ES_WRITE WriteFn,handle_t * pHandle)50 RPC_STATUS WINAPI MesEncodeIncrementalHandleCreate(
51     void *UserState, MIDL_ES_ALLOC AllocFn, MIDL_ES_WRITE WriteFn,
52     handle_t *pHandle)
53 {
54     MIDL_ES_MESSAGE *pEsMsg;
55 
56     TRACE("(%p, %p, %p, %p)\n", UserState, AllocFn, WriteFn, pHandle);
57 
58     pEsMsg = HeapAlloc(GetProcessHeap(), 0, sizeof(*pEsMsg));
59     if (!pEsMsg)
60         return RPC_S_OUT_OF_MEMORY;
61 
62     init_MIDL_ES_MESSAGE(pEsMsg);
63 
64     pEsMsg->Operation = MES_ENCODE;
65     pEsMsg->UserState = UserState;
66     pEsMsg->HandleStyle = MES_INCREMENTAL_HANDLE;
67     pEsMsg->Alloc = AllocFn;
68     pEsMsg->Write = WriteFn;
69 
70     *pHandle = (handle_t)pEsMsg;
71 
72     return RPC_S_OK;
73 }
74 
75 /***********************************************************************
76  *            MesDecodeIncrementalHandleCreate [RPCRT4.@]
77  */
MesDecodeIncrementalHandleCreate(void * UserState,MIDL_ES_READ ReadFn,handle_t * pHandle)78 RPC_STATUS WINAPI MesDecodeIncrementalHandleCreate(
79     void *UserState, MIDL_ES_READ ReadFn, handle_t *pHandle)
80 {
81     MIDL_ES_MESSAGE *pEsMsg;
82 
83     TRACE("(%p, %p, %p)\n", UserState, ReadFn, pHandle);
84 
85     pEsMsg = HeapAlloc(GetProcessHeap(), 0, sizeof(*pEsMsg));
86     if (!pEsMsg)
87         return RPC_S_OUT_OF_MEMORY;
88 
89     init_MIDL_ES_MESSAGE(pEsMsg);
90 
91     pEsMsg->Operation = MES_DECODE;
92     pEsMsg->UserState = UserState;
93     pEsMsg->HandleStyle = MES_INCREMENTAL_HANDLE;
94     pEsMsg->Read = ReadFn;
95 
96     *pHandle = (handle_t)pEsMsg;
97 
98     return RPC_S_OK;
99 }
100 
101 /***********************************************************************
102  *            MesIncrementalHandleReset [RPCRT4.@]
103  */
MesIncrementalHandleReset(handle_t Handle,void * UserState,MIDL_ES_ALLOC AllocFn,MIDL_ES_WRITE WriteFn,MIDL_ES_READ ReadFn,MIDL_ES_CODE Operation)104 RPC_STATUS WINAPI MesIncrementalHandleReset(
105     handle_t Handle, void *UserState, MIDL_ES_ALLOC AllocFn,
106     MIDL_ES_WRITE WriteFn, MIDL_ES_READ ReadFn, MIDL_ES_CODE Operation)
107 {
108     MIDL_ES_MESSAGE *pEsMsg = Handle;
109 
110     TRACE("(%p, %p, %p, %p, %p, %d)\n", Handle, UserState, AllocFn,
111         WriteFn, ReadFn, Operation);
112 
113     init_MIDL_ES_MESSAGE(pEsMsg);
114 
115     pEsMsg->Operation = Operation;
116     pEsMsg->UserState = UserState;
117     pEsMsg->HandleStyle = MES_INCREMENTAL_HANDLE;
118     pEsMsg->Alloc = AllocFn;
119     pEsMsg->Write = WriteFn;
120     pEsMsg->Read = ReadFn;
121 
122     return RPC_S_OK;
123 }
124 
125 /***********************************************************************
126  *            MesBufferHandleReset [RPCRT4.@]
127  */
MesBufferHandleReset(handle_t Handle,ULONG HandleStyle,MIDL_ES_CODE Operation,char ** Buffer,ULONG BufferSize,ULONG * EncodedSize)128 RPC_STATUS WINAPI MesBufferHandleReset(handle_t Handle, ULONG HandleStyle,
129     MIDL_ES_CODE Operation, char **Buffer, ULONG BufferSize, ULONG *EncodedSize)
130 {
131     MIDL_ES_MESSAGE *pEsMsg = (MIDL_ES_MESSAGE *)Handle;
132 
133     TRACE("(%p, %u, %d, %p, %u, %p)\n", Handle, HandleStyle, Operation, Buffer,
134         BufferSize, EncodedSize);
135 
136     if (!Handle || !Buffer || !EncodedSize)
137         return RPC_S_INVALID_ARG;
138 
139     if (Operation != MES_ENCODE && Operation != MES_DECODE && Operation != MES_ENCODE_NDR64)
140         return RPC_S_INVALID_ARG;
141 
142     if (HandleStyle != MES_FIXED_BUFFER_HANDLE && HandleStyle != MES_DYNAMIC_BUFFER_HANDLE)
143         return RPC_S_INVALID_ARG;
144 
145     init_MIDL_ES_MESSAGE(pEsMsg);
146 
147     pEsMsg->Operation = Operation;
148     pEsMsg->HandleStyle = HandleStyle;
149     if (HandleStyle == MES_FIXED_BUFFER_HANDLE)
150         pEsMsg->Buffer = (unsigned char*)*Buffer;
151     else
152         pEsMsg->pDynBuffer = (unsigned char**)Buffer;
153     pEsMsg->BufferSize = BufferSize;
154     pEsMsg->pEncodedSize = EncodedSize;
155 
156     return RPC_S_OK;
157 }
158 
159 /***********************************************************************
160  *            MesHandleFree [RPCRT4.@]
161  */
MesHandleFree(handle_t Handle)162 RPC_STATUS WINAPI MesHandleFree(handle_t Handle)
163 {
164     TRACE("(%p)\n", Handle);
165     HeapFree(GetProcessHeap(), 0, Handle);
166     return RPC_S_OK;
167 }
168 
validate_mes_buffer_pointer(const char * Buffer)169 static RPC_STATUS validate_mes_buffer_pointer(const char *Buffer)
170 {
171     if (!Buffer)
172         return RPC_S_INVALID_ARG;
173 
174     if (((ULONG_PTR)Buffer & 7) != 0)
175         return RPC_X_INVALID_BUFFER;
176 
177     return RPC_S_OK;
178 }
179 
180 /***********************************************************************
181  *            MesEncodeFixedBufferHandleCreate [RPCRT4.@]
182  */
MesEncodeFixedBufferHandleCreate(char * Buffer,ULONG BufferSize,ULONG * pEncodedSize,handle_t * pHandle)183 RPC_STATUS RPC_ENTRY MesEncodeFixedBufferHandleCreate(
184     char *Buffer, ULONG BufferSize, ULONG *pEncodedSize, handle_t *pHandle)
185 {
186     MIDL_ES_MESSAGE *pEsMsg;
187     RPC_STATUS status;
188 
189     TRACE("(%p, %d, %p, %p)\n", Buffer, BufferSize, pEncodedSize, pHandle);
190 
191     if ((status = validate_mes_buffer_pointer(Buffer)))
192         return status;
193 
194     if (!pEncodedSize)
195         return RPC_S_INVALID_ARG;
196 
197     /* FIXME: check BufferSize too */
198 
199     pEsMsg = HeapAlloc(GetProcessHeap(), 0, sizeof(*pEsMsg));
200     if (!pEsMsg)
201         return RPC_S_OUT_OF_MEMORY;
202 
203     init_MIDL_ES_MESSAGE(pEsMsg);
204 
205     pEsMsg->Operation = MES_ENCODE;
206     pEsMsg->HandleStyle = MES_FIXED_BUFFER_HANDLE;
207     pEsMsg->Buffer = (unsigned char *)Buffer;
208     pEsMsg->BufferSize = BufferSize;
209     pEsMsg->pEncodedSize = pEncodedSize;
210 
211     *pHandle = (handle_t)pEsMsg;
212 
213     return RPC_S_OK;
214 }
215 
216 /***********************************************************************
217  *            MesEncodeDynBufferHandleCreate [RPCRT4.@]
218  */
MesEncodeDynBufferHandleCreate(char ** Buffer,ULONG * pEncodedSize,handle_t * pHandle)219 RPC_STATUS RPC_ENTRY MesEncodeDynBufferHandleCreate(char **Buffer,
220         ULONG *pEncodedSize, handle_t *pHandle)
221 {
222     MIDL_ES_MESSAGE *pEsMsg;
223 
224     TRACE("(%p, %p, %p)\n", Buffer, pEncodedSize, pHandle);
225 
226     if (!pEncodedSize)
227         return RPC_S_INVALID_ARG;
228 
229     pEsMsg = HeapAlloc(GetProcessHeap(), 0, sizeof(*pEsMsg));
230     if (!pEsMsg)
231         return RPC_S_OUT_OF_MEMORY;
232 
233     init_MIDL_ES_MESSAGE(pEsMsg);
234 
235     pEsMsg->Operation = MES_ENCODE;
236     pEsMsg->HandleStyle = MES_DYNAMIC_BUFFER_HANDLE;
237     pEsMsg->pDynBuffer = (unsigned char **)Buffer;
238     pEsMsg->pEncodedSize = pEncodedSize;
239 
240     *pHandle = (handle_t)pEsMsg;
241 
242     return RPC_S_OK;
243 }
244 
245 /***********************************************************************
246  *            MesDecodeBufferHandleCreate [RPCRT4.@]
247  */
MesDecodeBufferHandleCreate(char * Buffer,ULONG BufferSize,handle_t * pHandle)248 RPC_STATUS RPC_ENTRY MesDecodeBufferHandleCreate(
249     char *Buffer, ULONG BufferSize, handle_t *pHandle)
250 {
251     MIDL_ES_MESSAGE *pEsMsg;
252     RPC_STATUS status;
253 
254     TRACE("(%p, %d, %p)\n", Buffer, BufferSize, pHandle);
255 
256     if ((status = validate_mes_buffer_pointer(Buffer)))
257         return status;
258 
259     pEsMsg = HeapAlloc(GetProcessHeap(), 0, sizeof(*pEsMsg));
260     if (!pEsMsg)
261         return RPC_S_OUT_OF_MEMORY;
262 
263     init_MIDL_ES_MESSAGE(pEsMsg);
264 
265     pEsMsg->Operation = MES_DECODE;
266     pEsMsg->HandleStyle = MES_FIXED_BUFFER_HANDLE;
267     pEsMsg->Buffer = (unsigned char *)Buffer;
268     pEsMsg->BufferSize = BufferSize;
269 
270     *pHandle = (handle_t)pEsMsg;
271 
272     return RPC_S_OK;
273 }
274 
es_data_alloc(MIDL_ES_MESSAGE * pEsMsg,ULONG size)275 static void es_data_alloc(MIDL_ES_MESSAGE *pEsMsg, ULONG size)
276 {
277     if (pEsMsg->HandleStyle == MES_INCREMENTAL_HANDLE)
278     {
279         unsigned int tmpsize = size;
280         TRACE("%d with incremental handle\n", size);
281         pEsMsg->Alloc(pEsMsg->UserState, (char **)&pEsMsg->StubMsg.Buffer, &tmpsize);
282         if (tmpsize < size)
283         {
284             ERR("not enough bytes allocated - requested %d, got %d\n", size, tmpsize);
285             RpcRaiseException(RPC_S_OUT_OF_MEMORY);
286         }
287     }
288     else if (pEsMsg->HandleStyle == MES_FIXED_BUFFER_HANDLE)
289     {
290         TRACE("%d with fixed buffer handle\n", size);
291         pEsMsg->StubMsg.Buffer = pEsMsg->Buffer;
292     }
293     pEsMsg->StubMsg.RpcMsg->Buffer = pEsMsg->StubMsg.BufferStart = pEsMsg->StubMsg.Buffer;
294 }
295 
es_data_read(MIDL_ES_MESSAGE * pEsMsg,ULONG size)296 static void es_data_read(MIDL_ES_MESSAGE *pEsMsg, ULONG size)
297 {
298     if (pEsMsg->HandleStyle == MES_INCREMENTAL_HANDLE)
299     {
300         unsigned int tmpsize = size;
301         TRACE("%d from incremental handle\n", size);
302         pEsMsg->Read(pEsMsg->UserState, (char **)&pEsMsg->StubMsg.Buffer, &tmpsize);
303         if (tmpsize < size)
304         {
305             ERR("not enough bytes read - requested %d, got %d\n", size, tmpsize);
306             RpcRaiseException(RPC_S_OUT_OF_MEMORY);
307         }
308     }
309     else
310     {
311         TRACE("%d from fixed or dynamic buffer handle\n", size);
312         /* FIXME: validate BufferSize? */
313         pEsMsg->StubMsg.Buffer = pEsMsg->Buffer;
314         pEsMsg->Buffer += size;
315         pEsMsg->BufferSize -= size;
316     }
317     pEsMsg->StubMsg.BufferLength = size;
318     pEsMsg->StubMsg.RpcMsg->Buffer = pEsMsg->StubMsg.BufferStart = pEsMsg->StubMsg.Buffer;
319     pEsMsg->StubMsg.BufferEnd = pEsMsg->StubMsg.Buffer + size;
320 }
321 
es_data_write(MIDL_ES_MESSAGE * pEsMsg,ULONG size)322 static void es_data_write(MIDL_ES_MESSAGE *pEsMsg, ULONG size)
323 {
324     if (pEsMsg->HandleStyle == MES_INCREMENTAL_HANDLE)
325     {
326         TRACE("%d to incremental handle\n", size);
327         pEsMsg->Write(pEsMsg->UserState, (char *)pEsMsg->StubMsg.BufferStart, size);
328     }
329     else
330     {
331         TRACE("%d to dynamic or fixed buffer handle\n", size);
332         *pEsMsg->pEncodedSize += size;
333     }
334 }
335 
mes_proc_header_buffer_size(void)336 static inline ULONG mes_proc_header_buffer_size(void)
337 {
338     return 4 + 2*sizeof(RPC_SYNTAX_IDENTIFIER) + 12;
339 }
340 
mes_proc_header_marshal(MIDL_ES_MESSAGE * pEsMsg)341 static void mes_proc_header_marshal(MIDL_ES_MESSAGE *pEsMsg)
342 {
343     const RPC_CLIENT_INTERFACE *client_interface = pEsMsg->StubMsg.StubDesc->RpcInterfaceInformation;
344     *(WORD *)pEsMsg->StubMsg.Buffer = 0x0101;
345     pEsMsg->StubMsg.Buffer += 2;
346     *(WORD *)pEsMsg->StubMsg.Buffer = 0xcccc;
347     pEsMsg->StubMsg.Buffer += 2;
348     memcpy(pEsMsg->StubMsg.Buffer, &client_interface->TransferSyntax, sizeof(RPC_SYNTAX_IDENTIFIER));
349     pEsMsg->StubMsg.Buffer += sizeof(RPC_SYNTAX_IDENTIFIER);
350     memcpy(pEsMsg->StubMsg.Buffer, &pEsMsg->InterfaceId, sizeof(RPC_SYNTAX_IDENTIFIER));
351     pEsMsg->StubMsg.Buffer += sizeof(RPC_SYNTAX_IDENTIFIER);
352     *(DWORD *)pEsMsg->StubMsg.Buffer = pEsMsg->ProcNumber;
353     pEsMsg->StubMsg.Buffer += 4;
354     *(DWORD *)pEsMsg->StubMsg.Buffer = 0x00000001;
355     pEsMsg->StubMsg.Buffer += 4;
356     *(DWORD *)pEsMsg->StubMsg.Buffer = pEsMsg->ByteCount;
357     pEsMsg->StubMsg.Buffer += 4;
358 }
359 
mes_proc_header_unmarshal(MIDL_ES_MESSAGE * pEsMsg)360 static void mes_proc_header_unmarshal(MIDL_ES_MESSAGE *pEsMsg)
361 {
362     const RPC_CLIENT_INTERFACE *client_interface = pEsMsg->StubMsg.StubDesc->RpcInterfaceInformation;
363 
364     es_data_read(pEsMsg, mes_proc_header_buffer_size());
365 
366     if (*(WORD *)pEsMsg->StubMsg.Buffer != 0x0101)
367     {
368         FIXME("unknown value at Buffer[0] 0x%04x\n", *(WORD *)pEsMsg->StubMsg.Buffer);
369         RpcRaiseException(RPC_X_WRONG_ES_VERSION);
370     }
371     pEsMsg->StubMsg.Buffer += 2;
372     if (*(WORD *)pEsMsg->StubMsg.Buffer != 0xcccc)
373         FIXME("unknown value at Buffer[2] 0x%04x\n", *(WORD *)pEsMsg->StubMsg.Buffer);
374     pEsMsg->StubMsg.Buffer += 2;
375     if (memcmp(pEsMsg->StubMsg.Buffer, &client_interface->TransferSyntax, sizeof(RPC_SYNTAX_IDENTIFIER)))
376     {
377         const RPC_SYNTAX_IDENTIFIER *AlienTransferSyntax = (const RPC_SYNTAX_IDENTIFIER *)pEsMsg->StubMsg.Buffer;
378         ERR("bad transfer syntax %s {%d.%d}\n", debugstr_guid(&AlienTransferSyntax->SyntaxGUID),
379             AlienTransferSyntax->SyntaxVersion.MajorVersion,
380             AlienTransferSyntax->SyntaxVersion.MinorVersion);
381         RpcRaiseException(RPC_S_UNSUPPORTED_TRANS_SYN);
382     }
383     pEsMsg->StubMsg.Buffer += sizeof(RPC_SYNTAX_IDENTIFIER);
384     memcpy(&pEsMsg->InterfaceId, pEsMsg->StubMsg.Buffer, sizeof(RPC_SYNTAX_IDENTIFIER));
385     pEsMsg->StubMsg.Buffer += sizeof(RPC_SYNTAX_IDENTIFIER);
386     pEsMsg->ProcNumber = *(DWORD *)pEsMsg->StubMsg.Buffer;
387     pEsMsg->StubMsg.Buffer += 4;
388     if (*(DWORD *)pEsMsg->StubMsg.Buffer != 0x00000001)
389         FIXME("unknown value 0x%08x, expected 0x00000001\n", *(DWORD *)pEsMsg->StubMsg.Buffer);
390     pEsMsg->StubMsg.Buffer += 4;
391     pEsMsg->ByteCount = *(DWORD *)pEsMsg->StubMsg.Buffer;
392     pEsMsg->StubMsg.Buffer += 4;
393     if (pEsMsg->ByteCount + mes_proc_header_buffer_size() < pEsMsg->ByteCount)
394         RpcRaiseException(RPC_S_INVALID_BOUND);
395 }
396 
397 /***********************************************************************
398  *            NdrMesProcEncodeDecode [RPCRT4.@]
399  */
NdrMesProcEncodeDecode(handle_t Handle,const MIDL_STUB_DESC * pStubDesc,PFORMAT_STRING pFormat,...)400 void WINAPIV NdrMesProcEncodeDecode(handle_t Handle, const MIDL_STUB_DESC * pStubDesc, PFORMAT_STRING pFormat, ...)
401 {
402     /* pointer to start of stack where arguments start */
403     RPC_MESSAGE rpcMsg;
404     MIDL_ES_MESSAGE *pEsMsg = Handle;
405     /* size of stack */
406     unsigned short stack_size;
407     /* header for procedure string */
408     const NDR_PROC_HEADER *pProcHeader = (const NDR_PROC_HEADER *)&pFormat[0];
409     const RPC_CLIENT_INTERFACE *client_interface;
410     __ms_va_list args;
411     unsigned int number_of_params;
412     ULONG_PTR arg_buffer[256];
413 
414     TRACE("Handle %p, pStubDesc %p, pFormat %p, ...\n", Handle, pStubDesc, pFormat);
415 
416     /* Later NDR language versions probably won't be backwards compatible */
417     if (pStubDesc->Version > 0x50002)
418     {
419         FIXME("Incompatible stub description version: 0x%x\n", pStubDesc->Version);
420         RpcRaiseException(RPC_X_WRONG_STUB_VERSION);
421     }
422 
423     client_interface = pStubDesc->RpcInterfaceInformation;
424     pEsMsg->InterfaceId = client_interface->InterfaceId;
425 
426     if (pProcHeader->Oi_flags & Oi_HAS_RPCFLAGS)
427     {
428         const NDR_PROC_HEADER_RPC *header_rpc = (const NDR_PROC_HEADER_RPC *)&pFormat[0];
429         stack_size = header_rpc->stack_size;
430         pEsMsg->ProcNumber = header_rpc->proc_num;
431         pFormat += sizeof(NDR_PROC_HEADER_RPC);
432     }
433     else
434     {
435         stack_size = pProcHeader->stack_size;
436         pEsMsg->ProcNumber = pProcHeader->proc_num;
437         pFormat += sizeof(NDR_PROC_HEADER);
438     }
439 
440     if (pProcHeader->handle_type == 0)
441     {
442         switch (*pFormat) /* handle_type */
443         {
444         case FC_BIND_PRIMITIVE: /* explicit primitive */
445             pFormat += sizeof(NDR_EHD_PRIMITIVE);
446             break;
447         case FC_BIND_GENERIC: /* explicit generic */
448             pFormat += sizeof(NDR_EHD_GENERIC);
449             break;
450         case FC_BIND_CONTEXT: /* explicit context */
451             pFormat += sizeof(NDR_EHD_CONTEXT);
452             break;
453         default:
454             ERR("bad explicit binding handle type (0x%02x)\n", pProcHeader->handle_type);
455             RpcRaiseException(RPC_X_BAD_STUB_DATA);
456         }
457     }
458 
459     TRACE("stack size: 0x%x\n", stack_size);
460     TRACE("proc num: %d\n", pEsMsg->ProcNumber);
461 
462     memset(&rpcMsg, 0, sizeof(rpcMsg));
463     pEsMsg->StubMsg.RpcMsg = &rpcMsg;
464     pEsMsg->StubMsg.StubDesc = pStubDesc;
465     pEsMsg->StubMsg.pfnAllocate = pStubDesc->pfnAllocate;
466     pEsMsg->StubMsg.pfnFree = pStubDesc->pfnFree;
467 
468     /* create the full pointer translation tables, if requested */
469     if (pProcHeader->Oi_flags & Oi_FULL_PTR_USED)
470         pEsMsg->StubMsg.FullPtrXlatTables = NdrFullPointerXlatInit(0,XLAT_CLIENT);
471 
472     TRACE("Oi_flags = 0x%02x\n", pProcHeader->Oi_flags);
473     TRACE("stubdesc version = 0x%x\n", pStubDesc->Version);
474     TRACE("MIDL stub version = 0x%x\n", pStubDesc->MIDLVersion);
475 
476     /* needed for conformance of top-level objects */
477     __ms_va_start( args, pFormat );
478     pEsMsg->StubMsg.StackTop = va_arg( args, unsigned char * );
479     __ms_va_end( args );
480 
481     pFormat = convert_old_args( &pEsMsg->StubMsg, pFormat, stack_size, FALSE,
482                                 arg_buffer, sizeof(arg_buffer), &number_of_params );
483 
484     switch (pEsMsg->Operation)
485     {
486     case MES_ENCODE:
487         pEsMsg->StubMsg.BufferLength = mes_proc_header_buffer_size();
488 
489         client_do_args( &pEsMsg->StubMsg, pFormat, STUBLESS_CALCSIZE, NULL, number_of_params, NULL );
490 
491         pEsMsg->ByteCount = pEsMsg->StubMsg.BufferLength - mes_proc_header_buffer_size();
492         es_data_alloc(pEsMsg, pEsMsg->StubMsg.BufferLength);
493 
494         mes_proc_header_marshal(pEsMsg);
495 
496         client_do_args( &pEsMsg->StubMsg, pFormat, STUBLESS_MARSHAL, NULL, number_of_params, NULL );
497 
498         es_data_write(pEsMsg, pEsMsg->ByteCount);
499         break;
500     case MES_DECODE:
501         mes_proc_header_unmarshal(pEsMsg);
502 
503         es_data_read(pEsMsg, pEsMsg->ByteCount);
504 
505         client_do_args( &pEsMsg->StubMsg, pFormat, STUBLESS_UNMARSHAL, NULL, number_of_params, NULL );
506         break;
507     default:
508         RpcRaiseException(RPC_S_INTERNAL_ERROR);
509         return;
510     }
511     /* free the full pointer translation tables */
512     if (pProcHeader->Oi_flags & Oi_FULL_PTR_USED)
513         NdrFullPointerXlatFree(pEsMsg->StubMsg.FullPtrXlatTables);
514 }
515 
NdrMesTypeDecode2(handle_t Handle,const MIDL_TYPE_PICKLING_INFO * pPicklingInfo,const MIDL_STUB_DESC * pStubDesc,PFORMAT_STRING pFormatString,void * pObject)516 void RPC_ENTRY NdrMesTypeDecode2(handle_t Handle, const MIDL_TYPE_PICKLING_INFO *pPicklingInfo,
517     const MIDL_STUB_DESC *pStubDesc, PFORMAT_STRING pFormatString, void *pObject)
518 {
519     FIXME("(%p, %p, %p, %p, %p)\n", Handle, pPicklingInfo, pStubDesc, pFormatString, pObject);
520 }
521 
NdrMesTypeEncode2(handle_t Handle,const MIDL_TYPE_PICKLING_INFO * pPicklingInfo,const MIDL_STUB_DESC * pStubDesc,PFORMAT_STRING pFormatString,const void * pObject)522 void RPC_ENTRY NdrMesTypeEncode2(handle_t Handle, const MIDL_TYPE_PICKLING_INFO *pPicklingInfo,
523     const MIDL_STUB_DESC *pStubDesc, PFORMAT_STRING pFormatString, const void *pObject)
524 {
525     FIXME("(%p, %p, %p, %p, %p)\n", Handle, pPicklingInfo, pStubDesc, pFormatString, pObject);
526 }
527 
NdrMesTypeFree2(handle_t Handle,const MIDL_TYPE_PICKLING_INFO * pPicklingInfo,const MIDL_STUB_DESC * pStubDesc,PFORMAT_STRING pFormatString,void * pObject)528 void RPC_ENTRY NdrMesTypeFree2(handle_t Handle, const MIDL_TYPE_PICKLING_INFO *pPicklingInfo,
529     const MIDL_STUB_DESC *pStubDesc, PFORMAT_STRING pFormatString, void *pObject)
530 {
531     FIXME("(%p, %p, %p, %p, %p)\n", Handle, pPicklingInfo, pStubDesc, pFormatString, pObject);
532 }
533