Chromium Code Reviews| Index: src/arm/lithium-codegen-arm.cc |
| diff --git a/src/arm/lithium-codegen-arm.cc b/src/arm/lithium-codegen-arm.cc |
| index 129a0b60deaedf9472c23a8fb1af446cdb17844c..2e6f726176cd57b46e7865dbd0f55f1446b70d64 100644 |
| --- a/src/arm/lithium-codegen-arm.cc |
| +++ b/src/arm/lithium-codegen-arm.cc |
| @@ -2476,40 +2476,72 @@ void LCodeGen::DoLoadKeyedFastElement(LLoadKeyedFastElement* instr) { |
| void LCodeGen::DoLoadKeyedSpecializedArrayElement( |
| LLoadKeyedSpecializedArrayElement* instr) { |
| Register external_pointer = ToRegister(instr->external_pointer()); |
| - Register key = ToRegister(instr->key()); |
| + Register key = no_reg; |
| ExternalArrayType array_type = instr->array_type(); |
| + bool key_is_constant = instr->key()->IsConstantOperand(); |
| + int constant_key = 0; |
| + if (key_is_constant) { |
| + constant_key = ToInteger32(LConstantOperand::cast(instr->key())); |
| + if (constant_key & 0xF0000000) { |
| + Abort("array index constant value too big."); |
| + } |
| + } else { |
| + key = ToRegister(instr->key()); |
| + } |
| if (array_type == kExternalFloatArray) { |
| CpuFeatures::Scope scope(VFP3); |
| DwVfpRegister result(ToDoubleRegister(instr->result())); |
| - __ add(scratch0(), external_pointer, Operand(key, LSL, 2)); |
| + if (key_is_constant) { |
|
Jakob Kummerow
2011/04/29 10:04:16
Sure I can. Like this?
(I don't really like dupli
|
| + __ add(scratch0(), external_pointer, Operand(constant_key * 4)); |
| + } else { |
| + __ add(scratch0(), external_pointer, Operand(key, LSL, 2)); |
| + } |
| __ vldr(result.low(), scratch0(), 0); |
| __ vcvt_f64_f32(result, result.low()); |
| } else if (array_type == kExternalDoubleArray) { |
| CpuFeatures::Scope scope(VFP3); |
| DwVfpRegister result(ToDoubleRegister(instr->result())); |
| - __ add(scratch0(), external_pointer, Operand(key, LSL, 3)); |
| + Operand operand(key, LSL, 3); |
|
Jakob Kummerow
2011/04/29 10:04:16
Or like this?
(Empty initialization isn't possible
|
| + if (key_is_constant) { |
| + operand = Operand(constant_key * 8); |
| + } |
| + __ add(scratch0(), external_pointer, operand); |
| __ vldr(result, scratch0(), 0); |
| } else { |
| Register result(ToRegister(instr->result())); |
| switch (array_type) { |
| - case kExternalByteArray: |
| - __ ldrsb(result, MemOperand(external_pointer, key)); |
| + case kExternalByteArray: { |
|
Jakob Kummerow
2011/04/29 10:04:16
Or maybe like this?
(Doesn't avoid the multiline x
|
| + MemOperand operand( |
| + key_is_constant ? MemOperand(external_pointer, constant_key) |
| + : MemOperand(external_pointer, key)); |
| + __ ldrsb(result, operand); |
| break; |
| + } |
| case kExternalUnsignedByteArray: |
| case kExternalPixelArray: |
| - __ ldrb(result, MemOperand(external_pointer, key)); |
| + __ ldrb(result, key_is_constant |
|
Jakob Kummerow
2011/04/29 10:04:16
Or, on second thought, maybe stick with my origina
|
| + ? MemOperand(external_pointer, constant_key) |
| + : MemOperand(external_pointer, key)); |
| break; |
| case kExternalShortArray: |
| - __ ldrsh(result, MemOperand(external_pointer, key, LSL, 1)); |
| + __ ldrsh(result, key_is_constant |
| + ? MemOperand(external_pointer, constant_key * 2) |
| + : MemOperand(external_pointer, key, LSL, 1)); |
| break; |
| case kExternalUnsignedShortArray: |
| - __ ldrh(result, MemOperand(external_pointer, key, LSL, 1)); |
| + __ ldrh(result, key_is_constant |
| + ? MemOperand(external_pointer, constant_key * 2) |
| + : MemOperand(external_pointer, key, LSL, 1)); |
| break; |
| case kExternalIntArray: |
| - __ ldr(result, MemOperand(external_pointer, key, LSL, 2)); |
| + __ ldr(result, key_is_constant |
| + ? MemOperand(external_pointer, constant_key * 4) |
| + : MemOperand(external_pointer, key, LSL, 2)); |
| break; |
| case kExternalUnsignedIntArray: |
| - __ ldr(result, MemOperand(external_pointer, key, LSL, 2)); |
| + __ ldr(result, key_is_constant |
| + ? MemOperand(external_pointer, constant_key * 4) |
| + : MemOperand(external_pointer, key, LSL, 2)); |
| __ cmp(result, Operand(0x80000000)); |
| // TODO(danno): we could be more clever here, perhaps having a special |
| // version of the stub that detects if the overflow case actually |
| @@ -3239,19 +3271,31 @@ void LCodeGen::DoStoreKeyedSpecializedArrayElement( |
| LStoreKeyedSpecializedArrayElement* instr) { |
| Register external_pointer = ToRegister(instr->external_pointer()); |
| - Register key = ToRegister(instr->key()); |
| + Register key = no_reg; |
| ExternalArrayType array_type = instr->array_type(); |
| + bool key_is_constant = instr->key()->IsConstantOperand(); |
| + int constant_key = 0; |
| + if (key_is_constant) { |
| + constant_key = ToInteger32(LConstantOperand::cast(instr->key())); |
| + if (constant_key & 0xF0000000) { |
| + Abort("array index constant value too big."); |
| + } |
| + } else { |
| + key = ToRegister(instr->key()); |
| + } |
| if (array_type == kExternalFloatArray) { |
| CpuFeatures::Scope scope(VFP3); |
| DwVfpRegister value(ToDoubleRegister(instr->value())); |
| - __ add(scratch0(), external_pointer, Operand(key, LSL, 2)); |
| + __ add(scratch0(), external_pointer, |
| + key_is_constant ? Operand(constant_key * 4) : Operand(key, LSL, 2)); |
| __ vcvt_f32_f64(double_scratch0().low(), value); |
| __ vstr(double_scratch0().low(), scratch0(), 0); |
| } else if (array_type == kExternalDoubleArray) { |
| CpuFeatures::Scope scope(VFP3); |
| DwVfpRegister value(ToDoubleRegister(instr->value())); |
| - __ add(scratch0(), external_pointer, Operand(key, LSL, 3)); |
| + __ add(scratch0(), external_pointer, |
| + key_is_constant ? Operand(constant_key * 8) : Operand(key, LSL, 3)); |
| __ vstr(value, scratch0(), 0); |
| } else { |
| Register value(ToRegister(instr->value())); |
| @@ -3259,19 +3303,27 @@ void LCodeGen::DoStoreKeyedSpecializedArrayElement( |
| case kExternalPixelArray: |
| // Clamp the value to [0..255]. |
| __ Usat(value, 8, Operand(value)); |
| - __ strb(value, MemOperand(external_pointer, key)); |
| + __ strb(value, key_is_constant |
| + ? MemOperand(external_pointer, constant_key) |
| + : MemOperand(external_pointer, key)); |
| break; |
| case kExternalByteArray: |
| case kExternalUnsignedByteArray: |
| - __ strb(value, MemOperand(external_pointer, key)); |
| + __ strb(value, key_is_constant |
| + ? MemOperand(external_pointer, constant_key) |
| + : MemOperand(external_pointer, key)); |
| break; |
| case kExternalShortArray: |
| case kExternalUnsignedShortArray: |
| - __ strh(value, MemOperand(external_pointer, key, LSL, 1)); |
| + __ strh(value, key_is_constant |
| + ? MemOperand(external_pointer, constant_key * 2) |
| + : MemOperand(external_pointer, key, LSL, 1)); |
| break; |
| case kExternalIntArray: |
| case kExternalUnsignedIntArray: |
| - __ str(value, MemOperand(external_pointer, key, LSL, 2)); |
| + __ str(value, key_is_constant |
| + ? MemOperand(external_pointer, constant_key * 4) |
| + : MemOperand(external_pointer, key, LSL, 2)); |
| break; |
| case kExternalFloatArray: |
| case kExternalDoubleArray: |