[aravis/dom] genicam: add support for StructReg and StructEntry.



commit ae5ac0eae4c9a09415dfa60dd1305965cb1543b8
Author: Emmanuel Pacaud <emmanuel gnome org>
Date:   Sun Mar 4 21:46:04 2012 +0100

    genicam: add support for StructReg and StructEntry.
    
    It should enable support of Point Grey Research cameras.

 docs/reference/aravis/aravis-docs.xml     |    1 +
 docs/reference/aravis/aravis-sections.txt |   19 +++
 src/Makefile.am                           |    2 +
 src/arv-fake-camera.xml                   |   24 +++
 src/arvgc.c                               |    5 +
 src/arvgcregister.c                       |   78 ++++++++--
 src/arvgcregister.h                       |    8 +-
 src/arvgcstructentrynode.c                |  223 +++++++++++++++++++++++++++++
 src/arvgcstructentrynode.h                |   60 ++++++++
 src/arvtypes.h                            |    1 +
 tests/fake.c                              |   65 +++++++++
 11 files changed, 469 insertions(+), 17 deletions(-)
---
diff --git a/docs/reference/aravis/aravis-docs.xml b/docs/reference/aravis/aravis-docs.xml
index d4b14fb..ae949ee 100644
--- a/docs/reference/aravis/aravis-docs.xml
+++ b/docs/reference/aravis/aravis-docs.xml
@@ -65,6 +65,7 @@
 			<xi:include href="xml/arvgcintegernode.xml"/>
 			<xi:include href="xml/arvgcfloatnode.xml"/>
 			<xi:include href="xml/arvgcregister.xml"/>
+			<xi:include href="xml/arvgcstructentrynode.xml"/>
 			<xi:include href="xml/arvgcenumeration.xml"/>
 			<xi:include href="xml/arvgcenumentry.xml"/>
 			<xi:include href="xml/arvgcconverter.xml"/>
diff --git a/docs/reference/aravis/aravis-sections.txt b/docs/reference/aravis/aravis-sections.txt
index 18bdd51..13de108 100644
--- a/docs/reference/aravis/aravis-sections.txt
+++ b/docs/reference/aravis/aravis-sections.txt
@@ -786,10 +786,13 @@ arv_gc_register_new_integer
 arv_gc_register_new_masked_integer
 arv_gc_register_new_float
 arv_gc_register_new_string
+arv_gc_register_new_struct_register
 arv_gc_register_get
 arv_gc_register_set
 arv_gc_register_get_address
 arv_gc_register_get_length
+arv_gc_register_get_masked_integer_value
+arv_gc_register_set_masked_integer_value
 <SUBSECTION Standard>
 ARV_GC_REGISTER
 ARV_IS_GC_REGISTER
@@ -803,6 +806,22 @@ ArvGcRegisterClass
 </SECTION>
 
 <SECTION>
+<FILE>arvgcstructentrynode</FILE>
+<TITLE>ArvGcStructEntryNode</TITLE>
+arv_gc_struct_entry_node_new
+<SUBSECTION Standard>
+ArvGcStructEntryNode
+ARV_GC_STRUCT_ENTRY_NODE
+ARV_GC_STRUCT_ENTRY_NODE_CLASS
+ARV_GC_STRUCT_ENTRY_NODE_GET_CLASS
+ARV_IS_GC_STRUCT_ENTRY_NODE
+ARV_IS_GC_STRUCT_ENTRY_NODE_CLASS
+ARV_TYPE_GC_STRUCT_ENTRY_NODE
+ArvGcStructEntryNodeClass
+arv_gc_struct_entry_node_get_type
+>/SECTION>
+
+<SECTION>
 <FILE>arvgcstring</FILE>
 <TITLE>ArvGcString</TITLE>
 ArvGcString
diff --git a/src/Makefile.am b/src/Makefile.am
index 7cfc24f..b9e077e 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -60,6 +60,7 @@ ARAVIS_SRCS =					\
 	arvgcintegernode.c			\
 	arvgcfloatnode.c			\
 	arvgcregister.c				\
+	arvgcstructentrynode.c			\
 	arvgccommand.c				\
 	arvgcswissknife.c			\
 	arvgcconverter.c			\
@@ -120,6 +121,7 @@ ARAVIS_HDRS = 					\
 	arvgcintegernode.h			\
 	arvgcfloatnode.h			\
 	arvgcregister.h				\
+	arvgcstructentrynode.h			\
 	arvgccommand.h				\
 	arvgcswissknife.h			\
 	arvgcconverter.h			\
diff --git a/src/arv-fake-camera.xml b/src/arv-fake-camera.xml
index 864d565..c96f5e8 100644
--- a/src/arv-fake-camera.xml
+++ b/src/arv-fake-camera.xml
@@ -469,6 +469,30 @@
 		<Endianess>LittleEndian</Endianess>
 	</IntReg>
 
+	<StructReg Comment="TestStructReg">
+		<Address>0x1f0</Address>
+		<Length>4</Length>
+		<AccessMode>RW</AccessMode>
+		<pPort>Device</pPort>
+		<Endianess>LittleEndian</Endianess>
+
+		<StructEntry Name="StructEntry_0_15" NameSpace="Custom">
+			<LSB>0</LSB>
+			<MSB>15</MSB>
+			<Sign>Unsigned</Sign>
+		</StructEntry>
+
+		<StructEntry Name="StructEntry_16_31" NameSpace="Custom">
+			<LSB>16</LSB>
+			<MSB>31</MSB>
+			<Sign>Unsigned</Sign>
+		</StructEntry>
+
+		<StructEntry Name="StructEntry_16" NameSpace="Custom">
+			<Bit>16</Bit>
+		</StructEntry>
+	</StructReg>
+
 	<!-- Port -->
 
 	<Port Name="Device" NameSpace="Standard">
diff --git a/src/arvgc.c b/src/arvgc.c
index cc4a845..90e9e9e 100644
--- a/src/arvgc.c
+++ b/src/arvgc.c
@@ -43,6 +43,7 @@
 #include <arvgcintegernode.h>
 #include <arvgcfloatnode.h>
 #include <arvgcregister.h>
+#include <arvgcstructentrynode.h>
 #include <arvgccommand.h>
 #include <arvgcinteger.h>
 #include <arvgcfloat.h>
@@ -87,6 +88,10 @@ arv_gc_create_element (ArvDomDocument *document, const char *tag_name)
 		node = arv_gc_register_new_float ();
 	else if (strcmp (tag_name, "StringReg") == 0)
 		node = arv_gc_register_new_string ();
+	else if (strcmp (tag_name, "StructReg") == 0)
+		node = arv_gc_register_new_struct_register ();
+	else if (strcmp (tag_name, "StructEntry") == 0)
+		node = arv_gc_struct_entry_node_new ();
 	else if (strcmp (tag_name, "Integer") == 0)
 		node = arv_gc_integer_node_new ();
 	else if (strcmp (tag_name, "Float") == 0)
diff --git a/src/arvgcregister.c b/src/arvgcregister.c
index 795bc76..bbf78c8 100644
--- a/src/arvgcregister.c
+++ b/src/arvgcregister.c
@@ -58,6 +58,8 @@ arv_gc_register_get_node_name (ArvDomNode *node)
 			return "FloatReg";
 		case ARV_GC_REGISTER_TYPE_STRING:
 			return "StringReg";
+		case ARV_GC_REGISTER_TYPE_STRUCT_REGISTER:
+			return "StuctReg";
 	}
 
 	return NULL;
@@ -456,6 +458,18 @@ arv_gc_register_new_string (void)
 	return ARV_GC_NODE (gc_register);
 }
 
+ArvGcNode *
+arv_gc_register_new_struct_register (void)
+{
+	ArvGcRegister *gc_register;
+
+	gc_register = g_object_new (ARV_TYPE_GC_REGISTER, NULL);
+	gc_register->type = ARV_GC_REGISTER_TYPE_STRUCT_REGISTER;
+	gc_register->value_type = G_TYPE_INT64;
+
+	return ARV_GC_NODE (gc_register);
+}
+
 static void
 arv_gc_register_init (ArvGcRegister *gc_register)
 {
@@ -497,9 +511,8 @@ arv_gc_register_class_init (ArvGcRegisterClass *this_class)
 /* ArvGcInteger interface implementation */
 
 static gint64
-arv_gc_register_get_integer_value (ArvGcInteger *gc_integer)
+_get_integer_value (ArvGcRegister *gc_register, guint register_lsb, guint register_msb)
 {
-	ArvGcRegister *gc_register = ARV_GC_REGISTER (gc_integer);
 	gint64 value;
 	guint lsb;
 	guint msb;
@@ -512,15 +525,16 @@ arv_gc_register_get_integer_value (ArvGcInteger *gc_integer)
 	arv_copy_memory_with_endianess (&value, sizeof (value), G_BYTE_ORDER,
 					gc_register->cache, gc_register->cache_size, endianess);
 
-	if (gc_register->type == ARV_GC_REGISTER_TYPE_MASKED_INTEGER) {
+	if (gc_register->type == ARV_GC_REGISTER_TYPE_MASKED_INTEGER ||
+	    gc_register->type == ARV_GC_REGISTER_TYPE_STRUCT_REGISTER) {
 		guint64 mask;
 
 		if (endianess == G_BYTE_ORDER) {
-			msb = _get_msb (gc_register);
-			lsb = _get_lsb (gc_register);
+			msb = register_msb;
+			lsb = register_lsb;
 		} else {
-			lsb = 8 * gc_register->cache_size - _get_lsb (gc_register) - 1;
-			msb = 8 * gc_register->cache_size - _get_msb (gc_register) - 1;
+			lsb = 8 * gc_register->cache_size - register_lsb - 1;
+			msb = 8 * gc_register->cache_size - register_msb - 1;
 		}
 
 #if G_BYTE_ORDER == G_LITTLE_ENDIAN
@@ -535,24 +549,40 @@ arv_gc_register_get_integer_value (ArvGcInteger *gc_integer)
 #endif
 	}
 
-	arv_log_genicam ("[GcRegister::get_integer_value] address = 0x%Lx, value = 0x%Lx",
+	arv_log_genicam ("[GcRegister::_get_integer_value] address = 0x%Lx, value = 0x%Lx",
 			 arv_gc_register_get_address (gc_register),
 			 value);
 
 	return value;
 }
 
-static void
-arv_gc_register_set_integer_value (ArvGcInteger *gc_integer, gint64 value)
+gint64
+arv_gc_register_get_masked_integer_value (ArvGcRegister *gc_register, guint lsb, guint msb)
+{
+	g_return_val_if_fail (ARV_IS_GC_REGISTER (gc_register), 0);
+
+	return _get_integer_value (gc_register, lsb, msb);
+}
+
+static gint64
+arv_gc_register_get_integer_value (ArvGcInteger *gc_integer)
 {
 	ArvGcRegister *gc_register = ARV_GC_REGISTER (gc_integer);
+
+	return _get_integer_value (gc_register, _get_lsb (gc_register), _get_msb (gc_register));
+}
+
+static void
+_set_integer_value (ArvGcRegister *gc_register, guint register_lsb, guint register_msb, gint64 value)
+{
 	guint lsb;
 	guint msb;
 	guint endianess;
 
 	endianess = _get_endianess (gc_register);
 
-	if (gc_register->type == ARV_GC_REGISTER_TYPE_MASKED_INTEGER) {
+	if (gc_register->type == ARV_GC_REGISTER_TYPE_MASKED_INTEGER ||
+	    gc_register->type == ARV_GC_REGISTER_TYPE_STRUCT_REGISTER) {
 		gint64 current_value;
 		guint64 mask;
 
@@ -562,11 +592,11 @@ arv_gc_register_set_integer_value (ArvGcInteger *gc_integer, gint64 value)
 						gc_register->cache, gc_register->cache_size, endianess);
 
 		if (endianess == G_BYTE_ORDER) {
-			msb = _get_msb (gc_register);
-			lsb = _get_lsb (gc_register);
+			msb = register_msb;
+			lsb = register_lsb;
 		} else {
-			lsb = 8 * gc_register->cache_size - _get_lsb (gc_register) - 1;
-			msb = 8 * gc_register->cache_size - _get_msb (gc_register) - 1;
+			lsb = 8 * gc_register->cache_size - register_lsb - 1;
+			msb = 8 * gc_register->cache_size - register_msb - 1;
 		}
 
 #if G_BYTE_ORDER == G_LITTLE_ENDIAN
@@ -581,7 +611,7 @@ arv_gc_register_set_integer_value (ArvGcInteger *gc_integer, gint64 value)
 #endif
 	}
 
-	arv_log_genicam ("[GcRegister::set_integer_value] address = 0x%Lx, value = 0x%Lx",
+	arv_log_genicam ("[GcRegister::_set_integer_value] address = 0x%Lx, value = 0x%Lx",
 			 arv_gc_register_get_address (gc_register),
 			 value);
 
@@ -591,6 +621,22 @@ arv_gc_register_set_integer_value (ArvGcInteger *gc_integer, gint64 value)
 	_write_cache (gc_register);
 }
 
+void
+arv_gc_register_set_masked_integer_value (ArvGcRegister *gc_register, guint lsb, guint msb, gint64 value)
+{
+	g_return_if_fail (ARV_IS_GC_REGISTER (gc_register));
+
+	_set_integer_value (gc_register, lsb, msb, value);
+}
+
+static void
+arv_gc_register_set_integer_value (ArvGcInteger *gc_integer, gint64 value)
+{
+	ArvGcRegister *gc_register = ARV_GC_REGISTER (gc_integer);
+
+	_set_integer_value (gc_register, _get_lsb (gc_register), _get_msb (gc_register), value);
+}
+
 static void
 arv_gc_register_integer_interface_init (ArvGcIntegerInterface *interface)
 {
diff --git a/src/arvgcregister.h b/src/arvgcregister.h
index c43b566..930aa3c 100644
--- a/src/arvgcregister.h
+++ b/src/arvgcregister.h
@@ -48,6 +48,7 @@ typedef enum
  * @ARV_GC_REGISTER_TYPE_MASKED_INTEGER: MaskedIntReg node
  * @ARV_GC_REGISTER_TYPE_FLOAT: FloatReg node
  * @ARV_GC_REGISTER_TYPE_STRING: StringReg node
+ * @ARV_GC_REGISTER_TYPE_STRUCT_REGISTER: StructReg node
  */
 
 typedef enum {
@@ -55,7 +56,8 @@ typedef enum {
        ARV_GC_REGISTER_TYPE_INTEGER,
        ARV_GC_REGISTER_TYPE_MASKED_INTEGER,
        ARV_GC_REGISTER_TYPE_FLOAT,
-       ARV_GC_REGISTER_TYPE_STRING
+       ARV_GC_REGISTER_TYPE_STRING,
+       ARV_GC_REGISTER_TYPE_STRUCT_REGISTER
 } ArvGcRegisterType;
 
 #define ARV_TYPE_GC_REGISTER             (arv_gc_register_get_type ())
@@ -104,11 +106,15 @@ ArvGcNode * 	arv_gc_register_new_integer 		(void);
 ArvGcNode * 	arv_gc_register_new_masked_integer 	(void);
 ArvGcNode * 	arv_gc_register_new_float	 	(void);
 ArvGcNode * 	arv_gc_register_new_string 		(void);
+ArvGcNode * 	arv_gc_register_new_struct_register	(void);
 void 		arv_gc_register_get			(ArvGcRegister *gc_register, void *buffer, guint64 Length);
 void 		arv_gc_register_set			(ArvGcRegister *gc_register, void *buffer, guint64 Length);
 guint64 	arv_gc_register_get_address 		(ArvGcRegister *gc_register);
 guint64 	arv_gc_register_get_length		(ArvGcRegister *gc_register);
 
+gint64 		arv_gc_register_get_masked_integer_value 	(ArvGcRegister *gc_register, guint lsb, guint msb);
+void 		arv_gc_register_set_masked_integer_value 	(ArvGcRegister *gc_register, guint lsb, guint msb, gint64 value);
+
 G_END_DECLS
 
 #endif
diff --git a/src/arvgcstructentrynode.c b/src/arvgcstructentrynode.c
new file mode 100644
index 0000000..909c0b2
--- /dev/null
+++ b/src/arvgcstructentrynode.c
@@ -0,0 +1,223 @@
+/* Aravis - Digital camera library
+ *
+ * Copyright  2009-2012 Emmanuel Pacaud
+ *
+ * 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 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., 59 Temple Place, Suite 330,
+ * Boston, MA 02111-1307, USA.
+ *
+ * Author: Emmanuel Pacaud <emmanuel gnome org>
+ */
+
+/**
+ * SECTION: arvgcstructentrynode
+ * @short_description: Class for StructEntry nodes
+ */
+
+#include <arvgcstructentrynode.h>
+#include <arvgcregister.h>
+#include <arvgcinteger.h>
+#include <arvgcport.h>
+#include <arvgc.h>
+#include <arvmisc.h>
+#include <arvdebug.h>
+#include <stdlib.h>
+#include <string.h>
+
+/**
+ * SECTION: arvgcstructentrynode
+ * @short_description: Base class for StrucEntry nodes
+ *
+ * #ArvGcStructEntryNode provides a base class for the implementation of the different
+ * types of Genicam node.
+ */
+
+static GObjectClass *parent_class = NULL;
+
+/* ArvDomNode implementation */
+
+static const char *
+arv_gc_struct_entry_node_get_node_name (ArvDomNode *node)
+{
+	return "StructEntry";
+}
+
+static void
+arv_gc_struct_entry_node_post_new_child (ArvDomNode *self, ArvDomNode *child)
+{
+	ArvGcStructEntryNode *node = ARV_GC_STRUCT_ENTRY_NODE (self);
+
+	if (ARV_IS_GC_PROPERTY_NODE (child)) {
+		ArvGcPropertyNode *property_node = ARV_GC_PROPERTY_NODE (child);
+
+		switch (arv_gc_property_node_get_node_type (property_node)) {
+			case ARV_GC_PROPERTY_NODE_TYPE_SIGN:
+				/* TODO */
+				node->sign = property_node;
+				break;
+			case ARV_GC_PROPERTY_NODE_TYPE_LSB:
+				node->lsb = property_node;
+				break;
+			case ARV_GC_PROPERTY_NODE_TYPE_MSB:
+				node->msb = property_node;
+				break;
+			case ARV_GC_PROPERTY_NODE_TYPE_BIT:
+				node->msb = property_node;
+				node->lsb = property_node;
+				break;
+			default:
+				ARV_DOM_NODE_CLASS (parent_class)->post_new_child (self, child);
+				break;
+		}
+	}
+}
+
+static void
+arv_gc_struct_entry_node_pre_remove_child (ArvDomNode *self, ArvDomNode *child)
+{
+	g_assert_not_reached ();
+}
+
+/* ArvGcFeatureNode implementation */
+
+static GType
+arv_gc_struct_entry_node_get_value_type (ArvGcFeatureNode *node)
+{
+	return G_TYPE_INT64;
+}
+
+static void
+arv_gc_struct_entry_node_set_value_from_string (ArvGcFeatureNode *node, const char *string)
+{
+	arv_gc_integer_set_value (ARV_GC_INTEGER (node), g_ascii_strtoll (string, NULL, 0));
+}
+
+static const char *
+arv_gc_struct_entry_node_get_value_as_string (ArvGcFeatureNode *node)
+{
+	ArvGcStructEntryNode *gc_struct_entry_node = ARV_GC_STRUCT_ENTRY_NODE (node);
+
+	g_snprintf (gc_struct_entry_node->v_string, G_ASCII_DTOSTR_BUF_SIZE,
+		    "0x%08" G_GINT64_MODIFIER "x", arv_gc_integer_get_value (ARV_GC_INTEGER (node)));
+	return gc_struct_entry_node->v_string;
+}
+
+/* ArvGcStructEntryNode implementation */
+
+/* Set default to read only 32 bits little endian integer struct_entry_node */
+
+static ArvGcCachable
+_get_lsb (ArvGcStructEntryNode *gc_struct_entry_node)
+{
+	if (gc_struct_entry_node->lsb == NULL)
+		return 0;
+
+	return arv_gc_property_node_get_int64 (gc_struct_entry_node->lsb);
+}
+
+static ArvGcCachable
+_get_msb (ArvGcStructEntryNode *gc_struct_entry_node)
+{
+	if (gc_struct_entry_node->msb == NULL)
+		return 31;
+
+	return arv_gc_property_node_get_int64 (gc_struct_entry_node->msb);
+}
+
+ArvGcNode *
+arv_gc_struct_entry_node_new (void)
+{
+	ArvGcStructEntryNode *gc_struct_entry_node;
+
+	gc_struct_entry_node = g_object_new (ARV_TYPE_GC_STRUCT_ENTRY_NODE, NULL);
+
+	return ARV_GC_NODE (gc_struct_entry_node);
+}
+
+static void
+arv_gc_struct_entry_node_init (ArvGcStructEntryNode *gc_struct_entry_node)
+{
+}
+
+static void
+arv_gc_struct_entry_node_finalize (GObject *object)
+{
+	parent_class->finalize (object);
+}
+
+static void
+arv_gc_struct_entry_node_class_init (ArvGcStructEntryNodeClass *this_class)
+{
+	GObjectClass *object_class = G_OBJECT_CLASS (this_class);
+	ArvDomNodeClass *dom_node_class = ARV_DOM_NODE_CLASS (this_class);
+	ArvGcFeatureNodeClass *gc_feature_node_class = ARV_GC_FEATURE_NODE_CLASS (this_class);
+
+	parent_class = g_type_class_peek_parent (this_class);
+
+	object_class->finalize = arv_gc_struct_entry_node_finalize;
+	dom_node_class->get_node_name = arv_gc_struct_entry_node_get_node_name;
+	dom_node_class->post_new_child = arv_gc_struct_entry_node_post_new_child;
+	dom_node_class->pre_remove_child = arv_gc_struct_entry_node_pre_remove_child;
+	gc_feature_node_class->get_value_type = arv_gc_struct_entry_node_get_value_type;
+	gc_feature_node_class->set_value_from_string = arv_gc_struct_entry_node_set_value_from_string;
+	gc_feature_node_class->get_value_as_string = arv_gc_struct_entry_node_get_value_as_string;
+}
+
+/* ArvGcInteger interface implementation */
+
+static gint64
+arv_gc_struct_entry_node_get_integer_value (ArvGcInteger *gc_integer)
+{
+	ArvGcStructEntryNode *struct_entry = ARV_GC_STRUCT_ENTRY_NODE (gc_integer);
+	ArvDomNode *struct_register;
+	guint lsb;
+	guint msb;
+
+	struct_register = arv_dom_node_get_parent_node (ARV_DOM_NODE (gc_integer));
+	if (!ARV_IS_GC_REGISTER (struct_register))
+		return 0;
+
+	lsb = _get_lsb (struct_entry);
+	msb = _get_msb (struct_entry);
+
+	return arv_gc_register_get_masked_integer_value (ARV_GC_REGISTER (struct_register), lsb, msb);
+}
+
+static void
+arv_gc_struct_entry_node_set_integer_value (ArvGcInteger *gc_integer, gint64 value)
+{
+	ArvGcStructEntryNode *struct_entry = ARV_GC_STRUCT_ENTRY_NODE (gc_integer);
+	ArvDomNode *struct_register;
+	guint lsb;
+	guint msb;
+
+	struct_register = arv_dom_node_get_parent_node (ARV_DOM_NODE (gc_integer));
+	if (!ARV_IS_GC_REGISTER (struct_register))
+		return;
+
+	lsb = _get_lsb (struct_entry);
+	msb = _get_msb (struct_entry);
+
+	arv_gc_register_set_masked_integer_value (ARV_GC_REGISTER (struct_register), lsb, msb, value);
+}
+
+static void
+arv_gc_struct_entry_node_integer_interface_init (ArvGcIntegerInterface *interface)
+{
+	interface->get_value = arv_gc_struct_entry_node_get_integer_value;
+	interface->set_value = arv_gc_struct_entry_node_set_integer_value;
+}
+
+G_DEFINE_TYPE_WITH_CODE (ArvGcStructEntryNode, arv_gc_struct_entry_node, ARV_TYPE_GC_FEATURE_NODE,
+			 G_IMPLEMENT_INTERFACE (ARV_TYPE_GC_INTEGER, arv_gc_struct_entry_node_integer_interface_init))
diff --git a/src/arvgcstructentrynode.h b/src/arvgcstructentrynode.h
new file mode 100644
index 0000000..bbe54bf
--- /dev/null
+++ b/src/arvgcstructentrynode.h
@@ -0,0 +1,60 @@
+/* Aravis - Digital camera library
+ *
+ * Copyright  2009-2012 Emmanuel Pacaud
+ *
+ * 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 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., 59 Temple Place, Suite 330,
+ * Boston, MA 02111-1307, USA.
+ *
+ * Author: Emmanuel Pacaud <emmanuel gnome org>
+ */
+
+#ifndef ARV_GC_STRUCT_ENTRY_NODE_H
+#define ARV_GC_STRUCT_ENTRY_NODE_H
+
+#include <arvtypes.h>
+#include <arvgcfeaturenode.h>
+#include <arvgcpropertynode.h>
+
+G_BEGIN_DECLS
+
+#define ARV_TYPE_GC_STRUCT_ENTRY_NODE             (arv_gc_struct_entry_node_get_type ())
+#define ARV_GC_STRUCT_ENTRY_NODE(obj)             (G_TYPE_CHECK_INSTANCE_CAST ((obj), ARV_TYPE_GC_STRUCT_ENTRY_NODE, ArvGcStructEntryNode))
+#define ARV_GC_STRUCT_ENTRY_NODE_CLASS(klass)     (G_TYPE_CHECK_CLASS_CAST ((klass), ARV_TYPE_GC_STRUCT_ENTRY_NODE, ArvGcStructEntryNodeClass))
+#define ARV_IS_GC_STRUCT_ENTRY_NODE(obj)          (G_TYPE_CHECK_INSTANCE_TYPE ((obj), ARV_TYPE_GC_STRUCT_ENTRY_NODE))
+#define ARV_IS_GC_STRUCT_ENTRY_NODE_CLASS(klass)  (G_TYPE_CHECK_CLASS_TYPE ((klass), ARV_TYPE_GC_STRUCT_ENTRY_NODE))
+#define ARV_GC_STRUCT_ENTRY_NODE_GET_CLASS(obj)   (G_TYPE_INSTANCE_GET_CLASS((obj), ARV_TYPE_GC_STRUCT_ENTRY_NODE, ArvGcStructEntryNodeClass))
+
+typedef struct _ArvGcStructEntryNodeClass ArvGcStructEntryNodeClass;
+
+struct _ArvGcStructEntryNode {
+	ArvGcFeatureNode	node;
+
+	ArvGcPropertyNode *sign;
+	ArvGcPropertyNode *lsb;
+	ArvGcPropertyNode *msb;
+
+	char v_string[G_ASCII_DTOSTR_BUF_SIZE];
+};
+
+struct _ArvGcStructEntryNodeClass {
+	ArvGcFeatureNodeClass parent_class;
+};
+
+GType 		arv_gc_struct_entry_node_get_type 		(void);
+ArvGcNode * 	arv_gc_struct_entry_node_new 			(void);
+
+G_END_DECLS
+
+#endif
diff --git a/src/arvtypes.h b/src/arvtypes.h
index f7d8293..0b503ea 100644
--- a/src/arvtypes.h
+++ b/src/arvtypes.h
@@ -57,6 +57,7 @@ typedef struct _ArvGcEnumEntry			ArvGcEnumEntry;
 typedef struct _ArvGcIntegerNode		ArvGcIntegerNode;
 typedef struct _ArvGcFloatNode			ArvGcFloatNode;
 typedef struct _ArvGcRegister 			ArvGcRegister;
+typedef struct _ArvGcStructEntryNode		ArvGcStructEntryNode;
 typedef struct _ArvGcCommand			ArvGcCommand;
 typedef struct _ArvGcSwissKnife			ArvGcSwissKnife;
 typedef struct _ArvGcConverter			ArvGcConverter;
diff --git a/tests/fake.c b/tests/fake.c
index e4dc94f..1c84a0c 100644
--- a/tests/fake.c
+++ b/tests/fake.c
@@ -53,6 +53,70 @@ trigger_registers_test (void)
 }
 
 static void
+registers_test (void)
+{
+	ArvDevice *device;
+	ArvGc *genicam;
+	ArvGcNode *node;
+	ArvGcNode *node_a;
+	ArvGcNode *node_b;
+	ArvGcNode *node_c;
+	gint64 value;
+
+	device = arv_fake_device_new ("TEST0");
+	g_assert (ARV_IS_FAKE_DEVICE (device));
+
+	genicam = arv_device_get_genicam (device);
+	g_assert (ARV_IS_GC (genicam));
+
+	node = arv_gc_get_node (genicam, "TestRegister");
+	g_assert (ARV_IS_GC_NODE (node));
+
+	arv_gc_integer_set_value (ARV_GC_INTEGER (node), 0x12345678);
+	value = arv_gc_integer_get_value (ARV_GC_INTEGER (node));
+	g_assert_cmpint (value, ==, 0x12345678);
+
+	node_a = arv_gc_get_node (genicam, "StructEntry_0_15");
+	g_assert (ARV_IS_GC_NODE (node_a));
+	node_b = arv_gc_get_node (genicam, "StructEntry_16_31");
+	g_assert (ARV_IS_GC_NODE (node_b));
+	node_c = arv_gc_get_node (genicam, "StructEntry_16");
+	g_assert (ARV_IS_GC_NODE (node_c));
+
+	value = arv_gc_integer_get_value (ARV_GC_INTEGER (node_a));
+	g_assert_cmpint (value, ==, 0x5678);
+
+	value = arv_gc_integer_get_value (ARV_GC_INTEGER (node_b));
+	g_assert_cmpint (value, ==, 0x1234);
+
+	arv_gc_integer_set_value (ARV_GC_INTEGER (node_b), 0x10101010);
+
+	value = arv_gc_integer_get_value (ARV_GC_INTEGER (node_a));
+	g_assert_cmpint (value, ==, 0x5678);
+
+	arv_gc_integer_set_value (ARV_GC_INTEGER (node_a), 0xabcdefaa);
+
+	value = arv_gc_integer_get_value (ARV_GC_INTEGER (node_a));
+	g_assert_cmpint (value, ==, 0xefaa);
+
+	value = arv_gc_integer_get_value (ARV_GC_INTEGER (node_b));
+	g_assert_cmpint (value, ==, 0x1010);
+
+	value = arv_gc_integer_get_value (ARV_GC_INTEGER (node_c));
+	g_assert_cmpint (value, ==, 0x0);
+
+	arv_gc_integer_set_value (ARV_GC_INTEGER (node_c), 0xff);
+
+	value = arv_gc_integer_get_value (ARV_GC_INTEGER (node_c));
+	g_assert_cmpint (value, ==, 0x1);
+
+	value = arv_gc_integer_get_value (ARV_GC_INTEGER (node_b));
+	g_assert_cmpint (value, ==, 0x1011);
+
+	g_object_unref (device);
+}
+
+static void
 fake_device_test (void)
 {
 	ArvDevice *device;
@@ -115,6 +179,7 @@ main (int argc, char *argv[])
 
 	g_test_add_func ("/fake/load-fake-camera-genicam", load_fake_camera_genicam_test);
 	g_test_add_func ("/fake/trigger-registers", trigger_registers_test);
+	g_test_add_func ("/fake/registers", registers_test);
 	g_test_add_func ("/fake/fake-device", fake_device_test);
 
 	result = g_test_run();



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]