[gobject-introspection/wip/structure-parsing: 2/3] scanner: Add notion of "private" structures, fix parsing
- From: Colin Walters <walters src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gobject-introspection/wip/structure-parsing: 2/3] scanner: Add notion of "private" structures, fix parsing
- Date: Wed, 8 Sep 2010 23:11:48 +0000 (UTC)
commit 43378bd809b7b9aa0f46f8257695b78ba0d28ff6
Author: Colin Walters <walters verbum org>
Date: Wed Sep 8 15:23:22 2010 -0400
scanner: Add notion of "private" structures, fix parsing
giscanner/ast.py | 20 +++++++++---
giscanner/girparser.py | 1 +
giscanner/transformer.py | 76 +++++++++++++++++++++++++++-------------------
3 files changed, 61 insertions(+), 36 deletions(-)
---
diff --git a/giscanner/ast.py b/giscanner/ast.py
index 6e9dc89..13f290b 100644
--- a/giscanner/ast.py
+++ b/giscanner/ast.py
@@ -373,6 +373,7 @@ returned."""
self._ctypes[node.symbol] = node
def remove(self, node):
+ assert node.namespace is self
if isinstance(node, Alias):
del self._aliases[node.name]
elif isinstance(node, Registered) and node.gtype_name is not None:
@@ -719,7 +720,8 @@ class Compound(Node, Registered):
gtype_name=None,
get_type=None,
c_symbol_prefix=None,
- disguised=False):
+ disguised=False,
+ private=False):
Node.__init__(self, name)
Registered.__init__(self, gtype_name, get_type)
self.ctype = ctype
@@ -727,7 +729,11 @@ class Compound(Node, Registered):
self.static_methods = []
self.fields = []
self.constructors = []
+ # This compound is: typedef struct Foo * Foo;
+ # note the * which hides that it's a pointer.
self.disguised = disguised
+ # The definition of this structure is not known.
+ self.private = private
self.gtype_name = gtype_name
self.get_type = get_type
self.c_symbol_prefix = c_symbol_prefix
@@ -771,13 +777,15 @@ class Record(Compound):
gtype_name=None,
get_type=None,
c_symbol_prefix=None,
- disguised=False):
+ disguised=False,
+ private=False):
Compound.__init__(self, name,
ctype=ctype,
gtype_name=gtype_name,
get_type=get_type,
c_symbol_prefix=c_symbol_prefix,
- disguised=disguised)
+ disguised=disguised,
+ private=private)
# If non-None, this record defines the FooClass C structure
# for some Foo GObject (or similar for GInterface)
self.is_gtype_struct_for = None
@@ -790,13 +798,15 @@ class Union(Compound):
gtype_name=None,
get_type=None,
c_symbol_prefix=None,
- disguised=False):
+ disguised=False,
+ private=False):
Compound.__init__(self, name,
ctype=ctype,
gtype_name=gtype_name,
get_type=get_type,
c_symbol_prefix=c_symbol_prefix,
- disguised=disguised)
+ disguised=disguised,
+ private=private)
class Boxed(Node, Registered):
diff --git a/giscanner/girparser.py b/giscanner/girparser.py
index ab2b29d..442fc33 100644
--- a/giscanner/girparser.py
+++ b/giscanner/girparser.py
@@ -334,6 +334,7 @@ class GIRParser(object):
compound = cls(node.attrib.get('name'),
ctype=node.attrib.get(_cns('type')),
disguised=node.attrib.get('disguised') == '1',
+ private=node.attrib.get('private') == '1',
gtype_name=node.attrib.get(_glibns('type-name')),
get_type=node.attrib.get(_glibns('get-type')),
c_symbol_prefix=node.attrib.get(_cns('symbol-prefix')))
diff --git a/giscanner/transformer.py b/giscanner/transformer.py
index 328d29e..9e35620 100644
--- a/giscanner/transformer.py
+++ b/giscanner/transformer.py
@@ -50,7 +50,8 @@ class Transformer(object):
self._accept_unprefixed = accept_unprefixed
self._namespace = namespace
self._pkg_config_packages = set()
- self._typedefs_ns = {}
+ self._typedefs = {}
+ self._hidden_structures = {}
self._includes = {}
self._include_names = set()
self._includepaths = []
@@ -84,24 +85,25 @@ class Transformer(object):
if node:
self._append_new_node(node)
- # Now look through the namespace for things like
- # typedef struct _Foo Foo;
- # where we've never seen the struct _Foo. Just create
- # an empty structure for these as "disguised"
- # If we do have a class/interface, merge fields
- for typedef, compound in self._typedefs_ns.iteritems():
- ns_compound = self._namespace.get(compound.name)
- if not ns_compound:
- ns_compound = self._namespace.get('_' + compound.name)
- if (not ns_compound and isinstance(compound, (ast.Record, ast.Union))
- and len(compound.fields) == 0):
- disguised = ast.Record(compound.name, typedef, disguised=True)
- self._namespace.append(disguised)
- elif not ns_compound:
- self._namespace.append(compound)
- elif isinstance(ns_compound, (ast.Record, ast.Union)) and len(ns_compound.fields) == 0:
- ns_compound.fields = compound.fields
- self._typedefs_ns = None
+ for typedef, target_name in self._typedefs.iteritems():
+ if target_name.startswith('_'):
+ target = self._hidden_structures.get(target_name, None)
+ else:
+ continue
+ print "processing %r => %r, target=%r" % (typedef, target_name, target)
+ if target is None:
+ stub = ast.Record(typedef, typedef, private=True)
+ self._namespace.append(stub)
+ else:
+ target.name = typedef
+ self._namespace.append(target)
+ del self._hidden_structures[target_name]
+
+ for name, struct in self._hidden_structures.iteritems():
+ typedef = self._namespace.get(name[1:])
+ if not typedef:
+ message.warn_node(struct,
+"%r: Hidden structure with no corresponding typedef" % (name, ))
def set_include_paths(self, paths):
self._includepaths = list(paths)
@@ -282,7 +284,7 @@ raise ValueError."""
return '_' + name
return name
- def _traverse_one(self, symbol, stype=None):
+ def _traverse_one(self, symbol, stype=None, is_field=False):
assert isinstance(symbol, SourceSymbol), symbol
if stype is None:
@@ -292,13 +294,13 @@ raise ValueError."""
elif stype == CSYMBOL_TYPE_TYPEDEF:
return self._create_typedef(symbol)
elif stype == CSYMBOL_TYPE_STRUCT:
- return self._create_struct(symbol)
+ return self._create_struct(symbol, is_field=is_field)
elif stype == CSYMBOL_TYPE_ENUM:
return self._create_enum(symbol)
elif stype == CSYMBOL_TYPE_MEMBER:
return self._create_member(symbol)
elif stype == CSYMBOL_TYPE_UNION:
- return self._create_union(symbol)
+ return self._create_union(symbol, is_field=is_field)
elif stype == CSYMBOL_TYPE_CONST:
return self._create_const(symbol)
# Ignore variable declarations in the header
@@ -441,11 +443,11 @@ raise ValueError."""
node = self._create_typedef_callback(symbol)
elif (ctype == CTYPE_POINTER and
symbol.base_type.base_type.type == CTYPE_STRUCT):
- node = self._create_typedef_struct(symbol, disguised=True)
+ node = self._create_typedef_compound(ast.Struct, symbol, disguised=True)
elif ctype == CTYPE_STRUCT:
- node = self._create_typedef_struct(symbol)
+ node = self._create_typedef_compound(ast.Struct, symbol)
elif ctype == CTYPE_UNION:
- node = self._create_typedef_union(symbol)
+ node = self._create_typedef_compound(ast.Union, symbol)
elif ctype == CTYPE_ENUM:
return self._create_enum(symbol)
elif ctype in (CTYPE_TYPEDEF,
@@ -597,17 +599,29 @@ raise ValueError."""
const.add_symbol_reference(symbol)
return const
- def _create_typedef_struct(self, symbol, disguised=False):
+ def _create_typedef_compound(self, cls, symbol, disguised=False):
try:
name = self.strip_identifier(symbol.ident)
except TransformerException, e:
message.warn_symbol(symbol, e)
return None
- struct = ast.Record(name, symbol.ident, disguised=disguised)
- self._parse_fields(symbol, struct)
- struct.add_symbol_reference(symbol)
- self._typedefs_ns[symbol.ident] = struct
- return None
+
+ if disguised:
+ return cls(name, symbol.ident, disguised=True)
+
+ children = list(symbol.base_type.child_list)
+ if len(children) > 0:
+ compound = cls(name, symbol.ident, disguised)
+ self._parse_fields(symbol, compound)
+ compound.add_symbol_reference(symbol)
+ return compound
+ else:
+ try:
+ target_name = self.strip_identifier(symbol.base_type.name)
+ except TransformerException, e:
+ message.warn_symbol(symbol, e)
+ return None
+ self._typedefs[name] = target_name
def _create_typedef_union(self, symbol):
try:
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]