| 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/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 "vm/flow_graph_compiler.h" | 10 #include "vm/flow_graph_compiler.h" |
| (...skipping 138 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 149 return NULL; | 149 return NULL; |
| 150 } | 150 } |
| 151 | 151 |
| 152 | 152 |
| 153 void ReThrowInstr::EmitNativeCode(FlowGraphCompiler* compiler) { | 153 void ReThrowInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 154 UNIMPLEMENTED(); | 154 UNIMPLEMENTED(); |
| 155 } | 155 } |
| 156 | 156 |
| 157 | 157 |
| 158 LocationSummary* BranchInstr::MakeLocationSummary() const { | 158 LocationSummary* BranchInstr::MakeLocationSummary() const { |
| 159 return NULL; | 159 const int kNumInputs = 1; |
| 160 const int kNumTemps = 0; |
| 161 LocationSummary* locs = new LocationSummary(kNumInputs, kNumTemps); |
| 162 locs->set_in(0, Location::RequiresRegister()); |
| 163 return locs; |
| 160 } | 164 } |
| 161 | 165 |
| 162 | 166 |
| 163 void BranchInstr::EmitNativeCode(FlowGraphCompiler* compiler) { | 167 void BranchInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 164 UNIMPLEMENTED(); | 168 Register value = locs()->in(0).reg(); |
| 169 __ CompareObject(value, Bool::ZoneHandle(Bool::True())); |
| 170 if (compiler->IsNextBlock(false_successor())) { |
| 171 // If the next block is the false successor we will fall through to it if |
| 172 // comparison with true fails. |
| 173 __ j(EQUAL, compiler->GetBlockLabel(true_successor())); |
| 174 } else { |
| 175 ASSERT(compiler->IsNextBlock(true_successor())); |
| 176 // If the next block is the true successor we negate comparison and fall |
| 177 // through to it. |
| 178 __ j(NOT_EQUAL, compiler->GetBlockLabel(false_successor())); |
| 179 } |
| 165 } | 180 } |
| 166 | 181 |
| 167 | 182 |
| 168 LocationSummary* CurrentContextComp::MakeLocationSummary() const { | 183 LocationSummary* CurrentContextComp::MakeLocationSummary() const { |
| 169 return LocationSummary::Make(0, Location::RequiresRegister()); | 184 return LocationSummary::Make(0, Location::RequiresRegister()); |
| 170 } | 185 } |
| 171 | 186 |
| 172 | 187 |
| 173 void CurrentContextComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 188 void CurrentContextComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 174 __ movl(locs()->out().reg(), CTX); | 189 __ movl(locs()->out().reg(), CTX); |
| 175 } | 190 } |
| 176 | 191 |
| 177 | 192 |
| 178 LocationSummary* StoreContextComp::MakeLocationSummary() const { | 193 LocationSummary* StoreContextComp::MakeLocationSummary() const { |
| 179 const intptr_t kNumInputs = 1; | 194 const intptr_t kNumInputs = 1; |
| 180 const intptr_t kNumTemps = 0; | 195 const intptr_t kNumTemps = 0; |
| 181 LocationSummary* summary = new LocationSummary(kNumInputs, kNumTemps); | 196 LocationSummary* summary = new LocationSummary(kNumInputs, kNumTemps); |
| 182 summary->set_in(0, Location::RegisterLocation(CTX)); | 197 summary->set_in(0, Location::RegisterLocation(CTX)); |
| 183 return summary; | 198 return summary; |
| 184 } | 199 } |
| 185 | 200 |
| 186 | 201 |
| 187 void StoreContextComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 202 void StoreContextComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 188 // Nothing to do. Context register were loaded by register allocator. | 203 // Nothing to do. Context register were loaded by register allocator. |
| 189 ASSERT(locs()->in(0).reg() == CTX); | 204 ASSERT(locs()->in(0).reg() == CTX); |
| 190 } | 205 } |
| 191 | 206 |
| 192 | 207 |
| 193 LocationSummary* StrictCompareComp::MakeLocationSummary() const { | 208 LocationSummary* StrictCompareComp::MakeLocationSummary() const { |
| 194 return NULL; | 209 return LocationSummary::Make(2, Location::SameAsFirstInput()); |
| 195 } | 210 } |
| 196 | 211 |
| 197 | 212 |
| 198 void StrictCompareComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 213 void StrictCompareComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 199 UNIMPLEMENTED(); | 214 const Bool& bool_true = Bool::ZoneHandle(Bool::True()); |
| 215 const Bool& bool_false = Bool::ZoneHandle(Bool::False()); |
| 216 |
| 217 Register left = locs()->in(0).reg(); |
| 218 Register right = locs()->in(1).reg(); |
| 219 Register result = locs()->out().reg(); |
| 220 |
| 221 __ cmpl(left, right); |
| 222 Label load_true, done; |
| 223 if (kind() == Token::kEQ_STRICT) { |
| 224 __ j(EQUAL, &load_true, Assembler::kNearJump); |
| 225 } else { |
| 226 ASSERT(kind() == Token::kNE_STRICT); |
| 227 __ j(NOT_EQUAL, &load_true, Assembler::kNearJump); |
| 228 } |
| 229 __ LoadObject(result, bool_false); |
| 230 __ jmp(&done, Assembler::kNearJump); |
| 231 __ Bind(&load_true); |
| 232 __ LoadObject(result, bool_true); |
| 233 __ Bind(&done); |
| 200 } | 234 } |
| 201 | 235 |
| 202 | 236 |
| 203 LocationSummary* ClosureCallComp::MakeLocationSummary() const { | 237 LocationSummary* ClosureCallComp::MakeLocationSummary() const { |
| 204 return MakeCallSummary(); | 238 return MakeCallSummary(); |
| 205 } | 239 } |
| 206 | 240 |
| 207 | 241 |
| 208 void ClosureCallComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 242 void ClosureCallComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 209 ASSERT(VerifyCallComputation(this)); | 243 ASSERT(VerifyCallComputation(this)); |
| (...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 304 return NULL; | 338 return NULL; |
| 305 } | 339 } |
| 306 | 340 |
| 307 | 341 |
| 308 void UseVal::EmitNativeCode(FlowGraphCompiler* compiler) { | 342 void UseVal::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 309 UNIMPLEMENTED(); | 343 UNIMPLEMENTED(); |
| 310 } | 344 } |
| 311 | 345 |
| 312 | 346 |
| 313 LocationSummary* AssertAssignableComp::MakeLocationSummary() const { | 347 LocationSummary* AssertAssignableComp::MakeLocationSummary() const { |
| 314 return NULL; | 348 LocationSummary* summary = new LocationSummary(3, 0); |
| 349 summary->set_in(0, Location::RegisterLocation(EAX)); |
| 350 summary->set_in(1, Location::RegisterLocation(ECX)); |
| 351 summary->set_in(2, Location::RegisterLocation(EDX)); |
| 352 summary->set_out(Location::RegisterLocation(EAX)); |
| 353 return summary; |
| 315 } | 354 } |
| 316 | 355 |
| 317 | 356 |
| 318 void AssertAssignableComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 357 void AssertAssignableComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 319 UNIMPLEMENTED(); | 358 ASSERT(locs()->in(0).reg() == EAX); // Value. |
| 359 ASSERT(locs()->in(1).reg() == ECX); // Instantiator. |
| 360 ASSERT(locs()->in(2).reg() == EDX); // Instantiator type arguments. |
| 361 |
| 362 compiler->GenerateAssertAssignable(cid(), |
| 363 token_index(), |
| 364 try_index(), |
| 365 dst_type(), |
| 366 dst_name()); |
| 367 ASSERT(locs()->in(0).reg() == locs()->out().reg()); |
| 320 } | 368 } |
| 321 | 369 |
| 322 | 370 |
| 323 LocationSummary* AssertBooleanComp::MakeLocationSummary() const { | 371 LocationSummary* AssertBooleanComp::MakeLocationSummary() const { |
| 324 return NULL; | 372 return NULL; |
| 325 } | 373 } |
| 326 | 374 |
| 327 | 375 |
| 328 void AssertBooleanComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 376 void AssertBooleanComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 329 UNIMPLEMENTED(); | 377 UNIMPLEMENTED(); |
| (...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 378 return NULL; | 426 return NULL; |
| 379 } | 427 } |
| 380 | 428 |
| 381 | 429 |
| 382 void StoreIndexedComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 430 void StoreIndexedComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 383 UNIMPLEMENTED(); | 431 UNIMPLEMENTED(); |
| 384 } | 432 } |
| 385 | 433 |
| 386 | 434 |
| 387 LocationSummary* InstanceSetterComp::MakeLocationSummary() const { | 435 LocationSummary* InstanceSetterComp::MakeLocationSummary() const { |
| 436 const intptr_t kNumInputs = 2; |
| 437 return LocationSummary::Make(kNumInputs, Location::RequiresRegister()); |
| 388 return NULL; | 438 return NULL; |
| 389 } | 439 } |
| 390 | 440 |
| 391 | 441 |
| 392 void InstanceSetterComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 442 void InstanceSetterComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 393 UNIMPLEMENTED(); | 443 Register receiver = locs()->in(0).reg(); |
| 444 Register value = locs()->in(1).reg(); |
| 445 Register result = locs()->out().reg(); |
| 446 |
| 447 // Preserve the value (second argument) under the arguments as the result |
| 448 // of the computation, then call the setter. |
| 449 const String& function_name = |
| 450 String::ZoneHandle(Field::SetterSymbol(field_name())); |
| 451 |
| 452 // Insert a copy of the second (last) argument under the arguments. |
| 453 // TODO(fschneider): Avoid preserving the value if the result is not used. |
| 454 __ pushl(value); |
| 455 __ pushl(receiver); |
| 456 __ pushl(value); |
| 457 const intptr_t kArgumentCount = 2; |
| 458 const intptr_t kCheckedArgumentCount = 1; |
| 459 compiler->GenerateInstanceCall(cid(), |
| 460 token_index(), |
| 461 try_index(), |
| 462 function_name, |
| 463 kArgumentCount, |
| 464 Array::ZoneHandle(), |
| 465 kCheckedArgumentCount); |
| 466 __ popl(result); |
| 394 } | 467 } |
| 395 | 468 |
| 396 | 469 |
| 397 LocationSummary* StaticSetterComp::MakeLocationSummary() const { | 470 LocationSummary* StaticSetterComp::MakeLocationSummary() const { |
| 398 return NULL; | 471 return NULL; |
| 399 } | 472 } |
| 400 | 473 |
| 401 | 474 |
| 402 void StaticSetterComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 475 void StaticSetterComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 403 UNIMPLEMENTED(); | 476 UNIMPLEMENTED(); |
| (...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 448 return NULL; | 521 return NULL; |
| 449 } | 522 } |
| 450 | 523 |
| 451 | 524 |
| 452 void BooleanNegateComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 525 void BooleanNegateComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 453 UNIMPLEMENTED(); | 526 UNIMPLEMENTED(); |
| 454 } | 527 } |
| 455 | 528 |
| 456 | 529 |
| 457 LocationSummary* InstanceOfComp::MakeLocationSummary() const { | 530 LocationSummary* InstanceOfComp::MakeLocationSummary() const { |
| 458 return NULL; | 531 LocationSummary* summary = new LocationSummary(3, 0); |
| 532 summary->set_in(0, Location::RegisterLocation(EAX)); |
| 533 summary->set_in(1, Location::RegisterLocation(ECX)); |
| 534 summary->set_in(2, Location::RegisterLocation(EDX)); |
| 535 summary->set_out(Location::RegisterLocation(EAX)); |
| 536 return summary; |
| 459 } | 537 } |
| 460 | 538 |
| 461 | 539 |
| 462 void InstanceOfComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 540 void InstanceOfComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 463 UNIMPLEMENTED(); | 541 ASSERT(locs()->in(0).reg() == EAX); // Value. |
| 542 ASSERT(locs()->in(1).reg() == ECX); // Instantiator. |
| 543 ASSERT(locs()->in(2).reg() == EDX); // Instantiator type arguments. |
| 544 |
| 545 compiler->GenerateInstanceOf(cid(), |
| 546 token_index(), |
| 547 try_index(), |
| 548 type(), |
| 549 negate_result()); |
| 550 ASSERT(locs()->out().reg() == EAX); |
| 464 } | 551 } |
| 465 | 552 |
| 466 | 553 |
| 467 LocationSummary* CreateArrayComp::MakeLocationSummary() const { | 554 LocationSummary* CreateArrayComp::MakeLocationSummary() const { |
| 468 return NULL; | 555 return NULL; |
| 469 } | 556 } |
| 470 | 557 |
| 471 | 558 |
| 472 void CreateArrayComp::EmitNativeCode(FlowGraphCompiler* compiler) { | 559 void CreateArrayComp::EmitNativeCode(FlowGraphCompiler* compiler) { |
| 473 UNIMPLEMENTED(); | 560 UNIMPLEMENTED(); |
| (...skipping 379 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 853 UNREACHABLE(); | 940 UNREACHABLE(); |
| 854 } | 941 } |
| 855 } | 942 } |
| 856 | 943 |
| 857 | 944 |
| 858 } // namespace dart | 945 } // namespace dart |
| 859 | 946 |
| 860 #undef __ | 947 #undef __ |
| 861 | 948 |
| 862 #endif // defined TARGET_ARCH_X64 | 949 #endif // defined TARGET_ARCH_X64 |
| OLD | NEW |