OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved.7 | 1 // Copyright 2012 the V8 project authors. All rights reserved.7 |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 3064 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3075 constant_key = ToInteger32(LConstantOperand::cast(instr->key())); | 3075 constant_key = ToInteger32(LConstantOperand::cast(instr->key())); |
3076 if (constant_key & 0xF0000000) { | 3076 if (constant_key & 0xF0000000) { |
3077 Abort(kArrayIndexConstantValueTooBig); | 3077 Abort(kArrayIndexConstantValueTooBig); |
3078 } | 3078 } |
3079 } else { | 3079 } else { |
3080 key = ToRegister(instr->key()); | 3080 key = ToRegister(instr->key()); |
3081 } | 3081 } |
3082 int element_size_shift = ElementsKindToShiftSize(elements_kind); | 3082 int element_size_shift = ElementsKindToShiftSize(elements_kind); |
3083 int shift_size = (instr->hydrogen()->key()->representation().IsSmi()) | 3083 int shift_size = (instr->hydrogen()->key()->representation().IsSmi()) |
3084 ? (element_size_shift - kSmiTagSize) : element_size_shift; | 3084 ? (element_size_shift - kSmiTagSize) : element_size_shift; |
3085 int additional_offset = instr->additional_index() << element_size_shift; | 3085 int additional_offset = IsFixedTypedArrayElementsKind(elements_kind) |
| 3086 ? FixedTypedArrayBase::kDataOffset - kHeapObjectTag |
| 3087 : 0; |
3086 | 3088 |
3087 if (elements_kind == EXTERNAL_FLOAT_ELEMENTS || | 3089 if (elements_kind == EXTERNAL_FLOAT_ELEMENTS || |
3088 elements_kind == EXTERNAL_DOUBLE_ELEMENTS) { | 3090 elements_kind == FLOAT32_ELEMENTS || |
| 3091 elements_kind == EXTERNAL_DOUBLE_ELEMENTS || |
| 3092 elements_kind == FLOAT64_ELEMENTS) { |
| 3093 int base_offset = |
| 3094 (instr->additional_index() << element_size_shift) + additional_offset; |
3089 FPURegister result = ToDoubleRegister(instr->result()); | 3095 FPURegister result = ToDoubleRegister(instr->result()); |
3090 if (key_is_constant) { | 3096 if (key_is_constant) { |
3091 __ Addu(scratch0(), external_pointer, constant_key << element_size_shift); | 3097 __ Addu(scratch0(), external_pointer, constant_key << element_size_shift); |
3092 } else { | 3098 } else { |
3093 __ sll(scratch0(), key, shift_size); | 3099 __ sll(scratch0(), key, shift_size); |
3094 __ Addu(scratch0(), scratch0(), external_pointer); | 3100 __ Addu(scratch0(), scratch0(), external_pointer); |
3095 } | 3101 } |
3096 if (elements_kind == EXTERNAL_FLOAT_ELEMENTS) { | 3102 if (elements_kind == EXTERNAL_FLOAT_ELEMENTS || |
3097 __ lwc1(result, MemOperand(scratch0(), additional_offset)); | 3103 elements_kind == FLOAT32_ELEMENTS) { |
| 3104 __ lwc1(result, MemOperand(scratch0(), base_offset)); |
3098 __ cvt_d_s(result, result); | 3105 __ cvt_d_s(result, result); |
3099 } else { // i.e. elements_kind == EXTERNAL_DOUBLE_ELEMENTS | 3106 } else { // loading doubles, not floats. |
3100 __ ldc1(result, MemOperand(scratch0(), additional_offset)); | 3107 __ ldc1(result, MemOperand(scratch0(), base_offset)); |
3101 } | 3108 } |
3102 } else { | 3109 } else { |
3103 Register result = ToRegister(instr->result()); | 3110 Register result = ToRegister(instr->result()); |
3104 MemOperand mem_operand = PrepareKeyedOperand( | 3111 MemOperand mem_operand = PrepareKeyedOperand( |
3105 key, external_pointer, key_is_constant, constant_key, | 3112 key, external_pointer, key_is_constant, constant_key, |
3106 element_size_shift, shift_size, | 3113 element_size_shift, shift_size, |
3107 instr->additional_index(), additional_offset); | 3114 instr->additional_index(), additional_offset); |
3108 switch (elements_kind) { | 3115 switch (elements_kind) { |
3109 case EXTERNAL_BYTE_ELEMENTS: | 3116 case EXTERNAL_BYTE_ELEMENTS: |
| 3117 case INT8_ELEMENTS: |
3110 __ lb(result, mem_operand); | 3118 __ lb(result, mem_operand); |
3111 break; | 3119 break; |
3112 case EXTERNAL_PIXEL_ELEMENTS: | 3120 case EXTERNAL_PIXEL_ELEMENTS: |
3113 case EXTERNAL_UNSIGNED_BYTE_ELEMENTS: | 3121 case EXTERNAL_UNSIGNED_BYTE_ELEMENTS: |
| 3122 case UINT8_ELEMENTS: |
| 3123 case UINT8_CLAMPED_ELEMENTS: |
3114 __ lbu(result, mem_operand); | 3124 __ lbu(result, mem_operand); |
3115 break; | 3125 break; |
3116 case EXTERNAL_SHORT_ELEMENTS: | 3126 case EXTERNAL_SHORT_ELEMENTS: |
| 3127 case INT16_ELEMENTS: |
3117 __ lh(result, mem_operand); | 3128 __ lh(result, mem_operand); |
3118 break; | 3129 break; |
3119 case EXTERNAL_UNSIGNED_SHORT_ELEMENTS: | 3130 case EXTERNAL_UNSIGNED_SHORT_ELEMENTS: |
| 3131 case UINT16_ELEMENTS: |
3120 __ lhu(result, mem_operand); | 3132 __ lhu(result, mem_operand); |
3121 break; | 3133 break; |
3122 case EXTERNAL_INT_ELEMENTS: | 3134 case EXTERNAL_INT_ELEMENTS: |
| 3135 case INT32_ELEMENTS: |
3123 __ lw(result, mem_operand); | 3136 __ lw(result, mem_operand); |
3124 break; | 3137 break; |
3125 case EXTERNAL_UNSIGNED_INT_ELEMENTS: | 3138 case EXTERNAL_UNSIGNED_INT_ELEMENTS: |
| 3139 case UINT32_ELEMENTS: |
3126 __ lw(result, mem_operand); | 3140 __ lw(result, mem_operand); |
3127 if (!instr->hydrogen()->CheckFlag(HInstruction::kUint32)) { | 3141 if (!instr->hydrogen()->CheckFlag(HInstruction::kUint32)) { |
3128 DeoptimizeIf(Ugreater_equal, instr->environment(), | 3142 DeoptimizeIf(Ugreater_equal, instr->environment(), |
3129 result, Operand(0x80000000)); | 3143 result, Operand(0x80000000)); |
3130 } | 3144 } |
3131 break; | 3145 break; |
| 3146 case FLOAT32_ELEMENTS: |
| 3147 case FLOAT64_ELEMENTS: |
3132 case EXTERNAL_FLOAT_ELEMENTS: | 3148 case EXTERNAL_FLOAT_ELEMENTS: |
3133 case EXTERNAL_DOUBLE_ELEMENTS: | 3149 case EXTERNAL_DOUBLE_ELEMENTS: |
3134 case FAST_DOUBLE_ELEMENTS: | 3150 case FAST_DOUBLE_ELEMENTS: |
3135 case FAST_ELEMENTS: | 3151 case FAST_ELEMENTS: |
3136 case FAST_SMI_ELEMENTS: | 3152 case FAST_SMI_ELEMENTS: |
3137 case FAST_HOLEY_DOUBLE_ELEMENTS: | 3153 case FAST_HOLEY_DOUBLE_ELEMENTS: |
3138 case FAST_HOLEY_ELEMENTS: | 3154 case FAST_HOLEY_ELEMENTS: |
3139 case FAST_HOLEY_SMI_ELEMENTS: | 3155 case FAST_HOLEY_SMI_ELEMENTS: |
3140 case DICTIONARY_ELEMENTS: | 3156 case DICTIONARY_ELEMENTS: |
3141 case NON_STRICT_ARGUMENTS_ELEMENTS: | 3157 case NON_STRICT_ARGUMENTS_ELEMENTS: |
(...skipping 78 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3220 DeoptimizeIf(ne, instr->environment(), scratch, Operand(zero_reg)); | 3236 DeoptimizeIf(ne, instr->environment(), scratch, Operand(zero_reg)); |
3221 } else { | 3237 } else { |
3222 __ LoadRoot(scratch, Heap::kTheHoleValueRootIndex); | 3238 __ LoadRoot(scratch, Heap::kTheHoleValueRootIndex); |
3223 DeoptimizeIf(eq, instr->environment(), result, Operand(scratch)); | 3239 DeoptimizeIf(eq, instr->environment(), result, Operand(scratch)); |
3224 } | 3240 } |
3225 } | 3241 } |
3226 } | 3242 } |
3227 | 3243 |
3228 | 3244 |
3229 void LCodeGen::DoLoadKeyed(LLoadKeyed* instr) { | 3245 void LCodeGen::DoLoadKeyed(LLoadKeyed* instr) { |
3230 if (instr->is_external()) { | 3246 if (instr->is_typed_elements()) { |
3231 DoLoadKeyedExternalArray(instr); | 3247 DoLoadKeyedExternalArray(instr); |
3232 } else if (instr->hydrogen()->representation().IsDouble()) { | 3248 } else if (instr->hydrogen()->representation().IsDouble()) { |
3233 DoLoadKeyedFixedDoubleArray(instr); | 3249 DoLoadKeyedFixedDoubleArray(instr); |
3234 } else { | 3250 } else { |
3235 DoLoadKeyedFixedArray(instr); | 3251 DoLoadKeyedFixedArray(instr); |
3236 } | 3252 } |
3237 } | 3253 } |
3238 | 3254 |
3239 | 3255 |
3240 MemOperand LCodeGen::PrepareKeyedOperand(Register key, | 3256 MemOperand LCodeGen::PrepareKeyedOperand(Register key, |
3241 Register base, | 3257 Register base, |
3242 bool key_is_constant, | 3258 bool key_is_constant, |
3243 int constant_key, | 3259 int constant_key, |
3244 int element_size, | 3260 int element_size, |
3245 int shift_size, | 3261 int shift_size, |
3246 int additional_index, | 3262 int additional_index, |
3247 int additional_offset) { | 3263 int additional_offset) { |
3248 if (additional_index != 0 && !key_is_constant) { | 3264 int base_offset = (additional_index << element_size) + additional_offset; |
| 3265 if (key_is_constant) { |
| 3266 return MemOperand(base, |
| 3267 base_offset + (constant_key << element_size)); |
| 3268 } |
| 3269 |
| 3270 if (additional_offset != 0) { |
| 3271 if (shift_size >= 0) { |
| 3272 __ sll(scratch0(), key, shift_size); |
| 3273 __ Addu(scratch0(), scratch0(), Operand(base_offset)); |
| 3274 } else { |
| 3275 ASSERT_EQ(-1, shift_size); |
| 3276 __ srl(scratch0(), key, 1); |
| 3277 __ Addu(scratch0(), scratch0(), Operand(base_offset)); |
| 3278 } |
| 3279 __ Addu(scratch0(), base, scratch0()); |
| 3280 return MemOperand(scratch0()); |
| 3281 } |
| 3282 |
| 3283 if (additional_index != 0) { |
3249 additional_index *= 1 << (element_size - shift_size); | 3284 additional_index *= 1 << (element_size - shift_size); |
3250 __ Addu(scratch0(), key, Operand(additional_index)); | 3285 __ Addu(scratch0(), key, Operand(additional_index)); |
3251 } | 3286 } |
3252 | 3287 |
3253 if (key_is_constant) { | |
3254 return MemOperand(base, | |
3255 (constant_key << element_size) + additional_offset); | |
3256 } | |
3257 | |
3258 if (additional_index == 0) { | 3288 if (additional_index == 0) { |
3259 if (shift_size >= 0) { | 3289 if (shift_size >= 0) { |
3260 __ sll(scratch0(), key, shift_size); | 3290 __ sll(scratch0(), key, shift_size); |
3261 __ Addu(scratch0(), base, scratch0()); | 3291 __ Addu(scratch0(), base, scratch0()); |
3262 return MemOperand(scratch0()); | 3292 return MemOperand(scratch0()); |
3263 } else { | 3293 } else { |
3264 ASSERT_EQ(-1, shift_size); | 3294 ASSERT_EQ(-1, shift_size); |
3265 __ srl(scratch0(), key, 1); | 3295 __ srl(scratch0(), key, 1); |
3266 __ Addu(scratch0(), base, scratch0()); | 3296 __ Addu(scratch0(), base, scratch0()); |
3267 return MemOperand(scratch0()); | 3297 return MemOperand(scratch0()); |
(...skipping 903 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4171 constant_key = ToInteger32(LConstantOperand::cast(instr->key())); | 4201 constant_key = ToInteger32(LConstantOperand::cast(instr->key())); |
4172 if (constant_key & 0xF0000000) { | 4202 if (constant_key & 0xF0000000) { |
4173 Abort(kArrayIndexConstantValueTooBig); | 4203 Abort(kArrayIndexConstantValueTooBig); |
4174 } | 4204 } |
4175 } else { | 4205 } else { |
4176 key = ToRegister(instr->key()); | 4206 key = ToRegister(instr->key()); |
4177 } | 4207 } |
4178 int element_size_shift = ElementsKindToShiftSize(elements_kind); | 4208 int element_size_shift = ElementsKindToShiftSize(elements_kind); |
4179 int shift_size = (instr->hydrogen()->key()->representation().IsSmi()) | 4209 int shift_size = (instr->hydrogen()->key()->representation().IsSmi()) |
4180 ? (element_size_shift - kSmiTagSize) : element_size_shift; | 4210 ? (element_size_shift - kSmiTagSize) : element_size_shift; |
4181 int additional_offset = instr->additional_index() << element_size_shift; | 4211 int additional_offset = IsFixedTypedArrayElementsKind(elements_kind) |
| 4212 ? FixedTypedArrayBase::kDataOffset - kHeapObjectTag |
| 4213 : 0; |
4182 | 4214 |
4183 if (elements_kind == EXTERNAL_FLOAT_ELEMENTS || | 4215 if (elements_kind == EXTERNAL_FLOAT_ELEMENTS || |
4184 elements_kind == EXTERNAL_DOUBLE_ELEMENTS) { | 4216 elements_kind == FLOAT32_ELEMENTS || |
| 4217 elements_kind == EXTERNAL_DOUBLE_ELEMENTS || |
| 4218 elements_kind == FLOAT64_ELEMENTS) { |
| 4219 int base_offset = |
| 4220 (instr->additional_index() << element_size_shift) + additional_offset; |
4185 Register address = scratch0(); | 4221 Register address = scratch0(); |
4186 FPURegister value(ToDoubleRegister(instr->value())); | 4222 FPURegister value(ToDoubleRegister(instr->value())); |
4187 if (key_is_constant) { | 4223 if (key_is_constant) { |
4188 if (constant_key != 0) { | 4224 if (constant_key != 0) { |
4189 __ Addu(address, external_pointer, | 4225 __ Addu(address, external_pointer, |
4190 Operand(constant_key << element_size_shift)); | 4226 Operand(constant_key << element_size_shift)); |
4191 } else { | 4227 } else { |
4192 address = external_pointer; | 4228 address = external_pointer; |
4193 } | 4229 } |
4194 } else { | 4230 } else { |
4195 __ sll(address, key, shift_size); | 4231 __ sll(address, key, shift_size); |
4196 __ Addu(address, external_pointer, address); | 4232 __ Addu(address, external_pointer, address); |
4197 } | 4233 } |
4198 | 4234 |
4199 if (elements_kind == EXTERNAL_FLOAT_ELEMENTS) { | 4235 if (elements_kind == EXTERNAL_FLOAT_ELEMENTS || |
| 4236 elements_kind == FLOAT32_ELEMENTS) { |
4200 __ cvt_s_d(double_scratch0(), value); | 4237 __ cvt_s_d(double_scratch0(), value); |
4201 __ swc1(double_scratch0(), MemOperand(address, additional_offset)); | 4238 __ swc1(double_scratch0(), MemOperand(address, base_offset)); |
4202 } else { // i.e. elements_kind == EXTERNAL_DOUBLE_ELEMENTS | 4239 } else { // Storing doubles, not floats. |
4203 __ sdc1(value, MemOperand(address, additional_offset)); | 4240 __ sdc1(value, MemOperand(address, base_offset)); |
4204 } | 4241 } |
4205 } else { | 4242 } else { |
4206 Register value(ToRegister(instr->value())); | 4243 Register value(ToRegister(instr->value())); |
4207 MemOperand mem_operand = PrepareKeyedOperand( | 4244 MemOperand mem_operand = PrepareKeyedOperand( |
4208 key, external_pointer, key_is_constant, constant_key, | 4245 key, external_pointer, key_is_constant, constant_key, |
4209 element_size_shift, shift_size, | 4246 element_size_shift, shift_size, |
4210 instr->additional_index(), additional_offset); | 4247 instr->additional_index(), additional_offset); |
4211 switch (elements_kind) { | 4248 switch (elements_kind) { |
4212 case EXTERNAL_PIXEL_ELEMENTS: | 4249 case EXTERNAL_PIXEL_ELEMENTS: |
4213 case EXTERNAL_BYTE_ELEMENTS: | 4250 case EXTERNAL_BYTE_ELEMENTS: |
4214 case EXTERNAL_UNSIGNED_BYTE_ELEMENTS: | 4251 case EXTERNAL_UNSIGNED_BYTE_ELEMENTS: |
| 4252 case UINT8_ELEMENTS: |
| 4253 case UINT8_CLAMPED_ELEMENTS: |
| 4254 case INT8_ELEMENTS: |
4215 __ sb(value, mem_operand); | 4255 __ sb(value, mem_operand); |
4216 break; | 4256 break; |
4217 case EXTERNAL_SHORT_ELEMENTS: | 4257 case EXTERNAL_SHORT_ELEMENTS: |
4218 case EXTERNAL_UNSIGNED_SHORT_ELEMENTS: | 4258 case EXTERNAL_UNSIGNED_SHORT_ELEMENTS: |
| 4259 case INT16_ELEMENTS: |
| 4260 case UINT16_ELEMENTS: |
4219 __ sh(value, mem_operand); | 4261 __ sh(value, mem_operand); |
4220 break; | 4262 break; |
4221 case EXTERNAL_INT_ELEMENTS: | 4263 case EXTERNAL_INT_ELEMENTS: |
4222 case EXTERNAL_UNSIGNED_INT_ELEMENTS: | 4264 case EXTERNAL_UNSIGNED_INT_ELEMENTS: |
| 4265 case INT32_ELEMENTS: |
| 4266 case UINT32_ELEMENTS: |
4223 __ sw(value, mem_operand); | 4267 __ sw(value, mem_operand); |
4224 break; | 4268 break; |
| 4269 case FLOAT32_ELEMENTS: |
| 4270 case FLOAT64_ELEMENTS: |
4225 case EXTERNAL_FLOAT_ELEMENTS: | 4271 case EXTERNAL_FLOAT_ELEMENTS: |
4226 case EXTERNAL_DOUBLE_ELEMENTS: | 4272 case EXTERNAL_DOUBLE_ELEMENTS: |
4227 case FAST_DOUBLE_ELEMENTS: | 4273 case FAST_DOUBLE_ELEMENTS: |
4228 case FAST_ELEMENTS: | 4274 case FAST_ELEMENTS: |
4229 case FAST_SMI_ELEMENTS: | 4275 case FAST_SMI_ELEMENTS: |
4230 case FAST_HOLEY_DOUBLE_ELEMENTS: | 4276 case FAST_HOLEY_DOUBLE_ELEMENTS: |
4231 case FAST_HOLEY_ELEMENTS: | 4277 case FAST_HOLEY_ELEMENTS: |
4232 case FAST_HOLEY_SMI_ELEMENTS: | 4278 case FAST_HOLEY_SMI_ELEMENTS: |
4233 case DICTIONARY_ELEMENTS: | 4279 case DICTIONARY_ELEMENTS: |
4234 case NON_STRICT_ARGUMENTS_ELEMENTS: | 4280 case NON_STRICT_ARGUMENTS_ELEMENTS: |
(...skipping 98 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4333 GetRAState(), | 4379 GetRAState(), |
4334 kSaveFPRegs, | 4380 kSaveFPRegs, |
4335 EMIT_REMEMBERED_SET, | 4381 EMIT_REMEMBERED_SET, |
4336 check_needed); | 4382 check_needed); |
4337 } | 4383 } |
4338 } | 4384 } |
4339 | 4385 |
4340 | 4386 |
4341 void LCodeGen::DoStoreKeyed(LStoreKeyed* instr) { | 4387 void LCodeGen::DoStoreKeyed(LStoreKeyed* instr) { |
4342 // By cases: external, fast double | 4388 // By cases: external, fast double |
4343 if (instr->is_external()) { | 4389 if (instr->is_typed_elements()) { |
4344 DoStoreKeyedExternalArray(instr); | 4390 DoStoreKeyedExternalArray(instr); |
4345 } else if (instr->hydrogen()->value()->representation().IsDouble()) { | 4391 } else if (instr->hydrogen()->value()->representation().IsDouble()) { |
4346 DoStoreKeyedFixedDoubleArray(instr); | 4392 DoStoreKeyedFixedDoubleArray(instr); |
4347 } else { | 4393 } else { |
4348 DoStoreKeyedFixedArray(instr); | 4394 DoStoreKeyedFixedArray(instr); |
4349 } | 4395 } |
4350 } | 4396 } |
4351 | 4397 |
4352 | 4398 |
4353 void LCodeGen::DoStoreKeyedGeneric(LStoreKeyedGeneric* instr) { | 4399 void LCodeGen::DoStoreKeyedGeneric(LStoreKeyedGeneric* instr) { |
(...skipping 1435 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5789 __ Subu(scratch, result, scratch); | 5835 __ Subu(scratch, result, scratch); |
5790 __ lw(result, FieldMemOperand(scratch, | 5836 __ lw(result, FieldMemOperand(scratch, |
5791 FixedArray::kHeaderSize - kPointerSize)); | 5837 FixedArray::kHeaderSize - kPointerSize)); |
5792 __ bind(&done); | 5838 __ bind(&done); |
5793 } | 5839 } |
5794 | 5840 |
5795 | 5841 |
5796 #undef __ | 5842 #undef __ |
5797 | 5843 |
5798 } } // namespace v8::internal | 5844 } } // namespace v8::internal |
OLD | NEW |