Home | History | Annotate | Download | only in optimizing
      1 /*
      2  * Copyright (C) 2016 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 #ifndef ART_COMPILER_OPTIMIZING_NODES_MIPS_H_
     18 #define ART_COMPILER_OPTIMIZING_NODES_MIPS_H_
     19 
     20 namespace art {
     21 
     22 // Compute the address of the method for MIPS Constant area support.
     23 class HMipsComputeBaseMethodAddress : public HExpression<0> {
     24  public:
     25   // Treat the value as an int32_t, but it is really a 32 bit native pointer.
     26   HMipsComputeBaseMethodAddress()
     27       : HExpression(kMipsComputeBaseMethodAddress,
     28                     DataType::Type::kInt32,
     29                     SideEffects::None(),
     30                     kNoDexPc) {
     31   }
     32 
     33   bool CanBeMoved() const OVERRIDE { return true; }
     34 
     35   DECLARE_INSTRUCTION(MipsComputeBaseMethodAddress);
     36 
     37  protected:
     38   DEFAULT_COPY_CONSTRUCTOR(MipsComputeBaseMethodAddress);
     39 };
     40 
     41 // Mips version of HPackedSwitch that holds a pointer to the base method address.
     42 class HMipsPackedSwitch FINAL : public HTemplateInstruction<2> {
     43  public:
     44   HMipsPackedSwitch(int32_t start_value,
     45                     int32_t num_entries,
     46                     HInstruction* input,
     47                     HMipsComputeBaseMethodAddress* method_base,
     48                     uint32_t dex_pc)
     49     : HTemplateInstruction(kMipsPackedSwitch, SideEffects::None(), dex_pc),
     50       start_value_(start_value),
     51       num_entries_(num_entries) {
     52     SetRawInputAt(0, input);
     53     SetRawInputAt(1, method_base);
     54   }
     55 
     56   bool IsControlFlow() const OVERRIDE { return true; }
     57 
     58   int32_t GetStartValue() const { return start_value_; }
     59 
     60   int32_t GetNumEntries() const { return num_entries_; }
     61 
     62   HBasicBlock* GetDefaultBlock() const {
     63     // Last entry is the default block.
     64     return GetBlock()->GetSuccessors()[num_entries_];
     65   }
     66 
     67   DECLARE_INSTRUCTION(MipsPackedSwitch);
     68 
     69  protected:
     70   DEFAULT_COPY_CONSTRUCTOR(MipsPackedSwitch);
     71 
     72  private:
     73   const int32_t start_value_;
     74   const int32_t num_entries_;
     75 };
     76 
     77 // This instruction computes part of the array access offset (index offset).
     78 //
     79 // For array accesses the element address has the following structure:
     80 // Address = CONST_OFFSET + base_addr + index << ELEM_SHIFT. The address part
     81 // (index << ELEM_SHIFT) can be shared across array accesses with
     82 // the same data type and index. For example, in the following loop 5 accesses can share address
     83 // computation:
     84 //
     85 // void foo(int[] a, int[] b, int[] c) {
     86 //   for (i...) {
     87 //     a[i] = a[i] + 5;
     88 //     b[i] = b[i] + c[i];
     89 //   }
     90 // }
     91 //
     92 // Note: as the instruction doesn't involve base array address into computations it has no side
     93 // effects.
     94 class HIntermediateArrayAddressIndex FINAL : public HExpression<2> {
     95  public:
     96   HIntermediateArrayAddressIndex(HInstruction* index, HInstruction* shift, uint32_t dex_pc)
     97       : HExpression(kIntermediateArrayAddressIndex,
     98                     DataType::Type::kInt32,
     99                     SideEffects::None(),
    100                     dex_pc) {
    101     SetRawInputAt(0, index);
    102     SetRawInputAt(1, shift);
    103   }
    104 
    105   bool CanBeMoved() const OVERRIDE { return true; }
    106   bool InstructionDataEquals(const HInstruction* other ATTRIBUTE_UNUSED) const OVERRIDE {
    107     return true;
    108   }
    109   bool IsActualObject() const OVERRIDE { return false; }
    110 
    111   HInstruction* GetIndex() const { return InputAt(0); }
    112   HInstruction* GetShift() const { return InputAt(1); }
    113 
    114   DECLARE_INSTRUCTION(IntermediateArrayAddressIndex);
    115 
    116  protected:
    117   DEFAULT_COPY_CONSTRUCTOR(IntermediateArrayAddressIndex);
    118 };
    119 
    120 }  // namespace art
    121 
    122 #endif  // ART_COMPILER_OPTIMIZING_NODES_MIPS_H_
    123