Add support for foreign structs
[gnome.gobject-introspection] / tools / generate.c
1
2 /* -*- Mode: C; c-file-style: "gnu"; -*- */
3 /* GObject introspection: IDL generator
4  *
5  * Copyright (C) 2005 Matthias Clasen
6  * Copyright (C) 2008,2009 Red Hat, Inc.
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Lesser General Public
10  * License as published by the Free Software Foundation; either
11  * version 2 of the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16  * Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with this library; if not, write to the
20  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
21  * Boston, MA 02111-1307, USA.
22  */
23
24 #include <errno.h>
25 #include <string.h>
26
27 #include <glib.h>
28 #include <glib-object.h>
29 #include <glib/gstdio.h>
30
31 #include "girepository.h"
32 #include "gtypelib.h"
33
34 /* FIXME: Avoid global */
35 static gchar *output = NULL;
36 gchar **includedirs = NULL;
37 static gboolean show_all = FALSE;
38
39 typedef struct {
40   FILE *file;
41   GSList *stack;
42 } Xml;
43
44 typedef struct {
45   char *name;
46   guint has_children : 1;
47 } XmlElement;
48
49 static XmlElement *
50 xml_element_new (const char *name)
51 {
52   XmlElement *elem;
53
54   elem = g_new (XmlElement, 1);
55   elem->name = g_strdup (name);
56   elem->has_children = FALSE;
57   return elem;
58 }
59
60 static void
61 xml_element_free (XmlElement *elem)
62 {
63   g_free (elem->name);
64   g_free (elem);
65 }
66
67 static void
68 xml_printf (Xml *xml, const char *fmt, ...)
69 {
70   va_list ap;
71   char *s;
72
73   va_start (ap, fmt);
74   s = g_markup_vprintf_escaped (fmt, ap);
75   fputs (s, xml->file);
76   g_free (s);
77   va_end (ap);
78 }
79
80 static void
81 xml_start_element (Xml *xml, const char *element_name)
82 {
83   XmlElement *parent = NULL;
84
85   if (xml->stack)
86     {
87       parent = xml->stack->data;
88
89       if (!parent->has_children)
90         xml_printf (xml, ">\n");
91
92       parent->has_children = TRUE;
93     }
94
95   xml_printf (xml, "%*s<%s", g_slist_length(xml->stack)*2, "", element_name);
96
97   xml->stack = g_slist_prepend (xml->stack, xml_element_new (element_name));
98 }
99
100 static void
101 xml_end_element (Xml *xml, const char *name)
102 {
103   XmlElement *elem;
104
105   g_assert (xml->stack != NULL);
106
107   elem = xml->stack->data;
108   xml->stack = g_slist_delete_link (xml->stack, xml->stack);
109
110   if (name != NULL)
111     g_assert_cmpstr (name, ==, elem->name);
112
113   if (elem->has_children)
114     xml_printf (xml, "%*s</%s>\n", g_slist_length (xml->stack)*2, "", elem->name);
115   else
116     xml_printf (xml, "/>\n");
117
118   xml_element_free (elem);
119 }
120
121 static void
122 xml_end_element_unchecked (Xml *xml)
123 {
124   xml_end_element (xml, NULL);
125 }
126
127 static Xml *
128 xml_open (FILE *file)
129 {
130   Xml *xml;
131
132   xml = g_new (Xml, 1);
133   xml->file = file;
134   xml->stack = NULL;
135
136   return xml;
137 }
138
139 static void
140 xml_close (Xml *xml)
141 {
142   g_assert (xml->stack == NULL);
143   if (xml->file != NULL)
144     {
145       fflush (xml->file);
146       if (xml->file != stdout)
147         fclose (xml->file);
148       xml->file = NULL;
149     }
150 }
151
152 static void
153 xml_free (Xml *xml)
154 {
155   xml_close (xml);
156   g_free (xml);
157 }
158
159
160 static void
161 check_unresolved (GIBaseInfo *info)
162 {
163   if (g_base_info_get_type (info) != GI_INFO_TYPE_UNRESOLVED)
164     return;
165
166   g_critical ("Found unresolved type '%s' '%s'\n",
167               g_base_info_get_name (info), g_base_info_get_namespace (info));
168 }
169
170 static void
171 write_type_name (const gchar *namespace,
172                  GIBaseInfo  *info,
173                  Xml         *file)
174 {
175   if (strcmp (namespace, g_base_info_get_namespace (info)) != 0)
176     xml_printf (file, "%s.", g_base_info_get_namespace (info));
177
178   xml_printf (file, "%s", g_base_info_get_name (info));
179 }
180
181 static void
182 write_type_name_attribute (const gchar *namespace,
183                            GIBaseInfo  *info,
184                            const char  *attr_name,
185                            Xml         *file)
186 {
187   xml_printf (file, " %s=\"", attr_name);
188   write_type_name (namespace, info, file);
189   xml_printf (file, "\"");
190 }
191
192 static void
193 write_type_info (const gchar *namespace,
194                  GITypeInfo  *info,
195                  Xml         *file)
196 {
197   gint tag;
198   gint i;
199   GITypeInfo *type;
200   gboolean is_pointer;
201
202   check_unresolved ((GIBaseInfo*)info);
203
204   tag = g_type_info_get_tag (info);
205   is_pointer = g_type_info_is_pointer (info);
206
207   if (tag == GI_TYPE_TAG_VOID)
208     {
209       xml_start_element (file, "type");
210
211       xml_printf (file, " name=\"%s\"", is_pointer ? "any" : "none");
212
213       xml_end_element (file, "type");
214     }
215   else if (G_TYPE_TAG_IS_BASIC (tag))
216     {
217       xml_start_element (file, "type");
218       xml_printf (file, " name=\"%s\"", g_type_tag_to_string (tag));
219       xml_end_element (file, "type");
220     }
221   else if (tag == GI_TYPE_TAG_ARRAY)
222     {
223       gint length, size;
224
225       xml_start_element (file, "array");
226
227       type = g_type_info_get_param_type (info, 0);
228
229       length = g_type_info_get_array_length (info);
230       if (length >= 0)
231         xml_printf (file, " length=\"%d\"", length);
232
233       size = g_type_info_get_array_fixed_size (info);
234       if (size >= 0)
235         xml_printf (file, " fixed-size=\"%d\"", size);
236
237       if (g_type_info_is_zero_terminated (info))
238         xml_printf (file, " zero-terminated=\"1\"");
239
240       write_type_info (namespace, type, file);
241
242       g_base_info_unref ((GIBaseInfo *)type);
243
244       xml_end_element (file, "array");
245     }
246   else if (tag == GI_TYPE_TAG_INTERFACE)
247     {
248       GIBaseInfo *iface = g_type_info_get_interface (info);
249       xml_start_element (file, "type");
250       write_type_name_attribute (namespace, iface, "name", file);
251       xml_end_element (file, "type");
252       g_base_info_unref (iface);
253     }
254   else if (tag == GI_TYPE_TAG_GLIST)
255     {
256       xml_start_element (file, "type");
257       xml_printf (file, " name=\"GLib.List\"");
258       type = g_type_info_get_param_type (info, 0);
259       if (type)
260         {
261           write_type_info (namespace, type, file);
262           g_base_info_unref ((GIBaseInfo *)type);
263         }
264       xml_end_element (file, "type");
265     }
266   else if (tag == GI_TYPE_TAG_GSLIST)
267     {
268       xml_start_element (file, "type");
269       xml_printf (file, " name=\"GLib.SList\"");
270       type = g_type_info_get_param_type (info, 0);
271       if (type)
272         {
273           write_type_info (namespace, type, file);
274           g_base_info_unref ((GIBaseInfo *)type);
275         }
276       xml_end_element (file, "type");
277     }
278   else if (tag == GI_TYPE_TAG_GHASH)
279     {
280       xml_start_element (file, "type");
281       xml_printf (file, " name=\"GLib.HashTable\"");
282       type = g_type_info_get_param_type (info, 0);
283       if (type)
284         {
285           write_type_info (namespace, type, file);
286           g_base_info_unref ((GIBaseInfo *)type);
287           type = g_type_info_get_param_type (info, 1);
288           write_type_info (namespace, type, file);
289           g_base_info_unref ((GIBaseInfo *)type);
290         }
291       xml_end_element (file, "type");
292     }
293   else if (tag == GI_TYPE_TAG_ERROR)
294     {
295       gint n;
296
297       xml_start_element (file, "type");
298       xml_printf (file, " name=\"GLib.Error\"");
299
300       n = g_type_info_get_n_error_domains (info);
301       if (n > 0)
302         {
303           for (i = 0; i < n; i++)
304             {
305               GIErrorDomainInfo *ed = g_type_info_get_error_domain (info, i);
306               xml_start_element (file, "type");
307               write_type_name_attribute (namespace, (GIBaseInfo *)ed, "name", file);
308               xml_end_element (file, "type");
309               g_base_info_unref ((GIBaseInfo *)ed);
310             }
311         }
312
313       xml_end_element (file, "type");
314     }
315   else
316     {
317       g_printerr ("Unhandled type tag %d\n", tag);
318       g_assert_not_reached ();
319     }
320 }
321
322 static void
323 write_attributes (Xml *file,
324                    GIBaseInfo *info)
325 {
326   GIAttributeIter iter = { 0, };
327   char *name, *value;
328
329   while (g_base_info_iterate_attributes (info, &iter, &name, &value))
330     {
331       xml_start_element (file, "attribute");
332       xml_printf (file, " name=\"%s\" value=\"%s\"", name, value);
333       xml_end_element (file, "attribute");
334     }
335 }
336
337 static void
338 write_constant_value (const gchar *namespace,
339                       GITypeInfo *info,
340                       GArgument *argument,
341                       Xml *file);
342
343 static void
344 write_callback_info (const gchar    *namespace,
345                      GICallbackInfo *info,
346                      Xml            *file);
347
348 static void
349 write_field_info (const gchar *namespace,
350                   GIFieldInfo *info,
351                   GIConstantInfo *branch,
352                   Xml         *file)
353 {
354   const gchar *name;
355   GIFieldInfoFlags flags;
356   gint size;
357   gint offset;
358   GITypeInfo *type;
359   GIBaseInfo *interface;
360   GArgument value;
361
362   name = g_base_info_get_name ((GIBaseInfo *)info);
363   flags = g_field_info_get_flags (info);
364   size = g_field_info_get_size (info);
365   offset = g_field_info_get_offset (info);
366
367   xml_start_element (file, "field");
368   xml_printf (file, " name=\"%s\"", name);
369
370   /* Fields are assumed to be read-only
371    * (see also girwriter.py and girparser.c)
372    */
373   if (!(flags & GI_FIELD_IS_READABLE))
374     xml_printf (file, " readable=\"0\"");
375   if (flags & GI_FIELD_IS_WRITABLE)
376     xml_printf (file, " writable=\"1\"");
377
378   if (size)
379     xml_printf (file, " bits=\"%d\"", size);
380
381   write_attributes (file, (GIBaseInfo*) info);
382
383   type = g_field_info_get_type (info);
384
385   if (branch)
386     {
387       xml_printf (file, " branch=\"");
388       type = g_constant_info_get_type (branch);
389       g_constant_info_get_value (branch, &value);
390       write_constant_value (namespace, type, &value, file);
391       xml_printf (file, "\"");
392     }
393
394   if (show_all)
395     {
396       if (offset >= 0)
397         xml_printf (file, "offset=\"%d\"", offset);
398     }
399
400   interface = g_type_info_get_interface (type);
401   if (interface && g_base_info_get_type(interface) == GI_INFO_TYPE_CALLBACK)
402     write_callback_info (namespace, (GICallbackInfo *)interface, file);
403   else
404     write_type_info (namespace, type, file);
405
406   if (interface)
407     g_base_info_unref (interface);
408
409   g_base_info_unref ((GIBaseInfo *)type);
410
411   xml_end_element (file, "field");
412 }
413
414 static void
415 write_callable_info (const gchar    *namespace,
416                      GICallableInfo *info,
417                      Xml            *file)
418 {
419   GITypeInfo *type;
420   gint i;
421
422   write_attributes (file, (GIBaseInfo*) info);
423
424   type = g_callable_info_get_return_type (info);
425
426   xml_start_element (file, "return-value");
427
428   switch (g_callable_info_get_caller_owns (info))
429     {
430     case GI_TRANSFER_NOTHING:
431       xml_printf (file, " transfer-ownership=\"none\"");
432       break;
433     case GI_TRANSFER_CONTAINER:
434       xml_printf (file, " transfer-ownership=\"container\"");
435       break;
436     case GI_TRANSFER_EVERYTHING:
437       xml_printf (file, " transfer-ownership=\"full\"");
438       break;
439     default:
440       g_assert_not_reached ();
441     }
442
443   if (g_callable_info_may_return_null (info))
444     xml_printf (file, " allow-none=\"1\"");
445
446   write_type_info (namespace, type, file);
447
448   xml_end_element (file, "return-value");
449
450   if (g_callable_info_get_n_args (info) <= 0)
451     return;
452
453   xml_start_element (file, "parameters");
454   for (i = 0; i < g_callable_info_get_n_args (info); i++)
455     {
456       GIArgInfo *arg = g_callable_info_get_arg (info, i);
457
458       xml_start_element (file, "parameter");
459       xml_printf (file, " name=\"%s\"",
460                   g_base_info_get_name ((GIBaseInfo *) arg));
461
462       switch (g_arg_info_get_ownership_transfer (arg))
463         {
464         case GI_TRANSFER_NOTHING:
465           xml_printf (file, " transfer-ownership=\"none\"");
466           break;
467         case GI_TRANSFER_CONTAINER:
468           xml_printf (file, " transfer-ownership=\"container\"");
469           break;
470         case GI_TRANSFER_EVERYTHING:
471           xml_printf (file, " transfer-ownership=\"full\"");
472           break;
473         default:
474           g_assert_not_reached ();
475         }
476
477       switch (g_arg_info_get_direction (arg))
478         {
479         case GI_DIRECTION_IN:
480           break;
481         case GI_DIRECTION_OUT:
482           xml_printf (file, " direction=\"out\"");
483           break;
484         case GI_DIRECTION_INOUT:
485           xml_printf (file, " direction=\"inout\"");
486           break;
487         }
488
489       if (g_arg_info_may_be_null (arg))
490         xml_printf (file, " allow-none=\"1\"");
491
492       if (g_arg_info_is_dipper (arg))
493         xml_printf (file, " dipper=\"1\"");
494
495       if (g_arg_info_is_return_value (arg))
496         xml_printf (file, " retval=\"1\"");
497
498       if (g_arg_info_is_optional (arg))
499         xml_printf (file, " optional=\"1\"");
500
501       switch (g_arg_info_get_scope (arg))
502         {
503         case GI_SCOPE_TYPE_INVALID:
504           break;
505         case GI_SCOPE_TYPE_CALL:
506           xml_printf (file, " scope=\"call\"");
507           break;
508         case GI_SCOPE_TYPE_ASYNC:
509           xml_printf (file, " scope=\"async\"");
510           break;
511         case GI_SCOPE_TYPE_NOTIFIED:
512           xml_printf (file, " scope=\"notified\"");
513           break;
514         }
515
516       if (g_arg_info_get_closure (arg) >= 0)
517         xml_printf (file, " closure=\"%d\"", g_arg_info_get_closure (arg));
518
519       if (g_arg_info_get_destroy (arg) >= 0)
520         xml_printf (file, " destroy=\"%d\"", g_arg_info_get_destroy (arg));
521
522       type = g_arg_info_get_type (arg);
523       write_type_info (namespace, type, file);
524
525       xml_end_element (file, "parameter");
526
527       g_base_info_unref ((GIBaseInfo *)arg);
528     }
529
530   xml_end_element (file, "parameters");
531   g_base_info_unref ((GIBaseInfo *)type);
532 }
533
534 static void
535 write_function_info (const gchar    *namespace,
536                      GIFunctionInfo *info,
537                      Xml            *file)
538 {
539   GIFunctionInfoFlags flags;
540   const gchar *tag;
541   const gchar *name;
542   const gchar *symbol;
543   gboolean deprecated;
544   gboolean throws;
545
546   flags = g_function_info_get_flags (info);
547   name = g_base_info_get_name ((GIBaseInfo *)info);
548   symbol = g_function_info_get_symbol (info);
549   deprecated = g_base_info_is_deprecated ((GIBaseInfo *)info);
550   throws = flags & GI_FUNCTION_THROWS;
551
552   if (flags & GI_FUNCTION_IS_CONSTRUCTOR)
553     tag = "constructor";
554   else if (flags & GI_FUNCTION_IS_METHOD)
555     tag = "method";
556   else
557     tag = "function";
558
559   xml_start_element (file, tag);
560   xml_printf (file, " name=\"%s\" c:identifier=\"%s\"",
561               name, symbol);
562
563   if (flags & GI_FUNCTION_IS_SETTER)
564     xml_printf (file, " type=\"setter\"");
565   else if (flags & GI_FUNCTION_IS_GETTER)
566     xml_printf (file, " type=\"getter\"");
567
568   if (deprecated)
569     xml_printf (file, " deprecated=\"1\"");
570
571   if (throws)
572     xml_printf (file, " throws=\"1\"");
573
574   write_callable_info (namespace, (GICallableInfo*)info, file);
575   xml_end_element (file, tag);
576 }
577
578 static void
579 write_callback_info (const gchar    *namespace,
580                      GICallbackInfo *info,
581                      Xml            *file)
582 {
583   const gchar *name;
584   gboolean deprecated;
585
586   name = g_base_info_get_name ((GIBaseInfo *)info);
587   deprecated = g_base_info_is_deprecated ((GIBaseInfo *)info);
588
589   xml_start_element (file, "callback");
590   xml_printf (file, " name=\"%s\"", name);
591
592   if (deprecated)
593     xml_printf (file, " deprecated=\"1\"");
594
595   write_callable_info (namespace, (GICallableInfo*)info, file);
596   xml_end_element (file, "callback");
597 }
598
599 static void
600 write_struct_info (const gchar  *namespace,
601                    GIStructInfo *info,
602                    Xml          *file)
603 {
604   const gchar *name;
605   const gchar *type_name;
606   const gchar *type_init;
607   gboolean deprecated;
608   gboolean is_gtype_struct;
609   gboolean foreign;
610   gint i;
611   gint size;
612   int n_elts;
613
614   name = g_base_info_get_name ((GIBaseInfo *)info);
615   deprecated = g_base_info_is_deprecated ((GIBaseInfo *)info);
616
617   type_name = g_registered_type_info_get_type_name ((GIRegisteredTypeInfo*)info);
618   type_init = g_registered_type_info_get_type_init ((GIRegisteredTypeInfo*)info);
619
620   if (g_base_info_get_type ((GIBaseInfo *)info) == GI_INFO_TYPE_BOXED)
621     {
622       xml_start_element (file, "glib:boxed");
623       xml_printf (file, " glib:name=\"%s\"", name);
624     }
625   else
626     {
627       xml_start_element (file, "record");
628       xml_printf (file, " name=\"%s\"", name);
629     }
630
631   if (type_name != NULL)
632     xml_printf (file, " glib:type-name=\"%s\" glib:get-type=\"%s\"", type_name, type_init);
633
634   if (deprecated)
635     xml_printf (file, " deprecated=\"1\"");
636
637   is_gtype_struct = g_struct_info_is_gtype_struct (info);
638   if (is_gtype_struct)
639     xml_printf (file, " glib:is-gtype-struct=\"1\"");
640
641   write_attributes (file, (GIBaseInfo*) info);
642
643   size = g_struct_info_get_size (info);
644   if (show_all && size >= 0)
645     xml_printf (file, " size=\"%d\"", size);
646
647   foreign = g_struct_info_is_foreign (info);
648   if (foreign)
649     xml_printf (file, " foreign=\"1\"");
650
651   n_elts = g_struct_info_get_n_fields (info) + g_struct_info_get_n_methods (info);
652   if (n_elts > 0)
653     {
654       for (i = 0; i < g_struct_info_get_n_fields (info); i++)
655         {
656           GIFieldInfo *field = g_struct_info_get_field (info, i);
657           write_field_info (namespace, field, NULL, file);
658           g_base_info_unref ((GIBaseInfo *)field);
659         }
660
661       for (i = 0; i < g_struct_info_get_n_methods (info); i++)
662         {
663           GIFunctionInfo *function = g_struct_info_get_method (info, i);
664           write_function_info (namespace, function, file);
665           g_base_info_unref ((GIBaseInfo *)function);
666         }
667
668     }
669
670   xml_end_element_unchecked (file);
671 }
672
673 static void
674 write_value_info (const gchar *namespace,
675                   GIValueInfo *info,
676                   Xml         *file)
677 {
678   const gchar *name;
679   glong value;
680   gboolean deprecated;
681
682   name = g_base_info_get_name ((GIBaseInfo *)info);
683   value = g_value_info_get_value (info);
684   deprecated = g_base_info_is_deprecated ((GIBaseInfo *)info);
685
686   xml_start_element (file, "member");
687   xml_printf (file, " name=\"%s\" value=\"%ld\"", name, value);
688
689   if (deprecated)
690     xml_printf (file, " deprecated=\"1\"");
691
692   write_attributes (file, (GIBaseInfo*) info);
693
694   xml_end_element (file, "member");
695 }
696
697 static void
698 write_constant_value (const gchar *namespace,
699                       GITypeInfo *type,
700                       GArgument  *value,
701                       Xml        *file)
702 {
703   switch (g_type_info_get_tag (type))
704     {
705     case GI_TYPE_TAG_BOOLEAN:
706       xml_printf (file, "%d", value->v_boolean);
707       break;
708     case GI_TYPE_TAG_INT8:
709       xml_printf (file, "%d", value->v_int8);
710       break;
711     case GI_TYPE_TAG_UINT8:
712       xml_printf (file, "%d", value->v_uint8);
713       break;
714     case GI_TYPE_TAG_INT16:
715       xml_printf (file, "%" G_GINT16_FORMAT, value->v_int16);
716       break;
717     case GI_TYPE_TAG_UINT16:
718       xml_printf (file, "%" G_GUINT16_FORMAT, value->v_uint16);
719       break;
720     case GI_TYPE_TAG_INT32:
721       xml_printf (file, "%" G_GINT32_FORMAT, value->v_int32);
722       break;
723     case GI_TYPE_TAG_UINT32:
724       xml_printf (file, "%" G_GUINT32_FORMAT, value->v_uint32);
725       break;
726     case GI_TYPE_TAG_INT64:
727       xml_printf (file, "%" G_GINT64_FORMAT, value->v_int64);
728       break;
729     case GI_TYPE_TAG_UINT64:
730       xml_printf (file, "%" G_GUINT64_FORMAT, value->v_uint64);
731       break;
732     case GI_TYPE_TAG_INT:
733       xml_printf (file, "%d", value->v_int);
734       break;
735     case GI_TYPE_TAG_UINT:
736       xml_printf (file, "%d", value->v_uint);
737       break;
738     case GI_TYPE_TAG_LONG:
739       xml_printf (file, "%ld", value->v_long);
740       break;
741     case GI_TYPE_TAG_ULONG:
742       xml_printf (file, "%ld", value->v_ulong);
743       break;
744     case GI_TYPE_TAG_SSIZE:
745       xml_printf (file, "%zd", value->v_ssize);
746       break;
747     case GI_TYPE_TAG_SIZE:
748       xml_printf (file, "%zd", value->v_size);
749       break;
750     case GI_TYPE_TAG_FLOAT:
751       xml_printf (file, "%f", value->v_float);
752       break;
753     case GI_TYPE_TAG_DOUBLE:
754       xml_printf (file, "%f", value->v_double);
755       break;
756     case GI_TYPE_TAG_UTF8:
757     case GI_TYPE_TAG_FILENAME:
758       xml_printf (file, "%s", value->v_string);
759       break;
760     default:
761       g_assert_not_reached ();
762     }
763 }
764
765 static void
766 write_constant_info (const gchar    *namespace,
767                      GIConstantInfo *info,
768                      Xml            *file)
769 {
770   GITypeInfo *type;
771   const gchar *name;
772   gboolean deprecated;
773   GArgument value;
774
775   name = g_base_info_get_name ((GIBaseInfo *)info);
776   deprecated = g_base_info_is_deprecated ((GIBaseInfo *)info);
777
778   xml_start_element (file, "constant");
779   xml_printf (file, " name=\"%s\"", name);
780
781   type = g_constant_info_get_type (info);
782   xml_printf (file, " value=\"");
783
784   g_constant_info_get_value (info, &value);
785   write_constant_value (namespace, type, &value, file);
786   xml_printf (file, "\"");
787
788   write_type_info (namespace, type, file);
789
790   write_attributes (file, (GIBaseInfo*) info);
791
792   xml_end_element (file, "constant");
793
794   g_base_info_unref ((GIBaseInfo *)type);
795 }
796
797
798 static void
799 write_enum_info (const gchar *namespace,
800                  GIEnumInfo *info,
801                  Xml         *file)
802 {
803   const gchar *name;
804   const gchar *type_name;
805   const gchar *type_init;
806   gboolean deprecated;
807   gint i;
808
809   name = g_base_info_get_name ((GIBaseInfo *)info);
810   deprecated = g_base_info_is_deprecated ((GIBaseInfo *)info);
811
812   type_name = g_registered_type_info_get_type_name ((GIRegisteredTypeInfo*)info);
813   type_init = g_registered_type_info_get_type_init ((GIRegisteredTypeInfo*)info);
814
815   if (g_base_info_get_type ((GIBaseInfo *)info) == GI_INFO_TYPE_ENUM)
816     xml_start_element (file, "enumeration");
817   else
818     xml_start_element (file, "bitfield");
819   xml_printf (file, " name=\"%s\"", name);
820
821   if (type_init)
822     xml_printf (file, " glib:type-name=\"%s\" glib:get-type=\"%s\"", type_name, type_init);
823
824   if (deprecated)
825     xml_printf (file, " deprecated=\"1\"");
826
827   write_attributes (file, (GIBaseInfo*) info);
828
829   for (i = 0; i < g_enum_info_get_n_values (info); i++)
830     {
831       GIValueInfo *value = g_enum_info_get_value (info, i);
832       write_value_info (namespace, value, file);
833       g_base_info_unref ((GIBaseInfo *)value);
834     }
835
836   xml_end_element_unchecked (file);
837 }
838
839 static void
840 write_signal_info (const gchar  *namespace,
841                    GISignalInfo *info,
842                    Xml          *file)
843 {
844   GSignalFlags flags;
845   const gchar *name;
846   gboolean deprecated;
847
848   name = g_base_info_get_name ((GIBaseInfo *)info);
849   flags = g_signal_info_get_flags (info);
850   deprecated = g_base_info_is_deprecated ((GIBaseInfo *)info);
851
852   xml_start_element (file, "glib:signal");
853   xml_printf (file, " name=\"%s\"", name);
854
855   if (deprecated)
856     xml_printf (file, " deprecated=\"1\"");
857
858   if (flags & G_SIGNAL_RUN_FIRST)
859     xml_printf (file, " when=\"FIRST\"");
860   else if (flags & G_SIGNAL_RUN_LAST)
861     xml_printf (file, " when=\"LAST\"");
862   else if (flags & G_SIGNAL_RUN_CLEANUP)
863     xml_printf (file, " when=\"CLEANUP\"");
864
865   if (flags & G_SIGNAL_NO_RECURSE)
866     xml_printf (file, " no-recurse=\"1\"");
867
868   if (flags & G_SIGNAL_DETAILED)
869     xml_printf (file, " detailed=\"1\"");
870
871   if (flags & G_SIGNAL_ACTION)
872     xml_printf (file, " action=\"1\"");
873
874   if (flags & G_SIGNAL_NO_HOOKS)
875     xml_printf (file, " no-hooks=\"1\"");
876
877   write_callable_info (namespace, (GICallableInfo*)info, file);
878
879   xml_end_element (file, "glib:signal");
880 }
881
882 static void
883 write_vfunc_info (const gchar *namespace,
884                   GIVFuncInfo *info,
885                   Xml         *file)
886 {
887   GIVFuncInfoFlags flags;
888   const gchar *name;
889   GIFunctionInfo *invoker;
890   gboolean deprecated;
891   gint offset;
892
893   name = g_base_info_get_name ((GIBaseInfo *)info);
894   flags = g_vfunc_info_get_flags (info);
895   deprecated = g_base_info_is_deprecated ((GIBaseInfo *)info);
896   offset = g_vfunc_info_get_offset (info);
897   invoker = g_vfunc_info_get_invoker (info);
898
899   xml_start_element (file, "virtual-method");
900   xml_printf (file, " name=\"%s\"", name);
901
902   if (deprecated)
903     xml_printf (file, " deprecated=\"1\"");
904
905   if (flags & GI_VFUNC_MUST_CHAIN_UP)
906     xml_printf (file, " must-chain-up=\"1\"");
907
908   if (flags & GI_VFUNC_MUST_OVERRIDE)
909     xml_printf (file, " override=\"always\"");
910   else if (flags & GI_VFUNC_MUST_NOT_OVERRIDE)
911     xml_printf (file, " override=\"never\"");
912
913   xml_printf (file, " offset=\"%d\"", offset);
914
915   if (invoker)
916     xml_printf (file, " invoker=\"%s\"", g_base_info_get_name ((GIBaseInfo*)invoker));
917
918   write_callable_info (namespace, (GICallableInfo*)info, file);
919
920   xml_end_element (file, "virtual-method");
921 }
922
923 static void
924 write_property_info (const gchar    *namespace,
925                      GIPropertyInfo *info,
926                      Xml            *file)
927 {
928   GParamFlags flags;
929   const gchar *name;
930   gboolean deprecated;
931   GITypeInfo *type;
932
933   name = g_base_info_get_name ((GIBaseInfo *)info);
934   flags = g_property_info_get_flags (info);
935   deprecated = g_base_info_is_deprecated ((GIBaseInfo *)info);
936
937   xml_start_element (file, "property");
938   xml_printf (file, " name=\"%s\"", name);
939
940   if (deprecated)
941     xml_printf (file, " deprecated=\"1\"");
942
943   /* Properties are assumed to be read-only (see also girwriter.py) */
944   if (!(flags & G_PARAM_READABLE))
945     xml_printf (file, " readable=\"0\"");
946   if (flags & G_PARAM_WRITABLE)
947     xml_printf (file, " writable=\"1\"");
948
949   if (flags & G_PARAM_CONSTRUCT)
950     xml_printf (file, " construct=\"1\"");
951
952   if (flags & G_PARAM_CONSTRUCT_ONLY)
953     xml_printf (file, " construct-only=\"1\"");
954
955   write_attributes (file, (GIBaseInfo*) info);
956
957   type = g_property_info_get_type (info);
958
959   write_type_info (namespace, type, file);
960
961   xml_end_element (file, "property");
962 }
963
964 static void
965 write_object_info (const gchar  *namespace,
966                    GIObjectInfo *info,
967                    Xml          *file)
968 {
969   const gchar *name;
970   const gchar *type_name;
971   const gchar *type_init;
972   gboolean deprecated;
973   gboolean is_abstract;
974   GIObjectInfo *pnode;
975   GIStructInfo *class_struct;
976   gint i;
977
978   name = g_base_info_get_name ((GIBaseInfo *)info);
979   deprecated = g_base_info_is_deprecated ((GIBaseInfo *)info);
980   is_abstract = g_object_info_get_abstract (info);
981
982   type_name = g_registered_type_info_get_type_name ((GIRegisteredTypeInfo*)info);
983   type_init = g_registered_type_info_get_type_init ((GIRegisteredTypeInfo*)info);
984   xml_start_element (file, "class");
985   xml_printf (file, " name=\"%s\"", name);
986
987   pnode = g_object_info_get_parent (info);
988   if (pnode)
989     {
990       write_type_name_attribute (namespace, (GIBaseInfo *)pnode, "parent", file);
991       g_base_info_unref ((GIBaseInfo *)pnode);
992     }
993
994   class_struct = g_object_info_get_class_struct (info);
995   if (class_struct)
996     {
997       write_type_name_attribute (namespace, (GIBaseInfo*) class_struct, "glib:type-struct", file);
998       g_base_info_unref ((GIBaseInfo*)class_struct);
999     }
1000
1001   if (is_abstract)
1002     xml_printf (file, " abstract=\"1\"");
1003
1004   xml_printf (file, " glib:type-name=\"%s\" glib:get-type=\"%s\"", type_name, type_init);
1005
1006   if (deprecated)
1007     xml_printf (file, " deprecated=\"1\"");
1008
1009   write_attributes (file, (GIBaseInfo*) info);
1010
1011   if (g_object_info_get_n_interfaces (info) > 0)
1012     {
1013       for (i = 0; i < g_object_info_get_n_interfaces (info); i++)
1014         {
1015           GIInterfaceInfo *imp = g_object_info_get_interface (info, i);
1016           xml_start_element (file, "implements");
1017           write_type_name_attribute (namespace, (GIBaseInfo *)imp, "name", file);
1018           xml_end_element (file, "implements");
1019           g_base_info_unref ((GIBaseInfo*)imp);
1020         }
1021     }
1022
1023   for (i = 0; i < g_object_info_get_n_fields (info); i++)
1024     {
1025       GIFieldInfo *field = g_object_info_get_field (info, i);
1026       write_field_info (namespace, field, NULL, file);
1027       g_base_info_unref ((GIBaseInfo *)field);
1028     }
1029
1030   for (i = 0; i < g_object_info_get_n_methods (info); i++)
1031     {
1032       GIFunctionInfo *function = g_object_info_get_method (info, i);
1033       write_function_info (namespace, function, file);
1034       g_base_info_unref ((GIBaseInfo *)function);
1035     }
1036
1037   for (i = 0; i < g_object_info_get_n_properties (info); i++)
1038     {
1039       GIPropertyInfo *prop = g_object_info_get_property (info, i);
1040       write_property_info (namespace, prop, file);
1041       g_base_info_unref ((GIBaseInfo *)prop);
1042     }
1043
1044   for (i = 0; i < g_object_info_get_n_signals (info); i++)
1045     {
1046       GISignalInfo *signal = g_object_info_get_signal (info, i);
1047       write_signal_info (namespace, signal, file);
1048       g_base_info_unref ((GIBaseInfo *)signal);
1049     }
1050
1051   for (i = 0; i < g_object_info_get_n_vfuncs (info); i++)
1052     {
1053       GIVFuncInfo *vfunc = g_object_info_get_vfunc (info, i);
1054       write_vfunc_info (namespace, vfunc, file);
1055       g_base_info_unref ((GIBaseInfo *)vfunc);
1056     }
1057
1058   for (i = 0; i < g_object_info_get_n_constants (info); i++)
1059     {
1060       GIConstantInfo *constant = g_object_info_get_constant (info, i);
1061       write_constant_info (namespace, constant, file);
1062       g_base_info_unref ((GIBaseInfo *)constant);
1063     }
1064
1065   xml_end_element (file, "class");
1066 }
1067
1068 static void
1069 write_interface_info (const gchar     *namespace,
1070                       GIInterfaceInfo *info,
1071                       Xml             *file)
1072 {
1073   const gchar *name;
1074   const gchar *type_name;
1075   const gchar *type_init;
1076   GIStructInfo *class_struct;
1077   gboolean deprecated;
1078   gint i;
1079
1080   name = g_base_info_get_name ((GIBaseInfo *)info);
1081   deprecated = g_base_info_is_deprecated ((GIBaseInfo *)info);
1082
1083   type_name = g_registered_type_info_get_type_name ((GIRegisteredTypeInfo*)info);
1084   type_init = g_registered_type_info_get_type_init ((GIRegisteredTypeInfo*)info);
1085   xml_start_element (file, "interface");
1086   xml_printf (file, " name=\"%s\" glib:type-name=\"%s\" glib:get-type=\"%s\"",
1087              name, type_name, type_init);
1088
1089   class_struct = g_interface_info_get_iface_struct (info);
1090   if (class_struct)
1091     {
1092       write_type_name_attribute (namespace, (GIBaseInfo*) class_struct, "glib:type-struct", file);
1093       g_base_info_unref ((GIBaseInfo*)class_struct);
1094     }
1095
1096   if (deprecated)
1097     xml_printf (file, " deprecated=\"1\"");
1098
1099   write_attributes (file, (GIBaseInfo*) info);
1100
1101   if (g_interface_info_get_n_prerequisites (info) > 0)
1102     {
1103       for (i = 0; i < g_interface_info_get_n_prerequisites (info); i++)
1104         {
1105           GIBaseInfo *req = g_interface_info_get_prerequisite (info, i);
1106
1107           xml_start_element (file, "prerequisite");
1108           write_type_name_attribute (namespace, req, "name", file);
1109
1110           xml_end_element_unchecked (file);
1111           g_base_info_unref (req);
1112         }
1113     }
1114
1115   for (i = 0; i < g_interface_info_get_n_methods (info); i++)
1116     {
1117       GIFunctionInfo *function = g_interface_info_get_method (info, i);
1118       write_function_info (namespace, function, file);
1119       g_base_info_unref ((GIBaseInfo *)function);
1120     }
1121
1122   for (i = 0; i < g_interface_info_get_n_properties (info); i++)
1123     {
1124       GIPropertyInfo *prop = g_interface_info_get_property (info, i);
1125       write_property_info (namespace, prop, file);
1126       g_base_info_unref ((GIBaseInfo *)prop);
1127     }
1128
1129   for (i = 0; i < g_interface_info_get_n_signals (info); i++)
1130     {
1131       GISignalInfo *signal = g_interface_info_get_signal (info, i);
1132       write_signal_info (namespace, signal, file);
1133       g_base_info_unref ((GIBaseInfo *)signal);
1134     }
1135
1136   for (i = 0; i < g_interface_info_get_n_vfuncs (info); i++)
1137     {
1138       GIVFuncInfo *vfunc = g_interface_info_get_vfunc (info, i);
1139       write_vfunc_info (namespace, vfunc, file);
1140       g_base_info_unref ((GIBaseInfo *)vfunc);
1141     }
1142
1143   for (i = 0; i < g_interface_info_get_n_constants (info); i++)
1144     {
1145       GIConstantInfo *constant = g_interface_info_get_constant (info, i);
1146       write_constant_info (namespace, constant, file);
1147       g_base_info_unref ((GIBaseInfo *)constant);
1148     }
1149
1150   xml_end_element (file, "interface");
1151 }
1152
1153 static void
1154 write_error_domain_info (const gchar       *namespace,
1155                          GIErrorDomainInfo *info,
1156                          Xml               *file)
1157 {
1158   GIBaseInfo *enum_;
1159   const gchar *name, *quark;
1160
1161   name = g_base_info_get_name ((GIBaseInfo *)info);
1162   quark = g_error_domain_info_get_quark (info);
1163   enum_ = (GIBaseInfo *)g_error_domain_info_get_codes (info);
1164   xml_start_element (file, "errordomain");
1165   xml_printf (file, " name=\"%s\" get-quark=\"%s\"",
1166               name, quark);
1167   write_type_name_attribute (namespace, enum_, "codes", file);
1168   xml_end_element (file, "errordomain");
1169   g_base_info_unref (enum_);
1170 }
1171
1172 static void
1173 write_union_info (const gchar *namespace,
1174                   GIUnionInfo *info,
1175                   Xml         *file)
1176 {
1177   const gchar *name;
1178   const gchar *type_name;
1179   const gchar *type_init;
1180   gboolean deprecated;
1181   gint i;
1182   gint size;
1183
1184   name = g_base_info_get_name ((GIBaseInfo *)info);
1185   deprecated = g_base_info_is_deprecated ((GIBaseInfo *)info);
1186
1187   type_name = g_registered_type_info_get_type_name ((GIRegisteredTypeInfo*)info);
1188   type_init = g_registered_type_info_get_type_init ((GIRegisteredTypeInfo*)info);
1189
1190   xml_start_element (file, "union");
1191   xml_printf (file, " name=\"%s\"", name);
1192
1193   if (type_name)
1194     xml_printf (file, " type-name=\"%s\" get-type=\"%s\"", type_name, type_init);
1195
1196   if (deprecated)
1197     xml_printf (file, " deprecated=\"1\"");
1198
1199   size = g_union_info_get_size (info);
1200   if (show_all && size >= 0)
1201     xml_printf (file, " size=\"%d\"", size);
1202
1203   write_attributes (file, (GIBaseInfo*) info);
1204
1205   if (g_union_info_is_discriminated (info))
1206     {
1207       gint offset;
1208       GITypeInfo *type;
1209
1210       offset = g_union_info_get_discriminator_offset (info);
1211       type = g_union_info_get_discriminator_type (info);
1212
1213       xml_start_element (file, "discriminator");
1214       xml_printf (file, " offset=\"%d\" type=\"", offset);
1215       write_type_info (namespace, type, file);
1216       xml_end_element (file, "discriminator");
1217       g_base_info_unref ((GIBaseInfo *)type);
1218     }
1219
1220   for (i = 0; i < g_union_info_get_n_fields (info); i++)
1221     {
1222       GIFieldInfo *field = g_union_info_get_field (info, i);
1223       GIConstantInfo *constant = g_union_info_get_discriminator (info, i);
1224       write_field_info (namespace, field, constant, file);
1225       g_base_info_unref ((GIBaseInfo *)field);
1226       if (constant)
1227         g_base_info_unref ((GIBaseInfo *)constant);
1228     }
1229
1230   for (i = 0; i < g_union_info_get_n_methods (info); i++)
1231     {
1232       GIFunctionInfo *function = g_union_info_get_method (info, i);
1233       write_function_info (namespace, function, file);
1234       g_base_info_unref ((GIBaseInfo *)function);
1235     }
1236
1237   xml_end_element (file, "union");
1238 }
1239
1240 static void
1241 write_repository (const char   *namespace,
1242                   gboolean      needs_prefix)
1243 {
1244   FILE *ofile;
1245   gint i, j;
1246   char **dependencies;
1247   GIRepository *repository;
1248   Xml *xml;
1249
1250   repository = g_irepository_get_default ();
1251
1252   if (output == NULL)
1253     ofile = stdout;
1254   else
1255     {
1256       gchar *filename;
1257
1258       if (needs_prefix)
1259         filename = g_strdup_printf ("%s-%s", namespace, output);
1260       else
1261         filename = g_strdup (output);
1262       ofile = g_fopen (filename, "w");
1263
1264       if (ofile == NULL)
1265         {
1266           g_fprintf (stderr, "failed to open '%s': %s\n",
1267                      filename, g_strerror (errno));
1268           g_free (filename);
1269
1270           return;
1271         }
1272
1273       g_free (filename);
1274     }
1275
1276   xml = xml_open (ofile);
1277
1278   xml_printf (xml, "<?xml version=\"1.0\"?>\n");
1279   xml_start_element (xml, "repository");
1280   xml_printf (xml, " version=\"1.0\"\n"
1281               "            xmlns=\"http://www.gtk.org/introspection/core/1.0\"\n"
1282               "            xmlns:c=\"http://www.gtk.org/introspection/c/1.0\"\n"
1283               "            xmlns:glib=\"http://www.gtk.org/introspection/glib/1.0\"");
1284
1285   dependencies = g_irepository_get_dependencies (repository,
1286                                                  namespace);
1287   if (dependencies != NULL)
1288     {
1289       for (i = 0; dependencies[i]; i++)
1290         {
1291           char **parts = g_strsplit (dependencies[i], "-", 2);
1292           xml_start_element (xml, "include");
1293           xml_printf (xml, " name=\"%s\" version=\"%s\"", parts[0], parts[1]);
1294           xml_end_element (xml, "include");
1295           g_strfreev (parts);
1296         }
1297     }
1298
1299   if (TRUE)
1300     {
1301       const gchar *shared_library;
1302       const gchar *c_prefix;
1303       const char *ns = namespace;
1304       const char *version;
1305
1306       version = g_irepository_get_version (repository, ns);
1307
1308       shared_library = g_irepository_get_shared_library (repository, ns);
1309       c_prefix = g_irepository_get_c_prefix (repository, ns);
1310       xml_start_element (xml, "namespace");
1311       xml_printf (xml, " name=\"%s\" version=\"%s\"", ns, version);
1312       if (shared_library)
1313         xml_printf (xml, " shared-library=\"%s\"", shared_library);
1314       if (c_prefix)
1315         xml_printf (xml, " c:prefix=\"%s\"", c_prefix);
1316
1317       for (j = 0; j < g_irepository_get_n_infos (repository, ns); j++)
1318         {
1319           GIBaseInfo *info = g_irepository_get_info (repository, ns, j);
1320           switch (g_base_info_get_type (info))
1321             {
1322             case GI_INFO_TYPE_FUNCTION:
1323               write_function_info (ns, (GIFunctionInfo *)info, xml);
1324               break;
1325
1326             case GI_INFO_TYPE_CALLBACK:
1327               write_callback_info (ns, (GICallbackInfo *)info, xml);
1328               break;
1329
1330             case GI_INFO_TYPE_STRUCT:
1331             case GI_INFO_TYPE_BOXED:
1332               write_struct_info (ns, (GIStructInfo *)info, xml);
1333               break;
1334
1335             case GI_INFO_TYPE_UNION:
1336               write_union_info (ns, (GIUnionInfo *)info, xml);
1337               break;
1338
1339             case GI_INFO_TYPE_ENUM:
1340             case GI_INFO_TYPE_FLAGS:
1341               write_enum_info (ns, (GIEnumInfo *)info, xml);
1342               break;
1343
1344             case GI_INFO_TYPE_CONSTANT:
1345               write_constant_info (ns, (GIConstantInfo *)info, xml);
1346               break;
1347
1348             case GI_INFO_TYPE_OBJECT:
1349               write_object_info (ns, (GIObjectInfo *)info, xml);
1350               break;
1351
1352             case GI_INFO_TYPE_INTERFACE:
1353               write_interface_info (ns, (GIInterfaceInfo *)info, xml);
1354               break;
1355
1356             case GI_INFO_TYPE_ERROR_DOMAIN:
1357               write_error_domain_info (ns, (GIErrorDomainInfo *)info, xml);
1358               break;
1359
1360             default:
1361               g_error ("unknown info type %d\n", g_base_info_get_type (info));
1362             }
1363
1364           g_base_info_unref (info);
1365         }
1366
1367       xml_end_element (xml, "namespace");
1368     }
1369
1370   xml_end_element (xml, "repository");
1371
1372   xml_free (xml);
1373 }
1374
1375 static const guchar *
1376 load_typelib (const gchar  *filename,
1377                GModule     **dlhandle,
1378                gsize        *len)
1379 {
1380   guchar *typelib;
1381   gsize *typelib_size;
1382   GModule *handle;
1383
1384   handle = g_module_open (filename, G_MODULE_BIND_LOCAL|G_MODULE_BIND_LAZY);
1385   if (handle == NULL)
1386     {
1387       g_printerr ("Could not load typelib from '%s': %s\n",
1388                   filename, g_module_error ());
1389       return NULL;
1390     }
1391
1392   if (!g_module_symbol (handle, "_G_TYPELIB", (gpointer *) &typelib))
1393     {
1394       g_printerr ("Could not load typelib from '%s': %s\n",
1395                   filename, g_module_error ());
1396       return NULL;
1397     }
1398
1399   if (!g_module_symbol (handle, "_G_TYPELIB_SIZE", (gpointer *) &typelib_size))
1400     {
1401       g_printerr ("Could not load typelib from '%s': %s\n",
1402                   filename, g_module_error ());
1403       return NULL;
1404     }
1405
1406   *len = *typelib_size;
1407
1408   if (dlhandle)
1409     *dlhandle = handle;
1410
1411   return typelib;
1412 }
1413
1414 int
1415 main (int argc, char *argv[])
1416 {
1417   gboolean shlib = FALSE;
1418   gchar **input = NULL;
1419   GOptionContext *context;
1420   GError *error = NULL;
1421   gboolean needs_prefix;
1422   gint i;
1423   GTypelib *data;
1424   GOptionEntry options[] =
1425     {
1426       { "shlib", 0, 0, G_OPTION_ARG_NONE, &shlib, "handle typelib embedded in shlib", NULL },
1427       { "output", 'o', 0, G_OPTION_ARG_FILENAME, &output, "output file", "FILE" },
1428       { "includedir", 0, 0, G_OPTION_ARG_FILENAME_ARRAY, &includedirs, "include directories in GIR search path", NULL },
1429       { "all", 0, 0, G_OPTION_ARG_NONE, &show_all, "show all available information", NULL, },
1430       { G_OPTION_REMAINING, 0, 0, G_OPTION_ARG_FILENAME_ARRAY, &input, NULL, NULL },
1431       { NULL, }
1432     };
1433
1434   g_log_set_always_fatal (G_LOG_LEVEL_WARNING | G_LOG_LEVEL_CRITICAL);
1435
1436   g_type_init ();
1437
1438   g_typelib_check_sanity ();
1439
1440   context = g_option_context_new ("");
1441   g_option_context_add_main_entries (context, options, NULL);
1442   g_option_context_parse (context, &argc, &argv, &error);
1443
1444   if (!input)
1445     {
1446       g_fprintf (stderr, "no input files\n");
1447
1448       return 1;
1449     }
1450
1451   if (includedirs != NULL)
1452     for (i = 0; includedirs[i]; i++)
1453       g_irepository_prepend_search_path (includedirs[i]);
1454
1455   for (i = 0; input[i]; i++)
1456     {
1457       GModule *dlhandle = NULL;
1458       const guchar *typelib;
1459       gsize len;
1460       const char *namespace;
1461
1462       if (!shlib)
1463         {
1464           if (!g_file_get_contents (input[i], (gchar **)&typelib, &len, &error))
1465             {
1466               g_fprintf (stderr, "failed to read '%s': %s\n",
1467                          input[i], error->message);
1468               g_clear_error (&error);
1469               continue;
1470             }
1471         }
1472       else
1473         {
1474           typelib = load_typelib (input[i], &dlhandle, &len);
1475           if (!typelib)
1476             {
1477               g_fprintf (stderr, "failed to load typelib from '%s'\n",
1478                          input[i]);
1479               continue;
1480             }
1481         }
1482
1483       if (input[i + 1] && output)
1484         needs_prefix = TRUE;
1485       else
1486         needs_prefix = FALSE;
1487
1488       data = g_typelib_new_from_const_memory (typelib, len);
1489       {
1490         GError *error = NULL;
1491         if (!g_typelib_validate (data, &error)) {
1492           g_printerr ("typelib not valid: %s\n", error->message);
1493           g_clear_error (&error);
1494           return 1;
1495         }
1496       }
1497       namespace = g_irepository_load_typelib (g_irepository_get_default (), data, 0,
1498                                               &error);
1499       if (namespace == NULL)
1500         {
1501           g_printerr ("failed to load typelib: %s\n", error->message);
1502           return 1;
1503         }
1504
1505       write_repository (namespace, needs_prefix);
1506
1507       if (dlhandle)
1508         {
1509           g_module_close (dlhandle);
1510           dlhandle = NULL;
1511         }
1512
1513       /* when writing to stdout, stop after the first module */
1514       if (input[i + 1] && !output)
1515         {
1516           g_fprintf (stderr, "warning, %d modules omitted\n",
1517                      g_strv_length (input) - 1);
1518
1519           break;
1520         }
1521     }
1522
1523   return 0;
1524 }