Example #1
0
 def init(self) -> None:
     builder = self.builder
     # Create a register to store the state of the loop index and
     # initialize this register along with the loop index to 0.
     zero = builder.add(LoadInt(0))
     self.index_reg = builder.maybe_spill_assignable(zero)
     self.index_target = builder.get_assignment_target(
         self.index)  # type: Union[Register, AssignmentTarget]
     builder.assign(self.index_target, zero, self.line)
Example #2
0
 def gen_step(self) -> None:
     # Step to the next item.
     builder = self.builder
     line = self.line
     step = 1 if not self.reverse else -1
     builder.assign(self.index_target, builder.primitive_op(
         unsafe_short_add,
         [builder.read(self.index_target, line),
          builder.add(LoadInt(step))], line), line)
Example #3
0
 def begin_body(self) -> None:
     # Assign the value obtained from __next__ to the
     # lvalue so that it can be referenced by code in the body of the loop.
     builder = self.builder
     line = self.line
     # We unbox here so that iterating with tuple unpacking generates a tuple based
     # unpack instead of an iterator based one.
     next_reg = builder.coerce(self.next_reg, self.target_type, line)
     builder.assign(builder.get_assignment_target(self.index), next_reg, line)
Example #4
0
 def gen_step(self) -> None:
     builder = self.builder
     line = self.line
     # We can safely assume that the integer is short, since we are not going to wrap
     # around a 63-bit integer.
     # NOTE: This would be questionable if short ints could be 32 bits.
     new_val = builder.primitive_op(
         unsafe_short_add, [builder.read(self.index_reg, line),
                            builder.add(LoadInt(1))], line)
     builder.assign(self.index_reg, new_val, line)
     builder.assign(self.index_target, new_val, line)
Example #5
0
 def init(self, start_reg: Value, end_reg: Value, step: int) -> None:
     builder = self.builder
     self.start_reg = start_reg
     self.end_reg = end_reg
     self.step = step
     self.end_target = builder.maybe_spill(end_reg)
     self.index_reg = builder.maybe_spill_assignable(start_reg)
     # Initialize loop index to 0. Assert that the index target is assignable.
     self.index_target = builder.get_assignment_target(
         self.index)  # type: Union[Register, AssignmentTarget]
     builder.assign(self.index_target, builder.read(self.index_reg, self.line), self.line)
Example #6
0
 def begin_body(self) -> None:
     builder = self.builder
     line = self.line
     # Read the next list item.
     value_box = unsafe_index(builder, builder.read(self.expr_target, line),
                              builder.read(self.index_target, line), line)
     assert value_box
     # We coerce to the type of list elements here so that
     # iterating with tuple unpacking generates a tuple based
     # unpack instead of an iterator based one.
     builder.assign(builder.get_assignment_target(self.index),
                    builder.coerce(value_box, self.target_type, line), line)
Example #7
0
    def gen_step(self) -> None:
        builder = self.builder
        line = self.line

        # Increment index register. If the range is known to fit in short ints, use
        # short ints.
        if (is_short_int_rprimitive(self.start_reg.type)
                and is_short_int_rprimitive(self.end_reg.type)):
            new_val = builder.primitive_op(
                unsafe_short_add, [builder.read(self.index_reg, line),
                                   builder.add(LoadInt(self.step))], line)

        else:
            new_val = builder.binary_op(
                builder.read(self.index_reg, line), builder.add(LoadInt(self.step)), '+', line)
        builder.assign(self.index_reg, new_val, line)
        builder.assign(self.index_target, new_val, line)