dbus/mono InterfaceProxy.cs, NONE, 1.1 Arguments.cs, 1.1,
1.2 Handler.cs, 1.1, 1.2 Introspector.cs, 1.1, 1.2 Makefile.am,
1.3, 1.4 Message.cs, 1.6, 1.7 ProxyBuilder.cs, 1.1,
1.2 Service.cs, 1.1, 1.2
Owen Fraser-Green
ow3n at pdx.freedesktop.org
Tue Mar 23 10:07:50 PST 2004
Update of /cvs/dbus/dbus/mono
In directory pdx:/tmp/cvs-serv27858/mono
Modified Files:
Arguments.cs Handler.cs Introspector.cs Makefile.am Message.cs
ProxyBuilder.cs Service.cs
Added Files:
InterfaceProxy.cs
Log Message:
Added InterfaceProxy to Mono bindings to avoid having to generate a proxy for every registered object. Also added object_path functions to dbus-message.
--- NEW FILE: InterfaceProxy.cs ---
namespace DBus
{
using System;
using System.Collections;
using System.Reflection;
internal class InterfaceProxy
{
private static Hashtable interfaceProxies = new Hashtable();
private Hashtable methods = null;
private string interfaceName;
private InterfaceProxy(Type type)
{
object[] attributes = type.GetCustomAttributes(typeof(InterfaceAttribute), true);
InterfaceAttribute interfaceAttribute = (InterfaceAttribute) attributes[0];
this.interfaceName = interfaceAttribute.InterfaceName;
AddMethods(type);
}
private void AddMethods(Type type)
{
this.methods = new Hashtable();
foreach (MethodInfo method in type.GetMethods(BindingFlags.Public |
BindingFlags.Instance |
BindingFlags.DeclaredOnly)) {
object[] attributes = method.GetCustomAttributes(typeof(MethodAttribute), true);
if (attributes.GetLength(0) > 0) {
methods.Add(GetKey(method), method);
}
}
}
public static InterfaceProxy GetInterface(Type type)
{
if (!interfaceProxies.Contains(type)) {
interfaceProxies[type] = new InterfaceProxy(type);
}
return (InterfaceProxy) interfaceProxies[type];
}
public bool HasMethod(string key)
{
return this.Methods.Contains(key);
}
public MethodInfo GetMethod(string key)
{
return (MethodInfo) this.Methods[key];
}
private string GetKey(MethodInfo method)
{
ParameterInfo[] pars = method.GetParameters();
string key = method.Name + " ";
foreach (ParameterInfo par in pars) {
if (!par.IsOut) {
Type dbusType = Arguments.MatchType(par.ParameterType);
key += Arguments.GetCode(dbusType);
}
}
return key;
}
public Hashtable Methods
{
get {
return this.methods;
}
}
public string InterfaceName
{
get {
return this.interfaceName;
}
}
}
}
Index: Arguments.cs
===================================================================
RCS file: /cvs/dbus/dbus/mono/Arguments.cs,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -d -r1.1 -r1.2
--- a/Arguments.cs 23 Mar 2004 12:10:32 -0000 1.1
+++ b/Arguments.cs 23 Mar 2004 18:07:48 -0000 1.2
@@ -170,22 +170,6 @@
return constructor;
}
- // Get the signature of a method
- public static string ParseParameters(MethodInfo method)
- {
- ParameterInfo[] pars = method.GetParameters();
- string key = "";
-
- foreach (ParameterInfo par in pars) {
- if (!par.IsOut) {
- Type dbusType = MatchType(par.ParameterType);
- key += GetCode(dbusType);
- }
- }
-
- return key;
- }
-
// Get the type code for a given D-BUS type
public static char GetCode(Type dbusType)
{
Index: Handler.cs
===================================================================
RCS file: /cvs/dbus/dbus/mono/Handler.cs,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -d -r1.1 -r1.2
--- a/Handler.cs 23 Mar 2004 12:10:32 -0000 1.1
+++ b/Handler.cs 23 Mar 2004 18:07:48 -0000 1.2
@@ -12,7 +12,6 @@
private string pathName = null;
private Introspector introspector = null;
private object handledObject = null;
- private Hashtable handledMethods = null;
private DBusObjectPathVTable vTable;
private Connection connection;
private Service service;
@@ -99,33 +98,20 @@
throw new OutOfMemoryException();
}
- private void RegisterMethod(MethodInfo method)
- {
- string key = method.Name + " " + Arguments.ParseParameters(method);
- handledMethods.Add(key, method);
- }
-
public object HandledObject
{
- get
- {
- return this.handledObject;
- }
+ get {
+ return this.handledObject;
+ }
- set
- {
- this.handledObject = value;
-
- object[] attributes;
-
- // Register the methods
- this.handledMethods = new Hashtable();
- this.introspector = new Introspector(value.GetType());
-
- foreach (MethodInfo method in this.introspector.Methods) {
- RegisterMethod(method);
- }
- }
+ set {
+ this.handledObject = value;
+
+ object[] attributes;
+
+ // Register the methods
+ this.introspector = Introspector.GetIntrospector(value.GetType());
+ }
}
public int Filter_Called(IntPtr rawConnection,
@@ -169,22 +155,14 @@
private Result HandleMethod(MethodCall methodCall)
{
methodCall.Service = service;
-
- // Check the interface name matches
- if (methodCall.InterfaceName != this.introspector.InterfaceName) {
- return Result.NotYetHandled;
- }
-
- // Iterate through getting the type codes
- string key = methodCall.Name + " " + methodCall.Arguments;
-
- // Check it's one of our methods
- if (!handledMethods.Contains(key)) {
+
+ InterfaceProxy interfaceProxy = this.introspector.GetInterface(methodCall.InterfaceName);
+ if (interfaceProxy == null || !interfaceProxy.HasMethod(methodCall.Key)) {
+ // No such interface here.
return Result.NotYetHandled;
}
-
- // Got it!
- MethodInfo method = (MethodInfo) handledMethods[key];
+
+ MethodInfo method = interfaceProxy.GetMethod(methodCall.Key);
// Now call the method. FIXME: Error handling
object [] args = methodCall.Arguments.GetParameters(method);
Index: Introspector.cs
===================================================================
RCS file: /cvs/dbus/dbus/mono/Introspector.cs,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -d -r1.1 -r1.2
--- a/Introspector.cs 23 Mar 2004 12:10:32 -0000 1.1
+++ b/Introspector.cs 23 Mar 2004 18:07:48 -0000 1.2
@@ -10,97 +10,72 @@
internal class Introspector
{
private Type type;
- private string interfaceName;
+ private static Hashtable introspectors = new Hashtable();
+ private Hashtable interfaceProxies = null;
- public Introspector(Type type) {
- object[] attributes = type.GetCustomAttributes(typeof(InterfaceAttribute), true);
- if (attributes.Length != 1)
- throw new ApplicationException("Type '" + type + "' is not a D-BUS interface.");
-
- InterfaceAttribute interfaceAttribute = (InterfaceAttribute) attributes[0];
-
- this.interfaceName = interfaceAttribute.InterfaceName;
+ public static Introspector GetIntrospector(Type type)
+ {
+ if (!introspectors.Contains(type)) {
+ introspectors[type] = new Introspector(type);
+ }
+
+ return (Introspector) introspectors[type];
+ }
+
+ private Introspector(Type type)
+ {
+ interfaceProxies = new Hashtable();
+ AddType(type);
this.type = type;
}
- public string InterfaceName
+ private void AddType(Type type)
{
- get
- {
- return this.interfaceName;
- }
+ if (type == typeof(object)) {
+ // Base case
+ return;
+ }
+
+ object[] attributes = type.GetCustomAttributes(typeof(InterfaceAttribute), false);
+ if (attributes.Length >= 1) {
+ // This is a D-BUS interface so add it to the hashtable
+ InterfaceProxy interfaceProxy = InterfaceProxy.GetInterface(type);
+ interfaceProxies.Add(interfaceProxy.InterfaceName, interfaceProxy);
+ }
+
+ AddType(type.BaseType);
+ }
+
+ public InterfaceProxy GetInterface(string interfaceName) {
+ if (interfaceProxies.Contains(interfaceName)) {
+ return (InterfaceProxy) interfaceProxies[interfaceName];
+ } else {
+ return null;
+ }
}
- public ConstructorInfo Constructor
+ public Hashtable InterfaceProxies
{
- get
- {
- ConstructorInfo ret = this.type.GetConstructor(new Type[0]);
- if (ret != null) {
- return ret;
- } else {
- return typeof(object).GetConstructor(new Type[0]);
- }
- }
+ get {
+ return this.interfaceProxies;
+ }
}
- public IntrospectorMethods Methods
+ public ConstructorInfo Constructor
{
- get
- {
- return new IntrospectorMethods(this.type);
+ get {
+ ConstructorInfo ret = this.type.GetConstructor(new Type[0]);
+ if (ret != null) {
+ return ret;
+ } else {
+ return typeof(object).GetConstructor(new Type[0]);
}
+ }
}
- public class IntrospectorMethods : IEnumerable
+ public override string ToString()
{
- private Type type;
-
- public IntrospectorMethods(Type type)
- {
- this.type = type;
- }
-
- public IEnumerator GetEnumerator()
- {
- return new MethodEnumerator(this.type.GetMethods(BindingFlags.Public|BindingFlags.Instance).GetEnumerator());
- }
-
- private class MethodEnumerator : IEnumerator
- {
- private IEnumerator enumerator;
-
- public MethodEnumerator(IEnumerator enumerator)
- {
- this.enumerator = enumerator;
- }
-
- public bool MoveNext()
- {
- while (enumerator.MoveNext()) {
- MethodInfo method = (MethodInfo) enumerator.Current;
- object[] attributes = method.GetCustomAttributes(typeof(MethodAttribute), true);
- if (attributes.GetLength(0) > 0) {
- return true;
- }
- }
-
- return false;
- }
-
- public void Reset()
- {
- enumerator.Reset();
- }
-
- public object Current
- {
- get
- {
- return enumerator.Current;
- }
- }
- }
+ return this.type.ToString();
}
}
}
Index: Makefile.am
===================================================================
RCS file: /cvs/dbus/dbus/mono/Makefile.am,v
retrieving revision 1.3
retrieving revision 1.4
diff -u -d -r1.3 -r1.4
--- a/Makefile.am 23 Mar 2004 12:10:32 -0000 1.3
+++ b/Makefile.am 23 Mar 2004 18:07:48 -0000 1.4
@@ -12,6 +12,7 @@
Error.cs \
Handler.cs \
InterfaceAttribute.cs \
+ InterfaceProxy.cs \
Introspector.cs \
Message.cs \
MethodAttribute.cs \
Index: Message.cs
===================================================================
RCS file: /cvs/dbus/dbus/mono/Message.cs,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -d -r1.6 -r1.7
--- a/Message.cs 23 Mar 2004 12:10:32 -0000 1.6
+++ b/Message.cs 23 Mar 2004 18:07:48 -0000 1.7
@@ -35,6 +35,7 @@
protected string pathName = null;
protected string interfaceName = null;
protected string name = null;
+ private string key= null;
protected Message()
{
@@ -263,6 +264,17 @@
}
}
+ public string Key
+ {
+ get {
+ if (this.key == null) {
+ this.key = Name + " " + Arguments;
+ }
+
+ return this.key;
+ }
+ }
+
public Arguments Arguments
{
get
Index: ProxyBuilder.cs
===================================================================
RCS file: /cvs/dbus/dbus/mono/ProxyBuilder.cs,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -d -r1.1 -r1.2
--- a/ProxyBuilder.cs 23 Mar 2004 12:10:32 -0000 1.1
+++ b/ProxyBuilder.cs 23 Mar 2004 18:07:48 -0000 1.2
@@ -50,13 +50,13 @@
this.service = service;
this.pathName = pathName;
this.type = type;
- this.introspector = new Introspector(type);
+ this.introspector = Introspector.GetIntrospector(type);
}
private void BuildMethod(MethodInfo method,
+ InterfaceProxy interfaceProxy,
ref TypeBuilder typeB,
FieldInfo serviceF,
- FieldInfo interfaceF,
FieldInfo pathF)
{
ParameterInfo[] pars = method.GetParameters();
@@ -95,7 +95,7 @@
generator.Emit(OpCodes.Ldsfld, serviceF);
generator.Emit(OpCodes.Ldarg_0);
generator.Emit(OpCodes.Ldfld, pathF);
- generator.Emit(OpCodes.Ldsfld, interfaceF);
+ generator.Emit(OpCodes.Ldstr, interfaceProxy.InterfaceName);
generator.Emit(OpCodes.Ldstr, method.Name);
generator.Emit(OpCodes.Newobj, MethodCall_C);
generator.Emit(OpCodes.Stloc_0);
@@ -190,9 +190,9 @@
}
}
- public void BuildConstructor(ref TypeBuilder typeB, FieldInfo serviceF, FieldInfo interfaceF, FieldInfo pathF)
+ public void BuildConstructor(ref TypeBuilder typeB, FieldInfo serviceF, FieldInfo pathF)
{
- Type[] pars = {typeof(Service), typeof(string), typeof(string)};
+ Type[] pars = {typeof(Service), typeof(string)};
ConstructorBuilder constructor = typeB.DefineConstructor(MethodAttributes.RTSpecialName |
MethodAttributes.Public,
CallingConventions.Standard, pars);
@@ -202,10 +202,8 @@
generator.Emit(OpCodes.Call, this.introspector.Constructor);
generator.Emit(OpCodes.Ldarg_1);
generator.Emit(OpCodes.Stsfld, serviceF);
- generator.Emit(OpCodes.Ldarg_2);
- generator.Emit(OpCodes.Stsfld, interfaceF);
generator.Emit(OpCodes.Ldarg_0);
- generator.Emit(OpCodes.Ldarg_3);
+ generator.Emit(OpCodes.Ldarg_2);
generator.Emit(OpCodes.Stfld, pathF);
generator.Emit(OpCodes.Ret);
@@ -216,29 +214,28 @@
// Build the type
TypeBuilder typeB = ServiceModuleBuilder.DefineType(ProxyName, TypeAttributes.Public, this.type);
- //type.AddInterfaceImplementation(typeof(IProxy));
FieldBuilder serviceF = typeB.DefineField("service",
typeof(Service),
FieldAttributes.Private |
FieldAttributes.Static);
- FieldBuilder interfaceF = typeB.DefineField("interfaceName",
- typeof(string),
- FieldAttributes.Private |
- FieldAttributes.Static);
FieldBuilder pathF = typeB.DefineField("pathName",
typeof(string),
FieldAttributes.Private);
- BuildConstructor(ref typeB, serviceF, interfaceF, pathF);
+ BuildConstructor(ref typeB, serviceF, pathF);
// Build the methods
- foreach (MethodInfo method in this.introspector.Methods) {
- BuildMethod(method, ref typeB, serviceF, interfaceF, pathF);
+ foreach (DictionaryEntry interfaceEntry in this.introspector.InterfaceProxies) {
+ InterfaceProxy interfaceProxy = (InterfaceProxy) interfaceEntry.Value;
+ foreach (DictionaryEntry methodEntry in interfaceProxy.Methods) {
+ MethodInfo method = (MethodInfo) methodEntry.Value;
+ BuildMethod(method, interfaceProxy, ref typeB, serviceF, pathF);
+ }
}
- Type [] parTypes = new Type[] {typeof(Service), typeof(string), typeof(string)};
- object [] pars = new object[] {Service, this.introspector.InterfaceName, pathName};
+ Type [] parTypes = new Type[] {typeof(Service), typeof(string)};
+ object [] pars = new object[] {Service, pathName};
Type proxyType = typeB.CreateType();
@@ -247,7 +244,7 @@
// monodis. Note that in order for this to work you should copy
// the client assembly as a dll file so that monodis can pick it
// up.
- //ProxyAssembly.Save("proxy.dll");
+ ProxyAssembly.Save("proxy.dll");
ConstructorInfo constructor = proxyType.GetConstructor(parTypes);
object instance = constructor.Invoke(pars);
@@ -256,45 +253,41 @@
private ModuleBuilder ServiceModuleBuilder
{
- get
- {
- if (Service.module == null) {
- Service.module = ProxyAssembly.DefineDynamicModule(Service.Name, "proxy.dll", true);
- }
-
- return Service.module;
+ get {
+ if (Service.module == null) {
+ Service.module = ProxyAssembly.DefineDynamicModule(Service.Name, "proxy.dll", true);
}
+
+ return Service.module;
+ }
}
private Service Service
{
- get
- {
- return this.service;
- }
+ get {
+ return this.service;
+ }
}
private string ProxyName
{
- get
- {
- return this.introspector.InterfaceName + ".Proxy";
- }
+ get {
+ return this.introspector.ToString() + ".Proxy";
+ }
}
private AssemblyBuilder ProxyAssembly
{
- get
- {
- if (this.proxyAssembly == null){
- AssemblyName assemblyName = new AssemblyName();
- assemblyName.Name = "DBusProxy";
- this.proxyAssembly = Thread.GetDomain().DefineDynamicAssembly(assemblyName,
- AssemblyBuilderAccess.RunAndSave);
- }
-
- return this.proxyAssembly;
+ get {
+ if (this.proxyAssembly == null){
+ AssemblyName assemblyName = new AssemblyName();
+ assemblyName.Name = "DBusProxy";
+ this.proxyAssembly = Thread.GetDomain().DefineDynamicAssembly(assemblyName,
+ AssemblyBuilderAccess.RunAndSave);
}
+
+ return this.proxyAssembly;
+ }
}
}
}
Index: Service.cs
===================================================================
RCS file: /cvs/dbus/dbus/mono/Service.cs,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -d -r1.1 -r1.2
--- a/Service.cs 23 Mar 2004 12:10:32 -0000 1.1
+++ b/Service.cs 23 Mar 2004 18:07:48 -0000 1.2
@@ -68,8 +68,8 @@
string pathName)
{
Handler handler = new Handler(handledObject,
- pathName,
- this);
+ pathName,
+ this);
registeredHandlers.Add(handledObject, handler);
}
More information about the dbus-commit
mailing list