[4/4] wbemprox: Add support for creating new tables.
Hans Leidekker
hans at codeweavers.com
Fri Jul 13 04:35:39 CDT 2012
---
dlls/wbemprox/Makefile.in | 1 +
dlls/wbemprox/builtin.c | 17 +--
dlls/wbemprox/main.c | 1 +
dlls/wbemprox/query.c | 176 +------------------------
dlls/wbemprox/table.c | 280 ++++++++++++++++++++++++++++++++++++++
dlls/wbemprox/wbemprox_private.h | 14 ++
6 files changed, 303 insertions(+), 186 deletions(-)
create mode 100644 dlls/wbemprox/table.c
diff --git a/dlls/wbemprox/Makefile.in b/dlls/wbemprox/Makefile.in
index 2b6b34e..e610049 100644
--- a/dlls/wbemprox/Makefile.in
+++ b/dlls/wbemprox/Makefile.in
@@ -7,6 +7,7 @@ C_SRCS = \
main.c \
query.c \
services.c \
+ table.c \
wbemlocator.c
IDL_R_SRCS = wbemprox.idl
diff --git a/dlls/wbemprox/builtin.c b/dlls/wbemprox/builtin.c
index 6b8bb15..fd84ce3 100644
--- a/dlls/wbemprox/builtin.c
+++ b/dlls/wbemprox/builtin.c
@@ -815,7 +815,7 @@ done:
if (factory) IDXGIFactory_Release( factory );
}
-static struct table classtable[] =
+static struct table builtin_classes[] =
{
{ class_baseboardW, SIZEOF(col_baseboard), col_baseboard, SIZEOF(data_baseboard), (BYTE *)data_baseboard },
{ class_biosW, SIZEOF(col_bios), col_bios, SIZEOF(data_bios), (BYTE *)data_bios },
@@ -830,19 +830,14 @@ static struct table classtable[] =
{ class_videocontrollerW, SIZEOF(col_videocontroller), col_videocontroller, 0, NULL, fill_videocontroller }
};
-struct table *get_table( const WCHAR *name )
+void init_table_list( void )
{
+ static struct list tables = LIST_INIT( tables );
UINT i;
- struct table *table = NULL;
- for (i = 0; i < SIZEOF(classtable); i++)
+ for (i = 0; i < SIZEOF(builtin_classes); i++)
{
- if (!strcmpiW( classtable[i].name, name ))
- {
- table = &classtable[i];
- if (table->fill && !table->data) table->fill( table );
- break;
- }
+ list_add_tail( &tables, &builtin_classes[i].entry );
}
- return table;
+ table_list = &tables;
}
diff --git a/dlls/wbemprox/main.c b/dlls/wbemprox/main.c
index c9bff5d..6455efd 100644
--- a/dlls/wbemprox/main.c
+++ b/dlls/wbemprox/main.c
@@ -125,6 +125,7 @@ BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
case DLL_PROCESS_ATTACH:
instance = hinstDLL;
DisableThreadLibraryCalls(hinstDLL);
+ init_table_list();
break;
case DLL_PROCESS_DETACH:
break;
diff --git a/dlls/wbemprox/query.c b/dlls/wbemprox/query.c
index b6b74ef..74b48e4 100644
--- a/dlls/wbemprox/query.c
+++ b/dlls/wbemprox/query.c
@@ -30,156 +30,6 @@
WINE_DEFAULT_DEBUG_CHANNEL(wbemprox);
-static HRESULT get_column_index( const struct table *table, const WCHAR *name, UINT *column )
-{
- UINT i;
- for (i = 0; i < table->num_cols; i++)
- {
- if (!strcmpiW( table->columns[i].name, name ))
- {
- *column = i;
- return S_OK;
- }
- }
- return WBEM_E_INVALID_QUERY;
-}
-
-static UINT get_column_size( const struct table *table, UINT column )
-{
- if (table->columns[column].type & CIM_FLAG_ARRAY) return sizeof(void *);
-
- switch (table->columns[column].type & COL_TYPE_MASK)
- {
- case CIM_SINT16:
- case CIM_UINT16:
- return sizeof(INT16);
- case CIM_SINT32:
- case CIM_UINT32:
- return sizeof(INT32);
- case CIM_SINT64:
- case CIM_UINT64:
- return sizeof(INT64);
- case CIM_DATETIME:
- case CIM_STRING:
- return sizeof(WCHAR *);
- default:
- ERR("unknown column type %u\n", table->columns[column].type & COL_TYPE_MASK);
- break;
- }
- return sizeof(INT32);
-}
-
-static UINT get_column_offset( const struct table *table, UINT column )
-{
- UINT i, offset = 0;
- for (i = 0; i < column; i++) offset += get_column_size( table, i );
- return offset;
-}
-
-static UINT get_row_size( const struct table *table )
-{
- return get_column_offset( table, table->num_cols - 1 ) + get_column_size( table, table->num_cols - 1 );
-}
-
-static HRESULT get_value( const struct table *table, UINT row, UINT column, LONGLONG *val )
-{
- UINT col_offset, row_size;
- const BYTE *ptr;
-
- col_offset = get_column_offset( table, column );
- row_size = get_row_size( table );
- ptr = table->data + row * row_size + col_offset;
-
- if (table->columns[column].type & CIM_FLAG_ARRAY)
- {
- *val = (LONGLONG)(INT_PTR)*(const void **)ptr;
- return S_OK;
- }
- switch (table->columns[column].type & COL_TYPE_MASK)
- {
- case CIM_DATETIME:
- case CIM_STRING:
- *val = (LONGLONG)(INT_PTR)*(const WCHAR **)ptr;
- break;
- case CIM_SINT16:
- *val = *(const INT16 *)ptr;
- break;
- case CIM_UINT16:
- *val = *(const UINT16 *)ptr;
- break;
- case CIM_SINT32:
- *val = *(const INT32 *)ptr;
- break;
- case CIM_UINT32:
- *val = *(const UINT32 *)ptr;
- break;
- case CIM_SINT64:
- *val = *(const INT64 *)ptr;
- break;
- case CIM_UINT64:
- *val = *(const UINT64 *)ptr;
- break;
- default:
- ERR("invalid column type %u\n", table->columns[column].type & COL_TYPE_MASK);
- *val = 0;
- break;
- }
- return S_OK;
-}
-
-static BSTR get_value_bstr( const struct table *table, UINT row, UINT column )
-{
- static const WCHAR fmt_signedW[] = {'%','d',0};
- static const WCHAR fmt_unsignedW[] = {'%','u',0};
- static const WCHAR fmt_signed64W[] = {'%','I','6','4','d',0};
- static const WCHAR fmt_unsigned64W[] = {'%','I','6','4','u',0};
- static const WCHAR fmt_strW[] = {'\"','%','s','\"',0};
- LONGLONG val;
- BSTR ret;
- WCHAR number[22];
- UINT len;
-
- if (table->columns[column].type & CIM_FLAG_ARRAY)
- {
- FIXME("array to string conversion not handled\n");
- return NULL;
- }
- if (get_value( table, row, column, &val ) != S_OK) return NULL;
-
- switch (table->columns[column].type & COL_TYPE_MASK)
- {
- case CIM_DATETIME:
- case CIM_STRING:
- len = strlenW( (const WCHAR *)(INT_PTR)val ) + 2;
- if (!(ret = SysAllocStringLen( NULL, len ))) return NULL;
- sprintfW( ret, fmt_strW, (const WCHAR *)(INT_PTR)val );
- return ret;
-
- case CIM_SINT16:
- case CIM_SINT32:
- sprintfW( number, fmt_signedW, val );
- return SysAllocString( number );
-
- case CIM_UINT16:
- case CIM_UINT32:
- sprintfW( number, fmt_unsignedW, val );
- return SysAllocString( number );
-
- case CIM_SINT64:
- wsprintfW( number, fmt_signed64W, val );
- return SysAllocString( number );
-
- case CIM_UINT64:
- wsprintfW( number, fmt_unsigned64W, val );
- return SysAllocString( number );
-
- default:
- FIXME("unhandled column type %u\n", table->columns[column].type & COL_TYPE_MASK);
- break;
- }
- return NULL;
-}
-
HRESULT create_view( const struct property *proplist, const WCHAR *class,
const struct expr *cond, struct view **ret )
{
@@ -195,33 +45,9 @@ HRESULT create_view( const struct property *proplist, const WCHAR *class,
return S_OK;
}
-static void clear_table( struct table *table )
-{
- UINT i, j, type;
-
- if (!table->fill || !table->data) return;
-
- for (i = 0; i < table->num_rows; i++)
- {
- for (j = 0; j < table->num_cols; j++)
- {
- if (!(table->columns[j].type & COL_FLAG_DYNAMIC)) continue;
-
- type = table->columns[j].type & COL_TYPE_MASK;
- if (type == CIM_STRING || type == CIM_DATETIME || (type & CIM_FLAG_ARRAY))
- {
- void *ptr;
- if (get_value( table, i, j, (LONGLONG *)&ptr ) == S_OK) heap_free( ptr );
- }
- }
- }
- heap_free( table->data );
- table->data = NULL;
-}
-
void destroy_view( struct view *view )
{
- if (view->table) clear_table( view->table );
+ free_table( view->table );
heap_free( view->result );
heap_free( view );
}
diff --git a/dlls/wbemprox/table.c b/dlls/wbemprox/table.c
new file mode 100644
index 0000000..c3757d5
--- /dev/null
+++ b/dlls/wbemprox/table.c
@@ -0,0 +1,280 @@
+/*
+ * Copyright 2012 Hans Leidekker 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
+ */
+
+#define COBJMACROS
+
+#include "config.h"
+#include <stdarg.h>
+
+#include "windef.h"
+#include "winbase.h"
+#include "wbemcli.h"
+
+#include "wine/debug.h"
+#include "wbemprox_private.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(wbemprox);
+
+HRESULT get_column_index( const struct table *table, const WCHAR *name, UINT *column )
+{
+ UINT i;
+ for (i = 0; i < table->num_cols; i++)
+ {
+ if (!strcmpiW( table->columns[i].name, name ))
+ {
+ *column = i;
+ return S_OK;
+ }
+ }
+ return WBEM_E_INVALID_QUERY;
+}
+
+static UINT get_column_size( const struct table *table, UINT column )
+{
+ if (table->columns[column].type & CIM_FLAG_ARRAY) return sizeof(void *);
+
+ switch (table->columns[column].type & COL_TYPE_MASK)
+ {
+ case CIM_SINT16:
+ case CIM_UINT16:
+ return sizeof(INT16);
+ case CIM_SINT32:
+ case CIM_UINT32:
+ return sizeof(INT32);
+ case CIM_SINT64:
+ case CIM_UINT64:
+ return sizeof(INT64);
+ case CIM_DATETIME:
+ case CIM_STRING:
+ return sizeof(WCHAR *);
+ default:
+ ERR("unknown column type %u\n", table->columns[column].type & COL_TYPE_MASK);
+ break;
+ }
+ return sizeof(INT32);
+}
+
+static UINT get_column_offset( const struct table *table, UINT column )
+{
+ UINT i, offset = 0;
+ for (i = 0; i < column; i++) offset += get_column_size( table, i );
+ return offset;
+}
+
+static UINT get_row_size( const struct table *table )
+{
+ return get_column_offset( table, table->num_cols - 1 ) + get_column_size( table, table->num_cols - 1 );
+}
+
+HRESULT get_value( const struct table *table, UINT row, UINT column, LONGLONG *val )
+{
+ UINT col_offset, row_size;
+ const BYTE *ptr;
+
+ col_offset = get_column_offset( table, column );
+ row_size = get_row_size( table );
+ ptr = table->data + row * row_size + col_offset;
+
+ if (table->columns[column].type & CIM_FLAG_ARRAY)
+ {
+ *val = (LONGLONG)(INT_PTR)*(const void **)ptr;
+ return S_OK;
+ }
+ switch (table->columns[column].type & COL_TYPE_MASK)
+ {
+ case CIM_DATETIME:
+ case CIM_STRING:
+ *val = (LONGLONG)(INT_PTR)*(const WCHAR **)ptr;
+ break;
+ case CIM_SINT16:
+ *val = *(const INT16 *)ptr;
+ break;
+ case CIM_UINT16:
+ *val = *(const UINT16 *)ptr;
+ break;
+ case CIM_SINT32:
+ *val = *(const INT32 *)ptr;
+ break;
+ case CIM_UINT32:
+ *val = *(const UINT32 *)ptr;
+ break;
+ case CIM_SINT64:
+ *val = *(const INT64 *)ptr;
+ break;
+ case CIM_UINT64:
+ *val = *(const UINT64 *)ptr;
+ break;
+ default:
+ ERR("invalid column type %u\n", table->columns[column].type & COL_TYPE_MASK);
+ *val = 0;
+ break;
+ }
+ return S_OK;
+}
+
+BSTR get_value_bstr( const struct table *table, UINT row, UINT column )
+{
+ static const WCHAR fmt_signedW[] = {'%','d',0};
+ static const WCHAR fmt_unsignedW[] = {'%','u',0};
+ static const WCHAR fmt_signed64W[] = {'%','I','6','4','d',0};
+ static const WCHAR fmt_unsigned64W[] = {'%','I','6','4','u',0};
+ static const WCHAR fmt_strW[] = {'\"','%','s','\"',0};
+ LONGLONG val;
+ BSTR ret;
+ WCHAR number[22];
+ UINT len;
+
+ if (table->columns[column].type & CIM_FLAG_ARRAY)
+ {
+ FIXME("array to string conversion not handled\n");
+ return NULL;
+ }
+ if (get_value( table, row, column, &val ) != S_OK) return NULL;
+
+ switch (table->columns[column].type & COL_TYPE_MASK)
+ {
+ case CIM_DATETIME:
+ case CIM_STRING:
+ len = strlenW( (const WCHAR *)(INT_PTR)val ) + 2;
+ if (!(ret = SysAllocStringLen( NULL, len ))) return NULL;
+ sprintfW( ret, fmt_strW, (const WCHAR *)(INT_PTR)val );
+ return ret;
+
+ case CIM_SINT16:
+ case CIM_SINT32:
+ sprintfW( number, fmt_signedW, val );
+ return SysAllocString( number );
+
+ case CIM_UINT16:
+ case CIM_UINT32:
+ sprintfW( number, fmt_unsignedW, val );
+ return SysAllocString( number );
+
+ case CIM_SINT64:
+ wsprintfW( number, fmt_signed64W, val );
+ return SysAllocString( number );
+
+ case CIM_UINT64:
+ wsprintfW( number, fmt_unsigned64W, val );
+ return SysAllocString( number );
+
+ default:
+ FIXME("unhandled column type %u\n", table->columns[column].type & COL_TYPE_MASK);
+ break;
+ }
+ return NULL;
+}
+
+static void clear_table( struct table *table )
+{
+ UINT i, j, type;
+ LONGLONG val;
+
+ if (!table->data) return;
+
+ for (i = 0; i < table->num_rows; i++)
+ {
+ for (j = 0; j < table->num_cols; j++)
+ {
+ if (!(table->columns[j].type & COL_FLAG_DYNAMIC)) continue;
+
+ type = table->columns[j].type & COL_TYPE_MASK;
+ if (type == CIM_STRING || type == CIM_DATETIME || (type & CIM_FLAG_ARRAY))
+ {
+ if (get_value( table, i, j, &val ) == S_OK) heap_free( (void *)(INT_PTR)val );
+ }
+ }
+ }
+ table->num_rows = 0;
+ if (table->fill)
+ {
+ heap_free( table->data );
+ table->data = NULL;
+ }
+}
+
+void free_columns( struct column *columns, UINT num_cols )
+{
+ UINT i;
+
+ for (i = 0; i < num_cols; i++)
+ {
+ heap_free( (WCHAR *)columns[i].name );
+ }
+ heap_free( columns );
+}
+
+void free_table( struct table *table )
+{
+ if (!table) return;
+
+ clear_table( table );
+ if (table->flags & TABLE_FLAG_DYNAMIC)
+ {
+ heap_free( (WCHAR *)table->name );
+ free_columns( (struct column *)table->columns, table->num_cols );
+ heap_free( table );
+ }
+}
+
+struct table *get_table( const WCHAR *name )
+{
+ struct table *table;
+
+ LIST_FOR_EACH_ENTRY( table, table_list, struct table, entry )
+ {
+ if (!strcmpiW( table->name, name ))
+ {
+ if (table->fill && !table->data) table->fill( table );
+ return table;
+ }
+ }
+ return NULL;
+}
+
+struct table *create_table( const WCHAR *name, UINT num_cols, const struct column *columns,
+ UINT num_rows, BYTE *data, void (*fill)(struct table *) )
+{
+ struct table *table;
+
+ if (!(table = heap_alloc( sizeof(*table) ))) return NULL;
+ table->name = name;
+ table->num_cols = num_cols;
+ table->columns = columns;
+ table->num_rows = num_rows;
+ table->data = data;
+ table->fill = fill;
+ table->flags = TABLE_FLAG_DYNAMIC;
+ return table;
+}
+
+BOOL add_table( struct table *table )
+{
+ struct table *iter;
+
+ LIST_FOR_EACH_ENTRY( iter, table_list, struct table, entry )
+ {
+ if (!strcmpiW( iter->name, table->name ))
+ {
+ TRACE("table %s already exists\n", debugstr_w(table->name));
+ return FALSE;
+ }
+ }
+ list_add_tail( table_list, &table->entry );
+ return TRUE;
+}
diff --git a/dlls/wbemprox/wbemprox_private.h b/dlls/wbemprox/wbemprox_private.h
index a5b17dc..5f095c6 100644
--- a/dlls/wbemprox/wbemprox_private.h
+++ b/dlls/wbemprox/wbemprox_private.h
@@ -20,6 +20,7 @@
#include "wine/unicode.h"
IClientSecurity client_security;
+struct list *table_list;
#define SIZEOF(array) (sizeof(array)/sizeof((array)[0]))
@@ -37,6 +38,8 @@ struct column
VARTYPE vartype; /* 0 for default mapping */
};
+#define TABLE_FLAG_DYNAMIC 0x00000001
+
struct table
{
const WCHAR *name;
@@ -45,6 +48,8 @@ struct table
UINT num_rows;
BYTE *data;
void (*fill)(struct table *);
+ UINT flags;
+ struct list entry;
};
struct property
@@ -122,7 +127,16 @@ HRESULT parse_query( const WCHAR *, struct view **, struct list * ) DECLSPEC_HID
HRESULT create_view( const struct property *, const WCHAR *, const struct expr *,
struct view ** ) DECLSPEC_HIDDEN;
void destroy_view( struct view * ) DECLSPEC_HIDDEN;
+void init_table_list( void ) DECLSPEC_HIDDEN;
struct table *get_table( const WCHAR * ) DECLSPEC_HIDDEN;
+struct table *create_table( const WCHAR *, UINT, const struct column *, UINT,
+ BYTE *, void (*)(struct table *)) DECLSPEC_HIDDEN;
+BOOL add_table( struct table * ) DECLSPEC_HIDDEN;
+void free_columns( struct column *, UINT ) DECLSPEC_HIDDEN;
+void free_table( struct table * ) DECLSPEC_HIDDEN;
+HRESULT get_column_index( const struct table *, const WCHAR *, UINT * ) DECLSPEC_HIDDEN;
+HRESULT get_value( const struct table *, UINT, UINT, LONGLONG * ) DECLSPEC_HIDDEN;
+BSTR get_value_bstr( const struct table *, UINT, UINT ) DECLSPEC_HIDDEN;
HRESULT get_propval( const struct view *, UINT, const WCHAR *, VARIANT *,
CIMTYPE *, LONG * ) DECLSPEC_HIDDEN;
HRESULT get_properties( const struct view *, SAFEARRAY ** ) DECLSPEC_HIDDEN;
--
1.7.5.4
More information about the wine-patches
mailing list