1.1 --- a/rsvplib.py Sat Oct 10 01:52:27 2009 +0200
1.2 +++ b/rsvplib.py Sat Oct 10 03:09:29 2009 +0200
1.3 @@ -19,6 +19,7 @@
1.4 this program. If not, see <http://www.gnu.org/licenses/>.
1.5 """
1.6
1.7 +from micropython.program import DataValue
1.8 import operator
1.9
1.10 class Library:
1.11 @@ -62,20 +63,22 @@
1.12
1.13 # Get operands addresses.
1.14
1.15 - left_context, left = self.frame_stack[frame]
1.16 - right_context, right = self.frame_stack[frame + 1]
1.17 + left_value = self.frame_stack[frame]
1.18 + right_value = self.frame_stack[frame + 1]
1.19
1.20 # Test operand suitability.
1.21 # NOTE: Support other types.
1.22
1.23 - if not (self.machine._CheckInstance(left, self.int_class) and self.machine._CheckInstance(right, self.int_class)):
1.24 + if not (self.machine._CheckInstance(left_value.ref, self.int_class) and
1.25 + self.machine._CheckInstance(right_value.ref, self.int_class)):
1.26 +
1.27 self.machine.exception = self.machine._MakeObject(2, self.type_error_instance)
1.28 return self.machine.RaiseException()
1.29
1.30 # NOTE: Assume single location for data.
1.31
1.32 - left_data = left + 1
1.33 - right_data = right + 1
1.34 + left_data = left_value.ref + 1
1.35 + right_data = right_value.ref + 1
1.36
1.37 # Make a new object.
1.38
1.39 @@ -89,38 +92,40 @@
1.40 # Return the new object.
1.41 # Introduce object as context for the new object.
1.42
1.43 - self.machine.result = addr, addr
1.44 + self.machine.result = DataValue(addr, addr)
1.45
1.46 def builtins_logical_op(self, operand_class, op, true_if_incompatible):
1.47 frame = self.local_sp_stack[-1]
1.48
1.49 # Get operands addresses.
1.50
1.51 - left_context, left = self.frame_stack[frame]
1.52 - right_context, right = self.frame_stack[frame + 1]
1.53 + left_value = self.frame_stack[frame]
1.54 + right_value = self.frame_stack[frame + 1]
1.55
1.56 # Test operand suitability.
1.57 # NOTE: Handle comparisons of incompatible types more appropriately.
1.58
1.59 - if not (self.machine._CheckInstance(left, operand_class) and self.machine._CheckInstance(right, operand_class)):
1.60 + if not (self.machine._CheckInstance(left_value.ref, operand_class) and
1.61 + self.machine._CheckInstance(right_value.ref, operand_class)):
1.62 +
1.63 if true_if_incompatible:
1.64 - self.machine.result = self.true_constant, self.true_constant
1.65 + self.machine.result = DataValue(self.true_constant, self.true_constant)
1.66 else:
1.67 - self.machine.result = self.false_constant, self.false_constant
1.68 + self.machine.result = DataValue(self.false_constant, self.false_constant)
1.69 return
1.70
1.71 # NOTE: Assume single location for data.
1.72
1.73 - left_data = left + 1
1.74 - right_data = right + 1
1.75 + left_data = left_value.ref + 1
1.76 + right_data = right_value.ref + 1
1.77
1.78 # Test the data.
1.79 # NOTE: The data is considered ready to use.
1.80
1.81 if op(self.machine.load(left_data), self.machine.load(right_data)):
1.82 - self.machine.result = self.true_constant, self.true_constant
1.83 + self.machine.result = DataValue(self.true_constant, self.true_constant)
1.84 else:
1.85 - self.machine.result = self.false_constant, self.false_constant
1.86 + self.machine.result = DataValue(self.false_constant, self.false_constant)
1.87
1.88 # Operators.
1.89 # Although this takes a short-cut by using the operator module, testing is
1.90 @@ -185,42 +190,42 @@
1.91
1.92 # Get operands addresses.
1.93
1.94 - left_context, left = self.frame_stack[frame]
1.95 + left_value = self.frame_stack[frame]
1.96
1.97 # Test operand suitability.
1.98
1.99 - if not self.machine._CheckInstance(left, self.int_class):
1.100 + if not self.machine._CheckInstance(left_value.ref, self.int_class):
1.101 self.machine.exception = self.machine._MakeObject(2, self.type_error_instance)
1.102 return self.machine.RaiseException()
1.103
1.104 # NOTE: Assume single location for data.
1.105
1.106 - left_data = left + 1
1.107 + left_data = left_value.ref + 1
1.108
1.109 # Test the data.
1.110 # NOTE: The data is considered ready to use.
1.111
1.112 if self.machine.load(left_data) != 0:
1.113 - self.machine.result = self.true_constant, self.true_constant
1.114 + self.machine.result = DataValue(self.true_constant, self.true_constant)
1.115 else:
1.116 - self.machine.result = self.false_constant, self.false_constant
1.117 + self.machine.result = DataValue(self.false_constant, self.false_constant)
1.118
1.119 def builtins_int_neg(self):
1.120 frame = self.local_sp_stack[-1]
1.121
1.122 # Get operands addresses.
1.123
1.124 - left_context, left = self.frame_stack[frame]
1.125 + left_value = self.frame_stack[frame]
1.126
1.127 # Test operand suitability.
1.128
1.129 - if not self.machine._CheckInstance(left, self.int_class):
1.130 + if not self.machine._CheckInstance(left_value.ref, self.int_class):
1.131 self.machine.exception = self.machine._MakeObject(2, self.type_error_instance)
1.132 return self.machine.RaiseException()
1.133
1.134 # NOTE: Assume single location for data.
1.135
1.136 - left_data = left + 1
1.137 + left_data = left_value.ref + 1
1.138
1.139 # Make a new object.
1.140
1.141 @@ -234,7 +239,7 @@
1.142 # Return the new object.
1.143 # Introduce object as context for the new object.
1.144
1.145 - self.machine.result = addr, addr
1.146 + self.machine.result = DataValue(addr, addr)
1.147
1.148 # Various built-in methods.
1.149
1.150 @@ -243,8 +248,8 @@
1.151
1.152 # Get operands addresses.
1.153
1.154 - left_context, left = self.frame_stack[frame]
1.155 - self.machine.result = left, left
1.156 + left_value = self.frame_stack[frame]
1.157 + self.machine.result = DataValue(left_value.ref, left_value.ref)
1.158
1.159 def builtins_list_new(self):
1.160 frame = self.local_sp_stack[-1]
1.161 @@ -252,16 +257,16 @@
1.162 # The first parameter should be empty.
1.163 # NOTE: Specific copying of tuples/lists.
1.164
1.165 - args_context, args = self.frame_stack[frame + 1]
1.166 + args_value = self.frame_stack[frame + 1]
1.167
1.168 # Test operand suitability.
1.169
1.170 - if self.machine._CheckInstance(args, self.list_class):
1.171 - _x, sequence = self.machine.load(args + 1)
1.172 - header = self.machine.load(sequence)
1.173 + if self.machine._CheckInstance(args_value.ref, self.list_class):
1.174 + sequence = self.machine.load(args_value.ref + 1)
1.175 + header = self.machine.load(sequence.ref)
1.176 size = header.occupied_size
1.177 - elif self.machine._CheckInstance(args, self.tuple_class):
1.178 - sequence = args
1.179 + elif self.machine._CheckInstance(args_value.ref, self.tuple_class):
1.180 + sequence = args_value.ref
1.181 header = self.machine.load(sequence)
1.182 size = header.size
1.183 else:
1.184 @@ -277,34 +282,34 @@
1.185 # Make the list instance.
1.186
1.187 addr = self.machine._MakeObject(2, self.list_instance)
1.188 - self.machine.save(addr + 1, (None, new_fragment))
1.189 + self.machine.save(addr + 1, DataValue(None, new_fragment))
1.190
1.191 - self.machine.result = addr, addr
1.192 + self.machine.result = DataValue(addr, addr)
1.193
1.194 def builtins_list_getitem(self):
1.195 frame = self.local_sp_stack[-1]
1.196
1.197 # Get the operand address.
1.198
1.199 - item_context, item = self.frame_stack[frame + 1]
1.200 + item_value = self.frame_stack[frame + 1]
1.201
1.202 # Get the list address.
1.203
1.204 - obj_context, obj = self.frame_stack[frame]
1.205 + obj_value = self.frame_stack[frame]
1.206
1.207 # Get the fragment address.
1.208 # NOTE: Assume single location for header.
1.209
1.210 - _x, fragment = self.machine.load(obj + 1)
1.211 + fragment = self.machine.load(obj_value.ref + 1)
1.212
1.213 # Get the fragment header.
1.214
1.215 - header = self.machine.load(fragment)
1.216 + header = self.machine.load(fragment.ref)
1.217 nelements = header.occupied_size - 1
1.218
1.219 # NOTE: Assume single location for data and header.
1.220
1.221 - item_pos = self.machine.load(item + 1)
1.222 + item_pos = self.machine.load(item_value.ref + 1)
1.223
1.224 if item_pos >= 0 and item_pos < nelements:
1.225 pass
1.226 @@ -316,23 +321,23 @@
1.227
1.228 # NOTE: Assume single location for header.
1.229
1.230 - self.machine.result = self.machine.load(fragment + 1 + item_pos)
1.231 + self.machine.result = self.machine.load(fragment.ref + 1 + item_pos)
1.232
1.233 def builtins_list_len(self):
1.234 frame = self.local_sp_stack[-1]
1.235
1.236 # Get the list address.
1.237
1.238 - obj_context, obj = self.frame_stack[frame]
1.239 + obj_value = self.frame_stack[frame]
1.240
1.241 # Get the fragment address.
1.242 # NOTE: Assume single location for header.
1.243
1.244 - _x, fragment = self.machine.load(obj + 1)
1.245 + fragment = self.machine.load(obj_value.ref + 1)
1.246
1.247 # Get the fragment header.
1.248
1.249 - header = self.machine.load(fragment)
1.250 + header = self.machine.load(fragment.ref)
1.251 nelements = header.occupied_size - 1
1.252
1.253 # Make a new object.
1.254 @@ -347,32 +352,32 @@
1.255 # Return the new object.
1.256 # Introduce object as context for the new object.
1.257
1.258 - self.machine.result = addr, addr
1.259 + self.machine.result = DataValue(addr, addr)
1.260
1.261 def builtins_list_append(self):
1.262 frame = self.local_sp_stack[-1]
1.263
1.264 # Get operand address.
1.265
1.266 - arg_context, arg = self.frame_stack[frame + 1]
1.267 + arg_value = self.frame_stack[frame + 1]
1.268
1.269 # Get the list address.
1.270
1.271 - obj_context, obj = self.frame_stack[frame]
1.272 + obj_value = self.frame_stack[frame]
1.273
1.274 # Get the fragment address.
1.275 # NOTE: Assume single location for header.
1.276
1.277 - _x, fragment = self.machine.load(obj + 1)
1.278 + fragment = self.machine.load(obj_value.ref + 1)
1.279
1.280 # Get the fragment header.
1.281
1.282 - header = self.machine.load(fragment)
1.283 + header = self.machine.load(fragment.ref)
1.284
1.285 # Attempt to add the reference.
1.286
1.287 if header.occupied_size < header.allocated_size:
1.288 - self.machine.save(fragment + header.occupied_size, (arg_context, arg))
1.289 + self.machine.save(fragment.ref + header.occupied_size, arg_value)
1.290 header.occupied_size += 1
1.291 else:
1.292
1.293 @@ -384,26 +389,26 @@
1.294 # Copy existing elements.
1.295
1.296 for i in range(1, header.allocated_size):
1.297 - self.machine.save(new_fragment + i, self.machine.load(fragment + i))
1.298 + self.machine.save(new_fragment + i, self.machine.load(fragment.ref + i))
1.299
1.300 - self.machine.save(new_fragment + header.allocated_size, (arg_context, arg))
1.301 + self.machine.save(new_fragment + header.allocated_size, arg_value)
1.302
1.303 # Set the new fragment in the object.
1.304 # NOTE: The old fragment could be deallocated.
1.305
1.306 - self.machine.save(obj + 1, (None, new_fragment))
1.307 + self.machine.save(obj_value.ref + 1, DataValue(None, new_fragment))
1.308
1.309 def builtins_tuple_len(self):
1.310 frame = self.local_sp_stack[-1]
1.311
1.312 # Get the tuple address.
1.313
1.314 - obj_context, obj = self.frame_stack[frame]
1.315 + obj_value = self.frame_stack[frame]
1.316
1.317 # Get the header.
1.318 # NOTE: Assume single location for header.
1.319
1.320 - header = self.machine.load(obj)
1.321 + header = self.machine.load(obj_value.ref)
1.322 nelements = header.size - 1
1.323
1.324 # Make a new object.
1.325 @@ -418,28 +423,28 @@
1.326 # Return the new object.
1.327 # Introduce object as context for the new object.
1.328
1.329 - self.machine.result = addr, addr
1.330 + self.machine.result = DataValue(addr, addr)
1.331
1.332 def builtins_tuple_getitem(self):
1.333 frame = self.local_sp_stack[-1]
1.334
1.335 # Get the operand address.
1.336
1.337 - item_context, item = self.frame_stack[frame + 1]
1.338 + item_value = self.frame_stack[frame + 1]
1.339
1.340 # Get the tuple address.
1.341
1.342 - obj_context, obj = self.frame_stack[frame]
1.343 + obj_value = self.frame_stack[frame]
1.344
1.345 # Get the header.
1.346 # NOTE: Assume single location for header.
1.347
1.348 - header = self.machine.load(obj)
1.349 + header = self.machine.load(obj_value.ref)
1.350 nelements = header.size - 1
1.351
1.352 # NOTE: Assume single location for data and header.
1.353
1.354 - item_pos = self.machine.load(item + 1)
1.355 + item_pos = self.machine.load(item_value.ref + 1)
1.356
1.357 if item_pos >= 0 and item_pos < nelements:
1.358 pass
1.359 @@ -451,7 +456,7 @@
1.360
1.361 # NOTE: Assume single location for header.
1.362
1.363 - self.machine.result = self.machine.load(obj + 1 + item_pos)
1.364 + self.machine.result = self.machine.load(obj_value.ref + 1 + item_pos)
1.365
1.366 def builtins_object_init(self):
1.367 pass