ARM64: Minor optimization for conversions from long to int.
Change-Id: Ice7febba8dd09a4548ab235fc8aee76d7e7676a1
diff --git a/compiler/optimizing/code_generator_arm64.cc b/compiler/optimizing/code_generator_arm64.cc
index 4152355..25b3ea2 100644
--- a/compiler/optimizing/code_generator_arm64.cc
+++ b/compiler/optimizing/code_generator_arm64.cc
@@ -3202,6 +3202,15 @@
Register source = InputRegisterAt(conversion, 0);
if ((result_type == Primitive::kPrimChar) && (input_size < result_size)) {
__ Ubfx(output, source, 0, result_size * kBitsPerByte);
+ } else if (result_type == Primitive::kPrimInt && input_type == Primitive::kPrimLong) {
+ // 'int' values are used directly as W registers, discarding the top
+ // bits, so we don't need to sign-extend and can just perform a move.
+ // We do not pass the `kDiscardForSameWReg` argument to force clearing the
+ // top 32 bits of the target register. We theoretically could leave those
+ // bits unchanged, but we would have to make sure that no code uses a
+ // 32bit input value as a 64bit value assuming that the top 32 bits are
+ // zero.
+ __ Mov(output.W(), source.W());
} else if ((result_type == Primitive::kPrimChar) ||
((input_type == Primitive::kPrimChar) && (result_size > input_size))) {
__ Ubfx(output, output.IsX() ? source.X() : source.W(), 0, min_size * kBitsPerByte);