summaryrefslogtreecommitdiff
path: root/src/webidl-parser.y
diff options
context:
space:
mode:
authorVincent Sanders <vince@kyllikki.org>2012-10-31 01:20:20 +0000
committerVincent Sanders <vince@kyllikki.org>2012-10-31 01:20:20 +0000
commit65e49e23019a97d51702077c82613c6c26e84033 (patch)
treef21ba90ba9dc08826ef687f9bd148e6345fd673a /src/webidl-parser.y
parent26bbe37c6f0b99f23736380ba55f156f22bdaf06 (diff)
downloadnsgenbind-65e49e23019a97d51702077c82613c6c26e84033.tar.gz
nsgenbind-65e49e23019a97d51702077c82613c6c26e84033.tar.bz2
implement the "implements" webidl directive
Diffstat (limited to 'src/webidl-parser.y')
-rw-r--r--src/webidl-parser.y55
1 files changed, 37 insertions, 18 deletions
diff --git a/src/webidl-parser.y b/src/webidl-parser.y
index 3cf1b6c..53e21e1 100644
--- a/src/webidl-parser.y
+++ b/src/webidl-parser.y
@@ -167,22 +167,9 @@ webidl_error(YYLTYPE *locp, struct webidl_node **winbind_ast, const char *str)
%%
- /* default rule to add built AST to passed in one */
-Input:
- Definitions
- {
- *webidl_ast = webidl_node_prepend(*webidl_ast, $1);
- }
- |
- error
- {
- fprintf(stderr, "%d: %s\n", yylloc.first_line, errtxt);
- free(errtxt);
- YYABORT ;
- }
- ;
-
- /* [1] altered from original grammar to be left recusive, */
+ /* [1] default rule to add built AST to passed in one, altered from
+ * original grammar to be left recusive,
+ */
Definitions:
/* empty */
{
@@ -191,7 +178,14 @@ Definitions:
|
Definitions ExtendedAttributeList Definition
{
- $$ = webidl_node_prepend($1, $3);
+ $$ = *webidl_ast = webidl_node_prepend(*webidl_ast, $3);
+ }
+ |
+ error
+ {
+ fprintf(stderr, "%d: %s\n", yylloc.first_line, errtxt);
+ free(errtxt);
+ YYABORT ;
}
;
@@ -248,6 +242,7 @@ Interface:
interface_node = webidl_node_find_type_ident(*webidl_ast,
WEBIDL_NODE_TYPE_INTERFACE,
$2);
+
if (interface_node == NULL) {
/* no existing interface - create one with ident */
members = webidl_node_new(WEBIDL_NODE_TYPE_IDENT, members, $2);
@@ -480,7 +475,31 @@ Typedef:
ImplementsStatement:
TOK_IDENTIFIER TOK_IMPLEMENTS TOK_IDENTIFIER ';'
{
- $$ = NULL;
+ /* extend interface with implements members */
+ struct webidl_node *implements;
+ struct webidl_node *interface_node;
+
+
+ interface_node = webidl_node_find_type_ident(*webidl_ast,
+ WEBIDL_NODE_TYPE_INTERFACE,
+ $1);
+
+ implements = webidl_node_new(WEBIDL_NODE_TYPE_INTERFACE_IMPLEMENTS, NULL, $3);
+
+ if (interface_node == NULL) {
+ /* interface doesnt already exist so create it */
+
+ implements = webidl_node_new(WEBIDL_NODE_TYPE_IDENT, implements, $1);
+
+ $$ = webidl_node_new(WEBIDL_NODE_TYPE_INTERFACE, NULL, implements);
+ } else {
+ /* update the existing interface */
+
+ /* link implements node into interfaces_node */
+ webidl_node_add(interface_node, implements);
+
+ $$ = NULL; /* updating so no need to add a new node */
+ }
}
;