1.1 --- a/micropython/trans.py Sun Aug 07 23:01:35 2011 +0200
1.2 +++ b/micropython/trans.py Sun Aug 21 14:24:28 2011 +0200
1.3 @@ -130,8 +130,7 @@
1.4
1.5 after_test_block = self.new_block()
1.6
1.7 - self.new_op(LoadClass(obj))
1.8 - temp_target = self.optimiser.optimise_temp_storage()
1.9 + self.new_op(LoadClass(obj, target="source"))
1.10
1.11 # For only static attributes, classes are acceptable.
1.12
1.13 @@ -140,12 +139,11 @@
1.14 # Generate name is target (for classes).
1.15
1.16 self.dispatch(compiler.ast.Name(name))
1.17 - self.new_op(TestIdentity())
1.18 - self.optimiser.set_source(temp_target)
1.19 + self.new_op(TestIdentity(source="source", target="status"))
1.20
1.21 # Jump to the next guard or the code if successful.
1.22
1.23 - self.new_op(JumpIfTrue(after_test_block))
1.24 + self.new_op(JumpIfTrue(after_test_block, working="status"))
1.25
1.26 # Where instance attributes are involved, only instances are
1.27 # acceptable.
1.28 @@ -153,17 +151,16 @@
1.29 # Generate isinstance(name, target).
1.30
1.31 self.dispatch(compiler.ast.Name(name))
1.32 - self.new_op(CheckInstance())
1.33 - self.optimiser.set_source(temp_target)
1.34 + self.new_op(CheckInstance(source="source", target="status"))
1.35
1.36 # Jump to the next guard or the code if successful.
1.37
1.38 - self.new_op(JumpIfTrue(after_test_block))
1.39 + self.new_op(JumpIfTrue(after_test_block, working="status"))
1.40
1.41 # Where the type is inappropriate, raise an exception.
1.42
1.43 self.make_exception("TypeError")
1.44 - self.new_op(StoreException())
1.45 + self.set_target("exception")
1.46 self.new_op(RaiseException())
1.47
1.48 self.set_block(after_test_block)
1.49 @@ -341,20 +338,20 @@
1.50
1.51 # Remember the accessor.
1.52
1.53 - temp_accessor = self.optimiser.optimise_temp_storage()
1.54 + temp_accessor = self.get_temp()
1.55
1.56 attr_block = self.new_block()
1.57 end_block = self.new_block()
1.58
1.59 - self.new_op(CheckClass())
1.60 - self.new_op(JumpIfFalse(attr_block))
1.61 + self.new_op(CheckClass(target="status"))
1.62 + self.new_op(JumpIfFalse(attr_block, working="status"))
1.63 self.load_builtin("type", node)
1.64 self.new_op(Jump(end_block))
1.65 self.set_block(attr_block)
1.66
1.67 # Recall the accessor.
1.68
1.69 - self.new_op(temp_accessor)
1.70 + self.new_op(temp_accessor.copy())
1.71
1.72 # Otherwise, perform a normal operation.
1.73
1.74 @@ -383,6 +380,7 @@
1.75
1.76 if attrname == "__class__":
1.77 self.set_block(end_block)
1.78 + self.discard_temp(temp_accessor)
1.79
1.80 # Invocations involve the following:
1.81 #
1.82 @@ -451,7 +449,7 @@
1.83
1.84 if target is None or isinstance(context, Instance):
1.85 self.new_op(temp_target)
1.86 - self.new_op(LoadContextIntoValue())
1.87 + self.new_op(Transfer(source="working_context", target="working"))
1.88 temp_context = self.optimiser.optimise_temp_storage()
1.89 self.new_op(StoreFrame(0))
1.90
1.91 @@ -461,7 +459,7 @@
1.92
1.93 elif isinstance(context, Class):
1.94 self.new_op(temp_target)
1.95 - self.new_op(LoadContextIntoValue())
1.96 + self.new_op(Transfer(source="working_context", target="working"))
1.97 temp_context = self.optimiser.optimise_temp_storage()
1.98
1.99 # Otherwise omit the context.
1.100 @@ -759,17 +757,18 @@
1.101 # Adjust the frame if a replaceable context is provided.
1.102
1.103 self.new_op(temp_context)
1.104 - self.new_op(CheckContext())
1.105 - self.new_op(JumpIfFalse(adjust_block))
1.106 + self.new_op(CheckContext(target="status"))
1.107 + self.new_op(JumpIfFalse(adjust_block, working="status"))
1.108
1.109 # Skip adjustment and tests if the context is not a class.
1.110 # Classes themselves employ a placeholder context so that
1.111 # instantiators can be callable with a context which will be
1.112 # overwritten in the frame.
1.113
1.114 - self.new_op(temp_context)
1.115 - self.new_op(CheckClass())
1.116 - self.new_op(JumpIfFalse(continue_block))
1.117 + # Here, the working value should still refer to the context.
1.118 +
1.119 + self.new_op(CheckClass(target="status"))
1.120 + self.new_op(JumpIfFalse(continue_block, working="status"))
1.121
1.122 if temp_first_argument is not None:
1.123 self.new_op(temp_first_argument)
1.124 @@ -777,19 +776,20 @@
1.125 # Check the current value (the argument) against the known context
1.126 # (given as the source).
1.127
1.128 - self.new_op(CheckInstance())
1.129 - self.optimiser.set_source(temp_context)
1.130 + self.new_op(CheckInstance(target="status"))
1.131 + self.set_working(temp_context)
1.132
1.133 - self.new_op(JumpIfTrue(adjust_block))
1.134 + self.new_op(JumpIfTrue(adjust_block, working="status"))
1.135
1.136 # Where the context is inappropriate, drop the incomplete frame and
1.137 # raise an exception.
1.138
1.139 self.new_op(DropFrame())
1.140 - self.new_op(LoadResultIntoValue())
1.141 + self.new_op(Transfer(source="result", target="working"))
1.142 + self.new_op(Transfer(source="result_context", target="working_context"))
1.143
1.144 self.make_exception("TypeError")
1.145 - self.new_op(StoreException())
1.146 + self.set_target("exception")
1.147 self.new_op(RaiseException())
1.148
1.149 if target is None or temp_first_argument is not None:
1.150 @@ -806,7 +806,7 @@
1.151 # obtained via the class.
1.152
1.153 if isinstance(target, (Class, Function)):
1.154 - self.new_op(JumpWithFrameDirect(target))
1.155 + self.new_op(JumpWithFrameDirect(target, working="status"))
1.156 else:
1.157 self.new_op(temp_target)
1.158 self.new_op(LoadCallable())
1.159 @@ -825,7 +825,8 @@
1.160
1.161 self.new_op(DropFrame())
1.162 if load_result:
1.163 - self.new_op(LoadResultIntoValue())
1.164 + self.new_op(Transfer(source="result", target="working"))
1.165 + self.new_op(Transfer(source="result_context", target="working_context"))
1.166
1.167 # Discard any temporary storage instructions.
1.168
1.169 @@ -851,9 +852,9 @@
1.170
1.171 if temp is not None:
1.172 self.new_op(LoadConst(fn))
1.173 - self.new_op(LoadCallable())
1.174 + self.new_op(LoadCallable(target="source"))
1.175 self.new_op(temp)
1.176 - self.new_op(StoreCallable())
1.177 + self.new_op(StoreCallable(source="source"))
1.178
1.179 self.new_op(temp)
1.180 #self.discard_temp(temp)
1.181 @@ -878,7 +879,7 @@
1.182
1.183 # Check the number of parameters and defaults.
1.184
1.185 - self.new_op(CheckFrame((nparams, ndefaults)))
1.186 + self.new_op(CheckFrame((nparams, ndefaults), target="status"))
1.187
1.188 if ndefaults > 0:
1.189 if fn.is_dynamic():
1.190 @@ -900,7 +901,7 @@
1.191
1.192 # Ensure that the star parameter has a slot in the frame.
1.193
1.194 - self.new_op(CheckExtra(nparams))
1.195 + self.new_op(CheckExtra(nparams, target="status"))
1.196 self.new_op(StoreTemp(nparams))
1.197
1.198 # Extend the frame for local usage.
1.199 @@ -930,7 +931,12 @@
1.200 if not fn.is_lambda():
1.201 self.dispatch(compiler.ast.Name("None"))
1.202
1.203 - self.new_op(LoadValueIntoResult())
1.204 + # NOTE: Cannot guarantee that all active instructions can be set.
1.205 + #self.set_target("result")
1.206 +
1.207 + self.new_op(Transfer(source="working", target="result"))
1.208 + self.new_op(Transfer(source="working_context", target="result_context"))
1.209 +
1.210 self.new_op(Return())
1.211
1.212 # Make sure that enough frame space is reserved from the start.
1.213 @@ -1016,7 +1022,7 @@
1.214 self.discard_value()
1.215
1.216 if dynamic:
1.217 - return temp
1.218 + return temp.copy()
1.219 else:
1.220 return None
1.221
1.222 @@ -1199,8 +1205,8 @@
1.223
1.224 if not (self.optimiser.should_optimise_known_target() and self.optimiser.is_constant_input(temp_method)):
1.225 self.load_builtin("AttributeError", node)
1.226 - self.new_op(CheckException())
1.227 - self.new_op(JumpIfTrue(handled_block))
1.228 + self.new_op(CheckException(target="status"))
1.229 + self.new_op(JumpIfTrue(handled_block, working="status"))
1.230 self.new_op(RaiseException())
1.231
1.232 def _generateTuple(self, node):
1.233 @@ -1216,7 +1222,7 @@
1.234
1.235 self._populateSequence(temp, node)
1.236
1.237 - self.new_op(temp)
1.238 + self.new_op(temp.copy())
1.239 self.discard_temp(temp)
1.240
1.241 def _generateList(self, node):
1.242 @@ -1240,7 +1246,7 @@
1.243 self.set_source()
1.244 self.discard_value()
1.245
1.246 - self.new_op(list_temp)
1.247 + self.new_op(list_temp.copy())
1.248 self.discard_temp(temp)
1.249 self.discard_temp(list_temp)
1.250
1.251 @@ -1286,7 +1292,7 @@
1.252
1.253 # Convert result to boolean (a StoreBoolean operation).
1.254
1.255 - self.new_op(TestIdentityAddress(self.importer.get_predefined_constant("True")))
1.256 + self.new_op(TestIdentityAddress(self.importer.get_predefined_constant("True"), target="status"))
1.257
1.258 def _generateLoadBoolean(self, node):
1.259
1.260 @@ -1298,7 +1304,7 @@
1.261 true_block = self.new_block()
1.262 end_block = self.new_block()
1.263
1.264 - self.new_op(JumpIfTrue(true_block))
1.265 + self.new_op(JumpIfTrue(true_block, working="status"))
1.266 self.new_op(LoadConst(self.importer.get_predefined_constant("False")))
1.267 self.new_op(Jump(end_block))
1.268