00001 using System;
00002 using System.Runtime.InteropServices;
00003 using System.Reflection.Emit;
00004
00005 using DBus;
00006
00007 namespace DBus.DBusType
00008 {
00012 public class ObjectPath : IDBusType
00013 {
00014 public const char Code = 'o';
00015 private string path = null;
00016 private object val = null;
00017 private Service service = null;
00018
00019 private ObjectPath()
00020 {
00021 }
00022
00023 public ObjectPath(object val, Service service)
00024 {
00025 this.val = val;
00026 this.service = service;
00027 }
00028
00029 public ObjectPath(IntPtr iter, Service service)
00030 {
00031 IntPtr raw;
00032
00033 dbus_message_iter_get_basic (iter, out raw);
00034
00035 this.path = Marshal.PtrToStringAnsi (raw);
00036 this.service = service;
00037 }
00038
00039 private string Path
00040 {
00041 get {
00042 if (this.path == null && this.val != null) {
00043 Handler handler = this.service.GetHandler(this.val);
00044 this.path = handler.Path;
00045 }
00046
00047 return this.path;
00048 }
00049 }
00050
00051 public void Append(IntPtr iter)
00052 {
00053 IntPtr marshalVal = Marshal.StringToHGlobalAnsi (Path);
00054
00055 bool success = dbus_message_iter_append_basic (iter, (int) Code, ref marshalVal);
00056 Marshal.FreeHGlobal (marshalVal);
00057
00058 if (!success)
00059 throw new ApplicationException("Failed to append OBJECT_PATH argument:" + val);
00060 }
00061
00062 public static bool Suits(System.Type type)
00063 {
00064 object[] attributes = type.GetCustomAttributes(typeof(InterfaceAttribute), false);
00065 if (attributes.Length == 1) {
00066 return true;
00067 } else {
00068 return false;
00069 }
00070 }
00071
00072 public static void EmitMarshalIn(ILGenerator generator, Type type)
00073 {
00074 if (type.IsByRef) {
00075 generator.Emit(OpCodes.Ldind_Ref);
00076 }
00077 }
00078
00079 public static void EmitMarshalOut(ILGenerator generator, Type type, bool isReturn)
00080 {
00081 generator.Emit(OpCodes.Castclass, type);
00082 if (!isReturn) {
00083 generator.Emit(OpCodes.Stind_Ref);
00084 }
00085 }
00086
00087 public object Get()
00088 {
00089 throw new ArgumentException("Cannot call Get on an ObjectPath without specifying type.");
00090 }
00091
00092 public object Get(System.Type type)
00093 {
00094 try {
00095 return this.service.GetObject(type, Path);
00096 } catch(Exception ex) {
00097 throw new ArgumentException("Cannot cast object pointed to by Object Path to type '" + type.ToString() + "': " + ex);
00098 }
00099 }
00100
00101 [DllImport("dbus-1")]
00102 private extern static void dbus_message_iter_get_basic (IntPtr iter, out IntPtr path);
00103
00104 [DllImport("dbus-1")]
00105 private extern static bool dbus_message_iter_append_basic (IntPtr iter, int type, ref IntPtr path);
00106 }
00107 }