Bug 556489 – callback annotations
[gnome.gobject-introspection] / girepository / ginfo.c
1 /* GObject introspection: Repository implementation
2  *
3  * Copyright (C) 2005 Matthias Clasen
4  *
5  * This library is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU Lesser General Public
7  * License as published by the Free Software Foundation; either
8  * version 2 of the License, or (at your option) any later version.
9  *
10  * This library is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public
16  * License along with this library; if not, write to the
17  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18  * Boston, MA 02111-1307, USA.
19  */
20
21 #include <stdlib.h>
22 #include <string.h>
23
24 #include <glib.h>
25 #include <glib-object.h>
26
27 #include "gtypelib.h"
28 #include "ginfo.h"
29
30 struct _GIBaseInfo 
31 {
32   gint type;
33   gint ref_count;
34   GIRepository *repository;
35   GIBaseInfo *container;
36
37   GTypelib *typelib;
38   guint32 offset;
39 };
40
41 struct _GIUnresolvedInfo
42 {
43   gint type;
44   gint ref_count;
45   GIBaseInfo *container;
46
47   const gchar *name;
48   const gchar *namespace;
49 };
50
51 struct _GICallableInfo
52 {
53   GIBaseInfo base;
54 };
55
56 struct _GIFunctionInfo
57 {
58   GICallableInfo callable;
59 };
60
61 struct _GICallbackInfo
62 {
63   GICallableInfo callable;
64 };
65
66 struct _GIRegisteredTypeInfo
67 {
68   GIBaseInfo base;
69 };
70
71 struct _GIStructInfo
72 {
73   GIRegisteredTypeInfo registered;
74 };
75
76 struct _GIEnumInfo
77 {
78   GIRegisteredTypeInfo registered;
79 };
80
81 struct _GIObjectInfo
82 {
83   GIRegisteredTypeInfo registered;
84 };
85
86 struct _GIInterfaceInfo
87 {
88   GIRegisteredTypeInfo registered;
89 };
90
91 struct _GIConstantInfo
92 {
93   GIBaseInfo base;
94 };
95
96 struct _GIValueInfo
97 {
98   GIBaseInfo base;
99 };
100
101 struct _GISignalInfo
102 {
103   GICallableInfo callable;
104 };
105
106 struct _GIVFuncInfo
107 {
108   GICallableInfo callable;
109 };
110
111 struct _GIPropertyInfo
112 {
113   GIBaseInfo base;
114 };
115
116 struct _GIFieldInfo
117 {
118   GIBaseInfo base;
119 };
120
121 struct _GIArgInfo
122 {
123   GIBaseInfo base;
124 };
125
126 struct _GITypeInfo
127 {
128   GIBaseInfo base;
129 };
130
131 struct _GIUnionInfo
132 {
133   GIRegisteredTypeInfo registered;
134 };
135
136
137 /* info creation */
138 GIBaseInfo *
139 g_info_new_full (GIInfoType     type,
140                  GIRepository  *repository,
141                  GIBaseInfo    *container,
142                  GTypelib     *typelib, 
143                  guint32        offset)
144 {
145   GIBaseInfo *info;
146
147   g_return_val_if_fail (container != NULL || repository != NULL, NULL);
148
149   info = g_new0 (GIBaseInfo, 1);
150
151   info->ref_count = 1;
152   info->type = type;
153
154   info->typelib = typelib;
155   info->offset = offset;
156
157   if (container)
158     info->container = g_base_info_ref (container);
159
160   info->repository = g_object_ref (repository);
161
162   return info;
163 }
164
165 GIBaseInfo *
166 g_info_new (GIInfoType     type,
167             GIBaseInfo    *container,
168             GTypelib     *typelib, 
169             guint32        offset)
170 {
171   return g_info_new_full (type, container->repository, container, typelib, offset);
172 }
173
174 static GIBaseInfo *
175 g_info_from_entry (GIRepository *repository,
176                    GTypelib *typelib,
177                    guint16    index)
178 {
179   GIBaseInfo *result;
180   DirEntry *entry = g_typelib_get_dir_entry (typelib, index);
181
182   if (entry->local)
183     result = g_info_new_full (entry->blob_type, repository, NULL, typelib, entry->offset);
184   else
185     {
186       const gchar *namespace = g_typelib_get_string (typelib, entry->offset);
187       const gchar *name = g_typelib_get_string (typelib, entry->name);
188
189       result = g_irepository_find_by_name (repository, namespace, name);
190       if (result == NULL)
191         {
192           GIUnresolvedInfo *unresolved;
193
194           unresolved = g_new0 (GIUnresolvedInfo, 1);
195
196           unresolved->type = GI_INFO_TYPE_UNRESOLVED;
197           unresolved->ref_count = 1;
198           unresolved->container = NULL;
199           unresolved->name = name;
200           unresolved->namespace = namespace;
201
202           return (GIBaseInfo*)unresolved;
203         }
204       return result;
205     }
206
207   return result;
208 }
209
210 /* GIBaseInfo functions */
211 GIBaseInfo *
212 g_base_info_ref (GIBaseInfo *info)
213 {
214   info->ref_count++;
215
216   return info;
217 }
218
219 void
220 g_base_info_unref (GIBaseInfo *info)
221 {
222   g_assert (info->ref_count > 0);
223   info->ref_count--;
224
225   if (!info->ref_count)
226     {
227       if (info->container)
228         g_base_info_unref (info->container);
229
230       g_object_unref (info->repository);
231
232       g_free (info);
233     }
234 }
235
236 GIInfoType
237 g_base_info_get_type (GIBaseInfo *info)
238 {
239   
240   return info->type;
241 }
242
243 const gchar *
244 g_base_info_get_name (GIBaseInfo *info)
245 {
246   g_assert (info->ref_count > 0);
247   switch (info->type)
248     {
249     case GI_INFO_TYPE_FUNCTION:
250     case GI_INFO_TYPE_CALLBACK:
251     case GI_INFO_TYPE_STRUCT:
252     case GI_INFO_TYPE_BOXED:
253     case GI_INFO_TYPE_ENUM:
254     case GI_INFO_TYPE_FLAGS:
255     case GI_INFO_TYPE_OBJECT:
256     case GI_INFO_TYPE_INTERFACE:
257     case GI_INFO_TYPE_CONSTANT:
258     case GI_INFO_TYPE_ERROR_DOMAIN:
259     case GI_INFO_TYPE_UNION:
260       {
261         CommonBlob *blob = (CommonBlob *)&info->typelib->data[info->offset];
262
263         return g_typelib_get_string (info->typelib, blob->name);
264       }
265       break;
266
267     case GI_INFO_TYPE_VALUE:
268       {
269         ValueBlob *blob = (ValueBlob *)&info->typelib->data[info->offset];
270
271         return g_typelib_get_string (info->typelib, blob->name);
272       }
273       break;
274
275     case GI_INFO_TYPE_SIGNAL:
276       {
277         SignalBlob *blob = (SignalBlob *)&info->typelib->data[info->offset];
278
279         return g_typelib_get_string (info->typelib, blob->name);
280       }
281       break;
282
283     case GI_INFO_TYPE_PROPERTY:
284       {
285         PropertyBlob *blob = (PropertyBlob *)&info->typelib->data[info->offset];
286
287         return g_typelib_get_string (info->typelib, blob->name);
288       }
289       break;
290
291     case GI_INFO_TYPE_VFUNC:
292       {
293         VFuncBlob *blob = (VFuncBlob *)&info->typelib->data[info->offset];
294
295         return g_typelib_get_string (info->typelib, blob->name);
296       }
297       break;
298
299     case GI_INFO_TYPE_FIELD:
300       {
301         FieldBlob *blob = (FieldBlob *)&info->typelib->data[info->offset];
302         
303         return g_typelib_get_string (info->typelib, blob->name);
304       }
305       break;
306
307     case GI_INFO_TYPE_ARG:
308       {
309         ArgBlob *blob = (ArgBlob *)&info->typelib->data[info->offset];
310         
311         return g_typelib_get_string (info->typelib, blob->name);
312       }
313       break;
314     case GI_INFO_TYPE_UNRESOLVED:
315       {
316         GIUnresolvedInfo *unresolved = (GIUnresolvedInfo *)info;
317
318         return unresolved->name;
319       }
320       break;
321     case GI_INFO_TYPE_TYPE:
322     default: ;
323       g_assert_not_reached ();
324       /* unnamed */
325     }
326
327   return NULL;
328 }
329
330 const gchar *
331 g_base_info_get_namespace (GIBaseInfo *info)
332 {
333   Header *header = (Header *)info->typelib->data;
334
335   g_assert (info->ref_count > 0);
336
337   if (info->type == GI_INFO_TYPE_UNRESOLVED)
338     {
339       GIUnresolvedInfo *unresolved = (GIUnresolvedInfo *)info;
340       
341       return unresolved->namespace;
342     }
343
344   return g_typelib_get_string (info->typelib, header->namespace);
345 }
346
347 gboolean 
348 g_base_info_is_deprecated (GIBaseInfo *info)
349 {
350   switch (info->type)
351     {
352     case GI_INFO_TYPE_FUNCTION:
353     case GI_INFO_TYPE_CALLBACK:
354     case GI_INFO_TYPE_STRUCT:
355     case GI_INFO_TYPE_BOXED:
356     case GI_INFO_TYPE_ENUM:
357     case GI_INFO_TYPE_FLAGS:
358     case GI_INFO_TYPE_OBJECT:
359     case GI_INFO_TYPE_INTERFACE:
360     case GI_INFO_TYPE_CONSTANT:
361     case GI_INFO_TYPE_ERROR_DOMAIN:
362       {
363         CommonBlob *blob = (CommonBlob *)&info->typelib->data[info->offset];
364
365         return blob->deprecated;
366       }
367       break;
368
369     case GI_INFO_TYPE_VALUE:
370       {
371         ValueBlob *blob = (ValueBlob *)&info->typelib->data[info->offset];
372
373         return blob->deprecated;
374       }
375       break;
376
377     case GI_INFO_TYPE_SIGNAL:
378       {
379         SignalBlob *blob = (SignalBlob *)&info->typelib->data[info->offset];
380
381         return blob->deprecated;
382       }
383       break;
384
385     case GI_INFO_TYPE_PROPERTY:
386       {
387         PropertyBlob *blob = (PropertyBlob *)&info->typelib->data[info->offset];
388
389         return blob->deprecated;
390       }
391       break;
392
393     case GI_INFO_TYPE_VFUNC:
394     case GI_INFO_TYPE_FIELD:
395     case GI_INFO_TYPE_ARG:
396     case GI_INFO_TYPE_TYPE:
397     default: ;
398       /* no deprecation flag for these */
399     }
400   
401   return FALSE;
402 }
403
404 static int
405 cmp_annotation (const void *av,
406                 const void *bv)
407 {
408   const AnnotationBlob *a = av;
409   const AnnotationBlob *b = bv;
410  
411   if (b->offset < a->offset)
412     return -1;
413
414   if (b->offset > a->offset)
415     return 1;
416   
417   return 0;
418 }
419
420 const gchar *
421 g_base_info_get_annotation (GIBaseInfo   *info,
422                             const gchar *name)
423 {
424   GIBaseInfo *base = (GIBaseInfo *)info;
425   Header *header = (Header *)base->typelib->data;
426   AnnotationBlob blob, *first, *after, *res, *next;
427   const gchar *rname;
428
429   blob.offset = base->offset;
430   
431   first = (AnnotationBlob *) &base->typelib->data[header->annotations];
432   after = (AnnotationBlob *) &base->typelib->data[header->annotations + 
433                                              header->n_annotations * header->annotation_blob_size];
434
435   res = bsearch (&blob, first, header->n_annotations,
436                  header->annotation_blob_size, cmp_annotation);
437   
438   if (res == NULL)
439     return NULL;
440
441   next = res;
442   do 
443     {
444       res = next;
445       next = res -= header->annotation_blob_size;
446     }
447   while (next >= first && next->offset == base->offset);
448     
449   next = res;
450   do 
451     {
452       res = next;
453       
454       rname = g_typelib_get_string (base->typelib, res->name);
455       if (strcmp (name, rname) == 0)
456         return g_typelib_get_string (base->typelib, res->value);
457
458       next = res += header->annotation_blob_size;
459     }
460   while (next < after && next->offset == base->offset);
461
462   return NULL;
463 }
464
465 GIBaseInfo *
466 g_base_info_get_container (GIBaseInfo *info)
467 {
468   return info->container;
469 }
470
471 GTypelib *
472 g_base_info_get_typelib (GIBaseInfo *info)
473 {
474   return info->typelib;
475 }
476
477 /* GIFunctionInfo functions */
478 const gchar *
479 g_function_info_get_symbol (GIFunctionInfo *info)
480 {
481   GIBaseInfo *base = (GIBaseInfo *)info;
482   FunctionBlob *blob = (FunctionBlob *)&base->typelib->data[base->offset];
483
484   return g_typelib_get_string (base->typelib, blob->symbol);
485 }
486
487 GIFunctionInfoFlags
488 g_function_info_get_flags (GIFunctionInfo *info)
489 {
490   GIFunctionInfoFlags flags;
491   GIBaseInfo *base = (GIBaseInfo *)info;
492   FunctionBlob *blob = (FunctionBlob *)&base->typelib->data[base->offset];
493   
494   flags = 0;
495
496   /* Make sure we don't flag Constructors as methods */
497   if (!blob->constructor && !blob->is_static)
498     flags = flags | GI_FUNCTION_IS_METHOD;
499     
500   if (blob->constructor)
501     flags = flags | GI_FUNCTION_IS_CONSTRUCTOR;
502
503   if (blob->getter)
504     flags = flags | GI_FUNCTION_IS_GETTER;
505
506   if (blob->setter)
507     flags = flags | GI_FUNCTION_IS_SETTER;
508
509   if (blob->wraps_vfunc)
510     flags = flags | GI_FUNCTION_WRAPS_VFUNC;
511
512   if (blob->throws)
513     flags = flags | GI_FUNCTION_THROWS;
514
515   return flags;
516 }
517
518 GIPropertyInfo *
519 g_function_info_get_property (GIFunctionInfo *info)
520 {
521   GIBaseInfo *base = (GIBaseInfo *)info;
522   FunctionBlob *blob = (FunctionBlob *)&base->typelib->data[base->offset];
523   GIInterfaceInfo *container = (GIInterfaceInfo *)base->container;
524   
525   return g_interface_info_get_property (container, blob->index);  
526 }
527
528 GIVFuncInfo *
529 g_function_info_get_vfunc (GIFunctionInfo *info)
530 {
531   GIBaseInfo *base = (GIBaseInfo *)info;
532   FunctionBlob *blob = (FunctionBlob *)&base->typelib->data[base->offset];
533   GIInterfaceInfo *container = (GIInterfaceInfo *)base->container;
534   
535   return g_interface_info_get_vfunc (container, blob->index);  
536 }
537
538
539 /* GICallableInfo functions */
540 static guint32
541 signature_offset (GICallableInfo *info)
542 {
543   int sigoff = -1;
544   switch (info->base.type)
545     {
546     case GI_INFO_TYPE_FUNCTION:
547       sigoff = G_STRUCT_OFFSET (FunctionBlob, signature);
548       break;
549     case GI_INFO_TYPE_VFUNC:
550       sigoff = G_STRUCT_OFFSET (VFuncBlob, signature);
551       break;
552     case GI_INFO_TYPE_CALLBACK:
553       sigoff = G_STRUCT_OFFSET (CallbackBlob, signature);
554       break;
555     case GI_INFO_TYPE_SIGNAL:
556       sigoff = G_STRUCT_OFFSET (SignalBlob, signature);
557       break;
558     }
559   if (sigoff >= 0)
560     return *(guint32 *)&info->base.typelib->data[info->base.offset + sigoff];
561   return 0;
562 }
563
564 GITypeInfo *
565 g_type_info_new (GIBaseInfo    *container,
566                  GTypelib     *typelib,
567                  guint32        offset)
568 {
569   SimpleTypeBlob *type = (SimpleTypeBlob *)&typelib->data[offset];
570
571   return (GITypeInfo *) g_info_new (GI_INFO_TYPE_TYPE, container, typelib, 
572                                     (type->reserved == 0 && type->reserved2 == 0) ? offset : type->offset);
573 }
574
575 /**
576  * g_callable_info_get_return_type:
577  * @info: a #GICallableInfo
578  *
579  * Get the return type of a callable item as
580  * a #GITypeInfo
581  *
582  * Returns: a #GITypeInfo idexing the TypeBlob for the
583  * return type of #info
584  */
585 GITypeInfo *
586 g_callable_info_get_return_type (GICallableInfo *info)
587 {
588   GIBaseInfo *base = (GIBaseInfo *)info;
589   guint32 offset;
590
591   offset = signature_offset (info);
592
593   return g_type_info_new (base, base->typelib, offset);
594 }
595
596 /**
597  * g_callable_info_may_return_null:
598  * @info: a #GICallableInfo
599  *
600  * See if a callable could return NULL.
601  *
602  * Returns: TRUE if callable could return NULL
603  */
604 gboolean
605 g_callable_info_may_return_null (GICallableInfo *info)
606 {
607   GIBaseInfo *base = (GIBaseInfo *)info;
608   SignatureBlob *blob = (SignatureBlob *)&base->typelib->data[signature_offset (info)];
609
610   return blob->may_return_null;
611 }
612
613 /**
614  * g_callable_info_get_caller_owns:
615  * @info: a #GICallableInfo
616  *
617  * See whether the caller owns the return value
618  * of this callable.
619  *
620  * Returns: TRUE if the caller owns the return value, FALSE otherwise.
621  */
622 GITransfer
623 g_callable_info_get_caller_owns (GICallableInfo *info)
624 {
625   GIBaseInfo *base = (GIBaseInfo *)info;
626   SignatureBlob *blob = (SignatureBlob *)&base->typelib->data[signature_offset (info)];
627
628   if (blob->caller_owns_return_value)
629     return GI_TRANSFER_EVERYTHING;
630   else if (blob->caller_owns_return_container)
631     return GI_TRANSFER_CONTAINER;
632   else
633     return GI_TRANSFER_NOTHING;
634 }
635
636 /**
637  * g_callable_info_get_n_args:
638  * @info: a #GICallableInfo
639  *
640  * Get the number of arguments (both IN and OUT) for this callable.
641  *
642  * Returns: The number of arguments this callable expects.
643  */
644 gint 
645 g_callable_info_get_n_args (GICallableInfo *info)
646 {
647   GIBaseInfo *base = (GIBaseInfo *)info;
648   gint offset;
649   SignatureBlob *blob;
650
651   offset = signature_offset (info);
652   blob = (SignatureBlob *)&base->typelib->data[offset];
653
654   return blob->n_arguments;
655 }
656
657 /**
658  * g_callable_info_get_arg:
659  * @info: a #GICallableInfo
660  *
661  * Get information about a particular argument of this callable.
662  *
663  * Returns: A #GIArgInfo indexing the typelib on the given argument.
664  */
665 GIArgInfo *
666 g_callable_info_get_arg (GICallableInfo *info,
667                          gint           n)
668 {
669   GIBaseInfo *base = (GIBaseInfo *)info;
670   Header *header = (Header *)base->typelib->data;
671   gint offset;
672
673   offset = signature_offset (info);
674   
675   return (GIArgInfo *) g_info_new (GI_INFO_TYPE_ARG, base, base->typelib, 
676                                    offset + header->signature_blob_size + n * header->arg_blob_size);
677 }
678
679 /* GIArgInfo function */
680 GIDirection
681 g_arg_info_get_direction (GIArgInfo *info)
682 {
683   GIBaseInfo *base = (GIBaseInfo *)info;
684   ArgBlob *blob = (ArgBlob *)&base->typelib->data[base->offset];
685   
686   if (blob->in && blob->out)
687     return GI_DIRECTION_INOUT;
688   else if (blob->out)
689     return GI_DIRECTION_OUT;
690   else
691     return GI_DIRECTION_IN;
692 }
693
694 gboolean
695 g_arg_info_is_return_value (GIArgInfo *info)
696 {
697   GIBaseInfo *base = (GIBaseInfo *)info;
698   ArgBlob *blob = (ArgBlob *)&base->typelib->data[base->offset];
699   
700   return blob->return_value;
701 }
702
703 gboolean
704 g_arg_info_is_dipper (GIArgInfo *info)
705 {
706   GIBaseInfo *base = (GIBaseInfo *)info;
707   ArgBlob *blob = (ArgBlob *)&base->typelib->data[base->offset];
708   
709   return blob->dipper;
710 }
711
712 gboolean
713 g_arg_info_is_optional (GIArgInfo *info)
714 {
715   GIBaseInfo *base = (GIBaseInfo *)info;
716   ArgBlob *blob = (ArgBlob *)&base->typelib->data[base->offset];
717   
718   return blob->optional;
719 }
720
721 gboolean
722 g_arg_info_may_be_null (GIArgInfo *info)
723 {
724   GIBaseInfo *base = (GIBaseInfo *)info;
725   ArgBlob *blob = (ArgBlob *)&base->typelib->data[base->offset];
726   
727   return blob->allow_none;
728 }
729
730 GITransfer
731 g_arg_info_get_ownership_transfer (GIArgInfo *info)
732 {
733   GIBaseInfo *base = (GIBaseInfo *)info;
734   ArgBlob *blob = (ArgBlob *)&base->typelib->data[base->offset];
735
736   if (blob->transfer_ownership)
737     return GI_TRANSFER_EVERYTHING;
738   else if (blob->transfer_container_ownership)
739     return GI_TRANSFER_CONTAINER;
740   else
741     return GI_TRANSFER_NOTHING;
742 }
743
744 GIScopeType
745 g_arg_info_get_scope (GIArgInfo *info)
746 {
747   GIBaseInfo *base = (GIBaseInfo *)info;
748   ArgBlob *blob = (ArgBlob *)&base->typelib->data[base->offset];
749
750   return blob->scope;
751 }
752
753 gint
754 g_arg_info_get_closure (GIArgInfo *info)
755 {
756   GIBaseInfo *base = (GIBaseInfo *)info;
757   ArgBlob *blob = (ArgBlob *)&base->typelib->data[base->offset];
758
759   return blob->closure;
760 }
761
762 gint
763 g_arg_info_get_destroy (GIArgInfo *info)
764 {
765   GIBaseInfo *base = (GIBaseInfo *)info;
766   ArgBlob *blob = (ArgBlob *)&base->typelib->data[base->offset];
767
768   return blob->destroy;
769 }
770
771 GITypeInfo *
772 g_arg_info_get_type (GIArgInfo *info)
773 {
774   GIBaseInfo *base = (GIBaseInfo *)info;
775  
776   return g_type_info_new (base, base->typelib, base->offset + 12);
777 }
778
779 /* GITypeInfo functions */
780 gboolean
781 g_type_info_is_pointer (GITypeInfo *info)
782 {
783   GIBaseInfo *base = (GIBaseInfo *)info;
784   SimpleTypeBlob *type = (SimpleTypeBlob *)&base->typelib->data[base->offset];
785   
786   if (type->reserved == 0 && type->reserved2 == 0)
787     return type->pointer;
788   else
789     {
790       InterfaceTypeBlob *iface = (InterfaceTypeBlob *)&base->typelib->data[base->offset];
791       
792       return iface->pointer;
793     }
794 }
795
796 GITypeTag
797 g_type_info_get_tag (GITypeInfo *info)
798 {
799   GIBaseInfo *base = (GIBaseInfo *)info;
800   SimpleTypeBlob *type = (SimpleTypeBlob *)&base->typelib->data[base->offset];
801
802   if (type->reserved == 0 && type->reserved2 == 0)
803     return type->tag;
804   else
805     {
806       InterfaceTypeBlob *iface = (InterfaceTypeBlob *)&base->typelib->data[base->offset];
807
808       return iface->tag;
809     }
810 }
811
812 GITypeInfo *
813 g_type_info_get_param_type (GITypeInfo *info,
814                             gint       n)
815 {
816   GIBaseInfo *base = (GIBaseInfo *)info;
817   SimpleTypeBlob *type = (SimpleTypeBlob *)&base->typelib->data[base->offset];
818   
819   if (!(type->reserved == 0 && type->reserved2 == 0))
820     {
821       ParamTypeBlob *param = (ParamTypeBlob *)&base->typelib->data[base->offset];
822
823       switch (param->tag)
824         {
825         case GI_TYPE_TAG_ARRAY: 
826         case GI_TYPE_TAG_GLIST:
827         case GI_TYPE_TAG_GSLIST:
828         case GI_TYPE_TAG_GHASH:
829           return g_type_info_new (base, base->typelib, base->offset + 4 + 4 * n);
830           break;
831           
832         default: ;
833         }
834     }
835       
836   return NULL;
837 }
838
839 GIBaseInfo *
840 g_type_info_get_interface (GITypeInfo *info)
841 {
842   GIBaseInfo *base = (GIBaseInfo *)info;
843   SimpleTypeBlob *type = (SimpleTypeBlob *)&base->typelib->data[base->offset];
844   
845   if (!(type->reserved == 0 && type->reserved2 == 0))
846     {
847       InterfaceTypeBlob *blob = (InterfaceTypeBlob *)&base->typelib->data[base->offset];
848       
849       if (blob->tag == GI_TYPE_TAG_INTERFACE)
850         return g_info_from_entry (base->repository, base->typelib, blob->interface);
851     }
852
853   return NULL;
854 }
855
856 gint
857 g_type_info_get_array_length (GITypeInfo *info)
858 {
859   GIBaseInfo *base = (GIBaseInfo *)info;
860   SimpleTypeBlob *type = (SimpleTypeBlob *)&base->typelib->data[base->offset];
861   
862   if (!(type->reserved == 0 && type->reserved2 == 0))
863     {
864       ArrayTypeBlob *blob = (ArrayTypeBlob *)&base->typelib->data[base->offset];
865
866       if (blob->tag == GI_TYPE_TAG_ARRAY)
867         {
868           if (blob->has_length)
869             return blob->length;
870         }
871     }
872
873   return -1;
874 }
875
876 gint
877 g_type_info_get_array_fixed_size (GITypeInfo *info)
878 {
879   GIBaseInfo *base = (GIBaseInfo *)info;
880   SimpleTypeBlob *type = (SimpleTypeBlob *)&base->typelib->data[base->offset];
881   
882   if (!(type->reserved == 0 && type->reserved2 == 0))
883     {
884       ArrayTypeBlob *blob = (ArrayTypeBlob *)&base->typelib->data[base->offset];
885
886       if (blob->tag == GI_TYPE_TAG_ARRAY)
887         {
888           if (blob->has_size)
889             return blob->size;
890         }
891     }
892
893   return -1;
894 }
895
896 gboolean
897 g_type_info_is_zero_terminated (GITypeInfo *info)
898 {
899   GIBaseInfo *base = (GIBaseInfo *)info;
900   SimpleTypeBlob *type = (SimpleTypeBlob *)&base->typelib->data[base->offset];
901   
902   if (!(type->reserved == 0 && type->reserved2 == 0))
903     {
904       ArrayTypeBlob *blob = (ArrayTypeBlob *)&base->typelib->data[base->offset];
905
906       if (blob->tag == GI_TYPE_TAG_ARRAY)
907         return blob->zero_terminated;
908     }
909
910   return FALSE;
911 }
912
913 gint
914 g_type_info_get_n_error_domains (GITypeInfo *info)
915 {
916   GIBaseInfo *base = (GIBaseInfo *)info;
917   SimpleTypeBlob *type = (SimpleTypeBlob *)&base->typelib->data[base->offset];
918   
919   if (!(type->reserved == 0 && type->reserved2 == 0))
920     {
921       ErrorTypeBlob *blob = (ErrorTypeBlob *)&base->typelib->data[base->offset];
922
923       if (blob->tag == GI_TYPE_TAG_ERROR)
924         return blob->n_domains;
925     }
926
927   return 0;
928 }
929
930 GIErrorDomainInfo *
931 g_type_info_get_error_domain (GITypeInfo *info,
932                               gint       n)
933 {
934   GIBaseInfo *base = (GIBaseInfo *)info;
935   SimpleTypeBlob *type = (SimpleTypeBlob *)&base->typelib->data[base->offset];
936   
937   if (!(type->reserved == 0 && type->reserved2 == 0))
938     {
939       ErrorTypeBlob *blob = (ErrorTypeBlob *)&base->typelib->data[base->offset];
940
941       if (blob->tag == GI_TYPE_TAG_ERROR)
942         return (GIErrorDomainInfo *) g_info_from_entry (base->repository,
943                                                         base->typelib,
944                                                         blob->domains[n]);
945     }
946
947   return NULL;
948 }
949
950
951 /* GIErrorDomainInfo functions */
952 const gchar *
953 g_error_domain_info_get_quark (GIErrorDomainInfo *info)
954 {
955   GIBaseInfo *base = (GIBaseInfo *)info;
956   ErrorDomainBlob *blob = (ErrorDomainBlob *)&base->typelib->data[base->offset];
957
958   return g_typelib_get_string (base->typelib, blob->get_quark);
959 }
960
961 GIInterfaceInfo *
962 g_error_domain_info_get_codes (GIErrorDomainInfo *info)
963 {
964   GIBaseInfo *base = (GIBaseInfo *)info;
965   ErrorDomainBlob *blob = (ErrorDomainBlob *)&base->typelib->data[base->offset];
966   
967   return (GIInterfaceInfo *) g_info_from_entry (base->repository,
968                                                 base->typelib, blob->error_codes);
969 }
970
971
972 /* GIValueInfo functions */ 
973 glong
974 g_value_info_get_value (GIValueInfo *info)
975 {
976   GIBaseInfo *base = (GIBaseInfo *)info;
977   ValueBlob *blob = (ValueBlob *)&base->typelib->data[base->offset];
978
979   return (glong)blob->value;
980 }
981
982 /* GIFieldInfo functions */
983 GIFieldInfoFlags
984 g_field_info_get_flags (GIFieldInfo *info)
985 {
986   GIFieldInfoFlags flags;
987
988   GIBaseInfo *base = (GIBaseInfo *)info;
989   FieldBlob *blob = (FieldBlob *)&base->typelib->data[base->offset];
990
991   flags = 0;
992
993   if (blob->readable)
994     flags = flags | GI_FIELD_IS_READABLE;
995
996   if (blob->writable)
997     flags = flags | GI_FIELD_IS_WRITABLE;
998
999   return flags;
1000 }
1001
1002 gint
1003 g_field_info_get_size (GIFieldInfo *info)
1004 {
1005   GIBaseInfo *base = (GIBaseInfo *)info;
1006   FieldBlob *blob = (FieldBlob *)&base->typelib->data[base->offset];
1007   
1008   return blob->bits;
1009 }
1010
1011 gint
1012 g_field_info_get_offset (GIFieldInfo *info)
1013 {
1014   GIBaseInfo *base = (GIBaseInfo *)info;
1015   FieldBlob *blob = (FieldBlob *)&base->typelib->data[base->offset];
1016   
1017   return blob->struct_offset;
1018 }
1019
1020 GITypeInfo *
1021 g_field_info_get_type (GIFieldInfo *info)
1022 {
1023   GIBaseInfo *base = (GIBaseInfo *)info;
1024   
1025   return g_type_info_new (base, base->typelib, base->offset + 8);
1026 }
1027
1028 /* GIRegisteredTypeInfo functions */
1029 const gchar *
1030 g_registered_type_info_get_type_name (GIRegisteredTypeInfo *info)
1031 {
1032   GIBaseInfo *base = (GIBaseInfo *)info;
1033   RegisteredTypeBlob *blob = (RegisteredTypeBlob *)&base->typelib->data[base->offset];
1034
1035   if (blob->gtype_name)
1036     return g_typelib_get_string (base->typelib, blob->gtype_name);
1037
1038   return NULL;
1039 }
1040
1041 const gchar *
1042 g_registered_type_info_get_type_init (GIRegisteredTypeInfo *info)
1043 {
1044   GIBaseInfo *base = (GIBaseInfo *)info;
1045   RegisteredTypeBlob *blob = (RegisteredTypeBlob *)&base->typelib->data[base->offset];
1046
1047   if (blob->gtype_init)
1048     return g_typelib_get_string (base->typelib, blob->gtype_init);
1049
1050   return NULL;
1051 }
1052
1053 GType
1054 g_registered_type_info_get_g_type (GIRegisteredTypeInfo *info)
1055 {
1056   const char *type_init;
1057   GType (* get_type_func) (void);
1058
1059   type_init = g_registered_type_info_get_type_init (info);  
1060   
1061   if (type_init == NULL)
1062     return G_TYPE_NONE;
1063   
1064   get_type_func = NULL;
1065   if (!g_typelib_symbol (((GIBaseInfo*)info)->typelib,
1066                          type_init,
1067                          (void**) &get_type_func))
1068     return G_TYPE_NONE;
1069   
1070   return (* get_type_func) ();
1071 }
1072
1073 /* GIStructInfo functions */
1074 gint
1075 g_struct_info_get_n_fields (GIStructInfo *info)
1076 {
1077   GIBaseInfo *base = (GIBaseInfo *)info;
1078   StructBlob *blob = (StructBlob *)&base->typelib->data[base->offset];
1079   
1080   return blob->n_fields;
1081 }
1082
1083 GIFieldInfo *
1084 g_struct_info_get_field (GIStructInfo *info,
1085                          gint         n)
1086 {
1087   GIBaseInfo *base = (GIBaseInfo *)info;
1088   Header *header = (Header *)base->typelib->data;  
1089  
1090   return (GIFieldInfo *) g_info_new (GI_INFO_TYPE_FIELD, base, base->typelib, 
1091                                      base->offset + header->struct_blob_size + 
1092                                      n * header->field_blob_size);
1093 }
1094
1095 gint
1096 g_struct_info_get_n_methods (GIStructInfo *info)
1097 {
1098   GIBaseInfo *base = (GIBaseInfo *)info;
1099   StructBlob *blob = (StructBlob *)&base->typelib->data[base->offset];
1100   
1101   return blob->n_methods;
1102 }
1103
1104 GIFunctionInfo *
1105 g_struct_info_get_method (GIStructInfo *info,
1106                           gint         n)
1107 {
1108   GIBaseInfo *base = (GIBaseInfo *)info;
1109   StructBlob *blob = (StructBlob *)&base->typelib->data[base->offset];
1110   Header *header = (Header *)base->typelib->data;  
1111   gint offset;
1112
1113   offset = base->offset + header->struct_blob_size 
1114     + blob->n_fields * header->field_blob_size 
1115     + n * header->function_blob_size;
1116   return (GIFunctionInfo *) g_info_new (GI_INFO_TYPE_FUNCTION, base, 
1117                                         base->typelib, offset);
1118 }
1119
1120 static GIFunctionInfo *
1121 find_method (GIBaseInfo   *base,
1122              guint32       offset,
1123              gint          n_methods,
1124              const gchar  *name)
1125 {
1126   /* FIXME hash */
1127   Header *header = (Header *)base->typelib->data;  
1128   gint i;
1129
1130   for (i = 0; i < n_methods; i++)
1131     {
1132       FunctionBlob *fblob = (FunctionBlob *)&base->typelib->data[offset];
1133       const gchar *fname = (const gchar *)&base->typelib->data[fblob->name];
1134
1135       if (strcmp (name, fname) == 0)
1136         return (GIFunctionInfo *) g_info_new (GI_INFO_TYPE_FUNCTION, base, 
1137                                               base->typelib, offset);  
1138       
1139       offset += header->function_blob_size;
1140     }
1141       
1142   return NULL;
1143 }
1144
1145 GIFunctionInfo *
1146 g_struct_info_find_method (GIStructInfo *info,
1147                            const gchar  *name)
1148 {
1149   gint offset;
1150   GIBaseInfo *base = (GIBaseInfo *)info;
1151   Header *header = (Header *)base->typelib->data;  
1152   StructBlob *blob = (StructBlob *)&base->typelib->data[base->offset];
1153
1154   offset = base->offset + header->struct_blob_size
1155     + blob->n_fields * header->field_blob_size;
1156
1157   return find_method (base, offset, blob->n_methods, name);
1158 }
1159
1160 gsize
1161 g_struct_info_get_size (GIStructInfo *info)
1162 {
1163   GIBaseInfo *base = (GIBaseInfo *)info;
1164   StructBlob *blob = (StructBlob *)&base->typelib->data[base->offset];
1165
1166   return blob->size;
1167 }
1168
1169 gsize
1170 g_struct_info_get_alignment (GIStructInfo *info)
1171 {
1172   GIBaseInfo *base = (GIBaseInfo *)info;
1173   StructBlob *blob = (StructBlob *)&base->typelib->data[base->offset];
1174
1175   return blob->alignment;
1176 }
1177
1178 gint
1179 g_enum_info_get_n_values (GIEnumInfo *info)
1180 {
1181   GIBaseInfo *base = (GIBaseInfo *)info;
1182   EnumBlob *blob = (EnumBlob *)&base->typelib->data[base->offset];
1183
1184   return blob->n_values;
1185 }
1186
1187 GIValueInfo *
1188 g_enum_info_get_value (GIEnumInfo *info,
1189                        gint            n)
1190 {
1191   GIBaseInfo *base = (GIBaseInfo *)info;
1192   Header *header = (Header *)base->typelib->data;  
1193   gint offset;
1194
1195   offset = base->offset + header->enum_blob_size 
1196     + n * header->value_blob_size;
1197   return (GIValueInfo *) g_info_new (GI_INFO_TYPE_VALUE, base, base->typelib, offset);
1198 }
1199
1200 /**
1201  * g_enum_info_get_storage_type:
1202  * @info: GIEnumInfo
1203  *
1204  * Gets the tag of the type used for the enum in the C ABI. This will
1205  * will be a signed or unsigned integral type.
1206
1207  * Note that in the current implementation the width of the type is
1208  * computed correctly, but the signed or unsigned nature of the type
1209  * may not match the sign of the type used by the C compiler.
1210  *
1211  * Return Value: the storage type for the enumeration
1212  */
1213 GITypeTag
1214 g_enum_info_get_storage_type (GIEnumInfo *info)
1215 {
1216   GIBaseInfo *base = (GIBaseInfo *)info;
1217   EnumBlob *blob = (EnumBlob *)&base->typelib->data[base->offset];
1218
1219   return blob->storage_type;
1220 }
1221
1222 /* GIObjectInfo functions */
1223 GIObjectInfo *
1224 g_object_info_get_parent (GIObjectInfo *info)
1225 {
1226   GIBaseInfo *base = (GIBaseInfo *)info;
1227   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1228
1229   if (blob->parent)
1230     return (GIObjectInfo *) g_info_from_entry (base->repository,
1231                                                base->typelib, blob->parent);
1232   else
1233     return NULL;
1234 }
1235
1236 gboolean
1237 g_object_info_get_abstract (GIObjectInfo    *info)
1238 {
1239   GIBaseInfo *base = (GIBaseInfo *)info;
1240   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1241   return blob->abstract != 0;
1242 }
1243
1244 const gchar *
1245 g_object_info_get_type_name (GIObjectInfo *info)
1246 {
1247   GIBaseInfo *base = (GIBaseInfo *)info;
1248   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1249
1250   return g_typelib_get_string (base->typelib, blob->gtype_name);
1251 }
1252
1253 const gchar *
1254 g_object_info_get_type_init (GIObjectInfo *info)
1255 {
1256   GIBaseInfo *base = (GIBaseInfo *)info;
1257   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1258
1259   return g_typelib_get_string (base->typelib, blob->gtype_init);
1260 }
1261
1262 gint
1263 g_object_info_get_n_interfaces (GIObjectInfo *info)
1264 {
1265   GIBaseInfo *base = (GIBaseInfo *)info;
1266   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1267
1268   return blob->n_interfaces;
1269 }
1270
1271 GIInterfaceInfo *
1272 g_object_info_get_interface (GIObjectInfo *info,
1273                              gint          n)
1274 {
1275   GIBaseInfo *base = (GIBaseInfo *)info;
1276   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1277
1278   return (GIInterfaceInfo *) g_info_from_entry (base->repository,
1279                                                 base->typelib, blob->interfaces[n]);
1280 }
1281
1282 gint
1283 g_object_info_get_n_fields (GIObjectInfo *info)
1284 {
1285   GIBaseInfo *base = (GIBaseInfo *)info;
1286   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1287
1288   return blob->n_fields;
1289 }
1290
1291 GIFieldInfo *
1292 g_object_info_get_field (GIObjectInfo *info,
1293                          gint          n)
1294 {
1295   gint offset;
1296   GIBaseInfo *base = (GIBaseInfo *)info;
1297   Header *header = (Header *)base->typelib->data;  
1298   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1299   
1300   offset = base->offset + header->object_blob_size
1301     + (blob->n_interfaces + blob->n_interfaces % 2) * 2
1302     + n * header->field_blob_size;
1303   
1304   return (GIFieldInfo *) g_info_new (GI_INFO_TYPE_FIELD, base, base->typelib, offset);
1305 }
1306
1307 gint
1308 g_object_info_get_n_properties (GIObjectInfo *info)
1309 {
1310   GIBaseInfo *base = (GIBaseInfo *)info;
1311   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1312
1313   return blob->n_properties;  
1314 }
1315
1316 GIPropertyInfo *
1317 g_object_info_get_property (GIObjectInfo *info,
1318                             gint          n)
1319 {
1320   gint offset;
1321   GIBaseInfo *base = (GIBaseInfo *)info;
1322   Header *header = (Header *)base->typelib->data;  
1323   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1324   
1325   offset = base->offset + header->object_blob_size
1326     + (blob->n_interfaces + blob->n_interfaces % 2) * 2
1327     + blob->n_fields * header->field_blob_size
1328     + n * header->property_blob_size;
1329
1330   return (GIPropertyInfo *) g_info_new (GI_INFO_TYPE_PROPERTY, base, 
1331                                         base->typelib, offset);
1332 }
1333
1334 gint
1335 g_object_info_get_n_methods (GIObjectInfo *info)
1336 {
1337   GIBaseInfo *base = (GIBaseInfo *)info;
1338   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1339
1340   return blob->n_methods;
1341 }
1342
1343 GIFunctionInfo *
1344 g_object_info_get_method (GIObjectInfo *info,
1345                           gint          n)
1346 {
1347   gint offset;
1348   GIBaseInfo *base = (GIBaseInfo *)info;
1349   Header *header = (Header *)base->typelib->data;  
1350   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1351   
1352   offset = base->offset + header->object_blob_size
1353     + (blob->n_interfaces + blob->n_interfaces % 2) * 2
1354     + blob->n_fields * header->field_blob_size
1355     + blob->n_properties * header->property_blob_size
1356     + n * header->function_blob_size;
1357
1358     return (GIFunctionInfo *) g_info_new (GI_INFO_TYPE_FUNCTION, base, 
1359                                           base->typelib, offset);  
1360 }
1361
1362 GIFunctionInfo *
1363 g_object_info_find_method (GIObjectInfo *info,
1364                            const gchar  *name)
1365 {
1366   gint offset;
1367   GIBaseInfo *base = (GIBaseInfo *)info;
1368   Header *header = (Header *)base->typelib->data;  
1369   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1370
1371   offset = base->offset + header->object_blob_size
1372     + (blob->n_interfaces + blob->n_interfaces % 2) * 2
1373     + blob->n_fields * header->field_blob_size +
1374     + blob->n_properties * header->property_blob_size;
1375
1376   return find_method (base, offset, blob->n_methods, name);
1377 }
1378
1379 gint
1380 g_object_info_get_n_signals (GIObjectInfo *info)
1381 {
1382   GIBaseInfo *base = (GIBaseInfo *)info;
1383   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1384
1385   return blob->n_signals;
1386 }
1387
1388 GISignalInfo *
1389 g_object_info_get_signal (GIObjectInfo *info,
1390                           gint          n)
1391 {
1392   gint offset;
1393   GIBaseInfo *base = (GIBaseInfo *)info;
1394   Header *header = (Header *)base->typelib->data;  
1395   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1396   
1397   offset = base->offset + header->object_blob_size
1398     + (blob->n_interfaces + blob->n_interfaces % 2) * 2
1399     + blob->n_fields * header->field_blob_size
1400     + blob->n_properties * header->property_blob_size
1401     + blob->n_methods * header->function_blob_size 
1402     + n * header->signal_blob_size;
1403
1404   return (GISignalInfo *) g_info_new (GI_INFO_TYPE_SIGNAL, base, 
1405                                       base->typelib, offset);  
1406 }
1407
1408 gint
1409 g_object_info_get_n_vfuncs (GIObjectInfo *info)
1410 {
1411   GIBaseInfo *base = (GIBaseInfo *)info;
1412   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1413   
1414   return blob->n_vfuncs;
1415 }
1416
1417 GIVFuncInfo *
1418 g_object_info_get_vfunc (GIObjectInfo *info,
1419                          gint          n)
1420 {
1421   gint offset;
1422   GIBaseInfo *base = (GIBaseInfo *)info;
1423   Header *header = (Header *)base->typelib->data;  
1424   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1425   
1426   offset = base->offset + header->object_blob_size
1427     + (blob->n_interfaces + blob->n_interfaces % 2) * 2
1428     + blob->n_fields * header->field_blob_size
1429     + blob->n_properties * header->property_blob_size
1430     + blob->n_methods * header->function_blob_size 
1431     + blob->n_signals * header->signal_blob_size 
1432     + n * header->vfunc_blob_size;
1433
1434   return (GIVFuncInfo *) g_info_new (GI_INFO_TYPE_VFUNC, base, 
1435                                      base->typelib, offset);  
1436 }
1437
1438 gint
1439 g_object_info_get_n_constants (GIObjectInfo *info)
1440 {
1441   GIBaseInfo *base = (GIBaseInfo *)info;
1442   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1443   
1444   return blob->n_constants;
1445 }
1446
1447 GIConstantInfo *
1448 g_object_info_get_constant (GIObjectInfo *info,
1449                             gint          n)
1450 {
1451   gint offset;
1452   GIBaseInfo *base = (GIBaseInfo *)info;
1453   Header *header = (Header *)base->typelib->data;  
1454   ObjectBlob *blob = (ObjectBlob *)&base->typelib->data[base->offset];
1455   
1456   offset = base->offset + header->object_blob_size
1457     + (blob->n_interfaces + blob->n_interfaces % 2) * 2
1458     + blob->n_fields * header->field_blob_size
1459     + blob->n_properties * header->property_blob_size
1460     + blob->n_methods * header->function_blob_size 
1461     + blob->n_signals * header->signal_blob_size 
1462     + blob->n_vfuncs * header->vfunc_blob_size 
1463     + n * header->constant_blob_size;
1464
1465   return (GIConstantInfo *) g_info_new (GI_INFO_TYPE_CONSTANT, base, 
1466                                         base->typelib, offset);  
1467 }
1468
1469
1470 /* GIInterfaceInfo functions */
1471 gint
1472 g_interface_info_get_n_prerequisites (GIInterfaceInfo *info)
1473 {
1474   GIBaseInfo *base = (GIBaseInfo *)info;
1475   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1476
1477   return blob->n_prerequisites;
1478 }
1479
1480 GIBaseInfo *
1481 g_interface_info_get_prerequisite (GIInterfaceInfo *info,
1482                                    gint            n)
1483 {
1484   GIBaseInfo *base = (GIBaseInfo *)info;
1485   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1486
1487   return g_info_from_entry (base->repository,
1488                             base->typelib, blob->prerequisites[n]);
1489 }
1490
1491
1492 gint
1493 g_interface_info_get_n_properties (GIInterfaceInfo *info)
1494 {
1495   GIBaseInfo *base = (GIBaseInfo *)info;
1496   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1497
1498   return blob->n_properties;  
1499 }
1500
1501 GIPropertyInfo *
1502 g_interface_info_get_property (GIInterfaceInfo *info,
1503                                gint            n)
1504 {
1505   gint offset;
1506   GIBaseInfo *base = (GIBaseInfo *)info;
1507   Header *header = (Header *)base->typelib->data;  
1508   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1509   
1510   offset = base->offset + header->interface_blob_size
1511     + (blob->n_prerequisites + (blob->n_prerequisites % 2)) * 2
1512     + n * header->property_blob_size;
1513
1514   return (GIPropertyInfo *) g_info_new (GI_INFO_TYPE_PROPERTY, base, 
1515                                         base->typelib, offset);
1516 }
1517
1518 gint
1519 g_interface_info_get_n_methods (GIInterfaceInfo *info)
1520 {
1521   GIBaseInfo *base = (GIBaseInfo *)info;
1522   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1523
1524   return blob->n_methods;
1525 }
1526
1527 GIFunctionInfo *
1528 g_interface_info_get_method (GIInterfaceInfo *info,
1529                              gint            n)
1530 {
1531   gint offset;
1532   GIBaseInfo *base = (GIBaseInfo *)info;
1533   Header *header = (Header *)base->typelib->data;  
1534   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1535   
1536   offset = base->offset + header->interface_blob_size
1537     + (blob->n_prerequisites + (blob->n_prerequisites % 2)) * 2
1538     + blob->n_properties * header->property_blob_size 
1539     + n * header->function_blob_size;
1540   
1541   return (GIFunctionInfo *) g_info_new (GI_INFO_TYPE_FUNCTION, base, 
1542                                         base->typelib, offset);  
1543 }
1544
1545 GIFunctionInfo *
1546 g_interface_info_find_method (GIInterfaceInfo *info,
1547                               const gchar     *name)
1548 {
1549   gint offset;
1550   GIBaseInfo *base = (GIBaseInfo *)info;
1551   Header *header = (Header *)base->typelib->data;  
1552   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1553
1554   offset = base->offset + header->interface_blob_size
1555     + (blob->n_prerequisites + (blob->n_prerequisites % 2)) * 2
1556     + blob->n_properties * header->property_blob_size;
1557
1558   return find_method (base, offset, blob->n_methods, name);
1559 }
1560
1561 gint
1562 g_interface_info_get_n_signals (GIInterfaceInfo *info)
1563 {
1564   GIBaseInfo *base = (GIBaseInfo *)info;
1565   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1566
1567   return blob->n_signals;
1568 }
1569
1570 GISignalInfo *
1571 g_interface_info_get_signal (GIInterfaceInfo *info,
1572                              gint            n)
1573 {
1574   gint offset;
1575   GIBaseInfo *base = (GIBaseInfo *)info;
1576   Header *header = (Header *)base->typelib->data;  
1577   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1578   
1579   offset = base->offset + header->interface_blob_size 
1580     + (blob->n_prerequisites + (blob->n_prerequisites % 2)) * 2
1581     + blob->n_properties * header->property_blob_size 
1582     + blob->n_methods * header->function_blob_size 
1583     + n * header->signal_blob_size;
1584   
1585   return (GISignalInfo *) g_info_new (GI_INFO_TYPE_SIGNAL, base, 
1586                                       base->typelib, offset);  
1587 }
1588
1589 gint
1590 g_interface_info_get_n_vfuncs (GIInterfaceInfo *info)
1591 {
1592   GIBaseInfo *base = (GIBaseInfo *)info;
1593   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1594
1595   return blob->n_vfuncs;
1596 }
1597
1598 GIVFuncInfo *
1599 g_interface_info_get_vfunc (GIInterfaceInfo *info,
1600                             gint            n)
1601 {
1602   gint offset;
1603   GIBaseInfo *base = (GIBaseInfo *)info;
1604   Header *header = (Header *)base->typelib->data;  
1605   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1606   
1607   offset = base->offset + header->interface_blob_size 
1608     + (blob->n_prerequisites + (blob->n_prerequisites % 2)) * 2
1609     + blob->n_properties * header->property_blob_size 
1610     + blob->n_methods * header->function_blob_size 
1611     + blob->n_signals * header->signal_blob_size
1612     + n * header->vfunc_blob_size;
1613   
1614   return (GIVFuncInfo *) g_info_new (GI_INFO_TYPE_VFUNC, base, 
1615                                      base->typelib, offset);  
1616 }
1617
1618 gint
1619 g_interface_info_get_n_constants (GIInterfaceInfo *info)
1620 {
1621   GIBaseInfo *base = (GIBaseInfo *)info;
1622   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1623   
1624   return blob->n_constants;
1625 }
1626
1627 GIConstantInfo *
1628 g_interface_info_get_constant (GIInterfaceInfo *info,
1629                                gint             n)
1630 {
1631   gint offset;
1632   GIBaseInfo *base = (GIBaseInfo *)info;
1633   Header *header = (Header *)base->typelib->data;  
1634   InterfaceBlob *blob = (InterfaceBlob *)&base->typelib->data[base->offset];
1635   
1636   offset = base->offset + header->interface_blob_size
1637     + (blob->n_prerequisites + (blob->n_prerequisites % 2)) * 2
1638     + blob->n_properties * header->property_blob_size
1639     + blob->n_methods * header->function_blob_size 
1640     + blob->n_signals * header->signal_blob_size 
1641     + blob->n_vfuncs * header->vfunc_blob_size 
1642     + n * header->constant_blob_size;
1643
1644   return (GIConstantInfo *) g_info_new (GI_INFO_TYPE_CONSTANT, base, 
1645                                         base->typelib, offset);  
1646 }
1647
1648
1649
1650
1651 /* GIPropertyInfo functions */
1652 GParamFlags
1653 g_property_info_get_flags (GIPropertyInfo *info)
1654 {
1655   GParamFlags flags;
1656   GIBaseInfo *base = (GIBaseInfo *)info;
1657   PropertyBlob *blob = (PropertyBlob *)&base->typelib->data[base->offset];
1658   
1659   flags = 0;
1660
1661   if (blob->readable)
1662     flags = flags | G_PARAM_READABLE;
1663
1664   if (blob->writable)
1665     flags = flags | G_PARAM_WRITABLE;
1666
1667   if (blob->construct)
1668     flags = flags | G_PARAM_CONSTRUCT;
1669
1670   if (blob->construct_only)
1671     flags = flags | G_PARAM_CONSTRUCT_ONLY;
1672
1673   return flags;
1674 }
1675
1676 GITypeInfo *
1677 g_property_info_get_type (GIPropertyInfo *info)
1678 {
1679   GIBaseInfo *base = (GIBaseInfo *)info;
1680
1681   return g_type_info_new (base, base->typelib, base->offset + 8);  
1682 }
1683
1684
1685 /* GISignalInfo functions */
1686 GSignalFlags
1687 g_signal_info_get_flags (GISignalInfo *info)
1688 {
1689   GSignalFlags flags;
1690
1691   GIBaseInfo *base = (GIBaseInfo *)info;
1692   SignalBlob *blob = (SignalBlob *)&base->typelib->data[base->offset];
1693
1694   flags = 0;
1695
1696   if (blob->run_first)
1697     flags = flags | G_SIGNAL_RUN_FIRST;
1698
1699   if (blob->run_last)
1700     flags = flags | G_SIGNAL_RUN_LAST;
1701
1702   if (blob->run_cleanup)
1703     flags = flags | G_SIGNAL_RUN_CLEANUP;
1704
1705   if (blob->no_recurse)
1706     flags = flags | G_SIGNAL_NO_RECURSE;
1707
1708   if (blob->detailed)
1709     flags = flags | G_SIGNAL_DETAILED;
1710
1711   if (blob->action)
1712     flags = flags | G_SIGNAL_ACTION;
1713
1714   if (blob->no_hooks)
1715     flags = flags | G_SIGNAL_NO_HOOKS;
1716
1717   return flags;
1718 }
1719
1720 GIVFuncInfo *
1721 g_signal_info_get_class_closure (GISignalInfo *info)
1722 {
1723   GIBaseInfo *base = (GIBaseInfo *)info;
1724   SignalBlob *blob = (SignalBlob *)&base->typelib->data[base->offset];
1725
1726   if (blob->has_class_closure)
1727     return g_interface_info_get_vfunc ((GIInterfaceInfo *)base->container, blob->class_closure);
1728
1729   return NULL;
1730 }
1731
1732 gboolean
1733 g_signal_info_true_stops_emit (GISignalInfo *info)
1734 {
1735   GIBaseInfo *base = (GIBaseInfo *)info;
1736   SignalBlob *blob = (SignalBlob *)&base->typelib->data[base->offset];
1737
1738   return blob->true_stops_emit;
1739 }
1740
1741 /* GIVFuncInfo functions */
1742 GIVFuncInfoFlags
1743 g_vfunc_info_get_flags (GIVFuncInfo *info)
1744 {
1745   GIVFuncInfoFlags flags;
1746
1747   GIBaseInfo *base = (GIBaseInfo *)info;
1748   VFuncBlob *blob = (VFuncBlob *)&base->typelib->data[base->offset];
1749
1750   flags = 0;
1751
1752   if (blob->must_chain_up)
1753     flags = flags | GI_VFUNC_MUST_CHAIN_UP;
1754
1755   if (blob->must_be_implemented)
1756     flags = flags | GI_VFUNC_MUST_OVERRIDE;
1757
1758   if (blob->must_not_be_implemented)
1759     flags = flags | GI_VFUNC_MUST_NOT_OVERRIDE;
1760
1761   return flags;
1762 }
1763
1764 gint
1765 g_vfunc_info_get_offset (GIVFuncInfo *info)
1766 {
1767   GIBaseInfo *base = (GIBaseInfo *)info;
1768   VFuncBlob *blob = (VFuncBlob *)&base->typelib->data[base->offset];
1769   
1770   return blob->struct_offset;
1771 }
1772
1773 GISignalInfo *
1774 g_vfunc_info_get_signal (GIVFuncInfo *info)
1775 {
1776   GIBaseInfo *base = (GIBaseInfo *)info;
1777   VFuncBlob *blob = (VFuncBlob *)&base->typelib->data[base->offset];
1778
1779   if (blob->class_closure)
1780     return g_interface_info_get_signal ((GIInterfaceInfo *)base->container, blob->signal);
1781   
1782   return NULL;
1783 }
1784
1785
1786 /* GIConstantInfo functions */
1787 GITypeInfo *
1788 g_constant_info_get_type (GIConstantInfo *info)
1789 {
1790   GIBaseInfo *base = (GIBaseInfo *)info;
1791   
1792   return g_type_info_new (base, base->typelib, base->offset + 8);
1793 }
1794
1795 gint
1796 g_constant_info_get_value (GIConstantInfo *info, 
1797                            GArgument      *value)
1798 {
1799   GIBaseInfo *base = (GIBaseInfo *)info;
1800   ConstantBlob *blob = (ConstantBlob *)&base->typelib->data[base->offset];
1801
1802   /* FIXME non-basic types ? */
1803   if (blob->type.reserved == 0 && blob->type.reserved2 == 0)
1804     {
1805       if (blob->type.pointer)
1806         value->v_pointer = g_memdup (&base->typelib->data[blob->offset], blob->size);
1807       else
1808         {
1809           switch (blob->type.tag)
1810             {
1811             case GI_TYPE_TAG_BOOLEAN:
1812               value->v_boolean = *(gboolean*)&base->typelib->data[blob->offset];
1813               break;
1814             case GI_TYPE_TAG_INT8:
1815               value->v_int8 = *(gint8*)&base->typelib->data[blob->offset];
1816               break;
1817             case GI_TYPE_TAG_UINT8:
1818               value->v_uint8 = *(guint8*)&base->typelib->data[blob->offset];
1819               break;
1820             case GI_TYPE_TAG_INT16:
1821               value->v_int16 = *(gint16*)&base->typelib->data[blob->offset];
1822               break;
1823             case GI_TYPE_TAG_UINT16:
1824               value->v_uint16 = *(guint16*)&base->typelib->data[blob->offset];
1825               break;
1826             case GI_TYPE_TAG_INT32:
1827               value->v_int32 = *(gint32*)&base->typelib->data[blob->offset];
1828               break;
1829             case GI_TYPE_TAG_UINT32:
1830               value->v_uint32 = *(guint32*)&base->typelib->data[blob->offset];
1831               break;
1832             case GI_TYPE_TAG_INT64:
1833               value->v_int64 = *(gint64*)&base->typelib->data[blob->offset];
1834               break;
1835             case GI_TYPE_TAG_UINT64:
1836               value->v_uint64 = *(guint64*)&base->typelib->data[blob->offset];
1837               break;
1838             case GI_TYPE_TAG_FLOAT:
1839               value->v_float = *(gfloat*)&base->typelib->data[blob->offset];
1840               break;
1841             case GI_TYPE_TAG_DOUBLE:
1842               value->v_double = *(gdouble*)&base->typelib->data[blob->offset];
1843               break;
1844             case GI_TYPE_TAG_TIME_T:
1845               value->v_long = *(long*)&base->typelib->data[blob->offset];
1846               break;
1847             case GI_TYPE_TAG_INT:
1848               value->v_int = *(gint*)&base->typelib->data[blob->offset];
1849               break;
1850             case GI_TYPE_TAG_UINT:
1851               value->v_uint = *(guint*)&base->typelib->data[blob->offset];
1852               break;
1853             case GI_TYPE_TAG_LONG:
1854               value->v_long = *(glong*)&base->typelib->data[blob->offset];
1855               break;
1856             case GI_TYPE_TAG_ULONG:
1857               value->v_ulong = *(gulong*)&base->typelib->data[blob->offset];
1858               break;
1859             }
1860         }
1861     }
1862
1863   return blob->size;
1864 }
1865
1866 /* GIUnionInfo functions */
1867 gint
1868 g_union_info_get_n_fields  (GIUnionInfo *info)
1869 {
1870   GIBaseInfo *base = (GIBaseInfo *)info;
1871   UnionBlob *blob = (UnionBlob *)&base->typelib->data[base->offset];
1872   
1873   return blob->n_fields;
1874 }
1875
1876 GIFieldInfo *
1877 g_union_info_get_field (GIUnionInfo *info,
1878                         gint         n)
1879 {
1880   GIBaseInfo *base = (GIBaseInfo *)info;
1881   Header *header = (Header *)base->typelib->data;  
1882  
1883   return (GIFieldInfo *) g_info_new (GI_INFO_TYPE_FIELD, base, base->typelib, 
1884                                      base->offset + header->union_blob_size + 
1885                                      n * header->field_blob_size);
1886 }
1887
1888 gint
1889 g_union_info_get_n_methods (GIUnionInfo *info)
1890 {
1891   GIBaseInfo *base = (GIBaseInfo *)info;
1892   UnionBlob *blob = (UnionBlob *)&base->typelib->data[base->offset];
1893   
1894   return blob->n_functions;
1895 }
1896
1897 GIFunctionInfo *
1898 g_union_info_get_method (GIUnionInfo *info,
1899                          gint         n)
1900 {
1901   GIBaseInfo *base = (GIBaseInfo *)info;
1902   UnionBlob *blob = (UnionBlob *)&base->typelib->data[base->offset];
1903   Header *header = (Header *)base->typelib->data;  
1904   gint offset;
1905
1906   offset = base->offset + header->union_blob_size 
1907     + blob->n_fields * header->field_blob_size 
1908     + n * header->function_blob_size;
1909   return (GIFunctionInfo *) g_info_new (GI_INFO_TYPE_FUNCTION, base, 
1910                                         base->typelib, offset);
1911 }
1912
1913 gboolean
1914 g_union_info_is_discriminated (GIUnionInfo *info)
1915 {
1916   GIBaseInfo *base = (GIBaseInfo *)info;
1917   UnionBlob *blob = (UnionBlob *)&base->typelib->data[base->offset];
1918   
1919   return blob->discriminated;
1920 }
1921
1922 gint
1923 g_union_info_get_discriminator_offset (GIUnionInfo *info)
1924 {
1925   GIBaseInfo *base = (GIBaseInfo *)info;
1926   UnionBlob *blob = (UnionBlob *)&base->typelib->data[base->offset];
1927   
1928   return blob->discriminator_offset;
1929 }
1930
1931 GITypeInfo *
1932 g_union_info_get_discriminator_type (GIUnionInfo *info)
1933 {
1934   GIBaseInfo *base = (GIBaseInfo *)info;
1935  
1936   return g_type_info_new (base, base->typelib, base->offset + 24);
1937 }
1938
1939 GIConstantInfo *
1940 g_union_info_get_discriminator (GIUnionInfo *info,
1941                                 gint         n)
1942 {
1943   GIBaseInfo *base = (GIBaseInfo *)info;
1944   UnionBlob *blob = (UnionBlob *)&base->typelib->data[base->offset];
1945   
1946   if (blob->discriminated)
1947     {
1948       Header *header = (Header *)base->typelib->data;  
1949       gint offset;
1950
1951       offset = base->offset + header->union_blob_size 
1952         + blob->n_fields * header->field_blob_size 
1953         + blob->n_functions * header->function_blob_size
1954         + n * header->constant_blob_size;
1955       
1956       return (GIConstantInfo *) g_info_new (GI_INFO_TYPE_CONSTANT, base, 
1957                                             base->typelib, offset);  
1958     }
1959
1960   return NULL;
1961 }
1962
1963 GIFunctionInfo *
1964 g_union_info_find_method (GIUnionInfo *info,
1965                           const gchar *name)
1966 {
1967   gint offset;
1968   GIBaseInfo *base = (GIBaseInfo *)info;
1969   Header *header = (Header *)base->typelib->data;
1970   UnionBlob *blob = (UnionBlob *)&base->typelib->data[base->offset];
1971
1972   offset = base->offset + header->union_blob_size
1973     + blob->n_fields * header->field_blob_size;
1974
1975   return find_method (base, offset, blob->n_functions, name);
1976 }
1977
1978 gsize
1979 g_union_info_get_size (GIUnionInfo *info)
1980 {
1981   GIBaseInfo *base = (GIBaseInfo *)info;
1982   UnionBlob *blob = (UnionBlob *)&base->typelib->data[base->offset];
1983
1984   return blob->size;
1985 }
1986
1987 gsize
1988 g_union_info_get_alignment (GIUnionInfo *info)
1989 {
1990   GIBaseInfo *base = (GIBaseInfo *)info;
1991   UnionBlob *blob = (UnionBlob *)&base->typelib->data[base->offset];
1992
1993   return blob->alignment;
1994 }