main.go 1.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131
  1. package main
  2. import (
  3. "fmt"
  4. "io"
  5. "io/ioutil"
  6. "os"
  7. )
  8. type CPU struct {
  9. code []byte
  10. memory [30000]int
  11. filename string
  12. char []byte
  13. counter int
  14. }
  15. func (self *CPU) New(filename string) {
  16. self.filename = filename
  17. self.char = make([]byte, 1)
  18. self.counter = 0
  19. self.ReadFile()
  20. self.Exec()
  21. }
  22. func (self *CPU) ReadFile() {
  23. code, err := ioutil.ReadFile(self.filename)
  24. if err != nil {
  25. fmt.Fprintf(os.Stderr, "error: %s\n", err)
  26. os.Exit(-1)
  27. }
  28. self.code = code
  29. }
  30. func (self *CPU) Input() error {
  31. var input io.Reader
  32. input = os.Stdin
  33. _, err := input.Read(self.char)
  34. self.memory[self.counter] = int(self.char[0])
  35. return err
  36. }
  37. func (self *CPU) Print() error {
  38. self.char[0] = byte(self.memory[self.counter])
  39. var output io.Writer
  40. output = os.Stdout
  41. _, err := output.Write(self.char)
  42. return err
  43. }
  44. func (self CPU) Exec() {
  45. var i int
  46. for i < len(self.code) {
  47. ins := self.code[i]
  48. switch ins {
  49. case '+':
  50. self.memory[self.counter]++
  51. case '-':
  52. self.memory[self.counter]--
  53. case '>':
  54. self.counter = self.counter + 1
  55. case '<':
  56. self.counter = self.counter - 1
  57. case '.':
  58. err := self.Print()
  59. if err != nil {
  60. panic(err)
  61. }
  62. case ',':
  63. err := self.Input()
  64. if err != nil {
  65. panic(err)
  66. }
  67. case '[':
  68. if self.memory[self.counter] == 0 {
  69. depth := 1
  70. for depth != 0 {
  71. i++
  72. switch self.code[i] {
  73. case '[':
  74. depth++
  75. case ']':
  76. depth--
  77. }
  78. }
  79. }
  80. case ']':
  81. if self.memory[self.counter] != 0 {
  82. depth := 1
  83. for depth != 0 {
  84. i--
  85. switch self.code[i] {
  86. case ']':
  87. depth++
  88. case '[':
  89. depth--
  90. }
  91. }
  92. }
  93. }
  94. i++
  95. }
  96. }
  97. func main() {
  98. var filename string
  99. env := os.Args
  100. if(len(env) == 1) {
  101. fmt.Println("no filename")
  102. return
  103. } else {
  104. filename = env[1]
  105. }
  106. cpu := CPU{}
  107. cpu.New(filename)
  108. }