changeset 351:3529c7e93c4f

fix generate_stub
author mir3636
date Thu, 08 Jun 2017 15:44:39 +0900
parents a9863b41f026
children 3e01e963eb2d
files src/parallel_execution/Stack.cbc src/parallel_execution/generate_stub.pl src/parallel_execution/test/stack_test.cbc
diffstat 3 files changed, 117 insertions(+), 36 deletions(-) [+]
line wrap: on
line diff
--- a/src/parallel_execution/Stack.cbc	Wed Jun 07 15:17:36 2017 +0900
+++ b/src/parallel_execution/Stack.cbc	Thu Jun 08 15:44:39 2017 +0900
@@ -1,14 +1,14 @@
-typedef struct Stack<Impl>{
-        union Data* stack;
-        union Data* data;
-        union Data* data1;
+typedef struct Stack<Type, Impl>{
+        Type* stack;
+        Type* data;
+        Type* data1;
         __code whenEmpty(...);
         __code clear(Impl* stack,__code next(...));
-        __code push(Impl* stack,union Data* data, __code next(...));
-        __code pop(Impl* stack, __code next(union Data*, ...));
-        __code pop2(Impl* stack, union Data** data, union Data** data1, __code next(union Data**, union Data**, ...));
+        __code push(Impl* stack,Type* data, __code next(...));
+        __code pop(Impl* stack, __code next(Type* data, ...));
+        __code pop2(Impl* stack, Type** data, Type** data1, __code next(Type** data, Type** data1, ...));
         __code isEmpty(Impl* stack, __code next(...), __code whenEmpty(...));
-        __code get(Impl* stack, union Data** data, __code next(...));
+        __code get(Impl* stack, Type** data, __code next(...));
         __code get2(Impl* stack,..., __code next(...));
         __code next(...);
 } Stack;
--- a/src/parallel_execution/generate_stub.pl	Wed Jun 07 15:17:36 2017 +0900
+++ b/src/parallel_execution/generate_stub.pl	Thu Jun 08 15:44:39 2017 +0900
@@ -41,18 +41,54 @@
 my $implementation;
 my $interface;
 
+# interface definision
+#
+# typedef struct Stack<Type, Impl>{
+#         Type* stack;
+#         Type* data;
+#         Type* data1;
+#         __code whenEmpty(...);
+#         __code clear(Impl* stack,__code next(...));
+#         __code push(Impl* stack,Type* data, __code next(...));
+#         __code pop(Impl* stack, __code next(Type*, ...));
+#         __code pop2(Impl* stack, Type** data, Type** data1, __code next(Type**, Type**, ...));
+#         __code isEmpty(Impl* stack, __code next(...), __code whenEmpty(...));
+#         __code get(Impl* stack, Type** data, __code next(...));
+#         __code get2(Impl* stack,..., __code next(...));
+#         __code next(...);
+# } Stack;
+#
+# calling example
+#
+# goto nodeStack->push((union Data*)node, stackTest3);
+#
+# generated meta level code
+#
+# Gearef(context, Stack)->stack = nodeStack->stack;
+# Gearef(context, Stack)->data = (union Data*)node;
+# Gearef(context, Stack)->next = C_stackTest3;
+# goto meta(context, nodeStack->push);
+
 sub getDataGear {
     my ($filename) = @_;
     my ($codeGearName, $name, $inTypedef);
     open my $fd,"<",$filename or die("can't open $filename $!");
     while (<$fd>) {
         if (! $inTypedef) {
-            if (/^typedef struct (\w+)/) {
+            if (/^typedef struct (\w+)\s*<(.*)>/) {
                 $inTypedef = 1;
                 $name = $1;
                 $dataGear{$name} = $_;
                 $var{$name} = {};
                 $code{$name} = {};
+                $generic{$name} = \split(/,/,$2);
+            } elsif (/^typedef struct (\w+)/) {
+                $inTypedef = 1;
+                $name = $1;
+                $dataGear{$name} = $_;
+                $var{$name} = {};
+                $code{$name} = {};
+                $generic{$name} = [];
             } elsif (/^(\w+)(\*)+ create(\w+)\(/) {
                 if (defined $interface) {
                    die "duplicate interface $interface\n"; 
@@ -74,8 +110,29 @@
                 $ttype = $2;
             }
             $var{$name}->{$tname} = $ttype;
-	} elsif (/\_\_code (\w+)\(/) {
-            $code{$name}->{$1} = 1;
+        } elsif (/^\_\_code (\w+)\((.*)\)(.*)/) {
+            my $args = $2;
+            my $method = $1;
+            $code{$name}->{$method} = [];
+            while($args) {
+                if ($args =~ s/(^\s*,\s*)//) {
+                }
+                # continuation case
+                if ($args =~ s/^(\s)*\_\_code\s+(\w+)\(([^)]*)\)//) {
+                    my $next = $2;
+                    my @args = split(/,/,$3);
+                    push(@{$code{$name}->{$method}},$next); 
+                } elsif ($args =~ s/^(struct|union) (\w+)(\*)+\s(\w+)//) {
+                    my $structType = $1;
+                    my $typeName = $2;
+                    my $varName = $4;
+                    my $typeField = lcfirst($typeName);
+                    push(@{$code{$name}->{$method}},$varName); 
+                } elsif ($args =~ s/(.*,)//) {
+                } else {
+                    last;
+                }
+            }
         }
         if (/^}/) {
             $inTypedef = 0;
@@ -99,6 +156,7 @@
         return 0 if ( $n eq $varname1);
     }
     push @{$dataGearVar{$codeGearName}}, $varname1;
+    push @{$dataGearVarType{$codeGearName}}, $typeName;
     if ($typeName eq $implementation) {
         # get implementation
         $dataGearName{$codeGearName} .= "\t$typeName* $varName = ($typeName*)GearImpl(context, $interface, $varName);\n";
@@ -253,6 +311,31 @@
                     print $fd $outputVar{$codeGearName};
                 }
                 next;
+            } elsif (/^(.*)goto (\w+)\-\>(\w+)\((.*)\);/) {
+                # handling goto statement  
+                # convert it to the meta call form with two arugments, that is context and enum Code
+                my $prev = $1;
+                my $next = $2;
+                my $method = $3;
+                my @args = split(/,/,$4);
+                my @types = @$dataGearVarType;
+                my $ntype;
+                for my $v (@$dataGearVar) {
+                    my $t = shift @types;
+                    if ($v eq $next) {
+                        $ntype = $t;
+                    }
+                }
+                print $fd "\tGearef(context, $ntype)->$next = $next->$next;\n";
+                # Put interface argument 
+                my $prot = $code->{$method};
+                for my $arg (@args) {
+                    my $p = shift @$prot;
+                    next if ($p eq $arg);
+                    print $fd "\tGearef(context, $ntype)->$p = $arg;\n";
+                }
+                print $fd "${prev}goto meta(context, $next->$next->$ntype.$method);\n";
+                next;
             } elsif (/^(.*)goto (\w+)\((.*)\);/) {
                 # handling goto statement  
                 # convert it to the meta call form with two arugments, that is context and enum Code
--- a/src/parallel_execution/test/stack_test.cbc	Wed Jun 07 15:17:36 2017 +0900
+++ b/src/parallel_execution/test/stack_test.cbc	Thu Jun 08 15:44:39 2017 +0900
@@ -5,46 +5,44 @@
     stack->stack = (union Data*)createSingleLinkedStack(context);
     Node* node = new Node();
     node->color = Red;
-    stack->data = (union Data*)node;
-    stack->next = C_assert1;
-    goto meta(context, stack->stack->Stack.push);
-}
-
-__code assert1(struct Stack* stack) {
-    SingleLinkedStack* singleLinkedStack = &stack->stack->Stack.stack->SingleLinkedStack;
-    assert(singleLinkedStack->top->data->Node.color == Red);
-    goto meta(context, C_stackTest2);
+    goto stack->push(node, stackTest2);
 }
 
 __code stackTest2(struct Stack* stack) {
     Node* node = new Node();
     node->color = Black;
-    stack->data = (union Data*)node;
-    stack->next = C_assert2;
-    goto meta(context, stack->stack->Stack.push);
+    goto stack->push(node, stackTest3);
 }
 
-__code assert2(struct Stack* stack) {
+__code stackTest2_stub(struct Context* context) {
     SingleLinkedStack* singleLinkedStack = &stack->stack->Stack.stack->SingleLinkedStack;
-    assert(singleLinkedStack->top->data->Node.color == Black);
-    goto meta(context, C_stackTest3);
+    assert(singleLinkedStack->top->data->Node.color == Red);
+    Stack* stack = Gearef(context, Stack);
+    goto stackTest2(context, stack);
 }
 
 __code stackTest3(struct Stack* stack) {
-    stack->next = C_assert3;
-    goto meta(context, stack->stack->Stack.pop);
+    goto stack->pop(assert3);
 }
 
-
-__code assert3(struct Stack* stack) {
+__code stackTest3_stub(struct Context* context) {
+    /*
+        assert on stack implementation
+    */
     SingleLinkedStack* singleLinkedStack = &stack->stack->Stack.stack->SingleLinkedStack;
-    assert(singleLinkedStack->top->data->Node.color == Red);
-    goto meta(context, C_exit_code);
+    assert(singleLinkedStack->top->data->Node.color == Black);
+    Stack* stack = Gearef(context, Stack);
+    goto stackTest3(context, stack);
+} 
+
+__code assert3(struct Node* node, struct Stack* stack) {
+    /*
+        assert in normal level
+    */
+    assert(node->color == Red);
+    goto exit_code(0);
 }
 
 int main(int argc, char const* argv[]) {
-    struct Context* main_context = NEW(struct Context);
-    initContext(main_context);
-    main_context->next = C_stackTest1;
-    goto start_code(main_context);
+    goto stackTest1();
 }