mirror of
				https://github.com/GayPizzaSpecifications/pork.git
				synced 2025-11-03 17:39:38 +00:00 
			
		
		
		
	add a standard library, and introduce formed imports (import std "myfile.pork")
This commit is contained in:
		@ -110,6 +110,8 @@ types:
 | 
				
			|||||||
  ImportDeclaration:
 | 
					  ImportDeclaration:
 | 
				
			||||||
    parent: Declaration
 | 
					    parent: Declaration
 | 
				
			||||||
    values:
 | 
					    values:
 | 
				
			||||||
 | 
					    - name: form
 | 
				
			||||||
 | 
					      type: Symbol?
 | 
				
			||||||
    - name: path
 | 
					    - name: path
 | 
				
			||||||
      type: StringLiteral
 | 
					      type: StringLiteral
 | 
				
			||||||
  IntLiteral:
 | 
					  IntLiteral:
 | 
				
			||||||
 | 
				
			|||||||
@ -6,22 +6,23 @@ import kotlinx.serialization.Serializable
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
@Serializable
 | 
					@Serializable
 | 
				
			||||||
@SerialName("importDeclaration")
 | 
					@SerialName("importDeclaration")
 | 
				
			||||||
class ImportDeclaration(val path: StringLiteral) : Declaration() {
 | 
					class ImportDeclaration(val form: Symbol?, val path: StringLiteral) : Declaration() {
 | 
				
			||||||
  override val type: NodeType = NodeType.ImportDeclaration
 | 
					  override val type: NodeType = NodeType.ImportDeclaration
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  override fun <T> visitChildren(visitor: NodeVisitor<T>): List<T> =
 | 
					  override fun <T> visitChildren(visitor: NodeVisitor<T>): List<T> =
 | 
				
			||||||
    visitor.visitNodes(path)
 | 
					    visitor.visitNodes(form, path)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  override fun <T> visit(visitor: NodeVisitor<T>): T =
 | 
					  override fun <T> visit(visitor: NodeVisitor<T>): T =
 | 
				
			||||||
    visitor.visitImportDeclaration(this)
 | 
					    visitor.visitImportDeclaration(this)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  override fun equals(other: Any?): Boolean {
 | 
					  override fun equals(other: Any?): Boolean {
 | 
				
			||||||
    if (other !is ImportDeclaration) return false
 | 
					    if (other !is ImportDeclaration) return false
 | 
				
			||||||
    return other.path == path
 | 
					    return other.form == form && other.path == path
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  override fun hashCode(): Int {
 | 
					  override fun hashCode(): Int {
 | 
				
			||||||
    var result = path.hashCode()
 | 
					    var result = form.hashCode()
 | 
				
			||||||
 | 
					    result = 31 * result + path.hashCode()
 | 
				
			||||||
    result = 31 * result + type.hashCode()
 | 
					    result = 31 * result + type.hashCode()
 | 
				
			||||||
    return result
 | 
					    return result
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
				
			|||||||
@ -4,6 +4,7 @@ import gay.pizza.pork.ast.CompilationUnit
 | 
				
			|||||||
import gay.pizza.pork.ast.Definition
 | 
					import gay.pizza.pork.ast.Definition
 | 
				
			||||||
import gay.pizza.pork.ast.FunctionDefinition
 | 
					import gay.pizza.pork.ast.FunctionDefinition
 | 
				
			||||||
import gay.pizza.pork.ast.ImportDeclaration
 | 
					import gay.pizza.pork.ast.ImportDeclaration
 | 
				
			||||||
 | 
					import gay.pizza.pork.frontend.ImportLocator
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class CompilationUnitContext(
 | 
					class CompilationUnitContext(
 | 
				
			||||||
  val compilationUnit: CompilationUnit,
 | 
					  val compilationUnit: CompilationUnit,
 | 
				
			||||||
@ -50,8 +51,8 @@ class CompilationUnitContext(
 | 
				
			|||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  private fun processImport(import: ImportDeclaration) {
 | 
					  private fun processImport(import: ImportDeclaration) {
 | 
				
			||||||
    val path = import.path.text
 | 
					    val importLocator = ImportLocator(import.path.text, import.form?.id)
 | 
				
			||||||
    val evaluationContext = evaluator.context(path)
 | 
					    val evaluationContext = evaluator.context(importLocator)
 | 
				
			||||||
    internalScope.inherit(evaluationContext.externalScope)
 | 
					    internalScope.inherit(evaluationContext.externalScope)
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,17 +1,18 @@
 | 
				
			|||||||
package gay.pizza.pork.evaluator
 | 
					package gay.pizza.pork.evaluator
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					import gay.pizza.pork.frontend.ImportLocator
 | 
				
			||||||
import gay.pizza.pork.frontend.World
 | 
					import gay.pizza.pork.frontend.World
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class Evaluator(val world: World, val scope: Scope) {
 | 
					class Evaluator(val world: World, val scope: Scope) {
 | 
				
			||||||
  private val contexts = mutableMapOf<String, CompilationUnitContext>()
 | 
					  private val contexts = mutableMapOf<String, CompilationUnitContext>()
 | 
				
			||||||
  private val nativeFunctionProviders = mutableMapOf<String, NativeFunctionProvider>()
 | 
					  private val nativeFunctionProviders = mutableMapOf<String, NativeFunctionProvider>()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  fun evaluate(path: String): Scope =
 | 
					  fun evaluate(locator: ImportLocator): Scope =
 | 
				
			||||||
    context(path).externalScope
 | 
					    context(locator).externalScope
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  fun context(path: String): CompilationUnitContext {
 | 
					  fun context(locator: ImportLocator): CompilationUnitContext {
 | 
				
			||||||
    val unit = world.load(path)
 | 
					    val unit = world.load(locator)
 | 
				
			||||||
    val identity = world.contentSource.stableContentIdentity(path)
 | 
					    val identity = world.stableIdentity(locator)
 | 
				
			||||||
    val context = contexts.computeIfAbsent(identity) {
 | 
					    val context = contexts.computeIfAbsent(identity) {
 | 
				
			||||||
      CompilationUnitContext(unit, this, scope)
 | 
					      CompilationUnitContext(unit, this, scope)
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
				
			|||||||
@ -1,8 +1,4 @@
 | 
				
			|||||||
func malloc(size)
 | 
					import std "ffi/malloc.pork"
 | 
				
			||||||
  native ffi "c:malloc:void*"
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
func free(pointer)
 | 
					 | 
				
			||||||
  native ffi "c:free:void"
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
export func main() {
 | 
					export func main() {
 | 
				
			||||||
  while true {
 | 
					  while true {
 | 
				
			||||||
 | 
				
			|||||||
@ -0,0 +1,3 @@
 | 
				
			|||||||
 | 
					package gay.pizza.pork.frontend
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					data class ImportLocator(val path: String, val form: String? = null)
 | 
				
			||||||
@ -0,0 +1,7 @@
 | 
				
			|||||||
 | 
					package gay.pizza.pork.frontend
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					interface ImportSource {
 | 
				
			||||||
 | 
					  val fileContentSource: ContentSource
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  fun provideContentSource(form: String): ContentSource
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
@ -0,0 +1,14 @@
 | 
				
			|||||||
 | 
					package gay.pizza.pork.frontend
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class StandardImportSource(override val fileContentSource: ContentSource) : ImportSource {
 | 
				
			||||||
 | 
					  private val providers = mutableMapOf<String,ContentSource>()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  override fun provideContentSource(form: String): ContentSource {
 | 
				
			||||||
 | 
					    return providers[form] ?:
 | 
				
			||||||
 | 
					      throw RuntimeException("Unknown import form: $form")
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  fun addContentSource(form: String, contentSource: ContentSource) {
 | 
				
			||||||
 | 
					    providers[form] = contentSource
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
@ -7,37 +7,57 @@ import gay.pizza.pork.parser.Parser
 | 
				
			|||||||
import gay.pizza.pork.parser.TokenStreamSource
 | 
					import gay.pizza.pork.parser.TokenStreamSource
 | 
				
			||||||
import gay.pizza.pork.parser.Tokenizer
 | 
					import gay.pizza.pork.parser.Tokenizer
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class World(val contentSource: ContentSource) {
 | 
					class World(val importSource: ImportSource) {
 | 
				
			||||||
  private val internalUnits = mutableMapOf<String, CompilationUnit>()
 | 
					  private val internalUnits = mutableMapOf<String, CompilationUnit>()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  val units: List<CompilationUnit>
 | 
					  val units: List<CompilationUnit>
 | 
				
			||||||
    get() = internalUnits.values.toList()
 | 
					    get() = internalUnits.values.toList()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  private fun loadOneUnit(path: String): CompilationUnit {
 | 
					  private fun loadOneUnit(importLocator: ImportLocator): CompilationUnit {
 | 
				
			||||||
    val stableIdentity = contentSource.stableContentIdentity(path)
 | 
					    val contentSource = pickContentSource(importLocator.form)
 | 
				
			||||||
    val cached = internalUnits[stableIdentity]
 | 
					    val stableKey = stableIdentity(importLocator, contentSource = contentSource)
 | 
				
			||||||
 | 
					    val cached = internalUnits[stableKey]
 | 
				
			||||||
    if (cached != null) {
 | 
					    if (cached != null) {
 | 
				
			||||||
      return cached
 | 
					      return cached
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
    val charSource = contentSource.loadAsCharSource(path)
 | 
					    val charSource = contentSource.loadAsCharSource(importLocator.path)
 | 
				
			||||||
    val tokenizer = Tokenizer(charSource)
 | 
					    val tokenizer = Tokenizer(charSource)
 | 
				
			||||||
    val tokenStream = tokenizer.tokenize()
 | 
					    val tokenStream = tokenizer.tokenize()
 | 
				
			||||||
    val parser = Parser(TokenStreamSource(tokenStream), DiscardNodeAttribution)
 | 
					    val parser = Parser(TokenStreamSource(tokenStream), DiscardNodeAttribution)
 | 
				
			||||||
    return parser.readCompilationUnit()
 | 
					    val unit = parser.readCompilationUnit()
 | 
				
			||||||
 | 
					    internalUnits[stableKey] = unit
 | 
				
			||||||
 | 
					    return unit
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  private fun resolveAllImports(unit: CompilationUnit): Set<CompilationUnit> {
 | 
					  private fun resolveAllImports(unit: CompilationUnit): Set<CompilationUnit> {
 | 
				
			||||||
    val units = mutableSetOf<CompilationUnit>()
 | 
					    val units = mutableSetOf<CompilationUnit>()
 | 
				
			||||||
    for (declaration in unit.declarations.filterIsInstance<ImportDeclaration>()) {
 | 
					    for (declaration in unit.declarations.filterIsInstance<ImportDeclaration>()) {
 | 
				
			||||||
      val importedUnit = loadOneUnit(declaration.path.text)
 | 
					      val importLocator = ImportLocator(declaration.path.text, form = declaration.form?.id)
 | 
				
			||||||
 | 
					      val importedUnit = loadOneUnit(importLocator)
 | 
				
			||||||
      units.add(importedUnit)
 | 
					      units.add(importedUnit)
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
    return units
 | 
					    return units
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  fun load(path: String): CompilationUnit {
 | 
					  fun load(importLocator: ImportLocator): CompilationUnit {
 | 
				
			||||||
    val unit = loadOneUnit(path)
 | 
					    val unit = loadOneUnit(importLocator)
 | 
				
			||||||
    resolveAllImports(unit)
 | 
					    resolveAllImports(unit)
 | 
				
			||||||
    return unit
 | 
					    return unit
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  private fun pickContentSource(form: String? = null): ContentSource {
 | 
				
			||||||
 | 
					    if (form != null) {
 | 
				
			||||||
 | 
					      return importSource.provideContentSource(form)
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    return importSource.fileContentSource
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  fun stableIdentity(
 | 
				
			||||||
 | 
					    importLocator: ImportLocator,
 | 
				
			||||||
 | 
					    contentSource: ContentSource = pickContentSource(importLocator.form)
 | 
				
			||||||
 | 
					  ): String {
 | 
				
			||||||
 | 
					    val formKey = importLocator.form ?: "file"
 | 
				
			||||||
 | 
					    val stableIdentity = contentSource.stableContentIdentity(importLocator.path)
 | 
				
			||||||
 | 
					    return "[${formKey}][${stableIdentity}]"
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -183,7 +183,11 @@ class Parser(source: PeekableSource<Token>, val attribution: NodeAttribution) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
  private fun readImportDeclaration(): ImportDeclaration = within {
 | 
					  private fun readImportDeclaration(): ImportDeclaration = within {
 | 
				
			||||||
    expect(TokenType.Import)
 | 
					    expect(TokenType.Import)
 | 
				
			||||||
    ImportDeclaration(readStringLiteral())
 | 
					    var form: Symbol? = null
 | 
				
			||||||
 | 
					    if (peek(TokenType.Symbol)) {
 | 
				
			||||||
 | 
					      form = readSymbolRaw()
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    ImportDeclaration(form, readStringLiteral())
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  private fun readFunctionDeclaration(): FunctionDefinition = within {
 | 
					  private fun readFunctionDeclaration(): FunctionDefinition = within {
 | 
				
			||||||
 | 
				
			|||||||
@ -8,6 +8,7 @@ include(
 | 
				
			|||||||
  ":parser",
 | 
					  ":parser",
 | 
				
			||||||
  ":frontend",
 | 
					  ":frontend",
 | 
				
			||||||
  ":evaluator",
 | 
					  ":evaluator",
 | 
				
			||||||
 | 
					  ":stdlib",
 | 
				
			||||||
  ":ffi",
 | 
					  ":ffi",
 | 
				
			||||||
  ":tool"
 | 
					  ":tool"
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										13
									
								
								stdlib/build.gradle.kts
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										13
									
								
								stdlib/build.gradle.kts
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,13 @@
 | 
				
			|||||||
 | 
					plugins {
 | 
				
			||||||
 | 
					  id("gay.pizza.pork.module")
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					tasks.processResources {
 | 
				
			||||||
 | 
					  from("src/main/pork") {
 | 
				
			||||||
 | 
					    into("pork/stdlib")
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					dependencies {
 | 
				
			||||||
 | 
					  implementation(project(":frontend"))
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
							
								
								
									
										33
									
								
								stdlib/src/main/kotlin/gay/pizza/pork/stdlib/PorkStdlib.kt
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										33
									
								
								stdlib/src/main/kotlin/gay/pizza/pork/stdlib/PorkStdlib.kt
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,33 @@
 | 
				
			|||||||
 | 
					package gay.pizza.pork.stdlib
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					import gay.pizza.pork.frontend.ContentSource
 | 
				
			||||||
 | 
					import gay.pizza.pork.parser.CharSource
 | 
				
			||||||
 | 
					import gay.pizza.pork.parser.StringCharSource
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					object PorkStdlib : ContentSource {
 | 
				
			||||||
 | 
					  private val stdlibClass = PorkStdlib::class.java
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  private fun readManifestFiles(): List<String> {
 | 
				
			||||||
 | 
					    val manifestContent = read("stdlib.manifest")
 | 
				
			||||||
 | 
					    return manifestContent.split("\n").filter { line ->
 | 
				
			||||||
 | 
					      val trimmed = line.trim()
 | 
				
			||||||
 | 
					      trimmed.isNotEmpty() && !trimmed.startsWith("#")
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  val files: List<String> = readManifestFiles()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  private fun read(path: String): String {
 | 
				
			||||||
 | 
					    val stream = stdlibClass.getResourceAsStream("/pork/stdlib/${path}")
 | 
				
			||||||
 | 
					      ?: throw RuntimeException("Stdlib does not contain file '${path}'")
 | 
				
			||||||
 | 
					    return String(stream.readAllBytes())
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  override fun loadAsCharSource(path: String): CharSource {
 | 
				
			||||||
 | 
					    return StringCharSource(read(path))
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  override fun stableContentIdentity(path: String): String {
 | 
				
			||||||
 | 
					    return path
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
							
								
								
									
										5
									
								
								stdlib/src/main/pork/ffi/malloc.pork
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										5
									
								
								stdlib/src/main/pork/ffi/malloc.pork
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,5 @@
 | 
				
			|||||||
 | 
					export func malloc(size)
 | 
				
			||||||
 | 
					  native ffi "c:malloc:void*"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					export func free(pointer)
 | 
				
			||||||
 | 
					  native ffi "c:free:void"
 | 
				
			||||||
							
								
								
									
										15
									
								
								stdlib/src/main/pork/numbers.pork
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										15
									
								
								stdlib/src/main/pork/numbers.pork
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,15 @@
 | 
				
			|||||||
 | 
					export func add(a, b) {
 | 
				
			||||||
 | 
					  a + b
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					export func subtract(a, b) {
 | 
				
			||||||
 | 
					  a - b
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					export func multiply(a, b) {
 | 
				
			||||||
 | 
					  a * b
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					export func divide(a, b) {
 | 
				
			||||||
 | 
					  a / b
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
							
								
								
									
										1
									
								
								stdlib/src/main/pork/stdlib.manifest
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										1
									
								
								stdlib/src/main/pork/stdlib.manifest
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1 @@
 | 
				
			|||||||
 | 
					numbers.pork
 | 
				
			||||||
@ -10,6 +10,7 @@ dependencies {
 | 
				
			|||||||
  api(project(":parser"))
 | 
					  api(project(":parser"))
 | 
				
			||||||
  api(project(":frontend"))
 | 
					  api(project(":frontend"))
 | 
				
			||||||
  api(project(":evaluator"))
 | 
					  api(project(":evaluator"))
 | 
				
			||||||
 | 
					  api(project(":stdlib"))
 | 
				
			||||||
  api(project(":ffi"))
 | 
					  api(project(":ffi"))
 | 
				
			||||||
  api("com.github.ajalt.clikt:clikt:4.2.0")
 | 
					  api("com.github.ajalt.clikt:clikt:4.2.0")
 | 
				
			||||||
  implementation(project(":common"))
 | 
					  implementation(project(":common"))
 | 
				
			||||||
 | 
				
			|||||||
@ -1,16 +1,17 @@
 | 
				
			|||||||
package gay.pizza.pork.tool
 | 
					package gay.pizza.pork.tool
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import gay.pizza.pork.ast.NodeVisitor
 | 
					 | 
				
			||||||
import gay.pizza.pork.parser.Printer
 | 
					 | 
				
			||||||
import gay.pizza.pork.ast.CompilationUnit
 | 
					import gay.pizza.pork.ast.CompilationUnit
 | 
				
			||||||
 | 
					import gay.pizza.pork.ast.NodeVisitor
 | 
				
			||||||
import gay.pizza.pork.ast.visit
 | 
					import gay.pizza.pork.ast.visit
 | 
				
			||||||
import gay.pizza.pork.evaluator.Arguments
 | 
					 | 
				
			||||||
import gay.pizza.pork.evaluator.CallableFunction
 | 
					import gay.pizza.pork.evaluator.CallableFunction
 | 
				
			||||||
import gay.pizza.pork.evaluator.Evaluator
 | 
					import gay.pizza.pork.evaluator.Evaluator
 | 
				
			||||||
import gay.pizza.pork.evaluator.Scope
 | 
					import gay.pizza.pork.evaluator.Scope
 | 
				
			||||||
import gay.pizza.pork.frontend.ContentSource
 | 
					import gay.pizza.pork.frontend.ContentSource
 | 
				
			||||||
 | 
					import gay.pizza.pork.frontend.ImportLocator
 | 
				
			||||||
 | 
					import gay.pizza.pork.frontend.StandardImportSource
 | 
				
			||||||
import gay.pizza.pork.frontend.World
 | 
					import gay.pizza.pork.frontend.World
 | 
				
			||||||
import gay.pizza.pork.parser.*
 | 
					import gay.pizza.pork.parser.*
 | 
				
			||||||
 | 
					import gay.pizza.pork.stdlib.PorkStdlib
 | 
				
			||||||
 | 
					
 | 
				
			||||||
abstract class Tool {
 | 
					abstract class Tool {
 | 
				
			||||||
  abstract fun createCharSource(): CharSource
 | 
					  abstract fun createCharSource(): CharSource
 | 
				
			||||||
@ -31,11 +32,13 @@ abstract class Tool {
 | 
				
			|||||||
  fun <T> visit(visitor: NodeVisitor<T>): T = visitor.visit(parse())
 | 
					  fun <T> visit(visitor: NodeVisitor<T>): T = visitor.visit(parse())
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  fun loadMainFunction(scope: Scope, setupEvaluator: Evaluator.() -> Unit = {}): CallableFunction {
 | 
					  fun loadMainFunction(scope: Scope, setupEvaluator: Evaluator.() -> Unit = {}): CallableFunction {
 | 
				
			||||||
    val contentSource = createContentSource()
 | 
					    val fileContentSource = createContentSource()
 | 
				
			||||||
    val world = World(contentSource)
 | 
					    val standardImportSource = StandardImportSource(fileContentSource)
 | 
				
			||||||
 | 
					    standardImportSource.addContentSource("std", PorkStdlib)
 | 
				
			||||||
 | 
					    val world = World(standardImportSource)
 | 
				
			||||||
    val evaluator = Evaluator(world, scope)
 | 
					    val evaluator = Evaluator(world, scope)
 | 
				
			||||||
    setupEvaluator(evaluator)
 | 
					    setupEvaluator(evaluator)
 | 
				
			||||||
    val resultingScope = evaluator.evaluate(rootFilePath())
 | 
					    val resultingScope = evaluator.evaluate(ImportLocator(rootFilePath()))
 | 
				
			||||||
    return resultingScope.value("main") as CallableFunction
 | 
					    return resultingScope.value("main") as CallableFunction
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user