Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(336)

Side by Side Diff: runtime/vm/intermediate_language_ia32.cc

Issue 11232063: Enable merging of comparisons into branches in checked mode. (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 8 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
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/globals.h" // Needed here to get TARGET_ARCH_IA32. 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_IA32.
6 #if defined(TARGET_ARCH_IA32) 6 #if defined(TARGET_ARCH_IA32)
7 7
8 #include "vm/intermediate_language.h" 8 #include "vm/intermediate_language.h"
9 9
10 #include "lib/error.h" 10 #include "lib/error.h"
(...skipping 173 matching lines...) Expand 10 before | Expand all | Expand 10 after
184 const intptr_t kNumInputs = 1; 184 const intptr_t kNumInputs = 1;
185 const intptr_t kNumTemps = 0; 185 const intptr_t kNumTemps = 0;
186 LocationSummary* locs = 186 LocationSummary* locs =
187 new LocationSummary(kNumInputs, kNumTemps, LocationSummary::kCall); 187 new LocationSummary(kNumInputs, kNumTemps, LocationSummary::kCall);
188 locs->set_in(0, Location::RegisterLocation(EAX)); 188 locs->set_in(0, Location::RegisterLocation(EAX));
189 locs->set_out(Location::RegisterLocation(EAX)); 189 locs->set_out(Location::RegisterLocation(EAX));
190 return locs; 190 return locs;
191 } 191 }
192 192
193 193
194 static void EmitAssertBoolean(Register reg,
195 intptr_t token_pos,
196 LocationSummary* locs,
197 FlowGraphCompiler* compiler) {
198 // Check that the type of the value is allowed in conditional context.
199 // Call the runtime if the object is not bool::true or bool::false.
200 ASSERT(locs->always_calls());
201 Label done;
202 __ CompareObject(reg, compiler->bool_true());
203 __ j(EQUAL, &done, Assembler::kNearJump);
204 __ CompareObject(reg, compiler->bool_false());
205 __ j(EQUAL, &done, Assembler::kNearJump);
srdjan 2012/10/23 18:06:06 Would it be faster to get cid of reg and check if
Florian Schneider 2012/10/24 13:02:09 I have not measured that yet, but I'll do a measur
206
207 __ pushl(reg); // Push the source object.
208 compiler->GenerateCallRuntime(token_pos,
209 kConditionTypeErrorRuntimeEntry,
210 locs);
211 // We should never return here.
212 __ int3();
213 __ Bind(&done);
214 }
215
216
194 void AssertBooleanInstr::EmitNativeCode(FlowGraphCompiler* compiler) { 217 void AssertBooleanInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
195 Register obj = locs()->in(0).reg(); 218 Register obj = locs()->in(0).reg();
196 Register result = locs()->out().reg(); 219 Register result = locs()->out().reg();
197 220
198 if (!is_eliminated()) { 221 if (!is_eliminated()) {
199 // Check that the type of the value is allowed in conditional context. 222 EmitAssertBoolean(obj, token_pos(), locs(), compiler);
200 // Call the runtime if the object is not bool::true or bool::false.
201 Label done;
202 __ CompareObject(obj, compiler->bool_true());
203 __ j(EQUAL, &done, Assembler::kNearJump);
204 __ CompareObject(obj, compiler->bool_false());
205 __ j(EQUAL, &done, Assembler::kNearJump);
206
207 __ pushl(obj); // Push the source object.
208 compiler->GenerateCallRuntime(token_pos(),
209 kConditionTypeErrorRuntimeEntry,
210 locs());
211 // We should never return here.
212 __ int3();
213 __ Bind(&done);
214 } 223 }
215 ASSERT(obj == result); 224 ASSERT(obj == result);
216 } 225 }
217 226
218 227
219 LocationSummary* ArgumentDefinitionTestInstr::MakeLocationSummary() const { 228 LocationSummary* ArgumentDefinitionTestInstr::MakeLocationSummary() const {
220 const intptr_t kNumInputs = 1; 229 const intptr_t kNumInputs = 1;
221 const intptr_t kNumTemps = 0; 230 const intptr_t kNumTemps = 0;
222 LocationSummary* locs = 231 LocationSummary* locs =
223 new LocationSummary(kNumInputs, kNumTemps, LocationSummary::kCall); 232 new LocationSummary(kNumInputs, kNumTemps, LocationSummary::kCall);
(...skipping 226 matching lines...) Expand 10 before | Expand all | Expand 10 after
450 Label false_label; 459 Label false_label;
451 __ CompareObject(EAX, compiler->bool_true()); 460 __ CompareObject(EAX, compiler->bool_true());
452 __ j(EQUAL, &false_label, Assembler::kNearJump); 461 __ j(EQUAL, &false_label, Assembler::kNearJump);
453 __ LoadObject(EAX, compiler->bool_true()); 462 __ LoadObject(EAX, compiler->bool_true());
454 __ jmp(&done); 463 __ jmp(&done);
455 __ Bind(&false_label); 464 __ Bind(&false_label);
456 __ LoadObject(EAX, compiler->bool_false()); 465 __ LoadObject(EAX, compiler->bool_false());
457 __ jmp(&done); 466 __ jmp(&done);
458 } 467 }
459 } else { 468 } else {
469 if (branch->is_checked()) {
470 EmitAssertBoolean(EAX, token_pos, locs, compiler);
471 }
460 __ CompareObject(EAX, compiler->bool_true()); 472 __ CompareObject(EAX, compiler->bool_true());
461 branch->EmitBranchOnCondition(compiler, cond); 473 branch->EmitBranchOnCondition(compiler, cond);
462 } 474 }
463 } 475 }
464 __ jmp(&done); 476 __ jmp(&done);
465 __ Bind(&next_test); 477 __ Bind(&next_test);
466 } 478 }
467 // Fall through leads to deoptimization 479 // Fall through leads to deoptimization
468 __ jmp(deopt); 480 __ jmp(deopt);
469 __ Bind(&done); 481 __ Bind(&done);
(...skipping 300 matching lines...) Expand 10 before | Expand all | Expand 10 after
770 } 782 }
771 Register left = locs()->in(0).reg(); 783 Register left = locs()->in(0).reg();
772 Register right = locs()->in(1).reg(); 784 Register right = locs()->in(1).reg();
773 __ pushl(left); 785 __ pushl(left);
774 __ pushl(right); 786 __ pushl(right);
775 EmitEqualityAsInstanceCall(compiler, 787 EmitEqualityAsInstanceCall(compiler,
776 deopt_id(), 788 deopt_id(),
777 token_pos(), 789 token_pos(),
778 Token::kEQ, // kNE reverse occurs at branch. 790 Token::kEQ, // kNE reverse occurs at branch.
779 locs()); 791 locs());
792 if (branch->is_checked()) {
793 EmitAssertBoolean(EAX, token_pos(), locs(), compiler);
794 }
780 Condition branch_condition = (kind() == Token::kNE) ? NOT_EQUAL : EQUAL; 795 Condition branch_condition = (kind() == Token::kNE) ? NOT_EQUAL : EQUAL;
781 __ CompareObject(EAX, compiler->bool_true()); 796 __ CompareObject(EAX, compiler->bool_true());
782 branch->EmitBranchOnCondition(compiler, branch_condition); 797 branch->EmitBranchOnCondition(compiler, branch_condition);
783 } 798 }
784 799
785 800
786 LocationSummary* RelationalOpInstr::MakeLocationSummary() const { 801 LocationSummary* RelationalOpInstr::MakeLocationSummary() const {
787 const intptr_t kNumInputs = 2; 802 const intptr_t kNumInputs = 2;
788 const intptr_t kNumTemps = 0; 803 const intptr_t kNumTemps = 0;
789 if (operands_class_id() == kDoubleCid) { 804 if (operands_class_id() == kDoubleCid) {
(...skipping 1778 matching lines...) Expand 10 before | Expand all | Expand 10 after
2568 __ pcmpeqq(XMM0, XMM0); // Generate all 1's. 2583 __ pcmpeqq(XMM0, XMM0); // Generate all 1's.
2569 __ pxor(value, XMM0); 2584 __ pxor(value, XMM0);
2570 } 2585 }
2571 2586
2572 2587
2573 } // namespace dart 2588 } // namespace dart
2574 2589
2575 #undef __ 2590 #undef __
2576 2591
2577 #endif // defined TARGET_ARCH_X64 2592 #endif // defined TARGET_ARCH_X64
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698