summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorVincent Sanders <vince@kyllikki.org>2015-07-22 13:13:41 +0100
committerVincent Sanders <vince@kyllikki.org>2015-07-22 13:13:41 +0100
commit8bc392a91daf4cc1a27a8e6777af1a29ed24e3c4 (patch)
tree2d6b837bc51caf015a58b785ce276f024f65f3b0
parent1288d8c535edd2ce29eebdc4acca6b2beab89841 (diff)
downloadnsgenbind-8bc392a91daf4cc1a27a8e6777af1a29ed24e3c4.tar.gz
nsgenbind-8bc392a91daf4cc1a27a8e6777af1a29ed24e3c4.tar.bz2
chnage binding AST to put methds inside class nodes
-rw-r--r--src/nsgenbind-ast.c57
-rw-r--r--src/nsgenbind-ast.h4
-rw-r--r--src/nsgenbind-parser.y47
-rw-r--r--src/nsgenbind.c20
4 files changed, 115 insertions, 13 deletions
diff --git a/src/nsgenbind-ast.c b/src/nsgenbind-ast.c
index 49477cf..1b5f53c 100644
--- a/src/nsgenbind-ast.c
+++ b/src/nsgenbind-ast.c
@@ -38,6 +38,63 @@ struct genbind_node {
} r;
};
+/* insert node(s) at beginning of a list */
+struct genbind_node *
+genbind_node_prepend(struct genbind_node *list, struct genbind_node *inst)
+{
+ struct genbind_node *end = inst;
+
+ if (inst == NULL) {
+ return list; /* no node to prepend - return existing list */
+ }
+
+ /* find end of inserted node list */
+ while (end->l != NULL) {
+ end = end->l;
+ }
+
+ end->l = list;
+
+ return inst;
+}
+
+/* prepend list to a nodes list
+ *
+ * inserts a list into the beginning of a nodes r list
+ *
+ * CAUTION: if the \a node element is not a node type the node will not be added
+ */
+struct genbind_node *
+genbind_node_add(struct genbind_node *node, struct genbind_node *list)
+{
+ if (node == NULL) {
+ return list;
+ }
+
+ /* this does not use genbind_node_getnode() as it cannot
+ * determine between an empty node and a node which is not a
+ * list type
+ */
+ switch (node->type) {
+ case GENBIND_NODE_TYPE_BINDING:
+ case GENBIND_NODE_TYPE_CLASS:
+ case GENBIND_NODE_TYPE_PRIVATE:
+ case GENBIND_NODE_TYPE_INTERNAL:
+ case GENBIND_NODE_TYPE_PROPERTY:
+ case GENBIND_NODE_TYPE_FLAGS:
+ case GENBIND_NODE_TYPE_METHOD:
+ case GENBIND_NODE_TYPE_PARAMETER:
+ break;
+
+ default:
+ /* not a node type */
+ return list;
+ }
+
+ node->r.node = genbind_node_prepend(node->r.node, list);
+
+ return node;
+}
char *genbind_strapp(char *a, char *b)
{
diff --git a/src/nsgenbind-ast.h b/src/nsgenbind-ast.h
index f6800fb..e7215b1 100644
--- a/src/nsgenbind-ast.h
+++ b/src/nsgenbind-ast.h
@@ -70,6 +70,10 @@ char *genbind_strapp(char *a, char *b);
struct genbind_node *genbind_new_node(enum genbind_node_type type, struct genbind_node *l, void *r);
struct genbind_node *genbind_node_link(struct genbind_node *tgt, struct genbind_node *src);
+struct genbind_node *genbind_node_prepend(struct genbind_node *list, struct genbind_node *inst);
+
+struct genbind_node *genbind_node_add(struct genbind_node *node, struct genbind_node *list);
+
/**
* Dump the binding AST to file
*
diff --git a/src/nsgenbind-parser.y b/src/nsgenbind-parser.y
index c8e5154..454fb56 100644
--- a/src/nsgenbind-parser.y
+++ b/src/nsgenbind-parser.y
@@ -128,7 +128,7 @@ Statements
|
Statements Statement
{
- $$ = genbind_node_link($2, $1);
+ $$ = *genbind_ast = genbind_node_prepend($2, $1);
}
|
error ';'
@@ -330,11 +330,52 @@ Method
:
MethodType MethodDeclarator CBlock
{
- $$ = genbind_new_node(GENBIND_NODE_TYPE_METHOD, NULL,
+ struct genbind_node *declarator;
+ struct genbind_node *method_node;
+ struct genbind_node *class_node;
+ char *class_name;
+
+ declarator = $2;
+
+ /* extract the class name from the declarator */
+ class_name = genbind_node_gettext(
+ genbind_node_find_type(
+ genbind_node_getnode(
+ genbind_node_find_type(
+ declarator,
+ NULL,
+ GENBIND_NODE_TYPE_CLASS)),
+ NULL,
+ GENBIND_NODE_TYPE_IDENT));
+
+ /* generate method node */
+ method_node = genbind_new_node(GENBIND_NODE_TYPE_METHOD, NULL,
genbind_new_node(GENBIND_NODE_TYPE_METHOD_TYPE,
genbind_new_node(GENBIND_NODE_TYPE_CDATA,
- $2, $3),
+ declarator, $3),
(void *)$1));
+
+
+
+ class_node = genbind_node_find_type_ident(*genbind_ast,
+ NULL,
+ GENBIND_NODE_TYPE_CLASS,
+ class_name);
+ if (class_node == NULL) {
+ /* no existing class so manufacture one and attach method */
+ $$ = genbind_new_node(GENBIND_NODE_TYPE_CLASS, NULL,
+ genbind_new_node(GENBIND_NODE_TYPE_IDENT,
+ method_node,
+ class_name));
+
+ } else {
+ /* update the existing class */
+
+ /* link member node into class_node */
+ genbind_node_add(class_node, method_node);
+
+ $$ = NULL; /* updating so no need to add a new node */
+ }
}
diff --git a/src/nsgenbind.c b/src/nsgenbind.c
index 3174fa0..8d83d13 100644
--- a/src/nsgenbind.c
+++ b/src/nsgenbind.c
@@ -20,6 +20,12 @@
struct options *options;
+enum bindingtype_e {
+ BINDINGTYPE_UNKNOWN,
+ BINDINGTYPE_JSAPI_LIBDOM,
+ BINDINGTYPE_DUK_LIBDOM,
+};
+
static struct options* process_cmdline(int argc, char **argv)
{
int opt;
@@ -98,12 +104,6 @@ static int generate_binding(struct genbind_node *binding_node, void *ctx)
return res;
}
-enum bindingtype_e {
- BINDINGTYPE_UNKNOWN,
- BINDINGTYPE_JSAPI_LIBDOM,
- BINDINGTYPE_DUK_LIBDOM,
-};
-
/**
* get the type of binding
*/
@@ -146,7 +146,7 @@ static enum bindingtype_e genbind_get_type(struct genbind_node *node)
int main(int argc, char **argv)
{
int res;
- struct genbind_node *genbind_root;
+ struct genbind_node *genbind_root = NULL;
enum bindingtype_e bindingtype;
options = process_cmdline(argc, argv);
@@ -154,17 +154,17 @@ int main(int argc, char **argv)
return 1; /* bad commandline */
}
- /* parse input and generate dependancy */
+ /* parse binding */
res = genbind_parsefile(options->infilename, &genbind_root);
if (res != 0) {
fprintf(stderr, "Error: parse failed with code %d\n", res);
return res;
}
- /* dump the AST */
+ /* dump the binding AST */
genbind_dump_ast(genbind_root);
- /* get bindingtype */
+ /* get type of binding */
bindingtype = genbind_get_type(genbind_root);
if (bindingtype == BINDINGTYPE_UNKNOWN) {
return 3;