summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--gir/freetype2-2.0.gir4
-rw-r--r--girepository/girparser.c99
-rw-r--r--giscanner/girparser.py3
-rw-r--r--giscanner/girwriter.py5
-rw-r--r--tests/scanner/Foo-1.0-expected.gir19
-rw-r--r--tests/scanner/Utility-1.0-expected.gir4
-rw-r--r--tests/scanner/foo.h5
7 files changed, 89 insertions, 50 deletions
diff --git a/gir/freetype2-2.0.gir b/gir/freetype2-2.0.gir
index 9065bb9d..222d3389 100644
--- a/gir/freetype2-2.0.gir
+++ b/gir/freetype2-2.0.gir
@@ -6,7 +6,9 @@
<record name="Bitmap" c:type="FT_Bitmap"/>
<record name="Face" c:type="FT_Face"/>
<record name="Library" c:type="FT_Library"/>
- <alias name="Int32" target="int32" c:type="FT_Int32"/>
+ <alias name="Int32" c:type="FT_Int32">
+ <type name="int32"/>
+ </alias>
<function name="library_version" c:identifier="FT_Library_Version">
<return-value transfer-ownership="none">
<type name="none" c:type="void"/>
diff --git a/girepository/girparser.c b/girepository/girparser.c
index ae1e625d..17ed6b54 100644
--- a/girepository/girparser.c
+++ b/girepository/girparser.c
@@ -101,6 +101,7 @@ struct _ParseContext
const char *c_prefix;
GIrModule *current_module;
GSList *node_stack;
+ char *current_alias;
GIrNode *current_typed;
GList *type_stack;
GList *type_parameters;
@@ -127,6 +128,8 @@ static void text_handler (GMarkupParseContext *context,
static void cleanup (GMarkupParseContext *context,
GError *error,
gpointer user_data);
+static void state_switch (ParseContext *ctx, ParseState newstate);
+
static GMarkupParser markup_parser =
{
@@ -144,6 +147,13 @@ start_alias (GMarkupParseContext *context,
const gchar **attribute_values,
ParseContext *ctx,
GError **error);
+static gboolean
+start_type (GMarkupParseContext *context,
+ const gchar *element_name,
+ const gchar **attribute_names,
+ const gchar **attribute_values,
+ ParseContext *ctx,
+ GError **error);
static const gchar *find_attribute (const gchar *name,
const gchar **attribute_names,
@@ -197,6 +207,11 @@ firstpass_start_element_handler (GMarkupParseContext *context,
start_alias (context, element_name, attribute_names, attribute_values,
ctx, error);
}
+ else if (ctx->state == STATE_ALIAS && strcmp (element_name, "type") == 0)
+ {
+ start_type (context, element_name, attribute_names, attribute_values,
+ ctx, error);
+ }
else if (strcmp (element_name, "record") == 0)
{
const gchar *name;
@@ -221,6 +236,15 @@ firstpass_end_element_handler (GMarkupParseContext *context,
gpointer user_data,
GError **error)
{
+ ParseContext *ctx = user_data;
+ if (strcmp (element_name, "alias") == 0)
+ {
+ state_switch (ctx, STATE_NAMESPACE);
+ g_free (ctx->current_alias);
+ ctx->current_alias = NULL;
+ }
+ else if (strcmp (element_name, "type") == 0 && ctx->state == STATE_TYPE)
+ state_switch (ctx, ctx->prev_state);
}
static GMarkupParser firstpass_parser =
@@ -1237,9 +1261,6 @@ start_alias (GMarkupParseContext *context,
GError **error)
{
const gchar *name;
- const gchar *target;
- char *key;
- char *value;
name = find_attribute ("name", attribute_names, attribute_values);
if (name == NULL)
@@ -1248,26 +1269,8 @@ start_alias (GMarkupParseContext *context,
return FALSE;
}
- target = find_attribute ("target", attribute_names, attribute_values);
- if (name == NULL)
- {
- MISSING_ATTRIBUTE (context, error, element_name, "target");
- return FALSE;
- }
-
- value = g_strdup (target);
- key = g_strdup_printf ("%s.%s", ctx->namespace, name);
- if (!strchr (target, '.'))
- {
- const BasicTypeInfo *basic = parse_basic (target);
- if (!basic)
- {
- g_free (value);
- /* For non-basic types, re-qualify the interface */
- value = g_strdup_printf ("%s.%s", ctx->namespace, target);
- }
- }
- g_hash_table_replace (ctx->aliases, key, value);
+ ctx->current_alias = g_strdup (name);
+ state_switch (ctx, STATE_ALIAS);
return TRUE;
}
@@ -1781,6 +1784,7 @@ start_type (GMarkupParseContext *context,
{
const gchar *name;
const gchar *ctype;
+ gboolean in_alias = FALSE;
gboolean is_array;
gboolean is_varargs;
GIrNodeType *typenode;
@@ -1808,15 +1812,55 @@ start_type (GMarkupParseContext *context,
ctx->state == STATE_BOXED_FIELD ||
ctx->state == STATE_NAMESPACE_CONSTANT ||
ctx->state == STATE_CLASS_CONSTANT ||
- ctx->state == STATE_INTERFACE_CONSTANT
+ ctx->state == STATE_INTERFACE_CONSTANT ||
+ ctx->state == STATE_ALIAS
)
{
+ if (ctx->state == STATE_ALIAS)
+ in_alias = TRUE;
state_switch (ctx, STATE_TYPE);
ctx->type_depth = 1;
ctx->type_stack = NULL;
ctx->type_parameters = NULL;
}
+ name = find_attribute ("name", attribute_names, attribute_values);
+
+ if (in_alias && ctx->current_alias)
+ {
+ char *key;
+ char *value;
+
+ if (name == NULL)
+ {
+ MISSING_ATTRIBUTE (context, error, element_name, "name");
+ return FALSE;
+ }
+
+ key = g_strdup_printf ("%s.%s", ctx->namespace, ctx->current_alias);
+ if (!strchr (name, '.'))
+ {
+ const BasicTypeInfo *basic = parse_basic (name);
+ if (!basic)
+ {
+ /* For non-basic types, re-qualify the interface */
+ value = g_strdup_printf ("%s.%s", ctx->namespace, name);
+ }
+ else
+ {
+ value = g_strdup (name);
+ }
+ }
+ else
+ value = g_strdup (name);
+
+ g_hash_table_replace (ctx->aliases, key, value);
+
+ return TRUE;
+ }
+ else if (!ctx->current_module || in_alias)
+ return TRUE;
+
if (!ctx->current_typed)
{
g_set_error (error,
@@ -1842,7 +1886,6 @@ start_type (GMarkupParseContext *context,
typenode->is_pointer = TRUE;
typenode->is_array = TRUE;
- name = find_attribute ("name", attribute_names, attribute_values);
if (name && strcmp (name, "GLib.Array") == 0) {
typenode->array_type = GI_ARRAY_TYPE_ARRAY;
} else if (name && strcmp (name, "GLib.ByteArray") == 0) {
@@ -1883,7 +1926,6 @@ start_type (GMarkupParseContext *context,
else
{
int pointer_depth;
- name = find_attribute ("name", attribute_names, attribute_values);
if (name == NULL)
{
@@ -2933,7 +2975,7 @@ start_element_handler (GMarkupParseContext *context,
break;
}
- if (ctx->state != STATE_PASSTHROUGH)
+ if (*error == NULL && ctx->state != STATE_PASSTHROUGH)
{
g_markup_parse_context_get_position (context, &line_number, &char_number);
if (!g_str_has_prefix (element_name, "c:"))
@@ -3088,6 +3130,8 @@ end_element_handler (GMarkupParseContext *context,
case STATE_ALIAS:
if (require_end_element (context, ctx, "alias", element_name, error))
{
+ g_free (ctx->current_alias);
+ ctx->current_alias = NULL;
state_switch (ctx, STATE_NAMESPACE);
}
break;
@@ -3415,6 +3459,7 @@ g_ir_parser_parse_string (GIrParser *parser,
g_markup_parse_context_free (context);
+ ctx.state = STATE_START;
context = g_markup_parse_context_new (&markup_parser, 0, &ctx, NULL);
if (!g_markup_parse_context_parse (context, buffer, length, error))
goto out;
diff --git a/giscanner/girparser.py b/giscanner/girparser.py
index 17cf630c..9fee1fc1 100644
--- a/giscanner/girparser.py
+++ b/giscanner/girparser.py
@@ -160,8 +160,9 @@ class GIRParser(object):
self._pkgconfig_packages.add(node.attrib['name'])
def _parse_alias(self, node):
+ typeval = self._parse_type(node)
alias = Alias(node.attrib['name'],
- node.attrib['target'],
+ typeval,
node.attrib.get(_cns('type')))
self._add_node(alias)
diff --git a/giscanner/girwriter.py b/giscanner/girwriter.py
index 2e0a6cdc..0f621251 100644
--- a/giscanner/girwriter.py
+++ b/giscanner/girwriter.py
@@ -153,10 +153,11 @@ and/or use gtk-doc annotations. ''')
attrs.append(('throws', '1'))
def _write_alias(self, alias):
- attrs = [('name', alias.name), ('target', alias.target)]
+ attrs = [('name', alias.name)]
if alias.ctype is not None:
attrs.append(('c:type', alias.ctype))
- self.write_tag('alias', attrs)
+ with self.tagcontext('alias', attrs):
+ self._write_type(alias.target)
def _write_callable(self, callable, tag_name, extra_attrs):
attrs = [('name', callable.name)]
diff --git a/tests/scanner/Foo-1.0-expected.gir b/tests/scanner/Foo-1.0-expected.gir
index 4007d96a..e14d3c80 100644
--- a/tests/scanner/Foo-1.0-expected.gir
+++ b/tests/scanner/Foo-1.0-expected.gir
@@ -16,9 +16,12 @@ and/or use gtk-doc annotations. -->
version="1.0"
shared-library="libfoo.so"
c:prefix="Foo">
- <alias name="List" target="GLib.SList" c:type="FooList"/>
- <alias name="ObjectCookie" target="any" c:type="FooObjectCookie"/>
- <alias name="XEvent" target="none" c:type="FooXEvent"/>
+ <alias name="ObjectCookie" c:type="FooObjectCookie">
+ <type name="any"/>
+ </alias>
+ <alias name="XEvent" c:type="FooXEvent">
+ <type name="none"/>
+ </alias>
<enumeration name="ASingle" c:type="FooASingle">
<member name="some_single_enum"
value="0"
@@ -379,16 +382,6 @@ uses a C sugar return type.</doc>
</parameter>
</parameters>
</method>
- <method name="with_tdef" c:identifier="foo_object_with_tdef">
- <return-value transfer-ownership="none">
- <type name="none" c:type="void"/>
- </return-value>
- <parameters>
- <parameter name="blah" transfer-ownership="none">
- <type name="List" c:type="FooList*"/>
- </parameter>
- </parameters>
- </method>
<method name="new_cookie" c:identifier="foo_object_new_cookie">
<return-value transfer-ownership="full">
<type name="ObjectCookie" c:type="FooObjectCookie"/>
diff --git a/tests/scanner/Utility-1.0-expected.gir b/tests/scanner/Utility-1.0-expected.gir
index d7e50ed0..6bf37446 100644
--- a/tests/scanner/Utility-1.0-expected.gir
+++ b/tests/scanner/Utility-1.0-expected.gir
@@ -13,7 +13,9 @@ and/or use gtk-doc annotations. -->
version="1.0"
shared-library="libutility.so"
c:prefix="Utility">
- <alias name="Glyph" target="uint32" c:type="UtilityGlyph"/>
+ <alias name="Glyph" c:type="UtilityGlyph">
+ <type name="uint32"/>
+ </alias>
<record name="Buffer" c:type="UtilityBuffer">
<field name="data" writable="1">
<type name="any" c:type="char*"/>
diff --git a/tests/scanner/foo.h b/tests/scanner/foo.h
index fb4bc5cc..7120d015 100644
--- a/tests/scanner/foo.h
+++ b/tests/scanner/foo.h
@@ -103,11 +103,6 @@ void foo_object_various (FooObject *object, void *dat
void foo_object_take_all (FooObject *object, int x, ...);
-/* A random typedef */
-typedef GSList FooList;
-
-void foo_object_with_tdef (FooObject *object, FooList *blah);
-
typedef gpointer FooObjectCookie;
FooObjectCookie foo_object_new_cookie (FooObject *object, const char *target);