[Kde-bindings] playground/bindings/kimono
Richard Dale
Richard_Dale at tipitina.demon.co.uk
Mon Feb 12 14:03:16 UTC 2007
SVN commit 632847 by rdale:
* The scheme for caching the smoke methodId inside a SmokeMethod Attribute
didn't work, and the value returned was always -1, even when it had been
set to a value. So use a dictionary of type Dictionary<MethodInfo, int>
as a cache instead.
CCMAIL: kde-bindings at kde.org
M +7 -0 ChangeLog
M +29 -20 SmokeInvocation.cs
--- trunk/playground/bindings/kimono/ChangeLog #632846:632847
@@ -1,3 +1,10 @@
+2007-02-12 Richard Dale <rdale at foton.es>
+
+ * The scheme for caching the smoke methodId inside a SmokeMethod Attribute
+ didn't work, and the value returned was always -1, even when it had been
+ set to a value. So use a dictionary of type Dictionary<MethodInfo, int>
+ as a cache instead.
+
2007-02-11 Richard Dale <rdale at foton.es>
* Don't call a destructor is the instance was allocated in the C++ world
--- trunk/playground/bindings/kimono/SmokeInvocation.cs #632846:632847
@@ -340,6 +340,8 @@
private Type _classToProxy;
private Object _instance;
private string _className = "";
+
+ private static Dictionary<MethodInfo, int> methodIdCache = new Dictionary<MethodInfo, int>();
public SmokeInvocation(Type classToProxy, Object instance) : base(classToProxy)
{
@@ -357,6 +359,8 @@
public override IMessage Invoke(IMessage message) {
IMethodCallMessage callMessage = (IMethodCallMessage) message;
+ IMethodReturnMessage returnMessage = (IMethodReturnMessage) message;
+
#if DEBUG
if ((Debug.DebugChannel() & QtDebugChannel.QTDB_TRANSPARENT_PROXY) != 0) {
Console.WriteLine( "ENTER SmokeInvocation.Invoke() MethodName: {0}.{1} Type: {2} ArgCount: {3}",
@@ -366,30 +370,32 @@
callMessage.ArgCount.ToString() );
}
#endif
-
- StackItem[] stack = new StackItem[callMessage.ArgCount+1];
int methodId = -1;
- object[] smokeMethod = ((MethodInfo) callMessage.MethodBase).GetCustomAttributes(typeof(SmokeMethod), false);
- if (smokeMethod.Length > 0) {
- methodId = ((SmokeMethod) smokeMethod[0]).methodId;
- if (methodId == -1) {
+ if (!methodIdCache.TryGetValue((MethodInfo) callMessage.MethodBase, out methodId)) {
+ object[] smokeMethod = ((MethodInfo) callMessage.MethodBase).GetCustomAttributes(typeof(SmokeMethod), false);
+ if (smokeMethod.Length > 0) {
methodId = FindMethodId( _className,
((SmokeMethod) smokeMethod[0]).MungedName,
((SmokeMethod) smokeMethod[0]).ArgsSignature );
- ((SmokeMethod) smokeMethod[0]).methodId = methodId;
- }
- }
- IMethodReturnMessage returnMessage = (IMethodReturnMessage) message;
+ if (methodId == -1) {
+ Console.Error.WriteLine( "LEAVE Invoke() ** Missing method ** {0}.{1}",
+ _className,
+ ((MethodInfo) callMessage.MethodBase).Name );
+ return returnMessage;
+ }
- if (methodId == -1) {
- Console.Error.WriteLine( "LEAVE Invoke() ** Missing method ** {0}.{1}",
- _className,
- ((MethodInfo) callMessage.MethodBase).Name );
- return returnMessage;
+ // Don't cache calls to QObject.MetaObject() as it is the same method for all
+ // classes, and the wrong method is cached for classes which aren't QObject.
+ if (!callMessage.MethodName.EndsWith("MetaObject")) {
+ methodIdCache[(MethodInfo) callMessage.MethodBase] = methodId;
+ }
+ }
}
+ StackItem[] stack = new StackItem[callMessage.ArgCount+1];
+
if (callMessage.MethodSignature != null) {
Type[] types = (Type[]) callMessage.MethodSignature;
for (int i = 0; i < callMessage.ArgCount; i++) {
@@ -397,6 +403,10 @@
unsafe {
stack[i+1].s_class = (IntPtr) 0;
}
+ } else if (types[i] == typeof(int) || types[i].IsEnum) {
+ stack[i+1].s_int = (int) callMessage.Args[i];
+ } else if (!types[i].IsPrimitive) {
+ stack[i+1].s_class = (IntPtr) GCHandle.Alloc(callMessage.Args[i]);
} else if (types[i] == typeof(bool)) {
stack[i+1].s_bool = (bool) callMessage.Args[i];
} else if (types[i] == typeof(sbyte)) {
@@ -407,8 +417,6 @@
stack[i+1].s_short = (short) callMessage.Args[i];
} else if (types[i] == typeof(ushort)) {
stack[i+1].s_ushort = (ushort) callMessage.Args[i];
- } else if (types[i] == typeof(int) || types[i].IsEnum) {
- stack[i+1].s_int = (int) callMessage.Args[i];
} else if (types[i] == typeof(uint)) {
stack[i+1].s_uint = (uint) callMessage.Args[i];
} else if (types[i] == typeof(long)) {
@@ -419,10 +427,11 @@
stack[i+1].s_float = (float) callMessage.Args[i];
} else if (types[i] == typeof(double)) {
stack[i+1].s_double = (double) callMessage.Args[i];
- } else if (types[i] == typeof(string)) {
- stack[i+1].s_class = (IntPtr) GCHandle.Alloc(callMessage.Args[i]);
} else {
- stack[i+1].s_class = (IntPtr) GCHandle.Alloc(callMessage.Args[i]);
+ Console.Error.WriteLine( "MethodName: {0}.{1} Unknown type: {2}",
+ _className,
+ callMessage.MethodName,
+ types[i] );
}
}
}
More information about the Kde-bindings
mailing list