rpcrt4: Factorise conformant varying array functions into array_* functions.

This allows conformant varying array types to be
marshalled/unmarshalled when embedded in a complex type.
This commit is contained in:
Rob Shearman 2008-08-10 11:14:21 +01:00 committed by Alexandre Julliard
parent 518242ef33
commit 9e3260847a
1 changed files with 118 additions and 82 deletions

View File

@ -2138,6 +2138,11 @@ static inline void array_compute_and_size_conformance(
ComputeConformance(pStubMsg, pMemory, pFormat+4, 0); ComputeConformance(pStubMsg, pMemory, pFormat+4, 0);
SizeConformance(pStubMsg); SizeConformance(pStubMsg);
break; break;
case RPC_FC_CVARRAY:
pFormat = ComputeConformance(pStubMsg, pMemory, pFormat + 4, 0);
pFormat = ComputeVariance(pStubMsg, pMemory, pFormat, 0);
SizeConformance(pStubMsg);
break;
default: default:
ERR("unknown array format 0x%x\n", fc); ERR("unknown array format 0x%x\n", fc);
RpcRaiseException(RPC_X_BAD_STUB_DATA); RpcRaiseException(RPC_X_BAD_STUB_DATA);
@ -2166,6 +2171,22 @@ static inline void array_buffer_size(
/* conformance value plus array */ /* conformance value plus array */
safe_buffer_length_increment(pStubMsg, size); safe_buffer_length_increment(pStubMsg, size);
EmbeddedPointerBufferSize(pStubMsg, pMemory, pFormat);
break;
case RPC_FC_CVARRAY:
esize = *(const WORD*)(pFormat+2);
alignment = pFormat[1] + 1;
pFormat = SkipConformance(pStubMsg, pFormat + 4);
pFormat = SkipConformance(pStubMsg, pFormat);
SizeVariance(pStubMsg);
ALIGN_LENGTH(pStubMsg->BufferLength, alignment);
size = safe_multiply(esize, pStubMsg->ActualCount);
safe_buffer_length_increment(pStubMsg, size);
EmbeddedPointerBufferSize(pStubMsg, pMemory, pFormat); EmbeddedPointerBufferSize(pStubMsg, pMemory, pFormat);
break; break;
default: default:
@ -2184,6 +2205,11 @@ static inline void array_compute_and_write_conformance(
ComputeConformance(pStubMsg, pMemory, pFormat+4, 0); ComputeConformance(pStubMsg, pMemory, pFormat+4, 0);
WriteConformance(pStubMsg); WriteConformance(pStubMsg);
break; break;
case RPC_FC_CVARRAY:
pFormat = ComputeConformance(pStubMsg, pMemory, pFormat + 4, 0);
pFormat = ComputeVariance(pStubMsg, pMemory, pFormat, 0);
WriteConformance(pStubMsg);
break;
default: default:
ERR("unknown array format 0x%x\n", fc); ERR("unknown array format 0x%x\n", fc);
RpcRaiseException(RPC_X_BAD_STUB_DATA); RpcRaiseException(RPC_X_BAD_STUB_DATA);
@ -2212,6 +2238,26 @@ static inline void array_write_variance_and_marshall(
pStubMsg->BufferMark = pStubMsg->Buffer; pStubMsg->BufferMark = pStubMsg->Buffer;
safe_copy_to_buffer(pStubMsg, pMemory, size); safe_copy_to_buffer(pStubMsg, pMemory, size);
EmbeddedPointerMarshall(pStubMsg, pMemory, pFormat);
break;
case RPC_FC_CVARRAY:
esize = *(const WORD*)(pFormat+2);
alignment = pFormat[1] + 1;
/* conformance */
pFormat = SkipConformance(pStubMsg, pFormat + 4);
/* variance */
pFormat = SkipConformance(pStubMsg, pFormat);
WriteVariance(pStubMsg);
ALIGN_POINTER_CLEAR(pStubMsg->Buffer, alignment);
size = safe_multiply(esize, pStubMsg->ActualCount);
pStubMsg->BufferMark = pStubMsg->Buffer;
safe_copy_to_buffer(pStubMsg, pMemory + pStubMsg->Offset, size);
EmbeddedPointerMarshall(pStubMsg, pMemory, pFormat); EmbeddedPointerMarshall(pStubMsg, pMemory, pFormat);
break; break;
default: default:
@ -2231,6 +2277,10 @@ static inline ULONG array_read_conformance(
esize = *(const WORD*)(pFormat+2); esize = *(const WORD*)(pFormat+2);
pFormat = ReadConformance(pStubMsg, pFormat+4); pFormat = ReadConformance(pStubMsg, pFormat+4);
return safe_multiply(esize, pStubMsg->MaxCount); return safe_multiply(esize, pStubMsg->MaxCount);
case RPC_FC_CVARRAY:
esize = *(const WORD*)(pFormat+2);
pFormat = ReadConformance(pStubMsg, pFormat+4);
return safe_multiply(esize, pStubMsg->MaxCount);
default: default:
ERR("unknown array format 0x%x\n", fc); ERR("unknown array format 0x%x\n", fc);
RpcRaiseException(RPC_X_BAD_STUB_DATA); RpcRaiseException(RPC_X_BAD_STUB_DATA);
@ -2243,9 +2293,10 @@ static inline void array_read_variance_and_unmarshall(
unsigned char fUseBufferMemoryServer) unsigned char fUseBufferMemoryServer)
{ {
ULONG bufsize, memsize; ULONG bufsize, memsize;
DWORD esize; WORD esize;
unsigned char alignment; unsigned char alignment;
unsigned char *saved_buffer; unsigned char *saved_buffer;
ULONG offset;
switch (fc) switch (fc)
{ {
@ -2276,6 +2327,31 @@ static inline void array_read_variance_and_unmarshall(
if (*ppMemory != saved_buffer) if (*ppMemory != saved_buffer)
memcpy(*ppMemory, saved_buffer, bufsize); memcpy(*ppMemory, saved_buffer, bufsize);
break; break;
case RPC_FC_CVARRAY:
esize = *(const WORD*)(pFormat+2);
alignment = pFormat[1] + 1;
pFormat = SkipConformance(pStubMsg, pFormat + 4);
pFormat = ReadVariance(pStubMsg, pFormat, pStubMsg->MaxCount);
ALIGN_POINTER(pStubMsg->Buffer, alignment);
bufsize = safe_multiply(esize, pStubMsg->ActualCount);
memsize = safe_multiply(esize, pStubMsg->MaxCount);
offset = pStubMsg->Offset;
if (!fMustAlloc && !*ppMemory)
fMustAlloc = TRUE;
if (fMustAlloc)
*ppMemory = NdrAllocate(pStubMsg, memsize);
saved_buffer = pStubMsg->BufferMark = pStubMsg->Buffer;
safe_buffer_increment(pStubMsg, bufsize);
EmbeddedPointerUnmarshall(pStubMsg, saved_buffer, *ppMemory, pFormat, fMustAlloc);
memcpy(*ppMemory + offset, saved_buffer, bufsize);
break;
default: default:
ERR("unknown array format 0x%x\n", fc); ERR("unknown array format 0x%x\n", fc);
RpcRaiseException(RPC_X_BAD_STUB_DATA); RpcRaiseException(RPC_X_BAD_STUB_DATA);
@ -2285,7 +2361,7 @@ static inline void array_read_variance_and_unmarshall(
static inline void array_memory_size( static inline void array_memory_size(
unsigned char fc, PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFormat) unsigned char fc, PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFormat)
{ {
DWORD size; ULONG bufsize, memsize;
DWORD esize; DWORD esize;
unsigned char alignment; unsigned char alignment;
@ -2297,12 +2373,30 @@ static inline void array_memory_size(
pFormat = SkipConformance(pStubMsg, pFormat + 4); pFormat = SkipConformance(pStubMsg, pFormat + 4);
size = safe_multiply(esize, pStubMsg->MaxCount); bufsize = memsize = safe_multiply(esize, pStubMsg->MaxCount);
pStubMsg->MemorySize += size; pStubMsg->MemorySize += memsize;
ALIGN_POINTER(pStubMsg->Buffer, alignment); ALIGN_POINTER(pStubMsg->Buffer, alignment);
pStubMsg->BufferMark = pStubMsg->Buffer; pStubMsg->BufferMark = pStubMsg->Buffer;
safe_buffer_increment(pStubMsg, size); safe_buffer_increment(pStubMsg, bufsize);
EmbeddedPointerMemorySize(pStubMsg, pFormat);
break;
case RPC_FC_CVARRAY:
esize = *(const WORD*)(pFormat+2);
alignment = pFormat[1] + 1;
pFormat = SkipConformance(pStubMsg, pFormat + 4);
pFormat = ReadVariance(pStubMsg, pFormat, pStubMsg->MaxCount);
bufsize = safe_multiply(esize, pStubMsg->ActualCount);
memsize = safe_multiply(esize, pStubMsg->MaxCount);
pStubMsg->MemorySize += memsize;
ALIGN_POINTER(pStubMsg->Buffer, alignment);
pStubMsg->BufferMark = pStubMsg->Buffer;
safe_buffer_increment(pStubMsg, bufsize);
EmbeddedPointerMemorySize(pStubMsg, pFormat); EmbeddedPointerMemorySize(pStubMsg, pFormat);
break; break;
@ -2322,6 +2416,11 @@ static inline void array_free(
pFormat = ComputeConformance(pStubMsg, pMemory, pFormat+4, 0); pFormat = ComputeConformance(pStubMsg, pMemory, pFormat+4, 0);
EmbeddedPointerFree(pStubMsg, pMemory, pFormat); EmbeddedPointerFree(pStubMsg, pMemory, pFormat);
break; break;
case RPC_FC_CVARRAY:
pFormat = ComputeConformance(pStubMsg, pMemory, pFormat+4, 0);
pFormat = ComputeVariance(pStubMsg, pMemory, pFormat, 0);
EmbeddedPointerFree(pStubMsg, pMemory, pFormat);
break;
case RPC_FC_C_CSTRING: case RPC_FC_C_CSTRING:
case RPC_FC_C_WSTRING: case RPC_FC_C_WSTRING:
/* No embedded pointers so nothing to do */ /* No embedded pointers so nothing to do */
@ -3463,10 +3562,6 @@ unsigned char* WINAPI NdrConformantVaryingArrayMarshall( PMIDL_STUB_MESSAGE pStu
unsigned char* pMemory, unsigned char* pMemory,
PFORMAT_STRING pFormat ) PFORMAT_STRING pFormat )
{ {
ULONG bufsize;
unsigned char alignment = pFormat[1] + 1;
DWORD esize = *(const WORD*)(pFormat+2);
TRACE("(%p, %p, %p)\n", pStubMsg, pMemory, pFormat); TRACE("(%p, %p, %p)\n", pStubMsg, pMemory, pFormat);
if (pFormat[0] != RPC_FC_CVARRAY) if (pFormat[0] != RPC_FC_CVARRAY)
@ -3476,20 +3571,10 @@ unsigned char* WINAPI NdrConformantVaryingArrayMarshall( PMIDL_STUB_MESSAGE pStu
return NULL; return NULL;
} }
pFormat = ComputeConformance(pStubMsg, pMemory, pFormat+4, 0); array_compute_and_write_conformance(RPC_FC_CVARRAY, pStubMsg, pMemory,
pFormat = ComputeVariance(pStubMsg, pMemory, pFormat, 0); pFormat);
array_write_variance_and_marshall(RPC_FC_CVARRAY, pStubMsg, pMemory,
WriteConformance(pStubMsg); pFormat);
WriteVariance(pStubMsg);
ALIGN_POINTER_CLEAR(pStubMsg->Buffer, alignment);
bufsize = safe_multiply(esize, pStubMsg->ActualCount);
pStubMsg->BufferMark = pStubMsg->Buffer;
safe_copy_to_buffer(pStubMsg, pMemory + pStubMsg->Offset, bufsize);
EmbeddedPointerMarshall(pStubMsg, pMemory, pFormat);
return NULL; return NULL;
} }
@ -3503,12 +3588,6 @@ unsigned char* WINAPI NdrConformantVaryingArrayUnmarshall( PMIDL_STUB_MESSAGE pS
PFORMAT_STRING pFormat, PFORMAT_STRING pFormat,
unsigned char fMustAlloc ) unsigned char fMustAlloc )
{ {
ULONG bufsize, memsize;
unsigned char alignment = pFormat[1] + 1;
DWORD esize = *(const WORD*)(pFormat+2);
unsigned char *saved_buffer;
ULONG offset;
TRACE("(%p, %p, %p, %d)\n", pStubMsg, ppMemory, pFormat, fMustAlloc); TRACE("(%p, %p, %p, %d)\n", pStubMsg, ppMemory, pFormat, fMustAlloc);
if (pFormat[0] != RPC_FC_CVARRAY) if (pFormat[0] != RPC_FC_CVARRAY)
@ -3518,23 +3597,10 @@ unsigned char* WINAPI NdrConformantVaryingArrayUnmarshall( PMIDL_STUB_MESSAGE pS
return NULL; return NULL;
} }
pFormat = ReadConformance(pStubMsg, pFormat+4); array_read_conformance(RPC_FC_CVARRAY, pStubMsg, pFormat);
pFormat = ReadVariance(pStubMsg, pFormat, pStubMsg->MaxCount); array_read_variance_and_unmarshall(RPC_FC_CVARRAY, pStubMsg, ppMemory,
pFormat, fMustAlloc,
ALIGN_POINTER(pStubMsg->Buffer, alignment); TRUE /* fUseBufferMemoryServer */);
bufsize = safe_multiply(esize, pStubMsg->ActualCount);
memsize = safe_multiply(esize, pStubMsg->MaxCount);
offset = pStubMsg->Offset;
if (!*ppMemory || fMustAlloc)
*ppMemory = NdrAllocate(pStubMsg, memsize);
saved_buffer = pStubMsg->BufferMark = pStubMsg->Buffer;
safe_buffer_increment(pStubMsg, bufsize);
EmbeddedPointerUnmarshall(pStubMsg, saved_buffer, *ppMemory, pFormat, fMustAlloc);
memcpy(*ppMemory + offset, saved_buffer, bufsize);
return NULL; return NULL;
} }
@ -3556,10 +3622,7 @@ void WINAPI NdrConformantVaryingArrayFree( PMIDL_STUB_MESSAGE pStubMsg,
return; return;
} }
pFormat = ComputeConformance(pStubMsg, pMemory, pFormat+4, 0); array_free(RPC_FC_CVARRAY, pStubMsg, pMemory, pFormat);
pFormat = ComputeVariance(pStubMsg, pMemory, pFormat, 0);
EmbeddedPointerFree(pStubMsg, pMemory, pFormat);
} }
@ -3569,9 +3632,6 @@ void WINAPI NdrConformantVaryingArrayFree( PMIDL_STUB_MESSAGE pStubMsg,
void WINAPI NdrConformantVaryingArrayBufferSize( PMIDL_STUB_MESSAGE pStubMsg, void WINAPI NdrConformantVaryingArrayBufferSize( PMIDL_STUB_MESSAGE pStubMsg,
unsigned char* pMemory, PFORMAT_STRING pFormat ) unsigned char* pMemory, PFORMAT_STRING pFormat )
{ {
unsigned char alignment = pFormat[1] + 1;
DWORD esize = *(const WORD*)(pFormat+2);
TRACE("(%p, %p, %p)\n", pStubMsg, pMemory, pFormat); TRACE("(%p, %p, %p)\n", pStubMsg, pMemory, pFormat);
if (pFormat[0] != RPC_FC_CVARRAY) if (pFormat[0] != RPC_FC_CVARRAY)
@ -3581,19 +3641,9 @@ void WINAPI NdrConformantVaryingArrayBufferSize( PMIDL_STUB_MESSAGE pStubMsg,
return; return;
} }
/* compute size */ array_compute_and_size_conformance(RPC_FC_CVARRAY, pStubMsg, pMemory,
pFormat = ComputeConformance(pStubMsg, pMemory, pFormat+4, 0); pFormat);
/* compute length */ array_buffer_size(RPC_FC_CVARRAY, pStubMsg, pMemory, pFormat);
pFormat = ComputeVariance(pStubMsg, pMemory, pFormat, 0);
SizeConformance(pStubMsg);
SizeVariance(pStubMsg);
ALIGN_LENGTH(pStubMsg->BufferLength, alignment);
safe_buffer_length_increment(pStubMsg, safe_multiply(esize, pStubMsg->ActualCount));
EmbeddedPointerBufferSize(pStubMsg, pMemory, pFormat);
} }
@ -3603,10 +3653,6 @@ void WINAPI NdrConformantVaryingArrayBufferSize( PMIDL_STUB_MESSAGE pStubMsg,
ULONG WINAPI NdrConformantVaryingArrayMemorySize( PMIDL_STUB_MESSAGE pStubMsg, ULONG WINAPI NdrConformantVaryingArrayMemorySize( PMIDL_STUB_MESSAGE pStubMsg,
PFORMAT_STRING pFormat ) PFORMAT_STRING pFormat )
{ {
ULONG bufsize, memsize;
unsigned char alignment = pFormat[1] + 1;
DWORD esize = *(const WORD*)(pFormat+2);
TRACE("(%p, %p)\n", pStubMsg, pFormat); TRACE("(%p, %p)\n", pStubMsg, pFormat);
if (pFormat[0] != RPC_FC_CVARRAY) if (pFormat[0] != RPC_FC_CVARRAY)
@ -3616,18 +3662,8 @@ ULONG WINAPI NdrConformantVaryingArrayMemorySize( PMIDL_STUB_MESSAGE pStubMsg,
return pStubMsg->MemorySize; return pStubMsg->MemorySize;
} }
pFormat = ReadConformance(pStubMsg, pFormat+4); array_read_conformance(RPC_FC_CVARRAY, pStubMsg, pFormat);
pFormat = ReadVariance(pStubMsg, pFormat, pStubMsg->MaxCount); array_memory_size(RPC_FC_CVARRAY, pStubMsg, pFormat);
ALIGN_POINTER(pStubMsg->Buffer, alignment);
bufsize = safe_multiply(esize, pStubMsg->ActualCount);
memsize = safe_multiply(esize, pStubMsg->MaxCount);
safe_buffer_increment(pStubMsg, bufsize);
pStubMsg->MemorySize += memsize;
EmbeddedPointerMemorySize(pStubMsg, pFormat);
return pStubMsg->MemorySize; return pStubMsg->MemorySize;
} }