Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2006-2008 the V8 project authors. All rights reserved. | 1 // Copyright 2006-2008 the V8 project authors. All rights reserved. |
| 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 1430 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1441 | 1441 |
| 1442 | 1442 |
| 1443 void CodeGenerator::GenerateFastCaseSwitchJumpTable( | 1443 void CodeGenerator::GenerateFastCaseSwitchJumpTable( |
| 1444 SwitchStatement* node, | 1444 SwitchStatement* node, |
| 1445 int min_index, | 1445 int min_index, |
| 1446 int range, | 1446 int range, |
| 1447 Label* default_label, | 1447 Label* default_label, |
| 1448 Vector<Label*> case_targets, | 1448 Vector<Label*> case_targets, |
| 1449 Vector<Label> case_labels) { | 1449 Vector<Label> case_labels) { |
| 1450 VirtualFrame::SpilledScope spilled_scope(this); | 1450 VirtualFrame::SpilledScope spilled_scope(this); |
| 1451 JumpTarget setup_default(this); | |
| 1452 JumpTarget is_smi(this); | |
| 1453 | |
| 1454 // A non-null default label pointer indicates a default case among | |
| 1455 // the case labels. Otherwise we use the break target as a | |
| 1456 // "default". | |
| 1457 JumpTarget* default_target = | |
| 1458 (default_label == NULL) ? node->break_target() : &setup_default; | |
| 1459 | |
| 1451 ASSERT(kSmiTag == 0 && kSmiTagSize <= 2); | 1460 ASSERT(kSmiTag == 0 && kSmiTagSize <= 2); |
| 1452 | |
| 1453 frame_->EmitPop(r0); | 1461 frame_->EmitPop(r0); |
| 1454 | 1462 |
| 1455 // Test for a Smi value in a HeapNumber. | 1463 // Test for a Smi value in a HeapNumber. |
| 1456 JumpTarget is_smi(this); | |
| 1457 __ tst(r0, Operand(kSmiTagMask)); | 1464 __ tst(r0, Operand(kSmiTagMask)); |
| 1458 is_smi.Branch(eq); | 1465 is_smi.Branch(eq); |
| 1459 __ ldr(r1, MemOperand(r0, HeapObject::kMapOffset - kHeapObjectTag)); | 1466 __ ldr(r1, MemOperand(r0, HeapObject::kMapOffset - kHeapObjectTag)); |
| 1460 __ ldrb(r1, MemOperand(r1, Map::kInstanceTypeOffset - kHeapObjectTag)); | 1467 __ ldrb(r1, MemOperand(r1, Map::kInstanceTypeOffset - kHeapObjectTag)); |
| 1461 __ cmp(r1, Operand(HEAP_NUMBER_TYPE)); | 1468 __ cmp(r1, Operand(HEAP_NUMBER_TYPE)); |
| 1462 __ b(ne, default_label); | 1469 default_target->Branch(ne); |
| 1463 frame_->EmitPush(r0); | 1470 frame_->EmitPush(r0); |
| 1464 frame_->CallRuntime(Runtime::kNumberToSmi, 1); | 1471 frame_->CallRuntime(Runtime::kNumberToSmi, 1); |
| 1465 is_smi.Bind(); | 1472 is_smi.Bind(); |
| 1466 | 1473 |
| 1467 if (min_index != 0) { | 1474 if (min_index != 0) { |
| 1468 // Small positive numbers can be immediate operands. | 1475 // Small positive numbers can be immediate operands. |
| 1469 if (min_index < 0) { | 1476 if (min_index < 0) { |
| 1470 // If min_index is Smi::kMinValue, -min_index is not a Smi. | 1477 // If min_index is Smi::kMinValue, -min_index is not a Smi. |
| 1471 if (Smi::IsValid(-min_index)) { | 1478 if (Smi::IsValid(-min_index)) { |
| 1472 __ add(r0, r0, Operand(Smi::FromInt(-min_index))); | 1479 __ add(r0, r0, Operand(Smi::FromInt(-min_index))); |
| 1473 } else { | 1480 } else { |
| 1474 __ add(r0, r0, Operand(Smi::FromInt(-min_index - 1))); | 1481 __ add(r0, r0, Operand(Smi::FromInt(-min_index - 1))); |
| 1475 __ add(r0, r0, Operand(Smi::FromInt(1))); | 1482 __ add(r0, r0, Operand(Smi::FromInt(1))); |
| 1476 } | 1483 } |
| 1477 } else { | 1484 } else { |
| 1478 __ sub(r0, r0, Operand(Smi::FromInt(min_index))); | 1485 __ sub(r0, r0, Operand(Smi::FromInt(min_index))); |
| 1479 } | 1486 } |
| 1480 } | 1487 } |
| 1481 __ tst(r0, Operand(0x80000000 | kSmiTagMask)); | 1488 __ tst(r0, Operand(0x80000000 | kSmiTagMask)); |
| 1482 __ b(ne, default_label); | 1489 default_target->Branch(ne); |
| 1483 __ cmp(r0, Operand(Smi::FromInt(range))); | 1490 __ cmp(r0, Operand(Smi::FromInt(range))); |
| 1484 __ b(ge, default_label); | 1491 default_target->Branch(ge); |
| 1492 VirtualFrame* start_frame = new VirtualFrame(frame_); | |
| 1485 __ SmiJumpTable(r0, case_targets); | 1493 __ SmiJumpTable(r0, case_targets); |
| 1486 | 1494 |
| 1487 VirtualFrame* start_frame = new VirtualFrame(frame_); | 1495 GenerateFastCaseSwitchCases(node, case_labels, start_frame); |
| 1488 // Table containing branch operations. | 1496 |
| 1489 for (int i = 0; i < range; i++) { | 1497 // If there was a default case, we need to emit the code to match |
| 1490 __ jmp(case_targets[i]); | 1498 // it. |
|
Lasse Reichstein
2009/02/24 11:55:06
This comment should be more descriptive.
Kevin Millikin (Chromium)
2009/02/24 12:33:19
Descriptified.
| |
| 1499 if (default_label != NULL) { | |
| 1500 node->break_target()->Jump(); | |
| 1501 setup_default.Bind(); | |
| 1502 frame_->MergeTo(start_frame); | |
| 1503 __ b(default_label); | |
| 1504 DeleteFrame(); | |
| 1491 } | 1505 } |
| 1492 GenerateFastCaseSwitchCases(node, case_labels, start_frame); | 1506 node->break_target()->Bind(); |
| 1507 | |
| 1493 delete start_frame; | 1508 delete start_frame; |
| 1494 } | 1509 } |
| 1495 | 1510 |
| 1496 | 1511 |
| 1497 void CodeGenerator::VisitSwitchStatement(SwitchStatement* node) { | 1512 void CodeGenerator::VisitSwitchStatement(SwitchStatement* node) { |
| 1498 #ifdef DEBUG | 1513 #ifdef DEBUG |
| 1499 int original_height = frame_->height(); | 1514 int original_height = frame_->height(); |
| 1500 #endif | 1515 #endif |
| 1501 VirtualFrame::SpilledScope spilled_scope(this); | 1516 VirtualFrame::SpilledScope spilled_scope(this); |
| 1502 Comment cmnt(masm_, "[ SwitchStatement"); | 1517 Comment cmnt(masm_, "[ SwitchStatement"); |
| (...skipping 3536 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 5039 __ mov(r2, Operand(0)); | 5054 __ mov(r2, Operand(0)); |
| 5040 __ GetBuiltinEntry(r3, Builtins::CALL_NON_FUNCTION); | 5055 __ GetBuiltinEntry(r3, Builtins::CALL_NON_FUNCTION); |
| 5041 __ Jump(Handle<Code>(Builtins::builtin(Builtins::ArgumentsAdaptorTrampoline)), | 5056 __ Jump(Handle<Code>(Builtins::builtin(Builtins::ArgumentsAdaptorTrampoline)), |
| 5042 RelocInfo::CODE_TARGET); | 5057 RelocInfo::CODE_TARGET); |
| 5043 } | 5058 } |
| 5044 | 5059 |
| 5045 | 5060 |
| 5046 #undef __ | 5061 #undef __ |
| 5047 | 5062 |
| 5048 } } // namespace v8::internal | 5063 } } // namespace v8::internal |
| OLD | NEW |