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..7766f5689bca0fc4f87926ebcf24571e27e1d8d6 100644 |
| --- a/src/arm/lithium-codegen-arm.cc |
| +++ b/src/arm/lithium-codegen-arm.cc |
| @@ -2476,40 +2476,64 @@ 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)); |
| + __ add(scratch0(), external_pointer, |
| + key_is_constant ? Operand(constant_key * 4) : Operand(key, LSL, 2)); |
|
danno
2011/04/28 17:59:55
Can you break out the Operand into another line to
|
| __ 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)); |
| + __ add(scratch0(), external_pointer, |
| + key_is_constant ? Operand(constant_key * 8) : Operand(key, LSL, 3)); |
|
danno
2011/04/28 17:59:55
Same here and below?
|
| __ vldr(result, scratch0(), 0); |
| } else { |
| Register result(ToRegister(instr->result())); |
| switch (array_type) { |
| case kExternalByteArray: |
| - __ ldrsb(result, MemOperand(external_pointer, key)); |
| + __ ldrsb(result, key_is_constant |
| + ? MemOperand(external_pointer, constant_key) |
| + : MemOperand(external_pointer, key)); |
| break; |
| case kExternalUnsignedByteArray: |
| case kExternalPixelArray: |
| - __ ldrb(result, MemOperand(external_pointer, key)); |
| + __ ldrb(result, key_is_constant |
| + ? 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 +3263,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 +3295,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: |