Compiler for a small language into x86-64 Assembly

Compiler

This project is a small compiler, that compiles my own little language into X86-64 Assembly. It then uses yasm and ld to assemble and link into a Linux X86-64 executable.

But why?

I've always wanted to write a compiler myself! But just never got around to do it. So the current Coronavirus quarantine situation finally gives me enough time to tackle it myself.

And I was really impressed by people, that wrote solutions for last years adventofcode.com in their own language. So that is something I'd like to achieve :)

So no, no real reason other than - I like to work on challenging problems and found compilers intriguing.

How to run

  • go build
  • ./compiler <source_file>
  • ./executable

The compiler will always create an executable called executable. Additionally, it will create a file source.asm that contains the generated (not optimized) assembly.

Dependencies

Everything is written from scratch, there are no code dependencies. But to assemble and link the program into an executable, you need:

  • yasm
  • ld

The resulting Assembly also has no external dependencies (No C std lib, printing is implemented in Assembly directly).

Language influences

  • Go
  • C
  • Python
  • Lua

Features

  • Strong and static type system
  • Multiple return values from functions
  • Automatic packing/unpacking of multiple arguments and/or function returns
  • Function overloading
  • Function inlining (only for system functions right now)
  • Dynamic Arrays with an internal capacity, so not every append needs a new memory allocation
  • Int and Float types are always 64bit
  • Very Python-like array creation
  • Switch expressions match either values or general boolean expressions
  • Range-based Loops with index and element
  • Structs

Examples

See the compiler_test.go file for a lot more working examples :)

Print

// There are overloaded functions: print, println that work on floats and integers
println(5)
println(6.543)

Assignment

// Types are derived from the expressions!
a = 4
b = 5.6
c = true

Functions

fun abc(i int, j float) int, float, int {
    return i, j, 100
}
// Can be overloaded
fun abc(i int, j int) int, float, int {
    return i, 5.5, j
}
// ...
a, b, c = abc(5, 6.5)

Lists

// List of integers. Type derived from the expressions
list = [1, 2, 3, 4, 5]
// Empty list of integers with length 10. Type explicitely set
list2 = [](int, 10)
// Lists can naturally contain other lists
list3 = [list, list2]
// There are build-in functions, to get the length and capacity
println(len(list3))
println(cap(list3))

// You have to free them yourself
free(list)

// And some convenience functions to clear/reset the list without deallocating the memory:
// reset only resets the length, while clear overwrites the memory with 0s

reset(list)
clear(list)

// Build-in append/extend function, similar to the one in Go
// Careful ! append/extend works on the first argument. Depending on the available capacity, it will
// extend list or free list and create a completely new memory block, copy list and list2 over and return
// the new pointer!

list = append(list, 6)
list = extend(list, list2)

// Lists in functions/structs
fun abc(a []int) {
    // ...
}

Loops

list = [1,2,3,4,5]

for i = 0; i < len(list); i++ {
    // ...
}

for i,e : list {
    // i is the current index
    // e is the actual element: list[i]
}    

Switch

switch 4 {
case 1:
    println(1)
case 2, 3, 6:
    println(4)
case 5:
    println(5)
default:
    println(999)
}

switch {
case 2 > 3:
    println(1)
case 2 == 3:
    println(4)
default:
    println(888)
}

Structs

struct B {
    i int
    j int
}
struct A {
    i int
    j B
}

// Structs are created by calling a function with the same name and an exact match of parameters 
// that match the expected types of the struct.
// Internally, this is just syntax, not a function. So there is no overhead!
a = A(1, B(3, 4))
a.j.j = 100
println(a.i)
println(a.j.j)

Type conversions

// Build-in (inline) functions: int(), float()
println(int(5.5))
println(float(5))
Similar Resources

Floppa programming language inspired by the brainf*ck programming language. Created just for fun and you can convert your brainf*ck code to floppa code.

Floppa Programming Language Created just for fun. But if you want to contribute, why not? Floppa p.l. inspired by the brainf*ck programming language.

Oct 20, 2022

T# Programming Language. Something like Porth, Forth but written in Go. Stack-oriented programming language.

The T# Programming Language WARNING! THIS LANGUAGE IS A WORK IN PROGRESS! ANYTHING CAN CHANGE AT ANY MOMENT WITHOUT ANY NOTICE! Something like Forth a

Jun 29, 2022

Yayx programming language is begginer friendly programming language.

Yayx programming language is begginer friendly programming language.

Yayx Yayx programming language is begginer friendly programming language. What have yayx: Easy syntax Dynamic types Can be compiled to outhers program

Dec 27, 2021

Yayx programming language is begginer friendly programming language.

Yayx Yayx programming language is begginer friendly programming language. What have yayx: Easy syntax Dynamic types Can be compiled to outhers program

May 20, 2022

Small Clojure interpreter, linter and formatter.

Small Clojure interpreter, linter and formatter.

Joker is a small Clojure interpreter, linter and formatter written in Go. Installation On macOS, the easiest way to install Joker is via Homebrew: bre

Dec 30, 2022

Go bindings to QuickJS: a fast, small, and embeddable ES2020 JavaScript interpreter.

quickjs Go bindings to QuickJS: a fast, small, and embeddable ES2020 JavaScript interpreter. These bindings are a WIP and do not match full parity wit

Dec 28, 2022

This package is built for Embedding PHP into Golang.

GoEmPHP This package is built for Embedding PHP into Golang. It is easy to use: script = php.New() script.Startup() defer script.Close()

Jul 2, 2022

DEPRECATED. Embeds mruby (mini Ruby) VM into Go.

GoMRuby Package gomruby embeds mruby (mini Ruby) VM into Go. Documentation. Installation It's slightly more than just go get: go get -d github.com/Ale

May 17, 2022

a dynamically typed, garbage collected, embeddable programming language built with Go

The agora programming language Agora is a dynamically typed, garbage collected, embeddable programming language. It is built with the Go programming l

Dec 30, 2022
Comments
  • return analysis is a bit naive

    return analysis is a bit naive

    Error should be emitted but isn't:

    fun test () int {
        for ;; {
            break
            return 0
        }    
    }
    

    Error emitted but shouldn't be:

    fun test (x int) int {
        if x == 0 { return 0 } else { }
    
        if x == 0 { return 0 } else { return 0 }
    }
    
  • macOS usage

    macOS usage

    First of all, really cool project! I'd love to try it out, but I can't seem to get it to work. So I did

    go build
    brew install yasm
    ./compiler test.lang
    

    I've taken a look a test.lang, and I assume it's the example source file. Then I get the following error:

    ld: warning: No version-min specified on command line
    ld: warning: -arch not specified
    ld: warning: -macosx_version_min not specified, assuming 10.11
    ld: warning: ignoring file /var/folders/5p/9qqn9bds0kxf85ctpy0s12bm0000gn/T/061022517, file was built for unsupported file format ( 0x7F 0x45 0x4C 0x46 0x02 0x01 0x01 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 ) which is not the architecture being linked (x86_64): /var/folders/5p/9qqn9bds0kxf85ctpy0s12bm0000gn/T/061022517
    Undefined symbols for architecture x86_64:
      "_main", referenced from:
         implicit entry/start for main executable
    ld: symbol(s) not found for inferred architecture x86_64
    Error while linking object file - exit status 1
    

    Maybe I'm supposed to be linking something, like in C it would be, e.g. gcc -lcurl ..., but I'm not sure. Thanks for the help!

ReCT-Go-Compiler - A compiler for the ReCT programming language written in Golang

ReCT-Go-Compiler A compiler for the ReCT programming language written in Golang

Nov 30, 2022
Go compiler made from scratch, which can compile itself. It's going to be the smallest and simplest go compiler in the world.

Babygo, a go compiler made from scratch Babygo is a small and simple go compiler. (Smallest and simplest in the world, I believe.) It is made from scr

Jan 8, 2023
🏃 An x86-64 assembler written in Go.

asm An x86-64 assembler written in Go. It is used by the Q programming language for machine code generation. Architectures Linux x86-64 (ELF binaries)

Nov 7, 2022
Gentee - script programming language for automation. It uses VM and compiler written in Go (Golang).

Gentee script programming language Gentee is a free open source script programming language. The Gentee programming language is designed to create scr

Dec 15, 2022
Monkey programming language project from 'Writing An Interpreter In Go'and 'Writing A Compiler In Go' Books
Monkey programming language project from 'Writing An Interpreter In Go'and 'Writing A Compiler In Go' Books

Monkey Monkey programming language ?? project from "Writing An Interpreter In Go

Dec 16, 2021
GopherLua: VM and compiler for Lua in Go

GopherLua: VM and compiler for Lua in Go. GopherLua is a Lua5.1 VM and compiler written in Go. GopherLua has a same goal with Lua: Be a scripting lang

Dec 31, 2022
A simple virtual machine - compiler & interpreter - written in golang

go.vm Installation Build without Go Modules (Go before 1.11) Build with Go Modules (Go 1.11 or higher) Usage Opcodes Notes The compiler The interprete

Dec 17, 2022
Cc - Toy C compiler for golang

Grammars program = funcDecl* decl = declspec declarator ("{" compou

May 2, 2022
A multi-pass compiler written in Go comprised of scanner, recursive-descent parser, generation of AST, intermediate representation (ILOC), and code generation (Armv8).

GoLite Project - Go Huskies! This is a project conducted and led in the course MPCS 51300 Compilers at the University of Chicago. In a group of two, w

Jan 10, 2022
Bfc - A compiler for brainfuck by someone who has no idea how compilers work

bfc bfc is a bad (probably) Brainfuck compiler. It compiles only to x64 assembly

Feb 5, 2022