comparison interps/whirl/whirlinterp.py @ 996:859f9b4339e6

<Gregor> tar xf egobot.tar.xz
author HackBot
date Sun, 09 Dec 2012 19:30:08 +0000
parents
children
comparison
equal deleted inserted replaced
995:6883f5911eb7 996:859f9b4339e6
1 #!/usr/bin/env python
2 import sys
3 global OPS,MEMORY,PC, MC
4 OPS = []
5 PC = 0
6 MC = 0
7 MEMORY = [0]
8 class OpRing:
9 def __init__(self):
10 self.currentop = 0
11 self.opring = ["NOOP","EXIT","ONE","ZERO","LOAD","STORE","PADD","DADD","LOGIC","IF","INTIO","ASCIO"]
12 self.val = 0
13 self.direction = 0
14 pass
15 def ROTATE(s):
16 if s.direction == 0:
17 s.currentop = (s.currentop + 1) % 12
18 elif s.direction == 1:
19 s.currentop = (s.currentop -1) % 12
20 else:
21 print "Error in ROTATE. self.direction not 0/1."
22 def FLIP(s):
23 s.direction = s.direction ^ 1
24 return s.direction
25 def EXEC(self):
26 global MEMORY,MC,PC,OPS
27 t = self.opring[self.currentop]
28
29 if t == "NOOP":
30 pass
31
32 elif t == "EXIT":
33 return "EXIT"
34
35 elif t == "ONE":
36 self.val = 1
37
38 elif t == "ZERO":
39 self.val = 0
40
41 elif t == "LOAD":
42 self.val = MEMORY[MC]
43
44 elif t == "STORE":
45 MEMORY[MC] = self.val
46
47 elif t == "PADD":
48 PC += self.val - 1
49 if PC < -1:
50 PC = -1
51 elif len(OPS) < PC:
52 return "EXIT"
53
54
55 elif t == "DADD":
56 MC += self.val
57 if MC < 0:
58 MC = 0
59 while len(MEMORY) <= MC:
60 MEMORY.append(0)
61
62 elif t == "LOGIC":
63 if MEMORY[MC] == 0:
64 self.val = 0
65 else:
66 self.val = (self.val and 1)
67
68 elif t == "IF":
69 if MEMORY[MC] != 0:
70 PC += (self.val-1)
71 if PC < -1:
72 PC = -1
73 elif len(OPS) < PC:
74 return "EXIT"
75
76 elif t == "INTIO":
77 if self.val == 0:
78 MEMORY[MC] = int(raw_input("Please enter an integer: "))
79 else:
80 return MEMORY[MC]
81 elif t == "ASCIO":
82 if self.val == 0:
83 MEMORY[MC] = raw_input("Please enter a character: ")[0]
84 else:
85 try:
86 return chr(MEMORY[MC])
87 except TypeError:
88 return MEMORY[MC]
89 def GETCURRENTOP(self):
90 return self.opring[self.currentop]
91
92 class MathRing:
93 global MEMORY,PC, MC
94 def __init__(self):
95 self.opring = ["NOOP","LOAD","STORE","ADD","MULT","DIV","ZERO","<",">","=","NOT","NEG"]
96 self.val = 0
97 self.currentop = 0
98 self.direction = 0
99 def ROTATE(s):
100 if s.direction == 0:
101 s.currentop = (s.currentop + 1) % 12
102 elif s.direction == 1:
103 s.currentop = (s.currentop -1) % 12
104 else:
105 print "Error in ROTATE. self.direction not 0/1."
106 def FLIP(s):
107 s.direction = s.direction ^ 1
108 return s.direction
109 def EXEC(self):
110 t = self.opring[self.currentop]
111
112 if t == "NOOP":
113 pass
114
115 elif t == "LOAD":
116 self.val = MEMORY[MC]
117
118 elif t == "STORE":
119 MEMORY[MC] = self.val
120
121 elif t == "ADD":
122 self.val += MEMORY[MC]
123
124 elif t == "MULT":
125 self.val *= MEMORY[MC]
126
127 elif t == "DIV":
128 if MEMORY[MC] != 0:
129 self.val /= MEMORY[MC]
130 else:
131 print "Attempted to divide by zero. Value in Math Ring unchanged."
132
133 elif t == "ZERO":
134 self.val = 0
135
136 elif t == "<":
137 self.val = (self.val < MEMORY[MC])
138
139 elif t == ">":
140 self.val = (self.val > MEMORY[MC])
141
142 elif t == "=":
143 self.val = (self.val == MEMORY[MC])
144
145 elif t == "NOT":
146 self.val = (self.val == 0)
147
148 elif t == "NEG":
149 self.val *= -1
150
151 def main():
152 global OPS,MEMORY,PC, MC
153
154 opring = OpRing()
155 mathring = MathRing()
156 rings = {"OPRING":opring,"MATHRING":mathring}
157 if len(sys.argv) < 2:
158 print "Must specify a filename as the argument. eg: python whirlinterp.py filename.txt"
159 raise SystemExit
160 filename = sys.argv[1]
161 f = file(filename,'r')
162 text = f.readlines()
163 f.close()
164 for line in text:
165 for char in line:
166 if char in ['0','1']:
167 OPS.append(char)
168 previousop = 3
169 current = "OPRING"
170 outputtext = ""
171 while PC < len(OPS):
172 if OPS[PC] == "0":
173 rings[current].FLIP()
174 if previousop == 0:
175 text = rings[current].EXEC()
176 if text == "EXIT":
177 print outputtext
178 raise SystemExit
179 elif text != None:
180 try:
181 sys.stdout.write(text)
182 except TypeError:
183 sys.stdout.write(str(text))
184
185 if current == "OPRING":
186 current = "MATHRING"
187 elif current == "MATHRING":
188 current = "OPRING"
189
190 previousop = 1
191 else:
192 previousop = 0
193
194 elif OPS[PC] == "1":
195 rings[current].ROTATE()
196 previousop = 1
197 PC += 1
198 print outputtext
199
200 if __name__ == "__main__":
201 main()