sync most of rpcrt4 to wine 1.1.4

svn path=/trunk/; revision=36188
This commit is contained in:
Christoph von Wittich 2008-09-13 15:52:50 +00:00
parent b34d6d8879
commit f1661e061c
24 changed files with 2615 additions and 1266 deletions

View file

@ -18,6 +18,9 @@
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/ */
#include "config.h"
#include "wine/port.h"
#include <stdarg.h> #include <stdarg.h>
#include <stdio.h> #include <stdio.h>
#include <string.h> #include <string.h>
@ -62,7 +65,7 @@ static HRESULT WINAPI CStdPSFactory_QueryInterface(LPPSFACTORYBUFFER iface,
if (IsEqualGUID(&IID_IUnknown,riid) || if (IsEqualGUID(&IID_IUnknown,riid) ||
IsEqualGUID(&IID_IPSFactoryBuffer,riid)) { IsEqualGUID(&IID_IPSFactoryBuffer,riid)) {
*obj = This; *obj = This;
This->RefCount++; InterlockedIncrement( &This->RefCount );
return S_OK; return S_OK;
} }
return E_NOINTERFACE; return E_NOINTERFACE;
@ -72,14 +75,14 @@ static ULONG WINAPI CStdPSFactory_AddRef(LPPSFACTORYBUFFER iface)
{ {
CStdPSFactoryBuffer *This = (CStdPSFactoryBuffer *)iface; CStdPSFactoryBuffer *This = (CStdPSFactoryBuffer *)iface;
TRACE("(%p)->AddRef()\n",iface); TRACE("(%p)->AddRef()\n",iface);
return ++(This->RefCount); return InterlockedIncrement( &This->RefCount );
} }
static ULONG WINAPI CStdPSFactory_Release(LPPSFACTORYBUFFER iface) static ULONG WINAPI CStdPSFactory_Release(LPPSFACTORYBUFFER iface)
{ {
CStdPSFactoryBuffer *This = (CStdPSFactoryBuffer *)iface; CStdPSFactoryBuffer *This = (CStdPSFactoryBuffer *)iface;
TRACE("(%p)->Release()\n",iface); TRACE("(%p)->Release()\n",iface);
return --(This->RefCount); return InterlockedDecrement( &This->RefCount );
} }
static HRESULT WINAPI CStdPSFactory_CreateProxy(LPPSFACTORYBUFFER iface, static HRESULT WINAPI CStdPSFactory_CreateProxy(LPPSFACTORYBUFFER iface,

View file

@ -67,8 +67,9 @@ void WINAPI NdrClientInitializeNew( PRPC_MESSAGE pRpcMessage, PMIDL_STUB_MESSAGE
pStubMsg->pPointerQueueState = NULL; pStubMsg->pPointerQueueState = NULL;
pStubMsg->IgnoreEmbeddedPointers = 0; pStubMsg->IgnoreEmbeddedPointers = 0;
pStubMsg->PointerBufferMark = NULL; pStubMsg->PointerBufferMark = NULL;
pStubMsg->fBufferValid = 0; pStubMsg->CorrDespIncrement = 0;
pStubMsg->uFlags = 0; pStubMsg->uFlags = 0;
pStubMsg->UniquePtrCount = 0;
pStubMsg->pfnAllocate = pStubDesc->pfnAllocate; pStubMsg->pfnAllocate = pStubDesc->pfnAllocate;
pStubMsg->pfnFree = pStubDesc->pfnFree; pStubMsg->pfnFree = pStubDesc->pfnFree;
pStubMsg->StackTop = NULL; pStubMsg->StackTop = NULL;
@ -81,6 +82,13 @@ void WINAPI NdrClientInitializeNew( PRPC_MESSAGE pRpcMessage, PMIDL_STUB_MESSAGE
pStubMsg->fHasReturn = 0; pStubMsg->fHasReturn = 0;
pStubMsg->fHasExtensions = 0; pStubMsg->fHasExtensions = 0;
pStubMsg->fHasNewCorrDesc = 0; pStubMsg->fHasNewCorrDesc = 0;
pStubMsg->fIsIn = 0;
pStubMsg->fIsOut = 0;
pStubMsg->fIsOicf = 0;
pStubMsg->fBufferValid = 0;
pStubMsg->fHasMemoryValidateCallback = 0;
pStubMsg->fInFree = 0;
pStubMsg->fNeedMCCP = 0;
pStubMsg->fUnused = 0; pStubMsg->fUnused = 0;
pStubMsg->dwDestContext = MSHCTX_DIFFERENTMACHINE; pStubMsg->dwDestContext = MSHCTX_DIFFERENTMACHINE;
pStubMsg->pvDestContext = NULL; pStubMsg->pvDestContext = NULL;
@ -113,6 +121,7 @@ unsigned char* WINAPI NdrServerInitializeNew( PRPC_MESSAGE pRpcMsg, PMIDL_STUB_M
pStubMsg->IgnoreEmbeddedPointers = 0; pStubMsg->IgnoreEmbeddedPointers = 0;
pStubMsg->PointerBufferMark = NULL; pStubMsg->PointerBufferMark = NULL;
pStubMsg->uFlags = 0; pStubMsg->uFlags = 0;
pStubMsg->UniquePtrCount = 0;
pStubMsg->pfnAllocate = pStubDesc->pfnAllocate; pStubMsg->pfnAllocate = pStubDesc->pfnAllocate;
pStubMsg->pfnFree = pStubDesc->pfnFree; pStubMsg->pfnFree = pStubDesc->pfnFree;
pStubMsg->StackTop = NULL; pStubMsg->StackTop = NULL;
@ -126,6 +135,12 @@ unsigned char* WINAPI NdrServerInitializeNew( PRPC_MESSAGE pRpcMsg, PMIDL_STUB_M
pStubMsg->fHasReturn = 0; pStubMsg->fHasReturn = 0;
pStubMsg->fHasExtensions = 0; pStubMsg->fHasExtensions = 0;
pStubMsg->fHasNewCorrDesc = 0; pStubMsg->fHasNewCorrDesc = 0;
pStubMsg->fIsIn = 0;
pStubMsg->fIsOut = 0;
pStubMsg->fIsOicf = 0;
pStubMsg->fHasMemoryValidateCallback = 0;
pStubMsg->fInFree = 0;
pStubMsg->fNeedMCCP = 0;
pStubMsg->fUnused = 0; pStubMsg->fUnused = 0;
pStubMsg->dwDestContext = MSHCTX_DIFFERENTMACHINE; pStubMsg->dwDestContext = MSHCTX_DIFFERENTMACHINE;
pStubMsg->pvDestContext = NULL; pStubMsg->pvDestContext = NULL;
@ -194,6 +209,7 @@ unsigned char *WINAPI NdrSendReceive( PMIDL_STUB_MESSAGE stubmsg, unsigned char
return NULL; return NULL;
} }
/* avoid sending uninitialised parts of the buffer on the wire */
stubmsg->RpcMsg->BufferLength = buffer - (unsigned char *)stubmsg->RpcMsg->Buffer; stubmsg->RpcMsg->BufferLength = buffer - (unsigned char *)stubmsg->RpcMsg->Buffer;
status = I_RpcSendReceive(stubmsg->RpcMsg); status = I_RpcSendReceive(stubmsg->RpcMsg);
if (status != RPC_S_OK) if (status != RPC_S_OK)

View file

@ -89,7 +89,10 @@ RPC_BINDING_HANDLE WINAPI NDRCContextBinding(NDR_CCONTEXT CContext)
LeaveCriticalSection(&ndr_context_cs); LeaveCriticalSection(&ndr_context_cs);
if (!handle) if (!handle)
{
ERR("invalid handle %p\n", CContext);
RpcRaiseException(ERROR_INVALID_HANDLE); RpcRaiseException(ERROR_INVALID_HANDLE);
}
return handle; return handle;
} }
@ -183,7 +186,7 @@ static UINT ndr_update_context_handle(NDR_CCONTEXT *CContext,
che->magic = NDR_CONTEXT_HANDLE_MAGIC; che->magic = NDR_CONTEXT_HANDLE_MAGIC;
RpcBindingCopy(hBinding, &che->handle); RpcBindingCopy(hBinding, &che->handle);
list_add_tail(&context_handle_list, &che->entry); list_add_tail(&context_handle_list, &che->entry);
memcpy(&che->wire_data, chi, sizeof *chi); che->wire_data = *chi;
} }
*CContext = che; *CContext = che;

View file

@ -0,0 +1,430 @@
/*
* NDR Serialization Services
*
* Copyright (c) 2007 Robert Shearman for CodeWeavers
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include <stdarg.h>
#include <stdio.h>
#include "windef.h"
#include "winbase.h"
#include "winerror.h"
#include "rpc.h"
#include "midles.h"
#include "ndrtypes.h"
#include "ndr_misc.h"
#include "ndr_stubless.h"
#include "wine/debug.h"
#include "wine/rpcfc.h"
WINE_DEFAULT_DEBUG_CHANNEL(ole);
static inline void init_MIDL_ES_MESSAGE(MIDL_ES_MESSAGE *pEsMsg)
{
memset(pEsMsg, 0, sizeof(*pEsMsg));
/* even if we are unmarshalling, as we don't want pointers to be pointed
* to buffer memory */
pEsMsg->StubMsg.IsClient = TRUE;
}
/***********************************************************************
* MesEncodeIncrementalHandleCreate [RPCRT4.@]
*/
RPC_STATUS WINAPI MesEncodeIncrementalHandleCreate(
void *UserState, MIDL_ES_ALLOC AllocFn, MIDL_ES_WRITE WriteFn,
handle_t *pHandle)
{
MIDL_ES_MESSAGE *pEsMsg;
TRACE("(%p, %p, %p, %p)\n", UserState, AllocFn, WriteFn, pHandle);
pEsMsg = HeapAlloc(GetProcessHeap(), 0, sizeof(*pEsMsg));
if (!pEsMsg)
return ERROR_OUTOFMEMORY;
init_MIDL_ES_MESSAGE(pEsMsg);
pEsMsg->Operation = MES_ENCODE;
pEsMsg->UserState = UserState;
pEsMsg->HandleStyle = MES_INCREMENTAL_HANDLE;
pEsMsg->Alloc = AllocFn;
pEsMsg->Write = WriteFn;
*pHandle = (handle_t)pEsMsg;
return RPC_S_OK;
}
/***********************************************************************
* MesDecodeIncrementalHandleCreate [RPCRT4.@]
*/
RPC_STATUS WINAPI MesDecodeIncrementalHandleCreate(
void *UserState, MIDL_ES_READ ReadFn, handle_t *pHandle)
{
MIDL_ES_MESSAGE *pEsMsg;
TRACE("(%p, %p, %p)\n", UserState, ReadFn, pHandle);
pEsMsg = HeapAlloc(GetProcessHeap(), 0, sizeof(*pEsMsg));
if (!pEsMsg)
return ERROR_OUTOFMEMORY;
init_MIDL_ES_MESSAGE(pEsMsg);
pEsMsg->Operation = MES_DECODE;
pEsMsg->UserState = UserState;
pEsMsg->HandleStyle = MES_INCREMENTAL_HANDLE;
pEsMsg->Read = ReadFn;
*pHandle = (handle_t)pEsMsg;
return RPC_S_OK;
}
/***********************************************************************
* MesIncrementalHandleReset [RPCRT4.@]
*/
RPC_STATUS WINAPI MesIncrementalHandleReset(
handle_t Handle, void *UserState, MIDL_ES_ALLOC AllocFn,
MIDL_ES_WRITE WriteFn, MIDL_ES_READ ReadFn, MIDL_ES_CODE Operation)
{
MIDL_ES_MESSAGE *pEsMsg = (MIDL_ES_MESSAGE *)Handle;
TRACE("(%p, %p, %p, %p, %p, %d)\n", Handle, UserState, AllocFn,
WriteFn, ReadFn, Operation);
init_MIDL_ES_MESSAGE(pEsMsg);
pEsMsg->Operation = Operation;
pEsMsg->UserState = UserState;
pEsMsg->HandleStyle = MES_INCREMENTAL_HANDLE;
pEsMsg->Alloc = AllocFn;
pEsMsg->Write = WriteFn;
pEsMsg->Read = ReadFn;
return RPC_S_OK;
}
/***********************************************************************
* MesHandleFree [RPCRT4.@]
*/
RPC_STATUS WINAPI MesHandleFree(handle_t Handle)
{
TRACE("(%p)\n", Handle);
HeapFree(GetProcessHeap(), 0, Handle);
return RPC_S_OK;
}
/***********************************************************************
* MesEncodeFixedBufferHandleCreate [RPCRT4.@]
*/
RPC_STATUS RPC_ENTRY MesEncodeFixedBufferHandleCreate(
char *Buffer, ULONG BufferSize, ULONG *pEncodedSize, handle_t *pHandle)
{
MIDL_ES_MESSAGE *pEsMsg;
TRACE("(%p, %d, %p, %p)\n", Buffer, BufferSize, pEncodedSize, pHandle);
pEsMsg = HeapAlloc(GetProcessHeap(), 0, sizeof(*pEsMsg));
if (!pEsMsg)
return ERROR_OUTOFMEMORY;
init_MIDL_ES_MESSAGE(pEsMsg);
pEsMsg->Operation = MES_ENCODE;
pEsMsg->HandleStyle = MES_FIXED_BUFFER_HANDLE;
pEsMsg->Buffer = (unsigned char *)Buffer;
pEsMsg->BufferSize = BufferSize;
pEsMsg->pEncodedSize = pEncodedSize;
*pHandle = (handle_t)pEsMsg;
return RPC_S_OK;}
/***********************************************************************
* MesDecodeBufferHandleCreate [RPCRT4.@]
*/
RPC_STATUS RPC_ENTRY MesDecodeBufferHandleCreate(
char *Buffer, ULONG BufferSize, handle_t *pHandle)
{
MIDL_ES_MESSAGE *pEsMsg;
TRACE("(%p, %d, %p)\n", Buffer, BufferSize, pHandle);
pEsMsg = HeapAlloc(GetProcessHeap(), 0, sizeof(*pEsMsg));
if (!pEsMsg)
return ERROR_OUTOFMEMORY;
init_MIDL_ES_MESSAGE(pEsMsg);
pEsMsg->Operation = MES_DECODE;
pEsMsg->HandleStyle = MES_FIXED_BUFFER_HANDLE;
pEsMsg->Buffer = (unsigned char *)Buffer;
pEsMsg->BufferSize = BufferSize;
*pHandle = (handle_t)pEsMsg;
return RPC_S_OK;
}
static void es_data_alloc(MIDL_ES_MESSAGE *pEsMsg, ULONG size)
{
if (pEsMsg->HandleStyle == MES_INCREMENTAL_HANDLE)
{
unsigned int tmpsize = size;
TRACE("%d with incremental handle\n", size);
pEsMsg->Alloc(pEsMsg->UserState, (char **)&pEsMsg->StubMsg.Buffer, &tmpsize);
if (tmpsize < size)
{
ERR("not enough bytes allocated - requested %d, got %d\n", size, tmpsize);
RpcRaiseException(ERROR_OUTOFMEMORY);
}
}
else if (pEsMsg->HandleStyle == MES_FIXED_BUFFER_HANDLE)
{
TRACE("%d with fixed buffer handle\n", size);
pEsMsg->StubMsg.Buffer = pEsMsg->Buffer;
}
pEsMsg->StubMsg.RpcMsg->Buffer = pEsMsg->StubMsg.BufferStart = pEsMsg->StubMsg.Buffer;
}
static void es_data_read(MIDL_ES_MESSAGE *pEsMsg, ULONG size)
{
if (pEsMsg->HandleStyle == MES_INCREMENTAL_HANDLE)
{
unsigned int tmpsize = size;
TRACE("%d from incremental handle\n", size);
pEsMsg->Read(pEsMsg->UserState, (char **)&pEsMsg->StubMsg.Buffer, &tmpsize);
if (tmpsize < size)
{
ERR("not enough bytes read - requested %d, got %d\n", size, tmpsize);
RpcRaiseException(ERROR_OUTOFMEMORY);
}
}
else
{
TRACE("%d from fixed or dynamic buffer handle\n", size);
/* FIXME: validate BufferSize? */
pEsMsg->StubMsg.Buffer = pEsMsg->Buffer;
pEsMsg->Buffer += size;
pEsMsg->BufferSize -= size;
}
pEsMsg->StubMsg.BufferLength = size;
pEsMsg->StubMsg.RpcMsg->Buffer = pEsMsg->StubMsg.BufferStart = pEsMsg->StubMsg.Buffer;
pEsMsg->StubMsg.BufferEnd = pEsMsg->StubMsg.Buffer + size;
}
static void es_data_write(MIDL_ES_MESSAGE *pEsMsg, ULONG size)
{
if (pEsMsg->HandleStyle == MES_INCREMENTAL_HANDLE)
{
TRACE("%d to incremental handle\n", size);
pEsMsg->Write(pEsMsg->UserState, (char *)pEsMsg->StubMsg.BufferStart, size);
}
else
{
TRACE("%d to dynamic or fixed buffer handle\n", size);
*pEsMsg->pEncodedSize += size;
}
}
static inline ULONG mes_proc_header_buffer_size(void)
{
return 4 + 2*sizeof(RPC_SYNTAX_IDENTIFIER) + 12;
}
static void mes_proc_header_marshal(MIDL_ES_MESSAGE *pEsMsg)
{
const RPC_CLIENT_INTERFACE *client_interface = pEsMsg->StubMsg.StubDesc->RpcInterfaceInformation;
*(WORD *)pEsMsg->StubMsg.Buffer = 0x0101;
pEsMsg->StubMsg.Buffer += 2;
*(WORD *)pEsMsg->StubMsg.Buffer = 0xcccc;
pEsMsg->StubMsg.Buffer += 2;
memcpy(pEsMsg->StubMsg.Buffer, &client_interface->TransferSyntax, sizeof(RPC_SYNTAX_IDENTIFIER));
pEsMsg->StubMsg.Buffer += sizeof(RPC_SYNTAX_IDENTIFIER);
memcpy(pEsMsg->StubMsg.Buffer, &pEsMsg->InterfaceId, sizeof(RPC_SYNTAX_IDENTIFIER));
pEsMsg->StubMsg.Buffer += sizeof(RPC_SYNTAX_IDENTIFIER);
*(DWORD *)pEsMsg->StubMsg.Buffer = pEsMsg->ProcNumber;
pEsMsg->StubMsg.Buffer += 4;
*(DWORD *)pEsMsg->StubMsg.Buffer = 0x00000001;
pEsMsg->StubMsg.Buffer += 4;
*(DWORD *)pEsMsg->StubMsg.Buffer = pEsMsg->ByteCount;
pEsMsg->StubMsg.Buffer += 4;
}
static void mes_proc_header_unmarshal(MIDL_ES_MESSAGE *pEsMsg)
{
const RPC_CLIENT_INTERFACE *client_interface = pEsMsg->StubMsg.StubDesc->RpcInterfaceInformation;
es_data_read(pEsMsg, mes_proc_header_buffer_size());
if (*(WORD *)pEsMsg->StubMsg.Buffer != 0x0101)
{
FIXME("unknown value at Buffer[0] 0x%04x\n", *(WORD *)pEsMsg->StubMsg.Buffer);
RpcRaiseException(RPC_X_WRONG_ES_VERSION);
}
pEsMsg->StubMsg.Buffer += 2;
if (*(WORD *)pEsMsg->StubMsg.Buffer != 0xcccc)
FIXME("unknown value at Buffer[2] 0x%04x\n", *(WORD *)pEsMsg->StubMsg.Buffer);
pEsMsg->StubMsg.Buffer += 2;
if (memcmp(pEsMsg->StubMsg.Buffer, &client_interface->TransferSyntax, sizeof(RPC_SYNTAX_IDENTIFIER)))
{
const RPC_SYNTAX_IDENTIFIER *AlienTransferSyntax = (const RPC_SYNTAX_IDENTIFIER *)pEsMsg->StubMsg.Buffer;
ERR("bad transfer syntax %s {%d.%d}\n", debugstr_guid(&AlienTransferSyntax->SyntaxGUID),
AlienTransferSyntax->SyntaxVersion.MajorVersion,
AlienTransferSyntax->SyntaxVersion.MinorVersion);
RpcRaiseException(RPC_S_UNSUPPORTED_TRANS_SYN);
}
pEsMsg->StubMsg.Buffer += sizeof(RPC_SYNTAX_IDENTIFIER);
memcpy(&pEsMsg->InterfaceId, pEsMsg->StubMsg.Buffer, sizeof(RPC_SYNTAX_IDENTIFIER));
pEsMsg->StubMsg.Buffer += sizeof(RPC_SYNTAX_IDENTIFIER);
pEsMsg->ProcNumber = *(DWORD *)pEsMsg->StubMsg.Buffer;
pEsMsg->StubMsg.Buffer += 4;
if (*(DWORD *)pEsMsg->StubMsg.Buffer != 0x00000001)
FIXME("unknown value 0x%08x, expected 0x00000001\n", *(DWORD *)pEsMsg->StubMsg.Buffer);
pEsMsg->StubMsg.Buffer += 4;
pEsMsg->ByteCount = *(DWORD *)pEsMsg->StubMsg.Buffer;
pEsMsg->StubMsg.Buffer += 4;
if (pEsMsg->ByteCount + mes_proc_header_buffer_size() < pEsMsg->ByteCount)
RpcRaiseException(RPC_S_INVALID_BOUND);
}
/***********************************************************************
* NdrMesProcEncodeDecode [RPCRT4.@]
*/
void WINAPIV NdrMesProcEncodeDecode(handle_t Handle, const MIDL_STUB_DESC * pStubDesc, PFORMAT_STRING pFormat, ...)
{
/* pointer to start of stack where arguments start */
RPC_MESSAGE rpcMsg;
MIDL_ES_MESSAGE *pEsMsg = (MIDL_ES_MESSAGE *)Handle;
/* size of stack */
unsigned short stack_size;
/* header for procedure string */
const NDR_PROC_HEADER *pProcHeader = (const NDR_PROC_HEADER *)&pFormat[0];
/* the value to return to the client from the remote procedure */
LONG_PTR RetVal = 0;
const RPC_CLIENT_INTERFACE *client_interface;
TRACE("Handle %p, pStubDesc %p, pFormat %p, ...\n", Handle, pStubDesc, pFormat);
/* Later NDR language versions probably won't be backwards compatible */
if (pStubDesc->Version > 0x50002)
{
FIXME("Incompatible stub description version: 0x%x\n", pStubDesc->Version);
RpcRaiseException(RPC_X_WRONG_STUB_VERSION);
}
client_interface = pStubDesc->RpcInterfaceInformation;
pEsMsg->InterfaceId = client_interface->InterfaceId;
if (pProcHeader->Oi_flags & RPC_FC_PROC_OIF_RPCFLAGS)
{
const NDR_PROC_HEADER_RPC *pProcHeader = (const NDR_PROC_HEADER_RPC *)&pFormat[0];
stack_size = pProcHeader->stack_size;
pEsMsg->ProcNumber = pProcHeader->proc_num;
pFormat += sizeof(NDR_PROC_HEADER_RPC);
}
else
{
stack_size = pProcHeader->stack_size;
pEsMsg->ProcNumber = pProcHeader->proc_num;
pFormat += sizeof(NDR_PROC_HEADER);
}
if (pProcHeader->handle_type == RPC_FC_BIND_EXPLICIT)
{
switch (*pFormat) /* handle_type */
{
case RPC_FC_BIND_PRIMITIVE: /* explicit primitive */
pFormat += sizeof(NDR_EHD_PRIMITIVE);
break;
case RPC_FC_BIND_GENERIC: /* explicit generic */
pFormat += sizeof(NDR_EHD_GENERIC);
break;
case RPC_FC_BIND_CONTEXT: /* explicit context */
pFormat += sizeof(NDR_EHD_CONTEXT);
break;
default:
ERR("bad explicit binding handle type (0x%02x)\n", pProcHeader->handle_type);
RpcRaiseException(RPC_X_BAD_STUB_DATA);
}
}
TRACE("stack size: 0x%x\n", stack_size);
TRACE("proc num: %d\n", pEsMsg->ProcNumber);
memset(&rpcMsg, 0, sizeof(rpcMsg));
pEsMsg->StubMsg.RpcMsg = &rpcMsg;
pEsMsg->StubMsg.StubDesc = pStubDesc;
pEsMsg->StubMsg.pfnAllocate = pStubDesc->pfnAllocate;
pEsMsg->StubMsg.pfnFree = pStubDesc->pfnFree;
/* create the full pointer translation tables, if requested */
if (pProcHeader->Oi_flags & RPC_FC_PROC_OIF_FULLPTR)
pEsMsg->StubMsg.FullPtrXlatTables = NdrFullPointerXlatInit(0,XLAT_CLIENT);
TRACE("Oi_flags = 0x%02x\n", pProcHeader->Oi_flags);
TRACE("stubdesc version = 0x%x\n", pStubDesc->Version);
TRACE("MIDL stub version = 0x%x\n", pStubDesc->MIDLVersion);
/* needed for conformance of top-level objects */
#ifdef __i386__
pEsMsg->StubMsg.StackTop = *(unsigned char **)(&pFormat+1);
#else
# warning Stack not retrieved for your CPU architecture
#endif
switch (pEsMsg->Operation)
{
case MES_ENCODE:
pEsMsg->StubMsg.BufferLength = mes_proc_header_buffer_size();
client_do_args_old_format(&pEsMsg->StubMsg, pFormat, PROXY_CALCSIZE,
pEsMsg->StubMsg.StackTop, stack_size, (unsigned char *)&RetVal,
FALSE /* object_proc */, TRUE /* ignore_retval */);
pEsMsg->ByteCount = pEsMsg->StubMsg.BufferLength - mes_proc_header_buffer_size();
es_data_alloc(pEsMsg, pEsMsg->StubMsg.BufferLength);
mes_proc_header_marshal(pEsMsg);
client_do_args_old_format(&pEsMsg->StubMsg, pFormat, PROXY_MARSHAL,
pEsMsg->StubMsg.StackTop, stack_size, (unsigned char *)&RetVal,
FALSE /* object_proc */, TRUE /* ignore_retval */);
es_data_write(pEsMsg, pEsMsg->ByteCount);
break;
case MES_DECODE:
mes_proc_header_unmarshal(pEsMsg);
es_data_read(pEsMsg, pEsMsg->ByteCount);
client_do_args_old_format(&pEsMsg->StubMsg, pFormat, PROXY_UNMARSHAL,
pEsMsg->StubMsg.StackTop, stack_size, (unsigned char *)&RetVal,
FALSE /* object_proc */, TRUE /* ignore_retval */);
break;
default:
RpcRaiseException(RPC_S_INTERNAL_ERROR);
return;
}
/* free the full pointer translation tables */
if (pProcHeader->Oi_flags & RPC_FC_PROC_OIF_FULLPTR)
NdrFullPointerXlatFree(pEsMsg->StubMsg.FullPtrXlatTables);
}

File diff suppressed because it is too large Load diff

View file

@ -79,7 +79,7 @@ static HMODULE LoadCOM(void)
typedef struct RpcStreamImpl typedef struct RpcStreamImpl
{ {
const IStreamVtbl *lpVtbl; const IStreamVtbl *lpVtbl;
DWORD RefCount; LONG RefCount;
PMIDL_STUB_MESSAGE pMsg; PMIDL_STUB_MESSAGE pMsg;
LPDWORD size; LPDWORD size;
unsigned char *data; unsigned char *data;
@ -95,7 +95,7 @@ static HRESULT WINAPI RpcStream_QueryInterface(LPSTREAM iface,
IsEqualGUID(&IID_ISequentialStream, riid) || IsEqualGUID(&IID_ISequentialStream, riid) ||
IsEqualGUID(&IID_IStream, riid)) { IsEqualGUID(&IID_IStream, riid)) {
*obj = This; *obj = This;
This->RefCount++; InterlockedIncrement( &This->RefCount );
return S_OK; return S_OK;
} }
return E_NOINTERFACE; return E_NOINTERFACE;
@ -104,19 +104,20 @@ static HRESULT WINAPI RpcStream_QueryInterface(LPSTREAM iface,
static ULONG WINAPI RpcStream_AddRef(LPSTREAM iface) static ULONG WINAPI RpcStream_AddRef(LPSTREAM iface)
{ {
RpcStreamImpl *This = (RpcStreamImpl *)iface; RpcStreamImpl *This = (RpcStreamImpl *)iface;
return ++(This->RefCount); return InterlockedIncrement( &This->RefCount );
} }
static ULONG WINAPI RpcStream_Release(LPSTREAM iface) static ULONG WINAPI RpcStream_Release(LPSTREAM iface)
{ {
RpcStreamImpl *This = (RpcStreamImpl *)iface; RpcStreamImpl *This = (RpcStreamImpl *)iface;
if (!--(This->RefCount)) { ULONG ref = InterlockedDecrement( &This->RefCount );
if (!ref) {
TRACE("size=%d\n", *This->size); TRACE("size=%d\n", *This->size);
This->pMsg->Buffer = This->data + *This->size; This->pMsg->Buffer = This->data + *This->size;
HeapFree(GetProcessHeap(),0,This); HeapFree(GetProcessHeap(),0,This);
return 0; return 0;
} }
return This->RefCount; return ref;
} }
static HRESULT WINAPI RpcStream_Read(LPSTREAM iface, static HRESULT WINAPI RpcStream_Read(LPSTREAM iface,

View file

@ -91,29 +91,6 @@ static inline void call_freer(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemor
if (m) m(pStubMsg, pMemory, pFormat); if (m) m(pStubMsg, pMemory, pFormat);
} }
static inline unsigned long call_memory_sizer(PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFormat)
{
NDR_MEMORYSIZE m = NdrMemorySizer[pFormat[0] & NDR_TABLE_MASK];
if (m)
{
unsigned char *saved_buffer = pStubMsg->Buffer;
unsigned long ret;
int saved_ignore_embedded_pointers = pStubMsg->IgnoreEmbeddedPointers;
pStubMsg->MemorySize = 0;
pStubMsg->IgnoreEmbeddedPointers = 1;
ret = m(pStubMsg, pFormat);
pStubMsg->IgnoreEmbeddedPointers = saved_ignore_embedded_pointers;
pStubMsg->Buffer = saved_buffer;
return ret;
}
else
{
FIXME("format type 0x%x not implemented\n", pFormat[0]);
RpcRaiseException(RPC_X_BAD_STUB_DATA);
return 0;
}
}
#define STUBLESS_UNMARSHAL 1 #define STUBLESS_UNMARSHAL 1
#define STUBLESS_INITOUT 2 #define STUBLESS_INITOUT 2
#define STUBLESS_CALLSERVER 3 #define STUBLESS_CALLSERVER 3
@ -159,7 +136,7 @@ static void WINAPI dump_INTERPRETER_OPT_FLAGS(INTERPRETER_OPT_FLAGS Oi2Flags)
TRACE("\n"); TRACE("\n");
} }
#define ARG_FROM_OFFSET(stubMsg, offset) ((stubMsg).StackTop + (offset)) #define ARG_FROM_OFFSET(args, offset) ((args) + (offset))
static PFORMAT_STRING client_get_handle( static PFORMAT_STRING client_get_handle(
PMIDL_STUB_MESSAGE pStubMsg, const NDR_PROC_HEADER *pProcHeader, PMIDL_STUB_MESSAGE pStubMsg, const NDR_PROC_HEADER *pProcHeader,
@ -179,9 +156,9 @@ static PFORMAT_STRING client_get_handle(
TRACE("Explicit primitive handle @ %d\n", pDesc->offset); TRACE("Explicit primitive handle @ %d\n", pDesc->offset);
if (pDesc->flag) /* pointer to binding */ if (pDesc->flag) /* pointer to binding */
*phBinding = **(handle_t **)ARG_FROM_OFFSET(*pStubMsg, pDesc->offset); *phBinding = **(handle_t **)ARG_FROM_OFFSET(pStubMsg->StackTop, pDesc->offset);
else else
*phBinding = *(handle_t *)ARG_FROM_OFFSET(*pStubMsg, pDesc->offset); *phBinding = *(handle_t *)ARG_FROM_OFFSET(pStubMsg->StackTop, pDesc->offset);
return pFormat + sizeof(NDR_EHD_PRIMITIVE); return pFormat + sizeof(NDR_EHD_PRIMITIVE);
} }
case RPC_FC_BIND_GENERIC: /* explicit generic */ case RPC_FC_BIND_GENERIC: /* explicit generic */
@ -194,9 +171,9 @@ static PFORMAT_STRING client_get_handle(
TRACE("Explicit generic binding handle #%d\n", pDesc->binding_routine_pair_index); TRACE("Explicit generic binding handle #%d\n", pDesc->binding_routine_pair_index);
if (pDesc->flag_and_size & HANDLE_PARAM_IS_VIA_PTR) if (pDesc->flag_and_size & HANDLE_PARAM_IS_VIA_PTR)
pArg = *(void **)ARG_FROM_OFFSET(*pStubMsg, pDesc->offset); pArg = *(void **)ARG_FROM_OFFSET(pStubMsg->StackTop, pDesc->offset);
else else
pArg = (void *)ARG_FROM_OFFSET(*pStubMsg, pDesc->offset); pArg = (void *)ARG_FROM_OFFSET(pStubMsg->StackTop, pDesc->offset);
memcpy(&pObject, pArg, pDesc->flag_and_size & 0xf); memcpy(&pObject, pArg, pDesc->flag_and_size & 0xf);
pGenPair = &pStubMsg->StubDesc->aGenericBindingRoutinePairs[pDesc->binding_routine_pair_index]; pGenPair = &pStubMsg->StubDesc->aGenericBindingRoutinePairs[pDesc->binding_routine_pair_index];
*phBinding = pGenPair->pfnBind(pObject); *phBinding = pGenPair->pfnBind(pObject);
@ -210,10 +187,10 @@ static PFORMAT_STRING client_get_handle(
if (pDesc->flags & HANDLE_PARAM_IS_VIA_PTR) if (pDesc->flags & HANDLE_PARAM_IS_VIA_PTR)
{ {
TRACE("\tHANDLE_PARAM_IS_VIA_PTR\n"); TRACE("\tHANDLE_PARAM_IS_VIA_PTR\n");
context_handle = **(NDR_CCONTEXT **)ARG_FROM_OFFSET(*pStubMsg, pDesc->offset); context_handle = **(NDR_CCONTEXT **)ARG_FROM_OFFSET(pStubMsg->StackTop, pDesc->offset);
} }
else else
context_handle = *(NDR_CCONTEXT *)ARG_FROM_OFFSET(*pStubMsg, pDesc->offset); context_handle = *(NDR_CCONTEXT *)ARG_FROM_OFFSET(pStubMsg->StackTop, pDesc->offset);
if ((pDesc->flags & NDR_CONTEXT_HANDLE_CANNOT_BE_NULL) && if ((pDesc->flags & NDR_CONTEXT_HANDLE_CANNOT_BE_NULL) &&
!context_handle) !context_handle)
{ {
@ -277,9 +254,9 @@ static void client_free_handle(
TRACE("Explicit generic binding handle #%d\n", pDesc->binding_routine_pair_index); TRACE("Explicit generic binding handle #%d\n", pDesc->binding_routine_pair_index);
if (pDesc->flag_and_size & HANDLE_PARAM_IS_VIA_PTR) if (pDesc->flag_and_size & HANDLE_PARAM_IS_VIA_PTR)
pArg = *(void **)ARG_FROM_OFFSET(*pStubMsg, pDesc->offset); pArg = *(void **)ARG_FROM_OFFSET(pStubMsg->StackTop, pDesc->offset);
else else
pArg = (void *)ARG_FROM_OFFSET(*pStubMsg, pDesc->offset); pArg = (void *)ARG_FROM_OFFSET(pStubMsg->StackTop, pDesc->offset);
memcpy(&pObject, pArg, pDesc->flag_and_size & 0xf); memcpy(&pObject, pArg, pDesc->flag_and_size & 0xf);
pGenPair = &pStubMsg->StubDesc->aGenericBindingRoutinePairs[pDesc->binding_routine_pair_index]; pGenPair = &pStubMsg->StubDesc->aGenericBindingRoutinePairs[pDesc->binding_routine_pair_index];
pGenPair->pfnUnbind(pObject, hBinding); pGenPair->pfnUnbind(pObject, hBinding);
@ -308,7 +285,8 @@ static void client_free_handle(
} }
static void client_do_args(PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFormat, static void client_do_args(PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFormat,
int phase, unsigned short number_of_params, unsigned char *pRetVal) int phase, unsigned char *args, unsigned short number_of_params,
unsigned char *pRetVal)
{ {
/* current format string offset */ /* current format string offset */
int current_offset = 0; int current_offset = 0;
@ -324,7 +302,7 @@ static void client_do_args(PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFormat,
unsigned char * pArg; unsigned char * pArg;
current_stack_offset = pParam->stack_offset; current_stack_offset = pParam->stack_offset;
pArg = ARG_FROM_OFFSET(*pStubMsg, current_stack_offset); pArg = ARG_FROM_OFFSET(args, current_stack_offset);
TRACE("param[%d]: new format\n", i); TRACE("param[%d]: new format\n", i);
TRACE("\tparam_attributes:"); dump_RPC_FC_PROC_PF(pParam->param_attributes); TRACE("\n"); TRACE("\tparam_attributes:"); dump_RPC_FC_PROC_PF(pParam->param_attributes); TRACE("\n");
@ -426,9 +404,44 @@ static void client_do_args(PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFormat,
} }
} }
static void client_do_args_old_format(PMIDL_STUB_MESSAGE pStubMsg, static unsigned int type_stack_size(unsigned char fc)
PFORMAT_STRING pFormat, int phase, unsigned short stack_size, {
unsigned char *pRetVal, BOOL object_proc) switch (fc)
{
case RPC_FC_BYTE:
case RPC_FC_CHAR:
case RPC_FC_SMALL:
case RPC_FC_USMALL:
return sizeof(char);
case RPC_FC_WCHAR:
case RPC_FC_SHORT:
case RPC_FC_USHORT:
return sizeof(short);
case RPC_FC_LONG:
case RPC_FC_ULONG:
case RPC_FC_ENUM16:
case RPC_FC_ENUM32:
return sizeof(int);
case RPC_FC_FLOAT:
return sizeof(float);
case RPC_FC_DOUBLE:
return sizeof(double);
case RPC_FC_HYPER:
return sizeof(ULONGLONG);
case RPC_FC_ERROR_STATUS_T:
return sizeof(error_status_t);
case RPC_FC_IGNORE:
return sizeof(void *);
default:
ERR("invalid base type 0x%x\n", fc);
RpcRaiseException(RPC_S_INTERNAL_ERROR);
}
}
void client_do_args_old_format(PMIDL_STUB_MESSAGE pStubMsg,
PFORMAT_STRING pFormat, int phase, unsigned char *args,
unsigned short stack_size,
unsigned char *pRetVal, BOOL object_proc, BOOL ignore_retval)
{ {
/* current format string offset */ /* current format string offset */
int current_offset = 0; int current_offset = 0;
@ -437,7 +450,7 @@ static void client_do_args_old_format(PMIDL_STUB_MESSAGE pStubMsg,
/* counter */ /* counter */
unsigned short i; unsigned short i;
/* NOTE: V1 style format does't terminate on the number_of_params /* NOTE: V1 style format doesn't terminate on the number_of_params
* condition as it doesn't have this attribute. Instead it * condition as it doesn't have this attribute. Instead it
* terminates when the stack size given in the header is exceeded. * terminates when the stack size given in the header is exceeded.
*/ */
@ -449,7 +462,7 @@ static void client_do_args_old_format(PMIDL_STUB_MESSAGE pStubMsg,
* if present, so adjust this */ * if present, so adjust this */
unsigned short current_stack_offset_adjusted = current_stack_offset + unsigned short current_stack_offset_adjusted = current_stack_offset +
(object_proc ? sizeof(void *) : 0); (object_proc ? sizeof(void *) : 0);
unsigned char * pArg = ARG_FROM_OFFSET(*pStubMsg, current_stack_offset_adjusted); unsigned char * pArg = ARG_FROM_OFFSET(args, current_stack_offset_adjusted);
/* no more parameters; exit loop */ /* no more parameters; exit loop */
if (current_stack_offset_adjusted >= stack_size) if (current_stack_offset_adjusted >= stack_size)
@ -479,10 +492,11 @@ static void client_do_args_old_format(PMIDL_STUB_MESSAGE pStubMsg,
call_marshaller(pStubMsg, pArg, pTypeFormat); call_marshaller(pStubMsg, pArg, pTypeFormat);
break; break;
case PROXY_UNMARSHAL: case PROXY_UNMARSHAL:
if (pParam->param_direction == RPC_FC_RETURN_PARAM_BASETYPE) if (!ignore_retval &&
pParam->param_direction == RPC_FC_RETURN_PARAM_BASETYPE)
{ {
if (pParam->param_direction & RPC_FC_RETURN_PARAM) if (pParam->param_direction & RPC_FC_RETURN_PARAM)
call_unmarshaller(pStubMsg, (unsigned char **)pRetVal, pTypeFormat, 0); call_unmarshaller(pStubMsg, &pRetVal, pTypeFormat, 0);
else else
call_unmarshaller(pStubMsg, &pArg, pTypeFormat, 0); call_unmarshaller(pStubMsg, &pArg, pTypeFormat, 0);
} }
@ -491,7 +505,7 @@ static void client_do_args_old_format(PMIDL_STUB_MESSAGE pStubMsg,
RpcRaiseException(RPC_S_INTERNAL_ERROR); RpcRaiseException(RPC_S_INTERNAL_ERROR);
} }
current_stack_offset += call_memory_sizer(pStubMsg, pTypeFormat); current_stack_offset += type_stack_size(*pTypeFormat);
current_offset += sizeof(NDR_PARAM_OI_BASETYPE); current_offset += sizeof(NDR_PARAM_OI_BASETYPE);
} }
else else
@ -705,12 +719,12 @@ LONG_PTR WINAPIV NdrClientCall2(PMIDL_STUB_DESC pStubDesc, PFORMAT_STRING pForma
case PROXY_MARSHAL: case PROXY_MARSHAL:
case PROXY_UNMARSHAL: case PROXY_UNMARSHAL:
if (bV2Format) if (bV2Format)
client_do_args(&stubMsg, pFormat, phase, number_of_params, client_do_args(&stubMsg, pFormat, phase, stubMsg.StackTop,
(unsigned char *)&RetVal); number_of_params, (unsigned char *)&RetVal);
else else
client_do_args_old_format(&stubMsg, pFormat, phase, stack_size, client_do_args_old_format(&stubMsg, pFormat, phase,
(unsigned char *)&RetVal, stubMsg.StackTop, stack_size, (unsigned char *)&RetVal,
(pProcHeader->Oi_flags & RPC_FC_PROC_OIF_OBJECT)); (pProcHeader->Oi_flags & RPC_FC_PROC_OIF_OBJECT), FALSE);
break; break;
default: default:
ERR("shouldn't reach here. phase %d\n", phase); ERR("shouldn't reach here. phase %d\n", phase);
@ -718,7 +732,7 @@ LONG_PTR WINAPIV NdrClientCall2(PMIDL_STUB_DESC pStubDesc, PFORMAT_STRING pForma
} }
} }
} }
__EXCEPT(NULL) __EXCEPT_ALL
{ {
RetVal = NdrProxyErrorHandler(GetExceptionCode()); RetVal = NdrProxyErrorHandler(GetExceptionCode());
} }
@ -783,12 +797,12 @@ LONG_PTR WINAPIV NdrClientCall2(PMIDL_STUB_DESC pStubDesc, PFORMAT_STRING pForma
case PROXY_MARSHAL: case PROXY_MARSHAL:
case PROXY_UNMARSHAL: case PROXY_UNMARSHAL:
if (bV2Format) if (bV2Format)
client_do_args(&stubMsg, pFormat, phase, number_of_params, client_do_args(&stubMsg, pFormat, phase, stubMsg.StackTop,
(unsigned char *)&RetVal); number_of_params, (unsigned char *)&RetVal);
else else
client_do_args_old_format(&stubMsg, pFormat, phase, stack_size, client_do_args_old_format(&stubMsg, pFormat, phase,
(unsigned char *)&RetVal, stubMsg.StackTop, stack_size, (unsigned char *)&RetVal,
(pProcHeader->Oi_flags & RPC_FC_PROC_OIF_OBJECT)); (pProcHeader->Oi_flags & RPC_FC_PROC_OIF_OBJECT), FALSE);
break; break;
default: default:
ERR("shouldn't reach here. phase %d\n", phase); ERR("shouldn't reach here. phase %d\n", phase);
@ -826,7 +840,7 @@ LONG_PTR WINAPIV NdrClientCall2(PMIDL_STUB_DESC pStubDesc, PFORMAT_STRING pForma
return RetVal; return RetVal;
} }
/* calls a function with the specificed arguments, restoring the stack /* Calls a function with the specified arguments, restoring the stack
* properly afterwards as we don't know the calling convention of the * properly afterwards as we don't know the calling convention of the
* function */ * function */
#if defined __i386__ && defined _MSC_VER #if defined __i386__ && defined _MSC_VER
@ -1160,7 +1174,7 @@ static LONG_PTR *stub_do_old_args(MIDL_STUB_MESSAGE *pStubMsg,
RpcRaiseException(RPC_S_INTERNAL_ERROR); RpcRaiseException(RPC_S_INTERNAL_ERROR);
} }
current_stack_offset += call_memory_sizer(pStubMsg, pTypeFormat); current_stack_offset += type_stack_size(*pTypeFormat);
current_offset += sizeof(NDR_PARAM_OI_BASETYPE); current_offset += sizeof(NDR_PARAM_OI_BASETYPE);
} }
else else
@ -1464,9 +1478,7 @@ LONG WINAPI NdrStubCall2(
Status = I_RpcGetBuffer(pRpcMsg); Status = I_RpcGetBuffer(pRpcMsg);
if (Status) if (Status)
RpcRaiseException(Status); RpcRaiseException(Status);
stubMsg.BufferStart = pRpcMsg->Buffer; stubMsg.Buffer = pRpcMsg->Buffer;
stubMsg.BufferEnd = stubMsg.BufferStart + stubMsg.BufferLength;
stubMsg.Buffer = stubMsg.BufferStart;
} }
break; break;
case STUBLESS_UNMARSHAL: case STUBLESS_UNMARSHAL:

View file

@ -23,7 +23,6 @@
/* there can't be any alignment with the structures in this file */ /* there can't be any alignment with the structures in this file */
#include "pshpack1.h" #include "pshpack1.h"
/* From http://msdn.microsoft.com/library/default.asp?url=/library/en-us/rpc/rpc/parameter_descriptors.asp */
typedef struct _NDR_PROC_HEADER typedef struct _NDR_PROC_HEADER
{ {
/* type of handle to use: /* type of handle to use:
@ -36,7 +35,7 @@ typedef struct _NDR_PROC_HEADER
* RPC_FC_BIND_PRIMITIVE = 32 - Implicit handle using handle_t created by * RPC_FC_BIND_PRIMITIVE = 32 - Implicit handle using handle_t created by
* calling application * calling application
* RPC_FC_AUTO_HANDLE = 33 - Automatic handle * RPC_FC_AUTO_HANDLE = 33 - Automatic handle
* RPC_FC_CALLBACK_HANDLE = 34 - undocmented * RPC_FC_CALLBACK_HANDLE = 34 - undocumented
*/ */
unsigned char handle_type; unsigned char handle_type;
@ -236,3 +235,8 @@ typedef struct _NDR_EHD_CONTEXT
} NDR_EHD_CONTEXT; } NDR_EHD_CONTEXT;
#include "poppack.h" #include "poppack.h"
void client_do_args_old_format(PMIDL_STUB_MESSAGE pStubMsg,
PFORMAT_STRING pFormat, int phase, unsigned char *args,
unsigned short stack_size, unsigned char *pRetVal, BOOL object_proc,
BOOL ignore_retval);

View file

@ -222,6 +222,8 @@ static RPC_STATUS RpcAssoc_BindConnection(const RpcAssoc *assoc, RpcConnection *
RpcPktHdr *response_hdr; RpcPktHdr *response_hdr;
RPC_MESSAGE msg; RPC_MESSAGE msg;
RPC_STATUS status; RPC_STATUS status;
unsigned char *auth_data = NULL;
unsigned long auth_length;
TRACE("sending bind request to server\n"); TRACE("sending bind request to server\n");
@ -235,10 +237,10 @@ static RPC_STATUS RpcAssoc_BindConnection(const RpcAssoc *assoc, RpcConnection *
if (status != RPC_S_OK) if (status != RPC_S_OK)
return status; return status;
status = RPCRT4_Receive(conn, &response_hdr, &msg); status = RPCRT4_ReceiveWithAuth(conn, &response_hdr, &msg, &auth_data, &auth_length);
if (status != RPC_S_OK) if (status != RPC_S_OK)
{ {
ERR("receive failed\n"); ERR("receive failed with error %ld\n", status);
return status; return status;
} }
@ -259,9 +261,17 @@ static RPC_STATUS RpcAssoc_BindConnection(const RpcAssoc *assoc, RpcConnection *
switch (results->results[0].result) switch (results->results[0].result)
{ {
case RESULT_ACCEPT: case RESULT_ACCEPT:
conn->assoc_group_id = response_hdr->bind_ack.assoc_gid; /* respond to authorization request */
conn->MaxTransmissionSize = response_hdr->bind_ack.max_tsize; if (auth_length > sizeof(RpcAuthVerifier))
conn->ActiveInterface = *InterfaceId; status = RPCRT4_AuthorizeConnection(conn,
auth_data + sizeof(RpcAuthVerifier),
auth_length);
if (status == RPC_S_OK)
{
conn->assoc_group_id = response_hdr->bind_ack.assoc_gid;
conn->MaxTransmissionSize = response_hdr->bind_ack.max_tsize;
conn->ActiveInterface = *InterfaceId;
}
break; break;
case RESULT_PROVIDER_REJECTION: case RESULT_PROVIDER_REJECTION:
switch (results->results[0].reason) switch (results->results[0].reason)
@ -334,6 +344,7 @@ static RPC_STATUS RpcAssoc_BindConnection(const RpcAssoc *assoc, RpcConnection *
I_RpcFree(msg.Buffer); I_RpcFree(msg.Buffer);
RPCRT4_FreeHeader(response_hdr); RPCRT4_FreeHeader(response_hdr);
HeapFree(GetProcessHeap(), 0, auth_data);
return status; return status;
} }

View file

@ -157,20 +157,19 @@ static RPC_STATUS RPCRT4_CompleteBindingA(RpcBinding* Binding, LPCSTR NetworkAdd
RPCRT4_strfree(Binding->NetworkAddr); RPCRT4_strfree(Binding->NetworkAddr);
Binding->NetworkAddr = RPCRT4_strdupA(NetworkAddr); Binding->NetworkAddr = RPCRT4_strdupA(NetworkAddr);
RPCRT4_strfree(Binding->Endpoint); RPCRT4_strfree(Binding->Endpoint);
if (Endpoint) { Binding->Endpoint = RPCRT4_strdupA(Endpoint);
Binding->Endpoint = RPCRT4_strdupA(Endpoint);
} else {
Binding->Endpoint = RPCRT4_strdupA("");
}
HeapFree(GetProcessHeap(), 0, Binding->NetworkOptions); HeapFree(GetProcessHeap(), 0, Binding->NetworkOptions);
Binding->NetworkOptions = RPCRT4_strdupAtoW(NetworkOptions); Binding->NetworkOptions = RPCRT4_strdupAtoW(NetworkOptions);
if (!Binding->Endpoint) ERR("out of memory?\n");
status = RPCRT4_GetAssociation(Binding->Protseq, Binding->NetworkAddr, /* only attempt to get an association if the binding is complete */
Binding->Endpoint, Binding->NetworkOptions, if (Endpoint && Endpoint[0] != '\0')
&Binding->Assoc); {
if (status != RPC_S_OK) status = RPCRT4_GetAssociation(Binding->Protseq, Binding->NetworkAddr,
return status; Binding->Endpoint, Binding->NetworkOptions,
&Binding->Assoc);
if (status != RPC_S_OK)
return status;
}
return RPC_S_OK; return RPC_S_OK;
} }
@ -186,20 +185,19 @@ static RPC_STATUS RPCRT4_CompleteBindingW(RpcBinding* Binding, LPCWSTR NetworkAd
RPCRT4_strfree(Binding->NetworkAddr); RPCRT4_strfree(Binding->NetworkAddr);
Binding->NetworkAddr = RPCRT4_strdupWtoA(NetworkAddr); Binding->NetworkAddr = RPCRT4_strdupWtoA(NetworkAddr);
RPCRT4_strfree(Binding->Endpoint); RPCRT4_strfree(Binding->Endpoint);
if (Endpoint) { Binding->Endpoint = RPCRT4_strdupWtoA(Endpoint);
Binding->Endpoint = RPCRT4_strdupWtoA(Endpoint);
} else {
Binding->Endpoint = RPCRT4_strdupA("");
}
if (!Binding->Endpoint) ERR("out of memory?\n");
HeapFree(GetProcessHeap(), 0, Binding->NetworkOptions); HeapFree(GetProcessHeap(), 0, Binding->NetworkOptions);
Binding->NetworkOptions = RPCRT4_strdupW(NetworkOptions); Binding->NetworkOptions = RPCRT4_strdupW(NetworkOptions);
status = RPCRT4_GetAssociation(Binding->Protseq, Binding->NetworkAddr, /* only attempt to get an association if the binding is complete */
Binding->Endpoint, Binding->NetworkOptions, if (Endpoint && Endpoint[0] != '\0')
&Binding->Assoc); {
if (status != RPC_S_OK) status = RPCRT4_GetAssociation(Binding->Protseq, Binding->NetworkAddr,
return status; Binding->Endpoint, Binding->NetworkOptions,
&Binding->Assoc);
if (status != RPC_S_OK)
return status;
}
return RPC_S_OK; return RPC_S_OK;
} }
@ -213,7 +211,7 @@ RPC_STATUS RPCRT4_ResolveBinding(RpcBinding* Binding, LPCSTR Endpoint)
RPCRT4_strfree(Binding->Endpoint); RPCRT4_strfree(Binding->Endpoint);
Binding->Endpoint = RPCRT4_strdupA(Endpoint); Binding->Endpoint = RPCRT4_strdupA(Endpoint);
RpcAssoc_Release(Binding->Assoc); if (Binding->Assoc) RpcAssoc_Release(Binding->Assoc);
Binding->Assoc = NULL; Binding->Assoc = NULL;
status = RPCRT4_GetAssociation(Binding->Protseq, Binding->NetworkAddr, status = RPCRT4_GetAssociation(Binding->Protseq, Binding->NetworkAddr,
Binding->Endpoint, Binding->NetworkOptions, Binding->Endpoint, Binding->NetworkOptions,
@ -227,7 +225,7 @@ RPC_STATUS RPCRT4_ResolveBinding(RpcBinding* Binding, LPCSTR Endpoint)
RPC_STATUS RPCRT4_SetBindingObject(RpcBinding* Binding, const UUID* ObjectUuid) RPC_STATUS RPCRT4_SetBindingObject(RpcBinding* Binding, const UUID* ObjectUuid)
{ {
TRACE("(*RpcBinding == ^%p, UUID == %s)\n", Binding, debugstr_guid(ObjectUuid)); TRACE("(*RpcBinding == ^%p, UUID == %s)\n", Binding, debugstr_guid(ObjectUuid));
if (ObjectUuid) memcpy(&Binding->ObjectUuid, ObjectUuid, sizeof(UUID)); if (ObjectUuid) Binding->ObjectUuid = *ObjectUuid;
else UuidCreateNil(&Binding->ObjectUuid); else UuidCreateNil(&Binding->ObjectUuid);
return RPC_S_OK; return RPC_S_OK;
} }
@ -249,14 +247,12 @@ RPC_STATUS RPCRT4_MakeBinding(RpcBinding** Binding, RpcConnection* Connection)
return RPC_S_OK; return RPC_S_OK;
} }
RPC_STATUS RPCRT4_ExportBinding(RpcBinding** Binding, RpcBinding* OldBinding) void RPCRT4_AddRefBinding(RpcBinding* Binding)
{ {
InterlockedIncrement(&OldBinding->refs); InterlockedIncrement(&Binding->refs);
*Binding = OldBinding;
return RPC_S_OK;
} }
RPC_STATUS RPCRT4_DestroyBinding(RpcBinding* Binding) RPC_STATUS RPCRT4_ReleaseBinding(RpcBinding* Binding)
{ {
if (InterlockedDecrement(&Binding->refs)) if (InterlockedDecrement(&Binding->refs))
return RPC_S_OK; return RPC_S_OK;
@ -310,21 +306,6 @@ RPC_STATUS RPCRT4_CloseBinding(RpcBinding* Binding, RpcConnection* Connection)
} }
} }
/* utility functions for string composing and parsing */
static unsigned RPCRT4_strcopyA(LPSTR data, LPCSTR src)
{
unsigned len = strlen(src);
memcpy(data, src, len*sizeof(CHAR));
return len;
}
static unsigned RPCRT4_strcopyW(LPWSTR data, LPCWSTR src)
{
unsigned len = strlenW(src);
memcpy(data, src, len*sizeof(WCHAR));
return len;
}
static LPSTR RPCRT4_strconcatA(LPSTR dst, LPCSTR src) static LPSTR RPCRT4_strconcatA(LPSTR dst, LPCSTR src)
{ {
DWORD len = strlen(dst), slen = strlen(src); DWORD len = strlen(dst), slen = strlen(src);
@ -353,6 +334,123 @@ static LPWSTR RPCRT4_strconcatW(LPWSTR dst, LPCWSTR src)
return ndst; return ndst;
} }
/* Copies the escaped version of a component into a string binding.
* Note: doesn't nul-terminate the string */
static RPC_CSTR escape_string_binding_component(RPC_CSTR string_binding,
const unsigned char *component)
{
for (; *component; component++) {
switch (*component) {
case '@':
case ':':
case '[':
case ']':
case '\\':
*string_binding++ = '\\';
*string_binding++ = *component;
break;
default:
*string_binding++ = *component;
break;
}
}
return string_binding;
}
static RPC_WSTR escape_string_binding_componentW(RPC_WSTR string_binding,
const WCHAR *component)
{
for (; *component; component++) {
switch (*component) {
case '@':
case ':':
case '[':
case ']':
case '\\':
*string_binding++ = '\\';
*string_binding++ = *component;
break;
default:
*string_binding++ = *component;
break;
}
}
return string_binding;
}
static const unsigned char *string_binding_find_delimiter(
const unsigned char *string_binding, unsigned char delim)
{
const unsigned char *next;
for (next = string_binding; *next; next++) {
if (*next == '\\') {
next++;
continue;
}
if (*next == delim)
return next;
}
return NULL;
}
static const WCHAR *string_binding_find_delimiterW(
const WCHAR *string_binding, WCHAR delim)
{
const WCHAR *next;
for (next = string_binding; *next; next++) {
if (*next == '\\') {
next++;
continue;
}
if (*next == delim)
return next;
}
return NULL;
}
static RPC_CSTR unescape_string_binding_component(
const unsigned char *string_binding, int len)
{
RPC_CSTR component, p;
if (len == -1) len = strlen((const char *)string_binding);
component = HeapAlloc(GetProcessHeap(), 0, (len + 1) * sizeof(*component));
if (!component) return NULL;
for (p = component; len > 0; string_binding++, len--) {
if (*string_binding == '\\') {
string_binding++;
len--;
*p++ = *string_binding;
} else {
*p++ = *string_binding;
}
}
*p = '\0';
return component;
}
static RPC_WSTR unescape_string_binding_componentW(
const WCHAR *string_binding, int len)
{
RPC_WSTR component, p;
if (len == -1) len = strlen((const char *)string_binding);
component = HeapAlloc(GetProcessHeap(), 0, (len + 1) * sizeof(*component));
if (!component) return NULL;
for (p = component; len > 0; string_binding++, len--) {
if (*string_binding == '\\') {
string_binding++;
len--;
*p++ = *string_binding;
} else {
*p++ = *string_binding;
}
}
*p = '\0';
return component;
}
/*********************************************************************** /***********************************************************************
* RpcStringBindingComposeA (RPCRT4.@) * RpcStringBindingComposeA (RPCRT4.@)
@ -362,42 +460,43 @@ RPC_STATUS WINAPI RpcStringBindingComposeA(RPC_CSTR ObjUuid, RPC_CSTR Protseq,
RPC_CSTR Options, RPC_CSTR *StringBinding ) RPC_CSTR Options, RPC_CSTR *StringBinding )
{ {
DWORD len = 1; DWORD len = 1;
LPSTR data; RPC_CSTR data;
TRACE( "(%s,%s,%s,%s,%s,%p)\n", TRACE( "(%s,%s,%s,%s,%s,%p)\n",
debugstr_a( (char*)ObjUuid ), debugstr_a( (char*)Protseq ), debugstr_a( (char*)ObjUuid ), debugstr_a( (char*)Protseq ),
debugstr_a( (char*)NetworkAddr ), debugstr_a( (char*)Endpoint ), debugstr_a( (char*)NetworkAddr ), debugstr_a( (char*)Endpoint ),
debugstr_a( (char*)Options ), StringBinding ); debugstr_a( (char*)Options ), StringBinding );
if (ObjUuid && *ObjUuid) len += strlen((char*)ObjUuid) + 1; /* overestimate for each component for escaping of delimiters */
if (Protseq && *Protseq) len += strlen((char*)Protseq) + 1; if (ObjUuid && *ObjUuid) len += strlen((char*)ObjUuid) * 2 + 1;
if (NetworkAddr && *NetworkAddr) len += strlen((char*)NetworkAddr); if (Protseq && *Protseq) len += strlen((char*)Protseq) * 2 + 1;
if (Endpoint && *Endpoint) len += strlen((char*)Endpoint) + 2; if (NetworkAddr && *NetworkAddr) len += strlen((char*)NetworkAddr) * 2;
if (Options && *Options) len += strlen((char*)Options) + 2; if (Endpoint && *Endpoint) len += strlen((char*)Endpoint) * 2 + 2;
if (Options && *Options) len += strlen((char*)Options) * 2 + 2;
data = HeapAlloc(GetProcessHeap(), 0, len); data = HeapAlloc(GetProcessHeap(), 0, len);
*StringBinding = (unsigned char*)data; *StringBinding = data;
if (ObjUuid && *ObjUuid) { if (ObjUuid && *ObjUuid) {
data += RPCRT4_strcopyA(data, (char*)ObjUuid); data = escape_string_binding_component(data, ObjUuid);
*data++ = '@'; *data++ = '@';
} }
if (Protseq && *Protseq) { if (Protseq && *Protseq) {
data += RPCRT4_strcopyA(data, (char*)Protseq); data = escape_string_binding_component(data, Protseq);
*data++ = ':'; *data++ = ':';
} }
if (NetworkAddr && *NetworkAddr) if (NetworkAddr && *NetworkAddr)
data += RPCRT4_strcopyA(data, (char*)NetworkAddr); data = escape_string_binding_component(data, NetworkAddr);
if ((Endpoint && *Endpoint) || if ((Endpoint && *Endpoint) ||
(Options && *Options)) { (Options && *Options)) {
*data++ = '['; *data++ = '[';
if (Endpoint && *Endpoint) { if (Endpoint && *Endpoint) {
data += RPCRT4_strcopyA(data, (char*)Endpoint); data = escape_string_binding_component(data, Endpoint);
if (Options && *Options) *data++ = ','; if (Options && *Options) *data++ = ',';
} }
if (Options && *Options) { if (Options && *Options) {
data += RPCRT4_strcopyA(data, (char*)Options); data = escape_string_binding_component(data, Options);
} }
*data++ = ']'; *data++ = ']';
} }
@ -421,35 +520,36 @@ RPC_STATUS WINAPI RpcStringBindingComposeW( RPC_WSTR ObjUuid, RPC_WSTR Protseq,
debugstr_w( NetworkAddr ), debugstr_w( Endpoint ), debugstr_w( NetworkAddr ), debugstr_w( Endpoint ),
debugstr_w( Options ), StringBinding); debugstr_w( Options ), StringBinding);
if (ObjUuid && *ObjUuid) len += strlenW(ObjUuid) + 1; /* overestimate for each component for escaping of delimiters */
if (Protseq && *Protseq) len += strlenW(Protseq) + 1; if (ObjUuid && *ObjUuid) len += strlenW(ObjUuid) * 2 + 1;
if (NetworkAddr && *NetworkAddr) len += strlenW(NetworkAddr); if (Protseq && *Protseq) len += strlenW(Protseq) * 2 + 1;
if (Endpoint && *Endpoint) len += strlenW(Endpoint) + 2; if (NetworkAddr && *NetworkAddr) len += strlenW(NetworkAddr) * 2;
if (Options && *Options) len += strlenW(Options) + 2; if (Endpoint && *Endpoint) len += strlenW(Endpoint) * 2 + 2;
if (Options && *Options) len += strlenW(Options) * 2 + 2;
data = HeapAlloc(GetProcessHeap(), 0, len*sizeof(WCHAR)); data = HeapAlloc(GetProcessHeap(), 0, len*sizeof(WCHAR));
*StringBinding = data; *StringBinding = data;
if (ObjUuid && *ObjUuid) { if (ObjUuid && *ObjUuid) {
data += RPCRT4_strcopyW(data, ObjUuid); data = escape_string_binding_componentW(data, ObjUuid);
*data++ = '@'; *data++ = '@';
} }
if (Protseq && *Protseq) { if (Protseq && *Protseq) {
data += RPCRT4_strcopyW(data, Protseq); data = escape_string_binding_componentW(data, Protseq);
*data++ = ':'; *data++ = ':';
} }
if (NetworkAddr && *NetworkAddr) { if (NetworkAddr && *NetworkAddr) {
data += RPCRT4_strcopyW(data, NetworkAddr); data = escape_string_binding_componentW(data, NetworkAddr);
} }
if ((Endpoint && *Endpoint) || if ((Endpoint && *Endpoint) ||
(Options && *Options)) { (Options && *Options)) {
*data++ = '['; *data++ = '[';
if (Endpoint && *Endpoint) { if (Endpoint && *Endpoint) {
data += RPCRT4_strcopyW(data, Endpoint); data = escape_string_binding_componentW(data, Endpoint);
if (Options && *Options) *data++ = ','; if (Options && *Options) *data++ = ',';
} }
if (Options && *Options) { if (Options && *Options) {
data += RPCRT4_strcopyW(data, Options); data = escape_string_binding_componentW(data, Options);
} }
*data++ = ']'; *data++ = ']';
} }
@ -466,8 +566,9 @@ RPC_STATUS WINAPI RpcStringBindingParseA( RPC_CSTR StringBinding, RPC_CSTR *ObjU
RPC_CSTR *Protseq, RPC_CSTR *NetworkAddr, RPC_CSTR *Protseq, RPC_CSTR *NetworkAddr,
RPC_CSTR *Endpoint, RPC_CSTR *Options) RPC_CSTR *Endpoint, RPC_CSTR *Options)
{ {
CHAR *data, *next; const unsigned char *data, *next;
static const char ep_opt[] = "endpoint="; static const char ep_opt[] = "endpoint=";
BOOL endpoint_already_found = FALSE;
TRACE("(%s,%p,%p,%p,%p,%p)\n", debugstr_a((char*)StringBinding), TRACE("(%s,%p,%p,%p,%p,%p)\n", debugstr_a((char*)StringBinding),
ObjUuid, Protseq, NetworkAddr, Endpoint, Options); ObjUuid, Protseq, NetworkAddr, Endpoint, Options);
@ -478,57 +579,75 @@ RPC_STATUS WINAPI RpcStringBindingParseA( RPC_CSTR StringBinding, RPC_CSTR *ObjU
if (Endpoint) *Endpoint = NULL; if (Endpoint) *Endpoint = NULL;
if (Options) *Options = NULL; if (Options) *Options = NULL;
data = (char*) StringBinding; data = StringBinding;
next = strchr(data, '@'); next = string_binding_find_delimiter(data, '@');
if (next) { if (next) {
if (ObjUuid) *ObjUuid = (unsigned char*)RPCRT4_strndupA(data, next - data); UUID uuid;
RPC_STATUS status;
RPC_CSTR str_uuid = unescape_string_binding_component(data, next - data);
status = UuidFromStringA(str_uuid, &uuid);
if (status != RPC_S_OK) {
HeapFree(GetProcessHeap(), 0, str_uuid);
return status;
}
if (ObjUuid)
*ObjUuid = str_uuid;
else
HeapFree(GetProcessHeap(), 0, str_uuid);
data = next+1; data = next+1;
} }
next = strchr(data, ':'); next = string_binding_find_delimiter(data, ':');
if (next) { if (next) {
if (Protseq) *Protseq = (unsigned char*)RPCRT4_strndupA(data, next - data); if (Protseq) *Protseq = unescape_string_binding_component(data, next - data);
data = next+1; data = next+1;
} }
next = strchr(data, '['); next = string_binding_find_delimiter(data, '[');
if (next) { if (next) {
CHAR *close, *opt; const unsigned char *close;
RPC_CSTR opt;
if (NetworkAddr) *NetworkAddr = (unsigned char*)RPCRT4_strndupA(data, next - data); if (NetworkAddr) *NetworkAddr = unescape_string_binding_component(data, next - data);
data = next+1; data = next+1;
close = strchr(data, ']'); close = string_binding_find_delimiter(data, ']');
if (!close) goto fail; if (!close) goto fail;
/* tokenize options */ /* tokenize options */
while (data < close) { while (data < close) {
next = strchr(data, ','); next = string_binding_find_delimiter(data, ',');
if (!next || next > close) next = close; if (!next || next > close) next = close;
/* FIXME: this is kind of inefficient */ /* FIXME: this is kind of inefficient */
opt = RPCRT4_strndupA(data, next - data); opt = unescape_string_binding_component(data, next - data);
data = next+1; data = next+1;
/* parse option */ /* parse option */
next = strchr(opt, '='); next = string_binding_find_delimiter(opt, '=');
if (!next) { if (!next) {
/* not an option, must be an endpoint */ /* not an option, must be an endpoint */
if (*Endpoint) goto fail; if (endpoint_already_found) goto fail;
*Endpoint = (unsigned char*) opt; if (Endpoint) *Endpoint = opt;
else HeapFree(GetProcessHeap(), 0, opt);
endpoint_already_found = TRUE;
} else { } else {
if (strncmp(opt, ep_opt, strlen(ep_opt)) == 0) { if (strncmp((const char *)opt, ep_opt, strlen(ep_opt)) == 0) {
/* endpoint option */ /* endpoint option */
if (*Endpoint) goto fail; if (endpoint_already_found) goto fail;
*Endpoint = (unsigned char*) RPCRT4_strdupA(next+1); if (Endpoint) *Endpoint = unescape_string_binding_component(next+1, -1);
HeapFree(GetProcessHeap(), 0, opt); HeapFree(GetProcessHeap(), 0, opt);
endpoint_already_found = TRUE;
} else { } else {
/* network option */ /* network option */
if (*Options) { if (Options) {
/* FIXME: this is kind of inefficient */ if (*Options) {
*Options = (unsigned char*) RPCRT4_strconcatA( (char*)*Options, opt); /* FIXME: this is kind of inefficient */
*Options = (unsigned char*) RPCRT4_strconcatA( (char*)*Options, (char *)opt);
HeapFree(GetProcessHeap(), 0, opt);
} else
*Options = opt;
} else
HeapFree(GetProcessHeap(), 0, opt); HeapFree(GetProcessHeap(), 0, opt);
} else
*Options = (unsigned char*) opt;
} }
} }
} }
@ -537,7 +656,7 @@ RPC_STATUS WINAPI RpcStringBindingParseA( RPC_CSTR StringBinding, RPC_CSTR *ObjU
if (*data) goto fail; if (*data) goto fail;
} }
else if (NetworkAddr) else if (NetworkAddr)
*NetworkAddr = (unsigned char*)RPCRT4_strdupA(data); *NetworkAddr = unescape_string_binding_component(data, -1);
return RPC_S_OK; return RPC_S_OK;
@ -557,8 +676,9 @@ RPC_STATUS WINAPI RpcStringBindingParseW( RPC_WSTR StringBinding, RPC_WSTR *ObjU
RPC_WSTR *Protseq, RPC_WSTR *NetworkAddr, RPC_WSTR *Protseq, RPC_WSTR *NetworkAddr,
RPC_WSTR *Endpoint, RPC_WSTR *Options) RPC_WSTR *Endpoint, RPC_WSTR *Options)
{ {
WCHAR *data, *next; const WCHAR *data, *next;
static const WCHAR ep_opt[] = {'e','n','d','p','o','i','n','t','=',0}; static const WCHAR ep_opt[] = {'e','n','d','p','o','i','n','t','=',0};
BOOL endpoint_already_found = FALSE;
TRACE("(%s,%p,%p,%p,%p,%p)\n", debugstr_w(StringBinding), TRACE("(%s,%p,%p,%p,%p,%p)\n", debugstr_w(StringBinding),
ObjUuid, Protseq, NetworkAddr, Endpoint, Options); ObjUuid, Protseq, NetworkAddr, Endpoint, Options);
@ -571,55 +691,73 @@ RPC_STATUS WINAPI RpcStringBindingParseW( RPC_WSTR StringBinding, RPC_WSTR *ObjU
data = StringBinding; data = StringBinding;
next = strchrW(data, '@'); next = string_binding_find_delimiterW(data, '@');
if (next) { if (next) {
if (ObjUuid) *ObjUuid = RPCRT4_strndupW(data, next - data); UUID uuid;
RPC_STATUS status;
RPC_WSTR str_uuid = unescape_string_binding_componentW(data, next - data);
status = UuidFromStringW(str_uuid, &uuid);
if (status != RPC_S_OK) {
HeapFree(GetProcessHeap(), 0, str_uuid);
return status;
}
if (ObjUuid)
*ObjUuid = str_uuid;
else
HeapFree(GetProcessHeap(), 0, str_uuid);
data = next+1; data = next+1;
} }
next = strchrW(data, ':'); next = string_binding_find_delimiterW(data, ':');
if (next) { if (next) {
if (Protseq) *Protseq = RPCRT4_strndupW(data, next - data); if (Protseq) *Protseq = unescape_string_binding_componentW(data, next - data);
data = next+1; data = next+1;
} }
next = strchrW(data, '['); next = string_binding_find_delimiterW(data, '[');
if (next) { if (next) {
WCHAR *close, *opt; const WCHAR *close;
RPC_WSTR opt;
if (NetworkAddr) *NetworkAddr = RPCRT4_strndupW(data, next - data); if (NetworkAddr) *NetworkAddr = unescape_string_binding_componentW(data, next - data);
data = next+1; data = next+1;
close = strchrW(data, ']'); close = string_binding_find_delimiterW(data, ']');
if (!close) goto fail; if (!close) goto fail;
/* tokenize options */ /* tokenize options */
while (data < close) { while (data < close) {
next = strchrW(data, ','); next = string_binding_find_delimiterW(data, ',');
if (!next || next > close) next = close; if (!next || next > close) next = close;
/* FIXME: this is kind of inefficient */ /* FIXME: this is kind of inefficient */
opt = RPCRT4_strndupW(data, next - data); opt = unescape_string_binding_componentW(data, next - data);
data = next+1; data = next+1;
/* parse option */ /* parse option */
next = strchrW(opt, '='); next = string_binding_find_delimiterW(opt, '=');
if (!next) { if (!next) {
/* not an option, must be an endpoint */ /* not an option, must be an endpoint */
if (*Endpoint) goto fail; if (endpoint_already_found) goto fail;
*Endpoint = opt; if (Endpoint) *Endpoint = opt;
else HeapFree(GetProcessHeap(), 0, opt);
endpoint_already_found = TRUE;
} else { } else {
if (strncmpW(opt, ep_opt, strlenW(ep_opt)) == 0) { if (strncmpW(opt, ep_opt, strlenW(ep_opt)) == 0) {
/* endpoint option */ /* endpoint option */
if (*Endpoint) goto fail; if (endpoint_already_found) goto fail;
*Endpoint = RPCRT4_strdupW(next+1); if (Endpoint) *Endpoint = unescape_string_binding_componentW(next+1, -1);
HeapFree(GetProcessHeap(), 0, opt); HeapFree(GetProcessHeap(), 0, opt);
endpoint_already_found = TRUE;
} else { } else {
/* network option */ /* network option */
if (*Options) { if (Options) {
/* FIXME: this is kind of inefficient */ if (*Options) {
*Options = RPCRT4_strconcatW(*Options, opt); /* FIXME: this is kind of inefficient */
*Options = RPCRT4_strconcatW(*Options, opt);
HeapFree(GetProcessHeap(), 0, opt);
} else
*Options = opt;
} else
HeapFree(GetProcessHeap(), 0, opt); HeapFree(GetProcessHeap(), 0, opt);
} else
*Options = opt;
} }
} }
} }
@ -627,7 +765,7 @@ RPC_STATUS WINAPI RpcStringBindingParseW( RPC_WSTR StringBinding, RPC_WSTR *ObjU
data = close+1; data = close+1;
if (*data) goto fail; if (*data) goto fail;
} else if (NetworkAddr) } else if (NetworkAddr)
*NetworkAddr = RPCRT4_strdupW(data); *NetworkAddr = unescape_string_binding_componentW(data, -1);
return RPC_S_OK; return RPC_S_OK;
@ -647,7 +785,7 @@ RPC_STATUS WINAPI RpcBindingFree( RPC_BINDING_HANDLE* Binding )
{ {
RPC_STATUS status; RPC_STATUS status;
TRACE("(%p) = %p\n", Binding, *Binding); TRACE("(%p) = %p\n", Binding, *Binding);
status = RPCRT4_DestroyBinding(*Binding); status = RPCRT4_ReleaseBinding(*Binding);
if (status == RPC_S_OK) *Binding = 0; if (status == RPC_S_OK) *Binding = 0;
return status; return status;
} }
@ -677,10 +815,10 @@ RPC_STATUS WINAPI RpcBindingInqObject( RPC_BINDING_HANDLE Binding, UUID* ObjectU
RpcBinding* bind = (RpcBinding*)Binding; RpcBinding* bind = (RpcBinding*)Binding;
TRACE("(%p,%p) = %s\n", Binding, ObjectUuid, debugstr_guid(&bind->ObjectUuid)); TRACE("(%p,%p) = %s\n", Binding, ObjectUuid, debugstr_guid(&bind->ObjectUuid));
memcpy(ObjectUuid, &bind->ObjectUuid, sizeof(UUID)); *ObjectUuid = bind->ObjectUuid;
return RPC_S_OK; return RPC_S_OK;
} }
/*********************************************************************** /***********************************************************************
* RpcBindingSetObject (RPCRT4.@) * RpcBindingSetObject (RPCRT4.@)
*/ */
@ -713,8 +851,8 @@ RPC_STATUS WINAPI RpcBindingFromStringBindingA( RPC_CSTR StringBinding, RPC_BIND
if (ret == RPC_S_OK) if (ret == RPC_S_OK)
ret = RPCRT4_CreateBindingA(&bind, FALSE, (char*)Protseq); ret = RPCRT4_CreateBindingA(&bind, FALSE, (char*)Protseq);
if (ret == RPC_S_OK) if (ret != RPC_S_OK) return ret;
ret = RPCRT4_SetBindingObject(bind, &Uuid); ret = RPCRT4_SetBindingObject(bind, &Uuid);
if (ret == RPC_S_OK) if (ret == RPC_S_OK)
ret = RPCRT4_CompleteBindingA(bind, (char*)NetworkAddr, (char*)Endpoint, (char*)Options); ret = RPCRT4_CompleteBindingA(bind, (char*)NetworkAddr, (char*)Endpoint, (char*)Options);
@ -727,7 +865,7 @@ RPC_STATUS WINAPI RpcBindingFromStringBindingA( RPC_CSTR StringBinding, RPC_BIND
if (ret == RPC_S_OK) if (ret == RPC_S_OK)
*Binding = (RPC_BINDING_HANDLE)bind; *Binding = (RPC_BINDING_HANDLE)bind;
else else
RPCRT4_DestroyBinding(bind); RPCRT4_ReleaseBinding(bind);
return ret; return ret;
} }
@ -752,8 +890,8 @@ RPC_STATUS WINAPI RpcBindingFromStringBindingW( RPC_WSTR StringBinding, RPC_BIND
if (ret == RPC_S_OK) if (ret == RPC_S_OK)
ret = RPCRT4_CreateBindingW(&bind, FALSE, Protseq); ret = RPCRT4_CreateBindingW(&bind, FALSE, Protseq);
if (ret == RPC_S_OK) if (ret != RPC_S_OK) return ret;
ret = RPCRT4_SetBindingObject(bind, &Uuid); ret = RPCRT4_SetBindingObject(bind, &Uuid);
if (ret == RPC_S_OK) if (ret == RPC_S_OK)
ret = RPCRT4_CompleteBindingW(bind, NetworkAddr, Endpoint, Options); ret = RPCRT4_CompleteBindingW(bind, NetworkAddr, Endpoint, Options);
@ -766,7 +904,7 @@ RPC_STATUS WINAPI RpcBindingFromStringBindingW( RPC_WSTR StringBinding, RPC_BIND
if (ret == RPC_S_OK) if (ret == RPC_S_OK)
*Binding = (RPC_BINDING_HANDLE)bind; *Binding = (RPC_BINDING_HANDLE)bind;
else else
RPCRT4_DestroyBinding(bind); RPCRT4_ReleaseBinding(bind);
return ret; return ret;
} }
@ -782,8 +920,13 @@ RPC_STATUS WINAPI RpcBindingToStringBindingA( RPC_BINDING_HANDLE Binding, RPC_CS
TRACE("(%p,%p)\n", Binding, StringBinding); TRACE("(%p,%p)\n", Binding, StringBinding);
ret = UuidToStringA(&bind->ObjectUuid, &ObjectUuid); if (UuidIsNil(&bind->ObjectUuid, &ret))
if (ret != RPC_S_OK) return ret; ObjectUuid = NULL;
else
{
ret = UuidToStringA(&bind->ObjectUuid, &ObjectUuid);
if (ret != RPC_S_OK) return ret;
}
ret = RpcStringBindingComposeA(ObjectUuid, (unsigned char*)bind->Protseq, (unsigned char*) bind->NetworkAddr, ret = RpcStringBindingComposeA(ObjectUuid, (unsigned char*)bind->Protseq, (unsigned char*) bind->NetworkAddr,
(unsigned char*) bind->Endpoint, NULL, StringBinding); (unsigned char*) bind->Endpoint, NULL, StringBinding);
@ -807,6 +950,17 @@ RPC_STATUS WINAPI RpcBindingToStringBindingW( RPC_BINDING_HANDLE Binding, RPC_WS
return ret; return ret;
} }
/***********************************************************************
* I_RpcBindingInqTransportType (RPCRT4.@)
*/
RPC_STATUS WINAPI I_RpcBindingInqTransportType( RPC_BINDING_HANDLE Binding, unsigned int * Type )
{
FIXME( "(%p,%p): stub\n", Binding, Type);
*Type = TRANSPORT_TYPE_LPC;
return RPC_S_OK;
}
/*********************************************************************** /***********************************************************************
* I_RpcBindingSetAsync (RPCRT4.@) * I_RpcBindingSetAsync (RPCRT4.@)
* NOTES * NOTES
@ -858,6 +1012,23 @@ RPC_STATUS RPC_ENTRY RpcBindingCopy(
return RPC_S_OK; return RPC_S_OK;
} }
/***********************************************************************
* RpcBindingReset (RPCRT4.@)
*/
RPC_STATUS RPC_ENTRY RpcBindingReset(RPC_BINDING_HANDLE Binding)
{
RpcBinding *bind = Binding;
TRACE("(%p)\n", Binding);
RPCRT4_strfree(bind->Endpoint);
bind->Endpoint = NULL;
if (bind->Assoc) RpcAssoc_Release(bind->Assoc);
bind->Assoc = NULL;
return RPC_S_OK;
}
/*********************************************************************** /***********************************************************************
* RpcImpersonateClient (RPCRT4.@) * RpcImpersonateClient (RPCRT4.@)
* *
@ -937,6 +1108,7 @@ static RPC_STATUS RpcAuthInfo_Create(ULONG AuthnLevel, ULONG AuthnSvc,
AuthInfo->exp = exp; AuthInfo->exp = exp;
AuthInfo->cbMaxToken = cbMaxToken; AuthInfo->cbMaxToken = cbMaxToken;
AuthInfo->identity = identity; AuthInfo->identity = identity;
AuthInfo->server_principal_name = NULL;
/* duplicate the SEC_WINNT_AUTH_IDENTITY structure, if applicable, to /* duplicate the SEC_WINNT_AUTH_IDENTITY structure, if applicable, to
* enable better matching in RpcAuthInfo_IsEqual */ * enable better matching in RpcAuthInfo_IsEqual */
@ -967,9 +1139,9 @@ static RPC_STATUS RpcAuthInfo_Create(ULONG AuthnLevel, ULONG AuthnSvc,
AuthInfo->nt_identity->Password = RPCRT4_strndupAtoW((const char *)nt_identity->Password, nt_identity->PasswordLength); AuthInfo->nt_identity->Password = RPCRT4_strndupAtoW((const char *)nt_identity->Password, nt_identity->PasswordLength);
AuthInfo->nt_identity->PasswordLength = nt_identity->PasswordLength; AuthInfo->nt_identity->PasswordLength = nt_identity->PasswordLength;
if (!AuthInfo->nt_identity->User || if ((nt_identity->User && !AuthInfo->nt_identity->User) ||
!AuthInfo->nt_identity->Domain || (nt_identity->Domain && !AuthInfo->nt_identity->Domain) ||
!AuthInfo->nt_identity->Password) (nt_identity->Password && !AuthInfo->nt_identity->Password))
{ {
HeapFree(GetProcessHeap(), 0, AuthInfo->nt_identity->User); HeapFree(GetProcessHeap(), 0, AuthInfo->nt_identity->User);
HeapFree(GetProcessHeap(), 0, AuthInfo->nt_identity->Domain); HeapFree(GetProcessHeap(), 0, AuthInfo->nt_identity->Domain);
@ -1004,6 +1176,7 @@ ULONG RpcAuthInfo_Release(RpcAuthInfo *AuthInfo)
HeapFree(GetProcessHeap(), 0, AuthInfo->nt_identity->Password); HeapFree(GetProcessHeap(), 0, AuthInfo->nt_identity->Password);
HeapFree(GetProcessHeap(), 0, AuthInfo->nt_identity); HeapFree(GetProcessHeap(), 0, AuthInfo->nt_identity);
} }
HeapFree(GetProcessHeap(), 0, AuthInfo->server_principal_name);
HeapFree(GetProcessHeap(), 0, AuthInfo); HeapFree(GetProcessHeap(), 0, AuthInfo);
} }
@ -1390,7 +1563,8 @@ RpcBindingSetAuthInfoExA( RPC_BINDING_HANDLE Binding, RPC_CSTR ServerPrincName,
return RPC_S_UNKNOWN_AUTHN_LEVEL; return RPC_S_UNKNOWN_AUTHN_LEVEL;
} }
if (AuthzSvr) /* RPC_C_AUTHN_WINNT ignores the AuthzSvr parameter */
if (AuthzSvr && AuthnSvc != RPC_C_AUTHN_WINNT)
{ {
FIXME("unsupported AuthzSvr %u\n", AuthzSvr); FIXME("unsupported AuthzSvr %u\n", AuthzSvr);
return RPC_S_UNKNOWN_AUTHZ_SERVICE; return RPC_S_UNKNOWN_AUTHZ_SERVICE;
@ -1415,19 +1589,32 @@ RpcBindingSetAuthInfoExA( RPC_BINDING_HANDLE Binding, RPC_CSTR ServerPrincName,
} }
TRACE("found package %s for service %u\n", packages[i].Name, AuthnSvc); TRACE("found package %s for service %u\n", packages[i].Name, AuthnSvc);
r = AcquireCredentialsHandleA((SEC_CHAR *)ServerPrincName, packages[i].Name, SECPKG_CRED_OUTBOUND, NULL, r = AcquireCredentialsHandleA(NULL, packages[i].Name, SECPKG_CRED_OUTBOUND, NULL,
AuthIdentity, NULL, NULL, &cred, &exp); AuthIdentity, NULL, NULL, &cred, &exp);
cbMaxToken = packages[i].cbMaxToken; cbMaxToken = packages[i].cbMaxToken;
FreeContextBuffer(packages); FreeContextBuffer(packages);
if (r == ERROR_SUCCESS) if (r == ERROR_SUCCESS)
{ {
if (bind->AuthInfo) RpcAuthInfo_Release(bind->AuthInfo); RpcAuthInfo *new_auth_info;
bind->AuthInfo = NULL;
r = RpcAuthInfo_Create(AuthnLevel, AuthnSvc, cred, exp, cbMaxToken, r = RpcAuthInfo_Create(AuthnLevel, AuthnSvc, cred, exp, cbMaxToken,
AuthIdentity, &bind->AuthInfo); AuthIdentity, &new_auth_info);
if (r != RPC_S_OK) if (r == RPC_S_OK)
{
new_auth_info->server_principal_name = RPCRT4_strdupAtoW((char *)ServerPrincName);
if (new_auth_info->server_principal_name)
{
if (bind->AuthInfo) RpcAuthInfo_Release(bind->AuthInfo);
bind->AuthInfo = new_auth_info;
}
else
{
RpcAuthInfo_Release(new_auth_info);
r = ERROR_OUTOFMEMORY;
}
}
else
FreeCredentialsHandle(&cred); FreeCredentialsHandle(&cred);
return RPC_S_OK; return r;
} }
else else
{ {
@ -1506,7 +1693,8 @@ RpcBindingSetAuthInfoExW( RPC_BINDING_HANDLE Binding, RPC_WSTR ServerPrincName,
return RPC_S_UNKNOWN_AUTHN_LEVEL; return RPC_S_UNKNOWN_AUTHN_LEVEL;
} }
if (AuthzSvr) /* RPC_C_AUTHN_WINNT ignores the AuthzSvr parameter */
if (AuthzSvr && AuthnSvc != RPC_C_AUTHN_WINNT)
{ {
FIXME("unsupported AuthzSvr %u\n", AuthzSvr); FIXME("unsupported AuthzSvr %u\n", AuthzSvr);
return RPC_S_UNKNOWN_AUTHZ_SERVICE; return RPC_S_UNKNOWN_AUTHZ_SERVICE;
@ -1515,7 +1703,7 @@ RpcBindingSetAuthInfoExW( RPC_BINDING_HANDLE Binding, RPC_WSTR ServerPrincName,
r = EnumerateSecurityPackagesW(&package_count, &packages); r = EnumerateSecurityPackagesW(&package_count, &packages);
if (r != SEC_E_OK) if (r != SEC_E_OK)
{ {
ERR("EnumerateSecurityPackagesA failed with error 0x%08x\n", r); ERR("EnumerateSecurityPackagesW failed with error 0x%08x\n", r);
return RPC_S_SEC_PKG_ERROR; return RPC_S_SEC_PKG_ERROR;
} }
@ -1531,23 +1719,36 @@ RpcBindingSetAuthInfoExW( RPC_BINDING_HANDLE Binding, RPC_WSTR ServerPrincName,
} }
TRACE("found package %s for service %u\n", debugstr_w(packages[i].Name), AuthnSvc); TRACE("found package %s for service %u\n", debugstr_w(packages[i].Name), AuthnSvc);
r = AcquireCredentialsHandleW((SEC_WCHAR *)ServerPrincName, packages[i].Name, SECPKG_CRED_OUTBOUND, NULL, r = AcquireCredentialsHandleW(NULL, packages[i].Name, SECPKG_CRED_OUTBOUND, NULL,
AuthIdentity, NULL, NULL, &cred, &exp); AuthIdentity, NULL, NULL, &cred, &exp);
cbMaxToken = packages[i].cbMaxToken; cbMaxToken = packages[i].cbMaxToken;
FreeContextBuffer(packages); FreeContextBuffer(packages);
if (r == ERROR_SUCCESS) if (r == ERROR_SUCCESS)
{ {
if (bind->AuthInfo) RpcAuthInfo_Release(bind->AuthInfo); RpcAuthInfo *new_auth_info;
bind->AuthInfo = NULL;
r = RpcAuthInfo_Create(AuthnLevel, AuthnSvc, cred, exp, cbMaxToken, r = RpcAuthInfo_Create(AuthnLevel, AuthnSvc, cred, exp, cbMaxToken,
AuthIdentity, &bind->AuthInfo); AuthIdentity, &new_auth_info);
if (r != RPC_S_OK) if (r == RPC_S_OK)
{
new_auth_info->server_principal_name = RPCRT4_strdupW(ServerPrincName);
if (!ServerPrincName || new_auth_info->server_principal_name)
{
if (bind->AuthInfo) RpcAuthInfo_Release(bind->AuthInfo);
bind->AuthInfo = new_auth_info;
}
else
{
RpcAuthInfo_Release(new_auth_info);
r = ERROR_OUTOFMEMORY;
}
}
else
FreeCredentialsHandle(&cred); FreeCredentialsHandle(&cred);
return RPC_S_OK; return r;
} }
else else
{ {
ERR("AcquireCredentialsHandleA failed with error 0x%08x\n", r); ERR("AcquireCredentialsHandleW failed with error 0x%08x\n", r);
return RPC_S_SEC_PKG_ERROR; return RPC_S_SEC_PKG_ERROR;
} }
} }
@ -1579,8 +1780,8 @@ RpcBindingSetAuthInfoW( RPC_BINDING_HANDLE Binding, RPC_WSTR ServerPrincName, UL
/*********************************************************************** /***********************************************************************
* RpcBindingSetOption (RPCRT4.@) * RpcBindingSetOption (RPCRT4.@)
*/ */
RPC_STATUS WINAPI RpcBindingSetOption(RPC_BINDING_HANDLE BindingHandle, ULONG Option, ULONG OptionValue) RPC_STATUS WINAPI RpcBindingSetOption(RPC_BINDING_HANDLE BindingHandle, ULONG Option, ULONG_PTR OptionValue)
{ {
FIXME("(%p, %d, %d): stub\n", BindingHandle, Option, OptionValue); FIXME("(%p, %d, %ld): stub\n", BindingHandle, Option, OptionValue);
return RPC_S_OK; return RPC_S_OK;
} }

View file

@ -145,8 +145,8 @@ RPC_STATUS RPCRT4_SpawnConnection(RpcConnection** Connection, RpcConnection* Old
RPC_STATUS RPCRT4_ResolveBinding(RpcBinding* Binding, LPCSTR Endpoint); RPC_STATUS RPCRT4_ResolveBinding(RpcBinding* Binding, LPCSTR Endpoint);
RPC_STATUS RPCRT4_SetBindingObject(RpcBinding* Binding, const UUID* ObjectUuid); RPC_STATUS RPCRT4_SetBindingObject(RpcBinding* Binding, const UUID* ObjectUuid);
RPC_STATUS RPCRT4_MakeBinding(RpcBinding** Binding, RpcConnection* Connection); RPC_STATUS RPCRT4_MakeBinding(RpcBinding** Binding, RpcConnection* Connection);
RPC_STATUS RPCRT4_ExportBinding(RpcBinding** Binding, RpcBinding* OldBinding); void RPCRT4_AddRefBinding(RpcBinding* Binding);
RPC_STATUS RPCRT4_DestroyBinding(RpcBinding* Binding); RPC_STATUS RPCRT4_ReleaseBinding(RpcBinding* Binding);
RPC_STATUS RPCRT4_OpenBinding(RpcBinding* Binding, RpcConnection** Connection, RPC_STATUS RPCRT4_OpenBinding(RpcBinding* Binding, RpcConnection** Connection,
const RPC_SYNTAX_IDENTIFIER *TransferSyntax, const RPC_SYNTAX_IDENTIFIER *InterfaceId); const RPC_SYNTAX_IDENTIFIER *TransferSyntax, const RPC_SYNTAX_IDENTIFIER *InterfaceId);
RPC_STATUS RPCRT4_CloseBinding(RpcBinding* Binding, RpcConnection* Connection); RPC_STATUS RPCRT4_CloseBinding(RpcBinding* Binding, RpcConnection* Connection);

View file

@ -22,8 +22,6 @@
#ifndef __WINE_RPC_DEFS_H #ifndef __WINE_RPC_DEFS_H
#define __WINE_RPC_DEFS_H #define __WINE_RPC_DEFS_H
/* info from http://www.microsoft.com/msj/0398/dcomtextfigs.htm */
typedef struct typedef struct
{ {
unsigned char rpc_ver; /* RPC major version (5) */ unsigned char rpc_ver; /* RPC major version (5) */

View file

@ -27,6 +27,7 @@
#include "windef.h" #include "windef.h"
#include "winbase.h" #include "winbase.h"
#include "winerror.h" #include "winerror.h"
#include "winuser.h"
#include "rpc.h" #include "rpc.h"
#include "rpcndr.h" #include "rpcndr.h"
@ -195,8 +196,8 @@ RpcPktHdr *RPCRT4_BuildBindHeader(unsigned long DataRepresentation,
header->bind.assoc_gid = AssocGroupId; header->bind.assoc_gid = AssocGroupId;
header->bind.num_elements = 1; header->bind.num_elements = 1;
header->bind.num_syntaxes = 1; header->bind.num_syntaxes = 1;
memcpy(&header->bind.abstract, AbstractId, sizeof(RPC_SYNTAX_IDENTIFIER)); header->bind.abstract = *AbstractId;
memcpy(&header->bind.transfer, TransferId, sizeof(RPC_SYNTAX_IDENTIFIER)); header->bind.transfer = *TransferId;
return header; return header;
} }
@ -277,7 +278,7 @@ RpcPktHdr *RPCRT4_BuildBindAckHeader(unsigned long DataRepresentation,
results->results[0].result = Result; results->results[0].result = Result;
results->results[0].reason = Reason; results->results[0].reason = Reason;
transfer_id = (RPC_SYNTAX_IDENTIFIER*)(results + 1); transfer_id = (RPC_SYNTAX_IDENTIFIER*)(results + 1);
memcpy(transfer_id, TransferId, sizeof(RPC_SYNTAX_IDENTIFIER)); *transfer_id = *TransferId;
return header; return header;
} }
@ -436,13 +437,13 @@ static RPC_STATUS RPCRT4_SecurePacket(RpcConnection *Connection,
} }
/*********************************************************************** /***********************************************************************
* RPCRT4_SendAuth (internal) * RPCRT4_SendWithAuth (internal)
* *
* Transmit a packet with authorization data over connection in acceptable fragments. * Transmit a packet with authorization data over connection in acceptable fragments.
*/ */
static RPC_STATUS RPCRT4_SendAuth(RpcConnection *Connection, RpcPktHdr *Header, static RPC_STATUS RPCRT4_SendWithAuth(RpcConnection *Connection, RpcPktHdr *Header,
void *Buffer, unsigned int BufferLength, void *Buffer, unsigned int BufferLength,
const void *Auth, unsigned int AuthLength) const void *Auth, unsigned int AuthLength)
{ {
PUCHAR buffer_pos; PUCHAR buffer_pos;
DWORD hdr_size; DWORD hdr_size;
@ -580,10 +581,10 @@ static RPC_STATUS RPCRT4_ClientAuthorize(RpcConnection *conn, SecBuffer *in,
inp_desc.pBuffers = in; inp_desc.pBuffers = in;
inp_desc.ulVersion = 0; inp_desc.ulVersion = 0;
r = InitializeSecurityContextA(&conn->AuthInfo->cred, in ? &conn->ctx : NULL, r = InitializeSecurityContextW(&conn->AuthInfo->cred, in ? &conn->ctx : NULL,
NULL, context_req, 0, SECURITY_NETWORK_DREP, in ? NULL : conn->AuthInfo->server_principal_name, context_req, 0,
in ? &inp_desc : NULL, 0, &conn->ctx, &out_desc, &conn->attr, SECURITY_NETWORK_DREP, in ? &inp_desc : NULL, 0, &conn->ctx,
&conn->exp); &out_desc, &conn->attr, &conn->exp);
if (FAILED(r)) if (FAILED(r))
{ {
WARN("InitializeSecurityContext failed with error 0x%08x\n", r); WARN("InitializeSecurityContext failed with error 0x%08x\n", r);
@ -630,8 +631,8 @@ failed:
/*********************************************************************** /***********************************************************************
* RPCRT4_AuthorizeBinding (internal) * RPCRT4_AuthorizeBinding (internal)
*/ */
static RPC_STATUS RPCRT_AuthorizeConnection(RpcConnection* conn, RPC_STATUS RPCRT4_AuthorizeConnection(RpcConnection* conn, BYTE *challenge,
BYTE *challenge, ULONG count) ULONG count)
{ {
SecBuffer inp, out; SecBuffer inp, out;
RpcPktHdr *resp_hdr; RpcPktHdr *resp_hdr;
@ -650,7 +651,7 @@ static RPC_STATUS RPCRT_AuthorizeConnection(RpcConnection* conn,
if (!resp_hdr) if (!resp_hdr)
return E_OUTOFMEMORY; return E_OUTOFMEMORY;
status = RPCRT4_SendAuth(conn, resp_hdr, NULL, 0, out.pvBuffer, out.cbBuffer); status = RPCRT4_SendWithAuth(conn, resp_hdr, NULL, 0, out.pvBuffer, out.cbBuffer);
HeapFree(GetProcessHeap(), 0, out.pvBuffer); HeapFree(GetProcessHeap(), 0, out.pvBuffer);
RPCRT4_FreeHeader(resp_hdr); RPCRT4_FreeHeader(resp_hdr);
@ -671,40 +672,65 @@ RPC_STATUS RPCRT4_Send(RpcConnection *Connection, RpcPktHdr *Header,
if (!Connection->AuthInfo || SecIsValidHandle(&Connection->ctx)) if (!Connection->AuthInfo || SecIsValidHandle(&Connection->ctx))
{ {
return RPCRT4_SendAuth(Connection, Header, Buffer, BufferLength, NULL, 0); return RPCRT4_SendWithAuth(Connection, Header, Buffer, BufferLength, NULL, 0);
} }
/* tack on a negotiate packet */ /* tack on a negotiate packet */
RPCRT4_ClientAuthorize(Connection, NULL, &out); r = RPCRT4_ClientAuthorize(Connection, NULL, &out);
r = RPCRT4_SendAuth(Connection, Header, Buffer, BufferLength, out.pvBuffer, out.cbBuffer); if (r == RPC_S_OK)
HeapFree(GetProcessHeap(), 0, out.pvBuffer); {
r = RPCRT4_SendWithAuth(Connection, Header, Buffer, BufferLength, out.pvBuffer, out.cbBuffer);
HeapFree(GetProcessHeap(), 0, out.pvBuffer);
}
return r; return r;
} }
/* validates version and frag_len fields */
RPC_STATUS RPCRT4_ValidateCommonHeader(const RpcPktCommonHdr *hdr)
{
DWORD hdr_length;
/* verify if the header really makes sense */
if (hdr->rpc_ver != RPC_VER_MAJOR ||
hdr->rpc_ver_minor != RPC_VER_MINOR)
{
WARN("unhandled packet version\n");
return RPC_S_PROTOCOL_ERROR;
}
hdr_length = RPCRT4_GetHeaderSize((const RpcPktHdr*)hdr);
if (hdr_length == 0)
{
WARN("header length == 0\n");
return RPC_S_PROTOCOL_ERROR;
}
if (hdr->frag_len < hdr_length)
{
WARN("bad frag length %d\n", hdr->frag_len);
return RPC_S_PROTOCOL_ERROR;
}
return RPC_S_OK;
}
/*********************************************************************** /***********************************************************************
* RPCRT4_Receive (internal) * RPCRT4_receive_fragment (internal)
* *
* Receive a packet from connection and merge the fragments. * Receive a fragment from a connection.
*/ */
RPC_STATUS RPCRT4_Receive(RpcConnection *Connection, RpcPktHdr **Header, RPC_STATUS RPCRT4_receive_fragment(RpcConnection *Connection, RpcPktHdr **Header, void **Payload)
PRPC_MESSAGE pMsg)
{ {
RPC_STATUS status; RPC_STATUS status;
DWORD hdr_length; DWORD hdr_length;
LONG dwRead; LONG dwRead;
unsigned short first_flag;
unsigned long data_length;
unsigned long buffer_length;
unsigned long auth_length;
unsigned char *auth_data = NULL;
RpcPktCommonHdr common_hdr; RpcPktCommonHdr common_hdr;
*Header = NULL; *Header = NULL;
*Payload = NULL;
TRACE("(%p, %p, %p)\n", Connection, Header, pMsg); TRACE("(%p, %p, %p)\n", Connection, Header, Payload);
RPCRT4_SetThreadCurrentConnection(Connection);
/* read packet common header */ /* read packet common header */
dwRead = rpcrt4_conn_read(Connection, &common_hdr, sizeof(common_hdr)); dwRead = rpcrt4_conn_read(Connection, &common_hdr, sizeof(common_hdr));
@ -714,13 +740,8 @@ RPC_STATUS RPCRT4_Receive(RpcConnection *Connection, RpcPktHdr **Header,
goto fail; goto fail;
} }
/* verify if the header really makes sense */ status = RPCRT4_ValidateCommonHeader(&common_hdr);
if (common_hdr.rpc_ver != RPC_VER_MAJOR || if (status != RPC_S_OK) goto fail;
common_hdr.rpc_ver_minor != RPC_VER_MINOR) {
WARN("unhandled packet version\n");
status = RPC_S_PROTOCOL_ERROR;
goto fail;
}
hdr_length = RPCRT4_GetHeaderSize((RpcPktHdr*)&common_hdr); hdr_length = RPCRT4_GetHeaderSize((RpcPktHdr*)&common_hdr);
if (hdr_length == 0) { if (hdr_length == 0) {
@ -740,8 +761,74 @@ RPC_STATUS RPCRT4_Receive(RpcConnection *Connection, RpcPktHdr **Header,
goto fail; goto fail;
} }
if (common_hdr.frag_len - hdr_length)
{
*Payload = HeapAlloc(GetProcessHeap(), 0, common_hdr.frag_len - hdr_length);
if (!*Payload)
{
status = RPC_S_OUT_OF_RESOURCES;
goto fail;
}
dwRead = rpcrt4_conn_read(Connection, *Payload, common_hdr.frag_len - hdr_length);
if (dwRead != common_hdr.frag_len - hdr_length)
{
WARN("bad data length, %d/%d\n", dwRead, common_hdr.frag_len - hdr_length);
status = RPC_S_CALL_FAILED;
goto fail;
}
}
else
*Payload = NULL;
/* success */
status = RPC_S_OK;
fail:
if (status != RPC_S_OK) {
RPCRT4_FreeHeader(*Header);
*Header = NULL;
HeapFree(GetProcessHeap(), 0, *Payload);
*Payload = NULL;
}
return status;
}
/***********************************************************************
* RPCRT4_ReceiveWithAuth (internal)
*
* Receive a packet from connection, merge the fragments and return the auth
* data.
*/
RPC_STATUS RPCRT4_ReceiveWithAuth(RpcConnection *Connection, RpcPktHdr **Header,
PRPC_MESSAGE pMsg,
unsigned char **auth_data_out,
unsigned long *auth_length_out)
{
RPC_STATUS status;
DWORD hdr_length;
unsigned short first_flag;
unsigned long data_length;
unsigned long buffer_length;
unsigned long auth_length = 0;
unsigned char *auth_data = NULL;
RpcPktHdr *CurrentHeader = NULL;
void *payload = NULL;
*Header = NULL;
pMsg->Buffer = NULL;
TRACE("(%p, %p, %p, %p)\n", Connection, Header, pMsg, auth_data_out);
RPCRT4_SetThreadCurrentConnection(Connection);
status = RPCRT4_receive_fragment(Connection, Header, &payload);
if (status != RPC_S_OK) goto fail;
hdr_length = RPCRT4_GetHeaderSize(*Header);
/* read packet body */ /* read packet body */
switch (common_hdr.ptype) { switch ((*Header)->common.ptype) {
case PKT_RESPONSE: case PKT_RESPONSE:
pMsg->BufferLength = (*Header)->response.alloc_hint; pMsg->BufferLength = (*Header)->response.alloc_hint;
break; break;
@ -749,7 +836,7 @@ RPC_STATUS RPCRT4_Receive(RpcConnection *Connection, RpcPktHdr **Header,
pMsg->BufferLength = (*Header)->request.alloc_hint; pMsg->BufferLength = (*Header)->request.alloc_hint;
break; break;
default: default:
pMsg->BufferLength = common_hdr.frag_len - hdr_length - RPC_AUTH_VERIFIER_LEN(&common_hdr); pMsg->BufferLength = (*Header)->common.frag_len - hdr_length - RPC_AUTH_VERIFIER_LEN(&(*Header)->common);
} }
TRACE("buffer length = %u\n", pMsg->BufferLength); TRACE("buffer length = %u\n", pMsg->BufferLength);
@ -762,43 +849,44 @@ RPC_STATUS RPCRT4_Receive(RpcConnection *Connection, RpcPktHdr **Header,
} }
first_flag = RPC_FLG_FIRST; first_flag = RPC_FLG_FIRST;
auth_length = common_hdr.auth_len; auth_length = (*Header)->common.auth_len;
if (auth_length) { if (auth_length) {
auth_data = HeapAlloc(GetProcessHeap(), 0, RPC_AUTH_VERIFIER_LEN(&common_hdr)); auth_data = HeapAlloc(GetProcessHeap(), 0, RPC_AUTH_VERIFIER_LEN(&(*Header)->common));
if (!auth_data) { if (!auth_data) {
status = RPC_S_OUT_OF_RESOURCES; status = RPC_S_OUT_OF_RESOURCES;
goto fail; goto fail;
} }
} }
CurrentHeader = *Header;
buffer_length = 0; buffer_length = 0;
while (TRUE) while (TRUE)
{ {
unsigned int header_auth_len = RPC_AUTH_VERIFIER_LEN(&(*Header)->common); unsigned int header_auth_len = RPC_AUTH_VERIFIER_LEN(&CurrentHeader->common);
/* verify header fields */ /* verify header fields */
if (((*Header)->common.frag_len < hdr_length) || if ((CurrentHeader->common.frag_len < hdr_length) ||
((*Header)->common.frag_len - hdr_length < header_auth_len)) { (CurrentHeader->common.frag_len - hdr_length < header_auth_len)) {
WARN("frag_len %d too small for hdr_length %d and auth_len %d\n", WARN("frag_len %d too small for hdr_length %d and auth_len %d\n",
(*Header)->common.frag_len, hdr_length, header_auth_len); CurrentHeader->common.frag_len, hdr_length, CurrentHeader->common.auth_len);
status = RPC_S_PROTOCOL_ERROR; status = RPC_S_PROTOCOL_ERROR;
goto fail; goto fail;
} }
if ((*Header)->common.auth_len != auth_length) { if (CurrentHeader->common.auth_len != auth_length) {
WARN("auth_len header field changed from %ld to %d\n", WARN("auth_len header field changed from %ld to %d\n",
auth_length, (*Header)->common.auth_len); auth_length, CurrentHeader->common.auth_len);
status = RPC_S_PROTOCOL_ERROR; status = RPC_S_PROTOCOL_ERROR;
goto fail; goto fail;
} }
if (((*Header)->common.flags & RPC_FLG_FIRST) != first_flag) { if ((CurrentHeader->common.flags & RPC_FLG_FIRST) != first_flag) {
TRACE("invalid packet flags\n"); TRACE("invalid packet flags\n");
status = RPC_S_PROTOCOL_ERROR; status = RPC_S_PROTOCOL_ERROR;
goto fail; goto fail;
} }
data_length = (*Header)->common.frag_len - hdr_length - header_auth_len; data_length = CurrentHeader->common.frag_len - hdr_length - header_auth_len;
if (data_length + buffer_length > pMsg->BufferLength) { if (data_length + buffer_length > pMsg->BufferLength) {
TRACE("allocation hint exceeded, new buffer length = %ld\n", TRACE("allocation hint exceeded, new buffer length = %ld\n",
data_length + buffer_length); data_length + buffer_length);
@ -807,17 +895,11 @@ RPC_STATUS RPCRT4_Receive(RpcConnection *Connection, RpcPktHdr **Header,
if (status != RPC_S_OK) goto fail; if (status != RPC_S_OK) goto fail;
} }
if (data_length == 0) dwRead = 0; else memcpy((unsigned char *)pMsg->Buffer + buffer_length, payload, data_length);
dwRead = rpcrt4_conn_read(Connection,
(unsigned char *)pMsg->Buffer + buffer_length, data_length);
if (dwRead != data_length) {
WARN("bad data length, %d/%ld\n", dwRead, data_length);
status = RPC_S_CALL_FAILED;
goto fail;
}
if (header_auth_len) { if (header_auth_len) {
if (header_auth_len < sizeof(RpcAuthVerifier)) { if (header_auth_len < sizeof(RpcAuthVerifier) ||
header_auth_len > RPC_AUTH_VERIFIER_LEN(&(*Header)->common)) {
WARN("bad auth verifier length %d\n", header_auth_len); WARN("bad auth verifier length %d\n", header_auth_len);
status = RPC_S_PROTOCOL_ERROR; status = RPC_S_PROTOCOL_ERROR;
goto fail; goto fail;
@ -828,22 +910,14 @@ RPC_STATUS RPCRT4_Receive(RpcConnection *Connection, RpcPktHdr **Header,
* however, the details of how this is done is very sketchy in the * however, the details of how this is done is very sketchy in the
* DCE/RPC spec. for all other packet types that have authentication * DCE/RPC spec. for all other packet types that have authentication
* verifier data then it is just duplicated in all the fragments */ * verifier data then it is just duplicated in all the fragments */
dwRead = rpcrt4_conn_read(Connection, auth_data, header_auth_len); memcpy(auth_data, (unsigned char *)payload + data_length, header_auth_len);
if (dwRead != header_auth_len) {
WARN("bad authentication data length, %d/%d\n", dwRead,
header_auth_len);
status = RPC_S_CALL_FAILED;
goto fail;
}
/* these packets are handled specially, not by the generic SecurePacket /* these packets are handled specially, not by the generic SecurePacket
* function */ * function */
if ((common_hdr.ptype != PKT_BIND) && if (!auth_data_out && SecIsValidHandle(&Connection->ctx))
(common_hdr.ptype != PKT_BIND_ACK) &&
(common_hdr.ptype != PKT_AUTH3))
{ {
status = RPCRT4_SecurePacket(Connection, SECURE_PACKET_RECEIVE, status = RPCRT4_SecurePacket(Connection, SECURE_PACKET_RECEIVE,
*Header, hdr_length, CurrentHeader, hdr_length,
(unsigned char *)pMsg->Buffer + buffer_length, data_length, (unsigned char *)pMsg->Buffer + buffer_length, data_length,
(RpcAuthVerifier *)auth_data, (RpcAuthVerifier *)auth_data,
auth_data + sizeof(RpcAuthVerifier), auth_data + sizeof(RpcAuthVerifier),
@ -853,16 +927,19 @@ RPC_STATUS RPCRT4_Receive(RpcConnection *Connection, RpcPktHdr **Header,
} }
buffer_length += data_length; buffer_length += data_length;
if (!((*Header)->common.flags & RPC_FLG_LAST)) { if (!(CurrentHeader->common.flags & RPC_FLG_LAST)) {
TRACE("next header\n"); TRACE("next header\n");
/* read the header of next packet */ if (*Header != CurrentHeader)
dwRead = rpcrt4_conn_read(Connection, *Header, hdr_length); {
if (dwRead != hdr_length) { RPCRT4_FreeHeader(CurrentHeader);
WARN("invalid packet header size (%d)\n", dwRead); CurrentHeader = NULL;
status = RPC_S_CALL_FAILED;
goto fail;
} }
HeapFree(GetProcessHeap(), 0, payload);
payload = NULL;
status = RPCRT4_receive_fragment(Connection, &CurrentHeader, &payload);
if (status != RPC_S_OK) goto fail;
first_flag = 0; first_flag = 0;
} else { } else {
@ -871,29 +948,40 @@ RPC_STATUS RPCRT4_Receive(RpcConnection *Connection, RpcPktHdr **Header,
} }
pMsg->BufferLength = buffer_length; pMsg->BufferLength = buffer_length;
/* respond to authorization request */
if (common_hdr.ptype == PKT_BIND_ACK && auth_length > sizeof(RpcAuthVerifier))
{
status = RPCRT_AuthorizeConnection(Connection,
auth_data + sizeof(RpcAuthVerifier),
auth_length);
if (status)
goto fail;
}
/* success */ /* success */
status = RPC_S_OK; status = RPC_S_OK;
fail: fail:
RPCRT4_SetThreadCurrentConnection(NULL); RPCRT4_SetThreadCurrentConnection(NULL);
if (CurrentHeader != *Header)
RPCRT4_FreeHeader(CurrentHeader);
if (status != RPC_S_OK) { if (status != RPC_S_OK) {
I_RpcFree(pMsg->Buffer);
pMsg->Buffer = NULL;
RPCRT4_FreeHeader(*Header); RPCRT4_FreeHeader(*Header);
*Header = NULL; *Header = NULL;
} }
HeapFree(GetProcessHeap(), 0, auth_data); if (auth_data_out && status == RPC_S_OK) {
*auth_length_out = auth_length;
*auth_data_out = auth_data;
}
else
HeapFree(GetProcessHeap(), 0, auth_data);
HeapFree(GetProcessHeap(), 0, payload);
return status; return status;
} }
/***********************************************************************
* RPCRT4_Receive (internal)
*
* Receive a packet from connection and merge the fragments.
*/
RPC_STATUS RPCRT4_Receive(RpcConnection *Connection, RpcPktHdr **Header,
PRPC_MESSAGE pMsg)
{
return RPCRT4_ReceiveWithAuth(Connection, Header, pMsg, NULL, NULL);
}
/*********************************************************************** /***********************************************************************
* I_RpcNegotiateTransferSyntax [RPCRT4.@] * I_RpcNegotiateTransferSyntax [RPCRT4.@]
* *
@ -936,7 +1024,10 @@ RPC_STATUS WINAPI I_RpcNegotiateTransferSyntax(PRPC_MESSAGE pMsg)
&cif->InterfaceId); &cif->InterfaceId);
if (status == RPC_S_OK) if (status == RPC_S_OK)
{
pMsg->ReservedForRuntime = conn; pMsg->ReservedForRuntime = conn;
RPCRT4_AddRefBinding(bind);
}
} }
return status; return status;
@ -1033,12 +1124,67 @@ RPC_STATUS WINAPI I_RpcFreeBuffer(PRPC_MESSAGE pMsg)
{ {
RpcConnection *conn = pMsg->ReservedForRuntime; RpcConnection *conn = pMsg->ReservedForRuntime;
RPCRT4_CloseBinding(bind, conn); RPCRT4_CloseBinding(bind, conn);
RPCRT4_ReleaseBinding(bind);
pMsg->ReservedForRuntime = NULL; pMsg->ReservedForRuntime = NULL;
} }
I_RpcFree(pMsg->Buffer); I_RpcFree(pMsg->Buffer);
return RPC_S_OK; return RPC_S_OK;
} }
static void CALLBACK async_apc_notifier_proc(ULONG_PTR ulParam)
{
RPC_ASYNC_STATE *state = (RPC_ASYNC_STATE *)ulParam;
state->u.APC.NotificationRoutine(state, NULL, state->Event);
}
static DWORD WINAPI async_notifier_proc(LPVOID p)
{
RpcConnection *conn = p;
RPC_ASYNC_STATE *state = conn->async_state;
if (state && conn->ops->wait_for_incoming_data(conn) != -1)
{
state->Event = RpcCallComplete;
switch (state->NotificationType)
{
case RpcNotificationTypeEvent:
TRACE("RpcNotificationTypeEvent %p\n", state->u.hEvent);
SetEvent(state->u.hEvent);
break;
case RpcNotificationTypeApc:
TRACE("RpcNotificationTypeApc %p\n", state->u.APC.hThread);
QueueUserAPC(async_apc_notifier_proc, state->u.APC.hThread, (ULONG_PTR)state);
break;
case RpcNotificationTypeIoc:
TRACE("RpcNotificationTypeIoc %p, 0x%x, 0x%lx, %p\n",
state->u.IOC.hIOPort, state->u.IOC.dwNumberOfBytesTransferred,
state->u.IOC.dwCompletionKey, state->u.IOC.lpOverlapped);
PostQueuedCompletionStatus(state->u.IOC.hIOPort,
state->u.IOC.dwNumberOfBytesTransferred,
state->u.IOC.dwCompletionKey,
state->u.IOC.lpOverlapped);
break;
case RpcNotificationTypeHwnd:
TRACE("RpcNotificationTypeHwnd %p 0x%x\n", state->u.HWND.hWnd,
state->u.HWND.Msg);
PostMessageW(state->u.HWND.hWnd, state->u.HWND.Msg, 0, 0);
break;
case RpcNotificationTypeCallback:
TRACE("RpcNotificationTypeCallback %p\n", state->u.NotificationRoutine);
state->u.NotificationRoutine(state, NULL, state->Event);
break;
case RpcNotificationTypeNone:
TRACE("RpcNotificationTypeNone\n");
break;
default:
FIXME("unknown NotificationType: %d/0x%x\n", state->NotificationType, state->NotificationType);
break;
}
}
return 0;
}
/*********************************************************************** /***********************************************************************
* I_RpcSend [RPCRT4.@] * I_RpcSend [RPCRT4.@]
* *
@ -1080,6 +1226,12 @@ RPC_STATUS WINAPI I_RpcSend(PRPC_MESSAGE pMsg)
RPCRT4_FreeHeader(hdr); RPCRT4_FreeHeader(hdr);
if (status == RPC_S_OK && pMsg->RpcFlags & RPC_BUFFER_ASYNC)
{
if (!QueueUserWorkItem(async_notifier_proc, conn, WT_EXECUTEDEFAULT | WT_EXECUTELONGFUNCTION))
status = RPC_S_OUT_OF_RESOURCES;
}
return status; return status;
} }
@ -1198,8 +1350,17 @@ RPC_STATUS WINAPI I_RpcSendReceive(PRPC_MESSAGE pMsg)
*/ */
RPC_STATUS WINAPI I_RpcAsyncSetHandle(PRPC_MESSAGE pMsg, PRPC_ASYNC_STATE pAsync) RPC_STATUS WINAPI I_RpcAsyncSetHandle(PRPC_MESSAGE pMsg, PRPC_ASYNC_STATE pAsync)
{ {
FIXME("(%p, %p): stub\n", pMsg, pAsync); RpcBinding* bind = (RpcBinding*)pMsg->Handle;
return RPC_S_INVALID_BINDING; RpcConnection *conn;
TRACE("(%p, %p)\n", pMsg, pAsync);
if (!bind || bind->server || !pMsg->ReservedForRuntime) return RPC_S_INVALID_BINDING;
conn = pMsg->ReservedForRuntime;
conn->async_state = pAsync;
return RPC_S_OK;
} }
/*********************************************************************** /***********************************************************************

View file

@ -34,7 +34,9 @@ RpcPktHdr *RPCRT4_BuildBindAckHeader(unsigned long DataRepresentation, unsigned
VOID RPCRT4_FreeHeader(RpcPktHdr *Header); VOID RPCRT4_FreeHeader(RpcPktHdr *Header);
RPC_STATUS RPCRT4_Send(RpcConnection *Connection, RpcPktHdr *Header, void *Buffer, unsigned int BufferLength); RPC_STATUS RPCRT4_Send(RpcConnection *Connection, RpcPktHdr *Header, void *Buffer, unsigned int BufferLength);
RPC_STATUS RPCRT4_Receive(RpcConnection *Connection, RpcPktHdr **Header, PRPC_MESSAGE pMsg); RPC_STATUS RPCRT4_Receive(RpcConnection *Connection, RpcPktHdr **Header, PRPC_MESSAGE pMsg);
RPC_STATUS RPCRT4_ReceiveWithAuth(RpcConnection *Connection, RpcPktHdr **Header, PRPC_MESSAGE pMsg, unsigned char **auth_data_out, unsigned long *auth_length_out);
NCA_STATUS RPC2NCA_STATUS(RPC_STATUS status); NCA_STATUS RPC2NCA_STATUS(RPC_STATUS status);
RPC_STATUS NCA2RPC_STATUS(NCA_STATUS status); RPC_STATUS NCA2RPC_STATUS(NCA_STATUS status);
RPC_STATUS RPCRT4_AuthorizeConnection(RpcConnection* conn, BYTE *challenge, ULONG count);
#endif #endif

View file

@ -1571,7 +1571,7 @@ RPC_STATUS RPCRT4_DestroyConnection(RpcConnection* Connection)
if (Connection->QOS) RpcQualityOfService_Release(Connection->QOS); if (Connection->QOS) RpcQualityOfService_Release(Connection->QOS);
/* server-only */ /* server-only */
if (Connection->server_binding) RPCRT4_DestroyBinding(Connection->server_binding); if (Connection->server_binding) RPCRT4_ReleaseBinding(Connection->server_binding);
HeapFree(GetProcessHeap(), 0, Connection); HeapFree(GetProcessHeap(), 0, Connection);
return RPC_S_OK; return RPC_S_OK;

View file

@ -39,6 +39,7 @@
<file>rpcrt4_main.c</file> <file>rpcrt4_main.c</file>
<file>rpcss_np_client.c</file> <file>rpcss_np_client.c</file>
<file>unix_func.c</file> <file>unix_func.c</file>
<file>ndr_es.c</file>
<file>rpcrt4.rc</file> <file>rpcrt4.rc</file>
<file>rpcrt4.spec</file> <file>rpcrt4.spec</file>
</module> </module>

View file

@ -31,7 +31,7 @@
@ stub I_RpcBindingInqDynamicEndPointW @ stub I_RpcBindingInqDynamicEndPointW
@ stub I_RpcBindingInqLocalClientPID # wxp @ stub I_RpcBindingInqLocalClientPID # wxp
@ stub I_RpcBindingInqSecurityContext @ stub I_RpcBindingInqSecurityContext
@ stub I_RpcBindingInqTransportType @ stdcall I_RpcBindingInqTransportType(ptr ptr)
@ stub I_RpcBindingInqWireIdForSnego @ stub I_RpcBindingInqWireIdForSnego
@ stub I_RpcBindingIsClientLocal @ stub I_RpcBindingIsClientLocal
# 9x version of I_RpcBindingSetAsync has 3 arguments, not 2 # 9x version of I_RpcBindingSetAsync has 3 arguments, not 2
@ -97,13 +97,13 @@
@ stub MIDL_wchar_strcpy @ stub MIDL_wchar_strcpy
@ stub MIDL_wchar_strlen @ stub MIDL_wchar_strlen
@ stub MesBufferHandleReset @ stub MesBufferHandleReset
@ stub MesDecodeBufferHandleCreate @ stdcall MesDecodeBufferHandleCreate(ptr long ptr)
@ stub MesDecodeIncrementalHandleCreate @ stdcall MesDecodeIncrementalHandleCreate(ptr ptr ptr)
@ stub MesEncodeDynBufferHandleCreate @ stub MesEncodeDynBufferHandleCreate
@ stub MesEncodeFixedBufferHandleCreate @ stdcall MesEncodeFixedBufferHandleCreate(ptr long ptr ptr)
@ stub MesEncodeIncrementalHandleCreate @ stdcall MesEncodeIncrementalHandleCreate(ptr ptr ptr ptr)
@ stub MesHandleFree @ stdcall MesHandleFree(ptr)
@ stub MesIncrementalHandleReset @ stdcall MesIncrementalHandleReset(ptr ptr ptr ptr ptr long)
@ stub MesInqProcEncodingId @ stub MesInqProcEncodingId
@ stdcall NDRCContextBinding(ptr) @ stdcall NDRCContextBinding(ptr)
@ stdcall NDRCContextMarshall(ptr ptr) @ stdcall NDRCContextMarshall(ptr ptr)
@ -218,7 +218,7 @@
@ stdcall NdrMapCommAndFaultStatus(ptr ptr ptr long) @ stdcall NdrMapCommAndFaultStatus(ptr ptr ptr long)
@ stub NdrMarkNextActivePipe @ stub NdrMarkNextActivePipe
@ stub NdrMesProcEncodeDecode2 @ stub NdrMesProcEncodeDecode2
@ stub NdrMesProcEncodeDecode @ varargs NdrMesProcEncodeDecode(ptr ptr ptr)
@ stub NdrMesSimpleTypeAlignSize @ stub NdrMesSimpleTypeAlignSize
@ stub NdrMesSimpleTypeDecode @ stub NdrMesSimpleTypeDecode
@ stub NdrMesSimpleTypeEncode @ stub NdrMesSimpleTypeEncode
@ -350,7 +350,7 @@
@ stdcall RpcBindingInqAuthInfoW(ptr ptr ptr ptr ptr ptr) @ stdcall RpcBindingInqAuthInfoW(ptr ptr ptr ptr ptr ptr)
@ stdcall RpcBindingInqObject(ptr ptr) @ stdcall RpcBindingInqObject(ptr ptr)
@ stub RpcBindingInqOption @ stub RpcBindingInqOption
@ stub RpcBindingReset @ stdcall RpcBindingReset(ptr)
@ stub RpcBindingServerFromClient @ stub RpcBindingServerFromClient
@ stdcall RpcBindingSetAuthInfoA(ptr str long long ptr long) @ stdcall RpcBindingSetAuthInfoA(ptr str long long ptr long)
@ stdcall RpcBindingSetAuthInfoExA(ptr str long long ptr long ptr) @ stdcall RpcBindingSetAuthInfoExA(ptr str long long ptr long ptr)

View file

@ -0,0 +1,133 @@
/*
* NDR Serialization Services
*
* Copyright (c) 2007 Robert Shearman for CodeWeavers
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#ifndef __WINE_MIDLES_H__
#define __WINE_MIDLES_H__
#include <rpcndr.h>
#ifdef __cplusplus
extern "C" {
#endif
typedef enum
{
MES_ENCODE,
MES_DECODE
} MIDL_ES_CODE;
typedef enum
{
MES_INCREMENTAL_HANDLE,
MES_FIXED_BUFFER_HANDLE,
MES_DYNAMIC_BUFFER_HANDLE
} MIDL_ES_HANDLE_STYLE;
typedef void (__RPC_USER * MIDL_ES_ALLOC)(void *,char **,unsigned int *);
typedef void (__RPC_USER * MIDL_ES_WRITE)(void *,char *,unsigned int);
typedef void (__RPC_USER * MIDL_ES_READ)(void *,char **,unsigned int *);
typedef struct _MIDL_ES_MESSAGE
{
MIDL_STUB_MESSAGE StubMsg;
MIDL_ES_CODE Operation;
void *UserState;
ULONG MesVersion : 8;
ULONG HandleStyle : 8;
ULONG HandleFlags : 8;
ULONG Reserve : 8;
MIDL_ES_ALLOC Alloc;
MIDL_ES_WRITE Write;
MIDL_ES_READ Read;
unsigned char *Buffer;
ULONG BufferSize;
unsigned char **pDynBuffer;
ULONG *pEncodedSize;
RPC_SYNTAX_IDENTIFIER InterfaceId;
ULONG ProcNumber;
ULONG AlienDataRep;
ULONG IncrDataSize;
ULONG ByteCount;
} MIDL_ES_MESSAGE, *PMIDL_ES_MESSAGE;
typedef PMIDL_ES_MESSAGE MIDL_ES_HANDLE;
typedef struct _MIDL_TYPE_PICKLING_INFO
{
ULONG Version;
ULONG Flags;
UINT_PTR Reserved[3];
} MIDL_TYPE_PICKLING_INFO, *PMIDL_TYPE_PICKLING_INFO;
RPC_STATUS RPC_ENTRY
MesEncodeIncrementalHandleCreate(void *,MIDL_ES_ALLOC,MIDL_ES_WRITE,handle_t *);
RPC_STATUS RPC_ENTRY
MesDecodeIncrementalHandleCreate(void *,MIDL_ES_READ,handle_t *);
RPC_STATUS RPC_ENTRY
MesIncrementalHandleReset(handle_t,void *,MIDL_ES_ALLOC,MIDL_ES_WRITE,MIDL_ES_READ,MIDL_ES_CODE);
RPC_STATUS RPC_ENTRY
MesEncodeFixedBufferHandleCreate(char *,ULONG,ULONG *,handle_t *);
RPC_STATUS RPC_ENTRY
MesEncodeDynBufferHandleCreate(char **,ULONG *,handle_t *);
RPC_STATUS RPC_ENTRY
MesDecodeBufferHandleCreate(char *,ULONG,handle_t *);
RPC_STATUS RPC_ENTRY
MesBufferHandleReset(handle_t,ULONG,MIDL_ES_CODE,char **,ULONG,ULONG *);
RPC_STATUS RPC_ENTRY
MesHandleFree(handle_t);
RPC_STATUS RPC_ENTRY
MesInqProcEncodingId(handle_t,PRPC_SYNTAX_IDENTIFIER,ULONG *);
SIZE_T RPC_ENTRY
NdrMesSimpleTypeAlignSize(handle_t);
void RPC_ENTRY
NdrMesSimpleTypeDecode(handle_t,void *,short);
void RPC_ENTRY
NdrMesSimpleTypeEncode(handle_t,const MIDL_STUB_DESC *,const void *,short);
SIZE_T RPC_ENTRY
NdrMesTypeAlignSize(handle_t,const MIDL_STUB_DESC *,PFORMAT_STRING,const void *);
void RPC_ENTRY
NdrMesTypeEncode(handle_t,const MIDL_STUB_DESC *,PFORMAT_STRING,const void *);
void RPC_ENTRY
NdrMesTypeDecode(handle_t,const MIDL_STUB_DESC *,PFORMAT_STRING,void *);
SIZE_T RPC_ENTRY
NdrMesTypeAlignSize2(handle_t,const MIDL_TYPE_PICKLING_INFO *,const MIDL_STUB_DESC *,PFORMAT_STRING,const void *);
void RPC_ENTRY
NdrMesTypeEncode2(handle_t,const MIDL_TYPE_PICKLING_INFO *,const MIDL_STUB_DESC *,PFORMAT_STRING,const void *);
void RPC_ENTRY
NdrMesTypeDecode2(handle_t,const MIDL_TYPE_PICKLING_INFO *,const MIDL_STUB_DESC *,PFORMAT_STRING,void *);
void RPC_ENTRY
NdrMesTypeFree2(handle_t,const MIDL_TYPE_PICKLING_INFO *,const MIDL_STUB_DESC *,PFORMAT_STRING,void *);
void RPC_VAR_ENTRY
NdrMesProcEncodeDecode(handle_t,const MIDL_STUB_DESC *,PFORMAT_STRING,...);
CLIENT_CALL_RETURN RPC_VAR_ENTRY
NdrMesProcEncodeDeocde2(handle_t,const MIDL_STUB_DESC *,PFORMAT_STRING,...);
#ifdef __cplusplus
}
#endif
#endif /* __WINE_MIDLES_H__ */

View file

@ -15,12 +15,14 @@
* *
* You should have received a copy of the GNU Lesser General Public * You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software * License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/ */
#ifndef __NDRTYPES_H__ #ifndef __NDRTYPES_H__
#define __NDRTYPES_H__ #define __NDRTYPES_H__
#include <limits.h>
typedef struct typedef struct
{ {
unsigned short MustSize : 1; /* 0x0001 - client interpreter MUST size this unsigned short MustSize : 1; /* 0x0001 - client interpreter MUST size this
@ -29,9 +31,7 @@ typedef struct
unsigned short MustFree : 1; /* 0x0002 - server interpreter MUST size this unsigned short MustFree : 1; /* 0x0002 - server interpreter MUST size this
* parameter, other parameters may be skipped, using the value in * parameter, other parameters may be skipped, using the value in
* NDR_PROC_PARTIAL_OIF_HEADER::constant_server_buffer_size instead. */ * NDR_PROC_PARTIAL_OIF_HEADER::constant_server_buffer_size instead. */
unsigned short IsPipe : 1; /* 0x0004 - The parameter is a pipe handle. See unsigned short IsPipe : 1; /* 0x0004 - The parameter is a pipe handle */
* http://msdn.microsoft.com/library/default.asp?url=/library/en-us/rpc/rpc/pipes.asp
* for more information on pipes. */
unsigned short IsIn : 1; /* 0x0008 - The parameter is an input */ unsigned short IsIn : 1; /* 0x0008 - The parameter is an input */
unsigned short IsOut : 1; /* 0x0010 - The parameter is an output */ unsigned short IsOut : 1; /* 0x0010 - The parameter is an output */
unsigned short IsReturn : 1; /* 0x0020 - The parameter is to be returned */ unsigned short IsReturn : 1; /* 0x0020 - The parameter is to be returned */
@ -178,5 +178,4 @@ typedef enum
#define NDR_CONTEXT_HANDLE_SERIALIZE 0x02 #define NDR_CONTEXT_HANDLE_SERIALIZE 0x02
#define NDR_CONTEXT_HANDLE_CANNOT_BE_NULL 0x01 #define NDR_CONTEXT_HANDLE_CANNOT_BE_NULL 0x01
#endif #endif

View file

@ -18,7 +18,9 @@
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/ */
#ifndef DO_NO_IMPORTS
import "objidl.idl"; import "objidl.idl";
#endif
interface IOleInPlaceActiveObject; interface IOleInPlaceActiveObject;
@ -331,7 +333,7 @@ interface IOleItemContainer : IOleContainer
OLECONTF_EMBEDDINGS = 1, OLECONTF_EMBEDDINGS = 1,
OLECONTF_LINKS = 2, OLECONTF_LINKS = 2,
OLECONTF_OTHERS = 4, OLECONTF_OTHERS = 4,
OLECONTF_OLNYUSER = 8, OLECONTF_ONLYUSER = 8,
OLECONTF_ONLYIFRUNNING = 16 OLECONTF_ONLYIFRUNNING = 16
} OLECONTF; } OLECONTF;

View file

@ -139,6 +139,11 @@ typedef I_RPC_HANDLE *RPC_EP_INQ_HANDLE;
#define RPC_C_AUTHN_MQ 100 #define RPC_C_AUTHN_MQ 100
#define RPC_C_AUTHN_DEFAULT 0xffffffff #define RPC_C_AUTHN_DEFAULT 0xffffffff
#define RPC_C_AUTHZ_NONE 0
#define RPC_C_AUTHZ_NAME 1
#define RPC_C_AUTHZ_DCE 2
#define RPC_C_AUTHZ_DEFAULT 0xffffffff
/* values for RPC_SECURITY_QOS*::ImpersonationType */ /* values for RPC_SECURITY_QOS*::ImpersonationType */
#define RPC_C_IMP_LEVEL_DEFAULT 0 #define RPC_C_IMP_LEVEL_DEFAULT 0
#define RPC_C_IMP_LEVEL_ANONYMOUS 1 #define RPC_C_IMP_LEVEL_ANONYMOUS 1
@ -280,10 +285,13 @@ typedef struct _RPC_SECURITY_QOS_V2_A
#define SEC_WINNT_AUTH_IDENTITY_UNICODE 0x2 #define SEC_WINNT_AUTH_IDENTITY_UNICODE 0x2
/* RpcServerRegisterIfEx Flags */ /* RpcServerRegisterIfEx Flags */
#define RPC_IF_AUTOLISTEN 0x1 #define RPC_IF_AUTOLISTEN 0x01
#define RPC_IF_OLE 0x2 #define RPC_IF_OLE 0x02
#define RPC_IF_ALLOW_UNKNOWN_AUTHORITY 0x4 #define RPC_IF_ALLOW_UNKNOWN_AUTHORITY 0x04
#define RPC_IF_ALLOW_SECURE_ONLY 0x8 #define RPC_IF_ALLOW_SECURE_ONLY 0x08
#define RPC_IF_ALLOW_CALLBACKS_WITH_NO_AUTH 0x10
#define RPC_IF_ALLOW_LOCAL_ONLY 0x20
#define RPC_IF_SEC_NO_CACHE 0x40
RPC_STATUS RPC_ENTRY DceErrorInqTextA(RPC_STATUS e, RPC_CSTR buffer); RPC_STATUS RPC_ENTRY DceErrorInqTextA(RPC_STATUS e, RPC_CSTR buffer);
RPC_STATUS RPC_ENTRY DceErrorInqTextW(RPC_STATUS e, RPC_WSTR buffer); RPC_STATUS RPC_ENTRY DceErrorInqTextW(RPC_STATUS e, RPC_WSTR buffer);
@ -291,7 +299,7 @@ RPC_STATUS RPC_ENTRY DceErrorInqTextW(RPC_STATUS e, RPC_WSTR buffer);
RPCRTAPI DECLSPEC_NORETURN void RPC_ENTRY RPCRTAPI DECLSPEC_NORETURN void RPC_ENTRY
RpcRaiseException( RPC_STATUS exception ); RpcRaiseException( RPC_STATUS exception );
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcBindingCopy( RPC_BINDING_HANDLE SourceBinding, RPC_BINDING_HANDLE* DestinationBinding ); RpcBindingCopy( RPC_BINDING_HANDLE SourceBinding, RPC_BINDING_HANDLE* DestinationBinding );
@ -300,10 +308,14 @@ RPCRTAPI RPC_STATUS RPC_ENTRY
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcBindingInqObject( RPC_BINDING_HANDLE Binding, UUID* ObjectUuid ); RpcBindingInqObject( RPC_BINDING_HANDLE Binding, UUID* ObjectUuid );
RPCRTAPI RPC_STATUS RPC_ENTRY
RpcBindingInqOption( RPC_BINDING_HANDLE Binding, ULONG Option, ULONG_PTR *OptionValue );
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcBindingReset( RPC_BINDING_HANDLE Binding ); RpcBindingReset( RPC_BINDING_HANDLE Binding );
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcBindingSetObject( RPC_BINDING_HANDLE Binding, UUID* ObjectUuid ); RpcBindingSetObject( RPC_BINDING_HANDLE Binding, UUID* ObjectUuid );
RPCRTAPI RPC_STATUS RPC_ENTRY
RpcBindingSetOption( RPC_BINDING_HANDLE Binding, ULONG Option, ULONG_PTR OptionValue );
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcObjectSetType( UUID* ObjUuid, UUID* TypeUuid ); RpcObjectSetType( UUID* ObjUuid, UUID* TypeUuid );
@ -317,7 +329,7 @@ RPCRTAPI RPC_STATUS RPC_ENTRY
RpcBindingToStringBindingA( RPC_BINDING_HANDLE Binding, RPC_CSTR *StringBinding ); RpcBindingToStringBindingA( RPC_BINDING_HANDLE Binding, RPC_CSTR *StringBinding );
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcBindingToStringBindingW( RPC_BINDING_HANDLE Binding, RPC_WSTR *StringBinding ); RpcBindingToStringBindingW( RPC_BINDING_HANDLE Binding, RPC_WSTR *StringBinding );
#define RpcBindingFromStringBinding WINELIB_NAME_AW(RpcBindingFromStringBinding) #define RpcBindingToStringBinding WINELIB_NAME_AW(RpcBindingToStringBinding)
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcBindingVectorFree( RPC_BINDING_VECTOR** BindingVector ); RpcBindingVectorFree( RPC_BINDING_VECTOR** BindingVector );
@ -367,6 +379,9 @@ RPCRTAPI RPC_STATUS RPC_ENTRY
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcServerListen( unsigned int MinimumCallThreads, unsigned int MaxCalls, unsigned int DontWait ); RpcServerListen( unsigned int MinimumCallThreads, unsigned int MaxCalls, unsigned int DontWait );
RPCRTAPI RPC_STATUS RPC_ENTRY
RpcMgmtEnableIdleCleanup( void );
RPCRTAPI RPC_STATUS RPC_ENTRY RpcMgmtSetCancelTimeout(LONG); RPCRTAPI RPC_STATUS RPC_ENTRY RpcMgmtSetCancelTimeout(LONG);
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
@ -375,6 +390,9 @@ RPCRTAPI RPC_STATUS RPC_ENTRY
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcMgmtStopServerListening( RPC_BINDING_HANDLE Binding ); RpcMgmtStopServerListening( RPC_BINDING_HANDLE Binding );
RPCRTAPI RPC_STATUS RPC_ENTRY
RpcMgmtIsServerListening(RPC_BINDING_HANDLE Binding);
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcMgmtInqIfIds( RPC_BINDING_HANDLE Binding, RPC_IF_ID_VECTOR** IfIdVector ); RpcMgmtInqIfIds( RPC_BINDING_HANDLE Binding, RPC_IF_ID_VECTOR** IfIdVector );
@ -382,6 +400,12 @@ RPCRTAPI RPC_STATUS RPC_ENTRY
RpcMgmtEpEltInqBegin( RPC_BINDING_HANDLE EpBinding, ULONG InquiryType, RPC_IF_ID *IfId, RpcMgmtEpEltInqBegin( RPC_BINDING_HANDLE EpBinding, ULONG InquiryType, RPC_IF_ID *IfId,
ULONG VersOption, UUID *ObjectUuid, RPC_EP_INQ_HANDLE *InquiryContext); ULONG VersOption, UUID *ObjectUuid, RPC_EP_INQ_HANDLE *InquiryContext);
RPCRTAPI RPC_STATUS RPC_ENTRY
RpcMgmtSetComTimeout( RPC_BINDING_HANDLE Binding, unsigned int Timeout );
RPCRTAPI RPC_STATUS RPC_ENTRY
RpcMgmtSetServerStackSize( ULONG ThreadStackSize );
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcServerRegisterIf( RPC_IF_HANDLE IfSpec, UUID* MgrTypeUuid, RPC_MGR_EPV* MgrEpv ); RpcServerRegisterIf( RPC_IF_HANDLE IfSpec, UUID* MgrTypeUuid, RPC_MGR_EPV* MgrEpv );
@ -469,6 +493,10 @@ RPCRTAPI RPC_STATUS RPC_ENTRY
#define RpcBindingInqAuthInfo WINELIB_NAME_AW(RpcBindingInqAuthInfo) #define RpcBindingInqAuthInfo WINELIB_NAME_AW(RpcBindingInqAuthInfo)
RPCRTAPI RPC_STATUS RPC_ENTRY RpcCancelThread(void*); RPCRTAPI RPC_STATUS RPC_ENTRY RpcCancelThread(void*);
RPCRTAPI RPC_STATUS RPC_ENTRY RpcCancelThreadEx(void*,LONG);
RPCRTAPI RPC_STATUS RPC_ENTRY
RpcImpersonateClient( RPC_BINDING_HANDLE Binding );
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcNetworkIsProtseqValidA( RPC_CSTR protseq ); RpcNetworkIsProtseqValidA( RPC_CSTR protseq );
@ -476,6 +504,11 @@ RPCRTAPI RPC_STATUS RPC_ENTRY
RpcNetworkIsProtseqValidW( RPC_WSTR protseq ); RpcNetworkIsProtseqValidW( RPC_WSTR protseq );
#define RpcNetworkIsProtseqValid WINELIB_NAME_AW(RpcNetworkIsProtseqValid) #define RpcNetworkIsProtseqValid WINELIB_NAME_AW(RpcNetworkIsProtseqValid)
RPCRTAPI RPC_STATUS RPC_ENTRY
RpcRevertToSelf( void );
RPCRTAPI RPC_STATUS RPC_ENTRY
RpcRevertToSelfEx( RPC_BINDING_HANDLE Binding );
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
RpcStringFreeA(RPC_CSTR* String); RpcStringFreeA(RPC_CSTR* String);
RPCRTAPI RPC_STATUS RPC_ENTRY RPCRTAPI RPC_STATUS RPC_ENTRY
@ -509,13 +542,6 @@ RPCRTAPI unsigned short RPC_ENTRY
RPCRTAPI int RPC_ENTRY RPCRTAPI int RPC_ENTRY
UuidIsNil( UUID* Uuid, RPC_STATUS* Status_ ); UuidIsNil( UUID* Uuid, RPC_STATUS* Status_ );
RPCRTAPI RPC_STATUS RPC_ENTRY
RpcImpersonateClient (IN RPC_BINDING_HANDLE BindingHandle OPTIONAL);
RPCRTAPI RPC_STATUS RPC_ENTRY
RpcRevertToSelf ();
#ifdef __cplusplus #ifdef __cplusplus
} }
#endif #endif

View file

@ -48,7 +48,7 @@ typedef struct _RPC_MESSAGE
unsigned long RpcFlags; unsigned long RpcFlags;
} RPC_MESSAGE, *PRPC_MESSAGE; } RPC_MESSAGE, *PRPC_MESSAGE;
/* or'd with ProcNum */ /* or'ed with ProcNum */
#define RPC_FLAGS_VALID_BIT 0x00008000 #define RPC_FLAGS_VALID_BIT 0x00008000
#define RPC_CONTEXT_HANDLE_DEFAULT_GUARD ((void *)0xfffff00d) #define RPC_CONTEXT_HANDLE_DEFAULT_GUARD ((void *)0xfffff00d)

View file

@ -18,7 +18,7 @@
#ifndef __RPCNDR_H_VERSION__ #ifndef __RPCNDR_H_VERSION__
/* FIXME: What version? Perhaps something is better than nothing, however incorrect */ /* FIXME: What version? Perhaps something is better than nothing, however incorrect */
#define __RPCNDR_H_VERSION__ ( 500 ) #define __RPCNDR_H_VERSION__ ( 399 )
#endif #endif
#ifndef __WINE_RPCNDR_H #ifndef __WINE_RPCNDR_H
@ -175,13 +175,15 @@ typedef struct _MIDL_STUB_MESSAGE
ULONG BufferLength; ULONG BufferLength;
ULONG MemorySize; ULONG MemorySize;
unsigned char *Memory; unsigned char *Memory;
int IsClient; unsigned char IsClient;
unsigned char Pad;
unsigned short uFlags2;
int ReuseBuffer; int ReuseBuffer;
struct NDR_ALLOC_ALL_NODES_CONTEXT *pAllocAllNodesContext; struct NDR_ALLOC_ALL_NODES_CONTEXT *pAllocAllNodesContext;
struct NDR_POINTER_QUEUE_STATE *pPointerQueueState; struct NDR_POINTER_QUEUE_STATE *pPointerQueueState;
int IgnoreEmbeddedPointers; int IgnoreEmbeddedPointers;
unsigned char *PointerBufferMark; unsigned char *PointerBufferMark;
unsigned char fBufferValid; unsigned char CorrDespIncrement;
unsigned char uFlags; unsigned char uFlags;
unsigned short UniquePtrCount; unsigned short UniquePtrCount;
ULONG_PTR MaxCount; ULONG_PTR MaxCount;
@ -203,7 +205,14 @@ typedef struct _MIDL_STUB_MESSAGE
int fHasReturn:1; int fHasReturn:1;
int fHasExtensions:1; int fHasExtensions:1;
int fHasNewCorrDesc:1; int fHasNewCorrDesc:1;
int fUnused:10; int fIsIn:1;
int fIsOut:1;
int fIsOicf:1;
int fBufferValid:1;
int fHasMemoryValidateCallback:1;
int fInFree:1;
int fNeedMCCP:1;
int fUnused:3;
int fUnused2:16; int fUnused2:16;
DWORD dwDestContext; DWORD dwDestContext;
void *pvDestContext; void *pvDestContext;
@ -536,6 +545,9 @@ RPCRTAPI void RPC_ENTRY
RPCRTAPI NDR_SCONTEXT RPC_ENTRY RPCRTAPI NDR_SCONTEXT RPC_ENTRY
NdrServerContextNewUnmarshall( PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFormat ); NdrServerContextNewUnmarshall( PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFormat );
RPCRTAPI RPC_STATUS RPC_ENTRY
RpcSmDestroyClientContext( void **ContextHandle );
RPCRTAPI void RPC_ENTRY RPCRTAPI void RPC_ENTRY
RpcSsDestroyClientContext( void **ContextHandle ); RpcSsDestroyClientContext( void **ContextHandle );

View file

@ -350,8 +350,6 @@ ULONG WINAPI CStdStubBuffer2_Release(IRpcStubBuffer *This) \
#if 0 #if 0
/* see http://www.microsoft.com/msj/0199/com/com0199.aspx */
RPCRTAPI HRESULT RPC_ENTRY RPCRTAPI HRESULT RPC_ENTRY
CreateProxyFromTypeInfo( LPTYPEINFO pTypeInfo, LPUNKNOWN pUnkOuter, REFIID riid, CreateProxyFromTypeInfo( LPTYPEINFO pTypeInfo, LPUNKNOWN pUnkOuter, REFIID riid,
LPRPCPROXYBUFFER *ppProxy, LPVOID *ppv ); LPRPCPROXYBUFFER *ppProxy, LPVOID *ppv );
@ -365,4 +363,4 @@ RPCRTAPI HRESULT RPC_ENTRY
} }
#endif #endif
#endif /*__WINE_RPCDCE_H */ #endif /*__WINE_RPCPROXY_H */