OLD | NEW |
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #include "vm/flow_graph_builder.h" | 5 #include "vm/flow_graph_builder.h" |
6 | 6 |
7 #include "vm/ast_printer.h" | 7 #include "vm/ast_printer.h" |
8 #include "vm/code_descriptors.h" | 8 #include "vm/code_descriptors.h" |
9 #include "vm/dart_entry.h" | 9 #include "vm/dart_entry.h" |
10 #include "vm/flags.h" | 10 #include "vm/flags.h" |
(...skipping 1488 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1499 // No instantiator required. | 1499 // No instantiator required. |
1500 BindInstr* no_instantiator = | 1500 BindInstr* no_instantiator = |
1501 new BindInstr(new ConstantVal( | 1501 new BindInstr(new ConstantVal( |
1502 Smi::ZoneHandle(Smi::New( | 1502 Smi::ZoneHandle(Smi::New( |
1503 StubCode::kNoInstantiator)))); | 1503 StubCode::kNoInstantiator)))); |
1504 AddInstruction(no_instantiator); | 1504 AddInstruction(no_instantiator); |
1505 args->Add(new UseVal(type_args)); | 1505 args->Add(new UseVal(type_args)); |
1506 args->Add(new UseVal(no_instantiator)); | 1506 args->Add(new UseVal(no_instantiator)); |
1507 return; | 1507 return; |
1508 } | 1508 } |
1509 // The type arguments are uninstantiated. | 1509 // The type arguments are uninstantiated. The generated pseudo code: |
1510 // Place holder to hold uninstantiated constructor type arguments. | 1510 // t1 = InstantiatorTypeArguments(); |
1511 BindInstr* placeholder = | 1511 // t2 = ExtractConstructorTypeArguments(t1); |
1512 new BindInstr(new ConstantVal(Object::ZoneHandle())); | 1512 // t1 = ExtractConstructorInstantiator(t1, t2); |
1513 AddInstruction(placeholder); | 1513 // t_n <- t2 |
1514 Value* instantiator = | 1514 // t_n+1 <- t1 |
1515 BuildInstantiatorTypeArguments(node->token_index()); | 1515 const intptr_t context_level = owner()->context_level(); |
| 1516 // Use expression_temp_var and node->allocated_object_var() locals to keep |
| 1517 // intermediate results around (t1 and t2 above). |
| 1518 ASSERT(owner()->parsed_function().expression_temp_var() != NULL); |
| 1519 const LocalVariable& t1 = *owner()->parsed_function().expression_temp_var(); |
| 1520 const LocalVariable& t2 = node->allocated_object_var(); |
| 1521 |
| 1522 Value* instantiator = BuildInstantiatorTypeArguments(node->token_index()); |
1516 ASSERT(instantiator->IsUse()); | 1523 ASSERT(instantiator->IsUse()); |
1517 PickTempInstr* duplicate_instantiator = | 1524 Definition* stored_instantiator = new BindInstr(new StoreLocalComp( |
1518 new PickTempInstr(instantiator->AsUse()->definition()->temp_index()); | 1525 t1, instantiator, context_level)); |
1519 AddInstruction(duplicate_instantiator); | 1526 AddInstruction(stored_instantiator); |
| 1527 // t1: instantiator type arguments. |
| 1528 |
1520 BindInstr* extract_type_arguments = new BindInstr( | 1529 BindInstr* extract_type_arguments = new BindInstr( |
1521 new ExtractConstructorTypeArgumentsComp( | 1530 new ExtractConstructorTypeArgumentsComp( |
1522 node->token_index(), | 1531 node->token_index(), |
1523 owner()->try_index(), | 1532 owner()->try_index(), |
1524 node->type_arguments(), | 1533 node->type_arguments(), |
1525 new UseVal(duplicate_instantiator))); | 1534 new UseVal(stored_instantiator))); |
1526 AddInstruction(extract_type_arguments); | 1535 AddInstruction(extract_type_arguments); |
1527 AddInstruction(new TuckTempInstr(placeholder->temp_index(), | 1536 |
1528 extract_type_arguments->temp_index())); | 1537 Instruction* stored_type_arguments = new DoInstr(new StoreLocalComp( |
| 1538 t2, new UseVal(extract_type_arguments), context_level)); |
| 1539 AddInstruction(stored_type_arguments); |
| 1540 // t2: extracted constructor type arguments. |
| 1541 Definition* load_instantiator = new BindInstr( |
| 1542 new LoadLocalComp(t1, context_level)); |
| 1543 AddInstruction(load_instantiator); |
| 1544 Definition* load_type_arguments = new BindInstr( |
| 1545 new LoadLocalComp(t2, context_level)); |
| 1546 AddInstruction(load_type_arguments); |
| 1547 |
1529 BindInstr* extract_instantiator = | 1548 BindInstr* extract_instantiator = |
1530 new BindInstr(new ExtractConstructorInstantiatorComp( | 1549 new BindInstr(new ExtractConstructorInstantiatorComp( |
1531 node, | 1550 node, |
1532 instantiator, | 1551 new UseVal(load_instantiator), |
1533 new UseVal(extract_type_arguments))); | 1552 new UseVal(load_type_arguments))); |
1534 AddInstruction(extract_instantiator); | 1553 AddInstruction(extract_instantiator); |
1535 args->Add(new UseVal(placeholder)); | 1554 AddInstruction(new DoInstr(new StoreLocalComp( |
1536 args->Add(new UseVal(extract_instantiator)); | 1555 t1, new UseVal(extract_instantiator), context_level))); |
| 1556 // t2: extracted constructor type arguments. |
| 1557 // t1: extracted constructor instantiator. |
| 1558 Definition* load_0 = new BindInstr(new LoadLocalComp(t2, context_level)); |
| 1559 AddInstruction(load_0); |
| 1560 Definition* load_1 = new BindInstr(new LoadLocalComp(t1, context_level)); |
| 1561 AddInstruction(load_1); |
| 1562 args->Add(new UseVal(load_0)); |
| 1563 args->Add(new UseVal(load_1)); |
1537 } | 1564 } |
1538 | 1565 |
1539 | 1566 |
1540 void ValueGraphVisitor::VisitConstructorCallNode(ConstructorCallNode* node) { | 1567 void ValueGraphVisitor::VisitConstructorCallNode(ConstructorCallNode* node) { |
1541 if (node->constructor().IsFactory()) { | 1568 if (node->constructor().IsFactory()) { |
1542 EffectGraphVisitor::VisitConstructorCallNode(node); | 1569 EffectGraphVisitor::VisitConstructorCallNode(node); |
1543 return; | 1570 return; |
1544 } | 1571 } |
1545 | 1572 |
1546 // t_n contains the allocated and initialized object. | 1573 // t_n contains the allocated and initialized object. |
1547 // t_n <- AllocateObject(class) | 1574 // t_n <- AllocateObject(class) |
1548 // t_n+1 <- Pick(t_n) | 1575 // t_n <- StoreLocal(temp, t_n); |
1549 // t_n+2 <- ctor-arg | 1576 // t_n+1 <- ctor-arg |
1550 // t_n+3... <- constructor arguments start here | 1577 // t_n+2... <- constructor arguments start here |
1551 // StaticCall(constructor, t_n+1, t_n+2, ...) | 1578 // StaticCall(constructor, t_n, t_n+1, ...) |
| 1579 // tn <- LoadLocal(temp) |
1552 | 1580 |
1553 Definition* allocate = BuildObjectAllocation(node); | 1581 Definition* allocate = BuildObjectAllocation(node); |
1554 PickTempInstr* duplicate = new PickTempInstr(allocate->temp_index()); | 1582 StoreLocalComp* store_allocated = new StoreLocalComp( |
1555 AddInstruction(duplicate); | 1583 node->allocated_object_var(), |
1556 BuildConstructorCall(node, new UseVal(duplicate)); | 1584 new UseVal(allocate), |
1557 ReturnValue(new UseVal(allocate)); | 1585 owner()->context_level()); |
| 1586 Definition* allocated_value = new BindInstr(store_allocated); |
| 1587 AddInstruction(allocated_value); |
| 1588 BuildConstructorCall(node, new UseVal(allocated_value)); |
| 1589 LoadLocalComp* load_allocated = new LoadLocalComp( |
| 1590 node->allocated_object_var(), |
| 1591 owner()->context_level()); |
| 1592 allocated_value = new BindInstr(load_allocated); |
| 1593 AddInstruction(allocated_value); |
| 1594 ReturnValue(new UseVal(allocated_value)); |
1558 } | 1595 } |
1559 | 1596 |
1560 | 1597 |
1561 void EffectGraphVisitor::VisitInstanceGetterNode(InstanceGetterNode* node) { | 1598 void EffectGraphVisitor::VisitInstanceGetterNode(InstanceGetterNode* node) { |
1562 ValueGraphVisitor for_receiver(owner(), temp_index()); | 1599 ValueGraphVisitor for_receiver(owner(), temp_index()); |
1563 node->receiver()->Visit(&for_receiver); | 1600 node->receiver()->Visit(&for_receiver); |
1564 Append(for_receiver); | 1601 Append(for_receiver); |
1565 ZoneGrowableArray<Value*>* arguments = new ZoneGrowableArray<Value*>(1); | 1602 ZoneGrowableArray<Value*>* arguments = new ZoneGrowableArray<Value*>(1); |
1566 arguments->Add(for_receiver.value()); | 1603 arguments->Add(for_receiver.value()); |
1567 const String& name = | 1604 const String& name = |
(...skipping 859 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2427 instr->computation()->Accept(this); | 2464 instr->computation()->Accept(this); |
2428 } | 2465 } |
2429 | 2466 |
2430 | 2467 |
2431 void FlowGraphPrinter::VisitBind(BindInstr* instr) { | 2468 void FlowGraphPrinter::VisitBind(BindInstr* instr) { |
2432 OS::Print(" t%d <- ", instr->temp_index()); | 2469 OS::Print(" t%d <- ", instr->temp_index()); |
2433 instr->computation()->Accept(this); | 2470 instr->computation()->Accept(this); |
2434 } | 2471 } |
2435 | 2472 |
2436 | 2473 |
2437 void FlowGraphPrinter::VisitPickTemp(PickTempInstr* instr) { | |
2438 OS::Print(" t%d <- Pick(t%d)", instr->temp_index(), instr->source()); | |
2439 } | |
2440 | |
2441 | |
2442 void FlowGraphPrinter::VisitTuckTemp(TuckTempInstr* instr) { | |
2443 OS::Print(" t%d := t%d", instr->destination(), instr->source()); | |
2444 } | |
2445 | |
2446 | |
2447 void FlowGraphPrinter::VisitReturn(ReturnInstr* instr) { | 2474 void FlowGraphPrinter::VisitReturn(ReturnInstr* instr) { |
2448 OS::Print(" return "); | 2475 OS::Print(" return "); |
2449 instr->value()->Accept(this); | 2476 instr->value()->Accept(this); |
2450 } | 2477 } |
2451 | 2478 |
2452 | 2479 |
2453 void FlowGraphPrinter::VisitThrow(ThrowInstr* instr) { | 2480 void FlowGraphPrinter::VisitThrow(ThrowInstr* instr) { |
2454 OS::Print("Throw("); | 2481 OS::Print("Throw("); |
2455 instr->exception()->Accept(this); | 2482 instr->exception()->Accept(this); |
2456 OS::Print(")"); | 2483 OS::Print(")"); |
(...skipping 162 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2619 char* chars = reinterpret_cast<char*>( | 2646 char* chars = reinterpret_cast<char*>( |
2620 Isolate::Current()->current_zone()->Allocate(len)); | 2647 Isolate::Current()->current_zone()->Allocate(len)); |
2621 OS::SNPrint(chars, len, kFormat, function_name, reason); | 2648 OS::SNPrint(chars, len, kFormat, function_name, reason); |
2622 const Error& error = Error::Handle( | 2649 const Error& error = Error::Handle( |
2623 LanguageError::New(String::Handle(String::New(chars)))); | 2650 LanguageError::New(String::Handle(String::New(chars)))); |
2624 Isolate::Current()->long_jump_base()->Jump(1, error); | 2651 Isolate::Current()->long_jump_base()->Jump(1, error); |
2625 } | 2652 } |
2626 | 2653 |
2627 | 2654 |
2628 } // namespace dart | 2655 } // namespace dart |
OLD | NEW |