scala/comp2.scala
author Christian Urban <urbanc@in.tum.de>
Fri, 11 Jan 2019 13:37:54 +0000
changeset 297 bee184c83071
parent 271 4457185b22ef
permissions -rw-r--r--
added some text at the beginning
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
195
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents:
diff changeset
     1
package object comp2 {
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents:
diff changeset
     2
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents:
diff changeset
     3
//  Recusive function to Abacus translation
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents:
diff changeset
     4
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents:
diff changeset
     5
import lib._
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents:
diff changeset
     6
import abacus._
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents:
diff changeset
     7
import recs._
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents:
diff changeset
     8
205
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
     9
def AbacusAdd(m: Int, n: Int, p: Int) = 
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    10
  Abacus(Dec(m, 4), Inc(n), Inc(p), Goto(0), Dec(p, 7), Inc(m), Goto(4))
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    11
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    12
def MVReg(m: Int, n: Int) = Abacus(Dec(m, 3), Inc(n), Goto(0))
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    13
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    14
//move the registers ranging from i to i + n to range j to j + n
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    15
def MVRegs(i: Int, j: Int, n: Int) : Abacus = n match { 
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    16
  case 0 => Abacus() 
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    17
  case n => MVRegs(i, j, n - 1) :+ MVReg(i + n - 1, j + n - 1)
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    18
}
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    19
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    20
// clears the first n registers
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    21
def ClearRegs(n: Int) : Abacus = n match {
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    22
  case 0 => Abacus()
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    23
  case n => ClearRegs(n - 1) :+ Abacus(Dec(n - 1, 2), Goto(0))
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    24
}
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    25
271
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    26
def cn_merge_gs(x: List[(Abacus, Int)], n: Int, p: Int) : Abacus = x match {
205
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    27
  case Nil => Abacus(Nil)
271
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    28
  case (gprog, gn)::gs => gprog :+ MVReg(n, p) :+ cn_merge_gs(gs, n, p + 1)
205
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    29
}
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    30
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    31
// translation: 
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    32
// second component is the arity of the recursive function, 
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    33
// third componen is the maximum of registers used
271
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    34
def compile_rec(f: Rec) : (Abacus, Int) = f match {
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    35
  case Z => (Abacus(Goto(1)), 2)
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    36
  case S => (AbacusAdd(0, 1, 2) :+ Abacus(Inc(1)), 3)
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    37
  case Id(i, j) => (AbacusAdd(j, i, i + 1), i + 2) 
205
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    38
  case Cn(n, f, gs) => {
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    39
    val cied_gs = gs.map(compile_rec)
271
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    40
    val (fprog, fn) = compile_rec(f) 
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    41
    val qstr = (fn :: (cied_gs.map(_._2))).max
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    42
    (cn_merge_gs(cied_gs, n, qstr) :+ 
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    43
     MVRegs(0, qstr + gs.length, n) :+
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    44
     MVRegs(qstr, 0, gs.length) :+
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    45
     fprog :+ 
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    46
     MVReg(f.arity, qstr + gs.length + 1) :+ 
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    47
     ClearRegs(gs.length) :+
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    48
     MVRegs(qstr + gs.length , 0, n + 1), qstr + gs.length + n + 1)
205
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    49
  }
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    50
  case Pr(n, f, g) => { 
271
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    51
    val (fprog, fn) = compile_rec(f) 
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    52
    val (gprog, gn) = compile_rec(g) 
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    53
    val qstr = List(fn, gn).max 
205
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    54
    val e = gprog.p.length + 7 
271
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    55
    (MVReg(0, qstr) :+
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    56
     MVRegs(1, 0, n) :+ 
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    57
     fprog :+ 
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    58
     MVReg(n, n + 1) :+ 
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    59
     MVRegs(0, 2, n) :+ 
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    60
     ((Abacus(Dec(qstr, e)) :+ gprog :+ Abacus(Inc(0), Dec(n + 1, 3), Goto(1))) ++
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    61
       Abacus(Dec(n + 2, 0), Inc (1), Goto (gprog.p.length + 4))), qstr + 1)
205
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    62
  }
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    63
  case Mn(n, f) => {
271
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    64
    val (fprog, fn) = compile_rec(f)
205
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    65
    val len = fprog.p.length
271
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    66
    (MVRegs(0, 1, n) :+
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    67
     (fprog ++ Abacus(Dec(n + 1, len + 5), Dec(n + 1, len + 3), Goto(len + 1), Inc(0), Goto(0))), 
4457185b22ef added slides
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 205
diff changeset
    68
     fn)
205
c7975ab7c52e corrected scala compiler from recs to abacus
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents: 195
diff changeset
    69
  }
195
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents:
diff changeset
    70
}
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents:
diff changeset
    71
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents:
diff changeset
    72
}
Christian Urban <christian dot urban at kcl dot ac dot uk>
parents:
diff changeset
    73