Quick and dirty "C" to MIPS compiler - written in a day (and night) at Jugendforum Informatik 2020
  • C# 97.4%
  • Assembly 2.6%
Find a file
2026-06-11 17:25:54 +02:00
examples port to dotnet core 10 2026-06-11 17:17:43 +02:00
mips-samples final commit before presentation 2020-02-08 11:43:26 +01:00
.gitattributes added tokenizer and parts of the parser and code generator 2020-02-08 00:48:21 +01:00
.gitignore added tokenizer and parts of the parser and code generator 2020-02-08 00:48:21 +01:00
Generator.cs modernize 2026-06-11 17:25:54 +02:00
JFICompiler.csproj modernize 2026-06-11 17:25:54 +02:00
Parser.cs modernize 2026-06-11 17:25:54 +02:00
Program.cs modernize 2026-06-11 17:25:54 +02:00
README.md modernize 2026-06-11 17:25:54 +02:00
Tokenizer.cs modernize 2026-06-11 17:25:54 +02:00

JFI-Compiler

A tiny C-like to MIPS compiler written in one night at Jugenforum Informatik, a 4-day coding camp on Burg Liebenzell for participants of the German federal computer science competition (BWInf).

Four C# files, ~1000 lines, zero dependencies.

Note: 2026: This is project has since been modernized with .NET 10 best practices (no functionality or scope was changed).

Language

It's basically C, but with only int and these quirks:

  • print(x) -- prints an integer (no format strings)
  • read -- reads an integer from stdin (used as an rvalue: x = read)
  • return; -- statement-level (no value)
  • x += 1 / x -= 1 -- compound assignment at statement level only
  • No functions (single implicit main block)
  • No else
  • No nested expressions in conditions (must be a op b)
  • Only ==, !=, <, >, <=, >=, +, -, *, /, ^, &&, ||

Example

int number = read;
int factor = read;

int result = 0;
int i = 0;
while (i < factor)
{
    result += number;
    i += 1;
}

print(result);

(examples/multiply.asm)

ADDI $sp, $sp, 0
LI $v0, 5
SYSCALL
MOVE $t0, $v0
SW $t0, 0($sp)
LI $v0, 5
SYSCALL
MOVE $t0, $v0
SW $t0, -4($sp)
LI $t0, 0
SW $t0, -8($sp)
LI $t0, 0
SW $t0, -12($sp)
WHILE0:
LW $t1, -12($sp)
LW $t2, -4($sp)
BLT $t1, $t2, WHILE1
J WHILE2
WHILE1:
ADDI $sp, $sp, -16
LW $t0, 8($sp)
LW $t1, 16($sp)
ADD $t0, $t0, $t1
SW $t0, 8($sp)
LW $t0, 4($sp)
LI $t1, 1
ADD $t0, $t0, $t1
SW $t0, 4($sp)
BLOCK1:
ADDI $sp, $sp, 16
J WHILE0
WHILE2:
LW $a0, -8($sp)
LI $v0, 1
SYSCALL
BLOCK0:
ADDI $sp, $sp, 0

Usage

JFICompiler.exe <input.c> <output.asm>

Sample Outputs

print(16)

print(16);
li $a0, 16
li $v0, 1
syscall

Reading and writing variables (stack)

int x = 16;
print(x);
li $t1, 16
sw $t1, 4($sp)

lw $a0, 4($sp)
li $v0, 1
syscall

If statement

if (1 == 2)
{
    // true branch
}
LI $t1, 1
LI $t2, 2
BEQ $t1, $t2, IF1
J IF2
IF1:
    ; true branch
IF2:
    ; continue

While loop

while (i < j)
{
    // loop body
}
WHILE0:
    BEQ $t1, $t2, WHILE1
    J WHILE2
WHILE1:
    ; loop body
    J WHILE0
WHILE2:
    ; continue