Skip to content

Commit

Permalink
compiler: first attempt at restructuring
Browse files Browse the repository at this point in the history
  • Loading branch information
azenla committed Nov 15, 2023
1 parent 041848c commit 4c50d48
Show file tree
Hide file tree
Showing 10 changed files with 192 additions and 164 deletions.
43 changes: 43 additions & 0 deletions compiler/src/main/kotlin/gay/pizza/pork/compiler/CodeBuilder.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
package gay.pizza.pork.compiler

import gay.pizza.pork.bytecode.MutableRel
import gay.pizza.pork.bytecode.Op
import gay.pizza.pork.bytecode.Opcode

class CodeBuilder(val symbol: CompilableSymbol) {
private val ops = mutableListOf<StubOp>()

val localState: LocalState = LocalState(symbol)

fun nextOpInst(): UInt = ops.size.toUInt()

fun emit(op: StubOp) {
ops.add(op)
}

fun emit(op: Op) {
ops.add(StaticOp(op))
}

fun emit(code: Opcode, arguments: List<UInt>) {
emit(Op(code, arguments))
}

fun emit(code: Opcode) {
emit(code, emptyList())
}

fun patch(code: Opcode, arguments: List<UInt>, index: Int, symbol: CompilableSymbol, rel: MutableRel) {
emit(PatchRelOp(Op(code, arguments), index, symbol, rel))
}

fun patch(code: Opcode, arguments: List<UInt>, index: Int, symbol: CompilableSymbol, rel: UInt) {
emit(PatchRelOp(Op(code, arguments), index, symbol, MutableRel(rel)))
}

fun patch(code: Opcode, arguments: List<UInt>, patches: Map<Int, CompilableSymbol>) {
ops.add(PatchSymOp(Op(code, arguments), patches))
}

fun build(): List<StubOp> = ops.toList()
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ class CompilableSlab(val compiler: Compiler, val slab: Slab) {
}
}

fun compilableSymbolOf(symbol: Symbol): CompilableSymbol? = compilableSymbols.firstOrNull {
fun resolve(symbol: Symbol): CompilableSymbol? = compilableSymbols.firstOrNull {
it.scopeSymbol.symbol == symbol
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ class CompilableSymbol(val compilableSlab: CompilableSlab, val scopeSymbol: Scop
}
emitter.visit(what)
emitter.exit()
return emitter.ops()
return emitter.code.build()
}

val id: String
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ class Compiler {

fun resolveOrNull(scopeSymbol: ScopeSymbol): CompilableSymbol? {
val compiledSlab = compilableSlabs.of(scopeSymbol.slabScope.slab)
return compiledSlab.compilableSymbolOf(scopeSymbol.symbol)
return compiledSlab.resolve(scopeSymbol.symbol)
}

fun resolve(scopeSymbol: ScopeSymbol): CompilableSymbol = resolveOrNull(scopeSymbol) ?:
Expand Down
6 changes: 6 additions & 0 deletions compiler/src/main/kotlin/gay/pizza/pork/compiler/Loadable.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
package gay.pizza.pork.compiler

class Loadable(
val call: CompilableSymbol? = null,
val stubVar: StubVar? = null
)
55 changes: 55 additions & 0 deletions compiler/src/main/kotlin/gay/pizza/pork/compiler/LocalState.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
package gay.pizza.pork.compiler

import gay.pizza.pork.ast.gen.Symbol
import gay.pizza.pork.bytecode.MutableRel

class LocalState(val symbol: CompilableSymbol) {
private var internalLoopState: LoopState? = null
val loopState: LoopState?
get() = internalLoopState

private var localVarIndex: UInt = 0u
private val variables = mutableListOf<MutableList<StubVar>>()

fun startLoop(startOfLoop: UInt, exitJumpTarget: MutableRel) {
internalLoopState = LoopState(
startOfLoop = startOfLoop,
exitJumpTarget = exitJumpTarget,
scopeDepth = (internalLoopState?.scopeDepth ?: 0u) + 1u,
enclosing = internalLoopState
)
}

fun endLoop() {
internalLoopState = internalLoopState?.enclosing
}

fun createLocal(symbol: Symbol): StubVar {
val scope = variables.last()
val variable = StubVar(localVarIndex++, symbol)
scope.add(variable)
return variable
}

fun pushScope() {
variables.add(mutableListOf())
}

fun popScope() {
variables.removeLast()
}

fun resolve(symbol: Symbol): Loadable {
for (scope in variables.reversed()) {
val found = scope.firstOrNull { it.symbol == symbol }
if (found != null) {
return Loadable(stubVar = found)
}
}
val found = this.symbol.compilableSlab.resolve(symbol)
if (found != null) {
return Loadable(call = found)
}
throw RuntimeException("Unable to resolve symbol: ${symbol.id}")
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@ import gay.pizza.pork.bytecode.MutableRel
class LoopState(
val startOfLoop: UInt,
val exitJumpTarget: MutableRel,
val body: MutableRel,
val scopeDepth: Int,
val scopeDepth: UInt,
val enclosing: LoopState? = null
)
Loading

0 comments on commit 4c50d48

Please sign in to comment.