2007-12-06 Jb Evain <jbevain@novell.com>
[mono.git] / mono / tests / libtest.c
blobfaa9916e1ee6259849d723a7239c4c796d23bbf2
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 #include "initguid.h"
11 #endif
13 #ifdef WIN32
14 #define STDCALL __stdcall
15 #else
16 #define STDCALL
17 #endif
19 #ifdef WIN32
20 extern __declspec(dllimport) __stdcall void CoTaskMemFree(void *ptr);
21 #endif
23 typedef int (STDCALL *SimpleDelegate) (int a);
25 static void marshal_free (void *ptr)
27 #ifdef WIN32
28 CoTaskMemFree (ptr);
29 #else
30 g_free (ptr);
31 #endif
34 STDCALL unsigned short*
35 test_lpwstr_marshal (unsigned short* chars, long length)
37 int i = 0;
38 unsigned short *res;
40 res = malloc (2 * (length + 1));
42 // printf("test_lpwstr_marshal()\n");
44 while ( i < length ) {
45 // printf("X|%u|\n", chars[i]);
46 res [i] = chars[i];
47 i++;
50 res [i] = 0;
52 return res;
55 typedef struct {
56 int b;
57 int a;
58 int c;
59 } union_test_1_type;
61 STDCALL int
62 mono_union_test_1 (union_test_1_type u1) {
63 // printf ("Got values %d %d %d\n", u1.b, u1.a, u1.c);
64 return u1.a + u1.b + u1.c;
67 STDCALL int
68 mono_return_int (int a) {
69 // printf ("Got value %d\n", a);
70 return a;
73 struct ss
75 int i;
78 STDCALL int
79 mono_return_int_ss (struct ss a) {
80 // printf ("Got value %d\n", a.i);
81 return a.i;
84 STDCALL struct ss
85 mono_return_ss (struct ss a) {
86 // printf ("Got value %d\n", a.i);
87 a.i++;
88 return a;
91 struct sc1
93 char c[1];
96 STDCALL struct sc1
97 mono_return_sc1 (struct sc1 a) {
98 // printf ("Got value %d\n", a.c[0]);
99 a.c[0]++;
100 return a;
104 struct sc3
106 char c[3];
109 STDCALL struct sc3
110 mono_return_sc3 (struct sc3 a) {
111 // printf ("Got values %d %d %d\n", a.c[0], a.c[1], a.c[2]);
112 a.c[0]++;
113 a.c[1] += 2;
114 a.c[2] += 3;
115 return a;
118 struct sc5
120 char c[5];
123 STDCALL struct sc5
124 mono_return_sc5 (struct sc5 a) {
125 // printf ("Got values %d %d %d %d %d\n", a.c[0], a.c[1], a.c[2], a.c[3], a.c[4]);
126 a.c[0]++;
127 a.c[1] += 2;
128 a.c[2] += 3;
129 a.c[3] += 4;
130 a.c[4] += 5;
131 return a;
134 union su
136 int i1;
137 int i2;
140 STDCALL int
141 mono_return_int_su (union su a) {
142 // printf ("Got value %d\n", a.i1);
143 return a.i1;
146 STDCALL int
147 mono_test_many_int_arguments (int a, int b, int c, int d, int e,
148 int f, int g, int h, int i, int j);
149 STDCALL short
150 mono_test_many_short_arguments (short a, short b, short c, short d, short e,
151 short f, short g, short h, short i, short j);
152 STDCALL char
153 mono_test_many_char_arguments (char a, char b, char c, char d, char e,
154 char f, char g, char h, char i, char j);
156 STDCALL int
157 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)
159 return a + b + c + d + e + f + g + h + i + j;
162 STDCALL short
163 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)
165 return a + b + c + d + e + f + g + h + i + j;
168 STDCALL char
169 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)
171 return a + b + c + d + e + f + g + h + i + j;
174 STDCALL float
175 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)
177 return a + b + c + d + e + f + g + h + i + j;
180 STDCALL double
181 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)
183 return a + b + c + d + e + f + g + h + i + j;
186 STDCALL double
187 mono_test_split_double_arguments (double a, double b, float c, double d, double e)
189 return a + b + c + d + e;
192 STDCALL int
193 mono_test_puts_static (char *s)
195 // printf ("TEST %s\n", s);
196 return 1;
199 typedef int (STDCALL *SimpleDelegate3) (int a, int b);
201 STDCALL int
202 mono_invoke_delegate (SimpleDelegate3 delegate)
204 int res;
206 // printf ("start invoke %p\n", delegate);
208 res = delegate (2, 3);
210 // printf ("end invoke\n");
212 return res;
215 STDCALL int
216 mono_test_marshal_char (short a1)
218 if (a1 == 'a')
219 return 0;
221 return 1;
224 STDCALL void
225 mono_test_marshal_char_array (gunichar2 *s)
227 const char m[] = "abcdef";
228 gunichar2* s2;
229 glong len;
231 s2 = g_utf8_to_utf16 (m, -1, NULL, &len, NULL);
233 len = (len * 2) + 2;
234 memcpy (s, s2, len);
236 g_free (s2);
239 STDCALL int
240 mono_test_empty_pinvoke (int i)
242 return i;
245 STDCALL int
246 mono_test_marshal_bool_byref (int a, int *b, int c)
248 int res = *b;
250 *b = 1;
252 return res;
255 STDCALL int
256 mono_test_marshal_bool_in_as_I1_U1 (char bTrue, char bFalse)
258 if (!bTrue)
259 return 1;
260 if (bFalse)
261 return 2;
262 return 0;
265 STDCALL int
266 mono_test_marshal_bool_out_as_I1_U1 (char* bTrue, char* bFalse)
268 if (!bTrue || !bFalse)
269 return 3;
271 *bTrue = 1;
272 *bFalse = 0;
274 return 0;
277 STDCALL int
278 mono_test_marshal_bool_ref_as_I1_U1 (char* bTrue, char* bFalse)
280 if (!bTrue || !bFalse)
281 return 4;
283 if (!(*bTrue))
284 return 5;
285 if (*bFalse)
286 return 6;
288 *bFalse = 1;
289 *bTrue = 0;
291 return 0;
294 STDCALL int
295 mono_test_marshal_array (int *a1)
297 int i, sum = 0;
299 for (i = 0; i < 50; i++)
300 sum += a1 [i];
302 return sum;
305 STDCALL int
306 mono_test_marshal_inout_array (int *a1)
308 int i, sum = 0;
310 for (i = 0; i < 50; i++) {
311 sum += a1 [i];
312 a1 [i] = 50 - a1 [i];
315 return sum;
318 STDCALL int
319 mono_test_marshal_out_array (int *a1)
321 int i;
323 for (i = 0; i < 50; i++) {
324 a1 [i] = i;
327 return 0;
330 STDCALL int
331 mono_test_marshal_inout_nonblittable_array (gunichar2 *a1)
333 int i, sum = 0;
335 for (i = 0; i < 10; i++) {
336 a1 [i] = 'F';
339 return sum;
342 typedef struct {
343 int a;
344 int b;
345 int c;
346 const char *d;
347 gunichar2 *d2;
348 } simplestruct;
350 typedef struct {
351 double x;
352 double y;
353 } point;
355 STDCALL simplestruct
356 mono_test_return_vtype (int i)
358 simplestruct res;
359 static gunichar2 test2 [] = { 'T', 'E', 'S', 'T', '2', 0 };
361 res.a = 0;
362 res.b = 1;
363 res.c = 0;
364 res.d = "TEST";
365 res.d2 = test2;
367 return res;
370 STDCALL void
371 mono_test_delegate_struct (void)
373 // printf ("TEST\n");
376 typedef char* (STDCALL *ReturnStringDelegate) (const char *s);
378 STDCALL char *
379 mono_test_return_string (ReturnStringDelegate func)
381 char *res;
383 // printf ("mono_test_return_string\n");
385 res = func ("TEST");
386 marshal_free (res);
388 // printf ("got string: %s\n", res);
389 return g_strdup ("12345");
392 typedef int (STDCALL *RefVTypeDelegate) (int a, simplestruct *ss, int b);
394 STDCALL int
395 mono_test_ref_vtype (int a, simplestruct *ss, int b, RefVTypeDelegate func)
397 if (a == 1 && b == 2 && ss->a == 0 && ss->b == 1 && ss->c == 0 &&
398 !strcmp (ss->d, "TEST1")) {
399 ss->a = 1;
400 ss->b = 0;
401 ss->c = 1;
402 ss->d = "TEST2";
404 return func (a, ss, b);
407 return 1;
410 typedef int (STDCALL *OutVTypeDelegate) (int a, simplestruct *ss, int b);
412 STDCALL int
413 mono_test_marshal_out_struct (int a, simplestruct *ss, int b, OutVTypeDelegate func)
415 /* Check that the input pointer is ignored */
416 ss->d = (gpointer)0x12345678;
418 func (a, ss, b);
420 if (ss->a && ss->b && ss->c && !strcmp (ss->d, "TEST3"))
421 return 0;
422 else
423 return 1;
426 typedef struct {
427 int a;
428 SimpleDelegate func, func2;
429 } DelegateStruct;
431 STDCALL DelegateStruct
432 mono_test_marshal_delegate_struct (DelegateStruct ds)
434 DelegateStruct res;
436 res.a = ds.func (ds.a) + ds.func2 (ds.a);
437 res.func = ds.func;
438 res.func2 = ds.func2;
440 return res;
443 STDCALL int
444 mono_test_marshal_struct (simplestruct ss)
446 if (ss.a == 0 && ss.b == 1 && ss.c == 0 &&
447 !strcmp (ss.d, "TEST"))
448 return 0;
450 return 1;
453 STDCALL int
454 mono_test_marshal_byref_struct (simplestruct *ss, int a, int b, int c, char *d)
456 gboolean res = (ss->a == a && ss->b == b && ss->c == c && strcmp (ss->d, d) == 0);
458 marshal_free (ss->d);
460 ss->a = !ss->a;
461 ss->b = !ss->b;
462 ss->c = !ss->c;
463 ss->d = g_strdup ("DEF");
465 return res ? 0 : 1;
468 typedef struct {
469 int a;
470 int b;
471 int c;
472 char *d;
473 unsigned char e;
474 double f;
475 unsigned char g;
476 guint64 h;
477 } simplestruct2;
479 STDCALL int
480 mono_test_marshal_struct2 (simplestruct2 ss)
482 if (ss.a == 0 && ss.b == 1 && ss.c == 0 &&
483 !strcmp (ss.d, "TEST") &&
484 ss.e == 99 && ss.f == 1.5 && ss.g == 42 && ss.h == (guint64)123)
485 return 0;
487 return 1;
490 /* on HP some of the struct should be on the stack and not in registers */
491 STDCALL int
492 mono_test_marshal_struct2_2 (int i, int j, int k, simplestruct2 ss)
494 if (i != 10 || j != 11 || k != 12)
495 return 1;
496 if (ss.a == 0 && ss.b == 1 && ss.c == 0 &&
497 !strcmp (ss.d, "TEST") &&
498 ss.e == 99 && ss.f == 1.5 && ss.g == 42 && ss.h == (guint64)123)
499 return 0;
501 return 1;
504 STDCALL int
505 mono_test_marshal_lpstruct (simplestruct *ss)
507 if (ss->a == 0 && ss->b == 1 && ss->c == 0 &&
508 !strcmp (ss->d, "TEST"))
509 return 0;
511 return 1;
514 STDCALL int
515 mono_test_marshal_lpstruct_blittable (point *p)
517 if (p->x == 1.0 && p->y == 2.0)
518 return 0;
519 else
520 return 1;
523 STDCALL int
524 mono_test_marshal_struct_array (simplestruct2 *ss)
526 if (! (ss[0].a == 0 && ss[0].b == 1 && ss[0].c == 0 &&
527 !strcmp (ss[0].d, "TEST") &&
528 ss[0].e == 99 && ss[0].f == 1.5 && ss[0].g == 42 && ss[0].h == (guint64)123))
529 return 1;
531 if (! (ss[1].a == 0 && ss[1].b == 0 && ss[1].c == 0 &&
532 !strcmp (ss[1].d, "TEST2") &&
533 ss[1].e == 100 && ss[1].f == 2.5 && ss[1].g == 43 && ss[1].h == (guint64)124))
534 return 1;
536 return 0;
539 typedef struct long_align_struct {
540 gint32 a;
541 gint64 b;
542 gint64 c;
543 } long_align_struct;
545 STDCALL int
546 mono_test_marshal_long_align_struct_array (long_align_struct *ss)
548 return ss[0].a + ss[0].b + ss[0].c + ss[1].a + ss[1].b + ss[1].c;
551 STDCALL simplestruct2 *
552 mono_test_marshal_class (int i, int j, int k, simplestruct2 *ss, int l)
554 simplestruct2 *res;
556 if (!ss)
557 return NULL;
559 if (i != 10 || j != 11 || k != 12 || l != 14)
560 return NULL;
561 if (! (ss->a == 0 && ss->b == 1 && ss->c == 0 &&
562 !strcmp (ss->d, "TEST") &&
563 ss->e == 99 && ss->f == 1.5 && ss->g == 42 && ss->h == (guint64)123))
564 return NULL;
566 res = g_new0 (simplestruct2, 1);
567 memcpy (res, ss, sizeof (simplestruct2));
568 res->d = g_strdup ("TEST");
569 return res;
572 STDCALL int
573 mono_test_marshal_byref_class (simplestruct2 **ssp)
575 simplestruct2 *ss = *ssp;
576 simplestruct2 *res;
578 if (! (ss->a == 0 && ss->b == 1 && ss->c == 0 &&
579 !strcmp (ss->d, "TEST") &&
580 ss->e == 99 && ss->f == 1.5 && ss->g == 42 && ss->h == (guint64)123))
581 return 1;
583 res = g_new0 (simplestruct2, 1);
584 memcpy (res, ss, sizeof (simplestruct2));
585 res->d = g_strdup ("TEST-RES");
587 *ssp = res;
588 return 0;
591 static void *
592 get_sp (void)
594 int i;
595 void *p;
597 /* Yes, this is correct, we are only trying to determine the value of the stack here */
598 p = &i;
599 return p;
602 STDCALL int
603 reliable_delegate (int a)
605 return a;
609 * Checks whether get_sp() works as expected. It doesn't work with gcc-2.95.3 on linux.
611 static gboolean
612 is_get_sp_reliable (void)
614 void *sp1, *sp2;
616 reliable_delegate(1);
617 sp1 = get_sp();
618 reliable_delegate(1);
619 sp2 = get_sp();
620 return sp1 == sp2;
623 STDCALL int
624 mono_test_marshal_delegate (SimpleDelegate delegate)
626 void *sp1, *sp2;
628 /* Check that the delegate wrapper is stdcall */
629 delegate (2);
630 sp1 = get_sp ();
631 delegate (2);
632 sp2 = get_sp ();
633 if (is_get_sp_reliable())
634 g_assert (sp1 == sp2);
636 return delegate (2);
639 STDCALL SimpleDelegate
640 mono_test_marshal_return_delegate (SimpleDelegate delegate)
642 return delegate;
645 static STDCALL int
646 return_plus_one (int i)
648 return i + 1;
651 STDCALL SimpleDelegate
652 mono_test_marshal_return_delegate_2 ()
654 return return_plus_one;
657 typedef simplestruct (STDCALL *SimpleDelegate2) (simplestruct ss);
659 static gboolean
660 is_utf16_equals (gunichar2 *s1, const char *s2)
662 char *s;
663 int res;
665 s = g_utf16_to_utf8 (s1, -1, NULL, NULL, NULL);
666 res = strcmp (s, s2);
667 g_free (s);
669 return res == 0;
672 STDCALL int
673 mono_test_marshal_delegate2 (SimpleDelegate2 delegate)
675 simplestruct ss, res;
677 ss.a = 0;
678 ss.b = 1;
679 ss.c = 0;
680 ss.d = "TEST";
681 ss.d2 = g_utf8_to_utf16 ("TEST2", -1, NULL, NULL, NULL);
683 res = delegate (ss);
684 if (! (res.a && !res.b && res.c && !strcmp (res.d, "TEST-RES") && is_utf16_equals (res.d2, "TEST2-RES")))
685 return 1;
687 return 0;
690 typedef simplestruct* (STDCALL *SimpleDelegate4) (simplestruct *ss);
692 STDCALL int
693 mono_test_marshal_delegate4 (SimpleDelegate4 delegate)
695 simplestruct ss;
696 simplestruct *res;
698 ss.a = 0;
699 ss.b = 1;
700 ss.c = 0;
701 ss.d = "TEST";
703 /* Check argument */
704 res = delegate (&ss);
705 if (!res)
706 return 1;
708 /* Check return value */
709 if (! (!res->a && res->b && !res->c && !strcmp (res->d, "TEST")))
710 return 2;
712 /* Check NULL argument and NULL result */
713 res = delegate (NULL);
714 if (res)
715 return 3;
717 return 0;
720 typedef int (STDCALL *SimpleDelegate5) (simplestruct **ss);
722 STDCALL int
723 mono_test_marshal_delegate5 (SimpleDelegate5 delegate)
725 simplestruct ss;
726 int res;
727 simplestruct *ptr;
729 ss.a = 0;
730 ss.b = 1;
731 ss.c = 0;
732 ss.d = "TEST";
734 ptr = &ss;
736 res = delegate (&ptr);
737 if (res != 0)
738 return 1;
740 if (!(ptr->a && !ptr->b && ptr->c && !strcmp (ptr->d, "RES")))
741 return 2;
743 return 0;
746 STDCALL int
747 mono_test_marshal_delegate6 (SimpleDelegate5 delegate)
749 int res;
751 res = delegate (NULL);
753 return 0;
756 typedef int (STDCALL *SimpleDelegate7) (simplestruct **ss);
758 STDCALL int
759 mono_test_marshal_delegate7 (SimpleDelegate7 delegate)
761 int res;
762 simplestruct *ptr;
764 /* Check that the input pointer is ignored */
765 ptr = (gpointer)0x12345678;
767 res = delegate (&ptr);
768 if (res != 0)
769 return 1;
771 if (!(ptr->a && !ptr->b && ptr->c && !strcmp (ptr->d, "RES")))
772 return 2;
774 return 0;
777 typedef int (STDCALL *InOutByvalClassDelegate) (simplestruct *ss);
779 STDCALL int
780 mono_test_marshal_inout_byval_class_delegate (InOutByvalClassDelegate delegate)
782 int res;
783 simplestruct ss;
785 ss.a = FALSE;
786 ss.b = TRUE;
787 ss.c = FALSE;
788 ss.d = g_strdup_printf ("%s", "FOO");
790 res = delegate (&ss);
791 if (res != 0)
792 return 1;
794 if (!(ss.a && !ss.b && ss.c && !strcmp (ss.d, "RES")))
795 return 2;
797 return 0;
800 typedef int (STDCALL *SimpleDelegate8) (gunichar2 *s);
802 STDCALL int
803 mono_test_marshal_delegate8 (SimpleDelegate8 delegate, gunichar2 *s)
805 return delegate (s);
808 typedef int (STDCALL *return_int_fnt) (int i);
809 typedef int (STDCALL *SimpleDelegate9) (return_int_fnt d);
811 STDCALL int
812 mono_test_marshal_delegate9 (SimpleDelegate9 delegate, gpointer ftn)
814 return delegate (ftn);
817 STDCALL static int
818 return_self (int i)
820 return i;
823 STDCALL int
824 mono_test_marshal_delegate10 (SimpleDelegate9 delegate)
826 return delegate (return_self);
829 typedef int (STDCALL *PrimitiveByrefDelegate) (int *i);
831 STDCALL int
832 mono_test_marshal_primitive_byref_delegate (PrimitiveByrefDelegate delegate)
834 int i = 1;
836 int res = delegate (&i);
837 if (res != 0)
838 return res;
840 if (i != 2)
841 return 2;
843 return 0;
846 typedef int (STDCALL *return_int_delegate) (int i);
848 typedef return_int_delegate (STDCALL *ReturnDelegateDelegate) (void);
850 STDCALL int
851 mono_test_marshal_return_delegate_delegate (ReturnDelegateDelegate d)
853 return (d ()) (55);
856 STDCALL int
857 mono_test_marshal_stringbuilder (char *s, int n)
859 const char m[] = "This is my message. Isn't it nice?";
861 if (strcmp (s, "ABCD") != 0)
862 return 1;
863 strncpy(s, m, n);
864 s [n] = '\0';
865 return 0;
868 STDCALL int
869 mono_test_marshal_stringbuilder_default (char *s, int n)
871 const char m[] = "This is my message. Isn't it nice?";
873 strncpy(s, m, n);
874 s [n] = '\0';
875 return 0;
878 STDCALL int
879 mono_test_marshal_stringbuilder_unicode (gunichar2 *s, int n)
881 const char m[] = "This is my message. Isn't it nice?";
882 gunichar2* s2;
883 glong len;
885 s2 = g_utf8_to_utf16 (m, -1, NULL, &len, NULL);
887 len = (len * 2) + 2;
888 if (len > (n * 2))
889 len = n * 2;
890 memcpy (s, s2, len);
892 g_free (s2);
894 return 0;
897 typedef struct {
898 #ifndef __GNUC__
899 char a;
900 #endif
901 } EmptyStruct;
903 STDCALL int
904 mono_test_marshal_empty_string_array (char **array)
906 return (array == NULL) ? 0 : 1;
909 STDCALL int
910 mono_test_marshal_string_array (char **array)
912 if (strcmp (array [0], "ABC"))
913 return 1;
914 if (strcmp (array [1], "DEF"))
915 return 2;
917 if (array [2] != NULL)
918 return 3;
920 return 0;
923 STDCALL int
924 mono_test_marshal_byref_string_array (char ***array)
926 if (*array == NULL)
927 return 0;
929 if (strcmp ((*array) [0], "Alpha"))
930 return 2;
931 if (strcmp ((*array) [1], "Beta"))
932 return 2;
933 if (strcmp ((*array) [2], "Gamma"))
934 return 2;
936 return 1;
939 STDCALL int
940 mono_test_marshal_stringbuilder_array (char **array)
942 if (strcmp (array [0], "ABC"))
943 return 1;
944 if (strcmp (array [1], "DEF"))
945 return 2;
947 strcpy (array [0], "DEF");
948 strcpy (array [1], "ABC");
950 return 0;
953 STDCALL int
954 mono_test_marshal_unicode_string_array (gunichar2 **array, char **array2)
956 GError *error = NULL;
957 char *s;
959 s = g_utf16_to_utf8 (array [0], -1, NULL, NULL, &error);
960 if (strcmp (s, "ABC")) {
961 g_free (s);
962 return 1;
964 else
965 g_free (s);
967 s = g_utf16_to_utf8 (array [1], -1, NULL, NULL, &error);
968 if (strcmp (s, "DEF")) {
969 g_free (s);
970 return 2;
972 else
973 g_free (s);
975 if (strcmp (array2 [0], "ABC"))
976 return 3;
978 if (strcmp (array2 [1], "DEF"))
979 return 4;
981 return 0;
984 /* this does not work on Redhat gcc 2.96 */
985 STDCALL int
986 mono_test_empty_struct (int a, EmptyStruct es, int b)
988 // printf ("mono_test_empty_struct %d %d\n", a, b);
990 // Intel icc on ia64 passes 'es' in 2 registers
991 #if defined(__ia64) && defined(__INTEL_COMPILER)
992 return 0;
993 #else
994 if (a == 1 && b == 2)
995 return 0;
996 return 1;
997 #endif
1000 typedef struct {
1001 char a[100];
1002 } ByValStrStruct;
1004 STDCALL ByValStrStruct *
1005 mono_test_byvalstr_gen (void)
1007 ByValStrStruct *ret;
1009 ret = malloc(sizeof(ByValStrStruct));
1010 memset(ret, 'a', sizeof(ByValStrStruct)-1);
1011 ret->a[sizeof(ByValStrStruct)-1] = 0;
1013 return ret;
1016 STDCALL int
1017 mono_test_byvalstr_check (ByValStrStruct* data, char* correctString)
1019 int ret;
1021 ret = strcmp(data->a, correctString);
1022 // printf ("T1: %s\n", data->a);
1023 // printf ("T2: %s\n", correctString);
1025 marshal_free (data);
1026 return (ret != 0);
1029 typedef struct {
1030 guint16 a[4];
1031 int flag;
1032 } ByValStrStruct_Unicode;
1034 STDCALL int
1035 mono_test_byvalstr_check_unicode (ByValStrStruct_Unicode *ref, int test)
1037 if (ref->flag != 0x1234abcd){
1038 printf ("overwritten data");
1039 return 1;
1042 if (test == 1 || test == 3){
1043 if (ref->a [0] != '1' ||
1044 ref->a [1] != '2' ||
1045 ref->a [2] != '3')
1046 return 1;
1047 return 0;
1049 if (test == 2){
1050 if (ref->a [0] != '1' ||
1051 ref->a [1] != '2')
1052 return 1;
1053 return 0;
1055 return 10;
1058 STDCALL int
1059 NameManglingAnsi (char *data)
1061 return data [0] + data [1] + data [2];
1064 STDCALL int
1065 NameManglingAnsiA (char *data)
1067 g_assert_not_reached ();
1070 STDCALL int
1071 NameManglingAnsiW (char *data)
1073 g_assert_not_reached ();
1076 STDCALL int
1077 NameManglingAnsi2A (char *data)
1079 return data [0] + data [1] + data [2];
1082 STDCALL int
1083 NameManglingAnsi2W (char *data)
1085 g_assert_not_reached ();
1088 STDCALL int
1089 NameManglingUnicode (char *data)
1091 g_assert_not_reached ();
1094 STDCALL int
1095 NameManglingUnicodeW (gunichar2 *data)
1097 return data [0] + data [1] + data [2];
1100 STDCALL int
1101 NameManglingUnicode2 (gunichar2 *data)
1103 return data [0] + data [1] + data [2];
1106 STDCALL int
1107 NameManglingAutoW (char *data)
1109 #ifdef WIN32
1110 return (data [0] + data [1] + data [2]) == 131 ? 0 : 1;
1111 #else
1112 g_assert_not_reached ();
1113 #endif
1116 STDCALL int
1117 NameManglingAuto (char *data)
1119 #ifndef WIN32
1120 return (data [0] + data [1] + data [2]) == 198 ? 0 : 1;
1121 #else
1122 g_assert_not_reached ();
1123 #endif
1126 typedef int (STDCALL *intcharFunc)(const char*);
1128 STDCALL void
1129 callFunction (intcharFunc f)
1131 f ("ABC");
1134 typedef struct {
1135 const char* str;
1136 int i;
1137 } SimpleObj;
1139 STDCALL int
1140 class_marshal_test0 (SimpleObj *obj1)
1142 // printf ("class_marshal_test0 %s %d\n", obj1->str, obj1->i);
1144 if (strcmp(obj1->str, "T1"))
1145 return -1;
1146 if (obj1->i != 4)
1147 return -2;
1149 return 0;
1152 STDCALL int
1153 class_marshal_test4 (SimpleObj *obj1)
1155 if (obj1)
1156 return -1;
1158 return 0;
1161 STDCALL void
1162 class_marshal_test1 (SimpleObj **obj1)
1164 SimpleObj *res = malloc (sizeof (SimpleObj));
1166 res->str = g_strdup ("ABC");
1167 res->i = 5;
1169 *obj1 = res;
1172 STDCALL int
1173 class_marshal_test2 (SimpleObj **obj1)
1175 // printf ("class_marshal_test2 %s %d\n", (*obj1)->str, (*obj1)->i);
1177 if (strcmp((*obj1)->str, "ABC"))
1178 return -1;
1179 if ((*obj1)->i != 5)
1180 return -2;
1182 return 0;
1185 STDCALL int
1186 string_marshal_test0 (char *str)
1188 if (strcmp (str, "TEST0"))
1189 return -1;
1191 return 0;
1194 STDCALL void
1195 string_marshal_test1 (const char **str)
1197 *str = "TEST1";
1200 STDCALL int
1201 string_marshal_test2 (char **str)
1203 // printf ("string_marshal_test2 %s\n", *str);
1205 if (strcmp (*str, "TEST1"))
1206 return -1;
1208 return 0;
1211 STDCALL int
1212 string_marshal_test3 (char *str)
1214 if (str)
1215 return -1;
1217 return 0;
1220 typedef struct {
1221 int a;
1222 int b;
1223 } BlittableClass;
1225 STDCALL BlittableClass*
1226 TestBlittableClass (BlittableClass *vl)
1228 BlittableClass *res;
1230 // printf ("TestBlittableClass %d %d\n", vl->a, vl->b);
1232 if (vl) {
1233 vl->a++;
1234 vl->b++;
1236 res = g_new0 (BlittableClass, 1);
1237 memcpy (res, vl, sizeof (BlittableClass));
1238 } else {
1239 res = g_new0 (BlittableClass, 1);
1240 res->a = 42;
1241 res->b = 43;
1244 return res;
1247 typedef struct OSVERSIONINFO_STRUCT
1249 int a;
1250 int b;
1251 } OSVERSIONINFO_STRUCT;
1253 STDCALL int
1254 MyGetVersionEx (OSVERSIONINFO_STRUCT *osvi)
1257 // printf ("GOT %d %d\n", osvi->a, osvi->b);
1259 osvi->a += 1;
1260 osvi->b += 1;
1262 return osvi->a + osvi->b;
1265 STDCALL int
1266 BugGetVersionEx (int a, int b, int c, int d, int e, int f, int g, int h, OSVERSIONINFO_STRUCT *osvi)
1269 // printf ("GOT %d %d\n", osvi->a, osvi->b);
1271 osvi->a += 1;
1272 osvi->b += 1;
1274 return osvi->a + osvi->b;
1277 STDCALL int
1278 mono_test_marshal_point (point pt)
1280 // printf("point %g %g\n", pt.x, pt.y);
1281 if (pt.x == 1.25 && pt.y == 3.5)
1282 return 0;
1284 return 1;
1287 typedef struct {
1288 int x;
1289 double y;
1290 } mixed_point;
1292 STDCALL int
1293 mono_test_marshal_mixed_point (mixed_point pt)
1295 // printf("mixed point %d %g\n", pt.x, pt.y);
1296 if (pt.x == 5 && pt.y == 6.75)
1297 return 0;
1299 return 1;
1302 STDCALL int
1303 mono_test_marshal_mixed_point_2 (mixed_point *pt)
1305 if (pt->x != 5 || pt->y != 6.75)
1306 return 1;
1308 pt->x = 10;
1309 pt->y = 12.35;
1311 return 0;
1314 STDCALL int
1315 marshal_test_ref_bool(int i, char *b1, short *b2, int *b3)
1317 int res = 1;
1318 if (*b1 != 0 && *b1 != 1)
1319 return 1;
1320 if (*b2 != 0 && *b2 != -1) /* variant_bool */
1321 return 1;
1322 if (*b3 != 0 && *b3 != 1)
1323 return 1;
1324 if (i == ((*b1 << 2) | (-*b2 << 1) | *b3))
1325 res = 0;
1326 *b1 = !*b1;
1327 *b2 = ~*b2;
1328 *b3 = !*b3;
1329 return res;
1332 struct BoolStruct
1334 int i;
1335 char b1;
1336 short b2; /* variant_bool */
1337 int b3;
1340 STDCALL int
1341 marshal_test_bool_struct(struct BoolStruct *s)
1343 int res = 1;
1344 if (s->b1 != 0 && s->b1 != 1)
1345 return 1;
1346 if (s->b2 != 0 && s->b2 != -1)
1347 return 1;
1348 if (s->b3 != 0 && s->b3 != 1)
1349 return 1;
1350 if (s->i == ((s->b1 << 2) | (-s->b2 << 1) | s->b3))
1351 res = 0;
1352 s->b1 = !s->b1;
1353 s->b2 = ~s->b2;
1354 s->b3 = !s->b3;
1355 return res;
1358 STDCALL void
1359 mono_test_last_error (int err)
1361 #ifdef WIN32
1362 SetLastError (err);
1363 #else
1364 errno = err;
1365 #endif
1368 STDCALL int
1369 mono_test_asany (void *ptr, int what)
1371 switch (what) {
1372 case 1:
1373 return (*(int*)ptr == 5) ? 0 : 1;
1374 case 2:
1375 return strcmp (ptr, "ABC") == 0 ? 0 : 1;
1376 case 3: {
1377 simplestruct2 ss = *(simplestruct2*)ptr;
1379 if (ss.a == 0 && ss.b == 1 && ss.c == 0 &&
1380 !strcmp (ss.d, "TEST") &&
1381 ss.e == 99 && ss.f == 1.5 && ss.g == 42 && ss.h == (guint64)123)
1382 return 0;
1383 else
1384 return 1;
1386 case 4: {
1387 GError *error = NULL;
1388 char *s;
1390 s = g_utf16_to_utf8 (ptr, -1, NULL, NULL, &error);
1391 if (!strcmp (s, "ABC")) {
1392 g_free (s);
1393 return 0;
1395 else {
1396 g_free (s);
1397 return 1;
1400 default:
1401 g_assert_not_reached ();
1404 return 1;
1407 typedef struct
1409 int i;
1410 int j;
1411 int k;
1412 char *s;
1413 } AsAnyStruct;
1415 STDCALL int
1416 mono_test_marshal_asany_in (void* ptr)
1418 AsAnyStruct* asAny = ptr;
1419 int res = asAny->i + asAny->j + asAny->k;
1421 return res;
1424 STDCALL int
1425 mono_test_marshal_asany_inout (void* ptr)
1427 AsAnyStruct* asAny = ptr;
1428 int res = asAny->i + asAny->j + asAny->k;
1430 marshal_free (asAny->s);
1432 asAny->i = 10;
1433 asAny->j = 20;
1434 asAny->k = 30;
1435 asAny->s = 0;
1437 return res;
1440 STDCALL int
1441 mono_test_marshal_asany_out (void* ptr)
1443 AsAnyStruct* asAny = ptr;
1444 int res = asAny->i + asAny->j + asAny->k;
1446 asAny->i = 10;
1447 asAny->j = 20;
1448 asAny->k = 30;
1449 asAny->s = 0;
1451 return res;
1455 * AMD64 marshalling tests.
1458 typedef struct amd64_struct1 {
1459 int i;
1460 int j;
1461 int k;
1462 int l;
1463 } amd64_struct1;
1465 STDCALL amd64_struct1
1466 mono_test_marshal_amd64_pass_return_struct1 (amd64_struct1 s)
1468 s.i ++;
1469 s.j ++;
1470 s.k ++;
1471 s.l ++;
1473 return s;
1476 typedef struct amd64_struct2 {
1477 int i;
1478 int j;
1479 } amd64_struct2;
1481 STDCALL amd64_struct2
1482 mono_test_marshal_amd64_pass_return_struct2 (amd64_struct2 s)
1484 s.i ++;
1485 s.j ++;
1487 return s;
1490 typedef struct amd64_struct3 {
1491 int i;
1492 } amd64_struct3;
1494 STDCALL amd64_struct3
1495 mono_test_marshal_amd64_pass_return_struct3 (amd64_struct3 s)
1497 s.i ++;
1499 return s;
1502 typedef struct amd64_struct4 {
1503 double d1, d2;
1504 } amd64_struct4;
1506 STDCALL amd64_struct4
1507 mono_test_marshal_amd64_pass_return_struct4 (amd64_struct4 s)
1509 s.d1 ++;
1510 s.d2 ++;
1512 return s;
1516 * IA64 marshalling tests.
1518 typedef struct test_struct5 {
1519 float d1, d2;
1520 } test_struct5;
1522 STDCALL test_struct5
1523 mono_test_marshal_ia64_pass_return_struct5 (double d1, double d2, test_struct5 s, double d3, double d4)
1525 s.d1 += d1 + d2;
1526 s.d2 += d3 + d4;
1528 return s;
1531 typedef struct test_struct6 {
1532 double d1, d2;
1533 } test_struct6;
1535 STDCALL test_struct6
1536 mono_test_marshal_ia64_pass_return_struct6 (double d1, double d2, test_struct6 s, double d3, double d4)
1538 s.d1 += d1 + d2;
1539 s.d2 += d3 + d4;
1541 return s;
1544 static guint32 custom_res [2];
1546 STDCALL void*
1547 mono_test_marshal_pass_return_custom (int i, guint32 *ptr, int j)
1549 /* ptr will be freed by CleanupNative, so make a copy */
1550 custom_res [0] = 0; /* not allocated by AllocHGlobal */
1551 custom_res [1] = ptr [1];
1553 return &custom_res;
1556 STDCALL int
1557 mono_test_marshal_pass_out_custom (int i, guint32 **ptr, int j)
1559 custom_res [0] = 0;
1560 custom_res [1] = i + j + 10;
1562 *ptr = custom_res;
1564 return 0;
1567 STDCALL int
1568 mono_test_marshal_pass_inout_custom (int i, guint32 *ptr, int j)
1570 ptr [0] = 0;
1571 ptr [1] = i + ptr [1] + j;
1573 return 0;
1576 STDCALL int
1577 mono_test_marshal_pass_out_byval_custom (int i, guint32 *ptr, int j)
1579 return ptr == NULL ? 0 : 1;
1582 STDCALL int
1583 mono_test_marshal_pass_byref_custom (int i, guint32 **ptr, int j)
1585 (*ptr)[1] += i + j;
1587 return 0;
1590 STDCALL void*
1591 mono_test_marshal_pass_return_custom2 (int i, guint32 *ptr, int j)
1593 g_assert_not_reached ();
1595 return NULL;
1598 STDCALL void*
1599 mono_test_marshal_pass_return_custom_null (int i, guint32 *ptr, int j)
1601 g_assert (ptr == NULL);
1603 return NULL;
1606 typedef void *(STDCALL *PassReturnPtrDelegate) (void *ptr);
1608 STDCALL int
1609 mono_test_marshal_pass_return_custom_in_delegate (PassReturnPtrDelegate del)
1611 guint32 buf [2];
1612 guint32 res;
1613 guint32 *ptr;
1615 buf [0] = 0;
1616 buf [1] = 10;
1618 ptr = del (&buf);
1620 res = ptr [1];
1622 #ifdef WIN32
1623 /* FIXME: Freed with FreeHGlobal */
1624 #else
1625 g_free (ptr);
1626 #endif
1628 return res;
1631 STDCALL int
1632 mono_test_marshal_pass_return_custom_null_in_delegate (PassReturnPtrDelegate del)
1634 void *ptr = del (NULL);
1636 return (ptr == NULL) ? 15 : 0;
1639 typedef void (STDCALL *CustomOutParamDelegate) (void **pptr);
1641 STDCALL int
1642 mono_test_marshal_custom_out_param_delegate (CustomOutParamDelegate del)
1644 void* pptr = del;
1646 del (&pptr);
1648 if(pptr != NULL)
1649 return 1;
1651 return 0;
1654 typedef int (STDCALL *ReturnEnumDelegate) (int e);
1656 STDCALL int
1657 mono_test_marshal_return_enum_delegate (ReturnEnumDelegate func)
1659 return func (1);
1662 typedef struct {
1663 int a, b, c;
1664 gint64 d;
1665 } BlittableStruct;
1667 typedef BlittableStruct (STDCALL *SimpleDelegate10) (BlittableStruct ss);
1669 STDCALL int
1670 mono_test_marshal_blittable_struct_delegate (SimpleDelegate10 delegate)
1672 BlittableStruct ss, res;
1674 ss.a = 1;
1675 ss.b = 2;
1676 ss.c = 3;
1677 ss.d = 55;
1679 res = delegate (ss);
1680 if (! ((res.a == -1) && (res.b == -2) && (res.c == -3) && (res.d == -55)))
1681 return 1;
1683 return 0;
1686 STDCALL int
1687 mono_test_stdcall_name_mangling (int a, int b, int c)
1689 return a + b + c;
1693 * PASSING AND RETURNING SMALL STRUCTURES FROM DELEGATES TESTS
1696 typedef struct {
1697 int i;
1698 } SmallStruct1;
1700 typedef SmallStruct1 (STDCALL *SmallStructDelegate1) (SmallStruct1 ss);
1702 STDCALL int
1703 mono_test_marshal_small_struct_delegate1 (SmallStructDelegate1 delegate)
1705 SmallStruct1 ss, res;
1707 ss.i = 1;
1709 res = delegate (ss);
1710 if (! (res.i == -1))
1711 return 1;
1713 return 0;
1716 typedef struct {
1717 gint16 i, j;
1718 } SmallStruct2;
1720 typedef SmallStruct2 (STDCALL *SmallStructDelegate2) (SmallStruct2 ss);
1722 STDCALL int
1723 mono_test_marshal_small_struct_delegate2 (SmallStructDelegate2 delegate)
1725 SmallStruct2 ss, res;
1727 ss.i = 2;
1728 ss.j = 3;
1730 res = delegate (ss);
1731 if (! ((res.i == -2) && (res.j == -3)))
1732 return 1;
1734 return 0;
1737 typedef struct {
1738 gint16 i;
1739 gint8 j;
1740 } SmallStruct3;
1742 typedef SmallStruct3 (STDCALL *SmallStructDelegate3) (SmallStruct3 ss);
1744 STDCALL int
1745 mono_test_marshal_small_struct_delegate3 (SmallStructDelegate3 delegate)
1747 SmallStruct3 ss, res;
1749 ss.i = 1;
1750 ss.j = 2;
1752 res = delegate (ss);
1753 if (! ((res.i == -1) && (res.j == -2)))
1754 return 1;
1756 return 0;
1759 typedef struct {
1760 gint16 i;
1761 } SmallStruct4;
1763 typedef SmallStruct4 (STDCALL *SmallStructDelegate4) (SmallStruct4 ss);
1765 STDCALL int
1766 mono_test_marshal_small_struct_delegate4 (SmallStructDelegate4 delegate)
1768 SmallStruct4 ss, res;
1770 ss.i = 1;
1772 res = delegate (ss);
1773 if (! (res.i == -1))
1774 return 1;
1776 return 0;
1779 typedef struct {
1780 gint64 i;
1781 } SmallStruct5;
1783 typedef SmallStruct5 (STDCALL *SmallStructDelegate5) (SmallStruct5 ss);
1785 STDCALL int
1786 mono_test_marshal_small_struct_delegate5 (SmallStructDelegate5 delegate)
1788 SmallStruct5 ss, res;
1790 ss.i = 5;
1792 res = delegate (ss);
1793 if (! (res.i == -5))
1794 return 1;
1796 return 0;
1799 typedef struct {
1800 int i, j;
1801 } SmallStruct6;
1803 typedef SmallStruct6 (STDCALL *SmallStructDelegate6) (SmallStruct6 ss);
1805 STDCALL int
1806 mono_test_marshal_small_struct_delegate6 (SmallStructDelegate6 delegate)
1808 SmallStruct6 ss, res;
1810 ss.i = 1;
1811 ss.j = 2;
1813 res = delegate (ss);
1814 if (! ((res.i == -1) && (res.j == -2)))
1815 return 1;
1817 return 0;
1820 typedef struct {
1821 int i;
1822 gint16 j;
1823 } SmallStruct7;
1825 typedef SmallStruct7 (STDCALL *SmallStructDelegate7) (SmallStruct7 ss);
1827 STDCALL int
1828 mono_test_marshal_small_struct_delegate7 (SmallStructDelegate7 delegate)
1830 SmallStruct7 ss, res;
1832 ss.i = 1;
1833 ss.j = 2;
1835 res = delegate (ss);
1836 if (! ((res.i == -1) && (res.j == -2)))
1837 return 1;
1839 return 0;
1842 typedef struct {
1843 float i;
1844 } SmallStruct8;
1846 typedef SmallStruct8 (STDCALL *SmallStructDelegate8) (SmallStruct8 ss);
1848 STDCALL int
1849 mono_test_marshal_small_struct_delegate8 (SmallStructDelegate8 delegate)
1851 SmallStruct8 ss, res;
1853 ss.i = 1.0;
1855 res = delegate (ss);
1856 if (! ((res.i == -1.0)))
1857 return 1;
1859 return 0;
1862 typedef struct {
1863 double i;
1864 } SmallStruct9;
1866 typedef SmallStruct9 (STDCALL *SmallStructDelegate9) (SmallStruct9 ss);
1868 STDCALL int
1869 mono_test_marshal_small_struct_delegate9 (SmallStructDelegate9 delegate)
1871 SmallStruct9 ss, res;
1873 ss.i = 1.0;
1875 res = delegate (ss);
1876 if (! ((res.i == -1.0)))
1877 return 1;
1879 return 0;
1882 typedef struct {
1883 float i, j;
1884 } SmallStruct10;
1886 typedef SmallStruct10 (STDCALL *SmallStructDelegate10) (SmallStruct10 ss);
1888 STDCALL int
1889 mono_test_marshal_small_struct_delegate10 (SmallStructDelegate10 delegate)
1891 SmallStruct10 ss, res;
1893 ss.i = 1.0;
1894 ss.j = 2.0;
1896 res = delegate (ss);
1897 if (! ((res.i == -1.0) && (res.j == -2.0)))
1898 return 1;
1900 return 0;
1903 typedef struct {
1904 float i;
1905 int j;
1906 } SmallStruct11;
1908 typedef SmallStruct11 (STDCALL *SmallStructDelegate11) (SmallStruct11 ss);
1910 STDCALL int
1911 mono_test_marshal_small_struct_delegate11 (SmallStructDelegate11 delegate)
1913 SmallStruct11 ss, res;
1915 ss.i = 1.0;
1916 ss.j = 2;
1918 res = delegate (ss);
1919 if (! ((res.i == -1.0) && (res.j == -2)))
1920 return 1;
1922 return 0;
1925 typedef int (STDCALL *ArrayDelegate) (int i, char *j, void *arr);
1927 STDCALL int
1928 mono_test_marshal_array_delegate (void *arr, int len, ArrayDelegate del)
1930 return del (len, NULL, arr);
1933 STDCALL int
1934 mono_test_marshal_out_array_delegate (int *arr, int len, ArrayDelegate del)
1936 del (len, NULL, arr);
1938 if ((arr [0] != 1) || (arr [1] != 2))
1939 return 1;
1940 else
1941 return 0;
1944 typedef gunichar2* (STDCALL *UnicodeStringDelegate) (gunichar2 *message);
1946 STDCALL int
1947 mono_test_marshal_return_unicode_string_delegate (UnicodeStringDelegate del)
1949 const char m[] = "abcdef";
1950 gunichar2 *s2, *res;
1951 glong len;
1953 s2 = g_utf8_to_utf16 (m, -1, NULL, &len, NULL);
1955 res = del (s2);
1957 marshal_free (res);
1959 return 0;
1962 STDCALL int
1963 mono_test_marshal_out_string_array_delegate (char **arr, int len, ArrayDelegate del)
1965 del (len, NULL, arr);
1967 if (!strcmp (arr [0], "ABC") && !strcmp (arr [1], "DEF"))
1968 return 0;
1969 else
1970 return 1;
1973 typedef int (*CdeclDelegate) (int i, int j);
1975 STDCALL int
1976 mono_test_marshal_cdecl_delegate (CdeclDelegate del)
1978 int i;
1980 for (i = 0; i < 1000; ++i)
1981 del (1, 2);
1983 return 0;
1986 typedef char** (*ReturnStringArrayDelegate) (int i);
1988 STDCALL int
1989 mono_test_marshal_return_string_array_delegate (ReturnStringArrayDelegate d)
1991 char **arr = d (2);
1992 int res;
1994 if (arr == NULL)
1995 return 3;
1997 if (strcmp (arr [0], "ABC") || strcmp (arr [1], "DEF"))
1998 res = 1;
1999 else
2000 res = 0;
2002 marshal_free (arr);
2004 return res;
2007 STDCALL int
2008 add_delegate (int i, int j)
2010 return i + j;
2013 STDCALL gpointer
2014 mono_test_marshal_return_fnptr (void)
2016 return &add_delegate;
2019 STDCALL int
2020 mono_xr (int code)
2022 printf ("codigo %x\n", code);
2023 return code + 1234;
2026 typedef struct {
2027 int handle;
2028 } HandleRef;
2030 STDCALL HandleRef
2031 mono_xr_as_handle (int code)
2033 HandleRef ref;
2035 return ref;
2038 typedef struct {
2039 int a;
2040 void *handle1;
2041 void *handle2;
2042 int b;
2043 } HandleStructs;
2045 STDCALL int
2046 mono_safe_handle_struct_ref (HandleStructs *x)
2048 printf ("Dingus Ref! \n");
2049 printf ("Values: %d %d %d %d\n", x->a, x->b, x->handle1, x->handle2);
2050 if (x->a != 1234)
2051 return 1;
2052 if (x->b != 8743)
2053 return 2;
2055 if (x->handle1 != (void*) 0x7080feed)
2056 return 3;
2058 if (x->handle2 != (void*) 0x1234abcd)
2059 return 4;
2061 return 0xf00d;
2064 STDCALL int
2065 mono_safe_handle_struct (HandleStructs x)
2067 printf ("Dingus Standard! \n");
2068 printf ("Values: %d %d %d %d\n", x.a, x.b, x.handle1, x.handle2);
2069 if (x.a != 1234)
2070 return 1;
2071 if (x.b != 8743)
2072 return 2;
2074 if (x.handle1 != (void*) 0x7080feed)
2075 return 3;
2077 if (x.handle2 != (void*) 0x1234abcd)
2078 return 4;
2080 return 0xf00f;
2083 typedef struct {
2084 void *a;
2085 } TrivialHandle;
2087 STDCALL int
2088 mono_safe_handle_struct_simple (TrivialHandle x)
2090 printf ("The value is %d\n", x.a);
2091 return ((int)x.a) * 2;
2094 STDCALL int
2095 mono_safe_handle_return ()
2097 return 0x1000f00d;
2100 STDCALL void
2101 mono_safe_handle_ref (void **handle)
2103 if (*handle != 0){
2104 *handle = (void *) 0xbad;
2105 return;
2108 *handle = (void *) 0x800d;
2111 * COM INTEROP TESTS
2114 #ifdef WIN32
2116 STDCALL int
2117 mono_test_marshal_bstr_in(BSTR bstr)
2119 if (!wcscmp(bstr, L"mono_test_marshal_bstr_in"))
2120 return 0;
2121 return 1;
2124 STDCALL int
2125 mono_test_marshal_bstr_out(BSTR* bstr)
2127 *bstr = SysAllocString(L"mono_test_marshal_bstr_out");
2128 return 0;
2131 STDCALL int
2132 mono_test_marshal_bstr_in_null(BSTR bstr)
2134 if (!bstr)
2135 return 0;
2136 return 1;
2139 STDCALL int
2140 mono_test_marshal_bstr_out_null(BSTR* bstr)
2142 *bstr = NULL;
2143 return 0;
2146 STDCALL int
2147 mono_test_marshal_variant_in_sbyte(VARIANT variant)
2149 if (variant.vt == VT_I1 && variant.cVal == 100)
2150 return 0;
2151 return 1;
2154 STDCALL int
2155 mono_test_marshal_variant_in_byte(VARIANT variant)
2157 if (variant.vt == VT_UI1 && variant.bVal == 100)
2158 return 0;
2159 return 1;
2162 STDCALL int
2163 mono_test_marshal_variant_in_short(VARIANT variant)
2165 if (variant.vt == VT_I2 && variant.iVal == 314)
2166 return 0;
2167 return 1;
2170 STDCALL int
2171 mono_test_marshal_variant_in_ushort(VARIANT variant)
2173 if (variant.vt == VT_UI2 && variant.uiVal == 314)
2174 return 0;
2175 return 1;
2178 STDCALL int
2179 mono_test_marshal_variant_in_int(VARIANT variant)
2181 if (variant.vt == VT_I4 && variant.lVal == 314)
2182 return 0;
2183 return 1;
2186 STDCALL int
2187 mono_test_marshal_variant_in_uint(VARIANT variant)
2189 if (variant.vt == VT_UI4 && variant.ulVal == 314)
2190 return 0;
2191 return 1;
2194 STDCALL int
2195 mono_test_marshal_variant_in_long(VARIANT variant)
2197 if (variant.vt == VT_I8 && variant.llVal == 314)
2198 return 0;
2199 return 1;
2202 STDCALL int
2203 mono_test_marshal_variant_in_ulong(VARIANT variant)
2205 if (variant.vt == VT_UI8 && variant.ullVal == 314)
2206 return 0;
2207 return 1;
2210 STDCALL int
2211 mono_test_marshal_variant_in_float(VARIANT variant)
2213 if (variant.vt == VT_R4 && (variant.fltVal - 3.14)/3.14 < .001)
2214 return 0;
2215 return 1;
2218 STDCALL int
2219 mono_test_marshal_variant_in_double(VARIANT variant)
2221 if (variant.vt == VT_R8 && (variant.dblVal - 3.14)/3.14 < .001)
2222 return 0;
2223 return 1;
2226 STDCALL int
2227 mono_test_marshal_variant_in_bstr(VARIANT variant)
2229 if (variant.vt == VT_BSTR && !wcscmp(variant.bstrVal, L"PI"))
2230 return 0;
2231 return 1;
2234 STDCALL int
2235 mono_test_marshal_variant_in_bool_true (VARIANT variant)
2237 if (variant.vt == VT_BOOL && variant.boolVal == VARIANT_TRUE)
2238 return 0;
2239 return 1;
2242 STDCALL int
2243 mono_test_marshal_variant_in_bool_false (VARIANT variant)
2245 if (variant.vt == VT_BOOL && variant.boolVal == VARIANT_FALSE)
2246 return 0;
2247 return 1;
2250 STDCALL int
2251 mono_test_marshal_variant_out_sbyte(VARIANT* variant)
2253 variant->vt = VT_I1;
2254 variant->cVal = 100;
2256 return 0;
2259 STDCALL int
2260 mono_test_marshal_variant_out_byte(VARIANT* variant)
2262 variant->vt = VT_UI1;
2263 variant->bVal = 100;
2265 return 0;
2268 STDCALL int
2269 mono_test_marshal_variant_out_short(VARIANT* variant)
2271 variant->vt = VT_I2;
2272 variant->iVal = 314;
2274 return 0;
2277 STDCALL int
2278 mono_test_marshal_variant_out_ushort(VARIANT* variant)
2280 variant->vt = VT_UI2;
2281 variant->uiVal = 314;
2283 return 0;
2286 STDCALL int
2287 mono_test_marshal_variant_out_int(VARIANT* variant)
2289 variant->vt = VT_I4;
2290 variant->lVal = 314;
2292 return 0;
2295 STDCALL int
2296 mono_test_marshal_variant_out_uint(VARIANT* variant)
2298 variant->vt = VT_UI4;
2299 variant->ulVal = 314;
2301 return 0;
2304 STDCALL int
2305 mono_test_marshal_variant_out_long(VARIANT* variant)
2307 variant->vt = VT_I8;
2308 variant->llVal = 314;
2310 return 0;
2313 STDCALL int
2314 mono_test_marshal_variant_out_ulong(VARIANT* variant)
2316 variant->vt = VT_UI8;
2317 variant->ullVal = 314;
2319 return 0;
2322 STDCALL int
2323 mono_test_marshal_variant_out_float(VARIANT* variant)
2325 variant->vt = VT_R4;
2326 variant->fltVal = 3.14;
2328 return 0;
2331 STDCALL int
2332 mono_test_marshal_variant_out_double(VARIANT* variant)
2334 variant->vt = VT_R8;
2335 variant->dblVal = 3.14;
2337 return 0;
2340 STDCALL int
2341 mono_test_marshal_variant_out_bstr(VARIANT* variant)
2343 variant->vt = VT_BSTR;
2344 variant->bstrVal = SysAllocString(L"PI");
2346 return 0;
2349 STDCALL int
2350 mono_test_marshal_variant_out_bool_true (VARIANT* variant)
2352 variant->vt = VT_BOOL;
2353 variant->boolVal = VARIANT_TRUE;
2355 return 0;
2358 STDCALL int
2359 mono_test_marshal_variant_out_bool_false (VARIANT* variant)
2361 variant->vt = VT_BOOL;
2362 variant->boolVal = VARIANT_FALSE;
2364 return 0;
2367 typedef int (STDCALL *VarFunc) (int vt, VARIANT variant);
2368 typedef int (STDCALL *VarRefFunc) (int vt, VARIANT* variant);
2370 STDCALL int
2371 mono_test_marshal_variant_in_sbyte_unmanaged(VarFunc func)
2373 VARIANT vt;
2374 vt.vt = VT_I1;
2375 vt.cVal = -100;
2376 return func (VT_I1, vt);
2379 STDCALL int
2380 mono_test_marshal_variant_in_byte_unmanaged(VarFunc func)
2382 VARIANT vt;
2383 vt.vt = VT_UI1;
2384 vt.bVal = 100;
2385 return func (VT_UI1, vt);
2388 STDCALL int
2389 mono_test_marshal_variant_in_short_unmanaged(VarFunc func)
2391 VARIANT vt;
2392 vt.vt = VT_I2;
2393 vt.iVal = -100;
2394 return func (VT_I2, vt);
2397 STDCALL int
2398 mono_test_marshal_variant_in_ushort_unmanaged(VarFunc func)
2400 VARIANT vt;
2401 vt.vt = VT_UI2;
2402 vt.uiVal = 100;
2403 return func (VT_UI2, vt);
2406 STDCALL int
2407 mono_test_marshal_variant_in_int_unmanaged(VarFunc func)
2409 VARIANT vt;
2410 vt.vt = VT_I4;
2411 vt.lVal = -100;
2412 return func (VT_I4, vt);
2415 STDCALL int
2416 mono_test_marshal_variant_in_uint_unmanaged(VarFunc func)
2418 VARIANT vt;
2419 vt.vt = VT_UI4;
2420 vt.ulVal = 100;
2421 return func (VT_UI4, vt);
2424 STDCALL int
2425 mono_test_marshal_variant_in_long_unmanaged(VarFunc func)
2427 VARIANT vt;
2428 vt.vt = VT_I8;
2429 vt.llVal = -100;
2430 return func (VT_I8, vt);
2433 STDCALL int
2434 mono_test_marshal_variant_in_ulong_unmanaged(VarFunc func)
2436 VARIANT vt;
2437 vt.vt = VT_UI8;
2438 vt.ullVal = 100;
2439 return func (VT_UI8, vt);
2442 STDCALL int
2443 mono_test_marshal_variant_in_float_unmanaged(VarFunc func)
2445 VARIANT vt;
2446 vt.vt = VT_R4;
2447 vt.fltVal = 3.14;
2448 return func (VT_R4, vt);
2451 STDCALL int
2452 mono_test_marshal_variant_in_double_unmanaged(VarFunc func)
2454 VARIANT vt;
2455 vt.vt = VT_R8;
2456 vt.dblVal = 3.14;
2457 return func (VT_R8, vt);
2460 STDCALL int
2461 mono_test_marshal_variant_in_bstr_unmanaged(VarFunc func)
2463 VARIANT vt;
2464 vt.vt = VT_BSTR;
2465 vt.bstrVal = SysAllocString(L"PI");
2466 return func (VT_BSTR, vt);
2469 STDCALL int
2470 mono_test_marshal_variant_in_bool_true_unmanaged(VarFunc func)
2472 VARIANT vt;
2473 vt.vt = VT_BOOL;
2474 vt.boolVal = VARIANT_TRUE;
2475 return func (VT_BOOL, vt);
2478 STDCALL int
2479 mono_test_marshal_variant_in_bool_false_unmanaged(VarFunc func)
2481 VARIANT vt;
2482 vt.vt = VT_BOOL;
2483 vt.boolVal = VARIANT_FALSE;
2484 return func (VT_BOOL, vt);
2487 STDCALL int
2488 mono_test_marshal_variant_out_sbyte_unmanaged(VarRefFunc func)
2490 VARIANT vt;
2491 VariantInit (&vt);
2492 func (VT_I1, &vt);
2493 if (vt.vt == VT_I1 && vt.cVal == -100)
2494 return 0;
2495 return 1;
2498 STDCALL int
2499 mono_test_marshal_variant_out_byte_unmanaged(VarRefFunc func)
2501 VARIANT vt;
2502 VariantInit (&vt);
2503 func (VT_UI1, &vt);
2504 if (vt.vt == VT_UI1 && vt.bVal == 100)
2505 return 0;
2506 return 1;
2509 STDCALL int
2510 mono_test_marshal_variant_out_short_unmanaged(VarRefFunc func)
2512 VARIANT vt;
2513 VariantInit (&vt);
2514 func (VT_I2, &vt);
2515 if (vt.vt == VT_I2 && vt.iVal == -100)
2516 return 0;
2517 return 1;
2520 STDCALL int
2521 mono_test_marshal_variant_out_ushort_unmanaged(VarRefFunc func)
2523 VARIANT vt;
2524 VariantInit (&vt);
2525 func (VT_UI2, &vt);
2526 if (vt.vt == VT_UI2 && vt.uiVal == 100)
2527 return 0;
2528 return 1;
2531 STDCALL int
2532 mono_test_marshal_variant_out_int_unmanaged(VarRefFunc func)
2534 VARIANT vt;
2535 VariantInit (&vt);
2536 func (VT_I4, &vt);
2537 if (vt.vt == VT_I4 && vt.lVal == -100)
2538 return 0;
2539 return 1;
2542 STDCALL int
2543 mono_test_marshal_variant_out_uint_unmanaged(VarRefFunc func)
2545 VARIANT vt;
2546 VariantInit (&vt);
2547 func (VT_UI4, &vt);
2548 if (vt.vt == VT_UI4 && vt.ulVal == 100)
2549 return 0;
2550 return 1;
2553 STDCALL int
2554 mono_test_marshal_variant_out_long_unmanaged(VarRefFunc func)
2556 VARIANT vt;
2557 VariantInit (&vt);
2558 func (VT_I8, &vt);
2559 if (vt.vt == VT_I8 && vt.llVal == -100)
2560 return 0;
2561 return 1;
2564 STDCALL int
2565 mono_test_marshal_variant_out_ulong_unmanaged(VarRefFunc func)
2567 VARIANT vt;
2568 VariantInit (&vt);
2569 func (VT_UI8, &vt);
2570 if (vt.vt == VT_UI8 && vt.ullVal == 100)
2571 return 0;
2572 return 1;
2575 STDCALL int
2576 mono_test_marshal_variant_out_float_unmanaged(VarRefFunc func)
2578 VARIANT vt;
2579 VariantInit (&vt);
2580 func (VT_R4, &vt);
2581 if (vt.vt == VT_R4 && fabs (vt.fltVal - 3.14f) < 1e-10)
2582 return 0;
2583 return 1;
2586 STDCALL int
2587 mono_test_marshal_variant_out_double_unmanaged(VarRefFunc func)
2589 VARIANT vt;
2590 VariantInit (&vt);
2591 func (VT_R8, &vt);
2592 if (vt.vt == VT_R8 && fabs (vt.dblVal - 3.14) < 1e-10)
2593 return 0;
2594 return 1;
2597 STDCALL int
2598 mono_test_marshal_variant_out_bstr_unmanaged(VarRefFunc func)
2600 VARIANT vt;
2601 VariantInit (&vt);
2602 func (VT_BSTR, &vt);
2603 if (vt.vt == VT_BSTR && !wcscmp(vt.bstrVal, L"PI"))
2604 return 0;
2605 return 1;
2608 STDCALL int
2609 mono_test_marshal_variant_out_bool_true_unmanaged(VarRefFunc func)
2611 VARIANT vt;
2612 VariantInit (&vt);
2613 func (VT_BOOL, &vt);
2614 if (vt.vt == VT_BOOL && vt.boolVal == VARIANT_TRUE)
2615 return 0;
2616 return 1;
2619 STDCALL int
2620 mono_test_marshal_variant_out_bool_false_unmanaged(VarRefFunc func)
2622 VARIANT vt;
2623 VariantInit (&vt);
2624 func (VT_BOOL, &vt);
2625 if (vt.vt == VT_BOOL && vt.boolVal == VARIANT_TRUE)
2626 return 0;
2627 return 1;
2630 typedef struct MonoComObject MonoComObject;
2632 typedef struct
2634 int (STDCALL *QueryInterface)(MonoComObject* pUnk, gpointer riid, gpointer* ppv);
2635 int (STDCALL *AddRef)(MonoComObject* pUnk);
2636 int (STDCALL *Release)(MonoComObject* pUnk);
2637 int (STDCALL *get_ITest)(MonoComObject* pUnk, MonoComObject* *ppUnk);
2638 int (STDCALL *SByteIn)(MonoComObject* pUnk, char a);
2639 int (STDCALL *ByteIn)(MonoComObject* pUnk, unsigned char a);
2640 int (STDCALL *ShortIn)(MonoComObject* pUnk, short a);
2641 int (STDCALL *UShortIn)(MonoComObject* pUnk, unsigned short a);
2642 int (STDCALL *IntIn)(MonoComObject* pUnk, int a);
2643 int (STDCALL *UIntIn)(MonoComObject* pUnk, unsigned int a);
2644 int (STDCALL *LongIn)(MonoComObject* pUnk, LONGLONG a);
2645 int (STDCALL *ULongIn)(MonoComObject* pUnk, ULONGLONG a);
2646 int (STDCALL *FloatIn)(MonoComObject* pUnk, float a);
2647 int (STDCALL *DoubleIn)(MonoComObject* pUnk, double a);
2648 int (STDCALL *ITestIn)(MonoComObject* pUnk, MonoComObject* pUnk2);
2649 int (STDCALL *ITestOut)(MonoComObject* pUnk, MonoComObject* *ppUnk);
2650 } MonoIUnknown;
2652 struct MonoComObject
2654 MonoIUnknown* vtbl;
2655 int m_ref;
2658 DEFINE_GUID(IID_ITest, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1);
2659 DEFINE_GUID(IID_IMonoUnknown, 0, 0, 0, 0xC0, 0, 0, 0, 0, 0, 0, 0x46);
2660 DEFINE_GUID(IID_IMonoDispatch, 0x00020400, 0, 0, 0xC0, 0, 0, 0, 0, 0, 0, 0x46);
2662 int STDCALL MonoQueryInterface(MonoComObject* pUnk, gpointer riid, gpointer* ppv)
2664 *ppv = NULL;
2665 if (!memcmp(riid, &IID_IMonoUnknown, sizeof(GUID))) {
2666 *ppv = pUnk;
2667 return S_OK;
2669 else if (!memcmp(riid, &IID_ITest, sizeof(GUID))) {
2670 *ppv = pUnk;
2671 return S_OK;
2673 else if (!memcmp(riid, &IID_IMonoDispatch, sizeof(GUID))) {
2674 *ppv = pUnk;
2675 return S_OK;
2677 return E_NOINTERFACE;
2680 int STDCALL MonoAddRef(MonoComObject* pUnk)
2682 return ++(pUnk->m_ref);
2685 int STDCALL MonoRelease(MonoComObject* pUnk)
2687 return --(pUnk->m_ref);
2690 int STDCALL SByteIn(MonoComObject* pUnk, char a)
2692 return S_OK;
2695 int STDCALL ByteIn(MonoComObject* pUnk, unsigned char a)
2697 return S_OK;
2700 int STDCALL ShortIn(MonoComObject* pUnk, short a)
2702 return S_OK;
2705 int STDCALL UShortIn(MonoComObject* pUnk, unsigned short a)
2707 return S_OK;
2710 int STDCALL IntIn(MonoComObject* pUnk, int a)
2712 return S_OK;
2715 int STDCALL UIntIn(MonoComObject* pUnk, unsigned int a)
2717 return S_OK;
2720 int STDCALL LongIn(MonoComObject* pUnk, LONGLONG a)
2722 return S_OK;
2725 int STDCALL ULongIn(MonoComObject* pUnk, ULONGLONG a)
2727 return S_OK;
2730 int STDCALL FloatIn(MonoComObject* pUnk, float a)
2732 return S_OK;
2735 int STDCALL DoubleIn(MonoComObject* pUnk, double a)
2737 return S_OK;
2740 int STDCALL ITestIn(MonoComObject* pUnk, MonoComObject *pUnk2)
2742 return S_OK;
2745 int STDCALL ITestOut(MonoComObject* pUnk, MonoComObject* *ppUnk)
2747 return S_OK;
2750 int STDCALL get_ITest(MonoComObject* pUnk, MonoComObject* *ppUnk)
2752 return S_OK;
2755 static void create_com_object (MonoComObject** pOut)
2757 *pOut = g_new0 (MonoComObject, 1);
2758 (*pOut)->vtbl = g_new0 (MonoIUnknown, 1);
2760 (*pOut)->m_ref = 1;
2761 (*pOut)->vtbl->QueryInterface = MonoQueryInterface;
2762 (*pOut)->vtbl->AddRef = MonoAddRef;
2763 (*pOut)->vtbl->Release = MonoRelease;
2764 (*pOut)->vtbl->SByteIn = SByteIn;
2765 (*pOut)->vtbl->ByteIn = ByteIn;
2766 (*pOut)->vtbl->ShortIn = ShortIn;
2767 (*pOut)->vtbl->UShortIn = UShortIn;
2768 (*pOut)->vtbl->IntIn = IntIn;
2769 (*pOut)->vtbl->UIntIn = UIntIn;
2770 (*pOut)->vtbl->LongIn = LongIn;
2771 (*pOut)->vtbl->ULongIn = ULongIn;
2772 (*pOut)->vtbl->FloatIn = FloatIn;
2773 (*pOut)->vtbl->DoubleIn = DoubleIn;
2774 (*pOut)->vtbl->ITestIn = ITestIn;
2775 (*pOut)->vtbl->ITestOut = ITestOut;
2776 (*pOut)->vtbl->get_ITest = get_ITest;
2779 static MonoComObject* same_object = NULL;
2781 STDCALL int
2782 mono_test_marshal_com_object_create(MonoComObject* *pUnk)
2784 create_com_object (pUnk);
2786 if (!same_object)
2787 same_object = *pUnk;
2789 return 0;
2792 STDCALL int
2793 mono_test_marshal_com_object_same(MonoComObject* *pUnk)
2795 *pUnk = same_object;
2797 return 0;
2800 STDCALL int
2801 mono_test_marshal_com_object_destroy(MonoComObject *pUnk)
2803 int ref = --(pUnk->m_ref);
2804 g_free(pUnk->vtbl);
2805 g_free(pUnk);
2807 return ref;
2810 STDCALL int
2811 mono_test_marshal_com_object_ref_count(MonoComObject *pUnk)
2813 return pUnk->m_ref;
2816 STDCALL int
2817 mono_test_marshal_ccw_itest (MonoComObject *pUnk)
2819 int hr = 0;
2820 MonoComObject* pTest;
2822 if (!pUnk)
2823 return 1;
2825 hr = pUnk->vtbl->SByteIn (pUnk, -100);
2826 if (hr != 0)
2827 return 2;
2828 hr = pUnk->vtbl->ByteIn (pUnk, 100);
2829 if (hr != 0)
2830 return 3;
2831 hr = pUnk->vtbl->ShortIn (pUnk, -100);
2832 if (hr != 0)
2833 return 4;
2834 hr = pUnk->vtbl->UShortIn (pUnk, 100);
2835 if (hr != 0)
2836 return 5;
2837 hr = pUnk->vtbl->IntIn (pUnk, -100);
2838 if (hr != 0)
2839 return 6;
2840 hr = pUnk->vtbl->UIntIn (pUnk, 100);
2841 if (hr != 0)
2842 return 7;
2843 hr = pUnk->vtbl->LongIn (pUnk, -100);
2844 if (hr != 0)
2845 return 8;
2846 hr = pUnk->vtbl->ULongIn (pUnk, 100);
2847 if (hr != 0)
2848 return 9;
2849 hr = pUnk->vtbl->FloatIn (pUnk, 3.14f);
2850 if (hr != 0)
2851 return 10;
2852 hr = pUnk->vtbl->DoubleIn (pUnk, 3.14);
2853 if (hr != 0)
2854 return 11;
2855 hr = pUnk->vtbl->ITestIn (pUnk, pUnk);
2856 if (hr != 0)
2857 return 12;
2858 hr = pUnk->vtbl->ITestOut (pUnk, &pTest);
2859 if (hr != 0)
2860 return 13;
2862 return 0;
2866 #endif //NOT_YET