chiark / gitweb /
GINTERFACE renamed to INTERFACE
[clg] / glib / gtype.lisp
CommitLineData
55212af1 1;; Common Lisp bindings for GTK+ v2.x
08cb5756 2;; Copyright 2000-2006 Espen S. Johnsen <espen@users.sf.net>
0d07716f 3;;
55212af1 4;; Permission is hereby granted, free of charge, to any person obtaining
5;; a copy of this software and associated documentation files (the
6;; "Software"), to deal in the Software without restriction, including
7;; without limitation the rights to use, copy, modify, merge, publish,
8;; distribute, sublicense, and/or sell copies of the Software, and to
9;; permit persons to whom the Software is furnished to do so, subject to
10;; the following conditions:
0d07716f 11;;
55212af1 12;; The above copyright notice and this permission notice shall be
13;; included in all copies or substantial portions of the Software.
0d07716f 14;;
55212af1 15;; THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16;; EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17;; MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
18;; IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
19;; CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
20;; TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
21;; SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
22
d92bb6e7 23;; $Id: gtype.lisp,v 1.53 2006/04/26 10:29:01 espen Exp $
0d07716f 24
25(in-package "GLIB")
26
27(use-prefix "g")
28
d1266407 29;; Initialize the glib type system
30(defbinding type-init () nil)
31(type-init)
0d07716f 32
fb9bc912 33(deftype type-number () 'unsigned-long)
0d07716f 34
b4a2c852 35(deftype gtype () 'symbol)
36
4d1fea77 37(define-type-method alien-type ((type gtype))
38 (declare (ignore type))
b4a2c852 39 (alien-type 'type-number))
40
08cb5756 41(define-type-method size-of ((type gtype) &key (inlined t))
42 (assert-inlined type inlined)
b4a2c852 43 (size-of 'type-number))
44
08cb5756 45(define-type-method to-alien-form ((type gtype) gtype &optional copy-p)
46 (declare (ignore type copy-p))
b4a2c852 47 `(find-type-number ,gtype t))
48
08cb5756 49(define-type-method to-alien-function ((type gtype) &optional copy-p)
50 (declare (ignore type copy-p))
b4a2c852 51 #'(lambda (gtype)
52 (find-type-number gtype t)))
53
08cb5756 54(define-type-method from-alien-form ((type gtype) form &key ref)
55 (declare (ignore type ref))
56 `(type-from-number ,form))
b4a2c852 57
08cb5756 58(define-type-method from-alien-function ((type gtype) &key ref)
59 (declare (ignore type ref))
b4a2c852 60 #'(lambda (type-number)
40c346ec 61 (type-from-number type-number)))
b4a2c852 62
08cb5756 63(define-type-method writer-function ((type gtype) &key temp (inlined t))
64 (declare (ignore temp))
65 (assert-inlined type inlined)
b4a2c852 66 (let ((writer (writer-function 'type-number)))
67 #'(lambda (gtype location &optional (offset 0))
68 (funcall writer (find-type-number gtype t) location offset))))
69
08cb5756 70(define-type-method reader-function ((type gtype) &key ref (inlined t))
71 (declare (ignore ref))
72 (assert-inlined type inlined)
b4a2c852 73 (let ((reader (reader-function 'type-number)))
08cb5756 74 #'(lambda (location &optional (offset 0))
40c346ec 75 (type-from-number (funcall reader location offset)))))
b4a2c852 76
77
fc47a022 78(eval-when (:compile-toplevel :load-toplevel :execute)
3a935dfa 79 (defclass type-query (struct)
fc47a022 80 ((type-number :allocation :alien :type type-number)
08cb5756 81 (name :allocation :alien :type (copy-of string))
fc47a022 82 (class-size :allocation :alien :type unsigned-int)
83 (instance-size :allocation :alien :type unsigned-int))
4d1d3921 84 (:metaclass struct-class)))
fc47a022 85
86
b4a2c852 87(defbinding type-query (type) nil
88 ((find-type-number type t) type-number)
08cb5756 89 ((make-instance 'type-query) type-query :in/return))
fc47a022 90
91(defun type-instance-size (type)
92 (slot-value (type-query type) 'instance-size))
93
94(defun type-class-size (type)
95 (slot-value (type-query type) 'class-size))
0d07716f 96
3a935dfa 97(defbinding type-class-ref (type) pointer
98 ((find-type-number type t) type-number))
0d07716f 99
08cb5756 100(defbinding type-class-unref () nil
101 (class pointer))
fc47a022 102
3a935dfa 103(defbinding type-class-peek (type) pointer
104 ((find-type-number type t) type-number))
fc47a022 105
0d07716f 106
08cb5756 107
3a935dfa 108;;;; Mapping between lisp types and glib types
0d07716f 109
dcb31db6 110(defvar *registered-types* ())
111(defvar *registered-type-aliases* ())
0f68f696 112(defvar *registered-static-types* ())
dcb31db6 113(defvar *lisp-type-to-type-number* (make-hash-table))
114(defvar *type-number-to-lisp-type* (make-hash-table))
3a935dfa 115
116(defbinding %type-from-name () type-number
117 (name string))
118
dcb31db6 119(defun type-number-from-glib-name (name &optional (error-p t))
120 (let ((type-number (%type-from-name name)))
121 (cond
122 ((not (zerop type-number)) type-number)
123 (error-p (error "Invalid gtype name: ~A" name)))))
124
125(defun register-type (type id)
08cb5756 126 (cond
127 ((find-type-number type))
128 ((not id) (warn "Can't register type with no foreign id: ~A" type))
129 (t
130 (pushnew (cons type id) *registered-types* :key #'car)
131 (let ((type-number
132 (typecase id
133 (string (type-number-from-glib-name id))
134 (symbol (funcall id)))))
135 (setf (gethash type *lisp-type-to-type-number*) type-number)
136 (setf (gethash type-number *type-number-to-lisp-type*) type)
137 type-number))))
dcb31db6 138
139(defun register-type-alias (type alias)
140 (pushnew (cons type alias) *registered-type-aliases* :key #'car)
141 (setf
142 (gethash type *lisp-type-to-type-number*)
143 (find-type-number alias t)))
144
145(defun reinitialize-all-types ()
146 (clrhash *lisp-type-to-type-number*)
147 (clrhash *type-number-to-lisp-type*)
148 (type-init) ; initialize the glib type system
149 (mapc #'(lambda (type)
150 (register-type (car type) (cdr type)))
151 *registered-types*)
e9177b70 152 (mapc #'(lambda (type)
08cb5756 153 (apply #'register-new-type type))
e9177b70 154 *registered-static-types*)
dcb31db6 155 (mapc #'(lambda (type)
156 (register-type-alias (car type) (cdr type)))
157 *registered-type-aliases*))
158
159(pushnew 'reinitialize-all-types
160 #+cmu *after-save-initializations*
08cb5756 161 #+sbcl *init-hooks*
162 #+clisp custom:*init-hooks*)
dcb31db6 163
164#+cmu
165(pushnew 'system::reinitialize-global-table ; we shouldn't have to do this?
166 *after-save-initializations*)
167
168
169(defun find-type-number (type &optional error-p)
0d07716f 170 (etypecase type
171 (integer type)
dcb31db6 172 (string (type-number-from-glib-name type error-p))
3a935dfa 173 (symbol
dcb31db6 174 (or
175 (gethash type *lisp-type-to-type-number*)
176 (and error-p (error "Type not registered: ~A" type))))
177 (class (find-type-number (class-name type) error-p))))
0d07716f 178
b011356b 179(defun type-from-number (type-number &optional error)
180 (multiple-value-bind (type found)
dcb31db6 181 (gethash type-number *type-number-to-lisp-type*)
e40a19fb 182 (if found
183 type
dcb31db6 184 (let ((name (find-foreign-type-name type-number)))
e40a19fb 185 (cond
f53fad52 186 ((and name (not (= (type-number-from-glib-name name nil) type-number)))
e40a19fb 187 ;; This is a hack because GdkEvent seems to be registered
188 ;; multiple times
189 (type-from-number (type-number-from-glib-name name)))
190 ((and error name)
191 (error "Type number not registered: ~A (~A)" type-number name))
192 ((and error)
193 (error "Invalid type number: ~A" type-number)))))))
0d07716f 194
dcb31db6 195(defbinding (find-foreign-type-name "g_type_name") (type) (copy-of string)
3a935dfa 196 ((find-type-number type t) type-number))
197
198(defun type-number-of (object)
199 (find-type-number (type-of object) t))
200
6556dccd 201(eval-when (:compile-toplevel :load-toplevel :execute)
dcb31db6 202 (defvar *type-initializers* ())
203 (defun %find-types-in-library (pathname prefixes ignore)
08cb5756 204 (let ((process
205 (run-program
206 "/usr/bin/nm"
207 #+clisp :arguments
208 (list "--defined-only" "-D" (namestring (truename pathname)))
209 :output :stream :wait nil)))
6556dccd 210 (unwind-protect
211 (loop
08cb5756 212 as symbol = (let ((line (read-line
213 #+(or cmu sbcl)
214 (process-output process)
215 #+clisp process
216 nil)))
fb9bc912 217 (when line
218 (subseq line (1+ (position #\Space line :from-end t)))))
6556dccd 219 while symbol
220 when (and
dcb31db6 221 (> (length symbol) 9)
222 (or
223 (not prefixes)
224 (some #'(lambda (prefix)
225 (and
226 (> (length symbol) (length prefix))
227 (string= prefix symbol :end2 (length prefix))))
228 (mklist prefixes)))
229 (string= "_get_type" symbol :start2 (- (length symbol) 9))
6556dccd 230 (not (member symbol ignore :test #'string=)))
231 collect symbol)
08cb5756 232 (#+(or cmu sbcl)process-close
233 #+clisp close
234 process)))))
6556dccd 235
0d07716f 236
80031aba 237(defmacro init-types-in-library (filename &key prefix ignore)
6556dccd 238 (let ((names (%find-types-in-library filename prefix ignore)))
239 `(progn
240 ,@(mapcar #'(lambda (name)
241 `(progn
242 (defbinding (,(intern name) ,name) () type-number)
dcb31db6 243 (,(intern name))
244 (pushnew ',(intern name) *type-initializers*)))
6556dccd 245 names))))
246
dcb31db6 247(defun find-type-init-function (type-number)
80031aba 248 (loop
249 for type-init in *type-initializers*
250 when (= type-number (funcall type-init))
251 do (return type-init)))
252
253(defun register-type-as (type-number)
254 (or
255 (find-type-init-function type-number)
256 (find-foreign-type-name type-number)
257 (error "Unknown type-number: ~A" type-number)))
dcb31db6 258
259(defun default-type-init-name (type)
260 (find-symbol (format nil "~A_~A_get_type"
261 (package-prefix *package*)
262 (substitute #\_ #\- (string-downcase type)))))
263
6556dccd 264
0a77b51f 265(eval-when (:compile-toplevel :load-toplevel :execute)
266 (defclass type-info (struct)
267 ((class-size :allocation :alien :type (unsigned 16) :initarg :class-size)
268 (base-init :allocation :alien :type pointer)
269 (base-finalize :allocation :alien :type pointer)
270 (class-init :allocation :alien :type pointer)
271 (class-finalize :allocation :alien :type pointer)
272 (class-data :allocation :alien :type pointer)
273 (instance-size :allocation :alien :type (unsigned 16)
274 :initarg :instance-size)
275 (n-preallocs :allocation :alien :type (unsigned 16))
276 (instance-init :allocation :alien :type pointer)
277 (value-table :allocation :alien :type pointer))
278 (:metaclass struct-class)))
279
280(defbinding %type-register-static () type-number
e40a19fb 281 (parent-type type-number)
0a77b51f 282 (name string)
283 (info type-info)
284 (0 unsigned-int))
285
8fbfa684 286(defun register-new-type (type parent &optional foreign-name)
0a77b51f 287 (let ((parent-info (type-query parent)))
288 (with-slots ((parent-number type-number) class-size instance-size) parent-info
289 (let ((type-number
290 (%type-register-static
291 parent-number
8fbfa684 292 (or foreign-name (default-alien-type-name type))
0a77b51f 293 (make-instance 'type-info :class-size class-size :instance-size instance-size))))
0f68f696 294 (pushnew (list type parent foreign-name) *registered-static-types* :key #'car)
295 (setf (gethash type *lisp-type-to-type-number*) type-number)
296 (setf (gethash type-number *type-number-to-lisp-type*) type)
297 type-number))))
0a77b51f 298
299
6556dccd 300
301;;;; Metaclass for subclasses of ginstance
302
303(eval-when (:compile-toplevel :load-toplevel :execute)
304 (defclass ginstance-class (proxy-class)
7bab08b9 305 ((gtype :initarg :gtype :initform nil :reader ginstance-class-gtype))))
f53fad52 306
307
d905d6ef 308(defun update-size (class)
309 (let ((type-number (find-type-number class)))
310 (cond
08cb5756 311 ((not (foreign-size-p class))
312 (setf (foreign-size class) (type-instance-size type-number)))
d905d6ef 313 ((and
08cb5756 314 (foreign-size-p class)
315 (not (= (type-instance-size type-number) (foreign-size class))))
d905d6ef 316 (warn "Size mismatch for class ~A" class)))))
317
7ce0497d 318
f53fad52 319(defmethod finalize-inheritance ((class ginstance-class))
08cb5756 320 (prog1
321 #+clisp(call-next-method)
322 (let* ((class-name (class-name class))
323 (super (most-specific-proxy-superclass class))
324 (gtype (or
325 (first (ginstance-class-gtype class))
326 (default-alien-type-name class-name)))
327 (type-number
328 (or
329 (find-type-number class-name)
330 (let ((type-number
331 (if (or
332 (symbolp gtype)
333 (type-number-from-glib-name gtype nil))
334 (register-type class-name gtype)
335 (register-new-type class-name (class-name super) gtype))))
336 (type-class-ref type-number)
337 type-number))))
338 (when (and
339 (supertype type-number)
340 (not (eq (class-name super) (supertype type-number))))
341 (warn "Super class mismatch between CLOS and GObject for ~A"
342 class-name)))
343 (update-size class))
344 #-clisp(call-next-method))
d905d6ef 345
346
347(defmethod shared-initialize ((class ginstance-class) names &rest initargs)
08cb5756 348 (declare (ignore names initargs))
d905d6ef 349 (call-next-method)
350 (when (class-finalized-p class)
351 (update-size class)))
352
b011356b 353
6556dccd 354(defmethod validate-superclass ((class ginstance-class) (super standard-class))
355 (subtypep (class-name super) 'ginstance))
356
0d07716f 357
fc47a022 358;;;; Superclass for wrapping types in the glib type system
0d07716f 359
360(eval-when (:compile-toplevel :load-toplevel :execute)
fc47a022 361 (defclass ginstance (proxy)
7ce0497d 362 (;(class :allocation :alien :type pointer :offset 0)
363 )
364 (:metaclass proxy-class)
365 (:size #.(size-of 'pointer))))
0d07716f 366
08cb5756 367(defun ref-type-number (location &optional offset)
368 (declare (ignore location offset)))
369
370(setf (symbol-function 'ref-type-number) (reader-function 'type-number))
371
609ba905 372(defun %type-number-of-ginstance (location)
08cb5756 373 (let ((class (ref-pointer location)))
374 (ref-type-number class)))
0d07716f 375
08cb5756 376(defmethod make-proxy-instance :around ((class ginstance-class) location
377 &rest initargs)
4d1d3921 378 (declare (ignore class))
609ba905 379 (let ((class (labels ((find-known-class (type-number)
380 (or
381 (find-class (type-from-number type-number) nil)
382 (unless (zerop type-number)
383 (find-known-class (type-parent type-number))))))
384 (find-known-class (%type-number-of-ginstance location)))))
08cb5756 385 ;; Note that chancing the class argument should not alter "the
1d06a422 386 ;; ordered set of applicable methods" as specified in the
387 ;; Hyperspec
4d1d3921 388 (if class
1d06a422 389 (apply #'call-next-method class location initargs)
390 (error "Object at ~A has an unkown type number: ~A"
391 location (%type-number-of-ginstance location)))))
392
08cb5756 393(define-type-method from-alien-form ((type ginstance) form &key (ref :copy))
394 (call-next-method type form :ref ref))
0d07716f 395
08cb5756 396(define-type-method from-alien-function ((type ginstance) &key (ref :copy))
397 (call-next-method type :ref ref))
508d13a7 398
0d07716f 399
3a935dfa 400;;;; Registering fundamental types
401
40c346ec 402(register-type 'nil "void")
3a935dfa 403(register-type 'pointer "gpointer")
404(register-type 'char "gchar")
405(register-type 'unsigned-char "guchar")
406(register-type 'boolean "gboolean")
3a935dfa 407(register-type 'int "gint")
0b392a0d 408(register-type-alias 'integer 'int)
dcb31db6 409(register-type-alias 'fixnum 'int)
3a935dfa 410(register-type 'unsigned-int "guint")
411(register-type 'long "glong")
412(register-type 'unsigned-long "gulong")
413(register-type 'single-float "gfloat")
414(register-type 'double-float "gdouble")
b77fe850 415(register-type 'pathname "gchararray")
b011356b 416(register-type 'string "gchararray")
3a935dfa 417
418
e9934f39 419;;;; Introspection of type information
3a935dfa 420
4812615b 421(defvar *derivable-type-info* (make-hash-table))
3a935dfa 422
e9934f39 423(defun register-derivable-type (type id expander &optional dependencies)
3a935dfa 424 (register-type type id)
4812615b 425 (let ((type-number (register-type type id)))
e9934f39 426 (setf
427 (gethash type-number *derivable-type-info*)
428 (list expander dependencies))))
3a935dfa 429
b011356b 430(defun find-type-info (type)
431 (dolist (super (cdr (type-hierarchy type)))
4812615b 432 (let ((info (gethash super *derivable-type-info*)))
b011356b 433 (return-if info))))
434
e9934f39 435(defun expand-type-definition (type forward-p options)
436 (let ((expander (first (find-type-info type))))
437 (funcall expander (find-type-number type t) forward-p options)))
3a935dfa 438
08cb5756 439
3a935dfa 440(defbinding type-parent (type) type-number
441 ((find-type-number type t) type-number))
442
443(defun supertype (type)
444 (type-from-number (type-parent type)))
445
7858d45e 446(defbinding %type-interfaces (type) pointer
447 ((find-type-number type t) type-number)
448 (n-interfaces unsigned-int :out))
449
450(defun type-interfaces (type)
451 (multiple-value-bind (array length) (%type-interfaces type)
452 (unwind-protect
4d1d3921 453 (map-c-vector 'list #'identity array 'type-number length)
7858d45e 454 (deallocate-memory array))))
455
456(defun implements (type)
457 (mapcar #'type-from-number (type-interfaces type)))
458
3a935dfa 459(defun type-hierarchy (type)
460 (let ((type-number (find-type-number type t)))
461 (unless (= type-number 0)
462 (cons type-number (type-hierarchy (type-parent type-number))))))
463
464(defbinding (type-is-p "g_type_is_a") (type super) boolean
465 ((find-type-number type) type-number)
466 ((find-type-number super) type-number))
467
468(defbinding %type-children () pointer
469 (type-number type-number)
470 (num-children unsigned-int :out))
471
472(defun map-subtypes (function type &optional prefix)
473 (let ((type-number (find-type-number type t)))
474 (multiple-value-bind (array length) (%type-children type-number)
475 (unwind-protect
4d1d3921 476 (map-c-vector
3a935dfa 477 'nil
478 #'(lambda (type-number)
479 (when (or
480 (not prefix)
dcb31db6 481 (string-prefix-p prefix (find-foreign-type-name type-number)))
3a935dfa 482 (funcall function type-number))
483 (map-subtypes function type-number prefix))
484 array 'type-number length)
485 (deallocate-memory array)))))
486
487(defun find-types (prefix)
488 (let ((type-list nil))
4812615b 489 (maphash
490 #'(lambda (type-number expander)
491 (declare (ignore expander))
492 (map-subtypes
493 #'(lambda (type-number)
494 (pushnew type-number type-list))
495 type-number prefix))
496 *derivable-type-info*)
3a935dfa 497 type-list))
498
08cb5756 499(defun find-type-dependencies (type &optional options)
500 (let ((find-dependencies (second (find-type-info type))))
501 (when find-dependencies
502 (remove-duplicates
503 (mapcar #'find-type-number
504 (funcall find-dependencies (find-type-number type t) options))))))
505
506
507;; The argument is a list where each elements is on the form
508;; (type . dependencies)
509(defun sort-types-topologicaly (unsorted)
510 (flet ((depend-p (type1)
511 (find-if #'(lambda (type2)
512 (and
513 ;; If a type depends a subtype it has to be
514 ;; forward defined
515 (not (type-is-p (car type2) (car type1)))
516 (find (car type2) (cdr type1))))
517 unsorted)))
518 (let ((sorted
519 (loop
520 while unsorted
521 nconc (multiple-value-bind (sorted remaining)
522 (delete-collect-if
523 #'(lambda (type)
524 (or (not (cdr type)) (not (depend-p type))))
525 unsorted)
526 (cond
527 ((not sorted)
528 ;; We have a circular dependency which have to
529 ;; be resolved
530 (let ((selected
531 (find-if
532 #'(lambda (type)
533 (every
534 #'(lambda (dep)
535 (or
536 (not (type-is-p (car type) dep))
537 (not (find dep unsorted :key #'car))))
538 (cdr type)))
539 unsorted)))
540 (unless selected
541 (error "Couldn't resolve circular dependency"))
542 (setq unsorted (delete selected unsorted))
543 (list selected)))
544 (t
545 (setq unsorted remaining)
546 sorted))))))
547
548 ;; Mark types which have to be forward defined
549 (loop
550 for tmp on sorted
551 as (type . dependencies) = (first tmp)
552 collect (cons type (and
553 dependencies
554 (find-if #'(lambda (type)
555 (find (car type) dependencies))
556 (rest tmp))
557 t))))))
3a935dfa 558
559
560(defun expand-type-definitions (prefix &optional args)
dcb31db6 561 (flet ((type-options (type-number)
562 (let ((name (find-foreign-type-name type-number)))
b011356b 563 (cdr (assoc name args :test #'string=)))))
3a935dfa 564
4812615b 565 (let ((type-list
566 (delete-if
567 #'(lambda (type-number)
dcb31db6 568 (let ((name (find-foreign-type-name type-number)))
4812615b 569 (or
570 (getf (type-options type-number) :ignore)
571 (find-if
572 #'(lambda (options)
573 (and
574 (string-prefix-p (first options) name)
17c607d0 575 (getf (cdr options) :ignore-prefix)
576 (not (some
577 #'(lambda (exception)
578 (string= name exception))
579 (getf (cdr options) :except)))))
4812615b 580 args))))
581 (find-types prefix))))
6556dccd 582
4812615b 583 (dolist (type-number type-list)
dcb31db6 584 (let ((name (find-foreign-type-name type-number)))
4812615b 585 (register-type
586 (getf (type-options type-number) :type (default-type-name name))
80031aba 587 (register-type-as type-number))))
6556dccd 588
08cb5756 589 ;; This is needed for some unknown reason to get type numbers right
590 (mapc #'find-type-dependencies type-list)
591
592 (let ((sorted-type-list
593 #+clisp (mapcar #'list type-list)
594 #-clisp
595 (sort-types-topologicaly
596 (mapcar
597 #'(lambda (type)
598 (cons type (find-type-dependencies type (type-options type))))
599 type-list))))
e9934f39 600 `(progn
601 ,@(mapcar
6556dccd 602 #'(lambda (pair)
603 (destructuring-bind (type . forward-p) pair
604 (expand-type-definition type forward-p (type-options type))))
605 sorted-type-list)
e9934f39 606 ,@(mapcar
6556dccd 607 #'(lambda (pair)
608 (destructuring-bind (type . forward-p) pair
609 (when forward-p
610 (expand-type-definition type nil (type-options type)))))
e9934f39 611 sorted-type-list))))))
4812615b 612
3a935dfa 613(defmacro define-types-by-introspection (prefix &rest args)
b011356b 614 (expand-type-definitions prefix args))
6556dccd 615
08cb5756 616(defexport define-types-by-introspection (prefix &rest args)
d92bb6e7 617 (list-autoexported-symbols (expand-type-definitions prefix args)))
08cb5756 618
6556dccd 619
620;;;; Initialize all non static types in GObject
621
622(init-types-in-library #.(concatenate 'string (pkg-config:pkg-variable "glib-2.0" "libdir") "/libgobject-2.0.so"))