summaryrefslogtreecommitdiffstats
path: root/mono/DBusType/Array.cs
diff options
context:
space:
mode:
authorOwen Fraser-Green <owen@discobabe.net>2004-03-23 12:10:32 +0000
committerOwen Fraser-Green <owen@discobabe.net>2004-03-23 12:10:32 +0000
commitc916037773d7d3d8d37ca2c5a8899b7b728e377d (patch)
tree21c37372ab9795583e724e8459578b7fe0be330b /mono/DBusType/Array.cs
parent2195cf0dbde2ae26b5a684c6d914c1711f44c28d (diff)
First checkin of the Mono bindings.
Diffstat (limited to 'mono/DBusType/Array.cs')
-rw-r--r--mono/DBusType/Array.cs130
1 files changed, 130 insertions, 0 deletions
diff --git a/mono/DBusType/Array.cs b/mono/DBusType/Array.cs
new file mode 100644
index 00000000..3bce3afa
--- /dev/null
+++ b/mono/DBusType/Array.cs
@@ -0,0 +1,130 @@
+using System;
+using System.Collections;
+using System.Runtime.InteropServices;
+using System.Reflection.Emit;
+
+using DBus;
+
+namespace DBus.DBusType
+{
+ /// <summary>
+ /// Array.
+ /// </summary>
+ public class Array : IDBusType
+ {
+ public const char Code = 'a';
+ private System.Array val;
+ private ArrayList elements;
+ private Type elementType;
+
+ private Array()
+ {
+ }
+
+ public Array(System.Array val)
+ {
+ this.val = val;
+ this.elementType = Arguments.MatchType(val.GetType().UnderlyingSystemType);
+ }
+
+ public Array(IntPtr iter)
+ {
+ IntPtr arrayIter = Marshal.AllocCoTaskMem(Arguments.DBusMessageIterSize);
+
+ int elementTypeCode;
+ dbus_message_iter_init_array_iterator(iter, arrayIter, out elementTypeCode);
+ this.elementType = (Type) Arguments.DBusTypes[(char) elementTypeCode];
+
+ elements = new ArrayList();
+
+ do {
+ object [] pars = new Object[1];
+ pars[0] = arrayIter;
+ DBusType.IDBusType dbusType = (DBusType.IDBusType) Activator.CreateInstance(elementType, pars);
+ elements.Add(dbusType);
+ } while (dbus_message_iter_next(arrayIter));
+
+ Marshal.FreeCoTaskMem(arrayIter);
+ }
+
+ public void Append(IntPtr iter)
+ {
+ IntPtr arrayIter = Marshal.AllocCoTaskMem(Arguments.DBusMessageIterSize);
+
+ if (!dbus_message_iter_append_array(iter,
+ arrayIter,
+ (int) Arguments.GetCode(this.elementType))) {
+ throw new ApplicationException("Failed to append INT32 argument:" + val);
+ }
+
+ foreach (object element in this.val) {
+ object [] pars = new Object[1];
+ pars[0] = element;
+ DBusType.IDBusType dbusType = (DBusType.IDBusType) Activator.CreateInstance(elementType, pars);
+ dbusType.Append(arrayIter);
+ }
+
+ Marshal.FreeCoTaskMem(arrayIter);
+ }
+
+ public static bool Suits(System.Type type)
+ {
+ if (type.IsArray) {
+ return true;
+ }
+
+ return false;
+ }
+
+ public static void EmitMarshalIn(ILGenerator generator, Type type)
+ {
+ if (type.IsByRef) {
+ generator.Emit(OpCodes.Ldind_Ref);
+ }
+ }
+
+ public static void EmitMarshalOut(ILGenerator generator, Type type, bool isReturn)
+ {
+ generator.Emit(OpCodes.Castclass, type);
+ if (!isReturn) {
+ generator.Emit(OpCodes.Stind_Ref);
+ }
+ }
+
+ public object Get()
+ {
+ throw new ArgumentException("Cannot call Get on an Array without specifying type.");
+ }
+
+ public object Get(System.Type type)
+ {
+ if (Arguments.Suits(elementType, type.UnderlyingSystemType)) {
+ this.val = System.Array.CreateInstance(type.UnderlyingSystemType, elements.Count);
+ int i = 0;
+ foreach (DBusType.IDBusType element in elements) {
+ this.val.SetValue(element.Get(type.UnderlyingSystemType), i++);
+ }
+ } else {
+ throw new ArgumentException("Cannot cast DBus.Type.Array to type '" + type.ToString() + "'");
+ }
+
+ return this.val;
+ }
+
+ [DllImport("dbus-1")]
+ private extern static void dbus_message_iter_init_array_iterator(IntPtr iter,
+ IntPtr arrayIter,
+ out int elementType);
+
+ [DllImport("dbus-1")]
+ private extern static bool dbus_message_iter_append_array(IntPtr iter,
+ IntPtr arrayIter,
+ int elementType);
+
+ [DllImport("dbus-1")]
+ private extern static bool dbus_message_iter_has_next(IntPtr iter);
+
+ [DllImport("dbus-1")]
+ private extern static bool dbus_message_iter_next(IntPtr iter);
+ }
+}