2006-07-27 Zoltan Varga <vargaz@gmail.com>
[mono-project.git] / mono / tests / libtest.c
blobf2ffc9a996eaeb0481c071c96b2a3fea39989429
1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <string.h>
4 #include <glib.h>
5 #include <errno.h>
6 #include <time.h>
8 #ifdef WIN32
9 #include <windows.h>
10 #endif
12 #ifdef WIN32
13 #define STDCALL __stdcall
14 #else
15 #define STDCALL
16 #endif
18 #ifdef WIN32
19 extern __declspec(dllimport) __stdcall void CoTaskMemFree(void *ptr);
20 #endif
22 typedef int (STDCALL *SimpleDelegate) (int a);
24 static void marshal_free (void *ptr)
26 #ifdef WIN32
27 CoTaskMemFree (ptr);
28 #else
29 g_free (ptr);
30 #endif
33 STDCALL unsigned short*
34 test_lpwstr_marshal (unsigned short* chars, long length)
36 int i = 0;
37 unsigned short *res;
39 res = malloc (2 * (length + 1));
41 // printf("test_lpwstr_marshal()\n");
43 while ( i < length ) {
44 // printf("X|%u|\n", chars[i]);
45 res [i] = chars[i];
46 i++;
49 res [i] = 0;
51 return res;
54 typedef struct {
55 int b;
56 int a;
57 int c;
58 } union_test_1_type;
60 STDCALL int
61 mono_union_test_1 (union_test_1_type u1) {
62 // printf ("Got values %d %d %d\n", u1.b, u1.a, u1.c);
63 return u1.a + u1.b + u1.c;
66 STDCALL int
67 mono_return_int (int a) {
68 // printf ("Got value %d\n", a);
69 return a;
72 struct ss
74 int i;
77 STDCALL int
78 mono_return_int_ss (struct ss a) {
79 // printf ("Got value %d\n", a.i);
80 return a.i;
83 STDCALL struct ss
84 mono_return_ss (struct ss a) {
85 // printf ("Got value %d\n", a.i);
86 a.i++;
87 return a;
90 struct sc1
92 char c[1];
95 STDCALL struct sc1
96 mono_return_sc1 (struct sc1 a) {
97 // printf ("Got value %d\n", a.c[0]);
98 a.c[0]++;
99 return a;
103 struct sc3
105 char c[3];
108 STDCALL struct sc3
109 mono_return_sc3 (struct sc3 a) {
110 // printf ("Got values %d %d %d\n", a.c[0], a.c[1], a.c[2]);
111 a.c[0]++;
112 a.c[1] += 2;
113 a.c[2] += 3;
114 return a;
117 struct sc5
119 char c[5];
122 STDCALL struct sc5
123 mono_return_sc5 (struct sc5 a) {
124 // printf ("Got values %d %d %d %d %d\n", a.c[0], a.c[1], a.c[2], a.c[3], a.c[4]);
125 a.c[0]++;
126 a.c[1] += 2;
127 a.c[2] += 3;
128 a.c[3] += 4;
129 a.c[4] += 5;
130 return a;
133 union su
135 int i1;
136 int i2;
139 STDCALL int
140 mono_return_int_su (union su a) {
141 // printf ("Got value %d\n", a.i1);
142 return a.i1;
145 STDCALL int
146 mono_test_many_int_arguments (int a, int b, int c, int d, int e,
147 int f, int g, int h, int i, int j);
148 STDCALL short
149 mono_test_many_short_arguments (short a, short b, short c, short d, short e,
150 short f, short g, short h, short i, short j);
151 STDCALL char
152 mono_test_many_char_arguments (char a, char b, char c, char d, char e,
153 char f, char g, char h, char i, char j);
155 STDCALL int
156 mono_test_many_int_arguments (int a, int b, int c, int d, int e, int f, int g, int h, int i, int j)
158 return a + b + c + d + e + f + g + h + i + j;
161 STDCALL short
162 mono_test_many_short_arguments (short a, short b, short c, short d, short e, short f, short g, short h, short i, short j)
164 return a + b + c + d + e + f + g + h + i + j;
167 STDCALL char
168 mono_test_many_byte_arguments (char a, char b, char c, char d, char e, char f, char g, char h, char i, char j)
170 return a + b + c + d + e + f + g + h + i + j;
173 STDCALL float
174 mono_test_many_float_arguments (float a, float b, float c, float d, float e, float f, float g, float h, float i, float j)
176 return a + b + c + d + e + f + g + h + i + j;
179 STDCALL double
180 mono_test_many_double_arguments (double a, double b, double c, double d, double e, double f, double g, double h, double i, double j)
182 return a + b + c + d + e + f + g + h + i + j;
185 STDCALL double
186 mono_test_split_double_arguments (double a, double b, float c, double d, double e)
188 return a + b + c + d + e;
191 STDCALL int
192 mono_test_puts_static (char *s)
194 // printf ("TEST %s\n", s);
195 return 1;
198 typedef int (STDCALL *SimpleDelegate3) (int a, int b);
200 STDCALL int
201 mono_invoke_delegate (SimpleDelegate3 delegate)
203 int res;
205 // printf ("start invoke %p\n", delegate);
207 res = delegate (2, 3);
209 // printf ("end invoke\n");
211 return res;
214 STDCALL int
215 mono_test_marshal_char (short a1)
217 if (a1 == 'a')
218 return 0;
220 return 1;
223 STDCALL void
224 mono_test_marshal_char_array (gunichar2 *s)
226 const char m[] = "abcdef";
227 gunichar2* s2;
228 glong len;
230 s2 = g_utf8_to_utf16 (m, -1, NULL, &len, NULL);
232 len = (len * 2) + 2;
233 memcpy (s, s2, len);
235 g_free (s2);
238 STDCALL int
239 mono_test_empty_pinvoke (int i)
241 return i;
244 STDCALL int
245 mono_test_marshal_bool_byref (int a, int *b, int c)
247 int res = *b;
249 *b = 1;
251 return res;
254 STDCALL int
255 mono_test_marshal_array (int *a1)
257 int i, sum = 0;
259 for (i = 0; i < 50; i++)
260 sum += a1 [i];
262 return sum;
265 STDCALL int
266 mono_test_marshal_inout_array (int *a1)
268 int i, sum = 0;
270 for (i = 0; i < 50; i++) {
271 sum += a1 [i];
272 a1 [i] = 50 - a1 [i];
275 return sum;
278 STDCALL int
279 mono_test_marshal_out_array (int *a1)
281 int i;
283 for (i = 0; i < 50; i++) {
284 a1 [i] = i;
287 return 0;
290 STDCALL int
291 mono_test_marshal_inout_nonblittable_array (gunichar2 *a1)
293 int i, sum = 0;
295 for (i = 0; i < 10; i++) {
296 a1 [i] = 'F';
299 return sum;
302 typedef struct {
303 int a;
304 int b;
305 int c;
306 const char *d;
307 gunichar2 *d2;
308 } simplestruct;
310 typedef struct {
311 double x;
312 double y;
313 } point;
315 STDCALL simplestruct
316 mono_test_return_vtype (int i)
318 simplestruct res;
319 static gunichar2 test2 [] = { 'T', 'E', 'S', 'T', '2', 0 };
321 res.a = 0;
322 res.b = 1;
323 res.c = 0;
324 res.d = "TEST";
325 res.d2 = test2;
327 return res;
330 STDCALL void
331 mono_test_delegate_struct (void)
333 // printf ("TEST\n");
336 typedef char* (STDCALL *ReturnStringDelegate) (const char *s);
338 STDCALL char *
339 mono_test_return_string (ReturnStringDelegate func)
341 char *res;
343 // printf ("mono_test_return_string\n");
345 res = func ("TEST");
346 marshal_free (res);
348 // printf ("got string: %s\n", res);
349 return g_strdup ("12345");
352 typedef int (STDCALL *RefVTypeDelegate) (int a, simplestruct *ss, int b);
354 STDCALL int
355 mono_test_ref_vtype (int a, simplestruct *ss, int b, RefVTypeDelegate func)
357 if (a == 1 && b == 2 && ss->a == 0 && ss->b == 1 && ss->c == 0 &&
358 !strcmp (ss->d, "TEST1")) {
359 ss->a = 1;
360 ss->b = 0;
361 ss->c = 1;
362 ss->d = "TEST2";
364 return func (a, ss, b);
367 return 1;
370 typedef int (STDCALL *OutVTypeDelegate) (int a, simplestruct *ss, int b);
372 STDCALL int
373 mono_test_marshal_out_struct (int a, simplestruct *ss, int b, OutVTypeDelegate func)
375 /* Check that the input pointer is ignored */
376 ss->d = (gpointer)0x12345678;
378 func (a, ss, b);
380 if (ss->a && ss->b && ss->c && !strcmp (ss->d, "TEST3"))
381 return 0;
382 else
383 return 1;
386 typedef struct {
387 int a;
388 SimpleDelegate func, func2;
389 } DelegateStruct;
391 STDCALL DelegateStruct
392 mono_test_marshal_delegate_struct (DelegateStruct ds)
394 DelegateStruct res;
396 res.a = ds.func (ds.a) + ds.func2 (ds.a);
397 res.func = ds.func;
398 res.func2 = ds.func2;
400 return res;
403 STDCALL int
404 mono_test_marshal_struct (simplestruct ss)
406 if (ss.a == 0 && ss.b == 1 && ss.c == 0 &&
407 !strcmp (ss.d, "TEST"))
408 return 0;
410 return 1;
413 STDCALL int
414 mono_test_marshal_byref_struct (simplestruct *ss, int a, int b, int c, char *d)
416 gboolean res = (ss->a == a && ss->b == b && ss->c == c && strcmp (ss->d, d) == 0);
418 ss->a = !ss->a;
419 ss->b = !ss->b;
420 ss->c = !ss->c;
421 ss->d = g_strdup ("DEF");
423 return res ? 0 : 1;
426 typedef struct {
427 int a;
428 int b;
429 int c;
430 char *d;
431 unsigned char e;
432 double f;
433 unsigned char g;
434 guint64 h;
435 } simplestruct2;
437 STDCALL int
438 mono_test_marshal_struct2 (simplestruct2 ss)
440 if (ss.a == 0 && ss.b == 1 && ss.c == 0 &&
441 !strcmp (ss.d, "TEST") &&
442 ss.e == 99 && ss.f == 1.5 && ss.g == 42 && ss.h == (guint64)123)
443 return 0;
445 return 1;
448 /* on HP some of the struct should be on the stack and not in registers */
449 STDCALL int
450 mono_test_marshal_struct2_2 (int i, int j, int k, simplestruct2 ss)
452 if (i != 10 || j != 11 || k != 12)
453 return 1;
454 if (ss.a == 0 && ss.b == 1 && ss.c == 0 &&
455 !strcmp (ss.d, "TEST") &&
456 ss.e == 99 && ss.f == 1.5 && ss.g == 42 && ss.h == (guint64)123)
457 return 0;
459 return 1;
462 STDCALL int
463 mono_test_marshal_lpstruct (simplestruct *ss)
465 if (ss->a == 0 && ss->b == 1 && ss->c == 0 &&
466 !strcmp (ss->d, "TEST"))
467 return 0;
469 return 1;
472 STDCALL int
473 mono_test_marshal_lpstruct_blittable (point *p)
475 if (p->x == 1.0 && p->y == 2.0)
476 return 0;
477 else
478 return 1;
481 STDCALL int
482 mono_test_marshal_struct_array (simplestruct2 *ss)
484 if (! (ss[0].a == 0 && ss[0].b == 1 && ss[0].c == 0 &&
485 !strcmp (ss[0].d, "TEST") &&
486 ss[0].e == 99 && ss[0].f == 1.5 && ss[0].g == 42 && ss[0].h == (guint64)123))
487 return 1;
489 if (! (ss[1].a == 0 && ss[1].b == 0 && ss[1].c == 0 &&
490 !strcmp (ss[1].d, "TEST2") &&
491 ss[1].e == 100 && ss[1].f == 2.5 && ss[1].g == 43 && ss[1].h == (guint64)124))
492 return 1;
494 return 0;
497 typedef struct long_align_struct {
498 gint32 a;
499 gint64 b;
500 gint64 c;
501 } long_align_struct;
503 STDCALL int
504 mono_test_marshal_long_align_struct_array (long_align_struct *ss)
506 return ss[0].a + ss[0].b + ss[0].c + ss[1].a + ss[1].b + ss[1].c;
509 STDCALL simplestruct2 *
510 mono_test_marshal_class (int i, int j, int k, simplestruct2 *ss, int l)
512 simplestruct2 *res;
514 if (!ss)
515 return NULL;
517 if (i != 10 || j != 11 || k != 12 || l != 14)
518 return NULL;
519 if (! (ss->a == 0 && ss->b == 1 && ss->c == 0 &&
520 !strcmp (ss->d, "TEST") &&
521 ss->e == 99 && ss->f == 1.5 && ss->g == 42 && ss->h == (guint64)123))
522 return NULL;
524 res = g_new0 (simplestruct2, 1);
525 memcpy (res, ss, sizeof (simplestruct2));
526 res->d = g_strdup ("TEST");
527 return res;
530 STDCALL int
531 mono_test_marshal_byref_class (simplestruct2 **ssp)
533 simplestruct2 *ss = *ssp;
534 simplestruct2 *res;
536 if (! (ss->a == 0 && ss->b == 1 && ss->c == 0 &&
537 !strcmp (ss->d, "TEST") &&
538 ss->e == 99 && ss->f == 1.5 && ss->g == 42 && ss->h == (guint64)123))
539 return 1;
541 res = g_new0 (simplestruct2, 1);
542 memcpy (res, ss, sizeof (simplestruct2));
543 res->d = g_strdup ("TEST-RES");
545 *ssp = res;
546 return 0;
549 static void *
550 get_sp (void)
552 int i;
553 void *p;
555 /* Yes, this is correct, we are only trying to determine the value of the stack here */
556 p = &i;
557 return p;
560 STDCALL int
561 reliable_delegate (int a)
563 return a;
567 * Checks whether get_sp() works as expected. It doesn't work with gcc-2.95.3 on linux.
569 static gboolean
570 is_get_sp_reliable (void)
572 void *sp1, *sp2;
574 reliable_delegate(1);
575 sp1 = get_sp();
576 reliable_delegate(1);
577 sp2 = get_sp();
578 return sp1 == sp2;
581 STDCALL int
582 mono_test_marshal_delegate (SimpleDelegate delegate)
584 void *sp1, *sp2;
586 /* Check that the delegate wrapper is stdcall */
587 delegate (2);
588 sp1 = get_sp ();
589 delegate (2);
590 sp2 = get_sp ();
591 if (is_get_sp_reliable())
592 g_assert (sp1 == sp2);
594 return delegate (2);
597 STDCALL SimpleDelegate
598 mono_test_marshal_return_delegate (SimpleDelegate delegate)
600 return delegate;
603 static STDCALL int
604 return_plus_one (int i)
606 return i + 1;
609 STDCALL SimpleDelegate
610 mono_test_marshal_return_delegate_2 ()
612 return return_plus_one;
615 typedef simplestruct (STDCALL *SimpleDelegate2) (simplestruct ss);
617 static gboolean
618 is_utf16_equals (gunichar2 *s1, const char *s2)
620 char *s;
621 int res;
623 s = g_utf16_to_utf8 (s1, -1, NULL, NULL, NULL);
624 res = strcmp (s, s2);
625 g_free (s);
627 return res == 0;
630 STDCALL int
631 mono_test_marshal_delegate2 (SimpleDelegate2 delegate)
633 simplestruct ss, res;
635 ss.a = 0;
636 ss.b = 1;
637 ss.c = 0;
638 ss.d = "TEST";
639 ss.d2 = g_utf8_to_utf16 ("TEST2", -1, NULL, NULL, NULL);
641 res = delegate (ss);
642 if (! (res.a && !res.b && res.c && !strcmp (res.d, "TEST-RES") && is_utf16_equals (res.d2, "TEST2-RES")))
643 return 1;
645 return 0;
648 typedef simplestruct* (STDCALL *SimpleDelegate4) (simplestruct *ss);
650 STDCALL int
651 mono_test_marshal_delegate4 (SimpleDelegate4 delegate)
653 simplestruct ss;
654 simplestruct *res;
656 ss.a = 0;
657 ss.b = 1;
658 ss.c = 0;
659 ss.d = "TEST";
661 /* Check argument */
662 res = delegate (&ss);
663 if (!res)
664 return 1;
666 /* Check return value */
667 if (! (!res->a && res->b && !res->c && !strcmp (res->d, "TEST")))
668 return 2;
670 /* Check NULL argument and NULL result */
671 res = delegate (NULL);
672 if (res)
673 return 3;
675 return 0;
678 typedef int (STDCALL *SimpleDelegate5) (simplestruct **ss);
680 STDCALL int
681 mono_test_marshal_delegate5 (SimpleDelegate5 delegate)
683 simplestruct ss;
684 int res;
685 simplestruct *ptr;
687 ss.a = 0;
688 ss.b = 1;
689 ss.c = 0;
690 ss.d = "TEST";
692 ptr = &ss;
694 res = delegate (&ptr);
695 if (res != 0)
696 return 1;
698 if (!(ptr->a && !ptr->b && ptr->c && !strcmp (ptr->d, "RES")))
699 return 2;
701 return 0;
704 STDCALL int
705 mono_test_marshal_delegate6 (SimpleDelegate5 delegate)
707 int res;
709 res = delegate (NULL);
711 return 0;
714 typedef int (STDCALL *SimpleDelegate7) (simplestruct **ss);
716 STDCALL int
717 mono_test_marshal_delegate7 (SimpleDelegate7 delegate)
719 int res;
720 simplestruct *ptr;
722 /* Check that the input pointer is ignored */
723 ptr = (gpointer)0x12345678;
725 res = delegate (&ptr);
726 if (res != 0)
727 return 1;
729 if (!(ptr->a && !ptr->b && ptr->c && !strcmp (ptr->d, "RES")))
730 return 2;
732 return 0;
735 typedef int (STDCALL *SimpleDelegate8) (gunichar2 *s);
737 STDCALL int
738 mono_test_marshal_delegate8 (SimpleDelegate8 delegate, gunichar2 *s)
740 return delegate (s);
743 typedef int (STDCALL *return_int_fnt) (int i);
744 typedef int (STDCALL *SimpleDelegate9) (return_int_fnt d);
746 STDCALL int
747 mono_test_marshal_delegate9 (SimpleDelegate9 delegate, gpointer ftn)
749 return delegate (ftn);
752 STDCALL static int
753 return_self (int i)
755 return i;
758 STDCALL int
759 mono_test_marshal_delegate10 (SimpleDelegate9 delegate)
761 return delegate (return_self);
764 typedef int (STDCALL *PrimitiveByrefDelegate) (int *i);
766 STDCALL int
767 mono_test_marshal_primitive_byref_delegate (PrimitiveByrefDelegate delegate)
769 int i = 1;
771 int res = delegate (&i);
772 if (res != 0)
773 return res;
775 if (i != 2)
776 return 2;
778 return 0;
781 typedef int (STDCALL *return_int_delegate) (int i);
783 typedef return_int_delegate (STDCALL *ReturnDelegateDelegate) (void);
785 STDCALL int
786 mono_test_marshal_return_delegate_delegate (ReturnDelegateDelegate d)
788 return (d ()) (55);
791 STDCALL int
792 mono_test_marshal_stringbuilder (char *s, int n)
794 const char m[] = "This is my message. Isn't it nice?";
796 if (strcmp (s, "ABCD") != 0)
797 return 1;
798 strncpy(s, m, n);
799 return 0;
802 STDCALL int
803 mono_test_marshal_stringbuilder_unicode (gunichar2 *s, int n)
805 const char m[] = "This is my message. Isn't it nice?";
806 gunichar2* s2;
807 glong len;
809 s2 = g_utf8_to_utf16 (m, -1, NULL, &len, NULL);
811 len = (len * 2) + 2;
812 if (len > n)
813 len = n;
814 memcpy (s, s2, len);
816 g_free (s2);
818 return 0;
821 typedef struct {
822 #ifndef __GNUC__
823 char a;
824 #endif
825 } EmptyStruct;
827 STDCALL int
828 mono_test_marshal_empty_string_array (char **array)
830 return (array == NULL) ? 0 : 1;
833 STDCALL int
834 mono_test_marshal_string_array (char **array)
836 if (strcmp (array [0], "ABC"))
837 return 1;
838 if (strcmp (array [1], "DEF"))
839 return 2;
841 if (array [2] != NULL)
842 return 3;
844 return 0;
847 STDCALL int
848 mono_test_marshal_byref_string_array (char ***array)
850 if (*array == NULL)
851 return 0;
853 if (strcmp ((*array) [0], "Alpha"))
854 return 2;
855 if (strcmp ((*array) [1], "Beta"))
856 return 2;
857 if (strcmp ((*array) [2], "Gamma"))
858 return 2;
860 return 1;
863 STDCALL int
864 mono_test_marshal_stringbuilder_array (char **array)
866 if (strcmp (array [0], "ABC"))
867 return 1;
868 if (strcmp (array [1], "DEF"))
869 return 2;
871 strcpy (array [0], "DEF");
872 strcpy (array [1], "ABC");
874 return 0;
877 STDCALL int
878 mono_test_marshal_unicode_string_array (gunichar2 **array, char **array2)
880 GError *error = NULL;
881 char *s;
883 s = g_utf16_to_utf8 (array [0], -1, NULL, NULL, &error);
884 if (strcmp (s, "ABC")) {
885 g_free (s);
886 return 1;
888 else
889 g_free (s);
891 s = g_utf16_to_utf8 (array [1], -1, NULL, NULL, &error);
892 if (strcmp (s, "DEF")) {
893 g_free (s);
894 return 2;
896 else
897 g_free (s);
899 if (strcmp (array2 [0], "ABC"))
900 return 3;
902 if (strcmp (array2 [1], "DEF"))
903 return 4;
905 return 0;
908 /* this does not work on Redhat gcc 2.96 */
909 STDCALL int
910 mono_test_empty_struct (int a, EmptyStruct es, int b)
912 // printf ("mono_test_empty_struct %d %d\n", a, b);
914 // Intel icc on ia64 passes 'es' in 2 registers
915 #if defined(__ia64) && defined(__INTEL_COMPILER)
916 return 0;
917 #else
918 if (a == 1 && b == 2)
919 return 0;
920 return 1;
921 #endif
924 typedef struct {
925 char a[100];
926 } ByValStrStruct;
928 STDCALL ByValStrStruct *
929 mono_test_byvalstr_gen (void)
931 ByValStrStruct *ret;
933 ret = malloc(sizeof(ByValStrStruct));
934 memset(ret, 'a', sizeof(ByValStrStruct)-1);
935 ret->a[sizeof(ByValStrStruct)-1] = 0;
937 return ret;
940 STDCALL int
941 mono_test_byvalstr_check (ByValStrStruct* data, char* correctString)
943 int ret;
945 ret = strcmp(data->a, correctString);
946 // printf ("T1: %s\n", data->a);
947 // printf ("T2: %s\n", correctString);
949 marshal_free (data);
950 return (ret != 0);
953 STDCALL int
954 NameManglingAnsi (char *data)
956 return data [0] + data [1] + data [2];
959 STDCALL int
960 NameManglingAnsiA (char *data)
962 g_assert_not_reached ();
965 STDCALL int
966 NameManglingAnsiW (char *data)
968 g_assert_not_reached ();
971 STDCALL int
972 NameManglingAnsi2A (char *data)
974 return data [0] + data [1] + data [2];
977 STDCALL int
978 NameManglingAnsi2W (char *data)
980 g_assert_not_reached ();
983 STDCALL int
984 NameManglingUnicode (char *data)
986 g_assert_not_reached ();
989 STDCALL int
990 NameManglingUnicodeW (gunichar2 *data)
992 return data [0] + data [1] + data [2];
995 STDCALL int
996 NameManglingUnicode2 (gunichar2 *data)
998 return data [0] + data [1] + data [2];
1001 STDCALL int
1002 NameManglingAutoW (char *data)
1004 #ifdef WIN32
1005 return (data [0] + data [1] + data [2]) == 131 ? 0 : 1;
1006 #else
1007 g_assert_not_reached ();
1008 #endif
1011 STDCALL int
1012 NameManglingAuto (char *data)
1014 #ifndef WIN32
1015 return (data [0] + data [1] + data [2]) == 198 ? 0 : 1;
1016 #else
1017 g_assert_not_reached ();
1018 #endif
1021 typedef int (STDCALL *intcharFunc)(const char*);
1023 STDCALL void
1024 callFunction (intcharFunc f)
1026 f ("ABC");
1029 typedef struct {
1030 const char* str;
1031 int i;
1032 } SimpleObj;
1034 STDCALL int
1035 class_marshal_test0 (SimpleObj *obj1)
1037 // printf ("class_marshal_test0 %s %d\n", obj1->str, obj1->i);
1039 if (strcmp(obj1->str, "T1"))
1040 return -1;
1041 if (obj1->i != 4)
1042 return -2;
1044 return 0;
1047 STDCALL int
1048 class_marshal_test4 (SimpleObj *obj1)
1050 if (obj1)
1051 return -1;
1053 return 0;
1056 STDCALL void
1057 class_marshal_test1 (SimpleObj **obj1)
1059 SimpleObj *res = malloc (sizeof (SimpleObj));
1061 res->str = g_strdup ("ABC");
1062 res->i = 5;
1064 *obj1 = res;
1067 STDCALL int
1068 class_marshal_test2 (SimpleObj **obj1)
1070 // printf ("class_marshal_test2 %s %d\n", (*obj1)->str, (*obj1)->i);
1072 if (strcmp((*obj1)->str, "ABC"))
1073 return -1;
1074 if ((*obj1)->i != 5)
1075 return -2;
1077 return 0;
1080 STDCALL int
1081 string_marshal_test0 (char *str)
1083 if (strcmp (str, "TEST0"))
1084 return -1;
1086 return 0;
1089 STDCALL void
1090 string_marshal_test1 (const char **str)
1092 *str = "TEST1";
1095 STDCALL int
1096 string_marshal_test2 (char **str)
1098 // printf ("string_marshal_test2 %s\n", *str);
1100 if (strcmp (*str, "TEST1"))
1101 return -1;
1103 return 0;
1106 STDCALL int
1107 string_marshal_test3 (char *str)
1109 if (str)
1110 return -1;
1112 return 0;
1115 typedef struct {
1116 int a;
1117 int b;
1118 } VectorList;
1120 STDCALL VectorList*
1121 TestVectorList (VectorList *vl)
1123 VectorList *res;
1125 // printf ("TestVectorList %d %d\n", vl->a, vl->b);
1127 vl->a++;
1128 vl->b++;
1130 res = g_new0 (VectorList, 1);
1131 memcpy (res, vl, sizeof (VectorList));
1133 return res;
1136 typedef struct OSVERSIONINFO_STRUCT
1138 int a;
1139 int b;
1140 } OSVERSIONINFO_STRUCT;
1142 STDCALL int
1143 MyGetVersionEx (OSVERSIONINFO_STRUCT *osvi)
1146 // printf ("GOT %d %d\n", osvi->a, osvi->b);
1148 osvi->a += 1;
1149 osvi->b += 1;
1151 return osvi->a + osvi->b;
1154 STDCALL int
1155 BugGetVersionEx (int a, int b, int c, int d, int e, int f, int g, int h, OSVERSIONINFO_STRUCT *osvi)
1158 // printf ("GOT %d %d\n", osvi->a, osvi->b);
1160 osvi->a += 1;
1161 osvi->b += 1;
1163 return osvi->a + osvi->b;
1166 STDCALL int
1167 mono_test_marshal_point (point pt)
1169 // printf("point %g %g\n", pt.x, pt.y);
1170 if (pt.x == 1.25 && pt.y == 3.5)
1171 return 0;
1173 return 1;
1176 typedef struct {
1177 int x;
1178 double y;
1179 } mixed_point;
1181 STDCALL int
1182 mono_test_marshal_mixed_point (mixed_point pt)
1184 // printf("mixed point %d %g\n", pt.x, pt.y);
1185 if (pt.x == 5 && pt.y == 6.75)
1186 return 0;
1188 return 1;
1191 STDCALL int
1192 mono_test_marshal_mixed_point_2 (mixed_point *pt)
1194 if (pt->x != 5 || pt->y != 6.75)
1195 return 1;
1197 pt->x = 10;
1198 pt->y = 12.35;
1200 return 0;
1203 STDCALL int
1204 marshal_test_ref_bool(int i, char *b1, short *b2, int *b3)
1206 int res = 1;
1207 if (*b1 != 0 && *b1 != 1)
1208 return 1;
1209 if (*b2 != 0 && *b2 != -1) /* variant_bool */
1210 return 1;
1211 if (*b3 != 0 && *b3 != 1)
1212 return 1;
1213 if (i == ((*b1 << 2) | (-*b2 << 1) | *b3))
1214 res = 0;
1215 *b1 = !*b1;
1216 *b2 = ~*b2;
1217 *b3 = !*b3;
1218 return res;
1221 struct BoolStruct
1223 int i;
1224 char b1;
1225 short b2; /* variant_bool */
1226 int b3;
1229 STDCALL int
1230 marshal_test_bool_struct(struct BoolStruct *s)
1232 int res = 1;
1233 if (s->b1 != 0 && s->b1 != 1)
1234 return 1;
1235 if (s->b2 != 0 && s->b2 != -1)
1236 return 1;
1237 if (s->b3 != 0 && s->b3 != 1)
1238 return 1;
1239 if (s->i == ((s->b1 << 2) | (-s->b2 << 1) | s->b3))
1240 res = 0;
1241 s->b1 = !s->b1;
1242 s->b2 = ~s->b2;
1243 s->b3 = !s->b3;
1244 return res;
1247 STDCALL void
1248 mono_test_last_error (int err)
1250 #ifdef WIN32
1251 SetLastError (err);
1252 #else
1253 errno = err;
1254 #endif
1257 STDCALL int
1258 mono_test_asany (void *ptr, int what)
1260 switch (what) {
1261 case 1:
1262 return (*(int*)ptr == 5) ? 0 : 1;
1263 case 2:
1264 return strcmp (ptr, "ABC") == 0 ? 0 : 1;
1265 case 3: {
1266 simplestruct2 ss = *(simplestruct2*)ptr;
1268 if (ss.a == 0 && ss.b == 1 && ss.c == 0 &&
1269 !strcmp (ss.d, "TEST") &&
1270 ss.e == 99 && ss.f == 1.5 && ss.g == 42 && ss.h == (guint64)123)
1271 return 0;
1272 else
1273 return 1;
1275 case 4: {
1276 GError *error = NULL;
1277 char *s;
1279 s = g_utf16_to_utf8 (ptr, -1, NULL, NULL, &error);
1280 if (!strcmp (s, "ABC")) {
1281 g_free (s);
1282 return 0;
1284 else {
1285 g_free (s);
1286 return 1;
1289 default:
1290 g_assert_not_reached ();
1293 return 1;
1296 typedef struct
1298 int i;
1299 int j;
1300 int k;
1301 char *s;
1302 } AsAnyStruct;
1304 STDCALL int
1305 mono_test_marshal_asany_inout (void* ptr)
1307 AsAnyStruct* asAny = ptr;
1308 int res = asAny->i + asAny->j + asAny->k;
1310 asAny->i = 10;
1311 asAny->j = 20;
1312 asAny->k = 30;
1313 asAny->s = 0;
1315 return res;
1319 * AMD64 marshalling tests.
1322 typedef struct amd64_struct1 {
1323 int i;
1324 int j;
1325 int k;
1326 int l;
1327 } amd64_struct1;
1329 STDCALL amd64_struct1
1330 mono_test_marshal_amd64_pass_return_struct1 (amd64_struct1 s)
1332 s.i ++;
1333 s.j ++;
1334 s.k ++;
1335 s.l ++;
1337 return s;
1340 typedef struct amd64_struct2 {
1341 int i;
1342 int j;
1343 } amd64_struct2;
1345 STDCALL amd64_struct2
1346 mono_test_marshal_amd64_pass_return_struct2 (amd64_struct2 s)
1348 s.i ++;
1349 s.j ++;
1351 return s;
1354 typedef struct amd64_struct3 {
1355 int i;
1356 } amd64_struct3;
1358 STDCALL amd64_struct3
1359 mono_test_marshal_amd64_pass_return_struct3 (amd64_struct3 s)
1361 s.i ++;
1363 return s;
1366 typedef struct amd64_struct4 {
1367 double d1, d2;
1368 } amd64_struct4;
1370 STDCALL amd64_struct4
1371 mono_test_marshal_amd64_pass_return_struct4 (amd64_struct4 s)
1373 s.d1 ++;
1374 s.d2 ++;
1376 return s;
1380 * IA64 marshalling tests.
1382 typedef struct test_struct5 {
1383 float d1, d2;
1384 } test_struct5;
1386 STDCALL test_struct5
1387 mono_test_marshal_ia64_pass_return_struct5 (double d1, double d2, test_struct5 s, double d3, double d4)
1389 s.d1 += d1 + d2;
1390 s.d2 += d3 + d4;
1392 return s;
1395 typedef struct test_struct6 {
1396 double d1, d2;
1397 } test_struct6;
1399 STDCALL test_struct6
1400 mono_test_marshal_ia64_pass_return_struct6 (double d1, double d2, test_struct6 s, double d3, double d4)
1402 s.d1 += d1 + d2;
1403 s.d2 += d3 + d4;
1405 return s;
1408 static guint32 custom_res [2];
1410 STDCALL void*
1411 mono_test_marshal_pass_return_custom (int i, guint32 *ptr, int j)
1413 /* ptr will be freed by CleanupNative, so make a copy */
1414 custom_res [0] = 0; /* not allocated by AllocHGlobal */
1415 custom_res [1] = ptr [1];
1417 return &custom_res;
1420 STDCALL int
1421 mono_test_marshal_pass_out_custom (int i, guint32 **ptr, int j)
1423 custom_res [0] = 0;
1424 custom_res [1] = i + j + 10;
1426 *ptr = custom_res;
1428 return 0;
1431 STDCALL int
1432 mono_test_marshal_pass_byref_custom (int i, guint32 **ptr, int j)
1434 (*ptr)[1] += i + j;
1436 return 0;
1439 STDCALL void*
1440 mono_test_marshal_pass_return_custom2 (int i, guint32 *ptr, int j)
1442 g_assert_not_reached ();
1444 return NULL;
1447 STDCALL void*
1448 mono_test_marshal_pass_return_custom_null (int i, guint32 *ptr, int j)
1450 g_assert (ptr == NULL);
1452 return NULL;
1455 typedef void *(STDCALL *PassReturnPtrDelegate) (void *ptr);
1457 STDCALL int
1458 mono_test_marshal_pass_return_custom_in_delegate (PassReturnPtrDelegate del)
1460 guint32 buf [2];
1461 guint32 res;
1462 guint32 *ptr;
1464 buf [0] = 0;
1465 buf [1] = 10;
1467 ptr = del (&buf);
1469 res = ptr [1];
1471 #ifdef WIN32
1472 /* FIXME: Freed with FreeHGlobal */
1473 #else
1474 g_free (ptr);
1475 #endif
1477 return res;
1480 STDCALL int
1481 mono_test_marshal_pass_return_custom_null_in_delegate (PassReturnPtrDelegate del)
1483 void *ptr = del (NULL);
1485 return (ptr == NULL) ? 15 : 0;
1488 typedef int (STDCALL *ReturnEnumDelegate) (int e);
1490 STDCALL int
1491 mono_test_marshal_return_enum_delegate (ReturnEnumDelegate func)
1493 return func (1);
1496 typedef struct {
1497 int a, b, c;
1498 gint64 d;
1499 } BlittableStruct;
1501 typedef BlittableStruct (STDCALL *SimpleDelegate10) (BlittableStruct ss);
1503 STDCALL int
1504 mono_test_marshal_blittable_struct_delegate (SimpleDelegate10 delegate)
1506 BlittableStruct ss, res;
1508 ss.a = 1;
1509 ss.b = 2;
1510 ss.c = 3;
1511 ss.d = 55;
1513 res = delegate (ss);
1514 if (! ((res.a == -1) && (res.b == -2) && (res.c == -3) && (res.d == -55)))
1515 return 1;
1517 return 0;
1520 STDCALL int
1521 mono_test_stdcall_name_mangling (int a, int b, int c)
1523 return a + b + c;
1527 * PASSING AND RETURNING SMALL STRUCTURES FROM DELEGATES TESTS
1530 typedef struct {
1531 int i;
1532 } SmallStruct1;
1534 typedef SmallStruct1 (STDCALL *SmallStructDelegate1) (SmallStruct1 ss);
1536 STDCALL int
1537 mono_test_marshal_small_struct_delegate1 (SmallStructDelegate1 delegate)
1539 SmallStruct1 ss, res;
1541 ss.i = 1;
1543 res = delegate (ss);
1544 if (! (res.i == -1))
1545 return 1;
1547 return 0;
1550 typedef struct {
1551 gint16 i, j;
1552 } SmallStruct2;
1554 typedef SmallStruct2 (STDCALL *SmallStructDelegate2) (SmallStruct2 ss);
1556 STDCALL int
1557 mono_test_marshal_small_struct_delegate2 (SmallStructDelegate2 delegate)
1559 SmallStruct2 ss, res;
1561 ss.i = 2;
1562 ss.j = 3;
1564 res = delegate (ss);
1565 if (! ((res.i == -2) && (res.j == -3)))
1566 return 1;
1568 return 0;
1571 typedef struct {
1572 gint16 i;
1573 gint8 j;
1574 } SmallStruct3;
1576 typedef SmallStruct3 (STDCALL *SmallStructDelegate3) (SmallStruct3 ss);
1578 STDCALL int
1579 mono_test_marshal_small_struct_delegate3 (SmallStructDelegate3 delegate)
1581 SmallStruct3 ss, res;
1583 ss.i = 1;
1584 ss.j = 2;
1586 res = delegate (ss);
1587 if (! ((res.i == -1) && (res.j == -2)))
1588 return 1;
1590 return 0;
1593 typedef struct {
1594 gint16 i;
1595 } SmallStruct4;
1597 typedef SmallStruct4 (STDCALL *SmallStructDelegate4) (SmallStruct4 ss);
1599 STDCALL int
1600 mono_test_marshal_small_struct_delegate4 (SmallStructDelegate4 delegate)
1602 SmallStruct4 ss, res;
1604 ss.i = 1;
1606 res = delegate (ss);
1607 if (! (res.i == -1))
1608 return 1;
1610 return 0;
1613 typedef struct {
1614 gint64 i;
1615 } SmallStruct5;
1617 typedef SmallStruct5 (STDCALL *SmallStructDelegate5) (SmallStruct5 ss);
1619 STDCALL int
1620 mono_test_marshal_small_struct_delegate5 (SmallStructDelegate5 delegate)
1622 SmallStruct5 ss, res;
1624 ss.i = 5;
1626 res = delegate (ss);
1627 if (! (res.i == -5))
1628 return 1;
1630 return 0;
1633 typedef struct {
1634 int i, j;
1635 } SmallStruct6;
1637 typedef SmallStruct6 (STDCALL *SmallStructDelegate6) (SmallStruct6 ss);
1639 STDCALL int
1640 mono_test_marshal_small_struct_delegate6 (SmallStructDelegate6 delegate)
1642 SmallStruct6 ss, res;
1644 ss.i = 1;
1645 ss.j = 2;
1647 res = delegate (ss);
1648 if (! ((res.i == -1) && (res.j == -2)))
1649 return 1;
1651 return 0;
1654 typedef struct {
1655 int i;
1656 gint16 j;
1657 } SmallStruct7;
1659 typedef SmallStruct7 (STDCALL *SmallStructDelegate7) (SmallStruct7 ss);
1661 STDCALL int
1662 mono_test_marshal_small_struct_delegate7 (SmallStructDelegate7 delegate)
1664 SmallStruct7 ss, res;
1666 ss.i = 1;
1667 ss.j = 2;
1669 res = delegate (ss);
1670 if (! ((res.i == -1) && (res.j == -2)))
1671 return 1;
1673 return 0;
1676 typedef struct {
1677 float i;
1678 } SmallStruct8;
1680 typedef SmallStruct8 (STDCALL *SmallStructDelegate8) (SmallStruct8 ss);
1682 STDCALL int
1683 mono_test_marshal_small_struct_delegate8 (SmallStructDelegate8 delegate)
1685 SmallStruct8 ss, res;
1687 ss.i = 1.0;
1689 res = delegate (ss);
1690 if (! ((res.i == -1.0)))
1691 return 1;
1693 return 0;
1696 typedef struct {
1697 double i;
1698 } SmallStruct9;
1700 typedef SmallStruct9 (STDCALL *SmallStructDelegate9) (SmallStruct9 ss);
1702 STDCALL int
1703 mono_test_marshal_small_struct_delegate9 (SmallStructDelegate9 delegate)
1705 SmallStruct9 ss, res;
1707 ss.i = 1.0;
1709 res = delegate (ss);
1710 if (! ((res.i == -1.0)))
1711 return 1;
1713 return 0;
1716 typedef struct {
1717 float i, j;
1718 } SmallStruct10;
1720 typedef SmallStruct10 (STDCALL *SmallStructDelegate10) (SmallStruct10 ss);
1722 STDCALL int
1723 mono_test_marshal_small_struct_delegate10 (SmallStructDelegate10 delegate)
1725 SmallStruct10 ss, res;
1727 ss.i = 1.0;
1728 ss.j = 2.0;
1730 res = delegate (ss);
1731 if (! ((res.i == -1.0) && (res.j == -2.0)))
1732 return 1;
1734 return 0;
1737 typedef struct {
1738 float i;
1739 int j;
1740 } SmallStruct11;
1742 typedef SmallStruct11 (STDCALL *SmallStructDelegate11) (SmallStruct11 ss);
1744 STDCALL int
1745 mono_test_marshal_small_struct_delegate11 (SmallStructDelegate11 delegate)
1747 SmallStruct11 ss, res;
1749 ss.i = 1.0;
1750 ss.j = 2;
1752 res = delegate (ss);
1753 if (! ((res.i == -1.0) && (res.j == -2)))
1754 return 1;
1756 return 0;
1759 typedef int (STDCALL *ArrayDelegate) (int i, char *j, void *arr);
1761 STDCALL int
1762 mono_test_marshal_array_delegate (void *arr, int len, ArrayDelegate del)
1764 return del (len, NULL, arr);
1767 STDCALL int
1768 mono_test_marshal_out_array_delegate (int *arr, int len, ArrayDelegate del)
1770 del (len, NULL, arr);
1772 if ((arr [0] != 1) || (arr [1] != 2))
1773 return 1;
1774 else
1775 return 0;
1778 STDCALL int
1779 mono_test_marshal_out_string_array_delegate (char **arr, int len, ArrayDelegate del)
1781 del (len, NULL, arr);
1783 if (!strcmp (arr [0], "ABC") && !strcmp (arr [1], "DEF"))
1784 return 0;
1785 else
1786 return 1;
1789 typedef int (*CdeclDelegate) (int i, int j);
1791 STDCALL int
1792 mono_test_marshal_cdecl_delegate (CdeclDelegate del)
1794 int i;
1796 for (i = 0; i < 1000; ++i)
1797 del (1, 2);
1799 return 0;
1802 typedef char** (*ReturnStringArrayDelegate) (int i);
1804 STDCALL int
1805 mono_test_marshal_return_string_array_delegate (ReturnStringArrayDelegate d)
1807 char **arr = d (2);
1808 int res;
1810 if (arr == NULL)
1811 return 3;
1813 if (strcmp (arr [0], "ABC") || strcmp (arr [1], "DEF"))
1814 res = 1;
1815 else
1816 res = 0;
1818 marshal_free (arr);
1820 return res;
1823 STDCALL int
1824 add_delegate (int i, int j)
1826 return i + j;
1829 STDCALL gpointer
1830 mono_test_marshal_return_fnptr (void)
1832 return &add_delegate;
1836 * COM INTEROP TESTS
1839 #ifdef WIN32
1841 STDCALL int
1842 mono_test_marshal_bstr_in(BSTR bstr)
1844 if (!wcscmp(bstr, L"mono_test_marshal_bstr_in"))
1845 return 0;
1846 return 1;
1849 STDCALL int
1850 mono_test_marshal_bstr_out(BSTR* bstr)
1852 *bstr = SysAllocString(L"mono_test_marshal_bstr_out");
1853 return 0;
1856 STDCALL int
1857 mono_test_marshal_variant_in_sbyte(VARIANT variant)
1859 if (variant.vt == VT_I1 && variant.cVal == 100)
1860 return 0;
1861 return 1;
1864 STDCALL int
1865 mono_test_marshal_variant_in_byte(VARIANT variant)
1867 if (variant.vt == VT_UI1 && variant.bVal == 100)
1868 return 0;
1869 return 1;
1872 STDCALL int
1873 mono_test_marshal_variant_in_short(VARIANT variant)
1875 if (variant.vt == VT_I2 && variant.iVal == 314)
1876 return 0;
1877 return 1;
1880 STDCALL int
1881 mono_test_marshal_variant_in_ushort(VARIANT variant)
1883 if (variant.vt == VT_UI2 && variant.uiVal == 314)
1884 return 0;
1885 return 1;
1888 STDCALL int
1889 mono_test_marshal_variant_in_int(VARIANT variant)
1891 if (variant.vt == VT_I4 && variant.lVal == 314)
1892 return 0;
1893 return 1;
1896 STDCALL int
1897 mono_test_marshal_variant_in_uint(VARIANT variant)
1899 if (variant.vt == VT_UI4 && variant.ulVal == 314)
1900 return 0;
1901 return 1;
1904 STDCALL int
1905 mono_test_marshal_variant_in_long(VARIANT variant)
1907 if (variant.vt == VT_I8 && variant.llVal == 314)
1908 return 0;
1909 return 1;
1912 STDCALL int
1913 mono_test_marshal_variant_in_ulong(VARIANT variant)
1915 if (variant.vt == VT_UI8 && variant.ullVal == 314)
1916 return 0;
1917 return 1;
1920 STDCALL int
1921 mono_test_marshal_variant_in_float(VARIANT variant)
1923 if (variant.vt == VT_R4 && (variant.fltVal - 3.14)/3.14 < .001)
1924 return 0;
1925 return 1;
1928 STDCALL int
1929 mono_test_marshal_variant_in_double(VARIANT variant)
1931 if (variant.vt == VT_R8 && (variant.dblVal - 3.14)/3.14 < .001)
1932 return 0;
1933 return 1;
1936 STDCALL int
1937 mono_test_marshal_variant_in_bstr(VARIANT variant)
1939 if (variant.vt == VT_BSTR && !wcscmp(variant.bstrVal, L"PI"))
1940 return 0;
1941 return 1;
1944 STDCALL int
1945 mono_test_marshal_variant_out_sbyte(VARIANT* variant)
1947 variant->vt = VT_I1;
1948 variant->cVal = 100;
1950 return 0;
1953 STDCALL int
1954 mono_test_marshal_variant_out_byte(VARIANT* variant)
1956 variant->vt = VT_UI1;
1957 variant->bVal = 100;
1959 return 0;
1962 STDCALL int
1963 mono_test_marshal_variant_out_short(VARIANT* variant)
1965 variant->vt = VT_I2;
1966 variant->iVal = 314;
1968 return 0;
1971 STDCALL int
1972 mono_test_marshal_variant_out_ushort(VARIANT* variant)
1974 variant->vt = VT_UI2;
1975 variant->uiVal = 314;
1977 return 0;
1980 STDCALL int
1981 mono_test_marshal_variant_out_int(VARIANT* variant)
1983 variant->vt = VT_I4;
1984 variant->lVal = 314;
1986 return 0;
1989 STDCALL int
1990 mono_test_marshal_variant_out_uint(VARIANT* variant)
1992 variant->vt = VT_UI4;
1993 variant->ulVal = 314;
1995 return 0;
1998 STDCALL int
1999 mono_test_marshal_variant_out_long(VARIANT* variant)
2001 variant->vt = VT_I8;
2002 variant->llVal = 314;
2004 return 0;
2007 STDCALL int
2008 mono_test_marshal_variant_out_ulong(VARIANT* variant)
2010 variant->vt = VT_UI8;
2011 variant->ullVal = 314;
2013 return 0;
2016 STDCALL int
2017 mono_test_marshal_variant_out_float(VARIANT* variant)
2019 variant->vt = VT_R4;
2020 variant->fltVal = 3.14;
2022 return 0;
2025 STDCALL int
2026 mono_test_marshal_variant_out_double(VARIANT* variant)
2028 variant->vt = VT_R8;
2029 variant->dblVal = 3.14;
2031 return 0;
2034 STDCALL int
2035 mono_test_marshal_variant_out_bstr(VARIANT* variant)
2037 variant->vt = VT_BSTR;
2038 variant->bstrVal = SysAllocString(L"PI");
2040 return 0;
2043 #endif
2045 #ifdef NOT_YET
2047 #ifdef _MSC_VER
2048 #define COM_STDCALL __stdcall
2049 #else
2050 #define COM_STDCALL __attribute__((stdcall))
2051 #endif
2053 typedef struct MonoComObject MonoComObject;
2055 typedef struct
2057 int (COM_STDCALL *QueryInterface)(MonoComObject* pUnk, gpointer riid, gpointer* ppv);
2058 int (COM_STDCALL *AddRef)(MonoComObject* pUnk);
2059 int (COM_STDCALL *Release)(MonoComObject* pUnk);
2060 int (COM_STDCALL *Add)(MonoComObject* pUnk, int a, int b, int* c);
2061 int (COM_STDCALL *Subtract)(MonoComObject* pUnk, int a, int b, int* c);
2062 } MonoIUnknown;
2064 struct MonoComObject
2066 MonoIUnknown* vtbl;
2067 int m_ref;
2070 int COM_STDCALL MonoQueryInterface(MonoComObject* pUnk, gpointer riid, gpointer* ppv)
2072 *ppv = pUnk;
2073 return 0;
2076 int COM_STDCALL MonoAddRef(MonoComObject* pUnk)
2078 return ++(pUnk->m_ref);
2081 int COM_STDCALL MonoRelease(MonoComObject* pUnk)
2083 return --(pUnk->m_ref);
2086 int COM_STDCALL Add(MonoComObject* pUnk, int a, int b, int* c)
2088 *c = a + b;
2089 return 0;
2092 int COM_STDCALL Subtract(MonoComObject* pUnk, int a, int b, int* c)
2094 *c = a - b;
2095 return 0;
2098 STDCALL int
2099 mono_test_marshal_com_object_create(MonoComObject* *pUnk)
2101 *pUnk = g_new0 (MonoComObject, 1);
2102 (*pUnk)->vtbl = g_new0 (MonoIUnknown, 1);
2104 (*pUnk)->m_ref = 1;
2105 (*pUnk)->vtbl->QueryInterface = MonoQueryInterface;
2106 (*pUnk)->vtbl->AddRef = MonoAddRef;
2107 (*pUnk)->vtbl->Release = MonoRelease;
2108 (*pUnk)->vtbl->Add = Add;
2109 (*pUnk)->vtbl->Subtract = Subtract;
2112 return 0;
2115 STDCALL int
2116 mono_test_marshal_com_object_destroy(MonoComObject *pUnk)
2118 int ref = --(pUnk->m_ref);
2119 g_free(pUnk->vtbl);
2120 g_free(pUnk);
2122 return ref;
2125 STDCALL int
2126 mono_test_marshal_com_object_ref_count(MonoComObject *pUnk)
2128 return pUnk->m_ref;
2131 #endif //NOT_YET