Added two examples showing the machine in action

This commit is contained in:
Sasha Koshka 2022-08-29 01:10:04 -04:00
parent b0b055d6ce
commit 810ecdb3ac
2 changed files with 182 additions and 0 deletions

40
examples/echo.go Normal file
View File

@ -0,0 +1,40 @@
// +build ignore
package main
import "os"
import cre "git.tebibyte.media/sashakoshka/creature"
func main () {
// this is a simple echo program. it will take in input indefinetly and
// repeat it. due to line buffering in the terminal however, it will
// only print output once you have pressed enter.
machine := cre.Machine { Program: []int {
cre.PUSH, 0,
cre.CAL,
cre.PUSH, 1,
cre.CAL,
cre.PUSH, 1,
cre.PUSH, 0,
cre.JMP,
}}
machine.Register (0, read)
machine.Register (1, write)
err := machine.Execute(0)
if err != nil { panic(err.Error()) }
}
func read (machine *cre.Machine) (stop bool) {
ch := []byte { 0 }
os.Stdin.Read(ch)
machine.Push(int(ch[0]))
return
}
func write (machine *cre.Machine) (stop bool) {
print(string(rune(machine.Pop())))
return
}

142
examples/psychiatrist.go Normal file
View File

@ -0,0 +1,142 @@
// +build ignore
package main
import "os"
import cre "git.tebibyte.media/sashakoshka/creature"
func main () {
// this is an "ai psychiatrist" program. when it starts, it asks the
// user "What brings you in today?", and no matter what the user types,
// the program will respond with "And how does that make you feel?".
// this is a crude re-implementation of a program i used on macos at one
// point.
// constant address values
x := 0
introStart := 1
introLoopStart := 5
readLoopStart := 36
responseStart := 71
responseLoopStart := 50
machine := cre.Machine { Program: []int {
// reset x
cre.PUSH, introStart,
cre.PUSH, x,
cre.POKE,
// INTRO LOOP START
// get char
cre.PUSH, x,
cre.PEEK,
cre.PEEK,
// break if char is equal to zero
cre.PUSH, 0,
cre.EQ,
cre.PUSH, readLoopStart,
cre.JMP,
// get char
cre.PUSH, x,
cre.PEEK,
cre.PEEK,
// call write function
cre.PUSH, 1,
cre.CAL,
// increment x
cre.PUSH, x,
cre.PEEK,
cre.PUSH, 1,
cre.ADD,
cre.PUSH, x,
cre.POKE,
// loop
cre.PUSH, 1,
cre.PUSH, introLoopStart,
cre.JMP,
// INTRO LOOP END / READ LOOP START
// wait until the user presses enter
cre.PUSH, 0,
cre.CAL,
cre.PUSH, int('\n'),
cre.NEQ,
cre.PUSH, readLoopStart,
cre.JMP,
// reset x
cre.PUSH, responseStart,
cre.PUSH, x,
cre.POKE,
// RESPONSE LOOP START
// get char
cre.PUSH, x,
cre.PEEK,
cre.PEEK,
// if the char is zero, we have finished printing and can once
// again prompt the user for an answer
cre.PUSH, 0,
cre.EQ,
cre.PUSH, readLoopStart,
cre.JMP,
// get char
cre.PUSH, x,
cre.PEEK,
cre.PEEK,
// call write function
cre.PUSH, 1,
cre.CAL,
// increment x
cre.PUSH, x,
cre.PEEK,
cre.PUSH, 1,
cre.ADD,
cre.PUSH, x,
cre.POKE,
// loop
cre.PUSH, 1,
cre.PUSH, responseLoopStart,
cre.JMP,
}}
stringData := []byte (
"\x00" +
"== Artificial Intelligence Psychiatrist ==\n" +
"What brings you in today?\n\x00" +
"And how does that make you feel?\n\x00")
block := make([]int, len(stringData))
for index, char := range stringData {
block[index] = int(char)
}
machine.LoadMemory(block)
machine.Register (0, read)
machine.Register (1, write)
err := machine.Execute(0)
if err != nil { panic(err.Error()) }
}
func read (machine *cre.Machine) (stop bool) {
ch := []byte { 0 }
os.Stdin.Read(ch)
machine.Push(int(ch[0]))
return
}
func write (machine *cre.Machine) (stop bool) {
print(string(rune(machine.Pop())))
return
}