wsdapi: Ignore duplicate messages.
Signed-off-by: Owen Rudge <orudge@codeweavers.com> Signed-off-by: Huw Davies <huw@codeweavers.com> Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
parent
8e1d40b966
commit
1a82fb88b2
|
@ -78,6 +78,7 @@ static ULONG WINAPI IWSDiscoveryPublisherImpl_Release(IWSDiscoveryPublisher *ifa
|
|||
IWSDiscoveryPublisherImpl *This = impl_from_IWSDiscoveryPublisher(iface);
|
||||
ULONG ref = InterlockedDecrement(&This->ref);
|
||||
struct notificationSink *sink, *cursor;
|
||||
struct message_id *msg_id, *msg_id_cursor;
|
||||
|
||||
TRACE("(%p) ref=%d\n", This, ref);
|
||||
|
||||
|
@ -98,6 +99,15 @@ static ULONG WINAPI IWSDiscoveryPublisherImpl_Release(IWSDiscoveryPublisher *ifa
|
|||
}
|
||||
|
||||
DeleteCriticalSection(&This->notification_sink_critical_section);
|
||||
|
||||
LIST_FOR_EACH_ENTRY_SAFE(msg_id, msg_id_cursor, &This->message_ids, struct message_id, entry)
|
||||
{
|
||||
heap_free(msg_id->id);
|
||||
list_remove(&msg_id->entry);
|
||||
heap_free(msg_id);
|
||||
}
|
||||
|
||||
DeleteCriticalSection(&This->message_ids_critical_section);
|
||||
HeapFree(GetProcessHeap(), 0, This);
|
||||
}
|
||||
|
||||
|
@ -402,6 +412,9 @@ HRESULT WINAPI WSDCreateDiscoveryPublisher(IWSDXMLContext *pContext, IWSDiscover
|
|||
InitializeCriticalSection(&obj->notification_sink_critical_section);
|
||||
list_init(&obj->notificationSinks);
|
||||
|
||||
InitializeCriticalSection(&obj->message_ids_critical_section);
|
||||
list_init(&obj->message_ids);
|
||||
|
||||
*ppPublisher = &obj->IWSDiscoveryPublisher_iface;
|
||||
TRACE("Returning iface %p\n", *ppPublisher);
|
||||
|
||||
|
|
|
@ -302,7 +302,7 @@ static HRESULT process_received_message(listener_thread_params *params, char *me
|
|||
int msg_type;
|
||||
HRESULT ret;
|
||||
|
||||
ret = read_message(message, message_len, &msg, &msg_type);
|
||||
ret = read_message(params->impl, message, message_len, &msg, &msg_type);
|
||||
if (FAILED(ret)) return ret;
|
||||
|
||||
switch (msg_type)
|
||||
|
|
|
@ -1488,7 +1488,44 @@ static WSDXML_TYPE *generate_type(LPCWSTR uri, void *parent)
|
|||
return type;
|
||||
}
|
||||
|
||||
HRESULT read_message(const char *xml, int xml_length, WSD_SOAP_MESSAGE **out_msg, int *msg_type)
|
||||
static BOOL is_duplicate_message(IWSDiscoveryPublisherImpl *impl, LPCWSTR id)
|
||||
{
|
||||
struct message_id *msg_id, *msg_id_cursor;
|
||||
BOOL ret = FALSE;
|
||||
int len;
|
||||
|
||||
EnterCriticalSection(&impl->message_ids_critical_section);
|
||||
|
||||
LIST_FOR_EACH_ENTRY_SAFE(msg_id, msg_id_cursor, &impl->message_ids, struct message_id, entry)
|
||||
{
|
||||
if (lstrcmpW(msg_id->id, id) == 0)
|
||||
{
|
||||
ret = TRUE;
|
||||
goto end;
|
||||
}
|
||||
}
|
||||
|
||||
msg_id = heap_alloc(sizeof(*msg_id));
|
||||
if (!msg_id) goto end;
|
||||
|
||||
len = (lstrlenW(id) + 1) * sizeof(WCHAR);
|
||||
msg_id->id = heap_alloc(len);
|
||||
|
||||
if (!msg_id->id)
|
||||
{
|
||||
heap_free(msg_id);
|
||||
goto end;
|
||||
}
|
||||
|
||||
memcpy(msg_id->id, id, len);
|
||||
list_add_tail(&impl->message_ids, &msg_id->entry);
|
||||
|
||||
end:
|
||||
LeaveCriticalSection(&impl->message_ids_critical_section);
|
||||
return ret;
|
||||
}
|
||||
|
||||
HRESULT read_message(IWSDiscoveryPublisherImpl *impl, const char *xml, int xml_length, WSD_SOAP_MESSAGE **out_msg, int *msg_type)
|
||||
{
|
||||
WSDXML_ELEMENT *envelope = NULL, *header_element, *appsequence_element, *body_element;
|
||||
WS_XML_READER_TEXT_ENCODING encoding;
|
||||
|
@ -1606,6 +1643,14 @@ HRESULT read_message(const char *xml, int xml_length, WSD_SOAP_MESSAGE **out_msg
|
|||
|
||||
ret = WSDXMLGetValueFromAny(addressingNsUri, messageIdString, (WSDXML_ELEMENT *) header_element->FirstChild, &value);
|
||||
if (FAILED(ret)) goto cleanup;
|
||||
|
||||
/* Detect duplicate messages */
|
||||
if (is_duplicate_message(impl, value))
|
||||
{
|
||||
ret = E_FAIL;
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
soap_msg->Header.MessageID = duplicate_string(soap_msg, value);
|
||||
if (soap_msg->Header.MessageID == NULL) goto outofmemory;
|
||||
|
||||
|
|
|
@ -40,6 +40,12 @@ struct notificationSink
|
|||
IWSDiscoveryPublisherNotify *notificationSink;
|
||||
};
|
||||
|
||||
struct message_id
|
||||
{
|
||||
struct list entry;
|
||||
LPWSTR id;
|
||||
};
|
||||
|
||||
#define MAX_WSD_THREADS 20
|
||||
|
||||
typedef struct IWSDiscoveryPublisherImpl {
|
||||
|
@ -52,6 +58,8 @@ typedef struct IWSDiscoveryPublisherImpl {
|
|||
BOOL publisherStarted;
|
||||
HANDLE thread_handles[MAX_WSD_THREADS];
|
||||
int num_thread_handles;
|
||||
struct list message_ids;
|
||||
CRITICAL_SECTION message_ids_critical_section;
|
||||
} IWSDiscoveryPublisherImpl;
|
||||
|
||||
/* network.c */
|
||||
|
@ -72,7 +80,8 @@ HRESULT send_bye_message(IWSDiscoveryPublisherImpl *impl, LPCWSTR id, ULONGLONG
|
|||
|
||||
HRESULT register_namespaces(IWSDXMLContext *xml_context);
|
||||
|
||||
HRESULT read_message(const char *xml, int xml_length, WSD_SOAP_MESSAGE **out_msg, int *msg_type);
|
||||
HRESULT read_message(IWSDiscoveryPublisherImpl *impl, const char *xml, int xml_length, WSD_SOAP_MESSAGE **out_msg,
|
||||
int *msg_type);
|
||||
|
||||
#define MSGTYPE_UNKNOWN 0
|
||||
#define MSGTYPE_PROBE 1
|
||||
|
|
Loading…
Reference in New Issue