From: Scott W. <or...@gm...> - 2003-06-17 00:13:19
|
If more than one foreign function has a user-defined struct for a return type, the C compiler gets confused. When the following file is compiled as a module: ----[ testffi.lisp ]------ (defpackage "TESTFFI" (:use "FFI" "COMMON-LISP")) (in-package "TESTFFI") (default-foreign-language :stdc) (def-c-struct type1 (arg1 int)) (def-call-out func1 (:return-type type1)) (def-call-out func2 (:return-type type1)) ---[ end testffi.lisp ]---- I get the following function definitions in the testffi.c file: extern struct TYPE1 { int ARG1; } (func1)(); extern struct TYPE1 { int ARG1; } (func2)(); which results in the following compiler error: testffi.c:14: redefinition of `struct TYPE1' make[1]: *** [testffi.o] Error 1 This problem does not occur if TYPE1 is only used in argument declarations. A possible solution is to output a struct TYPE1 { int ARG1; }; when the def-c-struct command is encountered, and then refer to that type as "struct TYPE1" instead of redeclaring the structure each time it is used. Another possible solution is to avoid naming the struct, which would result in the following code: extern struct { int ARG1; } (func1)(); extern struct { int ARG1; } (func2)(); which does not cause a compiler error. I don't know anything about the internal mechanisms clisp uses to generate code for the FFI, otherwise i'd fix it myself :o) I hope someone can resolve the issue! -Scott Williams -- +++ GMX - Mail, Messaging & more http://www.gmx.net +++ Bitte lächeln! Fotogalerie online mit GMX ohne eigene Homepage! |
From: Sam S. <sd...@gn...> - 2003-06-17 13:47:35
|
> * In message <291...@ww...> > * On the subject of "FFI Code Generation Bug" > * Sent on Tue, 17 Jun 2003 02:13:08 +0200 (MEST) > * Honorable Scott Williams <or...@gm...> writes: > > If more than one foreign function has a user-defined struct for a > return type, the C compiler gets confused. When the following file is > compiled as a module: > > ----[ testffi.lisp ]------ > (defpackage "TESTFFI" > (:use "FFI" "COMMON-LISP")) > (in-package "TESTFFI") > > (default-foreign-language :stdc) > > (def-c-struct type1 > (arg1 int)) > > (def-call-out func1 > (:return-type type1)) > > (def-call-out func2 > (:return-type type1)) > ---[ end testffi.lisp ]---- > > I get the following function definitions in the testffi.c file: > > extern struct TYPE1 { int ARG1; } (func1)(); > extern struct TYPE1 { int ARG1; } (func2)(); > > which results in the following compiler error: > > testffi.c:14: redefinition of `struct TYPE1' > make[1]: *** [testffi.o] Error 1 > > This problem does not occur if TYPE1 is only used in argument declarations. > A possible solution is to output a > struct TYPE1 { int ARG1; }; > when the def-c-struct command is encountered, and then refer to that type as > "struct TYPE1" instead of redeclaring the structure each time it is > used. indeed. I am not sure why we are not doing that, but I _am_ sure there was a compelling reason for that. e.g., the appended patch will solve your problem, but might introduce others. I hope Joerg will chime in with his insight. > Another possible solution is to avoid naming the struct, which would result in > the following code: > extern struct { int ARG1; } (func1)(); > extern struct { int ARG1; } (func2)(); > which does not cause a compiler error. we did that before, it caused other problems. > I don't know anything about the internal mechanisms clisp uses to > generate code for the FFI, otherwise i'd fix it myself :o) see TO-C-TYPEDECL in clisp/src/foreign1.lisp. -- Sam Steingold (http://www.podval.org/~sds) running RedHat9 GNU/Linux <http://www.camera.org> <http://www.iris.org.il> <http://www.memri.org/> <http://www.mideasttruth.com/> <http://www.palestine-central.com/links.html> A poet who reads his verse in public may have other nasty habits. Index: foreign1.lisp =================================================================== RCS file: /cvsroot/clisp/clisp/src/foreign1.lisp,v retrieving revision 1.40 diff -u -w -b -u -b -w -i -B -r1.40 foreign1.lisp --- foreign1.lisp 12 May 2003 10:43:18 -0000 1.40 +++ foreign1.lisp 17 Jun 2003 13:34:59 -0000 @@ -560,11 +560,8 @@ (macrolet ((with-to-c ((class typename &key (tname '(gensym "t"))) &body body) `(let ((,typename (format nil "~A ~A" ,class ,tname))) - (unwind-protect - (progn (setf (gethash c-type *type-table*) - ,typename) - ,@body) - (setf (gethash c-type *type-table*) nil))))) + (setf (gethash c-type *type-table*) ,typename) + ,@body))) (case (ctype-type c-type) (c-struct (cond ((sys::memq :typedef (svref c-type 2)) |