ART: Add 16-bit Thumb2 ROR, NEGS and CMP for high registers.

Also clean up the usage of set_cc flag. Define a SetCc
enumeration that specifies whether to set or keep condition
codes or whether we don't care and a 16-bit instruction
should be selected if one exists.

This reduces the size of Nexus 5 boot.oat by 44KiB (when
compiled with Optimizing which is not the default yet).

Change-Id: I047072dc197ea678bf2019c01bcb28943fa9b604
diff --git a/compiler/utils/arm/assembler_arm.h b/compiler/utils/arm/assembler_arm.h
index ef60fef..7825457 100644
--- a/compiler/utils/arm/assembler_arm.h
+++ b/compiler/utils/arm/assembler_arm.h
@@ -375,6 +375,13 @@
   kItE = kItElse
 };
 
+// Set condition codes request.
+enum SetCc {
+  kCcDontCare,  // Allows prioritizing 16-bit instructions on Thumb2 whether they set CCs or not.
+  kCcSet,
+  kCcKeep,
+};
+
 constexpr uint32_t kNoItCondition = 3;
 constexpr uint32_t kInvalidModifiedImmediate = -1;
 
@@ -392,25 +399,61 @@
   virtual bool IsThumb() const = 0;
 
   // Data-processing instructions.
-  virtual void and_(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void and_(Register rd, Register rn, const ShifterOperand& so,
+                    Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
 
-  virtual void eor(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void ands(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) {
+    and_(rd, rn, so, cond, kCcSet);
+  }
 
-  virtual void sub(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
-  virtual void subs(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void eor(Register rd, Register rn, const ShifterOperand& so,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
 
-  virtual void rsb(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
-  virtual void rsbs(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void eors(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) {
+    eor(rd, rn, so, cond, kCcSet);
+  }
 
-  virtual void add(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void sub(Register rd, Register rn, const ShifterOperand& so,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
 
-  virtual void adds(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void subs(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) {
+    sub(rd, rn, so, cond, kCcSet);
+  }
 
-  virtual void adc(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void rsb(Register rd, Register rn, const ShifterOperand& so,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
 
-  virtual void sbc(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void rsbs(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) {
+    rsb(rd, rn, so, cond, kCcSet);
+  }
 
-  virtual void rsc(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void add(Register rd, Register rn, const ShifterOperand& so,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  virtual void adds(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) {
+    add(rd, rn, so, cond, kCcSet);
+  }
+
+  virtual void adc(Register rd, Register rn, const ShifterOperand& so,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  virtual void adcs(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) {
+    adc(rd, rn, so, cond, kCcSet);
+  }
+
+  virtual void sbc(Register rd, Register rn, const ShifterOperand& so,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  virtual void sbcs(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) {
+    sbc(rd, rn, so, cond, kCcSet);
+  }
+
+  virtual void rsc(Register rd, Register rn, const ShifterOperand& so,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  virtual void rscs(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) {
+    rsc(rd, rn, so, cond, kCcSet);
+  }
 
   virtual void tst(Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
 
@@ -420,16 +463,33 @@
 
   virtual void cmn(Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
 
-  virtual void orr(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
-  virtual void orrs(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void orr(Register rd, Register rn, const ShifterOperand& so,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
 
-  virtual void mov(Register rd, const ShifterOperand& so, Condition cond = AL) = 0;
-  virtual void movs(Register rd, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void orrs(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) {
+    orr(rd, rn, so, cond, kCcSet);
+  }
 
-  virtual void bic(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void mov(Register rd, const ShifterOperand& so,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
 
-  virtual void mvn(Register rd, const ShifterOperand& so, Condition cond = AL) = 0;
-  virtual void mvns(Register rd, const ShifterOperand& so, Condition cond = AL) = 0;
+  virtual void movs(Register rd, const ShifterOperand& so, Condition cond = AL) {
+    mov(rd, so, cond, kCcSet);
+  }
+
+  virtual void bic(Register rd, Register rn, const ShifterOperand& so,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  virtual void bics(Register rd, Register rn, const ShifterOperand& so, Condition cond = AL) {
+    bic(rd, rn, so, cond, kCcSet);
+  }
+
+  virtual void mvn(Register rd, const ShifterOperand& so,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  virtual void mvns(Register rd, const ShifterOperand& so, Condition cond = AL) {
+    mvn(rd, so, cond, kCcSet);
+  }
 
   // Miscellaneous data-processing instructions.
   virtual void clz(Register rd, Register rm, Condition cond = AL) = 0;
@@ -697,25 +757,68 @@
 
   // Convenience shift instructions. Use mov instruction with shifter operand
   // for variants setting the status flags or using a register shift count.
-  virtual void Lsl(Register rd, Register rm, uint32_t shift_imm, bool setcc = false,
-                   Condition cond = AL) = 0;
-  virtual void Lsr(Register rd, Register rm, uint32_t shift_imm, bool setcc = false,
-                   Condition cond = AL) = 0;
-  virtual void Asr(Register rd, Register rm, uint32_t shift_imm, bool setcc = false,
-                   Condition cond = AL) = 0;
-  virtual void Ror(Register rd, Register rm, uint32_t shift_imm, bool setcc = false,
-                   Condition cond = AL) = 0;
-  virtual void Rrx(Register rd, Register rm, bool setcc = false,
-                   Condition cond = AL) = 0;
+  virtual void Lsl(Register rd, Register rm, uint32_t shift_imm,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
 
-  virtual void Lsl(Register rd, Register rm, Register rn, bool setcc = false,
-                   Condition cond = AL) = 0;
-  virtual void Lsr(Register rd, Register rm, Register rn, bool setcc = false,
-                   Condition cond = AL) = 0;
-  virtual void Asr(Register rd, Register rm, Register rn, bool setcc = false,
-                   Condition cond = AL) = 0;
-  virtual void Ror(Register rd, Register rm, Register rn, bool setcc = false,
-                   Condition cond = AL) = 0;
+  void Lsls(Register rd, Register rm, uint32_t shift_imm, Condition cond = AL) {
+    Lsl(rd, rm, shift_imm, cond, kCcSet);
+  }
+
+  virtual void Lsr(Register rd, Register rm, uint32_t shift_imm,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  void Lsrs(Register rd, Register rm, uint32_t shift_imm, Condition cond = AL) {
+    Lsr(rd, rm, shift_imm, cond, kCcSet);
+  }
+
+  virtual void Asr(Register rd, Register rm, uint32_t shift_imm,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  void Asrs(Register rd, Register rm, uint32_t shift_imm, Condition cond = AL) {
+    Asr(rd, rm, shift_imm, cond, kCcSet);
+  }
+
+  virtual void Ror(Register rd, Register rm, uint32_t shift_imm,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  void Rors(Register rd, Register rm, uint32_t shift_imm, Condition cond = AL) {
+    Ror(rd, rm, shift_imm, cond, kCcSet);
+  }
+
+  virtual void Rrx(Register rd, Register rm,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  void Rrxs(Register rd, Register rm, Condition cond = AL) {
+    Rrx(rd, rm, cond, kCcSet);
+  }
+
+  virtual void Lsl(Register rd, Register rm, Register rn,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  void Lsls(Register rd, Register rm, Register rn, Condition cond = AL) {
+    Lsl(rd, rm, rn, cond, kCcSet);
+  }
+
+  virtual void Lsr(Register rd, Register rm, Register rn,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  void Lsrs(Register rd, Register rm, Register rn, Condition cond = AL) {
+    Lsr(rd, rm, rn, cond, kCcSet);
+  }
+
+  virtual void Asr(Register rd, Register rm, Register rn,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  void Asrs(Register rd, Register rm, Register rn, Condition cond = AL) {
+    Asr(rd, rm, rn, cond, kCcSet);
+  }
+
+  virtual void Ror(Register rd, Register rm, Register rn,
+                   Condition cond = AL, SetCc set_cc = kCcDontCare) = 0;
+
+  void Rors(Register rd, Register rm, Register rn, Condition cond = AL) {
+    Ror(rd, rm, rn, cond, kCcSet);
+  }
 
   // Returns whether the `immediate` can fit in a `ShifterOperand`. If yes,
   // `shifter_op` contains the operand.