OLD | NEW |
---|---|
1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2016, 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 import '../closure.dart'; | 5 import '../closure.dart'; |
6 import '../common.dart'; | 6 import '../common.dart'; |
7 import '../elements/elements.dart'; | 7 import '../elements/elements.dart'; |
8 import '../elements/entities.dart'; | 8 import '../elements/entities.dart'; |
9 import '../elements/types.dart'; | 9 import '../elements/types.dart'; |
10 import '../io/source_information.dart'; | 10 import '../io/source_information.dart'; |
(...skipping 160 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
171 redirectElement(from, to); | 171 redirectElement(from, to); |
172 updateLocal(from, instruction); | 172 updateLocal(from, instruction); |
173 } else { | 173 } else { |
174 redirectElement(from, to); | 174 redirectElement(from, to); |
175 } | 175 } |
176 }); | 176 }); |
177 } | 177 } |
178 | 178 |
179 /// Replaces the current box with a new box and copies over the given list | 179 /// Replaces the current box with a new box and copies over the given list |
180 /// of elements from the old box into the new box. | 180 /// of elements from the old box into the new box. |
181 void updateCaptureBox(LoopClosureScope loopInfo) { | 181 void updateCaptureBox(Local context, List<Local> toBeCopiedElements) { |
Siggi Cherem (dart-lang)
2017/06/30 22:02:10
nit: maybe rename context or update the comment to
Emily Fortuna
2017/06/30 23:48:10
Done.
| |
182 Local boxElement = loopInfo.context; | |
183 // Create a new box and copy over the values from the old box into the | 182 // Create a new box and copy over the values from the old box into the |
184 // new one. | 183 // new one. |
185 HInstruction oldBox = readLocal(boxElement); | 184 HInstruction oldBox = readLocal(context); |
186 HInstruction newBox = createBox(); | 185 HInstruction newBox = createBox(); |
187 loopInfo.forEachBoxedVariable((Local boxedVariable, _) { | 186 for (Local boxedVariable in toBeCopiedElements) { |
188 // [readLocal] uses the [boxElement] to find its box. By replacing it | 187 // [readLocal] uses the [context] to find its box. By replacing it |
189 // behind its back we can still get to the old values. | 188 // behind its back we can still get to the old values. |
190 updateLocal(boxElement, oldBox); | 189 updateLocal(context, oldBox); |
191 HInstruction oldValue = readLocal(boxedVariable); | 190 HInstruction oldValue = readLocal(boxedVariable); |
192 updateLocal(boxElement, newBox); | 191 updateLocal(context, newBox); |
193 updateLocal(boxedVariable, oldValue); | 192 updateLocal(boxedVariable, oldValue); |
194 }); | 193 } |
195 updateLocal(boxElement, newBox); | 194 updateLocal(context, newBox); |
196 } | 195 } |
197 | 196 |
198 /// Documentation wanted -- johnniwinther | 197 /// Documentation wanted -- johnniwinther |
199 /// | 198 /// |
200 /// Invariant: [function] must be an implementation element. | 199 /// Invariant: [function] must be an implementation element. |
201 void startFunction(MemberEntity element, ScopeInfo scopeInfo, | 200 void startFunction(MemberEntity element, ScopeInfo scopeInfo, |
202 ClosureScope scopeData, Map<Local, TypeMask> parameters, | 201 ClosureScope scopeData, Map<Local, TypeMask> parameters, |
203 {bool isGenerativeConstructorBody}) { | 202 {bool isGenerativeConstructorBody}) { |
204 assert(!(element is MemberElement && !element.isImplementation), | 203 assert(!(element is MemberElement && !element.isImplementation), |
205 failedAt(element)); | 204 failedAt(element)); |
(...skipping 265 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
471 /// <Create box> <== move the first box creation outside the loop. | 470 /// <Create box> <== move the first box creation outside the loop. |
472 /// <initializer>; | 471 /// <initializer>; |
473 /// loop-entry: | 472 /// loop-entry: |
474 /// if (!<condition>) goto loop-exit; | 473 /// if (!<condition>) goto loop-exit; |
475 /// <body> | 474 /// <body> |
476 /// <update box> // create a new box and copy the captured loop-variables. | 475 /// <update box> // create a new box and copy the captured loop-variables. |
477 /// <updates> | 476 /// <updates> |
478 /// goto loop-entry; | 477 /// goto loop-entry; |
479 /// loop-exit: | 478 /// loop-exit: |
480 void startLoop(LoopClosureScope loopInfo) { | 479 void startLoop(LoopClosureScope loopInfo) { |
481 if (loopInfo.hasBoxedVariables) { | 480 if (loopInfo.hasBoxedLoopVariables) { |
482 // If there are boxed loop variables then we set up the box and | 481 // If there are boxed loop variables then we set up the box and |
483 // redirections already now. This way the initializer can write its | 482 // redirections already now. This way the initializer can write its |
484 // values into the box. | 483 // values into the box. |
485 // For other loops the box will be created when entering the body. | 484 // For other loops the box will be created when entering the body. |
486 enterScope(loopInfo); | 485 enterScope(loopInfo); |
487 } | 486 } |
488 } | 487 } |
489 | 488 |
490 /// Create phis at the loop entry for local variables (ready for the values | 489 /// Create phis at the loop entry for local variables (ready for the values |
491 /// from the back edge). Populate the phis with the current values. | 490 /// from the back edge). Populate the phis with the current values. |
(...skipping 14 matching lines...) Expand all Loading... | |
506 } else { | 505 } else { |
507 directLocals[local] = instruction; | 506 directLocals[local] = instruction; |
508 } | 507 } |
509 } | 508 } |
510 }); | 509 }); |
511 } | 510 } |
512 | 511 |
513 void enterLoopBody(LoopClosureScope loopInfo) { | 512 void enterLoopBody(LoopClosureScope loopInfo) { |
514 // If there are no declared boxed loop variables then we did not create the | 513 // If there are no declared boxed loop variables then we did not create the |
515 // box before the initializer and we have to create the box now. | 514 // box before the initializer and we have to create the box now. |
516 if (!loopInfo.hasBoxedVariables) { | 515 if (!loopInfo.hasBoxedLoopVariables) { |
517 enterScope(loopInfo); | 516 enterScope(loopInfo); |
518 } | 517 } |
519 } | 518 } |
520 | 519 |
521 void enterLoopUpdates(LoopClosureScope loopInfo) { | 520 void enterLoopUpdates(LoopClosureScope loopInfo) { |
522 // If there are declared boxed loop variables then the updates might have | 521 // If there are declared boxed loop variables then the updates might have |
523 // access to the box and we must switch to a new box before executing the | 522 // access to the box and we must switch to a new box before executing the |
524 // updates. | 523 // updates. |
525 // In all other cases a new box will be created when entering the body of | 524 // In all other cases a new box will be created when entering the body of |
526 // the next iteration. | 525 // the next iteration. |
527 if (loopInfo.hasBoxedVariables) { | 526 if (loopInfo.hasBoxedLoopVariables) { |
528 updateCaptureBox(loopInfo); | 527 updateCaptureBox(loopInfo.context, loopInfo.boxedLoopVariables); |
529 } | 528 } |
530 } | 529 } |
531 | 530 |
532 /// Goes through the phis created in beginLoopHeader entry and adds the | 531 /// Goes through the phis created in beginLoopHeader entry and adds the |
533 /// input from the back edge (from the current value of directLocals) to them. | 532 /// input from the back edge (from the current value of directLocals) to them. |
534 void endLoop(HBasicBlock loopEntry) { | 533 void endLoop(HBasicBlock loopEntry) { |
535 // If the loop has an aborting body, we don't update the loop | 534 // If the loop has an aborting body, we don't update the loop |
536 // phis. | 535 // phis. |
537 if (loopEntry.predecessors.length == 1) return; | 536 if (loopEntry.predecessors.length == 1) return; |
538 loopEntry.forEachPhi((HPhi phi) { | 537 loopEntry.forEachPhi((HPhi phi) { |
(...skipping 135 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
674 final MemberEntity memberContext; | 673 final MemberEntity memberContext; |
675 | 674 |
676 // Avoid slow Object.hashCode. | 675 // Avoid slow Object.hashCode. |
677 final int hashCode = _nextHashCode = (_nextHashCode + 1).toUnsigned(30); | 676 final int hashCode = _nextHashCode = (_nextHashCode + 1).toUnsigned(30); |
678 static int _nextHashCode = 0; | 677 static int _nextHashCode = 0; |
679 | 678 |
680 SyntheticLocal(this.name, this.executableContext, this.memberContext); | 679 SyntheticLocal(this.name, this.executableContext, this.memberContext); |
681 | 680 |
682 toString() => 'SyntheticLocal($name)'; | 681 toString() => 'SyntheticLocal($name)'; |
683 } | 682 } |
OLD | NEW |