1.1 --- a/micropython/trans.py Sat Nov 07 02:36:33 2009 +0100
1.2 +++ b/micropython/trans.py Mon Nov 16 00:34:47 2009 +0100
1.3 @@ -306,6 +306,56 @@
1.4
1.5 # Common methods.
1.6
1.7 + def _generateGuards(self, node):
1.8 +
1.9 + if not (self.optimiser.should_optimise_accesses_by_attribute_usage() and hasattr(node, "_attrnames")):
1.10 + return
1.11 +
1.12 + # For each name, attempt to restrict the type employed.
1.13 +
1.14 + for name, names_used in node._attrnames.items():
1.15 +
1.16 + # Get the names of all object types supporting these names.
1.17 +
1.18 + target_names = self.objtable.all_possible_objects(names_used)
1.19 +
1.20 + # Where only one object type is suggested, produce a guard.
1.21 + # NOTE: This only supports classes as types, not modules.
1.22 +
1.23 + if len(target_names) == 1:
1.24 + target_name = target_names[0]
1.25 +
1.26 + # Access the object table to get the attribute.
1.27 + # NOTE: This depends on the special entry in the table
1.28 + # NOTE: for class equivalence tests.
1.29 +
1.30 + try:
1.31 + attr = self.objtable.access(target_name, target_name)
1.32 + except TableError, exc:
1.33 + raise TranslateError(self.module.full_name(), node, exc.args[0])
1.34 +
1.35 + after_test_block = self.new_block()
1.36 +
1.37 + # Generate isinstance(name, target).
1.38 +
1.39 + self.new_op(LoadClass(attr))
1.40 + temp_target = self.optimiser.optimise_temp_storage()
1.41 + self.dispatch(compiler.ast.Name(name))
1.42 + self.new_op(CheckSelf()) # NOTE: Should be CheckInstance.
1.43 + self.optimiser.set_source(temp_target)
1.44 +
1.45 + # Jump to the next guard or the code if successful.
1.46 +
1.47 + self.new_op(JumpIfTrue(after_test_block))
1.48 +
1.49 + # Where the type is inappropriate, raise an exception.
1.50 +
1.51 + self.make_exception("TypeError", node)
1.52 + self.new_op(StoreException())
1.53 + self.new_op(RaiseException())
1.54 +
1.55 + self.set_block(after_test_block)
1.56 +
1.57 def _visitAttr(self, node, classes):
1.58
1.59 """
1.60 @@ -424,11 +474,15 @@
1.61 except KeyError:
1.62 pass
1.63
1.64 + # Attempt to deduce the target of an attribute access by searching for a
1.65 + # unique type providing the names associated with the accessed object.
1.66 + # NOTE: This should re-use type information defined at assignment
1.67 + # NOTE: locations.
1.68 +
1.69 elif self.optimiser.should_optimise_accesses_by_attribute_usage():
1.70
1.71 if hasattr(node, "_attrnames"):
1.72 target_names = self.objtable.all_possible_objects(node._attrnames)
1.73 - print self.expr_temp, node._attrnames, "->", target_names
1.74
1.75 if len(target_names) == 1:
1.76 target_name = target_names[0]