Mike McCormack : ole32: Add a framework for implementing IEnum*
interfaces.
Alexandre Julliard
julliard at wine.codeweavers.com
Wed Jul 12 06:53:42 CDT 2006
Module: wine
Branch: master
Commit: 127ae2bf8b80c7f2b4a9d61fe6c318f1464ab585
URL: http://source.winehq.org/git/?p=wine.git;a=commit;h=127ae2bf8b80c7f2b4a9d61fe6c318f1464ab585
Author: Mike McCormack <mike at codeweavers.com>
Date: Tue Jul 11 16:12:38 2006 +0900
ole32: Add a framework for implementing IEnum* interfaces.
---
dlls/ole32/Makefile.in | 1
dlls/ole32/enumx.c | 202 ++++++++++++++++++++++++++++++++++++++++++++++++
dlls/ole32/enumx.h | 34 ++++++++
3 files changed, 237 insertions(+), 0 deletions(-)
create mode 100644 dlls/ole32/enumx.c
create mode 100644 dlls/ole32/enumx.h
diff --git a/dlls/ole32/Makefile.in b/dlls/ole32/Makefile.in
index 01b7ea6..0a44570 100644
--- a/dlls/ole32/Makefile.in
+++ b/dlls/ole32/Makefile.in
@@ -18,6 +18,7 @@ C_SRCS = \
datacache.c \
defaulthandler.c \
dictionary.c \
+ enumx.c \
errorinfo.c \
filemoniker.c \
ftmarshal.c \
diff --git a/dlls/ole32/enumx.c b/dlls/ole32/enumx.c
new file mode 100644
index 0000000..c928e4e
--- /dev/null
+++ b/dlls/ole32/enumx.c
@@ -0,0 +1,202 @@
+/*
+ * IEnum* implementation
+ *
+ * Copyright 2006 Mike McCormack
+ *
+ * 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
+ */
+
+#define COBJMACROS
+
+#include <stdarg.h>
+
+#include "windef.h"
+#include "winbase.h"
+#include "objbase.h"
+#include "wine/list.h"
+#include "wine/debug.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(ole);
+
+typedef struct tagEnumSTATPROPSETSTG_impl
+{
+ const void *vtbl;
+ LONG ref;
+ struct list elements;
+ struct list *current;
+ ULONG elem_size;
+ GUID riid;
+} enumx_impl;
+
+/************************************************************************
+ * enumx_QueryInterface
+ */
+HRESULT WINAPI enumx_QueryInterface(
+ enumx_impl *This,
+ REFIID riid,
+ void** ppvObject)
+{
+ if ( (This==0) || (ppvObject==0) )
+ return E_INVALIDARG;
+
+ *ppvObject = 0;
+
+ if (IsEqualGUID(&IID_IUnknown, riid) ||
+ IsEqualGUID(&This->riid, riid))
+ {
+ IUnknown_AddRef(((IUnknown*)This));
+ *ppvObject = This;
+ return S_OK;
+ }
+
+ return E_NOINTERFACE;
+}
+
+/************************************************************************
+ * enumx_AddRef
+ */
+ULONG WINAPI enumx_AddRef(enumx_impl *This)
+{
+ return InterlockedIncrement(&This->ref);
+}
+
+/************************************************************************
+ * enumx_Release
+ */
+ULONG WINAPI enumx_Release(enumx_impl *This)
+{
+ ULONG ref;
+
+ ref = InterlockedDecrement(&This->ref);
+ if (ref == 0)
+ {
+ while (!list_empty(&This->elements))
+ {
+ struct list *x = list_head(&This->elements);
+ list_remove(x);
+ HeapFree(GetProcessHeap(), 0, x);
+ }
+ HeapFree(GetProcessHeap(), 0, This);
+ }
+ return ref;
+}
+
+/************************************************************************
+ * enumx_Next
+ */
+HRESULT WINAPI enumx_Next(enumx_impl *This, ULONG celt,
+ void *rgelt, ULONG *pceltFetched)
+{
+ unsigned char *p;
+ ULONG count = 0;
+
+ TRACE("%p %lu %p\n", This, celt, pceltFetched);
+
+ if (This->current == NULL)
+ This->current = list_head(&This->elements);
+ p = rgelt;
+ while (count < celt && This->current && This->current != &This->elements)
+ {
+ memcpy(p, &This->current[1], This->elem_size);
+ p += This->elem_size;
+ This->current = This->current->next;
+ count++;
+ }
+ if (pceltFetched)
+ *pceltFetched = count;
+ if (count < celt)
+ return S_FALSE;
+ return S_OK;
+}
+
+/************************************************************************
+ * enumx_Skip
+ */
+HRESULT WINAPI enumx_Skip(enumx_impl *This, ULONG celt)
+{
+ ULONG count = 0;
+
+ TRACE("%p %lu\n", This, celt);
+
+ if (This->current == NULL)
+ This->current = list_head(&This->elements);
+
+ while (count < celt && This->current && This->current != &This->elements)
+ count++;
+
+ return S_OK;
+}
+
+/************************************************************************
+ * enumx_Reset
+ */
+HRESULT WINAPI enumx_Reset(enumx_impl *This)
+{
+ TRACE("\n");
+
+ This->current = NULL;
+ return S_OK;
+}
+
+/************************************************************************
+ * enumx_fnClone
+ */
+HRESULT WINAPI enumx_Clone(
+ enumx_impl *iface,
+ enumx_impl **ppenum)
+{
+ FIXME("\n");
+ return E_NOTIMPL;
+}
+
+/************************************************************************
+ * enumx_allocate
+ *
+ * Allocate a generic enumerator
+ */
+enumx_impl *enumx_allocate(REFIID riid, const void *vtbl, ULONG elem_size)
+{
+ enumx_impl *enumx;
+
+ enumx = HeapAlloc(GetProcessHeap(), 0, sizeof *enumx);
+ if (enumx)
+ {
+ enumx->vtbl = vtbl;
+ enumx->ref = 1;
+ enumx->current = NULL;
+ enumx->elem_size = elem_size;
+ memcpy(&enumx->riid, riid, sizeof *riid);
+ list_init(&enumx->elements);
+ }
+
+ return enumx;
+}
+
+/************************************************************************
+ * enumx_add_element
+ *
+ * Add an element to the enumeration.
+ */
+void *enumx_add_element(enumx_impl *enumx, void *data)
+{
+ struct list *element;
+
+ element = HeapAlloc(GetProcessHeap(), 0, sizeof *element + enumx->elem_size);
+ if (!element)
+ return NULL;
+ memcpy(&element[1], data, enumx->elem_size);
+ list_add_tail(&enumx->elements, element);
+ return &element[1];
+}
diff --git a/dlls/ole32/enumx.h b/dlls/ole32/enumx.h
new file mode 100644
index 0000000..2d36b73
--- /dev/null
+++ b/dlls/ole32/enumx.h
@@ -0,0 +1,34 @@
+/*
+ * Copyright 2006 Mike McCormack
+ *
+ * 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 __OLE_ENUM_H__
+#define __OLE_ENUM_H__
+
+typedef struct tagEnumSTATPROPSETSTG_impl enumx_impl;
+
+extern HRESULT WINAPI enumx_QueryInterface(enumx_impl *, REFIID, void**);
+extern ULONG WINAPI enumx_AddRef(enumx_impl *);
+extern ULONG WINAPI enumx_Release(enumx_impl *);
+extern HRESULT WINAPI enumx_Next(enumx_impl *, ULONG, void *, ULONG *);
+extern HRESULT WINAPI enumx_Skip(enumx_impl *, ULONG);
+extern HRESULT WINAPI enumx_Reset(enumx_impl *);
+extern HRESULT WINAPI enumx_Clone(enumx_impl *, enumx_impl **);
+extern enumx_impl *enumx_allocate(REFIID, const void *, ULONG);
+extern void *enumx_add_element(enumx_impl *, void *);
+
+#endif
More information about the wine-cvs
mailing list