1 USING: accessors alien alien.c-types alien.libraries
2 alien.syntax arrays classes.struct combinators
3 compiler continuations destructors effects generalizations io
4 io.backend io.pathnames io.streams.string kernel
5 math memory namespaces namespaces.private parser
6 quotations sequences specialized-arrays stack-checker
7 stack-checker.errors system threads tools.test words
8 alien.complex concurrency.promises alien.data
9 byte-arrays classes compiler.test libc layouts
11 FROM: alien.c-types => float short ;
12 SPECIALIZED-ARRAY: float
13 SPECIALIZED-ARRAY: char
14 IN: compiler.tests.alien
16 ! Make sure that invalid inputs don't pass the stack checker
17 [ [ void { } "cdecl" alien-indirect ] infer ] must-fail
18 [ [ "void" { } cdecl alien-indirect ] infer ] must-fail
19 [ [ void* 3 cdecl alien-indirect ] infer ] must-fail
20 [ [ void* { "int" } cdecl alien-indirect ] infer ] must-fail
21 [ [ void* { int } cdecl { } alien-callback ] infer ] must-fail
24 : libfactor-ffi-tests-path ( -- string )
25 "resource:" absolute-path
27 { [ os windows? ] [ "libfactor-ffi-test.dll" ] }
28 { [ os macosx? ] [ "libfactor-ffi-test.dylib" ] }
29 { [ os unix? ] [ "libfactor-ffi-test.so" ] }
32 : mingw? ( -- ? ) os windows? vm-compiler "GCC" head? and ;
34 "f-cdecl" libfactor-ffi-tests-path mingw? mingw cdecl ? add-library
36 "f-stdcall" libfactor-ffi-tests-path stdcall add-library
38 "f-fastcall" libfactor-ffi-tests-path fastcall add-library
43 FUNCTION: void ffi_test_0 ;
44 [ ] [ ffi_test_0 ] unit-test
46 FUNCTION: int ffi_test_1 ;
47 [ 3 ] [ ffi_test_1 ] unit-test
49 [ ] [ \ ffi_test_1 def>> [ drop ] append compile-call ] unit-test
51 FUNCTION: int ffi_test_2 int x int y ;
52 [ 5 ] [ 2 3 ffi_test_2 ] unit-test
53 [ "hi" 3 ffi_test_2 ] must-fail
55 FUNCTION: int ffi_test_3 int x int y int z int t ;
56 [ 25 ] [ 2 3 4 5 ffi_test_3 ] unit-test
58 FUNCTION: float ffi_test_4 ;
59 [ 1.5 ] [ ffi_test_4 ] unit-test
61 FUNCTION: double ffi_test_5 ;
62 [ 1.5 ] [ ffi_test_5 ] unit-test
64 FUNCTION: int ffi_test_9 int a int b int c int d int e int f int g ;
65 [ 28 ] [ 1 2 3 4 5 6 7 ffi_test_9 ] unit-test
66 [ "a" 2 3 4 5 6 7 ffi_test_9 ] must-fail
67 [ 1 2 3 4 5 6 "a" ffi_test_9 ] must-fail
69 STRUCT: FOO { x int } { y int } ;
71 : make-FOO ( x y -- FOO )
72 FOO <struct> swap >>y swap >>x ;
74 FUNCTION: int ffi_test_11 int a FOO b int c ;
76 [ 14 ] [ 1 2 3 make-FOO 4 ffi_test_11 ] unit-test
78 FUNCTION: int ffi_test_13 int a int b int c int d int e int f int g int h int i int j int k ;
80 [ 66 ] [ 1 2 3 4 5 6 7 8 9 10 11 ffi_test_13 ] unit-test
82 FUNCTION: FOO ffi_test_14 int x int y ;
84 [ 11 6 ] [ 11 6 ffi_test_14 [ x>> ] [ y>> ] bi ] unit-test
86 FUNCTION: c-string ffi_test_15 c-string x c-string y ;
88 [ "foo" ] [ "xy" "zt" ffi_test_15 ] unit-test
89 [ "bar" ] [ "xy" "xy" ffi_test_15 ] unit-test
90 [ 1 2 ffi_test_15 ] must-fail
92 STRUCT: BAR { x long } { y long } { z long } ;
94 FUNCTION: BAR ffi_test_16 long x long y long z ;
97 11 6 -7 ffi_test_16 [ x>> ] [ y>> ] [ z>> ] tri
100 STRUCT: TINY { x int } ;
102 FUNCTION: TINY ffi_test_17 int x ;
104 [ 11 ] [ 11 ffi_test_17 x>> ] unit-test
106 [ [ alien-indirect ] infer ] [ inference-error? ] must-fail-with
108 : indirect-test-1 ( ptr -- result )
109 int { } cdecl alien-indirect ;
111 { 1 1 } [ indirect-test-1 ] must-infer-as
113 [ 3 ] [ &: ffi_test_1 indirect-test-1 ] unit-test
115 : indirect-test-1' ( ptr -- )
116 int { } cdecl alien-indirect drop ;
118 { 1 0 } [ indirect-test-1' ] must-infer-as
120 [ ] [ &: ffi_test_1 indirect-test-1' ] unit-test
122 [ -1 indirect-test-1 ] must-fail
124 : indirect-test-2 ( x y ptr -- result )
125 int { int int } cdecl alien-indirect gc ;
127 { 3 1 } [ indirect-test-2 ] must-infer-as
130 [ 2 3 &: ffi_test_2 indirect-test-2 ]
133 : indirect-test-3 ( a b c d ptr -- result )
134 int { int int int int } stdcall alien-indirect
137 [ f ] [ "f-stdcall" load-library f = ] unit-test
138 [ stdcall ] [ "f-stdcall" lookup-library abi>> ] unit-test
140 : ffi_test_18 ( w x y z -- int )
141 int "f-stdcall" "ffi_test_18" { int int int int }
144 [ 25 ] [ 2 3 4 5 ffi_test_18 ] unit-test
146 : ffi_test_19 ( x y z -- BAR )
147 BAR "f-stdcall" "ffi_test_19" { long long long }
151 11 6 -7 ffi_test_19 [ x>> ] [ y>> ] [ z>> ] tri
154 : multi_ffi_test_18 ( w x y z w' x' y' z' -- int int )
155 [ int "f-stdcall" "ffi_test_18" { int int int int } alien-invoke ]
157 int "f-stdcall" "ffi_test_18" { int int int int } alien-invoke
160 [ 25 85 ] [ 2 3 4 5 6 7 8 9 multi_ffi_test_18 ] unit-test
162 FUNCTION: double ffi_test_6 float x float y ;
163 [ 6.0 ] [ 3.0 2.0 ffi_test_6 ] unit-test
164 [ "a" "b" ffi_test_6 ] must-fail
166 FUNCTION: double ffi_test_7 double x double y ;
167 [ 6.0 ] [ 3.0 2.0 ffi_test_7 ] unit-test
169 FUNCTION: double ffi_test_8 double x float y double z float t int w ;
170 [ 19.0 ] [ 3.0 2.0 1.0 6.0 7 ffi_test_8 ] unit-test
172 FUNCTION: int ffi_test_10 int a int b double c int d float e int f int g int h ;
173 [ -34 ] [ 1 2 3.0 4 5.0 6 7 8 ffi_test_10 ] unit-test
175 FUNCTION: void ffi_test_20 double x1, double x2, double x3,
176 double y1, double y2, double y3,
177 double z1, double z2, double z3 ;
179 [ ] [ 1.0 2.0 3.0 4.0 5.0 6.0 7.0 8.0 9.0 ffi_test_20 ] unit-test
181 ! Make sure XT doesn't get clobbered in stack frame
183 : ffi_test_31 ( a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a -- result y )
185 "f-cdecl" "ffi_test_31"
186 { int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int int }
189 [ 861 3 ] [ 42 [ ] each-integer ffi_test_31 ] unit-test
191 : ffi_test_31_point_5 ( a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a a -- result )
193 "f-cdecl" "ffi_test_31_point_5"
194 { float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float float }
197 [ 861.0 ] [ 42 [ >float ] each-integer ffi_test_31_point_5 ] unit-test
199 FUNCTION: longlong ffi_test_21 long x long y ;
201 [ 121932631112635269 ]
202 [ 123456789 987654321 ffi_test_21 ] unit-test
204 FUNCTION: long ffi_test_22 long x longlong y longlong z ;
207 [ 1111 121932631112635269 123456789 ffi_test_22 ] unit-test
209 [ 1111 f 123456789 ffi_test_22 ] must-fail
212 { x float } { y float }
213 { w float } { h float } ;
215 : <RECT> ( x y w h -- rect )
222 FUNCTION: int ffi_test_12 int a int b RECT c int d int e int f ;
224 [ 45 ] [ 1 2 3.0 4.0 5.0 6.0 <RECT> 7 8 9 ffi_test_12 ] unit-test
226 [ 1 2 { 1 2 3 } 7 8 9 ffi_test_12 ] must-fail
228 FUNCTION: float ffi_test_23 ( float[3] x, float[3] y ) ;
231 { 1.0 2.0 3.0 } float >c-array
232 { 4.0 5.0 6.0 } float >c-array
236 ! Test odd-size structs
237 STRUCT: test-struct-1 { x char[1] } ;
239 FUNCTION: test-struct-1 ffi_test_24 ;
241 [ S{ test-struct-1 { x char-array{ 1 } } } ] [ ffi_test_24 ] unit-test
243 STRUCT: test-struct-2 { x char[2] } ;
245 FUNCTION: test-struct-2 ffi_test_25 ;
247 [ S{ test-struct-2 { x char-array{ 1 2 } } } ] [ ffi_test_25 ] unit-test
249 STRUCT: test-struct-3 { x char[3] } ;
251 FUNCTION: test-struct-3 ffi_test_26 ;
253 [ S{ test-struct-3 { x char-array{ 1 2 3 } } } ] [ ffi_test_26 ] unit-test
255 STRUCT: test-struct-4 { x char[4] } ;
257 FUNCTION: test-struct-4 ffi_test_27 ;
259 [ S{ test-struct-4 { x char-array{ 1 2 3 4 } } } ] [ ffi_test_27 ] unit-test
261 STRUCT: test-struct-5 { x char[5] } ;
263 FUNCTION: test-struct-5 ffi_test_28 ;
265 [ S{ test-struct-5 { x char-array{ 1 2 3 4 5 } } } ] [ ffi_test_28 ] unit-test
267 STRUCT: test-struct-6 { x char[6] } ;
269 FUNCTION: test-struct-6 ffi_test_29 ;
271 [ S{ test-struct-6 { x char-array{ 1 2 3 4 5 6 } } } ] [ ffi_test_29 ] unit-test
273 STRUCT: test-struct-7 { x char[7] } ;
275 FUNCTION: test-struct-7 ffi_test_30 ;
277 [ S{ test-struct-7 { x char-array{ 1 2 3 4 5 6 7 } } } ] [ ffi_test_30 ] unit-test
279 STRUCT: test-struct-8 { x double } { y double } ;
281 FUNCTION: double ffi_test_32 test-struct-8 x int y ;
284 test-struct-8 <struct>
290 STRUCT: test-struct-9 { x float } { y float } ;
292 FUNCTION: double ffi_test_33 test-struct-9 x int y ;
295 test-struct-9 <struct>
301 STRUCT: test-struct-10 { x float } { y int } ;
303 FUNCTION: double ffi_test_34 test-struct-10 x int y ;
306 test-struct-10 <struct>
312 STRUCT: test-struct-11 { x int } { y int } ;
314 FUNCTION: double ffi_test_35 test-struct-11 x int y ;
317 test-struct-11 <struct>
323 STRUCT: test-struct-12 { a int } { x double } ;
325 : make-struct-12 ( x -- alien )
326 test-struct-12 <struct>
329 FUNCTION: double ffi_test_36 ( test-struct-12 x ) ;
331 [ 1.23456 ] [ 1.23456 make-struct-12 ffi_test_36 ] unit-test
333 FUNCTION: ulonglong ffi_test_38 ( ulonglong x, ulonglong y ) ;
335 [ t ] [ 31 2^ 32 2^ ffi_test_38 63 2^ = ] unit-test
338 : callback-throws ( -- x )
339 int { } cdecl [ "Hi" throw ] alien-callback ;
342 callback-throws [ alien? ] with-callback
345 : callback-1 ( -- callback ) void { } cdecl [ ] alien-callback ;
347 [ 0 1 ] [ [ callback-1 ] infer [ in>> length ] [ out>> length ] bi ] unit-test
349 { t } [ callback-1 [ alien? ] with-callback ] unit-test
351 : callback_test_1 ( ptr -- ) void { } cdecl alien-indirect ;
353 { } [ callback-1 [ callback_test_1 ] with-callback ] unit-test
355 : callback-2 ( -- callback ) void { } cdecl [ [ 5 throw ] ignore-errors ] alien-callback ;
357 { } [ callback-2 [ callback_test_1 ] with-callback ] unit-test
359 : callback-3 ( -- callback ) void { } cdecl [ 5 "x" set ] alien-callback ;
364 3 "x" set callback-3 [ callback_test_1 ] with-callback
366 "x" get "x" get-global
370 : callback-5 ( -- callback )
371 void { } cdecl [ gc ] alien-callback ;
374 "testing" callback-5 [ callback_test_1 ] with-callback
377 : callback-5b ( -- callback )
378 void { } cdecl [ compact-gc ] alien-callback ;
381 "testing" callback-5b [ callback_test_1 ] with-callback
384 : callback-6 ( -- callback )
385 void { } cdecl [ [ continue ] callcc0 ] alien-callback ;
388 callback-6 [ callback_test_1 1 2 3 ] with-callback
391 : callback-7 ( -- callback )
392 void { } cdecl [ 1000000 sleep ] alien-callback ;
394 [ 1 2 3 ] [ callback-7 [ callback_test_1 1 2 3 ] with-callback ] unit-test
396 [ f ] [ namespace global eq? ] unit-test
398 : callback-8 ( -- callback )
399 void { } cdecl [ [ ] in-thread yield ] alien-callback ;
401 [ ] [ callback-8 [ callback_test_1 ] with-callback ] unit-test
403 : callback-9 ( -- callback )
404 int { int int int } cdecl [
408 FUNCTION: void ffi_test_36_point_5 ( ) ;
410 [ ] [ ffi_test_36_point_5 ] unit-test
412 FUNCTION: int ffi_test_37 ( void* func ) ;
414 [ 1 ] [ callback-9 [ ffi_test_37 ] with-callback ] unit-test
416 [ 7 ] [ callback-9 [ ffi_test_37 ] with-callback ] unit-test
418 STRUCT: test_struct_13
426 : make-test-struct-13 ( -- alien )
427 test_struct_13 <struct>
435 FUNCTION: int ffi_test_39 ( long a, long b, test_struct_13 s ) ;
437 [ 21 ] [ 12347 12347 make-test-struct-13 ffi_test_39 ] unit-test
439 ! Joe Groff found this problem
446 : <double-rect> ( a b c d -- foo )
453 : >double-rect< ( foo -- a b c d )
461 : double-rect-callback ( -- alien )
462 void { void* void* double-rect } cdecl
463 [ "example" set-global 2drop ] alien-callback ;
465 : double-rect-test ( arg callback -- arg' )
467 void { void* void* double-rect } cdecl alien-indirect
468 "example" get-global ;
470 { byte-array 1.0 2.0 3.0 4.0 } [
471 1.0 2.0 3.0 4.0 <double-rect>
472 double-rect-callback [
474 [ >c-ptr class-of ] [ >double-rect< ] bi
478 STRUCT: test_struct_14
482 FUNCTION: test_struct_14 ffi_test_40 ( double x1, double x2 ) ;
485 1.0 2.0 ffi_test_40 [ x1>> ] [ x2>> ] bi
488 : callback-10 ( -- callback )
489 test_struct_14 { double double } cdecl
491 test_struct_14 <struct>
496 : callback-10-test ( x1 x2 callback -- result )
497 test_struct_14 { double double } cdecl alien-indirect ;
500 1.0 2.0 callback-10 [
501 callback-10-test [ x1>> ] [ x2>> ] bi
505 FUNCTION: test-struct-12 ffi_test_41 ( int a, double x ) ;
512 : callback-11 ( -- callback )
513 test-struct-12 { int double } cdecl
515 test-struct-12 <struct>
520 : callback-11-test ( x1 x2 callback -- result )
521 test-struct-12 { int double } cdecl alien-indirect ;
525 callback-11-test [ a>> ] [ x>> ] bi
529 STRUCT: test_struct_15
533 FUNCTION: test_struct_15 ffi_test_42 ( float x, float y ) ;
535 [ 1.0 2.0 ] [ 1.0 2.0 ffi_test_42 [ x>> ] [ y>> ] bi ] unit-test
537 : callback-12 ( -- callback )
538 test_struct_15 { float float } cdecl
540 test_struct_15 <struct>
545 : callback-12-test ( x1 x2 callback -- result )
546 test_struct_15 { float float } cdecl alien-indirect ;
549 1.0 2.0 callback-12 [
550 callback-12-test [ x>> ] [ y>> ] bi
554 STRUCT: test_struct_16
558 FUNCTION: test_struct_16 ffi_test_43 ( float x, int a ) ;
560 [ 1.0 2 ] [ 1.0 2 ffi_test_43 [ x>> ] [ a>> ] bi ] unit-test
562 : callback-13 ( -- callback )
563 test_struct_16 { float int } cdecl
565 test_struct_16 <struct>
570 : callback-13-test ( x1 x2 callback -- result )
571 test_struct_16 { float int } cdecl alien-indirect ;
575 callback-13-test [ x>> ] [ a>> ] bi
579 FUNCTION: test_struct_14 ffi_test_44 ( ) ; inline
581 [ 1.0 2.0 ] [ ffi_test_44 [ x1>> ] [ x2>> ] bi ] unit-test
583 : stack-frame-bustage ( -- a b ) ffi_test_44 gc 3 ;
585 [ ] [ stack-frame-bustage 2drop ] unit-test
590 FUNCTION: complex-float ffi_test_45 ( int x ) ;
592 [ C{ 3.0 0.0 } ] [ 3 ffi_test_45 ] unit-test
594 FUNCTION: complex-double ffi_test_46 ( int x ) ;
596 [ C{ 3.0 0.0 } ] [ 3 ffi_test_46 ] unit-test
598 FUNCTION: complex-float ffi_test_47 ( complex-float x, complex-double y ) ;
602 C{ 1.5 1.0 } ffi_test_47
606 STRUCT: bool-field-test
611 FUNCTION: short ffi_test_48 ( bool-field-test x ) ;
614 bool-field-test <struct>
621 ! Test interaction between threads and callbacks
622 : thread-callback-1 ( -- callback )
623 int { } cdecl [ yield 100 ] alien-callback ;
625 : thread-callback-2 ( -- callback )
626 int { } cdecl [ yield 200 ] alien-callback ;
628 : thread-callback-invoker ( callback -- n )
629 int { } cdecl alien-indirect ;
634 thread-callback-invoker
635 ] with-callback "p" get fulfill
638 thread-callback-2 [ thread-callback-invoker ] with-callback
640 [ 100 ] [ "p" get ?promise ] unit-test
642 ! More alien-assembly tests are in cpu.* vocabs
643 : assembly-test-1 ( -- ) void { } cdecl [ ] alien-assembly ;
645 [ ] [ assembly-test-1 ] unit-test
647 [ f ] [ "f-fastcall" load-library f = ] unit-test
648 [ fastcall ] [ "f-fastcall" lookup-library abi>> ] unit-test
650 : ffi_test_49 ( x -- int )
651 int "f-fastcall" "ffi_test_49" { int }
653 : ffi_test_50 ( x y -- int )
654 int "f-fastcall" "ffi_test_50" { int int }
656 : ffi_test_51 ( x y z -- int )
657 int "f-fastcall" "ffi_test_51" { int int int }
659 : multi_ffi_test_51 ( x y z x' y' z' -- int int )
660 [ int "f-fastcall" "ffi_test_51" { int int int } alien-invoke ]
662 int "f-fastcall" "ffi_test_51" { int int int } alien-invoke gc ;
664 [ 4 ] [ 3 ffi_test_49 ] unit-test
665 [ 8 ] [ 3 4 ffi_test_50 ] unit-test
666 [ 13 ] [ 3 4 5 ffi_test_51 ] unit-test
667 [ 13 22 ] [ 3 4 5 6 7 8 multi_ffi_test_51 ] unit-test
669 : ffi_test_52 ( x y z -- int )
670 int "f-fastcall" "ffi_test_52" { int float int }
672 : ffi_test_53 ( x y z w -- int )
673 int "f-fastcall" "ffi_test_53" { int float int int }
675 : ffi_test_57 ( x y -- test-struct-11 )
676 test-struct-11 "f-fastcall" "ffi_test_57" { int int }
678 : ffi_test_58 ( x y z -- test-struct-11 )
679 test-struct-11 "f-fastcall" "ffi_test_58" { int int int }
682 ! Make sure that large longlong/ulonglong are correctly dealt with
683 FUNCTION: longlong ffi_test_59 ( longlong x ) ;
684 FUNCTION: ulonglong ffi_test_60 ( ulonglong x ) ;
686 [ t ] [ most-positive-fixnum 1 + [ ffi_test_59 ] keep = ] unit-test
687 [ t ] [ most-positive-fixnum 1 + [ ffi_test_60 ] keep = ] unit-test
689 [ -1 ] [ -1 ffi_test_59 ] unit-test
690 [ -1 ] [ 0xffffffffffffffff ffi_test_59 ] unit-test
691 [ 0xffffffffffffffff ] [ -1 ffi_test_60 ] unit-test
692 [ 0xffffffffffffffff ] [ 0xffffffffffffffff ffi_test_60 ] unit-test
696 [ 13 ] [ 3 4.0 5 ffi_test_52 ] unit-test
698 [ 19 ] [ 3 4.0 5 6 ffi_test_53 ] unit-test
701 [ S{ test-struct-11 f 7 -1 } ] [ 3 4 ffi_test_57 ] unit-test
703 [ S{ test-struct-11 f 7 -3 } ] [ 3 4 7 ffi_test_58 ] unit-test
705 : fastcall-ii-indirect ( x y ptr -- result )
706 int { int int } fastcall alien-indirect ;
708 : fastcall-iii-indirect ( x y z ptr -- result )
709 int { int int int } fastcall alien-indirect ;
711 : fastcall-ifi-indirect ( x y z ptr -- result )
712 int { int float int } fastcall alien-indirect ;
714 : fastcall-ifii-indirect ( x y z w ptr -- result )
715 int { int float int int } fastcall alien-indirect ;
717 : fastcall-struct-return-ii-indirect ( x y ptr -- result )
718 test-struct-11 { int int } fastcall alien-indirect ;
720 : fastcall-struct-return-iii-indirect ( x y z ptr -- result )
721 test-struct-11 { int int int } fastcall alien-indirect ;
723 : win32? ( -- ? ) os windows? cpu x86.32? and ;
727 win32? [ &: @ffi_test_50@8 ] [ &: ffi_test_50 ] if
733 win32? [ &: @ffi_test_51@12 ] [ &: ffi_test_51 ] if
734 fastcall-iii-indirect
740 win32? [ &: @ffi_test_52@12 ] [ &: ffi_test_52 ] if
741 fastcall-ifi-indirect
746 win32? [ &: @ffi_test_53@16 ] [ &: ffi_test_53 ] if
747 fastcall-ifii-indirect
751 [ S{ test-struct-11 f 7 -1 } ]
754 win32? [ &: @ffi_test_57@8 ] [ &: ffi_test_57 ] if
755 fastcall-struct-return-ii-indirect
758 [ S{ test-struct-11 f 7 -3 } ]
761 win32? [ &: @ffi_test_58@12 ] [ &: ffi_test_58 ] if
762 fastcall-struct-return-iii-indirect
765 : fastcall-ii-callback ( -- ptr )
766 int { int int } fastcall [ + 1 + ] alien-callback ;
768 : fastcall-iii-callback ( -- ptr )
769 int { int int int } fastcall [ + + 1 + ] alien-callback ;
771 : fastcall-ifi-callback ( -- ptr )
772 int { int float int } fastcall
773 [ [ >integer ] dip + + 1 + ] alien-callback ;
775 : fastcall-ifii-callback ( -- ptr )
776 int { int float int int } fastcall
777 [ [ >integer ] 2dip + + + 1 + ] alien-callback ;
779 : fastcall-struct-return-ii-callback ( -- ptr )
780 test-struct-11 { int int } fastcall
781 [ [ + ] [ - ] 2bi test-struct-11 <struct-boa> ] alien-callback ;
783 : fastcall-struct-return-iii-callback ( -- ptr )
784 test-struct-11 { int int int } fastcall
785 [ [ drop + ] [ - nip ] 3bi test-struct-11 <struct-boa> ] alien-callback ;
788 3 4 fastcall-ii-callback [ fastcall-ii-indirect ] with-callback
792 3 4 5 fastcall-iii-callback [ fastcall-iii-indirect ] with-callback
796 3 4.0 5 fastcall-ifi-callback [ fastcall-ifi-indirect ] with-callback
800 3 4.0 5 6 fastcall-ifii-callback [ fastcall-ifii-indirect ] with-callback
803 [ S{ test-struct-11 f 7 -1 } ] [
804 3 4 fastcall-struct-return-ii-callback [
805 fastcall-struct-return-ii-indirect
809 [ S{ test-struct-11 f 7 -3 } ] [
810 3 4 7 fastcall-struct-return-iii-callback [
811 fastcall-struct-return-iii-indirect
815 : x64-regression-1 ( -- c )
816 int { int int int int int } cdecl [ + + + + ] alien-callback ;
818 : x64-regression-2 ( x x x x x c -- y )
819 int { int int int int int } cdecl alien-indirect ; inline
822 100 500 50 10 1 x64-regression-1 [ x64-regression-2 ] with-callback
826 : blah ( -- x ) { RECT } [
827 1.5 >>x 2.0 >>y [ x>> ] [ y>> ] bi * >fixnum
828 ] with-scoped-allocation ;
830 [ 3 ] [ blah ] unit-test
832 : out-param-test-1 ( -- b )
833 { int } [ [ 12 ] dip 0 int set-alien-value ] with-out-parameters ;
835 [ 12 ] [ out-param-test-1 ] unit-test
837 : out-param-test-2 ( -- b )
838 { { int initial: 12 } } [ drop ] with-out-parameters ;
840 [ 12 ] [ out-param-test-2 ] unit-test
842 : out-param-test-3 ( -- x y )
843 { { RECT initial: S{ RECT { x 3 } { y 4 } } } } [ drop ]
847 [ 3.0 4.0 ] [ out-param-test-3 ] unit-test
849 : out-param-callback ( -- a )
850 void { int pointer: int } cdecl
851 [ [ 2 * ] dip 0 int set-alien-value ] alien-callback ;
853 : out-param-indirect ( a a -- b )
855 swap void { int pointer: int } cdecl
857 ] with-out-parameters ;
860 6 out-param-callback [ out-param-indirect ] with-callback
863 ! Alias analysis regression
864 : aa-callback-1 ( -- c )
865 double { } cdecl [ 5.0 ] alien-callback ;
867 : aa-indirect-1 ( c -- x )
868 double { } cdecl alien-indirect ; inline
870 TUPLE: some-tuple x ;
872 [ T{ some-tuple f 5.0 } ] [
882 : anton's-regression ( -- )
885 [ ] [ anton's-regression ] unit-test
893 FUNCTION: bool-and-ptr ffi_test_61 ( ) ;
896 S{ bool-and-ptr { b t } { ptr f } }
897 } [ ffi_test_61 ] unit-test
903 FUNCTION: uint-pair ffi_test_62 ( ) ;
906 S{ uint-pair { a 0xabcdefab } { b 0x12345678 } }
907 } [ ffi_test_62 ] unit-test
909 STRUCT: ulonglong-pair
913 FUNCTION: ulonglong-pair ffi_test_63 ( ) ;
916 S{ ulonglong-pair { a 0xabcdefabcdefabcd } { b 0x1234567891234567 } }
917 } [ ffi_test_63 ] unit-test