transcendental-lisp/src/main/kotlin/table/ExecutionContext.kt
2018-03-23 18:12:47 -04:00

92 lines
2.0 KiB
Kotlin

package table
import function.LispFunction
import sexpression.Cons
import sexpression.Nil.NIL
import sexpression.SExpression
import table.SymbolTable.NullSymbolTable
import java.util.Stack
object ExecutionContext {
private val functionCalls: Stack<LispFunctionRecurInfo> = Stack()
var scope: SymbolTable = SymbolTable(NullSymbolTable)
var isRecur: Boolean = false
private set
val isInFunctionCall: Boolean
get() = !functionCalls.empty()
val currentFunction: LispFunction
get() = functionCalls.peek().lispFunction
val isRecurInitializing: Boolean
get() = functionCalls.peek().isRecurInitializing
fun clearContext() {
scope = SymbolTable(NullSymbolTable)
functionCalls.clear()
clearRecur()
}
fun restoreGlobalScope() {
while (!scope.isGlobal)
scope = scope.parent ?: NullSymbolTable
}
fun lookupSymbolValue(symbolName: String): SExpression? {
for (table in scope)
if (symbolName in table)
return table[symbolName]
return null
}
fun toList(): Cons {
var symbols: Cons = NIL
for (table in scope)
symbols = Cons(table.toList(), symbols)
return symbols
}
fun pushFunctionCall(function: LispFunction) {
functionCalls.push(LispFunctionRecurInfo(function))
}
fun popFunctionCall() {
functionCalls.pop()
}
fun setRecur() {
isRecur = true
}
fun clearRecur() {
isRecur = false
}
fun setRecurInitializing() {
functionCalls.peek().setRecurInitializing()
}
fun clearRecurInitializing() {
functionCalls.peek().clearRecurInitializing()
}
class LispFunctionRecurInfo(val lispFunction: LispFunction) {
var isRecurInitializing: Boolean = false
private set
fun setRecurInitializing() {
isRecurInitializing = true
}
fun clearRecurInitializing() {
isRecurInitializing = false
}
}
}