TC-C Samples

The combine module provides various tasks to simulate compiler options to use with tc, where you first enable extensions and then process them.

You can use --c-* to enable extensions and --combine-* tasks to perform operations combining multiple language extensions.

For instance, we perform renaming with bounds-checking and overloading activated:

bounds-n-overloads.tig
let
  type int_array = array of int
  type string_array = array of string

  function get(arr: int_array, pos: int) : int = arr[pos]
  function get(arr: string_array, pos: int) : string = arr[pos]

  var arr1 := int_array[10] of 0
  var arr2 := string_array[10] of ""
in
  get(arr1, 0);
  get(arr2, 10)
end
tc --c-bounds --c-overload --combine-rename -A bounds-n-overloads.tig
$ tc --c-bounds --c-overload --combine-rename -A bounds-n-overloads.tig
/* == Abstract Syntax Tree. == */

primitive print(string_0 : string)
primitive print_err(string_1 : string)
primitive print_int(int_2 : int)
primitive flush()
primitive getchar() : string
primitive ord(string_3 : string) : int
primitive chr(code_4 : int) : string
primitive size(string_5 : string) : int
primitive streq(s1_6 : string, s2_7 : string) : int
primitive strcmp(s1_8 : string, s2_9 : string) : int
primitive substring(string_10 : string, start_11 : int, length_12 : int) : string
primitive concat(fst_13 : string, snd_14 : string) : string
primitive not(boolean_15 : int) : int
primitive exit(status_16 : int)
function _main() =
  (
    let
      type int_array_17 = array of int
      type string_array_18 = array of string
      function get_21(arr_19 : int_array_17, pos_20 : int) : int =
        arr_19[pos_20]
      function get_24(arr_22 : string_array_18, pos_23 : int) : string =
        arr_22[pos_23]
      var arr1_25 := int_array_17 [10] of 0
      var arr2_26 := string_array_18 [10] of ""
    in
      (
        get_21(arr1_25, 0);
        get_24(arr2_26, 10)
      )
    end;
    ()
  )
$ echo $?
0

--c-all enables all extensions, and --combine-desugar desugars them into core Tiger.

0.tig
0
tc --c-all --combine-desugar -A 0.tig
$ tc --c-all --combine-desugar -A 0.tig
/* == Abstract Syntax Tree. == */

primitive print(string_0 : string)
primitive print_err(string_1 : string)
primitive print_int(int_2 : int)
primitive flush()
primitive getchar() : string
primitive ord(string_3 : string) : int
primitive chr(code_4 : int) : string
primitive size(string_5 : string) : int
primitive streq(s1_6 : string, s2_7 : string) : int
primitive strcmp(s1_8 : string, s2_9 : string) : int
primitive substring(string_10 : string, start_11 : int, length_12 : int) : string
primitive concat(fst_13 : string, snd_14 : string) : string
primitive not(boolean_15 : int) : int
primitive exit(status_16 : int)
function _main() =
  let
    type __int_array = array of int
    type _int_array = {
      arr : __int_array,
      size : int
    }
  in
    let
      type _variant_Object = { exact_type : int }
      var _id_Object := 0
    in
      (
        0;
        ()
      )
    end
  end
$ echo $?
0

Shorthands for these two tasks are also provided, respectively -a and -c.

all-extensions.tig
let
  type int_array = array of int

  function print(n: int) = print_int(n)


  class C
  {
    var a_size := 10
    var a := int_array[10] of 0

    method print_a() =
    (
      if self.a_size = 0
      then
        ()
      else
      (
        print(self.a[0]);
        for i := 1 to self.a_size - 1 do
          (
            print(", ");
            print(self.a[i])
          )
      )
    )
  }

  var c := new C
in
  c.a[c.a_size - 1] := 42;
  c.print_a()
end
tc -acA all-extensions.tig
$ tc -acA all-extensions.tig
/* == Abstract Syntax Tree. == */

primitive print(string_0 : string)
primitive print_err(string_1 : string)
primitive print_int(int_2 : int)
primitive flush()
primitive getchar() : string
primitive ord(string_3 : string) : int
primitive chr(code_4 : int) : string
primitive size(string_5 : string) : int
primitive streq(s1_6 : string, s2_7 : string) : int
primitive strcmp(s1_8 : string, s2_9 : string) : int
primitive substring(string_10 : string, start_11 : int, length_12 : int) : string
primitive concat(fst_13 : string, snd_14 : string) : string
primitive not(boolean_15 : int) : int
primitive exit(status_16 : int)
function _main() =
  let
    type __int_array = array of int
    type _int_array = {
      arr : __int_array,
      size : int
    }
  in
    let
      type _box_int_array_17 = {
        arr : int_array_17,
        size : int
      }
      type _variant_Object = {
        exact_type : int,
        field_C_22 : _contents_C_22
      }
      type int_array_17 = array of int
      type _contents_C_22 = {
        a_size : int,
        a : _box_int_array_17
      }
      type _variant_C_22 = {
        exact_type : int,
        field_C_22 : _contents_C_22
      }
      var _id_Object := 0
      var _id_C_22 := 1
    in
      (
        let
          var c_23 := let
              var res : _variant_C_22 := let
                  var contents_C_22 := _contents_C_22 {
                      a_size = 10,
                      a = let
                          var _size := 10
                        in
                          _box_int_array_17 {
                            arr = int_array_17 [_size] of 0,
                            size = _size
                          }
                        end
                    }
                in
                  _variant_C_22 {
                    exact_type = _id_C_22,
                    field_C_22 = contents_C_22
                  }
                end
            in
              res
            end
        in
          (
            c_23.field_C_22.a.arr[let
                var a : _int_array := _cast(c_23.field_C_22.a, _int_array)
                var index : int := c_23.field_C_22.a_size - 1
                var location : string := "all-extensions.tig:31.3-19"
                var res : int := (
                    if if index < 0
                          then 1
                          else (index >= a.size) <> 0
                      then (
                          print_err(location);
                          print_err(": array index out of bounds.\n");
                          exit(120)
                        )
                      else ();
                    index
                  )
              in
                res
              end] := 42;
            let
              var self : _variant_C_22 := c_23
              var res := let
                  var self : _variant_C_22 := self
                  var res := (if self.field_C_22.a_size = 0
                      then ()
                      else (
                          let
                            var n_18 : int := self.field_C_22.a.arr[let
                                  var a : _int_array := _cast(self.field_C_22.a, _int_array)
                                  var index : int := 0
                                  var location : string := "all-extensions.tig:19.9-23"
                                  var res : int := (
                                      if if index < 0
                                            then 1
                                            else (index >= a.size) <> 0
                                        then (
                                            print_err(location);
                                            print_err(": array index out of bounds.\n");
                                            exit(120)
                                          )
                                        else ();
                                      index
                                    )
                                in
                                  res
                                end]
                            var res := print_int(n_18)
                          in
                            res
                          end;
                          let
                            var _lo := 1
                            var _hi := self.field_C_22.a_size - 1
                            var i_20 := _lo
                          in
                            if _lo <= _hi
                              then while 1 do
                                  (
                                    (
                                      print(", ");
                                      let
                                        var n_18 : int := self.field_C_22.a.arr[let
                                              var a : _int_array := _cast(self.field_C_22.a, _int_array)
                                              var index : int := i_20
                                              var location : string := "all-extensions.tig:23.13-27"
                                              var res : int := (
                                                  if if index < 0
                                                        then 1
                                                        else (index >= a.size) <> 0
                                                    then (
                                                        print_err(location);
                                                        print_err(": array index out of bounds.\n");
                                                        exit(120)
                                                      )
                                                    else ();
                                                  index
                                                )
                                            in
                                              res
                                            end]
                                        var res := print_int(n_18)
                                      in
                                        res
                                      end
                                    );
                                    if i_20 = _hi
                                      then break
                                      else ();
                                    i_20 := i_20 + 1
                                  )
                              else ()
                          end
                        ))
                in
                  res
                end
            in
              res
            end
          )
        end;
        ()
      )
    end
  end
$ echo $?
0