summaryrefslogtreecommitdiff
path: root/giscanner
diff options
context:
space:
mode:
authorTomeu Vizoso <tomeu@sugarlabs.org>2010-05-04 16:57:51 +0200
committerTomeu Vizoso <tomeu@sugarlabs.org>2010-05-04 16:58:15 +0200
commitf84400b39b966289d6a98548f606b247b05fb6c1 (patch)
tree4d56b0cdee22ca172da53614ce68db1faa33cd25 /giscanner
parent39f2997b9f32598fa2288cdac36f513fcab590b5 (diff)
downloadgobject-introspection-f84400b39b966289d6a98548f606b247b05fb6c1.tar.gz
Add support for GArrays: add g_type_info_get_array_type() and properly scan GArray args
Based on a previous patch by C. Scott Ananian <cscott@litl.com> https://bugzilla.gnome.org/show_bug.cgi?id=581687
Diffstat (limited to 'giscanner')
-rw-r--r--giscanner/annotationparser.py22
-rw-r--r--giscanner/ast.py6
-rw-r--r--giscanner/girparser.py16
-rw-r--r--giscanner/girwriter.py6
-rw-r--r--giscanner/transformer.py2
5 files changed, 44 insertions, 8 deletions
diff --git a/giscanner/annotationparser.py b/giscanner/annotationparser.py
index 3480ac78..fa43378a 100644
--- a/giscanner/annotationparser.py
+++ b/giscanner/annotationparser.py
@@ -605,6 +605,12 @@ class AnnotationApplier(object):
has_element_type = OPT_ELEMENT_TYPE in options
has_array = OPT_ARRAY in options
+ if not has_array:
+ has_array = \
+ node.type.name in ['GLib.Array', 'GLib.PtrArray',
+ 'GLib.ByteArray'] or \
+ node.type.ctype in ['GArray*', 'GPtrArray*', 'GByteArray*']
+
# FIXME: This is a hack :-(
if (not isinstance(node, Field) and
(not has_element_type and
@@ -630,13 +636,25 @@ class AnnotationApplier(object):
else:
array_values = {}
+ is_g_array = node.type.ctype.startswith('GArray*') or \
+ node.type.ctype.startswith('GPtrArray*') or \
+ node.type.ctype.startswith('GByteArray*')
+
element_type = options.get(OPT_ELEMENT_TYPE)
if element_type is not None:
element_type_node = self._resolve(element_type.one())
else:
- element_type_node = Type(node.type.name) # erase ctype
+ if is_g_array:
+ element_type_node = None
+ else:
+ element_type_node = Type(node.type.name) # erase ctype
+
+ if is_g_array:
+ type_name = node.type.name
+ else:
+ type_name = None
- container_type = Array(node.type.ctype,
+ container_type = Array(type_name, node.type.ctype,
element_type_node)
container_type.is_const = node.type.is_const
if OPT_ARRAY_ZERO_TERMINATED in array_values:
diff --git a/giscanner/ast.py b/giscanner/ast.py
index 5e2a010d..9b432023 100644
--- a/giscanner/ast.py
+++ b/giscanner/ast.py
@@ -275,8 +275,10 @@ class Varargs(Type):
class Array(Type):
- def __init__(self, ctype, element_type):
- Type.__init__(self, '<carray>', ctype)
+ def __init__(self, name, ctype, element_type):
+ if name is None:
+ name = '<carray>'
+ Type.__init__(self, name, ctype)
self.element_type = element_type
self.zeroterminated = True
self.length_param_index = -1
diff --git a/giscanner/girparser.py b/giscanner/girparser.py
index 1db5c6e4..852874d9 100644
--- a/giscanner/girparser.py
+++ b/giscanner/girparser.py
@@ -280,17 +280,29 @@ class GIRParser(object):
if typenode is not None:
return Type(typenode.attrib['name'],
typenode.attrib.get(_cns('type')))
+
typenode = node.find(_corens('array'))
if typenode is not None:
- ret = Array(typenode.attrib.get(_cns('type')),
- self._parse_type(typenode))
+
+ array_type = typenode.attrib.get(_cns('type'))
+ if array_type.startswith('GArray*') or \
+ array_type.startswith('GPtrArray*') or \
+ array_type.startswith('GByteArray*'):
+ element_type = None
+ else:
+ element_type = self._parse_type(typenode)
+
+ ret = Array(None, array_type, element_type)
+
lenidx = typenode.attrib.get('length')
if lenidx:
ret.length_param_index = int(lenidx)
return ret
+
typenode = node.find(_corens('varargs'))
if typenode is not None:
return Varargs()
+
raise ValueError("Couldn't parse type of node %r; children=%r",
node, list(node))
diff --git a/giscanner/girwriter.py b/giscanner/girwriter.py
index 8088628d..8d625c73 100644
--- a/giscanner/girwriter.py
+++ b/giscanner/girwriter.py
@@ -244,11 +244,15 @@ and/or use gtk-doc annotations. ''')
attrs.append(('zero-terminated', '0'))
if ntype.length_param_index >= 0:
attrs.append(('length', '%d' % (ntype.length_param_index, )))
+ if ntype.name in ['GLib.Array', 'GLib.PtrArray', 'GLib.ByteArray']:
+ attrs.append(('name', ntype.name))
attrs.append(('c:type', ntype.ctype))
if ntype.size is not None:
attrs.append(('fixed-size', ntype.size))
+
with self.tagcontext('array', attrs):
- self._write_type(ntype.element_type)
+ if ntype.element_type is not None:
+ self._write_type(ntype.element_type)
return
attrs = [('name', self._type_to_string(ntype))]
# FIXME: figure out if type references a basic type
diff --git a/giscanner/transformer.py b/giscanner/transformer.py
index b59c20fc..fbc38d5b 100644
--- a/giscanner/transformer.py
+++ b/giscanner/transformer.py
@@ -373,7 +373,7 @@ class Transformer(object):
else:
derefed_name = canonical_ctype
derefed_name = self.resolve_param_type(derefed_name)
- ftype = Array(ctype, self.parse_ctype(derefed_name))
+ ftype = Array(None, ctype, self.parse_ctype(derefed_name))
child_list = list(symbol.base_type.child_list)
ftype.zeroterminated = False
if child_list: