summaryrefslogtreecommitdiff
path: root/sources/scala/runtime/ScalaRunTime.scala
blob: 8fe69a2f3105ee941b055c5960f89475f045079b (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
/*                     __                                               *\
**     ________ ___   / /  ___     Scala API                            **
**    / __/ __// _ | / /  / _ |    (c) 2002-2005, LAMP/EPFL             **
**  __\ \/ /__/ __ |/ /__/ __ |                                         **
** /____/\___/_/ |_/____/_/ | |                                         **
**                          |/                                          **
\*                                                                      */

// $Id$

package scala.runtime;

object ScalaRunTime {

  /** Names for primitive types, used by array unboxing */
  val ByteTag = ".Byte";
  val ShortTag = ".Short";
  val CharTag = ".Char";
  val IntTag = ".Int";
  val LongTag = ".Long";
  val FloatTag = ".Float";
  val DoubleTag = ".Double";
  val BooleanTag = ".Boolean";

  trait Try[a] {
    def Catch[b >: a](handler: PartialFunction[Throwable, b]): b;
    def Finally(handler: Unit): a;
  }

  def Try[a](block: => a): Try[a] = new Try[a] with Runnable {
    var result: a = _;
    var exception: Throwable = RunTime.tryCatch(this);

    def run(): Unit = result = block;

    def Catch[b >: a](handler: PartialFunction[Throwable, b]): b =
      if (exception == null)
	result.asInstanceOf$erased[b]
      // !!! else if (exception is LocalReturn)
      // !!!   // ...
      else if (handler isDefinedAt exception)
	handler(exception)
      else
	throw exception;

    def Finally(handler: Unit): a =
      if (exception == null)
        result.asInstanceOf$erased[a]
      else
        throw exception;
  }

  def caseFields(x: CaseClass): List[Any] = {
    val arity = x.caseArity;
    def fields(from: Int): List[Any] =
      if (from >= arity) List()
      else x.caseElement(from) :: fields(from + 1);
    fields(0)
  }

  def _toString(x: CaseClass): String = {
    caseFields(x).mkString(x.caseName + "(", ",", ")")
  }

  def _hashCode(x: CaseClass): Int = {
    var code = x.getClass().hashCode();
    val arity = x.caseArity;
    var i = 0;
    while (i < arity) {
      code = code * 41 + x.caseElement(i).hashCode();
      i = i + 1
    }
    code
  }

  def _equals(x: CaseClass, y: Any): Boolean = y match {
    case y1: CaseClass =>
      (x.getClass() eq y1.getClass()) && {
	val arity = x.caseArity;
	var i = 0;
	while (i < arity && x.caseElement(i) == y1.caseElement(i))
	  i = i + 1;
	i == arity
      }
    case _ =>
      false
  }

  def Seq[a](xs: a*): Seq[a] = null; // interpreted specially by new backend.
}