progs/compile_arr.scala
changeset 694 b6ed836ce59b
parent 616 24bbe4e4b37b
child 695 484b74bc057e
equal deleted inserted replaced
693:605d971e98fd 694:b6ed836ce59b
     1 // A Small Compiler for the WHILE Language
     1 // A Small Compiler for the WHILE Language
     2 // (stub for including arrays)
     2 //  - includes arrays and a small parser for
       
     3 //    translated BF programs
     3 
     4 
     4 // the abstract syntax trees
     5 // the abstract syntax trees
     5 abstract class Stmt
     6 abstract class Stmt
     6 abstract class AExp
     7 abstract class AExp
     7 abstract class BExp 
     8 abstract class BExp 
     8 type Block = List[Stmt]
     9 type Block = List[Stmt]
     9 
    10 
    10 // statements
    11 // statements
    11 case object Skip extends Stmt
    12 case object Skip extends Stmt
       
    13 case class Array(s: String, n: Int) extends Stmt
    12 case class If(a: BExp, bl1: Block, bl2: Block) extends Stmt
    14 case class If(a: BExp, bl1: Block, bl2: Block) extends Stmt
    13 case class While(b: BExp, bl: Block) extends Stmt
    15 case class While(b: BExp, bl: Block) extends Stmt
    14 case class Assign(s: String, a: AExp) extends Stmt
    16 case class Assign(s: String, a: AExp) extends Stmt
    15 case class AssignA(s: String, a1: AExp, a2: AExp) extends Stmt
    17 case class AssignA(s: String, a1: AExp, a2: AExp) extends Stmt
    16 case class Write(s: String) extends Stmt  // writes out a variable
    18 case class Write(s: String) extends Stmt
    17 case class Array(s: String, n: Int) extends Stmt 
    19 case class Read(s: String) extends Stmt
    18 
    20 
    19 // arithmetic expressions
    21 // arithmetic expressions
    20 case class Var(s: String) extends AExp
    22 case class Var(s: String) extends AExp
    21 case class Num(i: Int) extends AExp
    23 case class Num(i: Int) extends AExp
    22 case class Aop(o: String, a1: AExp, a2: AExp) extends AExp
    24 case class Aop(o: String, a1: AExp, a2: AExp) extends AExp
    23 case class Ref(s: String, a1: AExp) extends AExp
    25 case class Ref(s: String, a: AExp) extends AExp
    24 
    26 
    25 // boolean expressions
    27 // boolean expressions
    26 case object True extends BExp
    28 case object True extends BExp
    27 case object False extends BExp
    29 case object False extends BExp
    28 case class Bop(o: String, a1: AExp, a2: AExp) extends BExp
    30 case class Bop(o: String, a1: AExp, a2: AExp) extends BExp
    43 .method public static write(I)V 
    45 .method public static write(I)V 
    44     .limit locals 1 
    46     .limit locals 1 
    45     .limit stack 2 
    47     .limit stack 2 
    46     getstatic java/lang/System/out Ljava/io/PrintStream; 
    48     getstatic java/lang/System/out Ljava/io/PrintStream; 
    47     iload 0
    49     iload 0
    48     i2c
    50     i2c       ; Int => Char
    49     invokevirtual java/io/PrintStream/print(C)V 
    51     invokevirtual java/io/PrintStream/print(C)V   ; println(I)V => print(C)V    
    50     return 
    52     return 
       
    53 .end method
       
    54 
       
    55 .method public static read()I 
       
    56     .limit locals 10 
       
    57     .limit stack 10
       
    58 
       
    59     ldc 0 
       
    60     istore 1  ; this will hold our final integer 
       
    61 Label1: 
       
    62     getstatic java/lang/System/in Ljava/io/InputStream; 
       
    63     invokevirtual java/io/InputStream/read()I 
       
    64     istore 2 
       
    65     iload 2 
       
    66     ldc 10   ; the newline delimiter 
       
    67     isub 
       
    68     ifeq Label2 
       
    69     iload 2 
       
    70     ldc 32   ; the space delimiter 
       
    71     isub 
       
    72     ifeq Label2
       
    73 
       
    74     iload 2 
       
    75     ldc 48   ; we have our digit in ASCII, have to subtract it from 48 
       
    76     isub 
       
    77     ldc 10 
       
    78     iload 1 
       
    79     imul 
       
    80     iadd 
       
    81     istore 1 
       
    82     goto Label1 
       
    83 Label2: 
       
    84     ;when we come here we have our integer computed in local variable 1 
       
    85     iload 1 
       
    86     ireturn 
    51 .end method
    87 .end method
    52 
    88 
    53 .method public static main([Ljava/lang/String;)V
    89 .method public static main([Ljava/lang/String;)V
    54    .limit locals 200
    90    .limit locals 200
    55    .limit stack 200
    91    .limit stack 200
    61    return
    97    return
    62 
    98 
    63 .end method
    99 .end method
    64 """
   100 """
    65 
   101 
    66 println("Start compilation")
   102 
    67 
   103 
    68 
   104 
    69 // for generating new labels
   105 // for generating new labels
    70 var counter = -1
   106 var counter = -1
    71 
   107 
    73   counter += 1
   109   counter += 1
    74   x ++ "_" ++ counter.toString()
   110   x ++ "_" ++ counter.toString()
    75 }
   111 }
    76 
   112 
    77 // environments and instructions
   113 // environments and instructions
    78 type Env = Map[String, String]
   114 type Env = Map[String, Int]
    79 type Instrs = List[String]
   115 
       
   116 // convenient string interpolations 
       
   117 // for instructions and labels
       
   118 import scala.language.implicitConversions
       
   119 import scala.language.reflectiveCalls
       
   120 
       
   121 implicit def sring_inters(sc: StringContext) = new {
       
   122     def i(args: Any*): String = "   " ++ sc.s(args:_*) ++ "\n"
       
   123     def l(args: Any*): String = sc.s(args:_*) ++ ":\n"
       
   124 }
       
   125 
       
   126 def compile_op(op: String) = op match {
       
   127   case "+" => i"iadd"
       
   128   case "-" => i"isub"
       
   129   case "*" => i"imul"
       
   130 }
    80 
   131 
    81 // arithmetic expression compilation
   132 // arithmetic expression compilation
    82 def compile_aexp(a: AExp, env : Env) : Instrs = a match {
   133 def compile_aexp(a: AExp, env : Env) : String = a match {
    83   case Num(i) => List("ldc " + i.toString + "\n")
   134   case Num(i) => i"ldc $i"
    84   case Var(s) => List("iload " + env(s) + "\n")
   135   case Var(s) => i"iload ${env(s)} \t\t; $s"
    85   case Aop("+", a1, a2) => 
   136   case Aop(op, a1, a2) => 
    86     compile_aexp(a1, env) ++ 
   137     compile_aexp(a1, env) ++ compile_aexp(a2, env) ++ compile_op(op)
    87     compile_aexp(a2, env) ++ List("iadd\n")
   138   case Ref(s, a) =>
    88   case Aop("-", a1, a2) => 
   139     i"aload ${env(s)}" ++ compile_aexp(a, env) ++  i"iaload"
    89     compile_aexp(a1, env) ++ compile_aexp(a2, env) ++ List("isub\n")
       
    90   case Aop("*", a1, a2) => 
       
    91     compile_aexp(a1, env) ++ compile_aexp(a2, env) ++ List("imul\n")
       
    92   case Ref(s, a1) => 
       
    93     List("aload " + env(s) + "\n") ++ compile_aexp(a1, env) ++ List("iaload \n")
       
    94 }
   140 }
    95 
   141 
    96 // boolean expression compilation
   142 // boolean expression compilation
    97 def compile_bexp(b: BExp, env : Env, jmp: String) : Instrs = b match {
   143 def compile_bexp(b: BExp, env : Env, jmp: String) : String = b match {
    98   case True => Nil
   144     case True => ""
    99   case False => List("goto " + jmp + "\n")
   145   case False => i"goto $jmp"
   100   case Bop("=", a1, a2) => 
   146   case Bop("==", a1, a2) => 
   101     compile_aexp(a1, env) ++ compile_aexp(a2, env) ++ 
   147     compile_aexp(a1, env) ++ compile_aexp(a2, env) ++ i"if_icmpne $jmp"
   102     List("if_icmpne " + jmp + "\n")
       
   103   case Bop("!=", a1, a2) => 
   148   case Bop("!=", a1, a2) => 
   104     compile_aexp(a1, env) ++ compile_aexp(a2, env) ++ 
   149     compile_aexp(a1, env) ++ compile_aexp(a2, env) ++ i"if_icmpeq $jmp"
   105     List("if_icmpeq " + jmp + "\n")
       
   106   case Bop("<", a1, a2) => 
   150   case Bop("<", a1, a2) => 
   107     compile_aexp(a1, env) ++ compile_aexp(a2, env) ++ 
   151     compile_aexp(a1, env) ++ compile_aexp(a2, env) ++ i"if_icmpge $jmp"
   108     List("if_icmpge " + jmp + "\n")
       
   109 }
   152 }
   110 
   153 
   111 // statement compilation
   154 // statement compilation
   112 def compile_stmt(s: Stmt, env: Env) : (Instrs, Env) = s match {
   155 def compile_stmt(s: Stmt, env: Env) : (String, Env) = s match {
   113   case Skip => (Nil, env)
   156   case Skip => ("", env)
   114   case Assign(x, a) => {
   157   case Assign(x, a) => {
   115     val index = if (env.isDefinedAt(x)) env(x) else 
   158      val index = env.getOrElse(x, env.keys.size)
   116                     env.keys.size.toString
   159     (compile_aexp(a, env) ++ i"istore $index \t\t; $x", env + (x -> index)) 
   117     (compile_aexp(a, env) ++ 
       
   118      List("istore " + index + "\n"), env + (x -> index))
       
   119   } 
   160   } 
   120   case If(b, bl1, bl2) => {
   161   case If(b, bl1, bl2) => {
   121     val if_else = Fresh("If_else")
   162     val if_else = Fresh("If_else")
   122     val if_end = Fresh("If_end")
   163     val if_end = Fresh("If_end")
   123     val (instrs1, env1) = compile_block(bl1, env)
   164     val (instrs1, env1) = compile_block(bl1, env)
   124     val (instrs2, env2) = compile_block(bl2, env1)
   165     val (instrs2, env2) = compile_block(bl2, env1)
   125     (compile_bexp(b, env, if_else) ++
   166     (compile_bexp(b, env, if_else) ++
   126      instrs1 ++
   167      instrs1 ++
   127      List("goto " + if_end + "\n") ++
   168      i"goto $if_end" ++
   128      List("\n" + if_else + ":\n\n") ++
   169      l"$if_else" ++
   129      instrs2 ++
   170      instrs2 ++
   130      List("\n" + if_end + ":\n\n"), env2)
   171      l"$if_end", env2)
   131   }
   172   }
   132   case While(b, bl) => {
   173   case While(b, bl) => {
   133     val loop_begin = Fresh("Loop_begin")
   174     val loop_begin = Fresh("Loop_begin")
   134     val loop_end = Fresh("Loop_end")
   175     val loop_end = Fresh("Loop_end")
   135     val (instrs1, env1) = compile_block(bl, env)
   176     val (instrs1, env1) = compile_block(bl, env)
   136     (List("\n" + loop_begin + ":\n\n") ++
   177     (l"$loop_begin" ++
   137      compile_bexp(b, env, loop_end) ++
   178      compile_bexp(b, env, loop_end) ++
   138      instrs1 ++
   179      instrs1 ++
   139      List("goto " + loop_begin + "\n") ++
   180      i"goto $loop_begin" ++
   140      List("\n" + loop_end + ":\n\n"), env1)
   181      l"$loop_end", env1)
   141   }
   182   }
   142   case Write(x) => 
   183   case Write(x) => 
   143     (List("iload " + env(x) + "\n" + 
   184     (i"iload ${env(x)} \t\t; $x" ++ 
   144            "invokestatic XXX/XXX/write(I)V\n"), env)
   185      i"invokestatic XXX/XXX/write(I)V", env)
   145   case Array(s, n) => {
   186   case Read(x) => {
   146     val index = if (env.isDefinedAt(s)) throw new Exception("Array already defined") else 
   187     val index = env.getOrElse(x, env.keys.size) 
   147                     env.keys.size.toString
   188     (i"invokestatic XXX/XXX/read()I" ++ 
   148     (List("ldc " ++ n.toString ++ "\n",
   189      i"istore $index \t\t; $x", env + (x -> index))
   149           "newarray int \n",
   190   }
   150           "astore " ++ index ++ "\n"), env + (s -> index))
   191   case Array(s: String, n: Int) => {
   151   } 
   192     val index = if (env.isDefinedAt(s)) throw new Exception("array def error") else 
       
   193                     env.keys.size
       
   194     (i"ldc $n" ++
       
   195      i"newarray int" ++
       
   196      i"astore $index", env + (s -> index))
       
   197   }
   152   case AssignA(s, a1, a2) => {
   198   case AssignA(s, a1, a2) => {
   153     val index = if (env.isDefinedAt(s)) env(s) else 
   199     val index = if (env.isDefinedAt(s)) env(s) else 
   154                     throw new Exception("Array not yet defined")
   200                     throw new Exception("array not defined")
   155     (List("aload " + index + "\n") ++
   201     (i"aload ${env(s)}" ++
   156      compile_aexp(a1, env) ++
   202      compile_aexp(a1, env) ++
   157      compile_aexp(a2, env) ++
   203      compile_aexp(a2, env) ++
   158      List("iastore \n"), env)
   204      i"iastore", env)
   159   } 
   205   } 
   160 }
   206 }
   161 
   207 
   162 // compilation of a block (i.e. list of instructions)
   208 // compilation of a block (i.e. list of instructions)
   163 def compile_block(bl: Block, env: Env) : (Instrs, Env) = bl match {
   209 def compile_block(bl: Block, env: Env) : (String, Env) = bl match {
   164   case Nil => (Nil, env)
   210   case Nil => ("", env)
   165   case s::bl => {
   211   case s::bl => {
   166     val (instrs1, env1) = compile_stmt(s, env)
   212     val (instrs1, env1) = compile_stmt(s, env)
   167     val (instrs2, env2) = compile_block(bl, env1)
   213     val (instrs2, env2) = compile_block(bl, env1)
   168     (instrs1 ++ instrs2, env2)
   214     (instrs1 ++ instrs2, env2)
   169   }
   215   }
   170 }
   216 }
   171 
   217 
       
   218 
   172 // main compilation function for blocks
   219 // main compilation function for blocks
   173 def compile(bl: Block, class_name: String) : String = {
   220 def compile(bl: Block, class_name: String) : String = {
   174   val instructions = compile_block(bl, Map.empty)._1
   221   val instructions = compile_block(bl, Map.empty)._1
   175   (beginning ++ instructions.mkString ++ ending).replaceAllLiterally("XXX", class_name)
   222   (beginning ++ instructions.mkString ++ ending).replaceAllLiterally("XXX", class_name)
   176 }
   223 }
   177 
   224 
   178 
   225 
   179 // compiling and running files
       
   180 //
       
   181 // JVM files can be assembled with 
       
   182 //
       
   183 //    java -jar jvm/jasmin-2.4/jasmin.jar fib.j
       
   184 //
       
   185 // and started with
       
   186 //
       
   187 //    java fib/fib
       
   188 
       
   189 
       
   190 
       
   191 import scala.util._
       
   192 import scala.sys.process._
       
   193 import scala.io
       
   194 
       
   195 def compile_tofile(bl: Block, class_name: String) = {
       
   196   val output = compile(bl, class_name)
       
   197   val fw = new java.io.FileWriter(class_name + ".j") 
       
   198   fw.write(output) 
       
   199   fw.close()
       
   200 }
       
   201 
       
   202 def compile_all(bl: Block, class_name: String) : Unit = {
       
   203   compile_tofile(bl, class_name)
       
   204   println("compiled ")
       
   205   val test = ("java -jar jvm/jasmin-2.4/jasmin.jar " + class_name + ".j").!!
       
   206   println("assembled ")
       
   207 }
       
   208 
       
   209 def time_needed[T](i: Int, code: => T) = {
       
   210   val start = System.nanoTime()
       
   211   for (j <- 1 to i) code
       
   212   val end = System.nanoTime()
       
   213   (end - start)/(i * 1.0e9)
       
   214 }
       
   215 
       
   216 
       
   217 def compile_run(bl: Block, class_name: String) : Unit = {
       
   218   println("Start compilation")
       
   219   compile_all(bl, class_name)
       
   220   println("Time: " + time_needed(1, ("java " + class_name + "/" + class_name).!))
       
   221 }
       
   222 
       
   223 
       
   224 // Fibonacci numbers as a test-case
   226 // Fibonacci numbers as a test-case
   225 val fib_test = 
   227 val fib_test = 
   226   List(Assign("n", Num(10)),            //  n := 10;                     
   228   List(Read("n"),                       //  read n;                     
   227        Assign("minus1",Num(0)),         //  minus1 := 0;
   229        Assign("minus1",Num(0)),         //  minus1 := 0;
   228        Assign("minus2",Num(1)),         //  minus2 := 1;
   230        Assign("minus2",Num(1)),         //  minus2 := 1;
   229        Assign("temp",Num(0)),           //  temp := 0;
   231        Assign("temp",Num(0)),           //  temp := 0;
   230        While(Bop("<",Num(0),Var("n")),  //  while n > 0 do  {
   232        While(Bop("<",Num(0),Var("n")),  //  while n > 0 do  {
   231           List(Assign("temp",Var("minus2")),    //  temp := minus2;
   233           List(Assign("temp",Var("minus2")),    //  temp := minus2;
   233                                         //  minus2 := minus1 + minus2;
   235                                         //  minus2 := minus1 + minus2;
   234                Assign("minus1",Var("temp")), //  minus1 := temp;
   236                Assign("minus1",Var("temp")), //  minus1 := temp;
   235                Assign("n",Aop("-",Var("n"),Num(1))))), //  n := n - 1 };
   237                Assign("n",Aop("-",Var("n"),Num(1))))), //  n := n - 1 };
   236        Write("minus1"))                 //  write minus1
   238        Write("minus1"))                 //  write minus1
   237 
   239 
   238 
   240 // prints out the JVM-assembly program
   239 compile_run(fib_test, "fib")
   241 
       
   242 // println(compile(fib_test, "fib"))
       
   243 
       
   244 // can be assembled with 
       
   245 //
       
   246 //    java -jar jvm/jasmin-2.4/jasmin.jar fib.j
       
   247 //
       
   248 // and started with
       
   249 //
       
   250 //    java fib/fib
       
   251 
       
   252 import scala.util._
       
   253 import scala.sys.process._
       
   254 import scala.io
       
   255 
       
   256 def compile_tofile(bl: Block, class_name: String) = {
       
   257   val output = compile(bl, class_name)
       
   258   val fw = new java.io.FileWriter(class_name + ".j") 
       
   259   fw.write(output) 
       
   260   fw.close()
       
   261 }
       
   262 
       
   263 def compile_all(bl: Block, class_name: String) : Unit = {
       
   264   compile_tofile(bl, class_name)
       
   265   println("compiled ")
       
   266   val test = ("java -jar jvm/jasmin-2.4/jasmin.jar " + class_name + ".j").!!
       
   267   println("assembled ")
       
   268 }
       
   269 
       
   270 def time_needed[T](i: Int, code: => T) = {
       
   271   val start = System.nanoTime()
       
   272   for (j <- 1 to i) code
       
   273   val end = System.nanoTime()
       
   274   (end - start)/(i * 1.0e9)
       
   275 }
       
   276 
       
   277 
       
   278 def compile_run(bl: Block, class_name: String) : Unit = {
       
   279   println("Start compilation")
       
   280   compile_all(bl, class_name)
       
   281   println("Time: " + time_needed(1, ("java " + class_name + "/" + class_name).!))
       
   282 }
       
   283 
   240 
   284 
   241 
   285 
   242 val arr_test = 
   286 val arr_test = 
   243   List(Array("a", 10),                 // a[10]
   287   List(Array("a", 10),
   244        Array("b", 2),                  // b[2]
   288        Array("b", 2),
   245        AssignA("a", Num(0), Num(10)),  // a[0] := 10
   289        AssignA("a", Num(0), Num(10)),
   246        Assign("x", Ref("a", Num(0))),  // x := a[0]
   290        Assign("x", Ref("a", Num(0))),
   247        Write("x"),                     // write x
   291        Write("x"),
   248        AssignA("b", Num(1), Num(5)),   // b[1] := 5
   292        AssignA("b", Num(1), Num(5)),
   249        Assign("x", Ref("b", Num(1))),  // x := b[1]
   293        Assign("x", Ref("b", Num(1))),
   250        Write("x"))                     // write x
   294        Write("x"))       
   251 
   295 
   252 compile_run(arr_test, "a")
   296 
   253 
   297 //compile_run(arr_test, "a")
   254 
   298 
   255 //====================
   299 //====================
   256 // Parser Combinators
   300 // Parser Combinators
   257 //====================
   301 //====================
   258 
   302 
   259 import scala.language.implicitConversions
   303 import scala.language.implicitConversions
   260 import scala.language.reflectiveCalls
   304 import scala.language.reflectiveCalls
   261 
   305 
   262 
   306 type IsSeq[A] = A => Seq[_]
   263 abstract class Parser[I <% Seq[_], T] {
   307 
       
   308 abstract class Parser[I : IsSeq, T] {
   264   def parse(ts: I): Set[(T, I)]
   309   def parse(ts: I): Set[(T, I)]
   265 
   310 
   266   def parse_all(ts: I) : Set[T] =
   311   def parse_all(ts: I) : Set[T] =
   267     for ((head, tail) <- parse(ts); if (tail.isEmpty)) yield head
   312     for ((head, tail) <- parse(ts); if (tail.isEmpty)) yield head
   268 }
   313 }
   269 
   314 
   270 class SeqParser[I <% Seq[_], T, S](p: => Parser[I, T], q: => Parser[I, S]) extends Parser[I, (T, S)] {
   315 class SeqParser[I : IsSeq, T, S](p: => Parser[I, T], q: => Parser[I, S]) extends Parser[I, (T, S)] {
   271   def parse(sb: I) = 
   316   def parse(sb: I) = 
   272     for ((head1, tail1) <- p.parse(sb); 
   317     for ((head1, tail1) <- p.parse(sb); 
   273          (head2, tail2) <- q.parse(tail1)) yield ((head1, head2), tail2)
   318          (head2, tail2) <- q.parse(tail1)) yield ((head1, head2), tail2)
   274 }
   319 }
   275 
   320 
   276 class AltParser[I <% Seq[_], T](p: => Parser[I, T], q: => Parser[I, T]) extends Parser[I, T] {
   321 class AltParser[I : IsSeq, T](p: => Parser[I, T], q: => Parser[I, T]) extends Parser[I, T] {
   277   def parse(sb: I) = p.parse(sb) ++ q.parse(sb)   
   322   def parse(sb: I) = p.parse(sb) ++ q.parse(sb)   
   278 }
   323 }
   279 
   324 
   280 class FunParser[I <% Seq[_], T, S](p: => Parser[I, T], f: T => S) extends Parser[I, S] {
   325 class FunParser[I : IsSeq, T, S](p: => Parser[I, T], f: T => S) extends Parser[I, S] {
   281   def parse(sb: I) = 
   326   def parse(sb: I) = 
   282     for ((head, tail) <- p.parse(sb)) yield (f(head), tail)
   327     for ((head, tail) <- p.parse(sb)) yield (f(head), tail)
   283 }
   328 }
   284 
   329 
   285 
   330 
   294 def StringParser(s: String) = RegexParser(Regex.quote(s).r)
   339 def StringParser(s: String) = RegexParser(Regex.quote(s).r)
   295 
   340 
   296 
   341 
   297 implicit def string2parser(s : String) = StringParser(s)
   342 implicit def string2parser(s : String) = StringParser(s)
   298 
   343 
   299 implicit def ParserOps[I<% Seq[_], T](p: Parser[I, T]) = new {
   344 implicit def ParserOps[I : IsSeq, T](p: Parser[I, T]) = new {
   300   def | (q : => Parser[I, T]) = new AltParser[I, T](p, q)
   345   def | (q : => Parser[I, T]) = new AltParser[I, T](p, q)
   301   def ==>[S] (f: => T => S) = new FunParser[I, T, S](p, f)
   346   def ==>[S] (f: => T => S) = new FunParser[I, T, S](p, f)
   302   def ~[S] (q : => Parser[I, S]) = new SeqParser[I, T, S](p, q)
   347   def ~[S] (q : => Parser[I, S]) = new SeqParser[I, T, S](p, q)
   303 }
   348 }
   304 
   349 
   359 
   404 
   360 lazy val Block: Parser[String, Block] =
   405 lazy val Block: Parser[String, Block] =
   361    ("{" ~ Stmts ~ "}") ==> { case ((x, y), z) => y} | 
   406    ("{" ~ Stmts ~ "}") ==> { case ((x, y), z) => y} | 
   362    (Stmt ==> (s => List(s)))
   407    (Stmt ==> (s => List(s)))
   363 
   408 
   364 Stmts.parse_all("x2:=5+a")
   409 //Stmts.parse_all("x2:=5+a")
   365 Stmts.parse_all("x2:=5+a[3+a]")
   410 //Stmts.parse_all("x2:=5+a[3+a]")
   366 Stmts.parse_all("a[x2+3]:=5+a[3+a]")
   411 //Stmts.parse_all("a[x2+3]:=5+a[3+a]")
   367 Block.parse_all("{x:=5;y:=8}")
   412 //Block.parse_all("{x:=5;y:=8}")
   368 Block.parse_all("if(false)then{x:=5}else{x:=10}")
   413 //Block.parse_all("if(false)then{x:=5}else{x:=10}")
   369 
   414 
   370 
   415 
   371 
   416 
   372 val fib = """
   417 val fib = """
   373    n := 10;
   418    n := 10;
   434 
   479 
   435 def bf_str(prog: String) : String = {
   480 def bf_str(prog: String) : String = {
   436   "\n" ++
   481   "\n" ++
   437   //"new field[30000];\n" ++
   482   //"new field[30000];\n" ++
   438   "ptr := 15000;" ++
   483   "ptr := 15000;" ++
   439   instrs2(prog) ++
   484   instrs(prog) ++
   440   "skip"
   485   "skip"
   441 }
   486 }
   442 
   487 
   443 def bf_run(prog: String, name: String) = {
   488 def bf_run(prog: String, name: String) = {
   444   println("BF processing start")
   489   println("BF processing start")
   445   val bf_string = bf_str(prog).replaceAll("\\s", "")
   490   val bf_string = bf_str(prog).replaceAll("\\s", "")
       
   491   
   446   println(s"BF parsing start (string length ${bf_string.length})")
   492   println(s"BF parsing start (string length ${bf_string.length})")
   447   val bf_prog = Stmts.parse_all(bf_string).toList.head
   493   val bf_prog = Stmts.parse_all(bf_string).toList.head
   448   println("BF Compile start")
   494   println(s"BF Compile start ${bf_string.toList.length} characters")
   449   compile_run(Array("field", 30000) :: bf_prog, name)
   495   compile_run(Array("field", 30000) :: bf_prog, name)
   450 }
   496 }
       
   497 
       
   498 // a benchmark program (counts down from 'Z' to 'A')
       
   499 val bf0 = """>++[<+++++++++++++>-]<[[>+>+<<-]>[<+>-]++++++++
       
   500             [>++++++++<-]>.[-]<<>++++++++++[>++++++++++[>++
       
   501             ++++++++[>++++++++++[>++++++++++[>++++++++++[>+
       
   502             +++++++++[-]<-]<-]<-]<-]<-]<-]<-]++++++++++."""
       
   503 
       
   504 bf_run(bf0, "bench")
   451 
   505 
   452 
   506 
   453 
   507 
   454 val bf1 = """++++++++[>+>++++<<-]>++>>+<[-[>>+<<-]+>>]>+[-<<<[
   508 val bf1 = """++++++++[>+>++++<<-]>++>>+<[-[>>+<<-]+>>]>+[-<<<[
   455       ->[+[-]+>++>>>-<<]<[<]>>++++++[<<+++++>>-]+<<++.[-]<<
   509       ->[+[-]+>++>>>-<<]<[<]>>++++++[<<+++++>>-]+<<++.[-]<<
   458 bf_run(bf1, "sier")
   512 bf_run(bf1, "sier")
   459 
   513 
   460 bf_run("""++++++++[>++++[>++>+++>+++>+<<<<-]>+>+>->>+[<]<-]>>.>---.+++++++
   514 bf_run("""++++++++[>++++[>++>+++>+++>+<<<<-]>+>+>->>+[<]<-]>>.>---.+++++++
   461        ..+++.>>.<-.<.+++.------.--------.>>+.>++.""", "hello")
   515        ..+++.>>.<-.<.+++.------.--------.>>+.>++.""", "hello")
   462 
   516 
   463 bf_run("""+++++++++++
   517 
       
   518 val bf2 = """+++++++++++
   464       >+>>>>++++++++++++++++++++++++++++++++++++++++++++
   519       >+>>>>++++++++++++++++++++++++++++++++++++++++++++
   465       >++++++++++++++++++++++++++++++++<<<<<<[>[>>>>>>+>
   520       >++++++++++++++++++++++++++++++++<<<<<<[>[>>>>>>+>
   466       +<<<<<<<-]>>>>>>>[<<<<<<<+>>>>>>>-]<[>++++++++++[-
   521       +<<<<<<<-]>>>>>>>[<<<<<<<+>>>>>>>-]<[>++++++++++[-
   467       <-[>>+>+<<<-]>>>[<<<+>>>-]+<[>[-]<[-]]>[<<[>>>+<<<
   522       <-[>>+>+<<<-]>>>[<<<+>>>-]+<[>[-]<[-]]>[<<[>>>+<<<
   468       -]>>[-]]<<]>>>[>>+>+<<<-]>>>[<<<+>>>-]+<[>[-]<[-]]
   523       -]>>[-]]<<]>>>[>>+>+<<<-]>>>[<<<+>>>-]+<[>[-]<[-]]
   469       >[<<+>>[-]]<<<<<<<]>>>>>[+++++++++++++++++++++++++
   524       >[<<+>>[-]]<<<<<<<]>>>>>[+++++++++++++++++++++++++
   470       +++++++++++++++++++++++.[-]]++++++++++<[->-<]>++++
   525       +++++++++++++++++++++++.[-]]++++++++++<[->-<]>++++
   471       ++++++++++++++++++++++++++++++++++++++++++++.[-]<<
   526       ++++++++++++++++++++++++++++++++++++++++++++.[-]<<
   472       <<<<<<<<<<[>>>+>+<<<<-]>>>>[<<<<+>>>>-]<-[>>.>.<<<
   527       <<<<<<<<<<[>>>+>+<<<<-]>>>>[<<<<+>>>>-]<-[>>.>.<<<
   473       [-]]<<[>>+>+<<<-]>>>[<<<+>>>-]<<[<+>-]>[<+>-]<<<-]""", "fibs")
   528       [-]]<<[>>+>+<<<-]>>>[<<<+>>>-]<<[<+>-]>[<+>-]<<<-]"""
       
   529 
       
   530 bf_run(bf2, "fibs")
       
   531 
       
   532 
       
   533 bf_run("""      A mandelbrot set fractal viewer in brainf*** written by Erik Bosman
       
   534 +++++++++++++[->++>>>+++++>++>+<<<<<<]>>>>>++++++>--->>>>>>>>>>+++++++++++++++[[
       
   535 >>>>>>>>>]+[<<<<<<<<<]>>>>>>>>>-]+[>>>>>>>>[-]>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>[-]+
       
   536 <<<<<<<+++++[-[->>>>>>>>>+<<<<<<<<<]>>>>>>>>>]>>>>>>>+>>>>>>>>>>>>>>>>>>>>>>>>>>
       
   537 >+<<<<<<<<<<<<<<<<<[<<<<<<<<<]>>>[-]+[>>>>>>[>>>>>>>[-]>>]<<<<<<<<<[<<<<<<<<<]>>
       
   538 >>>>>[-]+<<<<<<++++[-[->>>>>>>>>+<<<<<<<<<]>>>>>>>>>]>>>>>>+<<<<<<+++++++[-[->>>
       
   539 >>>>>>+<<<<<<<<<]>>>>>>>>>]>>>>>>+<<<<<<<<<<<<<<<<[<<<<<<<<<]>>>[[-]>>>>>>[>>>>>
       
   540 >>[-<<<<<<+>>>>>>]<<<<<<[->>>>>>+<<+<<<+<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>
       
   541 [>>>>>>>>[-<<<<<<<+>>>>>>>]<<<<<<<[->>>>>>>+<<+<<<+<<]>>>>>>>>]<<<<<<<<<[<<<<<<<
       
   542 <<]>>>>>>>[-<<<<<<<+>>>>>>>]<<<<<<<[->>>>>>>+<<+<<<<<]>>>>>>>>>+++++++++++++++[[
       
   543 >>>>>>>>>]+>[-]>[-]>[-]>[-]>[-]>[-]>[-]>[-]>[-]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>-]+[
       
   544 >+>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>->>>>[-<<<<+>>>>]<<<<[->>>>+<<<<<[->>[
       
   545 -<<+>>]<<[->>+>>+<<<<]+>>>>>>>>>]<<<<<<<<[<<<<<<<<<]]>>>>>>>>>[>>>>>>>>>]<<<<<<<
       
   546 <<[>[->>>>>>>>>+<<<<<<<<<]<<<<<<<<<<]>[->>>>>>>>>+<<<<<<<<<]<+>>>>>>>>]<<<<<<<<<
       
   547 [>[-]<->>>>[-<<<<+>[<->-<<<<<<+>>>>>>]<[->+<]>>>>]<<<[->>>+<<<]<+<<<<<<<<<]>>>>>
       
   548 >>>>[>+>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>->>>>>[-<<<<<+>>>>>]<<<<<[->>>>>+
       
   549 <<<<<<[->>>[-<<<+>>>]<<<[->>>+>+<<<<]+>>>>>>>>>]<<<<<<<<[<<<<<<<<<]]>>>>>>>>>[>>
       
   550 >>>>>>>]<<<<<<<<<[>>[->>>>>>>>>+<<<<<<<<<]<<<<<<<<<<<]>>[->>>>>>>>>+<<<<<<<<<]<<
       
   551 +>>>>>>>>]<<<<<<<<<[>[-]<->>>>[-<<<<+>[<->-<<<<<<+>>>>>>]<[->+<]>>>>]<<<[->>>+<<
       
   552 <]<+<<<<<<<<<]>>>>>>>>>[>>>>[-<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<+>>>>>>>>>>>>>
       
   553 >>>>>>>>>>>>>>>>>>>>>>>]>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>+++++++++++++++[[>>>>
       
   554 >>>>>]<<<<<<<<<-<<<<<<<<<[<<<<<<<<<]>>>>>>>>>-]+>>>>>>>>>>>>>>>>>>>>>+<<<[<<<<<<
       
   555 <<<]>>>>>>>>>[>>>[-<<<->>>]+<<<[->>>->[-<<<<+>>>>]<<<<[->>>>+<<<<<<<<<<<<<[<<<<<
       
   556 <<<<]>>>>[-]+>>>>>[>>>>>>>>>]>+<]]+>>>>[-<<<<->>>>]+<<<<[->>>>-<[-<<<+>>>]<<<[->
       
   557 >>+<<<<<<<<<<<<[<<<<<<<<<]>>>[-]+>>>>>>[>>>>>>>>>]>[-]+<]]+>[-<[>>>>>>>>>]<<<<<<
       
   558 <<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]<<<<<<<[->+>>>-<<<<]>>>>>>>>>+++++++++++++++++++
       
   559 +++++++>>[-<<<<+>>>>]<<<<[->>>>+<<[-]<<]>>[<<<<<<<+<[-<+>>>>+<<[-]]>[-<<[->+>>>-
       
   560 <<<<]>>>]>>>>>>>>>>>>>[>>[-]>[-]>[-]>>>>>]<<<<<<<<<[<<<<<<<<<]>>>[-]>>>>>>[>>>>>
       
   561 [-<<<<+>>>>]<<<<[->>>>+<<<+<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>>[-<<<<<<<<
       
   562 <+>>>>>>>>>]>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>+++++++++++++++[[>>>>>>>>>]+>[-
       
   563 ]>[-]>[-]>[-]>[-]>[-]>[-]>[-]>[-]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>-]+[>+>>>>>>>>]<<<
       
   564 <<<<<<[<<<<<<<<<]>>>>>>>>>[>->>>>>[-<<<<<+>>>>>]<<<<<[->>>>>+<<<<<<[->>[-<<+>>]<
       
   565 <[->>+>+<<<]+>>>>>>>>>]<<<<<<<<[<<<<<<<<<]]>>>>>>>>>[>>>>>>>>>]<<<<<<<<<[>[->>>>
       
   566 >>>>>+<<<<<<<<<]<<<<<<<<<<]>[->>>>>>>>>+<<<<<<<<<]<+>>>>>>>>]<<<<<<<<<[>[-]<->>>
       
   567 [-<<<+>[<->-<<<<<<<+>>>>>>>]<[->+<]>>>]<<[->>+<<]<+<<<<<<<<<]>>>>>>>>>[>>>>>>[-<
       
   568 <<<<+>>>>>]<<<<<[->>>>>+<<<<+<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>+>>>>>>>>
       
   569 ]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>->>>>>[-<<<<<+>>>>>]<<<<<[->>>>>+<<<<<<[->>[-<<+
       
   570 >>]<<[->>+>>+<<<<]+>>>>>>>>>]<<<<<<<<[<<<<<<<<<]]>>>>>>>>>[>>>>>>>>>]<<<<<<<<<[>
       
   571 [->>>>>>>>>+<<<<<<<<<]<<<<<<<<<<]>[->>>>>>>>>+<<<<<<<<<]<+>>>>>>>>]<<<<<<<<<[>[-
       
   572 ]<->>>>[-<<<<+>[<->-<<<<<<+>>>>>>]<[->+<]>>>>]<<<[->>>+<<<]<+<<<<<<<<<]>>>>>>>>>
       
   573 [>>>>[-<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<+>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
       
   574 ]>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>>>[-<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<+>
       
   575 >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>]>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>++++++++
       
   576 +++++++[[>>>>>>>>>]<<<<<<<<<-<<<<<<<<<[<<<<<<<<<]>>>>>>>>>-]+[>>>>>>>>[-<<<<<<<+
       
   577 >>>>>>>]<<<<<<<[->>>>>>>+<<<<<<+<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>>>>>>[
       
   578 -]>>>]<<<<<<<<<[<<<<<<<<<]>>>>+>[-<-<<<<+>>>>>]>[-<<<<<<[->>>>>+<++<<<<]>>>>>[-<
       
   579 <<<<+>>>>>]<->+>]<[->+<]<<<<<[->>>>>+<<<<<]>>>>>>[-]<<<<<<+>>>>[-<<<<->>>>]+<<<<
       
   580 [->>>>->>>>>[>>[-<<->>]+<<[->>->[-<<<+>>>]<<<[->>>+<<<<<<<<<<<<[<<<<<<<<<]>>>[-]
       
   581 +>>>>>>[>>>>>>>>>]>+<]]+>>>[-<<<->>>]+<<<[->>>-<[-<<+>>]<<[->>+<<<<<<<<<<<[<<<<<
       
   582 <<<<]>>>>[-]+>>>>>[>>>>>>>>>]>[-]+<]]+>[-<[>>>>>>>>>]<<<<<<<<]>>>>>>>>]<<<<<<<<<
       
   583 [<<<<<<<<<]>>>>[-<<<<+>>>>]<<<<[->>>>+>>>>>[>+>>[-<<->>]<<[->>+<<]>>>>>>>>]<<<<<
       
   584 <<<+<[>[->>>>>+<<<<[->>>>-<<<<<<<<<<<<<<+>>>>>>>>>>>[->>>+<<<]<]>[->>>-<<<<<<<<<
       
   585 <<<<<+>>>>>>>>>>>]<<]>[->>>>+<<<[->>>-<<<<<<<<<<<<<<+>>>>>>>>>>>]<]>[->>>+<<<]<<
       
   586 <<<<<<<<<<]>>>>[-]<<<<]>>>[-<<<+>>>]<<<[->>>+>>>>>>[>+>[-<->]<[->+<]>>>>>>>>]<<<
       
   587 <<<<<+<[>[->>>>>+<<<[->>>-<<<<<<<<<<<<<<+>>>>>>>>>>[->>>>+<<<<]>]<[->>>>-<<<<<<<
       
   588 <<<<<<<+>>>>>>>>>>]<]>>[->>>+<<<<[->>>>-<<<<<<<<<<<<<<+>>>>>>>>>>]>]<[->>>>+<<<<
       
   589 ]<<<<<<<<<<<]>>>>>>+<<<<<<]]>>>>[-<<<<+>>>>]<<<<[->>>>+>>>>>[>>>>>>>>>]<<<<<<<<<
       
   590 [>[->>>>>+<<<<[->>>>-<<<<<<<<<<<<<<+>>>>>>>>>>>[->>>+<<<]<]>[->>>-<<<<<<<<<<<<<<
       
   591 +>>>>>>>>>>>]<<]>[->>>>+<<<[->>>-<<<<<<<<<<<<<<+>>>>>>>>>>>]<]>[->>>+<<<]<<<<<<<
       
   592 <<<<<]]>[-]>>[-]>[-]>>>>>[>>[-]>[-]>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>>>>>[-<
       
   593 <<<+>>>>]<<<<[->>>>+<<<+<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>+++++++++++++++[
       
   594 [>>>>>>>>>]+>[-]>[-]>[-]>[-]>[-]>[-]>[-]>[-]>[-]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>-]+
       
   595 [>+>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>->>>>[-<<<<+>>>>]<<<<[->>>>+<<<<<[->>
       
   596 [-<<+>>]<<[->>+>+<<<]+>>>>>>>>>]<<<<<<<<[<<<<<<<<<]]>>>>>>>>>[>>>>>>>>>]<<<<<<<<
       
   597 <[>[->>>>>>>>>+<<<<<<<<<]<<<<<<<<<<]>[->>>>>>>>>+<<<<<<<<<]<+>>>>>>>>]<<<<<<<<<[
       
   598 >[-]<->>>[-<<<+>[<->-<<<<<<<+>>>>>>>]<[->+<]>>>]<<[->>+<<]<+<<<<<<<<<]>>>>>>>>>[
       
   599 >>>[-<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<+>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>]>
       
   600 >>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>[-]>>>>+++++++++++++++[[>>>>>>>>>]<<<<<<<<<-<<<<<
       
   601 <<<<[<<<<<<<<<]>>>>>>>>>-]+[>>>[-<<<->>>]+<<<[->>>->[-<<<<+>>>>]<<<<[->>>>+<<<<<
       
   602 <<<<<<<<[<<<<<<<<<]>>>>[-]+>>>>>[>>>>>>>>>]>+<]]+>>>>[-<<<<->>>>]+<<<<[->>>>-<[-
       
   603 <<<+>>>]<<<[->>>+<<<<<<<<<<<<[<<<<<<<<<]>>>[-]+>>>>>>[>>>>>>>>>]>[-]+<]]+>[-<[>>
       
   604 >>>>>>>]<<<<<<<<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>[-<<<+>>>]<<<[->>>+>>>>>>[>+>>>
       
   605 [-<<<->>>]<<<[->>>+<<<]>>>>>>>>]<<<<<<<<+<[>[->+>[-<-<<<<<<<<<<+>>>>>>>>>>>>[-<<
       
   606 +>>]<]>[-<<-<<<<<<<<<<+>>>>>>>>>>>>]<<<]>>[-<+>>[-<<-<<<<<<<<<<+>>>>>>>>>>>>]<]>
       
   607 [-<<+>>]<<<<<<<<<<<<<]]>>>>[-<<<<+>>>>]<<<<[->>>>+>>>>>[>+>>[-<<->>]<<[->>+<<]>>
       
   608 >>>>>>]<<<<<<<<+<[>[->+>>[-<<-<<<<<<<<<<+>>>>>>>>>>>[-<+>]>]<[-<-<<<<<<<<<<+>>>>
       
   609 >>>>>>>]<<]>>>[-<<+>[-<-<<<<<<<<<<+>>>>>>>>>>>]>]<[-<+>]<<<<<<<<<<<<]>>>>>+<<<<<
       
   610 ]>>>>>>>>>[>>>[-]>[-]>[-]>>>>]<<<<<<<<<[<<<<<<<<<]>>>[-]>[-]>>>>>[>>>>>>>[-<<<<<
       
   611 <+>>>>>>]<<<<<<[->>>>>>+<<<<+<<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>+>[-<-<<<<+>>>>
       
   612 >]>>[-<<<<<<<[->>>>>+<++<<<<]>>>>>[-<<<<<+>>>>>]<->+>>]<<[->>+<<]<<<<<[->>>>>+<<
       
   613 <<<]+>>>>[-<<<<->>>>]+<<<<[->>>>->>>>>[>>>[-<<<->>>]+<<<[->>>-<[-<<+>>]<<[->>+<<
       
   614 <<<<<<<<<[<<<<<<<<<]>>>>[-]+>>>>>[>>>>>>>>>]>+<]]+>>[-<<->>]+<<[->>->[-<<<+>>>]<
       
   615 <<[->>>+<<<<<<<<<<<<[<<<<<<<<<]>>>[-]+>>>>>>[>>>>>>>>>]>[-]+<]]+>[-<[>>>>>>>>>]<
       
   616 <<<<<<<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>[-<<<+>>>]<<<[->>>+>>>>>>[>+>[-<->]<[->+
       
   617 <]>>>>>>>>]<<<<<<<<+<[>[->>>>+<<[->>-<<<<<<<<<<<<<+>>>>>>>>>>[->>>+<<<]>]<[->>>-
       
   618 <<<<<<<<<<<<<+>>>>>>>>>>]<]>>[->>+<<<[->>>-<<<<<<<<<<<<<+>>>>>>>>>>]>]<[->>>+<<<
       
   619 ]<<<<<<<<<<<]>>>>>[-]>>[-<<<<<<<+>>>>>>>]<<<<<<<[->>>>>>>+<<+<<<<<]]>>>>[-<<<<+>
       
   620 >>>]<<<<[->>>>+>>>>>[>+>>[-<<->>]<<[->>+<<]>>>>>>>>]<<<<<<<<+<[>[->>>>+<<<[->>>-
       
   621 <<<<<<<<<<<<<+>>>>>>>>>>>[->>+<<]<]>[->>-<<<<<<<<<<<<<+>>>>>>>>>>>]<<]>[->>>+<<[
       
   622 ->>-<<<<<<<<<<<<<+>>>>>>>>>>>]<]>[->>+<<]<<<<<<<<<<<<]]>>>>[-]<<<<]>>>>[-<<<<+>>
       
   623 >>]<<<<[->>>>+>[-]>>[-<<<<<<<+>>>>>>>]<<<<<<<[->>>>>>>+<<+<<<<<]>>>>>>>>>[>>>>>>
       
   624 >>>]<<<<<<<<<[>[->>>>+<<<[->>>-<<<<<<<<<<<<<+>>>>>>>>>>>[->>+<<]<]>[->>-<<<<<<<<
       
   625 <<<<<+>>>>>>>>>>>]<<]>[->>>+<<[->>-<<<<<<<<<<<<<+>>>>>>>>>>>]<]>[->>+<<]<<<<<<<<
       
   626 <<<<]]>>>>>>>>>[>>[-]>[-]>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>[-]>[-]>>>>>[>>>>>[-<<<<+
       
   627 >>>>]<<<<[->>>>+<<<+<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>>>>>>[-<<<<<+>>>>>
       
   628 ]<<<<<[->>>>>+<<<+<<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>+++++++++++++++[[>>>>
       
   629 >>>>>]+>[-]>[-]>[-]>[-]>[-]>[-]>[-]>[-]>[-]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>-]+[>+>>
       
   630 >>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>->>>>[-<<<<+>>>>]<<<<[->>>>+<<<<<[->>[-<<+
       
   631 >>]<<[->>+>>+<<<<]+>>>>>>>>>]<<<<<<<<[<<<<<<<<<]]>>>>>>>>>[>>>>>>>>>]<<<<<<<<<[>
       
   632 [->>>>>>>>>+<<<<<<<<<]<<<<<<<<<<]>[->>>>>>>>>+<<<<<<<<<]<+>>>>>>>>]<<<<<<<<<[>[-
       
   633 ]<->>>>[-<<<<+>[<->-<<<<<<+>>>>>>]<[->+<]>>>>]<<<[->>>+<<<]<+<<<<<<<<<]>>>>>>>>>
       
   634 [>+>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>->>>>>[-<<<<<+>>>>>]<<<<<[->>>>>+<<<<
       
   635 <<[->>>[-<<<+>>>]<<<[->>>+>+<<<<]+>>>>>>>>>]<<<<<<<<[<<<<<<<<<]]>>>>>>>>>[>>>>>>
       
   636 >>>]<<<<<<<<<[>>[->>>>>>>>>+<<<<<<<<<]<<<<<<<<<<<]>>[->>>>>>>>>+<<<<<<<<<]<<+>>>
       
   637 >>>>>]<<<<<<<<<[>[-]<->>>>[-<<<<+>[<->-<<<<<<+>>>>>>]<[->+<]>>>>]<<<[->>>+<<<]<+
       
   638 <<<<<<<<<]>>>>>>>>>[>>>>[-<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<+>>>>>>>>>>>>>>>>>
       
   639 >>>>>>>>>>>>>>>>>>>]>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>+++++++++++++++[[>>>>>>>>
       
   640 >]<<<<<<<<<-<<<<<<<<<[<<<<<<<<<]>>>>>>>>>-]+>>>>>>>>>>>>>>>>>>>>>+<<<[<<<<<<<<<]
       
   641 >>>>>>>>>[>>>[-<<<->>>]+<<<[->>>->[-<<<<+>>>>]<<<<[->>>>+<<<<<<<<<<<<<[<<<<<<<<<
       
   642 ]>>>>[-]+>>>>>[>>>>>>>>>]>+<]]+>>>>[-<<<<->>>>]+<<<<[->>>>-<[-<<<+>>>]<<<[->>>+<
       
   643 <<<<<<<<<<<[<<<<<<<<<]>>>[-]+>>>>>>[>>>>>>>>>]>[-]+<]]+>[-<[>>>>>>>>>]<<<<<<<<]>
       
   644 >>>>>>>]<<<<<<<<<[<<<<<<<<<]>>->>[-<<<<+>>>>]<<<<[->>>>+<<[-]<<]>>]<<+>>>>[-<<<<
       
   645 ->>>>]+<<<<[->>>>-<<<<<<.>>]>>>>[-<<<<<<<.>>>>>>>]<<<[-]>[-]>[-]>[-]>[-]>[-]>>>[
       
   646 >[-]>[-]>[-]>[-]>[-]>[-]>>>]<<<<<<<<<[<<<<<<<<<]>>>>>>>>>[>>>>>[-]>>>>]<<<<<<<<<
       
   647 [<<<<<<<<<]>+++++++++++[-[->>>>>>>>>+<<<<<<<<<]>>>>>>>>>]>>>>+>>>>>>>>>+<<<<<<<<
       
   648 <<<<<<[<<<<<<<<<]>>>>>>>[-<<<<<<<+>>>>>>>]<<<<<<<[->>>>>>>+[-]>>[>>>>>>>>>]<<<<<
       
   649 <<<<[>>>>>>>[-<<<<<<+>>>>>>]<<<<<<[->>>>>>+<<<<<<<[<<<<<<<<<]>>>>>>>[-]+>>>]<<<<
       
   650 <<<<<<]]>>>>>>>[-<<<<<<<+>>>>>>>]<<<<<<<[->>>>>>>+>>[>+>>>>[-<<<<->>>>]<<<<[->>>
       
   651 >+<<<<]>>>>>>>>]<<+<<<<<<<[>>>>>[->>+<<]<<<<<<<<<<<<<<]>>>>>>>>>[>>>>>>>>>]<<<<<
       
   652 <<<<[>[-]<->>>>>>>[-<<<<<<<+>[<->-<<<+>>>]<[->+<]>>>>>>>]<<<<<<[->>>>>>+<<<<<<]<
       
   653 +<<<<<<<<<]>>>>>>>-<<<<[-]+<<<]+>>>>>>>[-<<<<<<<->>>>>>>]+<<<<<<<[->>>>>>>->>[>>
       
   654 >>>[->>+<<]>>>>]<<<<<<<<<[>[-]<->>>>>>>[-<<<<<<<+>[<->-<<<+>>>]<[->+<]>>>>>>>]<<
       
   655 <<<<[->>>>>>+<<<<<<]<+<<<<<<<<<]>+++++[-[->>>>>>>>>+<<<<<<<<<]>>>>>>>>>]>>>>+<<<
       
   656 <<[<<<<<<<<<]>>>>>>>>>[>>>>>[-<<<<<->>>>>]+<<<<<[->>>>>->>[-<<<<<<<+>>>>>>>]<<<<
       
   657 <<<[->>>>>>>+<<<<<<<<<<<<<<<<[<<<<<<<<<]>>>>[-]+>>>>>[>>>>>>>>>]>+<]]+>>>>>>>[-<
       
   658 <<<<<<->>>>>>>]+<<<<<<<[->>>>>>>-<<[-<<<<<+>>>>>]<<<<<[->>>>>+<<<<<<<<<<<<<<[<<<
       
   659 <<<<<<]>>>[-]+>>>>>>[>>>>>>>>>]>[-]+<]]+>[-<[>>>>>>>>>]<<<<<<<<]>>>>>>>>]<<<<<<<
       
   660 <<[<<<<<<<<<]>>>>[-]<<<+++++[-[->>>>>>>>>+<<<<<<<<<]>>>>>>>>>]>>>>-<<<<<[<<<<<<<
       
   661 <<]]>>>]<<<<.>>>>>>>>>>[>>>>>>[-]>>>]<<<<<<<<<[<<<<<<<<<]>++++++++++[-[->>>>>>>>
       
   662 >+<<<<<<<<<]>>>>>>>>>]>>>>>+>>>>>>>>>+<<<<<<<<<<<<<<<[<<<<<<<<<]>>>>>>>>[-<<<<<<
       
   663 <<+>>>>>>>>]<<<<<<<<[->>>>>>>>+[-]>[>>>>>>>>>]<<<<<<<<<[>>>>>>>>[-<<<<<<<+>>>>>>
       
   664 >]<<<<<<<[->>>>>>>+<<<<<<<<[<<<<<<<<<]>>>>>>>>[-]+>>]<<<<<<<<<<]]>>>>>>>>[-<<<<<
       
   665 <<<+>>>>>>>>]<<<<<<<<[->>>>>>>>+>[>+>>>>>[-<<<<<->>>>>]<<<<<[->>>>>+<<<<<]>>>>>>
       
   666 >>]<+<<<<<<<<[>>>>>>[->>+<<]<<<<<<<<<<<<<<<]>>>>>>>>>[>>>>>>>>>]<<<<<<<<<[>[-]<-
       
   667 >>>>>>>>[-<<<<<<<<+>[<->-<<+>>]<[->+<]>>>>>>>>]<<<<<<<[->>>>>>>+<<<<<<<]<+<<<<<<
       
   668 <<<]>>>>>>>>-<<<<<[-]+<<<]+>>>>>>>>[-<<<<<<<<->>>>>>>>]+<<<<<<<<[->>>>>>>>->[>>>
       
   669 >>>[->>+<<]>>>]<<<<<<<<<[>[-]<->>>>>>>>[-<<<<<<<<+>[<->-<<+>>]<[->+<]>>>>>>>>]<<
       
   670 <<<<<[->>>>>>>+<<<<<<<]<+<<<<<<<<<]>+++++[-[->>>>>>>>>+<<<<<<<<<]>>>>>>>>>]>>>>>
       
   671 +>>>>>>>>>>>>>>>>>>>>>>>>>>>+<<<<<<[<<<<<<<<<]>>>>>>>>>[>>>>>>[-<<<<<<->>>>>>]+<
       
   672 <<<<<[->>>>>>->>[-<<<<<<<<+>>>>>>>>]<<<<<<<<[->>>>>>>>+<<<<<<<<<<<<<<<<<[<<<<<<<
       
   673 <<]>>>>[-]+>>>>>[>>>>>>>>>]>+<]]+>>>>>>>>[-<<<<<<<<->>>>>>>>]+<<<<<<<<[->>>>>>>>
       
   674 -<<[-<<<<<<+>>>>>>]<<<<<<[->>>>>>+<<<<<<<<<<<<<<<[<<<<<<<<<]>>>[-]+>>>>>>[>>>>>>
       
   675 >>>]>[-]+<]]+>[-<[>>>>>>>>>]<<<<<<<<]>>>>>>>>]<<<<<<<<<[<<<<<<<<<]>>>>[-]<<<++++
       
   676 +[-[->>>>>>>>>+<<<<<<<<<]>>>>>>>>>]>>>>>->>>>>>>>>>>>>>>>>>>>>>>>>>>-<<<<<<[<<<<
       
   677 <<<<<]]>>>]""", "mand")
       
   678