Felix Programming Language

Authors : erickt : March 2008

LLVM Bindings

posted on March 22, 2008 - 05:30 PM PDT by Erick Tryzelaar

For a long time I've wanted to write a llvm backend for felix, however, it seems to be a bit easier to bind the llvm libraries to felix. So here's my first attempt. It's pretty trivial:

llvm.flx:

namespace llvm {
  requires package "llvm";

  requires header "#include <llvm/Value.h>";
  requires header "#include <llvm/Type.h>";
  requires header "#include <llvm/DerivedTypes.h>";

  open C_hack;

  typeclass Value[t] {
    virtual proc dump: cptr[t] = "$1->dump();";
  }

  typeclass Type[t] {
    inherit Value[t];

    fun is_integer: t -> bool = "$1->isInteger()"; 
  }

  type type_ = "::llvm::Type";
  instance Type[type_] {}

  typeclass IntegerType[t] {
    inherit Type[t];

    fun get_bit_width: cptr[t] -> int = "$1->getBitWidth()";
  }

  type integer_type = "::llvm::IntegerType";
  instance IntegerType[integer_type] {}

  fun int8_type  : unit -> cptr[integer_type] = "::llvm::Type::Int8Ty";
  fun int16_type : unit -> cptr[integer_type] = "::llvm::Type::Int16Ty";
  fun int32_type : unit -> cptr[integer_type] = "::llvm::Type::Int32Ty";
  fun int64_type : unit -> cptr[integer_type] = "::llvm::Type::Int64Ty";

  fun float_type : unit -> cptr[type_] = "::llvm::Type::FloatTy";
}

llvm.fpc:

cflags: -I/tmp/llvm/include  -D_DEBUG  -D_GNU_SOURCE -D__STDC_LIMIT_MACROS
provides_dlib: -L/tmp/llvm/lib  -lpthread -lm -lLLVMCore -lLLVMSupport -lLLVMSystem

foo.flx:

include "llvm";
open llvm;

Value::dump $ int8_type ();
println $ Type::is_integer $ int8_type ();
println $ IntegerType::get_bit_width $ int8_type ();

Value::dump $ float_type ();
println $ Type::is_integer $ float_type ();

Which, when run, results in:

> flx foo.flx
Other exn = Flx_exceptions.Free_fixpoint(_)
i8
true
8
float
false

Of course there seems to be a couple typeclass bugs we're running into, as if we have this call:

println $ IntegerType::get_bit_width $ float_type ()

We manage to get through felix and error out in c++:

foo.cpp: In function 'void flxusr::foo::_init_(flxusr::foo::thread_frame_t*)':
foo.cpp:82: error: 'const class llvm::Type' has no member named 'getBitWidth'
compilation terminated due to -Wfatal-errors.

So we've got some work to do. :)

Update: Just to be clear, IntegerType::get_bit_width $ float_type () should be a type error, since float_type returns a cptr[type_], not a cptr[integer_type], and doesn't instantiate the IntegertType typeclass. `

read comments