Commit 19fecc4f authored by Hans Leidekker's avatar Hans Leidekker Committed by Alexandre Julliard

webservices: Add generic property handlers.

parent f52accf8
...@@ -29,12 +29,7 @@ ...@@ -29,12 +29,7 @@
WINE_DEFAULT_DEBUG_CHANNEL(webservices); WINE_DEFAULT_DEBUG_CHANNEL(webservices);
static const struct static const struct prop_desc channel_props[] =
{
ULONG size;
BOOL readonly;
}
channel_props[] =
{ {
{ sizeof(ULONG), FALSE }, /* WS_CHANNEL_PROPERTY_MAX_BUFFERED_MESSAGE_SIZE */ { sizeof(ULONG), FALSE }, /* WS_CHANNEL_PROPERTY_MAX_BUFFERED_MESSAGE_SIZE */
{ sizeof(UINT64), FALSE }, /* WS_CHANNEL_PROPERTY_MAX_STREAMED_MESSAGE_SIZE */ { sizeof(UINT64), FALSE }, /* WS_CHANNEL_PROPERTY_MAX_STREAMED_MESSAGE_SIZE */
...@@ -51,42 +46,14 @@ static struct channel *alloc_channel(void) ...@@ -51,42 +46,14 @@ static struct channel *alloc_channel(void)
{ {
static const ULONG count = sizeof(channel_props)/sizeof(channel_props[0]); static const ULONG count = sizeof(channel_props)/sizeof(channel_props[0]);
struct channel *ret; struct channel *ret;
ULONG i, size = sizeof(*ret) + count * sizeof(WS_CHANNEL_PROPERTY); ULONG size = sizeof(*ret) + prop_size( channel_props, count );
char *ptr;
for (i = 0; i < count; i++) size += channel_props[i].size;
if (!(ret = heap_alloc_zero( size ))) return NULL; if (!(ret = heap_alloc_zero( size ))) return NULL;
prop_init( channel_props, count, ret->prop, &ret[1] );
ptr = (char *)&ret->prop[count];
for (i = 0; i < count; i++)
{
ret->prop[i].value = ptr;
ret->prop[i].valueSize = channel_props[i].size;
ptr += ret->prop[i].valueSize;
}
ret->prop_count = count; ret->prop_count = count;
return ret; return ret;
} }
static HRESULT set_channel_prop( struct channel *channel, WS_CHANNEL_PROPERTY_ID id, const void *value,
ULONG size )
{
if (id >= channel->prop_count || size != channel_props[id].size || channel_props[id].readonly)
return E_INVALIDARG;
memcpy( channel->prop[id].value, value, size );
return S_OK;
}
static HRESULT get_channel_prop( struct channel *channel, WS_CHANNEL_PROPERTY_ID id, void *buf, ULONG size )
{
if (id >= channel->prop_count || size != channel_props[id].size)
return E_INVALIDARG;
memcpy( buf, channel->prop[id].value, channel->prop[id].valueSize );
return S_OK;
}
void free_channel( struct channel *channel ) void free_channel( struct channel *channel )
{ {
heap_free( channel ); heap_free( channel );
...@@ -101,11 +68,13 @@ HRESULT create_channel( WS_CHANNEL_TYPE type, WS_CHANNEL_BINDING binding, ...@@ -101,11 +68,13 @@ HRESULT create_channel( WS_CHANNEL_TYPE type, WS_CHANNEL_BINDING binding,
if (!(channel = alloc_channel())) return E_OUTOFMEMORY; if (!(channel = alloc_channel())) return E_OUTOFMEMORY;
set_channel_prop( channel, WS_CHANNEL_PROPERTY_MAX_BUFFERED_MESSAGE_SIZE, &msg_size, sizeof(msg_size) ); prop_set( channel->prop, channel->prop_count, WS_CHANNEL_PROPERTY_MAX_BUFFERED_MESSAGE_SIZE,
&msg_size, sizeof(msg_size) );
for (i = 0; i < count; i++) for (i = 0; i < count; i++)
{ {
hr = set_channel_prop( channel, properties[i].id, properties[i].value, properties[i].valueSize ); hr = prop_set( channel->prop, channel->prop_count, properties[i].id, properties[i].value,
properties[i].valueSize );
if (hr != S_OK) if (hr != S_OK)
{ {
free_channel( channel ); free_channel( channel );
...@@ -177,7 +146,7 @@ HRESULT WINAPI WsGetChannelProperty( WS_CHANNEL *handle, WS_CHANNEL_PROPERTY_ID ...@@ -177,7 +146,7 @@ HRESULT WINAPI WsGetChannelProperty( WS_CHANNEL *handle, WS_CHANNEL_PROPERTY_ID
TRACE( "%p %u %p %u %p\n", handle, id, buf, size, error ); TRACE( "%p %u %p %u %p\n", handle, id, buf, size, error );
if (error) FIXME( "ignoring error parameter\n" ); if (error) FIXME( "ignoring error parameter\n" );
return get_channel_prop( channel, id, buf, size ); return prop_get( channel->prop, channel->prop_count, id, buf, size );
} }
/************************************************************************** /**************************************************************************
...@@ -191,5 +160,5 @@ HRESULT WINAPI WsSetChannelProperty( WS_CHANNEL *handle, WS_CHANNEL_PROPERTY_ID ...@@ -191,5 +160,5 @@ HRESULT WINAPI WsSetChannelProperty( WS_CHANNEL *handle, WS_CHANNEL_PROPERTY_ID
TRACE( "%p %u %p %u\n", handle, id, value, size ); TRACE( "%p %u %p %u\n", handle, id, value, size );
if (error) FIXME( "ignoring error parameter\n" ); if (error) FIXME( "ignoring error parameter\n" );
return set_channel_prop( channel, id, value, size ); return prop_set( channel->prop, channel->prop_count, id, value, size );
} }
...@@ -35,12 +35,42 @@ const char *debugstr_xmlstr( const WS_XML_STRING *str ) ...@@ -35,12 +35,42 @@ const char *debugstr_xmlstr( const WS_XML_STRING *str )
return debugstr_an( (const char *)str->bytes, str->length ); return debugstr_an( (const char *)str->bytes, str->length );
} }
static const struct ULONG prop_size( const struct prop_desc *desc, ULONG count )
{ {
ULONG size; ULONG i, ret = count * sizeof(struct prop);
BOOL readonly; for (i = 0; i < count; i++) ret += desc[i].size;
return ret;
}
void prop_init( const struct prop_desc *desc, ULONG count, struct prop *prop, void *data )
{
ULONG i;
char *ptr = data;
for (i = 0; i < count; i++)
{
prop[i].value = ptr;
prop[i].size = desc[i].size;
prop[i].readonly = desc[i].readonly;
prop[i].writeonly = desc[i].writeonly;
ptr += prop[i].size;
}
} }
error_props[] =
HRESULT prop_set( const struct prop *prop, ULONG count, ULONG id, const void *value, ULONG size )
{
if (id >= count || size != prop[id].size || prop[id].readonly) return E_INVALIDARG;
memcpy( prop[id].value, value, size );
return S_OK;
}
HRESULT prop_get( const struct prop *prop, ULONG count, ULONG id, void *buf, ULONG size )
{
if (id >= count || size != prop[id].size || prop[id].writeonly) return E_INVALIDARG;
memcpy( buf, prop[id].value, prop[id].size );
return S_OK;
}
static const struct prop_desc error_props[] =
{ {
{ sizeof(ULONG), TRUE }, /* WS_ERROR_PROPERTY_STRING_COUNT */ { sizeof(ULONG), TRUE }, /* WS_ERROR_PROPERTY_STRING_COUNT */
{ sizeof(ULONG), FALSE }, /* WS_ERROR_PROPERTY_ORIGINAL_ERROR_CODE */ { sizeof(ULONG), FALSE }, /* WS_ERROR_PROPERTY_ORIGINAL_ERROR_CODE */
...@@ -49,49 +79,22 @@ error_props[] = ...@@ -49,49 +79,22 @@ error_props[] =
struct error struct error
{ {
ULONG prop_count; ULONG prop_count;
WS_ERROR_PROPERTY prop[sizeof(error_props)/sizeof(error_props[0])]; struct prop prop[sizeof(error_props)/sizeof(error_props[0])];
}; };
static struct error *alloc_error(void) static struct error *alloc_error(void)
{ {
static const ULONG count = sizeof(error_props)/sizeof(error_props[0]); static const ULONG count = sizeof(error_props)/sizeof(error_props[0]);
struct error *ret; struct error *ret;
ULONG i, size = sizeof(*ret) + count * sizeof(WS_ERROR_PROPERTY); ULONG size = sizeof(*ret) + prop_size( error_props, count );
char *ptr;
for (i = 0; i < count; i++) size += error_props[i].size;
if (!(ret = heap_alloc_zero( size ))) return NULL; if (!(ret = heap_alloc_zero( size ))) return NULL;
prop_init( error_props, count, ret->prop, &ret[1] );
ptr = (char *)&ret->prop[count];
for (i = 0; i < count; i++)
{
ret->prop[i].value = ptr;
ret->prop[i].valueSize = error_props[i].size;
ptr += ret->prop[i].valueSize;
}
ret->prop_count = count; ret->prop_count = count;
return ret; return ret;
} }
static HRESULT set_error_prop( struct error *error, WS_ERROR_PROPERTY_ID id, const void *value, ULONG size )
{
if (id >= error->prop_count || size != error_props[id].size || error_props[id].readonly)
return E_INVALIDARG;
memcpy( error->prop[id].value, value, size );
return S_OK;
}
static HRESULT get_error_prop( struct error *error, WS_ERROR_PROPERTY_ID id, void *buf, ULONG size )
{
if (id >= error->prop_count || size != error_props[id].size)
return E_INVALIDARG;
memcpy( buf, error->prop[id].value, error->prop[id].valueSize );
return S_OK;
}
/************************************************************************** /**************************************************************************
* WsCreateError [webservices.@] * WsCreateError [webservices.@]
*/ */
...@@ -107,7 +110,7 @@ HRESULT WINAPI WsCreateError( const WS_ERROR_PROPERTY *properties, ULONG count, ...@@ -107,7 +110,7 @@ HRESULT WINAPI WsCreateError( const WS_ERROR_PROPERTY *properties, ULONG count,
if (!handle) return E_INVALIDARG; if (!handle) return E_INVALIDARG;
if (!(error = alloc_error())) return E_OUTOFMEMORY; if (!(error = alloc_error())) return E_OUTOFMEMORY;
set_error_prop( error, WS_ERROR_PROPERTY_LANGID, &langid, sizeof(langid) ); prop_set( error->prop, error->prop_count, WS_ERROR_PROPERTY_LANGID, &langid, sizeof(langid) );
for (i = 0; i < count; i++) for (i = 0; i < count; i++)
{ {
if (properties[i].id == WS_ERROR_PROPERTY_ORIGINAL_ERROR_CODE) if (properties[i].id == WS_ERROR_PROPERTY_ORIGINAL_ERROR_CODE)
...@@ -115,7 +118,8 @@ HRESULT WINAPI WsCreateError( const WS_ERROR_PROPERTY *properties, ULONG count, ...@@ -115,7 +118,8 @@ HRESULT WINAPI WsCreateError( const WS_ERROR_PROPERTY *properties, ULONG count,
heap_free( error ); heap_free( error );
return E_INVALIDARG; return E_INVALIDARG;
} }
hr = set_error_prop( error, properties[i].id, properties[i].value, properties[i].valueSize ); hr = prop_set( error->prop, error->prop_count, properties[i].id, properties[i].value,
properties[i].valueSize );
if (hr != S_OK) if (hr != S_OK)
{ {
heap_free( error ); heap_free( error );
...@@ -138,12 +142,7 @@ void WINAPI WsFreeError( WS_ERROR *handle ) ...@@ -138,12 +142,7 @@ void WINAPI WsFreeError( WS_ERROR *handle )
heap_free( error ); heap_free( error );
} }
static const struct static const struct prop_desc heap_props[] =
{
ULONG size;
BOOL readonly;
}
heap_props[] =
{ {
{ sizeof(SIZE_T), FALSE }, /* WS_HEAP_PROPERTY_MAX_SIZE */ { sizeof(SIZE_T), FALSE }, /* WS_HEAP_PROPERTY_MAX_SIZE */
{ sizeof(SIZE_T), FALSE }, /* WS_HEAP_PROPERTY_TRIM_SIZE */ { sizeof(SIZE_T), FALSE }, /* WS_HEAP_PROPERTY_TRIM_SIZE */
...@@ -153,9 +152,9 @@ heap_props[] = ...@@ -153,9 +152,9 @@ heap_props[] =
struct heap struct heap
{ {
HANDLE handle; HANDLE handle;
ULONG prop_count; ULONG prop_count;
WS_HEAP_PROPERTY prop[sizeof(heap_props)/sizeof(heap_props[0])]; struct prop prop[sizeof(heap_props)/sizeof(heap_props[0])];
}; };
void *ws_alloc( WS_HEAP *handle, SIZE_T size ) void *ws_alloc( WS_HEAP *handle, SIZE_T size )
...@@ -209,41 +208,14 @@ static struct heap *alloc_heap(void) ...@@ -209,41 +208,14 @@ static struct heap *alloc_heap(void)
{ {
static const ULONG count = sizeof(heap_props)/sizeof(heap_props[0]); static const ULONG count = sizeof(heap_props)/sizeof(heap_props[0]);
struct heap *ret; struct heap *ret;
ULONG i, size = sizeof(*ret) + count * sizeof(WS_HEAP_PROPERTY); ULONG size = sizeof(*ret) + prop_size( heap_props, count );
char *ptr;
for (i = 0; i < count; i++) size += heap_props[i].size;
if (!(ret = heap_alloc_zero( size ))) return NULL; if (!(ret = heap_alloc_zero( size ))) return NULL;
prop_init( heap_props, count, ret->prop, &ret[1] );
ptr = (char *)&ret->prop[count];
for (i = 0; i < count; i++)
{
ret->prop[i].value = ptr;
ret->prop[i].valueSize = heap_props[i].size;
ptr += ret->prop[i].valueSize;
}
ret->prop_count = count; ret->prop_count = count;
return ret; return ret;
} }
static HRESULT set_heap_prop( struct heap *heap, WS_HEAP_PROPERTY_ID id, const void *value, ULONG size )
{
if (id >= heap->prop_count || size != heap_props[id].size || heap_props[id].readonly)
return E_INVALIDARG;
memcpy( heap->prop[id].value, value, size );
return S_OK;
}
static HRESULT get_heap_prop( struct heap *heap, WS_HEAP_PROPERTY_ID id, void *buf, ULONG size )
{
if (id >= heap->prop_count || size != heap_props[id].size)
return E_INVALIDARG;
memcpy( buf, heap->prop[id].value, heap->prop[id].valueSize );
return S_OK;
}
/************************************************************************** /**************************************************************************
* WsCreateHeap [webservices.@] * WsCreateHeap [webservices.@]
*/ */
...@@ -258,8 +230,8 @@ HRESULT WINAPI WsCreateHeap( SIZE_T max_size, SIZE_T trim_size, const WS_HEAP_PR ...@@ -258,8 +230,8 @@ HRESULT WINAPI WsCreateHeap( SIZE_T max_size, SIZE_T trim_size, const WS_HEAP_PR
if (!handle || count) return E_INVALIDARG; if (!handle || count) return E_INVALIDARG;
if (!(heap = alloc_heap())) return E_OUTOFMEMORY; if (!(heap = alloc_heap())) return E_OUTOFMEMORY;
set_heap_prop( heap, WS_HEAP_PROPERTY_MAX_SIZE, &max_size, sizeof(max_size) ); prop_set( heap->prop, heap->prop_count, WS_HEAP_PROPERTY_MAX_SIZE, &max_size, sizeof(max_size) );
set_heap_prop( heap, WS_HEAP_PROPERTY_TRIM_SIZE, &trim_size, sizeof(trim_size) ); prop_set( heap->prop, heap->prop_count, WS_HEAP_PROPERTY_TRIM_SIZE, &trim_size, sizeof(trim_size) );
if (!(heap->handle = HeapCreate( 0, 0, max_size ))) if (!(heap->handle = HeapCreate( 0, 0, max_size )))
{ {
...@@ -363,12 +335,7 @@ void destroy_nodes( struct node *node ) ...@@ -363,12 +335,7 @@ void destroy_nodes( struct node *node )
free_node( node ); free_node( node );
} }
static const struct static const struct prop_desc reader_props[] =
{
ULONG size;
BOOL readonly;
}
reader_props[] =
{ {
{ sizeof(ULONG), FALSE }, /* WS_XML_READER_PROPERTY_MAX_DEPTH */ { sizeof(ULONG), FALSE }, /* WS_XML_READER_PROPERTY_MAX_DEPTH */
{ sizeof(BOOL), FALSE }, /* WS_XML_READER_PROPERTY_ALLOW_FRAGMENT */ { sizeof(BOOL), FALSE }, /* WS_XML_READER_PROPERTY_ALLOW_FRAGMENT */
...@@ -424,19 +391,16 @@ struct reader ...@@ -424,19 +391,16 @@ struct reader
const unsigned char *input_data; const unsigned char *input_data;
ULONG input_size; ULONG input_size;
ULONG prop_count; ULONG prop_count;
WS_XML_READER_PROPERTY prop[sizeof(reader_props)/sizeof(reader_props[0])]; struct prop prop[sizeof(reader_props)/sizeof(reader_props[0])];
}; };
static struct reader *alloc_reader(void) static struct reader *alloc_reader(void)
{ {
static const ULONG count = sizeof(reader_props)/sizeof(reader_props[0]); static const ULONG count = sizeof(reader_props)/sizeof(reader_props[0]);
struct reader *ret; struct reader *ret;
ULONG i, size = sizeof(*ret) + count * sizeof(WS_XML_READER_PROPERTY); ULONG size = sizeof(*ret) + prop_size( reader_props, count );
char *ptr;
for (i = 0; i < count; i++) size += reader_props[i].size;
if (!(ret = heap_alloc_zero( size ))) return NULL; if (!(ret = heap_alloc_zero( size ))) return NULL;
if (!(ret->prefixes = heap_alloc_zero( sizeof(*ret->prefixes) ))) if (!(ret->prefixes = heap_alloc_zero( sizeof(*ret->prefixes) )))
{ {
heap_free( ret ); heap_free( ret );
...@@ -444,13 +408,7 @@ static struct reader *alloc_reader(void) ...@@ -444,13 +408,7 @@ static struct reader *alloc_reader(void)
} }
ret->nb_prefixes = ret->nb_prefixes_allocated = 1; ret->nb_prefixes = ret->nb_prefixes_allocated = 1;
ptr = (char *)&ret->prop[count]; prop_init( reader_props, count, ret->prop, &ret[1] );
for (i = 0; i < count; i++)
{
ret->prop[i].value = ptr;
ret->prop[i].valueSize = reader_props[i].size;
ptr += ret->prop[i].valueSize;
}
ret->prop_count = count; ret->prop_count = count;
return ret; return ret;
} }
...@@ -532,24 +490,6 @@ static const WS_XML_STRING *get_namespace( struct reader *reader, const WS_XML_S ...@@ -532,24 +490,6 @@ static const WS_XML_STRING *get_namespace( struct reader *reader, const WS_XML_S
return NULL; return NULL;
} }
static HRESULT set_reader_prop( struct reader *reader, WS_XML_READER_PROPERTY_ID id, const void *value, ULONG size )
{
if (id >= reader->prop_count || size != reader_props[id].size || reader_props[id].readonly)
return E_INVALIDARG;
memcpy( reader->prop[id].value, value, size );
return S_OK;
}
static HRESULT get_reader_prop( struct reader *reader, WS_XML_READER_PROPERTY_ID id, void *buf, ULONG size )
{
if (id >= reader->prop_count || size != reader_props[id].size)
return E_INVALIDARG;
memcpy( buf, reader->prop[id].value, reader->prop[id].valueSize );
return S_OK;
}
static void read_insert_eof( struct reader *reader, struct node *eof ) static void read_insert_eof( struct reader *reader, struct node *eof )
{ {
if (!reader->root) reader->root = eof; if (!reader->root) reader->root = eof;
...@@ -612,15 +552,16 @@ HRESULT WINAPI WsCreateReader( const WS_XML_READER_PROPERTY *properties, ULONG c ...@@ -612,15 +552,16 @@ HRESULT WINAPI WsCreateReader( const WS_XML_READER_PROPERTY *properties, ULONG c
if (!handle) return E_INVALIDARG; if (!handle) return E_INVALIDARG;
if (!(reader = alloc_reader())) return E_OUTOFMEMORY; if (!(reader = alloc_reader())) return E_OUTOFMEMORY;
set_reader_prop( reader, WS_XML_READER_PROPERTY_MAX_DEPTH, &max_depth, sizeof(max_depth) ); prop_set( reader->prop, reader->prop_count, WS_XML_READER_PROPERTY_MAX_DEPTH, &max_depth, sizeof(max_depth) );
set_reader_prop( reader, WS_XML_READER_PROPERTY_MAX_ATTRIBUTES, &max_attrs, sizeof(max_attrs) ); prop_set( reader->prop, reader->prop_count, WS_XML_READER_PROPERTY_MAX_ATTRIBUTES, &max_attrs, sizeof(max_attrs) );
set_reader_prop( reader, WS_XML_READER_PROPERTY_READ_DECLARATION, &read_decl, sizeof(read_decl) ); prop_set( reader->prop, reader->prop_count, WS_XML_READER_PROPERTY_READ_DECLARATION, &read_decl, sizeof(read_decl) );
set_reader_prop( reader, WS_XML_READER_PROPERTY_CHARSET, &charset, sizeof(charset) ); prop_set( reader->prop, reader->prop_count, WS_XML_READER_PROPERTY_CHARSET, &charset, sizeof(charset) );
set_reader_prop( reader, WS_XML_READER_PROPERTY_MAX_NAMESPACES, &max_ns, sizeof(max_ns) ); prop_set( reader->prop, reader->prop_count, WS_XML_READER_PROPERTY_MAX_NAMESPACES, &max_ns, sizeof(max_ns) );
for (i = 0; i < count; i++) for (i = 0; i < count; i++)
{ {
hr = set_reader_prop( reader, properties[i].id, properties[i].value, properties[i].valueSize ); hr = prop_set( reader->prop, reader->prop_count, properties[i].id, properties[i].value,
properties[i].valueSize );
if (hr != S_OK) if (hr != S_OK)
{ {
free_reader( reader ); free_reader( reader );
...@@ -678,7 +619,7 @@ HRESULT WINAPI WsGetErrorProperty( WS_ERROR *handle, WS_ERROR_PROPERTY_ID id, vo ...@@ -678,7 +619,7 @@ HRESULT WINAPI WsGetErrorProperty( WS_ERROR *handle, WS_ERROR_PROPERTY_ID id, vo
struct error *error = (struct error *)handle; struct error *error = (struct error *)handle;
TRACE( "%p %u %p %u\n", handle, id, buf, size ); TRACE( "%p %u %p %u\n", handle, id, buf, size );
return get_error_prop( error, id, buf, size ); return prop_get( error->prop, error->prop_count, id, buf, size );
} }
/************************************************************************** /**************************************************************************
...@@ -701,7 +642,7 @@ HRESULT WINAPI WsGetHeapProperty( WS_HEAP *handle, WS_HEAP_PROPERTY_ID id, void ...@@ -701,7 +642,7 @@ HRESULT WINAPI WsGetHeapProperty( WS_HEAP *handle, WS_HEAP_PROPERTY_ID id, void
TRACE( "%p %u %p %u %p\n", handle, id, buf, size, error ); TRACE( "%p %u %p %u %p\n", handle, id, buf, size, error );
if (error) FIXME( "ignoring error parameter\n" ); if (error) FIXME( "ignoring error parameter\n" );
return get_heap_prop( heap, id, buf, size ); return prop_get( heap->prop, heap->prop_count, id, buf, size );
} }
/************************************************************************** /**************************************************************************
...@@ -800,12 +741,12 @@ HRESULT WINAPI WsGetReaderProperty( WS_XML_READER *handle, WS_XML_READER_PROPERT ...@@ -800,12 +741,12 @@ HRESULT WINAPI WsGetReaderProperty( WS_XML_READER *handle, WS_XML_READER_PROPERT
WS_CHARSET charset; WS_CHARSET charset;
HRESULT hr; HRESULT hr;
if ((hr = get_reader_prop( reader, id, &charset, size )) != S_OK) return hr; if ((hr = prop_get( reader->prop, reader->prop_count, id, &charset, size )) != S_OK) return hr;
if (!charset) return WS_E_INVALID_FORMAT; if (!charset) return WS_E_INVALID_FORMAT;
*(WS_CHARSET *)buf = charset; *(WS_CHARSET *)buf = charset;
return S_OK; return S_OK;
} }
return get_reader_prop( reader, id, buf, size ); return prop_get( reader->prop, reader->prop_count, id, buf, size );
} }
/************************************************************************** /**************************************************************************
...@@ -3073,7 +3014,7 @@ HRESULT WINAPI WsSetErrorProperty( WS_ERROR *handle, WS_ERROR_PROPERTY_ID id, co ...@@ -3073,7 +3014,7 @@ HRESULT WINAPI WsSetErrorProperty( WS_ERROR *handle, WS_ERROR_PROPERTY_ID id, co
TRACE( "%p %u %p %u\n", handle, id, value, size ); TRACE( "%p %u %p %u\n", handle, id, value, size );
if (id == WS_ERROR_PROPERTY_LANGID) return WS_E_INVALID_OPERATION; if (id == WS_ERROR_PROPERTY_LANGID) return WS_E_INVALID_OPERATION;
return set_error_prop( error, id, value, size ); return prop_set( error->prop, error->prop_count, id, value, size );
} }
static inline BOOL is_utf8( const unsigned char *data, ULONG size, ULONG *offset ) static inline BOOL is_utf8( const unsigned char *data, ULONG size, ULONG *offset )
...@@ -3142,7 +3083,8 @@ HRESULT WINAPI WsSetInput( WS_XML_READER *handle, const WS_XML_READER_ENCODING * ...@@ -3142,7 +3083,8 @@ HRESULT WINAPI WsSetInput( WS_XML_READER *handle, const WS_XML_READER_ENCODING *
for (i = 0; i < count; i++) for (i = 0; i < count; i++)
{ {
hr = set_reader_prop( reader, properties[i].id, properties[i].value, properties[i].valueSize ); hr = prop_set( reader->prop, reader->prop_count, properties[i].id, properties[i].value,
properties[i].valueSize );
if (hr != S_OK) return hr; if (hr != S_OK) return hr;
} }
...@@ -3165,7 +3107,8 @@ HRESULT WINAPI WsSetInput( WS_XML_READER *handle, const WS_XML_READER_ENCODING * ...@@ -3165,7 +3107,8 @@ HRESULT WINAPI WsSetInput( WS_XML_READER *handle, const WS_XML_READER_ENCODING *
if (charset == WS_CHARSET_AUTO) if (charset == WS_CHARSET_AUTO)
charset = detect_charset( buf->encodedData, buf->encodedDataSize, &offset ); charset = detect_charset( buf->encodedData, buf->encodedDataSize, &offset );
hr = set_reader_prop( reader, WS_XML_READER_PROPERTY_CHARSET, &charset, sizeof(charset) ); hr = prop_set( reader->prop, reader->prop_count, WS_XML_READER_PROPERTY_CHARSET,
&charset, sizeof(charset) );
if (hr != S_OK) return hr; if (hr != S_OK) return hr;
break; break;
} }
...@@ -3212,14 +3155,16 @@ HRESULT WINAPI WsSetInputToBuffer( WS_XML_READER *handle, WS_XML_BUFFER *buffer, ...@@ -3212,14 +3155,16 @@ HRESULT WINAPI WsSetInputToBuffer( WS_XML_READER *handle, WS_XML_BUFFER *buffer,
for (i = 0; i < count; i++) for (i = 0; i < count; i++)
{ {
hr = set_reader_prop( reader, properties[i].id, properties[i].value, properties[i].valueSize ); hr = prop_set( reader->prop, reader->prop_count, properties[i].id, properties[i].value,
properties[i].valueSize );
if (hr != S_OK) return hr; if (hr != S_OK) return hr;
} }
if ((hr = read_init_state( reader )) != S_OK) return hr; if ((hr = read_init_state( reader )) != S_OK) return hr;
charset = detect_charset( xmlbuf->ptr, xmlbuf->size, &offset ); charset = detect_charset( xmlbuf->ptr, xmlbuf->size, &offset );
hr = set_reader_prop( reader, WS_XML_READER_PROPERTY_CHARSET, &charset, sizeof(charset) ); hr = prop_set( reader->prop, reader->prop_count, WS_XML_READER_PROPERTY_CHARSET,
&charset, sizeof(charset) );
if (hr != S_OK) return hr; if (hr != S_OK) return hr;
set_input_buffer( reader, (const unsigned char *)xmlbuf->ptr + offset, xmlbuf->size - offset ); set_input_buffer( reader, (const unsigned char *)xmlbuf->ptr + offset, xmlbuf->size - offset );
......
...@@ -50,12 +50,32 @@ static inline WS_XML_NODE_TYPE node_type( const struct node *node ) ...@@ -50,12 +50,32 @@ static inline WS_XML_NODE_TYPE node_type( const struct node *node )
return node->hdr.node.nodeType; return node->hdr.node.nodeType;
} }
struct prop_desc
{
ULONG size;
BOOL readonly;
BOOL writeonly;
};
struct prop
{
void *value;
ULONG size;
BOOL readonly;
BOOL writeonly;
};
ULONG prop_size( const struct prop_desc *, ULONG ) DECLSPEC_HIDDEN;
void prop_init( const struct prop_desc *, ULONG, struct prop *, void * ) DECLSPEC_HIDDEN;
HRESULT prop_set( const struct prop *, ULONG, ULONG, const void *, ULONG ) DECLSPEC_HIDDEN;
HRESULT prop_get( const struct prop *, ULONG, ULONG, void *, ULONG ) DECLSPEC_HIDDEN;
struct channel struct channel
{ {
WS_CHANNEL_TYPE type; WS_CHANNEL_TYPE type;
WS_CHANNEL_BINDING binding; WS_CHANNEL_BINDING binding;
ULONG prop_count; ULONG prop_count;
WS_CHANNEL_PROPERTY prop[9]; struct prop prop[9];
}; };
HRESULT create_channel( WS_CHANNEL_TYPE, WS_CHANNEL_BINDING, const WS_CHANNEL_PROPERTY *, HRESULT create_channel( WS_CHANNEL_TYPE, WS_CHANNEL_BINDING, const WS_CHANNEL_PROPERTY *,
......
...@@ -30,12 +30,7 @@ ...@@ -30,12 +30,7 @@
WINE_DEFAULT_DEBUG_CHANNEL(webservices); WINE_DEFAULT_DEBUG_CHANNEL(webservices);
static const struct static const struct prop_desc writer_props[] =
{
ULONG size;
BOOL readonly;
}
writer_props[] =
{ {
{ sizeof(ULONG), FALSE }, /* WS_XML_WRITER_PROPERTY_MAX_DEPTH */ { sizeof(ULONG), FALSE }, /* WS_XML_WRITER_PROPERTY_MAX_DEPTH */
{ sizeof(BOOL), FALSE }, /* WS_XML_WRITER_PROPERTY_ALLOW_FRAGMENT */ { sizeof(BOOL), FALSE }, /* WS_XML_WRITER_PROPERTY_ALLOW_FRAGMENT */
...@@ -83,49 +78,21 @@ struct writer ...@@ -83,49 +78,21 @@ struct writer
struct xmlbuf *output_buf; struct xmlbuf *output_buf;
WS_HEAP *output_heap; WS_HEAP *output_heap;
ULONG prop_count; ULONG prop_count;
WS_XML_WRITER_PROPERTY prop[sizeof(writer_props)/sizeof(writer_props[0])]; struct prop prop[sizeof(writer_props)/sizeof(writer_props[0])];
}; };
static struct writer *alloc_writer(void) static struct writer *alloc_writer(void)
{ {
static const ULONG count = sizeof(writer_props)/sizeof(writer_props[0]); static const ULONG count = sizeof(writer_props)/sizeof(writer_props[0]);
struct writer *ret; struct writer *ret;
ULONG i, size = sizeof(*ret) + count * sizeof(WS_XML_WRITER_PROPERTY); ULONG size = sizeof(*ret) + prop_size( writer_props, count );
char *ptr;
for (i = 0; i < count; i++) size += writer_props[i].size;
if (!(ret = heap_alloc_zero( size ))) return NULL; if (!(ret = heap_alloc_zero( size ))) return NULL;
prop_init( writer_props, count, ret->prop, &ret[1] );
ptr = (char *)&ret->prop[count];
for (i = 0; i < count; i++)
{
ret->prop[i].value = ptr;
ret->prop[i].valueSize = writer_props[i].size;
ptr += ret->prop[i].valueSize;
}
ret->prop_count = count; ret->prop_count = count;
return ret; return ret;
} }
static HRESULT set_writer_prop( struct writer *writer, WS_XML_WRITER_PROPERTY_ID id, const void *value,
ULONG size )
{
if (id >= writer->prop_count || size != writer_props[id].size || writer_props[id].readonly)
return E_INVALIDARG;
memcpy( writer->prop[id].value, value, size );
return S_OK;
}
static HRESULT get_writer_prop( struct writer *writer, WS_XML_WRITER_PROPERTY_ID id, void *buf, ULONG size )
{
if (id >= writer->prop_count || size != writer_props[id].size)
return E_INVALIDARG;
memcpy( buf, writer->prop[id].value, writer->prop[id].valueSize );
return S_OK;
}
static void free_writer( struct writer *writer ) static void free_writer( struct writer *writer )
{ {
destroy_nodes( writer->root ); destroy_nodes( writer->root );
...@@ -196,17 +163,18 @@ HRESULT WINAPI WsCreateWriter( const WS_XML_WRITER_PROPERTY *properties, ULONG c ...@@ -196,17 +163,18 @@ HRESULT WINAPI WsCreateWriter( const WS_XML_WRITER_PROPERTY *properties, ULONG c
if (!handle) return E_INVALIDARG; if (!handle) return E_INVALIDARG;
if (!(writer = alloc_writer())) return E_OUTOFMEMORY; if (!(writer = alloc_writer())) return E_OUTOFMEMORY;
set_writer_prop( writer, WS_XML_WRITER_PROPERTY_MAX_DEPTH, &max_depth, sizeof(max_depth) ); prop_set( writer->prop, writer->prop_count, WS_XML_WRITER_PROPERTY_MAX_DEPTH, &max_depth, sizeof(max_depth) );
set_writer_prop( writer, WS_XML_WRITER_PROPERTY_MAX_ATTRIBUTES, &max_attrs, sizeof(max_attrs) ); prop_set( writer->prop, writer->prop_count, WS_XML_WRITER_PROPERTY_MAX_ATTRIBUTES, &max_attrs, sizeof(max_attrs) );
set_writer_prop( writer, WS_XML_WRITER_PROPERTY_BUFFER_TRIM_SIZE, &trim_size, sizeof(trim_size) ); prop_set( writer->prop, writer->prop_count, WS_XML_WRITER_PROPERTY_BUFFER_TRIM_SIZE, &trim_size, sizeof(trim_size) );
set_writer_prop( writer, WS_XML_WRITER_PROPERTY_CHARSET, &charset, sizeof(charset) ); prop_set( writer->prop, writer->prop_count, WS_XML_WRITER_PROPERTY_CHARSET, &charset, sizeof(charset) );
set_writer_prop( writer, WS_XML_WRITER_PROPERTY_BUFFER_MAX_SIZE, &max_size, sizeof(max_size) ); prop_set( writer->prop, writer->prop_count, WS_XML_WRITER_PROPERTY_BUFFER_MAX_SIZE, &max_size, sizeof(max_size) );
set_writer_prop( writer, WS_XML_WRITER_PROPERTY_MAX_MIME_PARTS_BUFFER_SIZE, &max_size, sizeof(max_size) ); prop_set( writer->prop, writer->prop_count, WS_XML_WRITER_PROPERTY_MAX_MIME_PARTS_BUFFER_SIZE, &max_size, sizeof(max_size) );
set_writer_prop( writer, WS_XML_WRITER_PROPERTY_MAX_NAMESPACES, &max_ns, sizeof(max_ns) ); prop_set( writer->prop, writer->prop_count, WS_XML_WRITER_PROPERTY_MAX_NAMESPACES, &max_ns, sizeof(max_ns) );
for (i = 0; i < count; i++) for (i = 0; i < count; i++)
{ {
hr = set_writer_prop( writer, properties[i].id, properties[i].value, properties[i].valueSize ); hr = prop_set( writer->prop, writer->prop_count, properties[i].id, properties[i].value,
properties[i].valueSize );
if (hr != S_OK) if (hr != S_OK)
{ {
free_writer( writer ); free_writer( writer );
...@@ -214,7 +182,8 @@ HRESULT WINAPI WsCreateWriter( const WS_XML_WRITER_PROPERTY *properties, ULONG c ...@@ -214,7 +182,8 @@ HRESULT WINAPI WsCreateWriter( const WS_XML_WRITER_PROPERTY *properties, ULONG c
} }
} }
hr = get_writer_prop( writer, WS_XML_WRITER_PROPERTY_BUFFER_MAX_SIZE, &max_size, sizeof(max_size) ); hr = prop_get( writer->prop, writer->prop_count, WS_XML_WRITER_PROPERTY_BUFFER_MAX_SIZE,
&max_size, sizeof(max_size) );
if (hr != S_OK) if (hr != S_OK)
{ {
free_writer( writer ); free_writer( writer );
...@@ -315,7 +284,7 @@ HRESULT WINAPI WsGetWriterProperty( WS_XML_WRITER *handle, WS_XML_WRITER_PROPERT ...@@ -315,7 +284,7 @@ HRESULT WINAPI WsGetWriterProperty( WS_XML_WRITER *handle, WS_XML_WRITER_PROPERT
return S_OK; return S_OK;
} }
default: default:
return get_writer_prop( writer, id, buf, size ); return prop_get( writer->prop, writer->prop_count, id, buf, size );
} }
} }
...@@ -351,7 +320,8 @@ HRESULT WINAPI WsSetOutput( WS_XML_WRITER *handle, const WS_XML_WRITER_ENCODING ...@@ -351,7 +320,8 @@ HRESULT WINAPI WsSetOutput( WS_XML_WRITER *handle, const WS_XML_WRITER_ENCODING
for (i = 0; i < count; i++) for (i = 0; i < count; i++)
{ {
hr = set_writer_prop( writer, properties[i].id, properties[i].value, properties[i].valueSize ); hr = prop_set( writer->prop, writer->prop_count, properties[i].id, properties[i].value,
properties[i].valueSize );
if (hr != S_OK) return hr; if (hr != S_OK) return hr;
} }
...@@ -413,7 +383,8 @@ HRESULT WINAPI WsSetOutputToBuffer( WS_XML_WRITER *handle, WS_XML_BUFFER *buffer ...@@ -413,7 +383,8 @@ HRESULT WINAPI WsSetOutputToBuffer( WS_XML_WRITER *handle, WS_XML_BUFFER *buffer
for (i = 0; i < count; i++) for (i = 0; i < count; i++)
{ {
hr = set_writer_prop( writer, properties[i].id, properties[i].value, properties[i].valueSize ); hr = prop_set( writer->prop, writer->prop_count, properties[i].id, properties[i].value,
properties[i].valueSize );
if (hr != S_OK) return hr; if (hr != S_OK) return hr;
} }
...@@ -1686,7 +1657,8 @@ HRESULT WINAPI WsWriteXmlBufferToBytes( WS_XML_WRITER *handle, WS_XML_BUFFER *bu ...@@ -1686,7 +1657,8 @@ HRESULT WINAPI WsWriteXmlBufferToBytes( WS_XML_WRITER *handle, WS_XML_BUFFER *bu
for (i = 0; i < count; i++) for (i = 0; i < count; i++)
{ {
hr = set_writer_prop( writer, properties[i].id, properties[i].value, properties[i].valueSize ); hr = prop_set( writer->prop, writer->prop_count, properties[i].id, properties[i].value,
properties[i].valueSize );
if (hr != S_OK) return hr; if (hr != S_OK) return hr;
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment