summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJohan Dahlin <jdahlin@async.com.br>2009-01-12 23:54:48 +0000
committerJohan Dahlin <johan@src.gnome.org>2009-01-12 23:54:48 +0000
commit6de1b29629397bc7328f1a44da7530ea2ff53dac (patch)
treea3bbbe7e24b8fd51776d19592b007008cd900cea
parent9256e916164ec557ed66f92a0d6d95bb286cdf8b (diff)
downloadgobject-introspection-6de1b29629397bc7328f1a44da7530ea2ff53dac.tar.gz
Bug 546739 – Introspection should know precise signal parameter types
2009-01-12 Johan Dahlin <jdahlin@async.com.br> Bug 546739 – Introspection should know precise signal parameter types * giscanner/annotationparser.py: * tests/scanner/annotation-1.0-expected.gir: * tests/scanner/annotation-1.0-expected.tgir: * tests/scanner/annotation.c (annotation_object_class_init): Annotations are parsed for signals, the (type) annotation is introduced. svn path=/trunk/; revision=1026
-rw-r--r--ChangeLog11
-rw-r--r--giscanner/annotationparser.py52
-rw-r--r--tests/scanner/annotation-1.0-expected.gir13
-rw-r--r--tests/scanner/annotation-1.0-expected.tgir10
-rw-r--r--tests/scanner/annotation.c30
5 files changed, 103 insertions, 13 deletions
diff --git a/ChangeLog b/ChangeLog
index 7e4c22b9..1d991ee2 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,16 @@
2009-01-12 Johan Dahlin <jdahlin@async.com.br>
+ Bug 546739 – Introspection should know precise signal parameter types
+
+ * giscanner/annotationparser.py:
+ * tests/scanner/annotation-1.0-expected.gir:
+ * tests/scanner/annotation-1.0-expected.tgir:
+ * tests/scanner/annotation.c (annotation_object_class_init):
+
+ Annotations are parsed for signals, the (type) annotation is introduced.
+
+2009-01-12 Johan Dahlin <jdahlin@async.com.br>
+
Bug 563591 – Flags not recognized when there is no introspection data
* giscanner/ast.py:
diff --git a/giscanner/annotationparser.py b/giscanner/annotationparser.py
index 89d4b334..d61d8a5b 100644
--- a/giscanner/annotationparser.py
+++ b/giscanner/annotationparser.py
@@ -21,7 +21,7 @@
# AnnotationParser - parses gtk-doc annotations
# All gtk-doc comments needs to start with this:
-_COMMENT_HEADER = '*\n * '
+_COMMENT_HEADER = '*\n '
from .ast import (Array, Callback, Class, Enum, Field, Function, Interface,
List, Map, Parameter, Record, Return, Type, Union, Varargs,
@@ -34,6 +34,7 @@ from .ast import (Array, Callback, Class, Enum, Field, Function, Interface,
PARAM_TRANSFER_CONTAINER,
PARAM_TRANSFER_FULL,
TYPE_ANY, TYPE_NONE)
+from .odict import odict
from .glibast import GLibBoxed
@@ -46,10 +47,10 @@ class DocBlock(object):
def __init__(self, name):
self.name = name
self.value = None
- self.tags = {}
+ self.tags = odict()
def __repr__(self):
- return '<Directive %r>' % (self.name, )
+ return '<DocBlock %r>' % (self.name, )
def get(self, name):
if name == 'Returns':
@@ -114,9 +115,15 @@ class AnnotationParser(object):
aa.parse(self._namespace)
def _parse_comment(self, comment):
+ comment = comment.lstrip()
if not comment.startswith(_COMMENT_HEADER):
return
comment = comment[len(_COMMENT_HEADER):]
+ comment = comment.strip()
+ if not comment.startswith('* '):
+ return
+ comment = comment[2:]
+
pos = comment.index('\n ')
block_name = comment[:pos]
@@ -126,6 +133,7 @@ class AnnotationParser(object):
block = DocBlock(block_name[:-1])
content = comment[pos+1:]
for line in content.split('\n'):
+ line = line.lstrip()
line = line[2:].strip() # Skip ' *'
if not line:
continue
@@ -221,7 +229,7 @@ class AnnotationApplier(object):
self._parse_methods(class_.methods)
self._parse_methods(class_.static_methods)
self._parse_properties(class_.properties)
- self._parse_signals(class_.signals)
+ self._parse_signals(class_, class_.signals)
self._parse_fields(class_, class_.fields)
def _parse_interface(self, interface):
@@ -229,7 +237,7 @@ class AnnotationApplier(object):
self._parse_version(interface, block)
self._parse_methods(interface.methods)
self._parse_properties(interface.properties)
- self._parse_signals(interface.signals)
+ self._parse_signals(interface, interface.signals)
self._parse_fields(interface, interface.fields)
def _parse_record(self, record):
@@ -273,9 +281,9 @@ class AnnotationApplier(object):
for method in methods:
self._parse_function(method)
- def _parse_signals(self, signals):
+ def _parse_signals(self, parent, signals):
for signal in signals:
- self._parse_signal(signal)
+ self._parse_signal(parent, signal)
def _parse_property(self, prop):
pass
@@ -293,10 +301,28 @@ class AnnotationApplier(object):
self._parse_params(func, func.parameters, block)
self._parse_return(func, func.retval, block)
- def _parse_signal(self, signal):
- block = self._blocks.get(signal.name)
+ def _parse_signal(self, parent, signal):
+ block = self._blocks.get('%s::%s' % (parent.type_name, signal.name))
self._parse_version(signal, block)
- self._parse_params(signal, signal.parameters, block)
+ self._parse_deprecated(signal, block)
+ # We're only attempting to name the signal parameters if
+ # the number of parameter tags (@foo) is the same or greater
+ # than the number of signal parameters
+ if block and len(block.tags) > len(signal.parameters):
+ names = block.tags.items()
+ else:
+ names = []
+ for i, param in enumerate(signal.parameters):
+ if names:
+ name, tag = names[i+1]
+ param.name = name
+ options = getattr(tag, 'options', {})
+ param_type = options.get('type')
+ if param_type:
+ param.type.name = param_type.one()
+ else:
+ tag = None
+ self._parse_param(signal, param, tag)
self._parse_return(signal, signal.retval, block)
def _parse_field(self, parent, field):
@@ -305,15 +331,15 @@ class AnnotationApplier(object):
def _parse_params(self, parent, params, block):
for param in params:
- self._parse_param(parent, param, block)
+ tag = self._get_tag(block, param.name)
+ self._parse_param(parent, param, tag)
def _parse_return(self, parent, return_, block):
tag = self._get_tag(block, 'Returns')
options = getattr(tag, 'options', {})
self._parse_param_ret_common(parent, return_, options)
- def _parse_param(self, parent, param, block):
- tag = self._get_tag(block, param.name)
+ def _parse_param(self, parent, param, tag):
options = getattr(tag, 'options', {})
if isinstance(parent, Function):
diff --git a/tests/scanner/annotation-1.0-expected.gir b/tests/scanner/annotation-1.0-expected.gir
index 03915599..609d6d06 100644
--- a/tests/scanner/annotation-1.0-expected.gir
+++ b/tests/scanner/annotation-1.0-expected.gir
@@ -317,6 +317,19 @@
<field name="parent_instance">
<type name="GObject.Object" c:type="GObject"/>
</field>
+ <glib:signal name="string-signal"
+ version="1.0"
+ deprecated="Use other-signal instead"
+ deprecated-version="1.2">
+ <return-value transfer-ownership="full">
+ <type name="none" c:type="void"/>
+ </return-value>
+ <parameters>
+ <parameter name="string" transfer-ownership="none">
+ <type name="utf8" c:type="gpointer"/>
+ </parameter>
+ </parameters>
+ </glib:signal>
</class>
<record name="ObjectClass" c:type="AnnotationObjectClass">
<field name="parent_class">
diff --git a/tests/scanner/annotation-1.0-expected.tgir b/tests/scanner/annotation-1.0-expected.tgir
index bb160fc8..e06a3379 100644
--- a/tests/scanner/annotation-1.0-expected.tgir
+++ b/tests/scanner/annotation-1.0-expected.tgir
@@ -297,6 +297,16 @@
<type name="GObject.Object"/>
</return-value>
</method>
+ <glib:signal name="string-signal" when="LAST">
+ <return-value transfer-ownership="full">
+ <type name="none"/>
+ </return-value>
+ <parameters>
+ <parameter name="string" transfer-ownership="none">
+ <type name="utf8"/>
+ </parameter>
+ </parameters>
+ </glib:signal>
</class>
<record name="ObjectClass">
<field name="parent_class">
diff --git a/tests/scanner/annotation.c b/tests/scanner/annotation.c
index 8239400e..98b3b061 100644
--- a/tests/scanner/annotation.c
+++ b/tests/scanner/annotation.c
@@ -4,9 +4,39 @@ static char backslash_parsing_tester = '\\';
G_DEFINE_TYPE (AnnotationObject, annotation_object, G_TYPE_OBJECT);
+enum {
+ STRING_SIGNAL,
+ LAST_SIGNAL
+};
+
+static guint annotation_object_signals[LAST_SIGNAL] = { 0 };
+
static void
annotation_object_class_init (AnnotationObjectClass *klass)
{
+ GObjectClass *gobject_class;
+
+ gobject_class = G_OBJECT_CLASS (klass);
+
+ /**
+ * AnnotationObject::string-signal:
+ * @annotation: the annotation object
+ * @string: (type utf8): a string
+ *
+ * This is a signal which has a broken signal handler,
+ * it says it's pointer but it's actually a string.
+ *
+ * Since: 1.0
+ * Deprecated: 1.2: Use other-signal instead
+ */
+ annotation_object_signals[STRING_SIGNAL] =
+ g_signal_new ("string-signal",
+ G_OBJECT_CLASS_TYPE (gobject_class),
+ G_SIGNAL_RUN_LAST,
+ 0,
+ NULL, NULL,
+ (GSignalCMarshaller)g_cclosure_marshal_VOID__POINTER,
+ G_TYPE_NONE, 1, G_TYPE_POINTER);
}