Macro: DEFCFUN*

Documentation

if ret-type is keyword :error-int the cfunction will return an int indicating an error if ret!=0 and error-fun is called with using the returned value syntax: (defcfun* (name fun-name <:error-fun symbol> <:method t|nil>) ret-type args*) ctype ::= see cffi manual... args ::= (arg ctype [:key]) | (arg :out ctype) | (arg ctype :const value) | (arg :flag flag-list <:flag-type ctype> <:default flag-list> <:flag-system flag-system>) (arg ctype :class class-args) flag-list ::= (flag-keyword*) class-args ::= slot-name | (class-name slot-name) params: flag-type: default is uint32 default: flags being set to t by default name: cfunction name fun-name: function name for lisp interface error-fun: function called if ret-type id of type :error-int ret-type: see defcfun arglist: see defcfun (if arglist contains :out keyword for several args, these will be returned using values... try macroexpand to find out more :P )

Source

(defmacro defcfun* ((name fun-name &key
			  (error-fun 'std-check-error)
			  method)
		    ret-type &body arg-list)
  "if ret-type is keyword :error-int the cfunction will return
   an int indicating an error if ret!=0 and error-fun is called with using
   the returned value
   syntax: (defcfun* (name fun-name <:error-fun symbol> <:method t|nil>)
               ret-type
             args*)
           ctype ::= see cffi manual...
           args ::= (arg ctype [:key]) | (arg :out ctype) | 
                    (arg ctype :const value) |
                    (arg :flag flag-list
                         <:flag-type ctype>
                         <:default flag-list>
                         <:flag-system flag-system>)
                    (arg ctype :class class-args)
           flag-list ::= (flag-keyword*)
           class-args ::= slot-name | (class-name slot-name)
   params: flag-type: default is uint32 
           default: flags being set to t by default
           name: cfunction name
           fun-name: function name for lisp interface
           error-fun: function called if ret-type id of type :error-int
           ret-type: see defcfun
           arglist: see defcfun (if arglist contains :out keyword for
                                 several args, these will be returned
                                 using values... try macroexpand to find out
                                 more :P )"
  (let ((cfun-name (symb '% fun-name))
	(cffi-arglist (create-cffi-arglist arg-list))
	(lisp-arglist (create-lisp-arglist method arg-list))
	(out-arglist (create-out-arglist arg-list))
	(call-list (create-lisp-call-list arg-list))
	(real-ret-type (if (eq :error-int ret-type) :int ret-type)))
     `(progn
       (defcfun (,name ,cfun-name) ,real-ret-type
	 ,@cffi-arglist)

       (,(if method 'defmethod 'defun) ,fun-name ,lisp-arglist
	 ,(if (null out-arglist)
	      (if (eq :error-int ret-type)
		  `(,error-fun (,cfun-name ,@call-list))
		  `(,cfun-name ,@call-list))
	      `(with-foreign-objects ,(mapcar #'cdr out-arglist)
		(let ((ret (,cfun-name ,@call-list)))
		  ,(if (eq :error-int ret-type)
		       `(when (,error-fun ret)
			 (values ,@out-arglist))
		       `(values ,@(append (when (not (eq :void ret-type))
					    (list `ret))
					  out-arglist))))))))))
Source Context