OLD | NEW |
1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #if V8_TARGET_ARCH_X64 | 5 #if V8_TARGET_ARCH_X64 |
6 | 6 |
7 #include "src/bootstrapper.h" | 7 #include "src/bootstrapper.h" |
8 #include "src/code-stubs.h" | 8 #include "src/code-stubs.h" |
9 #include "src/codegen.h" | 9 #include "src/codegen.h" |
10 #include "src/ic/handler-compiler.h" | 10 #include "src/ic/handler-compiler.h" |
(...skipping 1265 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1276 | 1276 |
1277 #ifdef DEBUG | 1277 #ifdef DEBUG |
1278 __ Abort(kUnexpectedFallThroughFromStringComparison); | 1278 __ Abort(kUnexpectedFallThroughFromStringComparison); |
1279 #endif | 1279 #endif |
1280 | 1280 |
1281 __ bind(&check_unequal_objects); | 1281 __ bind(&check_unequal_objects); |
1282 if (cc == equal && !strict()) { | 1282 if (cc == equal && !strict()) { |
1283 // Not strict equality. Objects are unequal if | 1283 // Not strict equality. Objects are unequal if |
1284 // they are both JSObjects and not undetectable, | 1284 // they are both JSObjects and not undetectable, |
1285 // and their pointers are different. | 1285 // and their pointers are different. |
1286 Label return_unequal, undetectable; | 1286 Label return_equal, return_unequal, undetectable; |
1287 // At most one is a smi, so we can test for smi by adding the two. | 1287 // At most one is a smi, so we can test for smi by adding the two. |
1288 // A smi plus a heap object has the low bit set, a heap object plus | 1288 // A smi plus a heap object has the low bit set, a heap object plus |
1289 // a heap object has the low bit clear. | 1289 // a heap object has the low bit clear. |
1290 STATIC_ASSERT(kSmiTag == 0); | 1290 STATIC_ASSERT(kSmiTag == 0); |
1291 STATIC_ASSERT(kSmiTagMask == 1); | 1291 STATIC_ASSERT(kSmiTagMask == 1); |
1292 __ leap(rcx, Operand(rax, rdx, times_1, 0)); | 1292 __ leap(rcx, Operand(rax, rdx, times_1, 0)); |
1293 __ testb(rcx, Immediate(kSmiTagMask)); | 1293 __ testb(rcx, Immediate(kSmiTagMask)); |
1294 __ j(not_zero, &runtime_call, Label::kNear); | 1294 __ j(not_zero, &runtime_call, Label::kNear); |
1295 | 1295 |
1296 __ movp(rbx, FieldOperand(rax, HeapObject::kMapOffset)); | 1296 __ movp(rbx, FieldOperand(rax, HeapObject::kMapOffset)); |
1297 __ movp(rcx, FieldOperand(rdx, HeapObject::kMapOffset)); | 1297 __ movp(rcx, FieldOperand(rdx, HeapObject::kMapOffset)); |
1298 __ testb(FieldOperand(rbx, Map::kBitFieldOffset), | 1298 __ testb(FieldOperand(rbx, Map::kBitFieldOffset), |
1299 Immediate(1 << Map::kIsUndetectable)); | 1299 Immediate(1 << Map::kIsUndetectable)); |
1300 __ j(not_zero, &undetectable); | 1300 __ j(not_zero, &undetectable, Label::kNear); |
1301 __ testb(FieldOperand(rcx, Map::kBitFieldOffset), | 1301 __ testb(FieldOperand(rcx, Map::kBitFieldOffset), |
1302 Immediate(1 << Map::kIsUndetectable)); | 1302 Immediate(1 << Map::kIsUndetectable)); |
1303 __ j(not_zero, &return_unequal); | 1303 __ j(not_zero, &return_unequal, Label::kNear); |
1304 | 1304 |
1305 __ CmpInstanceType(rbx, FIRST_JS_RECEIVER_TYPE); | 1305 __ CmpInstanceType(rbx, FIRST_JS_RECEIVER_TYPE); |
1306 __ j(below, &runtime_call, Label::kNear); | 1306 __ j(below, &runtime_call, Label::kNear); |
1307 __ CmpInstanceType(rcx, FIRST_JS_RECEIVER_TYPE); | 1307 __ CmpInstanceType(rcx, FIRST_JS_RECEIVER_TYPE); |
1308 __ j(below, &runtime_call, Label::kNear); | 1308 __ j(below, &runtime_call, Label::kNear); |
1309 | 1309 |
1310 __ bind(&return_unequal); | 1310 __ bind(&return_unequal); |
1311 // Return non-equal by returning the non-zero object pointer in rax. | 1311 // Return non-equal by returning the non-zero object pointer in rax. |
1312 __ ret(0); | 1312 __ ret(0); |
1313 | 1313 |
1314 __ bind(&undetectable); | 1314 __ bind(&undetectable); |
1315 __ testb(FieldOperand(rcx, Map::kBitFieldOffset), | 1315 __ testb(FieldOperand(rcx, Map::kBitFieldOffset), |
1316 Immediate(1 << Map::kIsUndetectable)); | 1316 Immediate(1 << Map::kIsUndetectable)); |
1317 __ j(zero, &return_unequal); | 1317 __ j(zero, &return_unequal, Label::kNear); |
| 1318 |
| 1319 // If both sides are JSReceivers, then the result is false according to |
| 1320 // the HTML specification, which says that only comparisons with null or |
| 1321 // undefined are affected by special casing for document.all. |
| 1322 __ CmpInstanceType(rbx, ODDBALL_TYPE); |
| 1323 __ j(zero, &return_equal, Label::kNear); |
| 1324 __ CmpInstanceType(rcx, ODDBALL_TYPE); |
| 1325 __ j(not_zero, &return_unequal, Label::kNear); |
| 1326 |
| 1327 __ bind(&return_equal); |
1318 __ Set(rax, EQUAL); | 1328 __ Set(rax, EQUAL); |
1319 __ ret(0); | 1329 __ ret(0); |
1320 } | 1330 } |
1321 __ bind(&runtime_call); | 1331 __ bind(&runtime_call); |
1322 | 1332 |
1323 if (cc == equal) { | 1333 if (cc == equal) { |
1324 { | 1334 { |
1325 FrameScope scope(masm, StackFrame::INTERNAL); | 1335 FrameScope scope(masm, StackFrame::INTERNAL); |
1326 __ Push(rdx); | 1336 __ Push(rdx); |
1327 __ Push(rax); | 1337 __ Push(rax); |
(...skipping 4282 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5610 NULL); | 5620 NULL); |
5611 } | 5621 } |
5612 | 5622 |
5613 | 5623 |
5614 #undef __ | 5624 #undef __ |
5615 | 5625 |
5616 } // namespace internal | 5626 } // namespace internal |
5617 } // namespace v8 | 5627 } // namespace v8 |
5618 | 5628 |
5619 #endif // V8_TARGET_ARCH_X64 | 5629 #endif // V8_TARGET_ARCH_X64 |
OLD | NEW |