[Kde-bindings] Qyoto gets better...

Arno Rehn arno at arnorehn.de
Fri Dec 2 18:50:07 UTC 2005


Am Mittwoch, 30. November 2005 20:39 schrieb Richard Dale:
> On Wednesday 30 November 2005 18:40, Arno Rehn wrote:
> > Am Dienstag, 29. November 2005 12:33 schrieb Richard Dale:
> > > On Monday 28 November 2005 21:25, Arno Rehn wrote:
> > > > Am Montag, 28. November 2005 13:44 schrieb Arno Rehn:
> > > > > Hi,
> > > > >
> > > > > Ok, with the last update there's some progress. Now I don't get
> > > > > some Index out of range error anymore, but it still doesn't work:
> > > > >
> > > > > Invoke() MethodName: NewQApplication Type: Qt.QApplication, hello,
> > > > > Version=0.0.0.0, Culture=neutral, PublicKeyToken=null ArgCount: 2
> > > > > FindMethod() className: QApplication MethodName: QApplication$?
> > > > >                 In FindMethodId QApplication::QApplication$? => 146
> > > > > FindMethod() MethodName: QApplication$? result: 154
> > > > >         ArgName: argc Arg: 0 Type: System.Int32		//hmm... Arg:0 I
> > > > > think, the path to the executable is already an argument ?!
> > > > >
> > > > >         ArgName: argv Arg: System.String[] Type: System.String[]
> > > > > In CallMethod methodId: 154 target: 0x00000003 items: 2
> > > > > In CallMethod 0		// seems not to be right
> > > > > In CallMethod classId: 123
> > > > > result 999		// was not correctly called
> > > > >
> > > > > Invoke() MethodName: NewQDialog Type: Qt.QDialog, hello,
> > > > > Version=0.0.0.0, Culture=neutral, PublicKeyToken=null ArgCount: 0
> > > > > FindMethod() className: QDialog MethodName: QDialog
> > > > >                 In FindMethodId QDialog::QDialog => 2022
> > > > > FindMethod() MethodName: QDialog result: 2144
> > > > > In CallMethod methodId: 2144 target: 0x00000003 items: 0
> > > > > In CallMethod 137193560
> > > > > In CallMethod classId: 123
> > > > > result 999
> > > > > // this is called properly, but with no proper initialization of a
> > > > > QApplication it doesn't run.
> > > > >
> > > > >
> > > > > I modified the QApplication-Constructor to pass the Proxy an argc
> > > > > with a "Length + 1". Then the output says "ArgName: argc Arg: 1
> > > > > Type: System.Int32" and "In CallMethod 1" instead of "In CallMethod
> > > > > 0". This seems to be better, but not good.
> > >
> > > Yes, I'm not sure if C# has the program name in argv[0] or not - so
> > > maybe that needs adding before calling the C++ method that is expecting
> > > it to be there.
> > >
> > > > I think I have to take a look in the source-code before I say
> > > > something here. The "result 999" has to do nothing with the execution
> > > > of a method, that is hardcoded into the libqyoto.so. But why is the
> > > > mehtod not successfully called when there's more than one argument?
> > > > I'll have a closer look at the Qt.cpp from qtruby. Maybe that helps a
> > > > bit.
> > >
> > > Yes, stuff like the hard coded result is there just to demonstrate that
> > > it's possible to return a result back to C#. I'll try and post an
> > > explanation of what it's all about, and what is missing when I've time
> > > - it is very similar to qtruby though, so it won't do any harm to look
> > > at that code.
> > >
> > > -- Richard
> >
> > Thistime I took a closer look at the source. I don't understand the
> > CallMethod() in qyoto.cpp / qt3qyoto.cpp. Everything goes right until one
> > of the called Methods from the helloworld-example have any arguments. The
> > arguments are correctly passed to CallMethod(), but nothing is done with
> > them. What is done with "Smoke::StackItem * sp" ? You just print some
> > values on the console, but nothing else is done. As this variable
> > contains the arguments I wonder how this works.
>
> The Smoke::StackItem is an item in the array of C++ args that is passed
> when you call a method in the Smoke library.
>
> This loop is moving things from the array passed to
> SmokeInvocation.Invoke():
>
> 				for (int i = 0; i < callMessage.ArgCount; i++) {
> 					if (types[i] == typeof(bool)) {
> 						stack[i+1].s_bool = (bool) callMessage.Args[i];
> 					} else if (types[i] == typeof(sbyte)) {
> 						stack[i+1].s_char = (sbyte) callMessage.Args[i];
> 					} else if (types[i] == typeof(byte)) {
> 						stack[i+1].s_uchar = (byte) callMessage.Args[i];
> 					} else if (types[i] == typeof(short)) {
> 						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)) {
> 						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)) {
> 						stack[i+1].s_long = (long) callMessage.Args[i];
> 					} else if (types[i] == typeof(ulong)) {
> 						stack[i+1].s_ulong = (ulong) callMessage.Args[i];
> 					} else if (types[i] == typeof(float)) {
> 						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[])) {
> 						unsafe {
> 							stack[i+1].s_voidp = (void *) StringArrayToCharStarStar((string[])
> callMessage.Args[i]);
> 						}
> 					}
>
> What's missing is the one to set up the s_class entry for something like a
> QWidget. It needs to be a GCHandle, and over on the C/C++ side the
> corresponding C++ instance needs to be looked up and marshalled to the
> s_class field in the SmokeStack as a 'void *'.
>
> Here is the QtRuby code to call a method (from the method_missing()
> function in Qt.cpp):
>
>     MethodCall c(qt_Smoke, _current_method, self, temp_stack+4, argc-1);
>     c.next();
>     VALUE result = *(c.var());
>
> There is a C++ class called 'MethodCall' in qt3qyoto.cpp too, and so that
> needs to be passed the SmokeStack, once it is correctly set up. We already
> have the correct method lookup in the Smoke library.
>
I have added these lines after the 'printf' in 'CallMethod' in qt3qyoto.cpp:
	MethodCall c(qt_Smoke, methodId, obj, sp, items);
	c.next();
I didn't expect it to work, and it didn't. It compiles without errors, but 
while executing I get a SIGSEV. Waiting for your explanations, if you have 
some time.

> I'll post some more explanation ASAP - I'm afraid the net has been down for
> the last couple of days after a storm here in the Canaries. I'm still
> catching up with everything.
>
> -- Richard
> _______________________________________________
> Kde-bindings mailing list
> Kde-bindings at kde.org
> https://mail.kde.org/mailman/listinfo/kde-bindings

-- 
MfG
Arno Rehn
arno at arnorehn.de



More information about the Kde-bindings mailing list