| 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 #ifndef VM_INTERMEDIATE_LANGUAGE_H_ | 5 #ifndef VM_INTERMEDIATE_LANGUAGE_H_ | 
| 6 #define VM_INTERMEDIATE_LANGUAGE_H_ | 6 #define VM_INTERMEDIATE_LANGUAGE_H_ | 
| 7 | 7 | 
| 8 #include "vm/allocation.h" | 8 #include "vm/allocation.h" | 
| 9 #include "vm/ast.h" | 9 #include "vm/ast.h" | 
| 10 #include "vm/growable_array.h" | 10 #include "vm/growable_array.h" | 
| 11 #include "vm/handles_impl.h" | 11 #include "vm/handles_impl.h" | 
| 12 #include "vm/locations.h" | 12 #include "vm/locations.h" | 
| 13 #include "vm/object.h" | 13 #include "vm/object.h" | 
| 14 | 14 | 
| 15 namespace dart { | 15 namespace dart { | 
| 16 | 16 | 
| 17 class BindInstr; |  | 
| 18 class BitVector; | 17 class BitVector; | 
| 19 class BlockEntryInstr; | 18 class BlockEntryInstr; | 
| 20 class BufferFormatter; | 19 class BufferFormatter; | 
| 21 class ComparisonComp; | 20 class ComparisonInstr; | 
| 22 class ConstantComp; |  | 
| 23 class Computation; |  | 
| 24 class ControlInstruction; | 21 class ControlInstruction; | 
| 25 class Definition; | 22 class Definition; | 
| 26 class Environment; | 23 class Environment; | 
| 27 class FlowGraphCompiler; | 24 class FlowGraphCompiler; | 
| 28 class FlowGraphVisitor; | 25 class FlowGraphVisitor; | 
| 29 class Instruction; | 26 class Instruction; | 
| 30 class LocalVariable; | 27 class LocalVariable; | 
| 31 | 28 | 
| 32 | 29 | 
| 33 // TODO(srdjan): Add _ByteArrayBase, get:length. | 30 // TODO(srdjan): Add _ByteArrayBase, get:length. | 
| (...skipping 144 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 178 // Instructions. | 175 // Instructions. | 
| 179 | 176 | 
| 180 // M is a single argument macro.  It is applied to each concrete instruction | 177 // M is a single argument macro.  It is applied to each concrete instruction | 
| 181 // type name.  The concrete instruction classes are the name with Instr | 178 // type name.  The concrete instruction classes are the name with Instr | 
| 182 // concatenated. | 179 // concatenated. | 
| 183 #define FOR_EACH_INSTRUCTION(M)                                                \ | 180 #define FOR_EACH_INSTRUCTION(M)                                                \ | 
| 184   M(GraphEntry)                                                                \ | 181   M(GraphEntry)                                                                \ | 
| 185   M(JoinEntry)                                                                 \ | 182   M(JoinEntry)                                                                 \ | 
| 186   M(TargetEntry)                                                               \ | 183   M(TargetEntry)                                                               \ | 
| 187   M(Phi)                                                                       \ | 184   M(Phi)                                                                       \ | 
| 188   M(Bind)                                                                      \ |  | 
| 189   M(Parameter)                                                                 \ | 185   M(Parameter)                                                                 \ | 
| 190   M(ParallelMove)                                                              \ | 186   M(ParallelMove)                                                              \ | 
| 191   M(PushArgument)                                                              \ | 187   M(PushArgument)                                                              \ | 
| 192   M(Return)                                                                    \ | 188   M(Return)                                                                    \ | 
| 193   M(Throw)                                                                     \ | 189   M(Throw)                                                                     \ | 
| 194   M(ReThrow)                                                                   \ | 190   M(ReThrow)                                                                   \ | 
| 195   M(Goto)                                                                      \ | 191   M(Goto)                                                                      \ | 
| 196   M(Branch)                                                                    \ | 192   M(Branch)                                                                    \ | 
|  | 193   M(AssertAssignable)                                                          \ | 
|  | 194   M(AssertBoolean)                                                             \ | 
|  | 195   M(ArgumentDefinitionTest)                                                    \ | 
|  | 196   M(CurrentContext)                                                            \ | 
|  | 197   M(StoreContext)                                                              \ | 
|  | 198   M(ClosureCall)                                                               \ | 
|  | 199   M(InstanceCall)                                                              \ | 
|  | 200   M(PolymorphicInstanceCall)                                                   \ | 
|  | 201   M(StaticCall)                                                                \ | 
|  | 202   M(LoadLocal)                                                                 \ | 
|  | 203   M(StoreLocal)                                                                \ | 
|  | 204   M(StrictCompare)                                                             \ | 
|  | 205   M(EqualityCompare)                                                           \ | 
|  | 206   M(RelationalOp)                                                              \ | 
|  | 207   M(NativeCall)                                                                \ | 
|  | 208   M(LoadIndexed)                                                               \ | 
|  | 209   M(StoreIndexed)                                                              \ | 
|  | 210   M(LoadInstanceField)                                                         \ | 
|  | 211   M(StoreInstanceField)                                                        \ | 
|  | 212   M(LoadStaticField)                                                           \ | 
|  | 213   M(StoreStaticField)                                                          \ | 
|  | 214   M(BooleanNegate)                                                             \ | 
|  | 215   M(InstanceOf)                                                                \ | 
|  | 216   M(CreateArray)                                                               \ | 
|  | 217   M(CreateClosure)                                                             \ | 
|  | 218   M(AllocateObject)                                                            \ | 
|  | 219   M(AllocateObjectWithBoundsCheck)                                             \ | 
|  | 220   M(LoadVMField)                                                               \ | 
|  | 221   M(StoreVMField)                                                              \ | 
|  | 222   M(InstantiateTypeArguments)                                                  \ | 
|  | 223   M(ExtractConstructorTypeArguments)                                           \ | 
|  | 224   M(ExtractConstructorInstantiator)                                            \ | 
|  | 225   M(AllocateContext)                                                           \ | 
|  | 226   M(ChainContext)                                                              \ | 
|  | 227   M(CloneContext)                                                              \ | 
|  | 228   M(CatchEntry)                                                                \ | 
|  | 229   M(BinarySmiOp)                                                               \ | 
|  | 230   M(BinaryMintOp)                                                              \ | 
|  | 231   M(UnarySmiOp)                                                                \ | 
|  | 232   M(NumberNegate)                                                              \ | 
|  | 233   M(CheckStackOverflow)                                                        \ | 
|  | 234   M(DoubleToDouble)                                                            \ | 
|  | 235   M(SmiToDouble)                                                               \ | 
|  | 236   M(CheckClass)                                                                \ | 
|  | 237   M(CheckSmi)                                                                  \ | 
|  | 238   M(Constant)                                                                  \ | 
|  | 239   M(CheckEitherNonSmi)                                                         \ | 
|  | 240   M(UnboxedDoubleBinaryOp)                                                     \ | 
|  | 241   M(UnboxDouble)                                                               \ | 
|  | 242   M(BoxDouble)                                                                 \ | 
|  | 243   M(CheckArrayBound)                                                           \ | 
| 197 | 244 | 
| 198 | 245 | 
| 199 #define FORWARD_DECLARATION(type) class type##Instr; | 246 #define FORWARD_DECLARATION(type) class type##Instr; | 
| 200 FOR_EACH_INSTRUCTION(FORWARD_DECLARATION) | 247 FOR_EACH_INSTRUCTION(FORWARD_DECLARATION) | 
| 201 #undef FORWARD_DECLARATION | 248 #undef FORWARD_DECLARATION | 
| 202 | 249 | 
| 203 | 250 | 
| 204 // Functions required in all concrete instruction classes. | 251 // Functions required in all concrete instruction classes. | 
| 205 #define DECLARE_INSTRUCTION(type)                                              \ | 252 #define DECLARE_INSTRUCTION(type)                                              \ | 
|  | 253   virtual Tag tag() const { return k##type; }                                  \ | 
| 206   virtual void Accept(FlowGraphVisitor* visitor);                              \ | 254   virtual void Accept(FlowGraphVisitor* visitor);                              \ | 
| 207   virtual type##Instr* As##type() { return this; }                             \ | 255   virtual type##Instr* As##type() { return this; }                             \ | 
| 208   virtual const char* DebugName() const { return #type; }                      \ | 256   virtual const char* DebugName() const { return #type; }                      \ | 
| 209   virtual void PrintTo(BufferFormatter* f) const;                              \ | 257   virtual LocationSummary* MakeLocationSummary() const;                        \ | 
| 210   virtual void PrintToVisualizer(BufferFormatter* f) const; | 258   virtual void EmitNativeCode(FlowGraphCompiler* compiler);                    \ | 
| 211 | 259 | 
| 212 | 260 | 
| 213 class Instruction : public ZoneAllocated { | 261 class Instruction : public ZoneAllocated { | 
| 214  public: | 262  public: | 
|  | 263 #define DECLARE_TAG(type) k##type, | 
|  | 264   enum Tag { | 
|  | 265     FOR_EACH_INSTRUCTION(DECLARE_TAG) | 
|  | 266   }; | 
|  | 267 #undef DECLARE_TAG | 
|  | 268 | 
| 215   Instruction() | 269   Instruction() | 
| 216       : lifetime_position_(-1), previous_(NULL), next_(NULL), env_(NULL) { } | 270       : deopt_id_(Isolate::Current()->GetNextDeoptId()), | 
|  | 271         lifetime_position_(-1), | 
|  | 272         previous_(NULL), | 
|  | 273         next_(NULL), | 
|  | 274         env_(NULL) { } | 
|  | 275 | 
|  | 276   virtual Tag tag() const = 0; | 
|  | 277 | 
|  | 278   intptr_t deopt_id() const { return deopt_id_; } | 
| 217 | 279 | 
| 218   bool IsBlockEntry() { return (AsBlockEntry() != NULL); } | 280   bool IsBlockEntry() { return (AsBlockEntry() != NULL); } | 
| 219   virtual BlockEntryInstr* AsBlockEntry() { return NULL; } | 281   virtual BlockEntryInstr* AsBlockEntry() { return NULL; } | 
| 220 | 282 | 
| 221   bool IsDefinition() { return (AsDefinition() != NULL); } | 283   bool IsDefinition() { return (AsDefinition() != NULL); } | 
| 222   virtual Definition* AsDefinition() { return NULL; } | 284   virtual Definition* AsDefinition() { return NULL; } | 
| 223 | 285 | 
| 224   bool IsControl() { return (AsControl() != NULL); } | 286   bool IsControl() { return (AsControl() != NULL); } | 
| 225   virtual ControlInstruction* AsControl() { return NULL; } | 287   virtual ControlInstruction* AsControl() { return NULL; } | 
| 226 | 288 | 
| 227   virtual intptr_t InputCount() const = 0; | 289   virtual intptr_t InputCount() const = 0; | 
| 228   virtual Value* InputAt(intptr_t i) const = 0; | 290   virtual Value* InputAt(intptr_t i) const = 0; | 
| 229   virtual void SetInputAt(intptr_t i, Value* value) = 0; | 291   virtual void SetInputAt(intptr_t i, Value* value) = 0; | 
| 230 | 292 | 
| 231   // Call instructions override this function and return the | 293   // Call instructions override this function and return the number of | 
| 232   // number of pushed arguments. | 294   // pushed arguments. | 
| 233   virtual intptr_t ArgumentCount() const = 0; | 295   virtual intptr_t ArgumentCount() const = 0; | 
| 234 | 296 | 
| 235   // Returns true, if this instruction can deoptimize. | 297   // Returns true, if this instruction can deoptimize. | 
| 236   virtual bool CanDeoptimize() const = 0; | 298   virtual bool CanDeoptimize() const = 0; | 
| 237 | 299 | 
| 238   // Visiting support. | 300   // Visiting support. | 
| 239   virtual void Accept(FlowGraphVisitor* visitor) = 0; | 301   virtual void Accept(FlowGraphVisitor* visitor) = 0; | 
| 240 | 302 | 
| 241   Instruction* previous() const { return previous_; } | 303   Instruction* previous() const { return previous_; } | 
| 242   void set_previous(Instruction* instr) { | 304   void set_previous(Instruction* instr) { | 
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 292       intptr_t fixed_parameter_count) { | 354       intptr_t fixed_parameter_count) { | 
| 293     // Never called for instructions except block entries and branches. | 355     // Never called for instructions except block entries and branches. | 
| 294     UNREACHABLE(); | 356     UNREACHABLE(); | 
| 295   } | 357   } | 
| 296 | 358 | 
| 297   // Mutate assigned_vars to add the local variable index for all | 359   // Mutate assigned_vars to add the local variable index for all | 
| 298   // frame-allocated locals assigned to by the instruction. | 360   // frame-allocated locals assigned to by the instruction. | 
| 299   virtual void RecordAssignedVars(BitVector* assigned_vars, | 361   virtual void RecordAssignedVars(BitVector* assigned_vars, | 
| 300                                   intptr_t fixed_parameter_count); | 362                                   intptr_t fixed_parameter_count); | 
| 301 | 363 | 
|  | 364   virtual const char* DebugName() const = 0; | 
|  | 365 | 
| 302   // Printing support. | 366   // Printing support. | 
| 303   virtual void PrintTo(BufferFormatter* f) const = 0; | 367   virtual void PrintTo(BufferFormatter* f) const = 0; | 
| 304   virtual void PrintToVisualizer(BufferFormatter* f) const = 0; | 368   virtual void PrintToVisualizer(BufferFormatter* f) const = 0; | 
| 305 | 369 | 
| 306 #define INSTRUCTION_TYPE_CHECK(type)                                           \ | 370 #define INSTRUCTION_TYPE_CHECK(type)                                           \ | 
| 307   bool Is##type() { return (As##type() != NULL); }                             \ | 371   bool Is##type() { return (As##type() != NULL); }                             \ | 
| 308   virtual type##Instr* As##type() { return NULL; } | 372   virtual type##Instr* As##type() { return NULL; } | 
| 309 FOR_EACH_INSTRUCTION(INSTRUCTION_TYPE_CHECK) | 373 FOR_EACH_INSTRUCTION(INSTRUCTION_TYPE_CHECK) | 
| 310 #undef INSTRUCTION_TYPE_CHECK | 374 #undef INSTRUCTION_TYPE_CHECK | 
| 311 | 375 | 
| 312   // Returns structure describing location constraints required | 376   // Returns structure describing location constraints required | 
| 313   // to emit native code for this instruction. | 377   // to emit native code for this instruction. | 
| 314   virtual LocationSummary* locs() { | 378   virtual LocationSummary* locs() { | 
| 315     // TODO(vegorov): This should be pure virtual method. | 379     // TODO(vegorov): This should be pure virtual method. | 
| 316     // However we are temporary using NULL for instructions that | 380     // However we are temporary using NULL for instructions that | 
| 317     // were not converted to the location based code generation yet. | 381     // were not converted to the location based code generation yet. | 
| 318     return NULL; | 382     return NULL; | 
| 319   } | 383   } | 
| 320 | 384 | 
|  | 385   virtual LocationSummary* MakeLocationSummary() const = 0; | 
|  | 386 | 
|  | 387   static LocationSummary* MakeCallSummary(); | 
|  | 388 | 
| 321   virtual void EmitNativeCode(FlowGraphCompiler* compiler) { | 389   virtual void EmitNativeCode(FlowGraphCompiler* compiler) { | 
| 322     UNIMPLEMENTED(); | 390     UNIMPLEMENTED(); | 
| 323   } | 391   } | 
| 324 | 392 | 
| 325   Environment* env() const { return env_; } | 393   Environment* env() const { return env_; } | 
| 326   void set_env(Environment* env) { env_ = env; } | 394   void set_env(Environment* env) { env_ = env; } | 
| 327 | 395 | 
| 328   intptr_t lifetime_position() const { return lifetime_position_; } | 396   intptr_t lifetime_position() const { return lifetime_position_; } | 
| 329   void set_lifetime_position(intptr_t pos) { | 397   void set_lifetime_position(intptr_t pos) { | 
| 330     lifetime_position_ = pos; | 398     lifetime_position_ = pos; | 
| (...skipping 14 matching lines...) Expand all  Loading... | 
| 345   } | 413   } | 
| 346 | 414 | 
| 347   // Returns deoptimization id that corresponds to the deoptimization target | 415   // Returns deoptimization id that corresponds to the deoptimization target | 
| 348   // that input operands conversions inserted for this instruction can jump | 416   // that input operands conversions inserted for this instruction can jump | 
| 349   // to. | 417   // to. | 
| 350   virtual intptr_t DeoptimizationTarget() const { | 418   virtual intptr_t DeoptimizationTarget() const { | 
| 351     UNREACHABLE(); | 419     UNREACHABLE(); | 
| 352     return Isolate::kNoDeoptId; | 420     return Isolate::kNoDeoptId; | 
| 353   } | 421   } | 
| 354 | 422 | 
|  | 423  protected: | 
|  | 424   // Fetch deopt id without checking if this computation can deoptimize. | 
|  | 425   intptr_t GetDeoptId() const { | 
|  | 426     return deopt_id_; | 
|  | 427   } | 
|  | 428 | 
| 355  private: | 429  private: | 
| 356   friend class Definition;  // Needed for InsertBefore, InsertAfter. | 430   friend class Definition;  // Needed for InsertBefore, InsertAfter. | 
| 357 | 431 | 
|  | 432   // Classes that set deopt_id_. | 
|  | 433   friend class UnboxDoubleInstr; | 
|  | 434   friend class UnboxedDoubleBinaryOpInstr; | 
|  | 435   friend class CheckClassInstr; | 
|  | 436   friend class CheckSmiInstr; | 
|  | 437   friend class CheckNonSmiInstr; | 
|  | 438   friend class CheckArrayBoundInstr; | 
|  | 439   friend class CheckEitherNonSmiInstr; | 
|  | 440 | 
|  | 441   intptr_t deopt_id_; | 
| 358   intptr_t lifetime_position_;  // Position used by register allocator. | 442   intptr_t lifetime_position_;  // Position used by register allocator. | 
| 359   Instruction* previous_; | 443   Instruction* previous_; | 
| 360   Instruction* next_; | 444   Instruction* next_; | 
| 361   Environment* env_; | 445   Environment* env_; | 
| 362   DISALLOW_COPY_AND_ASSIGN(Instruction); | 446   DISALLOW_COPY_AND_ASSIGN(Instruction); | 
| 363 }; | 447 }; | 
| 364 | 448 | 
| 365 | 449 | 
| 366 template<intptr_t N> | 450 template<intptr_t N> | 
| 367 class TemplateInstruction: public Instruction { | 451 class TemplateInstruction: public Instruction { | 
| 368  public: | 452  public: | 
| 369   TemplateInstruction<N>() : locs_(NULL) { } | 453   TemplateInstruction<N>() : locs_(NULL) { } | 
| 370 | 454 | 
| 371   virtual intptr_t InputCount() const { return N; } | 455   virtual intptr_t InputCount() const { return N; } | 
| 372   virtual Value* InputAt(intptr_t i) const { return inputs_[i]; } | 456   virtual Value* InputAt(intptr_t i) const { return inputs_[i]; } | 
| 373   virtual void SetInputAt(intptr_t i, Value* value) { | 457   virtual void SetInputAt(intptr_t i, Value* value) { | 
| 374     ASSERT(value != NULL); | 458     ASSERT(value != NULL); | 
| 375     inputs_[i] = value; | 459     inputs_[i] = value; | 
| 376   } | 460   } | 
| 377 | 461 | 
| 378   virtual LocationSummary* locs() { | 462   virtual LocationSummary* locs() { | 
| 379     if (locs_ == NULL) { | 463     if (locs_ == NULL) { | 
| 380       locs_ = MakeLocationSummary(); | 464       locs_ = MakeLocationSummary(); | 
| 381     } | 465     } | 
| 382     return locs_; | 466     return locs_; | 
| 383   } | 467   } | 
| 384 | 468 | 
| 385   virtual LocationSummary* MakeLocationSummary() const = 0; |  | 
| 386 |  | 
| 387  protected: | 469  protected: | 
| 388   EmbeddedArray<Value*, N> inputs_; | 470   EmbeddedArray<Value*, N> inputs_; | 
| 389 | 471 | 
| 390  private: | 472  private: | 
| 391   LocationSummary* locs_; | 473   LocationSummary* locs_; | 
| 392 }; | 474 }; | 
| 393 | 475 | 
| 394 | 476 | 
| 395 class MoveOperands : public ZoneAllocated { | 477 class MoveOperands : public ZoneAllocated { | 
| 396  public: | 478  public: | 
| (...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 466     return move; | 548     return move; | 
| 467   } | 549   } | 
| 468 | 550 | 
| 469   MoveOperands* MoveOperandsAt(intptr_t index) const { return moves_[index]; } | 551   MoveOperands* MoveOperandsAt(intptr_t index) const { return moves_[index]; } | 
| 470 | 552 | 
| 471   void SetSrcSlotAt(intptr_t index, const Location& loc); | 553   void SetSrcSlotAt(intptr_t index, const Location& loc); | 
| 472   void SetDestSlotAt(intptr_t index, const Location& loc); | 554   void SetDestSlotAt(intptr_t index, const Location& loc); | 
| 473 | 555 | 
| 474   intptr_t NumMoves() const { return moves_.length(); } | 556   intptr_t NumMoves() const { return moves_.length(); } | 
| 475 | 557 | 
| 476   LocationSummary* MakeLocationSummary() const { return NULL; } | 558   virtual void PrintTo(BufferFormatter* f) const; | 
| 477 | 559   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
| 478   void EmitNativeCode(FlowGraphCompiler* compiler) { UNREACHABLE(); } |  | 
| 479 | 560 | 
| 480  private: | 561  private: | 
| 481   GrowableArray<MoveOperands*> moves_;   // Elements cannot be null. | 562   GrowableArray<MoveOperands*> moves_;   // Elements cannot be null. | 
| 482 | 563 | 
| 483   DISALLOW_COPY_AND_ASSIGN(ParallelMoveInstr); | 564   DISALLOW_COPY_AND_ASSIGN(ParallelMoveInstr); | 
| 484 }; | 565 }; | 
| 485 | 566 | 
| 486 | 567 | 
| 487 // Basic block entries are administrative nodes.  There is a distinguished | 568 // Basic block entries are administrative nodes.  There is a distinguished | 
| 488 // graph entry with no predecessor.  Joins are the only nodes with multiple | 569 // graph entry with no predecessor.  Joins are the only nodes with multiple | 
| (...skipping 118 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 607   void Advance() { | 688   void Advance() { | 
| 608     ASSERT(!Done()); | 689     ASSERT(!Done()); | 
| 609     current_ = current_->next(); | 690     current_ = current_->next(); | 
| 610   } | 691   } | 
| 611 | 692 | 
| 612   bool Done() const { return current_ == NULL; } | 693   bool Done() const { return current_ == NULL; } | 
| 613 | 694 | 
| 614   // Removes 'current_' from graph and sets 'current_' to previous instruction. | 695   // Removes 'current_' from graph and sets 'current_' to previous instruction. | 
| 615   void RemoveCurrentFromGraph(); | 696   void RemoveCurrentFromGraph(); | 
| 616 | 697 | 
|  | 698   // Inserts replaces 'current_', which must be a definition, with another | 
|  | 699   // definition.  The new definition becomes 'current_'. | 
|  | 700   void ReplaceCurrentWith(Definition* other); | 
|  | 701 | 
| 617   Instruction* Current() const { return current_; } | 702   Instruction* Current() const { return current_; } | 
| 618 | 703 | 
| 619  private: | 704  private: | 
| 620   BlockEntryInstr* block_entry_; | 705   BlockEntryInstr* block_entry_; | 
| 621   Instruction* current_; | 706   Instruction* current_; | 
| 622 }; | 707 }; | 
| 623 | 708 | 
| 624 | 709 | 
| 625 class BackwardInstructionIterator : public ValueObject { | 710 class BackwardInstructionIterator : public ValueObject { | 
| 626  public: | 711  public: | 
| (...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 669       intptr_t variable_count, | 754       intptr_t variable_count, | 
| 670       intptr_t fixed_parameter_count); | 755       intptr_t fixed_parameter_count); | 
| 671 | 756 | 
| 672   void AddCatchEntry(TargetEntryInstr* entry) { catch_entries_.Add(entry); } | 757   void AddCatchEntry(TargetEntryInstr* entry) { catch_entries_.Add(entry); } | 
| 673 | 758 | 
| 674   virtual void PrepareEntry(FlowGraphCompiler* compiler); | 759   virtual void PrepareEntry(FlowGraphCompiler* compiler); | 
| 675 | 760 | 
| 676   Environment* start_env() const { return start_env_; } | 761   Environment* start_env() const { return start_env_; } | 
| 677   void set_start_env(Environment* env) { start_env_ = env; } | 762   void set_start_env(Environment* env) { start_env_ = env; } | 
| 678 | 763 | 
| 679   Definition* constant_null() const { return constant_null_; } | 764   ConstantInstr* constant_null() const { return constant_null_; } | 
| 680 | 765 | 
| 681   intptr_t spill_slot_count() const { return spill_slot_count_; } | 766   intptr_t spill_slot_count() const { return spill_slot_count_; } | 
| 682   void set_spill_slot_count(intptr_t count) { | 767   void set_spill_slot_count(intptr_t count) { | 
| 683     ASSERT(count >= 0); | 768     ASSERT(count >= 0); | 
| 684     spill_slot_count_ = count; | 769     spill_slot_count_ = count; | 
| 685   } | 770   } | 
| 686 | 771 | 
| 687   TargetEntryInstr* normal_entry() const { return normal_entry_; } | 772   TargetEntryInstr* normal_entry() const { return normal_entry_; } | 
| 688 | 773 | 
|  | 774   virtual void PrintTo(BufferFormatter* f) const; | 
|  | 775   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
|  | 776 | 
| 689  private: | 777  private: | 
| 690   TargetEntryInstr* normal_entry_; | 778   TargetEntryInstr* normal_entry_; | 
| 691   GrowableArray<TargetEntryInstr*> catch_entries_; | 779   GrowableArray<TargetEntryInstr*> catch_entries_; | 
| 692   Environment* start_env_; | 780   Environment* start_env_; | 
| 693   Definition* constant_null_; | 781   ConstantInstr* constant_null_; | 
| 694   intptr_t spill_slot_count_; | 782   intptr_t spill_slot_count_; | 
| 695 | 783 | 
| 696   DISALLOW_COPY_AND_ASSIGN(GraphEntryInstr); | 784   DISALLOW_COPY_AND_ASSIGN(GraphEntryInstr); | 
| 697 }; | 785 }; | 
| 698 | 786 | 
| 699 | 787 | 
| 700 class JoinEntryInstr : public BlockEntryInstr { | 788 class JoinEntryInstr : public BlockEntryInstr { | 
| 701  public: | 789  public: | 
| 702   explicit JoinEntryInstr(intptr_t try_index) | 790   explicit JoinEntryInstr(intptr_t try_index) | 
| 703       : BlockEntryInstr(try_index), | 791       : BlockEntryInstr(try_index), | 
| (...skipping 16 matching lines...) Expand all  Loading... | 
| 720 | 808 | 
| 721   ZoneGrowableArray<PhiInstr*>* phis() const { return phis_; } | 809   ZoneGrowableArray<PhiInstr*>* phis() const { return phis_; } | 
| 722 | 810 | 
| 723   virtual void PrepareEntry(FlowGraphCompiler* compiler); | 811   virtual void PrepareEntry(FlowGraphCompiler* compiler); | 
| 724 | 812 | 
| 725   void InsertPhi(intptr_t var_index, intptr_t var_count); | 813   void InsertPhi(intptr_t var_index, intptr_t var_count); | 
| 726   void RemoveDeadPhis(); | 814   void RemoveDeadPhis(); | 
| 727 | 815 | 
| 728   intptr_t phi_count() const { return phi_count_; } | 816   intptr_t phi_count() const { return phi_count_; } | 
| 729 | 817 | 
|  | 818   virtual void PrintTo(BufferFormatter* f) const; | 
|  | 819   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
|  | 820 | 
| 730  private: | 821  private: | 
| 731   GrowableArray<BlockEntryInstr*> predecessors_; | 822   GrowableArray<BlockEntryInstr*> predecessors_; | 
| 732   ZoneGrowableArray<PhiInstr*>* phis_; | 823   ZoneGrowableArray<PhiInstr*>* phis_; | 
| 733   intptr_t phi_count_; | 824   intptr_t phi_count_; | 
| 734 | 825 | 
| 735   DISALLOW_COPY_AND_ASSIGN(JoinEntryInstr); | 826   DISALLOW_COPY_AND_ASSIGN(JoinEntryInstr); | 
| 736 }; | 827 }; | 
| 737 | 828 | 
| 738 | 829 | 
| 739 class TargetEntryInstr : public BlockEntryInstr { | 830 class TargetEntryInstr : public BlockEntryInstr { | 
| (...skipping 30 matching lines...) Expand all  Loading... | 
| 770 | 861 | 
| 771   // Returns try index for the try block to which this catch handler | 862   // Returns try index for the try block to which this catch handler | 
| 772   // corresponds. | 863   // corresponds. | 
| 773   intptr_t catch_try_index() const { | 864   intptr_t catch_try_index() const { | 
| 774     ASSERT(IsCatchEntry()); | 865     ASSERT(IsCatchEntry()); | 
| 775     return catch_try_index_; | 866     return catch_try_index_; | 
| 776   } | 867   } | 
| 777 | 868 | 
| 778   virtual void PrepareEntry(FlowGraphCompiler* compiler); | 869   virtual void PrepareEntry(FlowGraphCompiler* compiler); | 
| 779 | 870 | 
|  | 871   virtual void PrintTo(BufferFormatter* f) const; | 
|  | 872   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
|  | 873 | 
| 780  private: | 874  private: | 
| 781   BlockEntryInstr* predecessor_; | 875   BlockEntryInstr* predecessor_; | 
| 782   const intptr_t catch_try_index_; | 876   const intptr_t catch_try_index_; | 
| 783 | 877 | 
| 784   DISALLOW_COPY_AND_ASSIGN(TargetEntryInstr); | 878   DISALLOW_COPY_AND_ASSIGN(TargetEntryInstr); | 
| 785 }; | 879 }; | 
| 786 | 880 | 
| 787 | 881 | 
| 788 // Abstract super-class of all instructions that define a value (Bind, Phi). | 882 // Abstract super-class of all instructions that define a value (Bind, Phi). | 
| 789 class Definition : public Instruction { | 883 class Definition : public Instruction { | 
| 790  public: | 884  public: | 
| 791   enum UseKind { kEffect, kValue }; | 885   enum UseKind { kEffect, kValue }; | 
| 792 | 886 | 
| 793   Definition() | 887   Definition() | 
| 794       : temp_index_(-1), | 888       : temp_index_(-1), | 
| 795         ssa_temp_index_(-1), | 889         ssa_temp_index_(-1), | 
| 796         propagated_type_(AbstractType::Handle()), | 890         propagated_type_(AbstractType::Handle()), | 
| 797         propagated_cid_(kIllegalCid), | 891         propagated_cid_(kIllegalCid), | 
| 798         input_use_list_(NULL), | 892         input_use_list_(NULL), | 
| 799         env_use_list_(NULL), | 893         env_use_list_(NULL), | 
| 800         use_kind_(kValue) {  // Phis and parameters rely on this default. | 894         use_kind_(kValue) {  // Phis and parameters rely on this default. | 
| 801   } | 895   } | 
| 802 | 896 | 
| 803   virtual Definition* AsDefinition() { return this; } | 897   virtual Definition* AsDefinition() { return this; } | 
| 804 | 898 | 
|  | 899   bool IsComparison() { return (AsComparison() != NULL); } | 
|  | 900   virtual ComparisonInstr* AsComparison() { return NULL; } | 
|  | 901 | 
|  | 902   // Overridden by definitions that push arguments. | 
|  | 903   virtual intptr_t ArgumentCount() const { return 0; } | 
|  | 904 | 
| 805   intptr_t temp_index() const { return temp_index_; } | 905   intptr_t temp_index() const { return temp_index_; } | 
| 806   void set_temp_index(intptr_t index) { temp_index_ = index; } | 906   void set_temp_index(intptr_t index) { temp_index_ = index; } | 
| 807 | 907 | 
| 808   intptr_t ssa_temp_index() const { return ssa_temp_index_; } | 908   intptr_t ssa_temp_index() const { return ssa_temp_index_; } | 
| 809   void set_ssa_temp_index(intptr_t index) { | 909   void set_ssa_temp_index(intptr_t index) { | 
| 810     ASSERT(index >= 0); | 910     ASSERT(index >= 0); | 
| 811     ASSERT(is_used()); | 911     ASSERT(is_used()); | 
| 812     ssa_temp_index_ = index; | 912     ssa_temp_index_ = index; | 
| 813   } | 913   } | 
| 814   bool HasSSATemp() const { return ssa_temp_index_ >= 0; } | 914   bool HasSSATemp() const { return ssa_temp_index_ >= 0; } | 
| 815 | 915 | 
| 816   bool is_used() const { return (use_kind_ != kEffect); } | 916   bool is_used() const { return (use_kind_ != kEffect); } | 
| 817   void set_use_kind(UseKind kind) { use_kind_ = kind; } | 917   void set_use_kind(UseKind kind) { use_kind_ = kind; } | 
| 818 | 918 | 
| 819   // Compile time type of the definition, which may be requested before type | 919   // Compile time type of the definition, which may be requested before type | 
| 820   // propagation during graph building. | 920   // propagation during graph building. | 
| 821   virtual RawAbstractType* CompileType() const = 0; | 921   virtual RawAbstractType* CompileType() const = 0; | 
| 822 | 922 | 
|  | 923   virtual intptr_t ResultCid() const = 0; | 
|  | 924 | 
| 823   bool HasPropagatedType() const { | 925   bool HasPropagatedType() const { | 
| 824     return !propagated_type_.IsNull(); | 926     return !propagated_type_.IsNull(); | 
| 825   } | 927   } | 
| 826   RawAbstractType* PropagatedType() const { | 928   RawAbstractType* PropagatedType() const { | 
| 827     ASSERT(HasPropagatedType()); | 929     ASSERT(HasPropagatedType()); | 
| 828     return propagated_type_.raw(); | 930     return propagated_type_.raw(); | 
| 829   } | 931   } | 
| 830   // Returns true if the propagated type has changed. | 932   // Returns true if the propagated type has changed. | 
| 831   bool SetPropagatedType(const AbstractType& propagated_type) { | 933   bool SetPropagatedType(const AbstractType& propagated_type) { | 
| 832     if (propagated_type.IsNull()) { | 934     if (propagated_type.IsNull()) { | 
| 833       // Not a typed definition, e.g. access to a VM field. | 935       // Not a typed definition, e.g. access to a VM field. | 
| 834       return false; | 936       return false; | 
| 835     } | 937     } | 
| 836     const bool changed = | 938     const bool changed = | 
| 837         propagated_type_.IsNull() || !propagated_type.Equals(propagated_type_); | 939         propagated_type_.IsNull() || !propagated_type.Equals(propagated_type_); | 
| 838     propagated_type_ = propagated_type.raw(); | 940     propagated_type_ = propagated_type.raw(); | 
| 839     return changed; | 941     return changed; | 
| 840   } | 942   } | 
| 841 | 943 | 
| 842   bool has_propagated_cid() const { return propagated_cid_ != kIllegalCid; } | 944   bool has_propagated_cid() const { return propagated_cid_ != kIllegalCid; } | 
| 843   intptr_t propagated_cid() const { return propagated_cid_; } | 945   intptr_t propagated_cid() const { return propagated_cid_; } | 
|  | 946 | 
| 844   // May compute and set propagated cid. | 947   // May compute and set propagated cid. | 
| 845   virtual intptr_t GetPropagatedCid() = 0; | 948   virtual intptr_t GetPropagatedCid(); | 
| 846 | 949 | 
| 847   // Returns true if the propagated cid has changed. | 950   // Returns true if the propagated cid has changed. | 
| 848   bool SetPropagatedCid(intptr_t cid); | 951   bool SetPropagatedCid(intptr_t cid); | 
| 849 | 952 | 
|  | 953   // Returns true if the definition may have side effects. | 
|  | 954   // TODO(fschneider): Make this abstract and implement for all definitions | 
|  | 955   // instead of returning the safe default (true). | 
|  | 956   virtual bool HasSideEffect() const { return true; } | 
|  | 957 | 
| 850   Value* input_use_list() { return input_use_list_; } | 958   Value* input_use_list() { return input_use_list_; } | 
| 851   void set_input_use_list(Value* head) { input_use_list_ = head; } | 959   void set_input_use_list(Value* head) { input_use_list_ = head; } | 
| 852 | 960 | 
| 853   Value* env_use_list() { return env_use_list_; } | 961   Value* env_use_list() { return env_use_list_; } | 
| 854   void set_env_use_list(Value* head) { env_use_list_ = head; } | 962   void set_env_use_list(Value* head) { env_use_list_ = head; } | 
| 855 | 963 | 
|  | 964   // Returns a replacement for the definition or NULL if the definition can | 
|  | 965   // be eliminated.  By default returns the definition (input parameter) | 
|  | 966   // which means no change. | 
|  | 967   virtual Definition* Canonicalize(); | 
|  | 968 | 
| 856   // Replace uses of this definition with uses of other definition or value. | 969   // Replace uses of this definition with uses of other definition or value. | 
| 857   // Precondition: use lists must be properly calculated. | 970   // Precondition: use lists must be properly calculated. | 
| 858   // Postcondition: use lists and use values are still valid. | 971   // Postcondition: use lists and use values are still valid. | 
| 859   void ReplaceUsesWith(Definition* other); | 972   void ReplaceUsesWith(Definition* other); | 
| 860 | 973 | 
|  | 974   // Replace this definition and all uses with another definition.  If | 
|  | 975   // replacing during iteration, pass the iterator so that the instruction | 
|  | 976   // can be replaced without affecting iteration order, otherwise pass a | 
|  | 977   // NULL iterator. | 
|  | 978   void ReplaceWith(Definition* other, ForwardInstructionIterator* iterator); | 
|  | 979 | 
| 861   // Insert this definition before 'next'. | 980   // Insert this definition before 'next'. | 
| 862   void InsertBefore(Instruction* next); | 981   void InsertBefore(Instruction* next); | 
| 863 | 982 | 
| 864   // Insert this definition after 'prev'. | 983   // Insert this definition after 'prev'. | 
| 865   void InsertAfter(Instruction* prev); | 984   void InsertAfter(Instruction* prev); | 
| 866 | 985 | 
| 867   // If this definition is a bind of a constant return it. | 986   // Compares two definitions.  Returns true, iff: | 
| 868   // Otherwise return NULL. | 987   // 1. They have the same tag. | 
| 869   ConstantComp* AsConstant(); | 988   // 2. All input operands are Equals. | 
|  | 989   // 3. They satisfy AttributesEqual. | 
|  | 990   bool Equals(Definition* other) const; | 
|  | 991 | 
|  | 992   // Compare attributes of a definition (except input operands and tag). | 
|  | 993   // All definition that participate in CSE have to override this function. | 
|  | 994   // This function can assume that the argument has the same type as this. | 
|  | 995   virtual bool AttributesEqual(Definition* other) const { | 
|  | 996     UNREACHABLE(); | 
|  | 997     return false; | 
|  | 998   } | 
|  | 999 | 
|  | 1000   // Returns a hash code for use with hash maps. | 
|  | 1001   virtual intptr_t Hashcode() const; | 
|  | 1002 | 
|  | 1003   virtual void RecordAssignedVars(BitVector* assigned_vars, | 
|  | 1004                                   intptr_t fixed_parameter_count); | 
|  | 1005 | 
|  | 1006   // Printing support. These functions are sometimes overridden for custom | 
|  | 1007   // formatting. Otherwise, it prints in the format "opcode(op1, op2, op3)". | 
|  | 1008   virtual void PrintTo(BufferFormatter* f) const; | 
|  | 1009   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
|  | 1010   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
| 870 | 1011 | 
| 871  private: | 1012  private: | 
| 872   intptr_t temp_index_; | 1013   intptr_t temp_index_; | 
| 873   intptr_t ssa_temp_index_; | 1014   intptr_t ssa_temp_index_; | 
| 874   // TODO(regis): GrowableArray<const AbstractType*> propagated_types_; | 1015   // TODO(regis): GrowableArray<const AbstractType*> propagated_types_; | 
| 875   // For now: | 1016   // For now: | 
| 876   AbstractType& propagated_type_; | 1017   AbstractType& propagated_type_; | 
| 877   intptr_t propagated_cid_; | 1018   intptr_t propagated_cid_; | 
| 878   Value* input_use_list_; | 1019   Value* input_use_list_; | 
| 879   Value* env_use_list_; | 1020   Value* env_use_list_; | 
| 880   UseKind use_kind_; | 1021   UseKind use_kind_; | 
| 881 | 1022 | 
| 882   DISALLOW_COPY_AND_ASSIGN(Definition); | 1023   DISALLOW_COPY_AND_ASSIGN(Definition); | 
| 883 }; | 1024 }; | 
| 884 | 1025 | 
| 885 | 1026 | 
| 886 class BindInstr : public Definition { |  | 
| 887  public: |  | 
| 888   BindInstr(UseKind used, Computation* computation) |  | 
| 889       : computation_(computation) { |  | 
| 890     ASSERT(computation != NULL); |  | 
| 891     set_use_kind(used); |  | 
| 892   } |  | 
| 893 |  | 
| 894   DECLARE_INSTRUCTION(Bind) |  | 
| 895 |  | 
| 896   // Overridden functions from class Instruction. |  | 
| 897   virtual intptr_t ArgumentCount() const; |  | 
| 898   intptr_t InputCount() const; |  | 
| 899   Value* InputAt(intptr_t i) const; |  | 
| 900   void SetInputAt(intptr_t i, Value* value); |  | 
| 901   virtual bool CanDeoptimize() const; |  | 
| 902   virtual void RecordAssignedVars(BitVector* assigned_vars, |  | 
| 903                                   intptr_t fixed_parameter_count); |  | 
| 904   virtual LocationSummary* locs(); |  | 
| 905   virtual void EmitNativeCode(FlowGraphCompiler* compiler); |  | 
| 906   virtual Representation RequiredInputRepresentation(intptr_t i) const; |  | 
| 907   virtual Representation representation() const; |  | 
| 908   virtual intptr_t DeoptimizationTarget() const; |  | 
| 909 |  | 
| 910   Computation* computation() const { return computation_; } |  | 
| 911   void set_computation(Computation* value) { computation_ = value; } |  | 
| 912 |  | 
| 913   // Overridden functions from class Definition. |  | 
| 914   virtual RawAbstractType* CompileType() const; |  | 
| 915   virtual intptr_t GetPropagatedCid(); |  | 
| 916 |  | 
| 917   // Other functions that forward to the computation. |  | 
| 918   intptr_t Hashcode() const; |  | 
| 919   bool Equals(BindInstr* other) const; |  | 
| 920 |  | 
| 921  private: |  | 
| 922   Computation* computation_; |  | 
| 923 |  | 
| 924   DISALLOW_COPY_AND_ASSIGN(BindInstr); |  | 
| 925 }; |  | 
| 926 |  | 
| 927 |  | 
| 928 class PhiInstr : public Definition { | 1027 class PhiInstr : public Definition { | 
| 929  public: | 1028  public: | 
| 930   explicit PhiInstr(JoinEntryInstr* block, intptr_t num_inputs) | 1029   explicit PhiInstr(JoinEntryInstr* block, intptr_t num_inputs) | 
| 931     : block_(block), | 1030     : block_(block), | 
| 932       inputs_(num_inputs), | 1031       inputs_(num_inputs), | 
| 933       is_alive_(false), | 1032       is_alive_(false), | 
| 934       representation_(kTagged) { | 1033       representation_(kTagged) { | 
| 935     for (intptr_t i = 0; i < num_inputs; ++i) { | 1034     for (intptr_t i = 0; i < num_inputs; ++i) { | 
| 936       inputs_.Add(NULL); | 1035       inputs_.Add(NULL); | 
| 937     } | 1036     } | 
| 938   } | 1037   } | 
| 939 | 1038 | 
| 940   JoinEntryInstr* block() const { return block_; } | 1039   JoinEntryInstr* block() const { return block_; } | 
| 941 | 1040 | 
| 942   virtual RawAbstractType* CompileType() const; | 1041   virtual RawAbstractType* CompileType() const; | 
| 943   virtual intptr_t GetPropagatedCid() { return propagated_cid(); } | 1042   virtual intptr_t GetPropagatedCid(); | 
| 944 | 1043 | 
| 945   virtual intptr_t ArgumentCount() const { return 0; } | 1044   virtual intptr_t ArgumentCount() const { return 0; } | 
| 946 | 1045 | 
| 947   intptr_t InputCount() const { return inputs_.length(); } | 1046   intptr_t InputCount() const { return inputs_.length(); } | 
| 948 | 1047 | 
| 949   Value* InputAt(intptr_t i) const { return inputs_[i]; } | 1048   Value* InputAt(intptr_t i) const { return inputs_[i]; } | 
| 950 | 1049 | 
| 951   void SetInputAt(intptr_t i, Value* value) { inputs_[i] = value; } | 1050   void SetInputAt(intptr_t i, Value* value) { inputs_[i] = value; } | 
| 952 | 1051 | 
| 953   virtual bool CanDeoptimize() const { return false; } | 1052   virtual bool CanDeoptimize() const { return false; } | 
| (...skipping 10 matching lines...) Expand all  Loading... | 
| 964   } | 1063   } | 
| 965 | 1064 | 
| 966   virtual Representation representation() const { | 1065   virtual Representation representation() const { | 
| 967     return representation_; | 1066     return representation_; | 
| 968   } | 1067   } | 
| 969 | 1068 | 
| 970   virtual void set_representation(Representation r) { | 1069   virtual void set_representation(Representation r) { | 
| 971     representation_ = r; | 1070     representation_ = r; | 
| 972   } | 1071   } | 
| 973 | 1072 | 
|  | 1073   virtual intptr_t Hashcode() const { | 
|  | 1074     UNREACHABLE(); | 
|  | 1075     return 0; | 
|  | 1076   } | 
|  | 1077 | 
|  | 1078   virtual intptr_t ResultCid() const { | 
|  | 1079     UNREACHABLE(); | 
|  | 1080     return kIllegalCid; | 
|  | 1081   } | 
|  | 1082 | 
| 974   DECLARE_INSTRUCTION(Phi) | 1083   DECLARE_INSTRUCTION(Phi) | 
| 975 | 1084 | 
|  | 1085   virtual void PrintTo(BufferFormatter* f) const; | 
|  | 1086   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
|  | 1087 | 
| 976  private: | 1088  private: | 
| 977   JoinEntryInstr* block_; | 1089   JoinEntryInstr* block_; | 
| 978   GrowableArray<Value*> inputs_; | 1090   GrowableArray<Value*> inputs_; | 
| 979   bool is_alive_; | 1091   bool is_alive_; | 
| 980   Representation representation_; | 1092   Representation representation_; | 
| 981 | 1093 | 
| 982   DISALLOW_COPY_AND_ASSIGN(PhiInstr); | 1094   DISALLOW_COPY_AND_ASSIGN(PhiInstr); | 
| 983 }; | 1095 }; | 
| 984 | 1096 | 
| 985 | 1097 | 
| 986 class ParameterInstr : public Definition { | 1098 class ParameterInstr : public Definition { | 
| 987  public: | 1099  public: | 
| 988   explicit ParameterInstr(intptr_t index) : index_(index) { } | 1100   explicit ParameterInstr(intptr_t index) : index_(index) { } | 
| 989 | 1101 | 
| 990   DECLARE_INSTRUCTION(Parameter) | 1102   DECLARE_INSTRUCTION(Parameter) | 
| 991 | 1103 | 
| 992   intptr_t index() const { return index_; } | 1104   intptr_t index() const { return index_; } | 
| 993 | 1105 | 
| 994   // Compile type of the passed-in parameter. | 1106   // Compile type of the passed-in parameter. | 
| 995   virtual RawAbstractType* CompileType() const; | 1107   virtual RawAbstractType* CompileType() const; | 
|  | 1108 | 
| 996   // No known propagated cid for parameters. | 1109   // No known propagated cid for parameters. | 
| 997   virtual intptr_t GetPropagatedCid() { return propagated_cid(); } | 1110   virtual intptr_t GetPropagatedCid(); | 
| 998 | 1111 | 
| 999   virtual intptr_t ArgumentCount() const { return 0; } | 1112   virtual intptr_t ArgumentCount() const { return 0; } | 
| 1000 | 1113 | 
| 1001   intptr_t InputCount() const { return 0; } | 1114   intptr_t InputCount() const { return 0; } | 
| 1002   Value* InputAt(intptr_t i) const { | 1115   Value* InputAt(intptr_t i) const { | 
| 1003     UNREACHABLE(); | 1116     UNREACHABLE(); | 
| 1004     return NULL; | 1117     return NULL; | 
| 1005   } | 1118   } | 
| 1006   void SetInputAt(intptr_t i, Value* value) { UNREACHABLE(); } | 1119   void SetInputAt(intptr_t i, Value* value) { UNREACHABLE(); } | 
| 1007 | 1120 | 
| 1008   virtual bool CanDeoptimize() const { return false; } | 1121   virtual bool CanDeoptimize() const { return false; } | 
| 1009 | 1122 | 
|  | 1123   virtual intptr_t Hashcode() const { | 
|  | 1124     UNREACHABLE(); | 
|  | 1125     return 0; | 
|  | 1126   } | 
|  | 1127 | 
|  | 1128   virtual intptr_t ResultCid() const { | 
|  | 1129     UNREACHABLE(); | 
|  | 1130     return kIllegalCid; | 
|  | 1131   } | 
|  | 1132 | 
|  | 1133   virtual void PrintTo(BufferFormatter* f) const; | 
|  | 1134   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
|  | 1135 | 
| 1010  private: | 1136  private: | 
| 1011   const intptr_t index_; | 1137   const intptr_t index_; | 
| 1012 | 1138 | 
| 1013   DISALLOW_COPY_AND_ASSIGN(ParameterInstr); | 1139   DISALLOW_COPY_AND_ASSIGN(ParameterInstr); | 
| 1014 }; | 1140 }; | 
| 1015 | 1141 | 
| 1016 | 1142 | 
| 1017 class PushArgumentInstr : public Definition { | 1143 class PushArgumentInstr : public Definition { | 
| 1018  public: | 1144  public: | 
| 1019   explicit PushArgumentInstr(Value* value) : value_(value), locs_(NULL) { | 1145   explicit PushArgumentInstr(Value* value) : value_(value), locs_(NULL) { | 
| 1020     ASSERT(value != NULL); | 1146     ASSERT(value != NULL); | 
|  | 1147     set_use_kind(kEffect);  // Override the default. | 
| 1021   } | 1148   } | 
| 1022 | 1149 | 
| 1023   DECLARE_INSTRUCTION(PushArgument) | 1150   DECLARE_INSTRUCTION(PushArgument) | 
| 1024 | 1151 | 
| 1025   intptr_t InputCount() const { return 1; } | 1152   intptr_t InputCount() const { return 1; } | 
| 1026   Value* InputAt(intptr_t i) const { | 1153   Value* InputAt(intptr_t i) const { | 
| 1027     ASSERT(i == 0); | 1154     ASSERT(i == 0); | 
| 1028     return value_; | 1155     return value_; | 
| 1029   } | 1156   } | 
| 1030   void SetInputAt(intptr_t i, Value* value) { | 1157   void SetInputAt(intptr_t i, Value* value) { | 
| 1031     ASSERT(i == 0); | 1158     ASSERT(i == 0); | 
| 1032     value_ = value; | 1159     value_ = value; | 
| 1033   } | 1160   } | 
| 1034 | 1161 | 
| 1035   virtual intptr_t ArgumentCount() const { return 0; } | 1162   virtual intptr_t ArgumentCount() const { return 0; } | 
| 1036 | 1163 | 
| 1037   virtual RawAbstractType* CompileType() const; | 1164   virtual RawAbstractType* CompileType() const; | 
| 1038   virtual intptr_t GetPropagatedCid() { return propagated_cid(); } | 1165   virtual intptr_t GetPropagatedCid() { return propagated_cid(); } | 
|  | 1166   virtual intptr_t ResultCid() const { | 
|  | 1167     UNREACHABLE(); | 
|  | 1168     return kIllegalCid; | 
|  | 1169   } | 
| 1039 | 1170 | 
| 1040   Value* value() const { return value_; } | 1171   Value* value() const { return value_; } | 
| 1041 | 1172 | 
| 1042   virtual LocationSummary* locs() { | 1173   virtual LocationSummary* locs() { | 
| 1043     if (locs_ == NULL) { | 1174     if (locs_ == NULL) { | 
| 1044       locs_ = MakeLocationSummary(); | 1175       locs_ = MakeLocationSummary(); | 
| 1045     } | 1176     } | 
| 1046     return locs_; | 1177     return locs_; | 
| 1047   } | 1178   } | 
| 1048 | 1179 | 
| 1049   LocationSummary* MakeLocationSummary() const; | 1180   virtual intptr_t Hashcode() const { | 
| 1050 | 1181     UNREACHABLE(); | 
| 1051   virtual void EmitNativeCode(FlowGraphCompiler* compiler); | 1182     return 0; | 
|  | 1183   } | 
| 1052 | 1184 | 
| 1053   virtual bool CanDeoptimize() const { return false; } | 1185   virtual bool CanDeoptimize() const { return false; } | 
| 1054 | 1186 | 
|  | 1187   virtual void PrintTo(BufferFormatter* f) const; | 
|  | 1188   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
|  | 1189 | 
| 1055  private: | 1190  private: | 
| 1056   Value* value_; | 1191   Value* value_; | 
| 1057   LocationSummary* locs_; | 1192   LocationSummary* locs_; | 
| 1058 | 1193 | 
| 1059   DISALLOW_COPY_AND_ASSIGN(PushArgumentInstr); | 1194   DISALLOW_COPY_AND_ASSIGN(PushArgumentInstr); | 
| 1060 }; | 1195 }; | 
| 1061 | 1196 | 
| 1062 | 1197 | 
| 1063 class ReturnInstr : public TemplateInstruction<1> { | 1198 class ReturnInstr : public TemplateInstruction<1> { | 
| 1064  public: | 1199  public: | 
| 1065   ReturnInstr(intptr_t token_pos, Value* value) | 1200   ReturnInstr(intptr_t token_pos, Value* value) | 
| 1066       : deopt_id_(Isolate::Current()->GetNextDeoptId()), | 1201       : token_pos_(token_pos) { | 
| 1067         token_pos_(token_pos) { |  | 
| 1068     ASSERT(value != NULL); | 1202     ASSERT(value != NULL); | 
| 1069     inputs_[0] = value; | 1203     inputs_[0] = value; | 
| 1070   } | 1204   } | 
| 1071 | 1205 | 
| 1072   DECLARE_INSTRUCTION(Return) | 1206   DECLARE_INSTRUCTION(Return) | 
| 1073 | 1207 | 
| 1074   virtual intptr_t ArgumentCount() const { return 0; } | 1208   virtual intptr_t ArgumentCount() const { return 0; } | 
| 1075 | 1209 | 
| 1076   intptr_t deopt_id() const { return deopt_id_; } |  | 
| 1077   intptr_t token_pos() const { return token_pos_; } | 1210   intptr_t token_pos() const { return token_pos_; } | 
| 1078   Value* value() const { return inputs_[0]; } | 1211   Value* value() const { return inputs_[0]; } | 
| 1079 | 1212 | 
| 1080   virtual LocationSummary* MakeLocationSummary() const; |  | 
| 1081 |  | 
| 1082   virtual void EmitNativeCode(FlowGraphCompiler* compiler); |  | 
| 1083 |  | 
| 1084   virtual bool CanDeoptimize() const { return false; } | 1213   virtual bool CanDeoptimize() const { return false; } | 
| 1085 | 1214 | 
|  | 1215   virtual void PrintTo(BufferFormatter* f) const; | 
|  | 1216   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
|  | 1217 | 
| 1086  private: | 1218  private: | 
| 1087   const intptr_t deopt_id_; |  | 
| 1088   const intptr_t token_pos_; | 1219   const intptr_t token_pos_; | 
| 1089 | 1220 | 
| 1090   DISALLOW_COPY_AND_ASSIGN(ReturnInstr); | 1221   DISALLOW_COPY_AND_ASSIGN(ReturnInstr); | 
| 1091 }; | 1222 }; | 
| 1092 | 1223 | 
| 1093 | 1224 | 
| 1094 class ThrowInstr : public TemplateInstruction<0> { | 1225 class ThrowInstr : public TemplateInstruction<0> { | 
| 1095  public: | 1226  public: | 
| 1096   explicit ThrowInstr(intptr_t token_pos) : token_pos_(token_pos) { } | 1227   explicit ThrowInstr(intptr_t token_pos) : token_pos_(token_pos) { } | 
| 1097 | 1228 | 
| 1098   DECLARE_INSTRUCTION(Throw) | 1229   DECLARE_INSTRUCTION(Throw) | 
| 1099 | 1230 | 
| 1100   virtual intptr_t ArgumentCount() const { return 1; } | 1231   virtual intptr_t ArgumentCount() const { return 1; } | 
| 1101 | 1232 | 
| 1102   intptr_t token_pos() const { return token_pos_; } | 1233   intptr_t token_pos() const { return token_pos_; } | 
| 1103 | 1234 | 
| 1104   virtual LocationSummary* MakeLocationSummary() const; | 1235   virtual bool CanDeoptimize() const { return false; } | 
| 1105 | 1236 | 
| 1106   virtual void EmitNativeCode(FlowGraphCompiler* compiler); | 1237   virtual void PrintTo(BufferFormatter* f) const; | 
| 1107 | 1238   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
| 1108   virtual bool CanDeoptimize() const { return false; } |  | 
| 1109 | 1239 | 
| 1110  private: | 1240  private: | 
| 1111   const intptr_t token_pos_; | 1241   const intptr_t token_pos_; | 
| 1112 | 1242 | 
| 1113   DISALLOW_COPY_AND_ASSIGN(ThrowInstr); | 1243   DISALLOW_COPY_AND_ASSIGN(ThrowInstr); | 
| 1114 }; | 1244 }; | 
| 1115 | 1245 | 
| 1116 | 1246 | 
| 1117 class ReThrowInstr : public TemplateInstruction<0> { | 1247 class ReThrowInstr : public TemplateInstruction<0> { | 
| 1118  public: | 1248  public: | 
| 1119   explicit ReThrowInstr(intptr_t token_pos) : token_pos_(token_pos) { } | 1249   explicit ReThrowInstr(intptr_t token_pos) : token_pos_(token_pos) { } | 
| 1120 | 1250 | 
| 1121   DECLARE_INSTRUCTION(ReThrow) | 1251   DECLARE_INSTRUCTION(ReThrow) | 
| 1122 | 1252 | 
| 1123   virtual intptr_t ArgumentCount() const { return 2; } | 1253   virtual intptr_t ArgumentCount() const { return 2; } | 
| 1124 | 1254 | 
| 1125   intptr_t token_pos() const { return token_pos_; } | 1255   intptr_t token_pos() const { return token_pos_; } | 
| 1126 | 1256 | 
| 1127   virtual LocationSummary* MakeLocationSummary() const; | 1257   virtual bool CanDeoptimize() const { return false; } | 
| 1128 | 1258 | 
| 1129   virtual void EmitNativeCode(FlowGraphCompiler* compiler); | 1259   virtual void PrintTo(BufferFormatter* f) const; | 
| 1130 | 1260   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
| 1131   virtual bool CanDeoptimize() const { return false; } |  | 
| 1132 | 1261 | 
| 1133  private: | 1262  private: | 
| 1134   const intptr_t token_pos_; | 1263   const intptr_t token_pos_; | 
| 1135 | 1264 | 
| 1136   DISALLOW_COPY_AND_ASSIGN(ReThrowInstr); | 1265   DISALLOW_COPY_AND_ASSIGN(ReThrowInstr); | 
| 1137 }; | 1266 }; | 
| 1138 | 1267 | 
| 1139 | 1268 | 
| 1140 class GotoInstr : public TemplateInstruction<0> { | 1269 class GotoInstr : public TemplateInstruction<0> { | 
| 1141  public: | 1270  public: | 
| 1142   explicit GotoInstr(JoinEntryInstr* entry) | 1271   explicit GotoInstr(JoinEntryInstr* entry) | 
| 1143     : successor_(entry), | 1272     : successor_(entry), | 
| 1144       parallel_move_(NULL) { } | 1273       parallel_move_(NULL) { } | 
| 1145 | 1274 | 
| 1146   DECLARE_INSTRUCTION(Goto) | 1275   DECLARE_INSTRUCTION(Goto) | 
| 1147 | 1276 | 
| 1148   virtual intptr_t ArgumentCount() const { return 0; } | 1277   virtual intptr_t ArgumentCount() const { return 0; } | 
| 1149 | 1278 | 
| 1150   JoinEntryInstr* successor() const { return successor_; } | 1279   JoinEntryInstr* successor() const { return successor_; } | 
| 1151   void set_successor(JoinEntryInstr* successor) { successor_ = successor; } | 1280   void set_successor(JoinEntryInstr* successor) { successor_ = successor; } | 
| 1152   virtual intptr_t SuccessorCount() const; | 1281   virtual intptr_t SuccessorCount() const; | 
| 1153   virtual BlockEntryInstr* SuccessorAt(intptr_t index) const; | 1282   virtual BlockEntryInstr* SuccessorAt(intptr_t index) const; | 
| 1154 | 1283 | 
| 1155   virtual LocationSummary* MakeLocationSummary() const; |  | 
| 1156 |  | 
| 1157   virtual void EmitNativeCode(FlowGraphCompiler* compiler); |  | 
| 1158 |  | 
| 1159   virtual bool CanDeoptimize() const { return false; } | 1284   virtual bool CanDeoptimize() const { return false; } | 
| 1160 | 1285 | 
| 1161   ParallelMoveInstr* parallel_move() const { | 1286   ParallelMoveInstr* parallel_move() const { | 
| 1162     return parallel_move_; | 1287     return parallel_move_; | 
| 1163   } | 1288   } | 
| 1164 | 1289 | 
| 1165   bool HasParallelMove() const { | 1290   bool HasParallelMove() const { | 
| 1166     return parallel_move_ != NULL; | 1291     return parallel_move_ != NULL; | 
| 1167   } | 1292   } | 
| 1168 | 1293 | 
| 1169   ParallelMoveInstr* GetParallelMove() { | 1294   ParallelMoveInstr* GetParallelMove() { | 
| 1170     if (parallel_move_ == NULL) { | 1295     if (parallel_move_ == NULL) { | 
| 1171       parallel_move_ = new ParallelMoveInstr(); | 1296       parallel_move_ = new ParallelMoveInstr(); | 
| 1172     } | 1297     } | 
| 1173     return parallel_move_; | 1298     return parallel_move_; | 
| 1174   } | 1299   } | 
| 1175 | 1300 | 
|  | 1301   virtual void PrintTo(BufferFormatter* f) const; | 
|  | 1302   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
|  | 1303 | 
| 1176  private: | 1304  private: | 
| 1177   JoinEntryInstr* successor_; | 1305   JoinEntryInstr* successor_; | 
| 1178 | 1306 | 
| 1179   // Parallel move that will be used by linear scan register allocator to | 1307   // Parallel move that will be used by linear scan register allocator to | 
| 1180   // connect live ranges at the end of the block and resolve phis. | 1308   // connect live ranges at the end of the block and resolve phis. | 
| 1181   ParallelMoveInstr* parallel_move_; | 1309   ParallelMoveInstr* parallel_move_; | 
| 1182 }; | 1310 }; | 
| 1183 | 1311 | 
| 1184 | 1312 | 
| 1185 class ControlInstruction : public Instruction { | 1313 class ControlInstruction : public Instruction { | 
| (...skipping 27 matching lines...) Expand all  Loading... | 
| 1213  private: | 1341  private: | 
| 1214   TargetEntryInstr* true_successor_; | 1342   TargetEntryInstr* true_successor_; | 
| 1215   TargetEntryInstr* false_successor_; | 1343   TargetEntryInstr* false_successor_; | 
| 1216 | 1344 | 
| 1217   DISALLOW_COPY_AND_ASSIGN(ControlInstruction); | 1345   DISALLOW_COPY_AND_ASSIGN(ControlInstruction); | 
| 1218 }; | 1346 }; | 
| 1219 | 1347 | 
| 1220 | 1348 | 
| 1221 class BranchInstr : public ControlInstruction { | 1349 class BranchInstr : public ControlInstruction { | 
| 1222  public: | 1350  public: | 
| 1223   explicit BranchInstr(ComparisonComp* computation) | 1351   explicit BranchInstr(ComparisonInstr* comparison) | 
| 1224       : computation_(computation), locs_(NULL) { } | 1352       : comparison_(comparison) { } | 
| 1225 | 1353 | 
| 1226   DECLARE_INSTRUCTION(Branch) | 1354   DECLARE_INSTRUCTION(Branch) | 
| 1227 | 1355 | 
| 1228   virtual intptr_t ArgumentCount() const; | 1356   virtual intptr_t ArgumentCount() const; | 
| 1229   intptr_t InputCount() const; | 1357   intptr_t InputCount() const; | 
| 1230   Value* InputAt(intptr_t i) const; | 1358   Value* InputAt(intptr_t i) const; | 
| 1231   void SetInputAt(intptr_t i, Value* value); | 1359   void SetInputAt(intptr_t i, Value* value); | 
| 1232   virtual bool CanDeoptimize() const; | 1360   virtual bool CanDeoptimize() const; | 
| 1233 | 1361 | 
| 1234   ComparisonComp* computation() const { return computation_; } | 1362   ComparisonInstr* comparison() const { return comparison_; } | 
| 1235   void set_computation(ComparisonComp* value) { computation_ = value; } | 1363   void set_comparison(ComparisonInstr* value) { comparison_ = value; } | 
| 1236 |  | 
| 1237   virtual void EmitNativeCode(FlowGraphCompiler* compiler); |  | 
| 1238 | 1364 | 
| 1239   virtual LocationSummary* locs(); | 1365   virtual LocationSummary* locs(); | 
| 1240   virtual intptr_t DeoptimizationTarget() const; | 1366   virtual intptr_t DeoptimizationTarget() const; | 
| 1241   virtual Representation RequiredInputRepresentation(intptr_t i) const; | 1367   virtual Representation RequiredInputRepresentation(intptr_t i) const; | 
| 1242 | 1368 | 
|  | 1369   // Replace the comparison with another, leaving the branch intact. | 
|  | 1370   void ReplaceWith(ComparisonInstr* other, | 
|  | 1371                    ForwardInstructionIterator* ignored) { | 
|  | 1372     comparison_ = other; | 
|  | 1373   } | 
|  | 1374 | 
|  | 1375   virtual void PrintTo(BufferFormatter* f) const; | 
|  | 1376   virtual void PrintToVisualizer(BufferFormatter* f) const; | 
|  | 1377 | 
| 1243  private: | 1378  private: | 
| 1244   ComparisonComp* computation_; | 1379   ComparisonInstr* comparison_; | 
| 1245   LocationSummary* locs_; |  | 
| 1246 | 1380 | 
| 1247   DISALLOW_COPY_AND_ASSIGN(BranchInstr); | 1381   DISALLOW_COPY_AND_ASSIGN(BranchInstr); | 
| 1248 }; | 1382 }; | 
| 1249 | 1383 | 
| 1250 | 1384 | 
| 1251 #undef DECLARE_INSTRUCTION | 1385 template<intptr_t N> | 
|  | 1386 class TemplateDefinition : public Definition { | 
|  | 1387  public: | 
|  | 1388   TemplateDefinition<N>() : locs_(NULL) { } | 
| 1252 | 1389 | 
| 1253 | 1390   virtual intptr_t InputCount() const { return N; } | 
| 1254 // M is a two argument macro.  It is applied to each concrete instruction's | 1391   virtual Value* InputAt(intptr_t i) const { return inputs_[i]; } | 
| 1255 // (including the values) typename and classname. | 1392   virtual void SetInputAt(intptr_t i, Value* value) { | 
| 1256 #define FOR_EACH_COMPUTATION(M)                                                \ | 1393     ASSERT(value != NULL); | 
| 1257   M(AssertAssignable, AssertAssignableComp)                                    \ | 1394     inputs_[i] = value; | 
| 1258   M(AssertBoolean, AssertBooleanComp)                                          \ |  | 
| 1259   M(ArgumentDefinitionTest, ArgumentDefinitionTestComp)                        \ |  | 
| 1260   M(CurrentContext, CurrentContextComp)                                        \ |  | 
| 1261   M(StoreContext, StoreContextComp)                                            \ |  | 
| 1262   M(ClosureCall, ClosureCallComp)                                              \ |  | 
| 1263   M(InstanceCall, InstanceCallComp)                                            \ |  | 
| 1264   M(PolymorphicInstanceCall, PolymorphicInstanceCallComp)                      \ |  | 
| 1265   M(StaticCall, StaticCallComp)                                                \ |  | 
| 1266   M(LoadLocal, LoadLocalComp)                                                  \ |  | 
| 1267   M(StoreLocal, StoreLocalComp)                                                \ |  | 
| 1268   M(StrictCompare, StrictCompareComp)                                          \ |  | 
| 1269   M(EqualityCompare, EqualityCompareComp)                                      \ |  | 
| 1270   M(RelationalOp, RelationalOpComp)                                            \ |  | 
| 1271   M(NativeCall, NativeCallComp)                                                \ |  | 
| 1272   M(LoadIndexed, LoadIndexedComp)                                              \ |  | 
| 1273   M(StoreIndexed, StoreIndexedComp)                                            \ |  | 
| 1274   M(LoadInstanceField, LoadInstanceFieldComp)                                  \ |  | 
| 1275   M(StoreInstanceField, StoreInstanceFieldComp)                                \ |  | 
| 1276   M(LoadStaticField, LoadStaticFieldComp)                                      \ |  | 
| 1277   M(StoreStaticField, StoreStaticFieldComp)                                    \ |  | 
| 1278   M(BooleanNegate, BooleanNegateComp)                                          \ |  | 
| 1279   M(InstanceOf, InstanceOfComp)                                                \ |  | 
| 1280   M(CreateArray, CreateArrayComp)                                              \ |  | 
| 1281   M(CreateClosure, CreateClosureComp)                                          \ |  | 
| 1282   M(AllocateObject, AllocateObjectComp)                                        \ |  | 
| 1283   M(AllocateObjectWithBoundsCheck, AllocateObjectWithBoundsCheckComp)          \ |  | 
| 1284   M(LoadVMField, LoadVMFieldComp)                                              \ |  | 
| 1285   M(StoreVMField, StoreVMFieldComp)                                            \ |  | 
| 1286   M(InstantiateTypeArguments, InstantiateTypeArgumentsComp)                    \ |  | 
| 1287   M(ExtractConstructorTypeArguments, ExtractConstructorTypeArgumentsComp)      \ |  | 
| 1288   M(ExtractConstructorInstantiator, ExtractConstructorInstantiatorComp)        \ |  | 
| 1289   M(AllocateContext, AllocateContextComp)                                      \ |  | 
| 1290   M(ChainContext, ChainContextComp)                                            \ |  | 
| 1291   M(CloneContext, CloneContextComp)                                            \ |  | 
| 1292   M(CatchEntry, CatchEntryComp)                                                \ |  | 
| 1293   M(BinarySmiOp, BinarySmiOpComp)                                              \ |  | 
| 1294   M(BinaryMintOp, BinaryMintOpComp)                                            \ |  | 
| 1295   M(UnarySmiOp, UnarySmiOpComp)                                                \ |  | 
| 1296   M(NumberNegate, NumberNegateComp)                                            \ |  | 
| 1297   M(CheckStackOverflow, CheckStackOverflowComp)                                \ |  | 
| 1298   M(DoubleToDouble, DoubleToDoubleComp)                                        \ |  | 
| 1299   M(SmiToDouble, SmiToDoubleComp)                                              \ |  | 
| 1300   M(CheckClass, CheckClassComp)                                                \ |  | 
| 1301   M(CheckSmi, CheckSmiComp)                                                    \ |  | 
| 1302   M(Constant, ConstantComp)                                                    \ |  | 
| 1303   M(CheckEitherNonSmi, CheckEitherNonSmiComp)                                  \ |  | 
| 1304   M(UnboxedDoubleBinaryOp, UnboxedDoubleBinaryOpComp)                          \ |  | 
| 1305   M(UnboxDouble, UnboxDoubleComp)                                              \ |  | 
| 1306   M(BoxDouble, BoxDoubleComp)                                                  \ |  | 
| 1307   M(CheckArrayBound, CheckArrayBoundComp) |  | 
| 1308 |  | 
| 1309 |  | 
| 1310 #define FORWARD_DECLARATION(ShortName, ClassName) class ClassName; |  | 
| 1311 FOR_EACH_COMPUTATION(FORWARD_DECLARATION) |  | 
| 1312 #undef FORWARD_DECLARATION |  | 
| 1313 |  | 
| 1314 |  | 
| 1315 class Computation : public ZoneAllocated { |  | 
| 1316  public: |  | 
| 1317   Computation() |  | 
| 1318       : deopt_id_(Isolate::Current()->GetNextDeoptId()), locs_(NULL) { } |  | 
| 1319 |  | 
| 1320   // Unique id used for deoptimization. |  | 
| 1321   virtual intptr_t deopt_id() const { |  | 
| 1322     ASSERT(CanDeoptimize()); |  | 
| 1323     return deopt_id_; |  | 
| 1324   } | 1395   } | 
| 1325 | 1396 | 
| 1326   // Visiting support. | 1397   // Returns a structure describing the location constraints required | 
| 1327   virtual void Accept(FlowGraphVisitor* visitor, BindInstr* instr) = 0; | 1398   // to emit native code for this definition. | 
| 1328 |  | 
| 1329   virtual intptr_t InputCount() const = 0; |  | 
| 1330   virtual Value* InputAt(intptr_t i) const = 0; |  | 
| 1331   virtual void SetInputAt(intptr_t i, Value* value) = 0; |  | 
| 1332 |  | 
| 1333   // Call computations override this function and return the |  | 
| 1334   // number of pushed arguments. |  | 
| 1335   virtual intptr_t ArgumentCount() const = 0; |  | 
| 1336 |  | 
| 1337   // Returns true, if this computation can deoptimize. |  | 
| 1338   virtual bool CanDeoptimize() const  = 0; |  | 
| 1339 |  | 
| 1340   // Returns a replacement for the instruction that wraps this computation. |  | 
| 1341   // Returns NULL if instr can be eliminated. |  | 
| 1342   // By default returns instr (input parameter) which means no change. |  | 
| 1343   virtual Definition* TryReplace(BindInstr* instr) const; |  | 
| 1344 |  | 
| 1345   // Compares two computations. Returns true, if: |  | 
| 1346   // 1. They are of the same kind. |  | 
| 1347   // 2. All input operands match. |  | 
| 1348   // 3. All other attributes match. |  | 
| 1349   bool Equals(Computation* other) const; |  | 
| 1350 |  | 
| 1351   // Returns a hash code for use with hash maps. |  | 
| 1352   virtual intptr_t Hashcode() const; |  | 
| 1353 |  | 
| 1354   // Compare attributes of an computation (except input operands and kind). |  | 
| 1355   // All computations that participate in CSE have to override this function. |  | 
| 1356   virtual bool AttributesEqual(Computation* other) const { |  | 
| 1357     UNREACHABLE(); |  | 
| 1358     return false; |  | 
| 1359   } |  | 
| 1360 |  | 
| 1361   // Returns true if the instruction may have side effects. |  | 
| 1362   // TODO(fschneider): Make this abstract and implement for all computations |  | 
| 1363   // instead of returning the safe default (true). |  | 
| 1364   virtual bool HasSideEffect() const { return true; } |  | 
| 1365 |  | 
| 1366   // Compile time type of the computation, which typically depends on the |  | 
| 1367   // compile time types (and possibly propagated types) of its inputs. |  | 
| 1368   virtual RawAbstractType* CompileType() const = 0; |  | 
| 1369   virtual intptr_t ResultCid() const = 0; |  | 
| 1370 |  | 
| 1371   // Mutate assigned_vars to add the local variable index for all |  | 
| 1372   // frame-allocated locals assigned to by the computation. |  | 
| 1373   virtual void RecordAssignedVars(BitVector* assigned_vars, |  | 
| 1374                                   intptr_t fixed_parameter_count); |  | 
| 1375 |  | 
| 1376   virtual const char* DebugName() const = 0; |  | 
| 1377 |  | 
| 1378   // Printing support. These functions are sometimes overridden for custom |  | 
| 1379   // formatting. Otherwise, it prints in the format "opcode(op1, op2, op3)". |  | 
| 1380   virtual void PrintTo(BufferFormatter* f) const; |  | 
| 1381   virtual void PrintOperandsTo(BufferFormatter* f) const; |  | 
| 1382 |  | 
| 1383   // Returns structure describing location constraints required |  | 
| 1384   // to emit native code for this computation. |  | 
| 1385   LocationSummary* locs() { | 1399   LocationSummary* locs() { | 
| 1386     if (locs_ == NULL) { | 1400     if (locs_ == NULL) { | 
| 1387       locs_ = MakeLocationSummary(); | 1401       locs_ = MakeLocationSummary(); | 
| 1388     } | 1402     } | 
| 1389     return locs_; | 1403     return locs_; | 
| 1390   } | 1404   } | 
| 1391 | 1405 | 
| 1392   virtual ComparisonComp* AsComparison() { return NULL; } |  | 
| 1393 |  | 
| 1394   // Create a location summary for this computation. |  | 
| 1395   // TODO(fschneider): Temporarily returns NULL for instructions |  | 
| 1396   // that are not yet converted to the location based code generation. |  | 
| 1397   virtual LocationSummary* MakeLocationSummary() const = 0; |  | 
| 1398 |  | 
| 1399   // TODO(fschneider): Make EmitNativeCode and locs const. |  | 
| 1400   virtual void EmitNativeCode(FlowGraphCompiler* compiler) = 0; |  | 
| 1401 |  | 
| 1402   virtual void EmitBranchCode(FlowGraphCompiler* compiler, |  | 
| 1403                               BranchInstr* branch) { |  | 
| 1404     UNREACHABLE(); |  | 
| 1405   } |  | 
| 1406 |  | 
| 1407   static LocationSummary* MakeCallSummary(); |  | 
| 1408 |  | 
| 1409   // Declare an enum value used to define kind-test predicates. |  | 
| 1410   enum ComputationKind { |  | 
| 1411 #define DECLARE_COMPUTATION_KIND(ShortName, ClassName) k##ShortName, |  | 
| 1412 |  | 
| 1413   FOR_EACH_COMPUTATION(DECLARE_COMPUTATION_KIND) |  | 
| 1414 |  | 
| 1415 #undef DECLARE_COMPUTATION_KIND |  | 
| 1416   }; |  | 
| 1417 |  | 
| 1418   virtual ComputationKind computation_kind() const = 0; |  | 
| 1419 |  | 
| 1420   // Returns representation expected for the input operand at the given index. |  | 
| 1421   virtual Representation RequiredInputRepresentation(intptr_t idx) const { |  | 
| 1422     return kTagged; |  | 
| 1423   } |  | 
| 1424 |  | 
| 1425   // Representation of the value produced by this computation. |  | 
| 1426   virtual Representation representation() const { |  | 
| 1427     return kTagged; |  | 
| 1428   } |  | 
| 1429 |  | 
| 1430   // Returns deoptimization id that corresponds to the deoptimization target |  | 
| 1431   // that input operands conversions inserted for this instruction can jump |  | 
| 1432   // to. Can return kNoDeoptId. |  | 
| 1433   virtual intptr_t DeoptimizationTarget() const { |  | 
| 1434     UNREACHABLE(); |  | 
| 1435     return Isolate::kNoDeoptId; |  | 
| 1436   } |  | 
| 1437 |  | 
| 1438   // Declare predicate for each computation. |  | 
| 1439 #define DECLARE_PREDICATE(ShortName, ClassName)                                \ |  | 
| 1440   inline bool Is##ShortName() const;                                           \ |  | 
| 1441   inline const ClassName* As##ShortName() const;                               \ |  | 
| 1442   inline ClassName* As##ShortName(); |  | 
| 1443 FOR_EACH_COMPUTATION(DECLARE_PREDICATE) |  | 
| 1444 #undef DECLARE_PREDICATE |  | 
| 1445 |  | 
| 1446  protected: | 1406  protected: | 
| 1447   // Fetch deopt id without checking if this computation can deoptimize. | 1407   EmbeddedArray<Value*, N> inputs_; | 
| 1448   intptr_t GetDeoptId() const { |  | 
| 1449     return deopt_id_; |  | 
| 1450   } |  | 
| 1451 | 1408 | 
| 1452  private: | 1409  private: | 
| 1453   friend class BranchInstr; | 1410   friend class BranchInstr; | 
| 1454 | 1411 | 
| 1455   intptr_t deopt_id_; |  | 
| 1456   LocationSummary* locs_; | 1412   LocationSummary* locs_; | 
| 1457 |  | 
| 1458   DISALLOW_COPY_AND_ASSIGN(Computation); |  | 
| 1459 }; | 1413 }; | 
| 1460 | 1414 | 
| 1461 | 1415 | 
| 1462 // Inlined functions from class BindInstr that forward to their computation. | 1416 class ConstantInstr : public TemplateDefinition<0> { | 
| 1463 inline intptr_t BindInstr::ArgumentCount() const { | 1417  public: | 
| 1464   return computation()->ArgumentCount(); | 1418   explicit ConstantInstr(const Object& value) : value_(value) { } | 
| 1465 } |  | 
| 1466 | 1419 | 
| 1467 | 1420   DECLARE_INSTRUCTION(Constant) | 
| 1468 inline intptr_t BindInstr::InputCount() const { | 1421   virtual RawAbstractType* CompileType() const; | 
| 1469   return computation()->InputCount(); |  | 
| 1470 } |  | 
| 1471 |  | 
| 1472 |  | 
| 1473 inline Value* BindInstr::InputAt(intptr_t i) const { |  | 
| 1474   return computation()->InputAt(i); |  | 
| 1475 } |  | 
| 1476 |  | 
| 1477 |  | 
| 1478 inline void BindInstr::SetInputAt(intptr_t i, Value* value) { |  | 
| 1479   computation()->SetInputAt(i, value); |  | 
| 1480 } |  | 
| 1481 |  | 
| 1482 inline bool BindInstr::CanDeoptimize() const { |  | 
| 1483   return computation()->CanDeoptimize(); |  | 
| 1484 } |  | 
| 1485 |  | 
| 1486 |  | 
| 1487 inline intptr_t BindInstr::Hashcode() const { |  | 
| 1488   return computation()->Hashcode(); |  | 
| 1489 } |  | 
| 1490 |  | 
| 1491 |  | 
| 1492 inline bool BindInstr::Equals(BindInstr* other) const { |  | 
| 1493   return computation()->Equals(other->computation()); |  | 
| 1494 } |  | 
| 1495 |  | 
| 1496 |  | 
| 1497 inline LocationSummary* BindInstr::locs() { |  | 
| 1498   return computation()->locs(); |  | 
| 1499 } |  | 
| 1500 |  | 
| 1501 |  | 
| 1502 inline Representation BindInstr::RequiredInputRepresentation(intptr_t i) const { |  | 
| 1503   return computation()->RequiredInputRepresentation(i); |  | 
| 1504 } |  | 
| 1505 |  | 
| 1506 |  | 
| 1507 inline Representation BindInstr::representation() const { |  | 
| 1508   return computation()->representation(); |  | 
| 1509 } |  | 
| 1510 |  | 
| 1511 |  | 
| 1512 inline intptr_t BindInstr::DeoptimizationTarget() const { |  | 
| 1513   return computation()->DeoptimizationTarget(); |  | 
| 1514 } |  | 
| 1515 |  | 
| 1516 |  | 
| 1517 template<intptr_t N> |  | 
| 1518 class TemplateComputation : public Computation { |  | 
| 1519  public: |  | 
| 1520   virtual intptr_t InputCount() const { return N; } |  | 
| 1521   virtual Value* InputAt(intptr_t i) const { return inputs_[i]; } |  | 
| 1522   virtual void SetInputAt(intptr_t i, Value* value) { |  | 
| 1523     ASSERT(value != NULL); |  | 
| 1524     inputs_[i] = value; |  | 
| 1525   } |  | 
| 1526 |  | 
| 1527  protected: |  | 
| 1528   EmbeddedArray<Value*, N> inputs_; |  | 
| 1529 }; |  | 
| 1530 |  | 
| 1531 |  | 
| 1532 // Functions defined in all concrete computation classes. |  | 
| 1533 #define DECLARE_COMPUTATION(ShortName)                                         \ |  | 
| 1534   virtual void Accept(FlowGraphVisitor* visitor, BindInstr* instr);            \ |  | 
| 1535   virtual ComputationKind computation_kind() const {                           \ |  | 
| 1536     return Computation::k##ShortName;                                          \ |  | 
| 1537   }                                                                            \ |  | 
| 1538   virtual intptr_t ArgumentCount() const { return 0; }                         \ |  | 
| 1539   virtual const char* DebugName() const { return #ShortName; }                 \ |  | 
| 1540   virtual RawAbstractType* CompileType() const;                                \ |  | 
| 1541   virtual LocationSummary* MakeLocationSummary() const;                        \ |  | 
| 1542   virtual void EmitNativeCode(FlowGraphCompiler* compiler); |  | 
| 1543 |  | 
| 1544 |  | 
| 1545 // Function defined in all call computation classes. |  | 
| 1546 #define DECLARE_CALL_COMPUTATION(ShortName)                                    \ |  | 
| 1547   virtual void Accept(FlowGraphVisitor* visitor, BindInstr* instr);            \ |  | 
| 1548   virtual ComputationKind computation_kind() const {                           \ |  | 
| 1549     return Computation::k##ShortName;                                          \ |  | 
| 1550   }                                                                            \ |  | 
| 1551   virtual const char* DebugName() const { return #ShortName; }                 \ |  | 
| 1552   virtual RawAbstractType* CompileType() const;                                \ |  | 
| 1553   virtual LocationSummary* MakeLocationSummary() const;                        \ |  | 
| 1554   virtual void EmitNativeCode(FlowGraphCompiler* compiler); |  | 
| 1555 |  | 
| 1556 |  | 
| 1557 class ConstantComp : public TemplateComputation<0> { |  | 
| 1558  public: |  | 
| 1559   explicit ConstantComp(const Object& value) : value_(value) { } |  | 
| 1560 |  | 
| 1561   DECLARE_COMPUTATION(Constant) |  | 
| 1562 | 1422 | 
| 1563   const Object& value() const { return value_; } | 1423   const Object& value() const { return value_; } | 
| 1564 | 1424 | 
| 1565   virtual void PrintOperandsTo(BufferFormatter* f) const; | 1425   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 1566 | 1426 | 
| 1567   virtual bool CanDeoptimize() const { return false; } | 1427   virtual bool CanDeoptimize() const { return false; } | 
| 1568 | 1428 | 
| 1569   virtual intptr_t ResultCid() const; | 1429   virtual intptr_t ResultCid() const; | 
| 1570 | 1430 | 
| 1571   virtual bool AttributesEqual(Computation* other) const; | 1431   virtual bool AttributesEqual(Definition* other) const; | 
| 1572 | 1432 | 
| 1573  private: | 1433  private: | 
| 1574   const Object& value_; | 1434   const Object& value_; | 
| 1575 | 1435 | 
| 1576   DISALLOW_COPY_AND_ASSIGN(ConstantComp); | 1436   DISALLOW_COPY_AND_ASSIGN(ConstantInstr); | 
| 1577 }; | 1437 }; | 
| 1578 | 1438 | 
| 1579 | 1439 | 
| 1580 class AssertAssignableComp : public TemplateComputation<3> { | 1440 class AssertAssignableInstr : public TemplateDefinition<3> { | 
| 1581  public: | 1441  public: | 
| 1582   AssertAssignableComp(intptr_t token_pos, | 1442   AssertAssignableInstr(intptr_t token_pos, | 
| 1583                        Value* value, | 1443                         Value* value, | 
| 1584                        Value* instantiator, | 1444                         Value* instantiator, | 
| 1585                        Value* instantiator_type_arguments, | 1445                         Value* instantiator_type_arguments, | 
| 1586                        const AbstractType& dst_type, | 1446                         const AbstractType& dst_type, | 
| 1587                        const String& dst_name) | 1447                         const String& dst_name) | 
| 1588       : token_pos_(token_pos), | 1448       : token_pos_(token_pos), | 
| 1589         dst_type_(dst_type), | 1449         dst_type_(dst_type), | 
| 1590         dst_name_(dst_name), | 1450         dst_name_(dst_name), | 
| 1591         is_eliminated_(false) { | 1451         is_eliminated_(false) { | 
| 1592     ASSERT(value != NULL); | 1452     ASSERT(value != NULL); | 
| 1593     ASSERT(instantiator != NULL); | 1453     ASSERT(instantiator != NULL); | 
| 1594     ASSERT(instantiator_type_arguments != NULL); | 1454     ASSERT(instantiator_type_arguments != NULL); | 
| 1595     ASSERT(!dst_type.IsNull()); | 1455     ASSERT(!dst_type.IsNull()); | 
| 1596     ASSERT(!dst_name.IsNull()); | 1456     ASSERT(!dst_name.IsNull()); | 
| 1597     inputs_[0] = value; | 1457     inputs_[0] = value; | 
| 1598     inputs_[1] = instantiator; | 1458     inputs_[1] = instantiator; | 
| 1599     inputs_[2] = instantiator_type_arguments; | 1459     inputs_[2] = instantiator_type_arguments; | 
| 1600   } | 1460   } | 
| 1601 | 1461 | 
| 1602   DECLARE_COMPUTATION(AssertAssignable) | 1462   DECLARE_INSTRUCTION(AssertAssignable) | 
|  | 1463   virtual RawAbstractType* CompileType() const; | 
| 1603 | 1464 | 
| 1604   Value* value() const { return inputs_[0]; } | 1465   Value* value() const { return inputs_[0]; } | 
| 1605   Value* instantiator() const { return inputs_[1]; } | 1466   Value* instantiator() const { return inputs_[1]; } | 
| 1606   Value* instantiator_type_arguments() const { return inputs_[2]; } | 1467   Value* instantiator_type_arguments() const { return inputs_[2]; } | 
| 1607 | 1468 | 
| 1608   intptr_t token_pos() const { return token_pos_; } | 1469   intptr_t token_pos() const { return token_pos_; } | 
| 1609   const AbstractType& dst_type() const { return dst_type_; } | 1470   const AbstractType& dst_type() const { return dst_type_; } | 
| 1610   const String& dst_name() const { return dst_name_; } | 1471   const String& dst_name() const { return dst_name_; } | 
| 1611 | 1472 | 
| 1612   bool is_eliminated() const { | 1473   bool is_eliminated() const { | 
| 1613     return is_eliminated_; | 1474     return is_eliminated_; | 
| 1614   } | 1475   } | 
| 1615   void eliminate() { | 1476   void eliminate() { | 
| 1616     ASSERT(!is_eliminated_); | 1477     ASSERT(!is_eliminated_); | 
| 1617     is_eliminated_ = true; | 1478     is_eliminated_ = true; | 
| 1618   } | 1479   } | 
| 1619 | 1480 | 
| 1620   virtual void PrintOperandsTo(BufferFormatter* f) const; | 1481   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 1621 | 1482 | 
| 1622   virtual bool CanDeoptimize() const { return false; } | 1483   virtual bool CanDeoptimize() const { return false; } | 
| 1623   virtual intptr_t ResultCid() const { return kDynamicCid; } | 1484   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 1624 | 1485 | 
| 1625  private: | 1486  private: | 
| 1626   const intptr_t token_pos_; | 1487   const intptr_t token_pos_; | 
| 1627   const AbstractType& dst_type_; | 1488   const AbstractType& dst_type_; | 
| 1628   const String& dst_name_; | 1489   const String& dst_name_; | 
| 1629   bool is_eliminated_; | 1490   bool is_eliminated_; | 
| 1630 | 1491 | 
| 1631   DISALLOW_COPY_AND_ASSIGN(AssertAssignableComp); | 1492   DISALLOW_COPY_AND_ASSIGN(AssertAssignableInstr); | 
| 1632 }; | 1493 }; | 
| 1633 | 1494 | 
| 1634 | 1495 | 
| 1635 class AssertBooleanComp : public TemplateComputation<1> { | 1496 class AssertBooleanInstr : public TemplateDefinition<1> { | 
| 1636  public: | 1497  public: | 
| 1637   AssertBooleanComp(intptr_t token_pos, | 1498   AssertBooleanInstr(intptr_t token_pos, Value* value) | 
| 1638                     Value* value) |  | 
| 1639       : token_pos_(token_pos), | 1499       : token_pos_(token_pos), | 
| 1640         is_eliminated_(false) { | 1500         is_eliminated_(false) { | 
| 1641     ASSERT(value != NULL); | 1501     ASSERT(value != NULL); | 
| 1642     inputs_[0] = value; | 1502     inputs_[0] = value; | 
| 1643   } | 1503   } | 
| 1644 | 1504 | 
| 1645   DECLARE_COMPUTATION(AssertBoolean) | 1505   DECLARE_INSTRUCTION(AssertBoolean) | 
|  | 1506   virtual RawAbstractType* CompileType() const; | 
| 1646 | 1507 | 
| 1647   intptr_t token_pos() const { return token_pos_; } | 1508   intptr_t token_pos() const { return token_pos_; } | 
| 1648   Value* value() const { return inputs_[0]; } | 1509   Value* value() const { return inputs_[0]; } | 
| 1649 | 1510 | 
| 1650   bool is_eliminated() const { | 1511   bool is_eliminated() const { | 
| 1651     return is_eliminated_; | 1512     return is_eliminated_; | 
| 1652   } | 1513   } | 
| 1653   void eliminate() { | 1514   void eliminate() { | 
| 1654     ASSERT(!is_eliminated_); | 1515     ASSERT(!is_eliminated_); | 
| 1655     is_eliminated_ = true; | 1516     is_eliminated_ = true; | 
| 1656   } | 1517   } | 
| 1657 | 1518 | 
| 1658   virtual void PrintOperandsTo(BufferFormatter* f) const; | 1519   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 1659 | 1520 | 
| 1660   virtual bool CanDeoptimize() const { return false; } | 1521   virtual bool CanDeoptimize() const { return false; } | 
| 1661   virtual intptr_t ResultCid() const { return kBoolCid; } | 1522   virtual intptr_t ResultCid() const { return kBoolCid; } | 
| 1662 | 1523 | 
| 1663  private: | 1524  private: | 
| 1664   const intptr_t token_pos_; | 1525   const intptr_t token_pos_; | 
| 1665   bool is_eliminated_; | 1526   bool is_eliminated_; | 
| 1666 | 1527 | 
| 1667   DISALLOW_COPY_AND_ASSIGN(AssertBooleanComp); | 1528   DISALLOW_COPY_AND_ASSIGN(AssertBooleanInstr); | 
| 1668 }; | 1529 }; | 
| 1669 | 1530 | 
| 1670 | 1531 | 
| 1671 class ArgumentDefinitionTestComp : public TemplateComputation<1> { | 1532 class ArgumentDefinitionTestInstr : public TemplateDefinition<1> { | 
| 1672  public: | 1533  public: | 
| 1673   ArgumentDefinitionTestComp(ArgumentDefinitionTestNode* node, | 1534   ArgumentDefinitionTestInstr(ArgumentDefinitionTestNode* node, | 
| 1674                              Value* saved_arguments_descriptor) | 1535                               Value* saved_arguments_descriptor) | 
| 1675       : ast_node_(*node) { | 1536       : ast_node_(*node) { | 
| 1676     ASSERT(saved_arguments_descriptor != NULL); | 1537     ASSERT(saved_arguments_descriptor != NULL); | 
| 1677     inputs_[0] = saved_arguments_descriptor; | 1538     inputs_[0] = saved_arguments_descriptor; | 
| 1678   } | 1539   } | 
| 1679 | 1540 | 
| 1680   DECLARE_COMPUTATION(ArgumentDefinitionTest) | 1541   DECLARE_INSTRUCTION(ArgumentDefinitionTest) | 
|  | 1542   virtual RawAbstractType* CompileType() const; | 
| 1681 | 1543 | 
| 1682   intptr_t token_pos() const { return ast_node_.token_pos(); } | 1544   intptr_t token_pos() const { return ast_node_.token_pos(); } | 
| 1683   intptr_t formal_parameter_index() const { | 1545   intptr_t formal_parameter_index() const { | 
| 1684     return ast_node_.formal_parameter_index(); | 1546     return ast_node_.formal_parameter_index(); | 
| 1685   } | 1547   } | 
| 1686   const String& formal_parameter_name() const { | 1548   const String& formal_parameter_name() const { | 
| 1687     return ast_node_.formal_parameter_name(); | 1549     return ast_node_.formal_parameter_name(); | 
| 1688   } | 1550   } | 
| 1689   Value* saved_arguments_descriptor() const { return inputs_[0]; } | 1551   Value* saved_arguments_descriptor() const { return inputs_[0]; } | 
| 1690 | 1552 | 
| 1691   virtual void PrintOperandsTo(BufferFormatter* f) const; | 1553   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 1692 | 1554 | 
| 1693   virtual bool CanDeoptimize() const { return false; } | 1555   virtual bool CanDeoptimize() const { return false; } | 
| 1694   virtual intptr_t ResultCid() const { return kBoolCid; } | 1556   virtual intptr_t ResultCid() const { return kBoolCid; } | 
| 1695 | 1557 | 
| 1696  private: | 1558  private: | 
| 1697   const ArgumentDefinitionTestNode& ast_node_; | 1559   const ArgumentDefinitionTestNode& ast_node_; | 
| 1698 | 1560 | 
| 1699   DISALLOW_COPY_AND_ASSIGN(ArgumentDefinitionTestComp); | 1561   DISALLOW_COPY_AND_ASSIGN(ArgumentDefinitionTestInstr); | 
| 1700 }; | 1562 }; | 
| 1701 | 1563 | 
| 1702 | 1564 | 
| 1703 // Denotes the current context, normally held in a register.  This is | 1565 // Denotes the current context, normally held in a register.  This is | 
| 1704 // a computation, not a value, because it's mutable. | 1566 // a computation, not a value, because it's mutable. | 
| 1705 class CurrentContextComp : public TemplateComputation<0> { | 1567 class CurrentContextInstr : public TemplateDefinition<0> { | 
| 1706  public: | 1568  public: | 
| 1707   CurrentContextComp() { } | 1569   CurrentContextInstr() { } | 
| 1708 | 1570 | 
| 1709   DECLARE_COMPUTATION(CurrentContext) | 1571   DECLARE_INSTRUCTION(CurrentContext) | 
|  | 1572   virtual RawAbstractType* CompileType() const; | 
| 1710 | 1573 | 
| 1711   virtual bool CanDeoptimize() const { return false; } | 1574   virtual bool CanDeoptimize() const { return false; } | 
| 1712   virtual intptr_t ResultCid() const { return kDynamicCid; } | 1575   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 1713 | 1576 | 
| 1714  private: | 1577  private: | 
| 1715   DISALLOW_COPY_AND_ASSIGN(CurrentContextComp); | 1578   DISALLOW_COPY_AND_ASSIGN(CurrentContextInstr); | 
| 1716 }; | 1579 }; | 
| 1717 | 1580 | 
| 1718 | 1581 | 
| 1719 class StoreContextComp : public TemplateComputation<1> { | 1582 class StoreContextInstr : public TemplateDefinition<1> { | 
| 1720  public: | 1583  public: | 
| 1721   explicit StoreContextComp(Value* value) { | 1584   explicit StoreContextInstr(Value* value) { | 
| 1722     ASSERT(value != NULL); | 1585     ASSERT(value != NULL); | 
| 1723     inputs_[0] = value; | 1586     inputs_[0] = value; | 
| 1724   } | 1587   } | 
| 1725 | 1588 | 
| 1726   DECLARE_COMPUTATION(StoreContext); | 1589   DECLARE_INSTRUCTION(StoreContext); | 
|  | 1590   virtual RawAbstractType* CompileType() const; | 
| 1727 | 1591 | 
| 1728   Value* value() const { return inputs_[0]; } | 1592   Value* value() const { return inputs_[0]; } | 
| 1729 | 1593 | 
| 1730   virtual bool CanDeoptimize() const { return false; } | 1594   virtual bool CanDeoptimize() const { return false; } | 
| 1731   virtual intptr_t ResultCid() const { return kIllegalCid; } | 1595   virtual intptr_t ResultCid() const { return kIllegalCid; } | 
| 1732 | 1596 | 
| 1733  private: | 1597  private: | 
| 1734   DISALLOW_COPY_AND_ASSIGN(StoreContextComp); | 1598   DISALLOW_COPY_AND_ASSIGN(StoreContextInstr); | 
| 1735 }; | 1599 }; | 
| 1736 | 1600 | 
| 1737 | 1601 | 
| 1738 class ClosureCallComp : public TemplateComputation<0> { | 1602 class ClosureCallInstr : public TemplateDefinition<0> { | 
| 1739  public: | 1603  public: | 
| 1740   ClosureCallComp(ClosureCallNode* node, | 1604   ClosureCallInstr(ClosureCallNode* node, | 
| 1741                   ZoneGrowableArray<PushArgumentInstr*>* arguments) | 1605                    ZoneGrowableArray<PushArgumentInstr*>* arguments) | 
| 1742       : ast_node_(*node), | 1606       : ast_node_(*node), | 
| 1743         arguments_(arguments) { } | 1607         arguments_(arguments) { } | 
| 1744 | 1608 | 
| 1745   DECLARE_CALL_COMPUTATION(ClosureCall) | 1609   DECLARE_INSTRUCTION(ClosureCall) | 
|  | 1610   virtual RawAbstractType* CompileType() const; | 
| 1746 | 1611 | 
| 1747   const Array& argument_names() const { return ast_node_.arguments()->names(); } | 1612   const Array& argument_names() const { return ast_node_.arguments()->names(); } | 
| 1748   intptr_t token_pos() const { return ast_node_.token_pos(); } | 1613   intptr_t token_pos() const { return ast_node_.token_pos(); } | 
| 1749 | 1614 | 
| 1750   virtual intptr_t ArgumentCount() const { return arguments_->length(); } | 1615   virtual intptr_t ArgumentCount() const { return arguments_->length(); } | 
| 1751   PushArgumentInstr* ArgumentAt(intptr_t index) const { | 1616   PushArgumentInstr* ArgumentAt(intptr_t index) const { | 
| 1752     return (*arguments_)[index]; | 1617     return (*arguments_)[index]; | 
| 1753   } | 1618   } | 
| 1754 | 1619 | 
| 1755   virtual void PrintOperandsTo(BufferFormatter* f) const; | 1620   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 1756 | 1621 | 
| 1757   virtual bool CanDeoptimize() const { return true; } | 1622   virtual bool CanDeoptimize() const { return true; } | 
| 1758   virtual intptr_t ResultCid() const { return kDynamicCid; } | 1623   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 1759 | 1624 | 
| 1760  private: | 1625  private: | 
| 1761   const ClosureCallNode& ast_node_; | 1626   const ClosureCallNode& ast_node_; | 
| 1762   ZoneGrowableArray<PushArgumentInstr*>* arguments_; | 1627   ZoneGrowableArray<PushArgumentInstr*>* arguments_; | 
| 1763 | 1628 | 
| 1764   DISALLOW_COPY_AND_ASSIGN(ClosureCallComp); | 1629   DISALLOW_COPY_AND_ASSIGN(ClosureCallInstr); | 
| 1765 }; | 1630 }; | 
| 1766 | 1631 | 
| 1767 | 1632 | 
| 1768 class InstanceCallComp : public TemplateComputation<0> { | 1633 class InstanceCallInstr : public TemplateDefinition<0> { | 
| 1769  public: | 1634  public: | 
| 1770   InstanceCallComp(intptr_t token_pos, | 1635   InstanceCallInstr(intptr_t token_pos, | 
| 1771                    const String& function_name, | 1636                     const String& function_name, | 
| 1772                    Token::Kind token_kind, | 1637                     Token::Kind token_kind, | 
| 1773                    ZoneGrowableArray<PushArgumentInstr*>* arguments, | 1638                     ZoneGrowableArray<PushArgumentInstr*>* arguments, | 
| 1774                    const Array& argument_names, | 1639                     const Array& argument_names, | 
| 1775                    intptr_t checked_argument_count) | 1640                     intptr_t checked_argument_count) | 
| 1776       : ic_data_(Isolate::Current()->GetICDataForDeoptId(deopt_id())), | 1641       : ic_data_(Isolate::Current()->GetICDataForDeoptId(deopt_id())), | 
| 1777         token_pos_(token_pos), | 1642         token_pos_(token_pos), | 
| 1778         function_name_(function_name), | 1643         function_name_(function_name), | 
| 1779         token_kind_(token_kind), | 1644         token_kind_(token_kind), | 
| 1780         arguments_(arguments), | 1645         arguments_(arguments), | 
| 1781         argument_names_(argument_names), | 1646         argument_names_(argument_names), | 
| 1782         checked_argument_count_(checked_argument_count) { | 1647         checked_argument_count_(checked_argument_count) { | 
| 1783     ASSERT(function_name.IsZoneHandle()); | 1648     ASSERT(function_name.IsZoneHandle()); | 
| 1784     ASSERT(!arguments->is_empty()); | 1649     ASSERT(!arguments->is_empty()); | 
| 1785     ASSERT(argument_names.IsZoneHandle()); | 1650     ASSERT(argument_names.IsZoneHandle()); | 
| 1786     ASSERT(Token::IsBinaryToken(token_kind) || | 1651     ASSERT(Token::IsBinaryToken(token_kind) || | 
| 1787            Token::IsUnaryToken(token_kind) || | 1652            Token::IsUnaryToken(token_kind) || | 
| 1788            Token::IsIndexOperator(token_kind) || | 1653            Token::IsIndexOperator(token_kind) || | 
| 1789            token_kind == Token::kGET || | 1654            token_kind == Token::kGET || | 
| 1790            token_kind == Token::kSET || | 1655            token_kind == Token::kSET || | 
| 1791            token_kind == Token::kILLEGAL); | 1656            token_kind == Token::kILLEGAL); | 
| 1792   } | 1657   } | 
| 1793 | 1658 | 
| 1794   DECLARE_CALL_COMPUTATION(InstanceCall) | 1659   DECLARE_INSTRUCTION(InstanceCall) | 
|  | 1660   virtual RawAbstractType* CompileType() const; | 
| 1795 | 1661 | 
| 1796   const ICData* ic_data() const { return ic_data_; } | 1662   const ICData* ic_data() const { return ic_data_; } | 
| 1797   bool HasICData() const { | 1663   bool HasICData() const { | 
| 1798     return (ic_data() != NULL) && !ic_data()->IsNull(); | 1664     return (ic_data() != NULL) && !ic_data()->IsNull(); | 
| 1799   } | 1665   } | 
| 1800 | 1666 | 
| 1801   intptr_t token_pos() const { return token_pos_; } | 1667   intptr_t token_pos() const { return token_pos_; } | 
| 1802   const String& function_name() const { return function_name_; } | 1668   const String& function_name() const { return function_name_; } | 
| 1803   Token::Kind token_kind() const { return token_kind_; } | 1669   Token::Kind token_kind() const { return token_kind_; } | 
| 1804   virtual intptr_t ArgumentCount() const { return arguments_->length(); } | 1670   virtual intptr_t ArgumentCount() const { return arguments_->length(); } | 
| (...skipping 10 matching lines...) Expand all  Loading... | 
| 1815 | 1681 | 
| 1816  private: | 1682  private: | 
| 1817   const ICData* ic_data_; | 1683   const ICData* ic_data_; | 
| 1818   const intptr_t token_pos_; | 1684   const intptr_t token_pos_; | 
| 1819   const String& function_name_; | 1685   const String& function_name_; | 
| 1820   const Token::Kind token_kind_;  // Binary op, unary op, kGET or kILLEGAL. | 1686   const Token::Kind token_kind_;  // Binary op, unary op, kGET or kILLEGAL. | 
| 1821   ZoneGrowableArray<PushArgumentInstr*>* const arguments_; | 1687   ZoneGrowableArray<PushArgumentInstr*>* const arguments_; | 
| 1822   const Array& argument_names_; | 1688   const Array& argument_names_; | 
| 1823   const intptr_t checked_argument_count_; | 1689   const intptr_t checked_argument_count_; | 
| 1824 | 1690 | 
| 1825   DISALLOW_COPY_AND_ASSIGN(InstanceCallComp); | 1691   DISALLOW_COPY_AND_ASSIGN(InstanceCallInstr); | 
| 1826 }; | 1692 }; | 
| 1827 | 1693 | 
| 1828 | 1694 | 
| 1829 class PolymorphicInstanceCallComp : public TemplateComputation<0> { | 1695 class PolymorphicInstanceCallInstr : public TemplateDefinition<0> { | 
| 1830  public: | 1696  public: | 
| 1831   PolymorphicInstanceCallComp(InstanceCallComp* comp, | 1697   PolymorphicInstanceCallInstr(InstanceCallInstr* instance_call, | 
| 1832                               const ICData& ic_data, | 1698                                const ICData& ic_data, | 
| 1833                               bool with_checks) | 1699                                bool with_checks) | 
| 1834       : instance_call_(comp), ic_data_(ic_data), with_checks_(with_checks) { | 1700       : instance_call_(instance_call), | 
|  | 1701         ic_data_(ic_data), | 
|  | 1702         with_checks_(with_checks) { | 
| 1835     ASSERT(instance_call_ != NULL); | 1703     ASSERT(instance_call_ != NULL); | 
| 1836   } | 1704   } | 
| 1837 | 1705 | 
| 1838   InstanceCallComp* instance_call() const { return instance_call_; } | 1706   InstanceCallInstr* instance_call() const { return instance_call_; } | 
| 1839   bool with_checks() const { return with_checks_; } | 1707   bool with_checks() const { return with_checks_; } | 
| 1840 | 1708 | 
| 1841   void PrintTo(BufferFormatter* f) const; |  | 
| 1842 |  | 
| 1843   virtual intptr_t ArgumentCount() const { | 1709   virtual intptr_t ArgumentCount() const { | 
| 1844     return instance_call()->ArgumentCount(); | 1710     return instance_call()->ArgumentCount(); | 
| 1845   } | 1711   } | 
| 1846 | 1712 | 
| 1847   DECLARE_CALL_COMPUTATION(PolymorphicInstanceCall) | 1713   DECLARE_INSTRUCTION(PolymorphicInstanceCall) | 
|  | 1714   virtual RawAbstractType* CompileType() const; | 
| 1848 | 1715 | 
| 1849   const ICData& ic_data() const { return ic_data_; } | 1716   const ICData& ic_data() const { return ic_data_; } | 
| 1850 | 1717 | 
| 1851   virtual bool CanDeoptimize() const { return true; } | 1718   virtual bool CanDeoptimize() const { return true; } | 
| 1852   virtual intptr_t ResultCid() const { return kDynamicCid; } | 1719   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 1853 | 1720 | 
|  | 1721   virtual void PrintTo(BufferFormatter* f) const; | 
|  | 1722 | 
| 1854  private: | 1723  private: | 
| 1855   InstanceCallComp* instance_call_; | 1724   InstanceCallInstr* instance_call_; | 
| 1856   const ICData& ic_data_; | 1725   const ICData& ic_data_; | 
| 1857   const bool with_checks_; | 1726   const bool with_checks_; | 
| 1858 | 1727 | 
| 1859   DISALLOW_COPY_AND_ASSIGN(PolymorphicInstanceCallComp); | 1728   DISALLOW_COPY_AND_ASSIGN(PolymorphicInstanceCallInstr); | 
| 1860 }; | 1729 }; | 
| 1861 | 1730 | 
| 1862 | 1731 | 
| 1863 class ComparisonComp : public TemplateComputation<2> { | 1732 class ComparisonInstr : public TemplateDefinition<2> { | 
| 1864  public: | 1733  public: | 
| 1865   ComparisonComp(Token::Kind kind, Value* left, Value* right) : kind_(kind) { | 1734   ComparisonInstr(Token::Kind kind, Value* left, Value* right) : kind_(kind) { | 
| 1866     ASSERT(left != NULL); | 1735     ASSERT(left != NULL); | 
| 1867     ASSERT(right != NULL); | 1736     ASSERT(right != NULL); | 
| 1868     inputs_[0] = left; | 1737     inputs_[0] = left; | 
| 1869     inputs_[1] = right; | 1738     inputs_[1] = right; | 
| 1870   } | 1739   } | 
| 1871 | 1740 | 
| 1872   Value* left() const { return inputs_[0]; } | 1741   Value* left() const { return inputs_[0]; } | 
| 1873   Value* right() const { return inputs_[1]; } | 1742   Value* right() const { return inputs_[1]; } | 
| 1874 | 1743 | 
| 1875   virtual ComparisonComp* AsComparison() { return this; } | 1744   virtual ComparisonInstr* AsComparison() { return this; } | 
| 1876 | 1745 | 
| 1877   Token::Kind kind() const { return kind_; } | 1746   Token::Kind kind() const { return kind_; } | 
| 1878 | 1747 | 
|  | 1748   virtual void EmitBranchCode(FlowGraphCompiler* compiler, | 
|  | 1749                               BranchInstr* branch) = 0; | 
|  | 1750 | 
| 1879  private: | 1751  private: | 
| 1880   Token::Kind kind_; | 1752   Token::Kind kind_; | 
| 1881 }; | 1753 }; | 
| 1882 | 1754 | 
| 1883 | 1755 | 
| 1884 // Inlined functions from class BranchInstr that forward to their comparison. | 1756 // Inlined functions from class BranchInstr that forward to their comparison. | 
| 1885 inline intptr_t BranchInstr::ArgumentCount() const { | 1757 inline intptr_t BranchInstr::ArgumentCount() const { | 
| 1886   return computation()->ArgumentCount(); | 1758   return comparison()->ArgumentCount(); | 
| 1887 } | 1759 } | 
| 1888 | 1760 | 
| 1889 | 1761 | 
| 1890 inline intptr_t BranchInstr::InputCount() const { | 1762 inline intptr_t BranchInstr::InputCount() const { | 
| 1891   return computation()->InputCount(); | 1763   return comparison()->InputCount(); | 
| 1892 } | 1764 } | 
| 1893 | 1765 | 
| 1894 | 1766 | 
| 1895 inline Value* BranchInstr::InputAt(intptr_t i) const { | 1767 inline Value* BranchInstr::InputAt(intptr_t i) const { | 
| 1896   return computation()->InputAt(i); | 1768   return comparison()->InputAt(i); | 
| 1897 } | 1769 } | 
| 1898 | 1770 | 
| 1899 | 1771 | 
| 1900 inline void BranchInstr::SetInputAt(intptr_t i, Value* value) { | 1772 inline void BranchInstr::SetInputAt(intptr_t i, Value* value) { | 
| 1901   computation()->SetInputAt(i, value); | 1773   comparison()->SetInputAt(i, value); | 
| 1902 } | 1774 } | 
| 1903 | 1775 | 
| 1904 | 1776 | 
| 1905 inline bool BranchInstr::CanDeoptimize() const { | 1777 inline bool BranchInstr::CanDeoptimize() const { | 
| 1906   return computation()->CanDeoptimize(); | 1778   return comparison()->CanDeoptimize(); | 
| 1907 } | 1779 } | 
| 1908 | 1780 | 
| 1909 | 1781 | 
| 1910 inline LocationSummary* BranchInstr::locs() { | 1782 inline LocationSummary* BranchInstr::locs() { | 
| 1911   if (computation_->locs_ == NULL) { | 1783   if (comparison()->locs_ == NULL) { | 
| 1912     LocationSummary* summary = computation_->MakeLocationSummary(); | 1784     LocationSummary* summary = comparison()->MakeLocationSummary(); | 
| 1913     // Branches don't produce a result. | 1785     // Branches don't produce a result. | 
| 1914     summary->set_out(Location::NoLocation()); | 1786     summary->set_out(Location::NoLocation()); | 
| 1915     computation_->locs_ = summary; | 1787     comparison()->locs_ = summary; | 
| 1916   } | 1788   } | 
| 1917   return computation_->locs_; | 1789   return comparison()->locs_; | 
| 1918 } | 1790 } | 
| 1919 | 1791 | 
| 1920 | 1792 | 
| 1921 inline intptr_t BranchInstr::DeoptimizationTarget() const { | 1793 inline intptr_t BranchInstr::DeoptimizationTarget() const { | 
| 1922   return computation_->DeoptimizationTarget(); | 1794   return comparison()->DeoptimizationTarget(); | 
| 1923 } | 1795 } | 
| 1924 | 1796 | 
| 1925 | 1797 | 
| 1926 inline Representation BranchInstr::RequiredInputRepresentation( | 1798 inline Representation BranchInstr::RequiredInputRepresentation( | 
| 1927     intptr_t i) const { | 1799     intptr_t i) const { | 
| 1928   return computation()->RequiredInputRepresentation(i); | 1800   return comparison()->RequiredInputRepresentation(i); | 
| 1929 } | 1801 } | 
| 1930 | 1802 | 
| 1931 | 1803 | 
| 1932 class StrictCompareComp : public ComparisonComp { | 1804 class StrictCompareInstr : public ComparisonInstr { | 
| 1933  public: | 1805  public: | 
| 1934   StrictCompareComp(Token::Kind kind, Value* left, Value* right) | 1806   StrictCompareInstr(Token::Kind kind, Value* left, Value* right) | 
| 1935       : ComparisonComp(kind, left, right) { | 1807       : ComparisonInstr(kind, left, right) { | 
| 1936     ASSERT((kind == Token::kEQ_STRICT) || (kind == Token::kNE_STRICT)); | 1808     ASSERT((kind == Token::kEQ_STRICT) || (kind == Token::kNE_STRICT)); | 
| 1937   } | 1809   } | 
| 1938 | 1810 | 
| 1939   DECLARE_COMPUTATION(StrictCompare) | 1811   DECLARE_INSTRUCTION(StrictCompare) | 
|  | 1812   virtual RawAbstractType* CompileType() const; | 
| 1940 | 1813 | 
| 1941   virtual void PrintOperandsTo(BufferFormatter* f) const; | 1814   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 1942 | 1815 | 
| 1943   virtual bool CanDeoptimize() const { return false; } | 1816   virtual bool CanDeoptimize() const { return false; } | 
| 1944 | 1817 | 
| 1945   virtual Definition* TryReplace(BindInstr* instr) const; | 1818   virtual Definition* Canonicalize(); | 
| 1946 | 1819 | 
| 1947   virtual intptr_t ResultCid() const { return kBoolCid; } | 1820   virtual intptr_t ResultCid() const { return kBoolCid; } | 
| 1948 | 1821 | 
| 1949   virtual void EmitBranchCode(FlowGraphCompiler* compiler, | 1822   virtual void EmitBranchCode(FlowGraphCompiler* compiler, | 
| 1950                               BranchInstr* branch); | 1823                               BranchInstr* branch); | 
| 1951 | 1824 | 
| 1952  private: | 1825  private: | 
| 1953   DISALLOW_COPY_AND_ASSIGN(StrictCompareComp); | 1826   DISALLOW_COPY_AND_ASSIGN(StrictCompareInstr); | 
| 1954 }; | 1827 }; | 
| 1955 | 1828 | 
| 1956 | 1829 | 
| 1957 class EqualityCompareComp : public ComparisonComp { | 1830 class EqualityCompareInstr : public ComparisonInstr { | 
| 1958  public: | 1831  public: | 
| 1959   EqualityCompareComp(intptr_t token_pos, | 1832   EqualityCompareInstr(intptr_t token_pos, | 
| 1960                       Token::Kind kind, | 1833                        Token::Kind kind, | 
| 1961                       Value* left, | 1834                        Value* left, | 
| 1962                       Value* right) | 1835                        Value* right) | 
| 1963       : ComparisonComp(kind, left, right), | 1836       : ComparisonInstr(kind, left, right), | 
| 1964         ic_data_(Isolate::Current()->GetICDataForDeoptId(deopt_id())), | 1837         ic_data_(Isolate::Current()->GetICDataForDeoptId(deopt_id())), | 
| 1965         token_pos_(token_pos), | 1838         token_pos_(token_pos), | 
| 1966         receiver_class_id_(kIllegalCid) { | 1839         receiver_class_id_(kIllegalCid) { | 
| 1967     ASSERT((kind == Token::kEQ) || (kind == Token::kNE)); | 1840     ASSERT((kind == Token::kEQ) || (kind == Token::kNE)); | 
| 1968   } | 1841   } | 
| 1969 | 1842 | 
| 1970   DECLARE_COMPUTATION(EqualityCompare) | 1843   DECLARE_INSTRUCTION(EqualityCompare) | 
|  | 1844   virtual RawAbstractType* CompileType() const; | 
| 1971 | 1845 | 
| 1972   const ICData* ic_data() const { return ic_data_; } | 1846   const ICData* ic_data() const { return ic_data_; } | 
| 1973   bool HasICData() const { | 1847   bool HasICData() const { | 
| 1974     return (ic_data() != NULL) && !ic_data()->IsNull(); | 1848     return (ic_data() != NULL) && !ic_data()->IsNull(); | 
| 1975   } | 1849   } | 
| 1976 | 1850 | 
| 1977   intptr_t token_pos() const { return token_pos_; } | 1851   intptr_t token_pos() const { return token_pos_; } | 
| 1978 | 1852 | 
| 1979   // Receiver class id is computed from collected ICData. | 1853   // Receiver class id is computed from collected ICData. | 
| 1980   void set_receiver_class_id(intptr_t value) { receiver_class_id_ = value; } | 1854   void set_receiver_class_id(intptr_t value) { receiver_class_id_ = value; } | 
| (...skipping 18 matching lines...) Expand all  Loading... | 
| 1999   virtual Representation RequiredInputRepresentation(intptr_t idx) const { | 1873   virtual Representation RequiredInputRepresentation(intptr_t idx) const { | 
| 2000     ASSERT((idx == 0) || (idx == 1)); | 1874     ASSERT((idx == 0) || (idx == 1)); | 
| 2001     return (receiver_class_id() == kDoubleCid) ? kUnboxedDouble : kTagged; | 1875     return (receiver_class_id() == kDoubleCid) ? kUnboxedDouble : kTagged; | 
| 2002   } | 1876   } | 
| 2003 | 1877 | 
| 2004  private: | 1878  private: | 
| 2005   const ICData* ic_data_; | 1879   const ICData* ic_data_; | 
| 2006   const intptr_t token_pos_; | 1880   const intptr_t token_pos_; | 
| 2007   intptr_t receiver_class_id_;  // Set by optimizer. | 1881   intptr_t receiver_class_id_;  // Set by optimizer. | 
| 2008 | 1882 | 
| 2009   DISALLOW_COPY_AND_ASSIGN(EqualityCompareComp); | 1883   DISALLOW_COPY_AND_ASSIGN(EqualityCompareInstr); | 
| 2010 }; | 1884 }; | 
| 2011 | 1885 | 
| 2012 | 1886 | 
| 2013 class RelationalOpComp : public ComparisonComp { | 1887 class RelationalOpInstr : public ComparisonInstr { | 
| 2014  public: | 1888  public: | 
| 2015   RelationalOpComp(intptr_t token_pos, | 1889   RelationalOpInstr(intptr_t token_pos, | 
| 2016                    Token::Kind kind, | 1890                     Token::Kind kind, | 
| 2017                    Value* left, | 1891                     Value* left, | 
| 2018                    Value* right) | 1892                     Value* right) | 
| 2019       : ComparisonComp(kind, left, right), | 1893       : ComparisonInstr(kind, left, right), | 
| 2020         ic_data_(Isolate::Current()->GetICDataForDeoptId(deopt_id())), | 1894         ic_data_(Isolate::Current()->GetICDataForDeoptId(deopt_id())), | 
| 2021         token_pos_(token_pos), | 1895         token_pos_(token_pos), | 
| 2022         operands_class_id_(kIllegalCid) { | 1896         operands_class_id_(kIllegalCid) { | 
| 2023     ASSERT(Token::IsRelationalOperator(kind)); | 1897     ASSERT(Token::IsRelationalOperator(kind)); | 
| 2024   } | 1898   } | 
| 2025 | 1899 | 
| 2026   DECLARE_COMPUTATION(RelationalOp) | 1900   DECLARE_INSTRUCTION(RelationalOp) | 
|  | 1901   virtual RawAbstractType* CompileType() const; | 
| 2027 | 1902 | 
| 2028   const ICData* ic_data() const { return ic_data_; } | 1903   const ICData* ic_data() const { return ic_data_; } | 
| 2029   bool HasICData() const { | 1904   bool HasICData() const { | 
| 2030     return (ic_data() != NULL) && !ic_data()->IsNull(); | 1905     return (ic_data() != NULL) && !ic_data()->IsNull(); | 
| 2031   } | 1906   } | 
| 2032 | 1907 | 
| 2033   intptr_t token_pos() const { return token_pos_; } | 1908   intptr_t token_pos() const { return token_pos_; } | 
| 2034 | 1909 | 
| 2035   // TODO(srdjan): instead of class-id pass an enum that can differentiate | 1910   // TODO(srdjan): instead of class-id pass an enum that can differentiate | 
| 2036   // between boxed and unboxed doubles and integers. | 1911   // between boxed and unboxed doubles and integers. | 
| (...skipping 23 matching lines...) Expand all  Loading... | 
| 2060   virtual Representation RequiredInputRepresentation(intptr_t idx) const { | 1935   virtual Representation RequiredInputRepresentation(intptr_t idx) const { | 
| 2061     ASSERT((idx == 0) || (idx == 1)); | 1936     ASSERT((idx == 0) || (idx == 1)); | 
| 2062     return (operands_class_id() == kDoubleCid) ? kUnboxedDouble : kTagged; | 1937     return (operands_class_id() == kDoubleCid) ? kUnboxedDouble : kTagged; | 
| 2063   } | 1938   } | 
| 2064 | 1939 | 
| 2065  private: | 1940  private: | 
| 2066   const ICData* ic_data_; | 1941   const ICData* ic_data_; | 
| 2067   const intptr_t token_pos_; | 1942   const intptr_t token_pos_; | 
| 2068   intptr_t operands_class_id_;  // class id of both operands. | 1943   intptr_t operands_class_id_;  // class id of both operands. | 
| 2069 | 1944 | 
| 2070   DISALLOW_COPY_AND_ASSIGN(RelationalOpComp); | 1945   DISALLOW_COPY_AND_ASSIGN(RelationalOpInstr); | 
| 2071 }; | 1946 }; | 
| 2072 | 1947 | 
| 2073 | 1948 | 
| 2074 class StaticCallComp : public TemplateComputation<0> { | 1949 class StaticCallInstr : public TemplateDefinition<0> { | 
| 2075  public: | 1950  public: | 
| 2076   StaticCallComp(intptr_t token_pos, | 1951   StaticCallInstr(intptr_t token_pos, | 
| 2077                  const Function& function, | 1952                   const Function& function, | 
| 2078                  const Array& argument_names, | 1953                   const Array& argument_names, | 
| 2079                  ZoneGrowableArray<PushArgumentInstr*>* arguments) | 1954                   ZoneGrowableArray<PushArgumentInstr*>* arguments) | 
| 2080       : token_pos_(token_pos), | 1955       : token_pos_(token_pos), | 
| 2081         function_(function), | 1956         function_(function), | 
| 2082         argument_names_(argument_names), | 1957         argument_names_(argument_names), | 
| 2083         arguments_(arguments), | 1958         arguments_(arguments), | 
| 2084         recognized_(MethodRecognizer::kUnknown) { | 1959         recognized_(MethodRecognizer::kUnknown) { | 
| 2085     ASSERT(function.IsZoneHandle()); | 1960     ASSERT(function.IsZoneHandle()); | 
| 2086     ASSERT(argument_names.IsZoneHandle()); | 1961     ASSERT(argument_names.IsZoneHandle()); | 
| 2087   } | 1962   } | 
| 2088 | 1963 | 
| 2089   DECLARE_CALL_COMPUTATION(StaticCall) | 1964   DECLARE_INSTRUCTION(StaticCall) | 
|  | 1965   virtual RawAbstractType* CompileType() const; | 
| 2090 | 1966 | 
| 2091   // Accessors forwarded to the AST node. | 1967   // Accessors forwarded to the AST node. | 
| 2092   const Function& function() const { return function_; } | 1968   const Function& function() const { return function_; } | 
| 2093   const Array& argument_names() const { return argument_names_; } | 1969   const Array& argument_names() const { return argument_names_; } | 
| 2094   intptr_t token_pos() const { return token_pos_; } | 1970   intptr_t token_pos() const { return token_pos_; } | 
| 2095 | 1971 | 
| 2096   virtual intptr_t ArgumentCount() const { return arguments_->length(); } | 1972   virtual intptr_t ArgumentCount() const { return arguments_->length(); } | 
| 2097   PushArgumentInstr* ArgumentAt(intptr_t index) const { | 1973   PushArgumentInstr* ArgumentAt(intptr_t index) const { | 
| 2098     return (*arguments_)[index]; | 1974     return (*arguments_)[index]; | 
| 2099   } | 1975   } | 
| 2100 | 1976 | 
| 2101   MethodRecognizer::Kind recognized() const { return recognized_; } | 1977   MethodRecognizer::Kind recognized() const { return recognized_; } | 
| 2102   void set_recognized(MethodRecognizer::Kind kind) { recognized_ = kind; } | 1978   void set_recognized(MethodRecognizer::Kind kind) { recognized_ = kind; } | 
| 2103 | 1979 | 
| 2104   virtual void PrintOperandsTo(BufferFormatter* f) const; | 1980   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2105 | 1981 | 
| 2106   virtual bool CanDeoptimize() const { return true; } | 1982   virtual bool CanDeoptimize() const { return true; } | 
| 2107   virtual intptr_t ResultCid() const { return kDynamicCid; } | 1983   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2108 | 1984 | 
| 2109  private: | 1985  private: | 
| 2110   const intptr_t token_pos_; | 1986   const intptr_t token_pos_; | 
| 2111   const Function& function_; | 1987   const Function& function_; | 
| 2112   const Array& argument_names_; | 1988   const Array& argument_names_; | 
| 2113   ZoneGrowableArray<PushArgumentInstr*>* arguments_; | 1989   ZoneGrowableArray<PushArgumentInstr*>* arguments_; | 
| 2114   MethodRecognizer::Kind recognized_; | 1990   MethodRecognizer::Kind recognized_; | 
| 2115 | 1991 | 
| 2116   DISALLOW_COPY_AND_ASSIGN(StaticCallComp); | 1992   DISALLOW_COPY_AND_ASSIGN(StaticCallInstr); | 
| 2117 }; | 1993 }; | 
| 2118 | 1994 | 
| 2119 | 1995 | 
| 2120 class LoadLocalComp : public TemplateComputation<0> { | 1996 class LoadLocalInstr : public TemplateDefinition<0> { | 
| 2121  public: | 1997  public: | 
| 2122   LoadLocalComp(const LocalVariable& local, intptr_t context_level) | 1998   LoadLocalInstr(const LocalVariable& local, intptr_t context_level) | 
| 2123       : local_(local), | 1999       : local_(local), | 
| 2124         context_level_(context_level) { } | 2000         context_level_(context_level) { } | 
| 2125 | 2001 | 
| 2126   DECLARE_COMPUTATION(LoadLocal) | 2002   DECLARE_INSTRUCTION(LoadLocal) | 
|  | 2003   virtual RawAbstractType* CompileType() const; | 
| 2127 | 2004 | 
| 2128   const LocalVariable& local() const { return local_; } | 2005   const LocalVariable& local() const { return local_; } | 
| 2129   intptr_t context_level() const { return context_level_; } | 2006   intptr_t context_level() const { return context_level_; } | 
| 2130 | 2007 | 
| 2131   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2008   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2132 | 2009 | 
| 2133   virtual bool CanDeoptimize() const { return false; } | 2010   virtual bool CanDeoptimize() const { return false; } | 
| 2134   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2011   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2135 | 2012 | 
| 2136  private: | 2013  private: | 
| 2137   const LocalVariable& local_; | 2014   const LocalVariable& local_; | 
| 2138   const intptr_t context_level_; | 2015   const intptr_t context_level_; | 
| 2139 | 2016 | 
| 2140   DISALLOW_COPY_AND_ASSIGN(LoadLocalComp); | 2017   DISALLOW_COPY_AND_ASSIGN(LoadLocalInstr); | 
| 2141 }; | 2018 }; | 
| 2142 | 2019 | 
| 2143 | 2020 | 
| 2144 class StoreLocalComp : public TemplateComputation<1> { | 2021 class StoreLocalInstr : public TemplateDefinition<1> { | 
| 2145  public: | 2022  public: | 
| 2146   StoreLocalComp(const LocalVariable& local, | 2023   StoreLocalInstr(const LocalVariable& local, | 
| 2147                  Value* value, | 2024                   Value* value, | 
| 2148                  intptr_t context_level) | 2025                   intptr_t context_level) | 
| 2149       : local_(local), | 2026       : local_(local), | 
| 2150         context_level_(context_level) { | 2027         context_level_(context_level) { | 
| 2151     ASSERT(value != NULL); | 2028     ASSERT(value != NULL); | 
| 2152     inputs_[0] = value; | 2029     inputs_[0] = value; | 
| 2153   } | 2030   } | 
| 2154 | 2031 | 
| 2155   DECLARE_COMPUTATION(StoreLocal) | 2032   DECLARE_INSTRUCTION(StoreLocal) | 
|  | 2033   virtual RawAbstractType* CompileType() const; | 
| 2156 | 2034 | 
| 2157   const LocalVariable& local() const { return local_; } | 2035   const LocalVariable& local() const { return local_; } | 
| 2158   Value* value() const { return inputs_[0]; } | 2036   Value* value() const { return inputs_[0]; } | 
| 2159   intptr_t context_level() const { return context_level_; } | 2037   intptr_t context_level() const { return context_level_; } | 
| 2160 | 2038 | 
| 2161   virtual void RecordAssignedVars(BitVector* assigned_vars, | 2039   virtual void RecordAssignedVars(BitVector* assigned_vars, | 
| 2162                                   intptr_t fixed_parameter_count); | 2040                                   intptr_t fixed_parameter_count); | 
| 2163 | 2041 | 
| 2164   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2042   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2165 | 2043 | 
| 2166   virtual bool CanDeoptimize() const { return false; } | 2044   virtual bool CanDeoptimize() const { return false; } | 
| 2167   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2045   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2168 | 2046 | 
| 2169  private: | 2047  private: | 
| 2170   const LocalVariable& local_; | 2048   const LocalVariable& local_; | 
| 2171   const intptr_t context_level_; | 2049   const intptr_t context_level_; | 
| 2172 | 2050 | 
| 2173   DISALLOW_COPY_AND_ASSIGN(StoreLocalComp); | 2051   DISALLOW_COPY_AND_ASSIGN(StoreLocalInstr); | 
| 2174 }; | 2052 }; | 
| 2175 | 2053 | 
| 2176 | 2054 | 
| 2177 class NativeCallComp : public TemplateComputation<0> { | 2055 class NativeCallInstr : public TemplateDefinition<0> { | 
| 2178  public: | 2056  public: | 
| 2179   explicit NativeCallComp(NativeBodyNode* node) | 2057   explicit NativeCallInstr(NativeBodyNode* node) | 
| 2180       : ast_node_(*node) {} | 2058       : ast_node_(*node) {} | 
| 2181 | 2059 | 
| 2182   DECLARE_COMPUTATION(NativeCall) | 2060   DECLARE_INSTRUCTION(NativeCall) | 
|  | 2061   virtual RawAbstractType* CompileType() const; | 
| 2183 | 2062 | 
| 2184   intptr_t token_pos() const { return ast_node_.token_pos(); } | 2063   intptr_t token_pos() const { return ast_node_.token_pos(); } | 
| 2185 | 2064 | 
| 2186   const String& native_name() const { | 2065   const String& native_name() const { | 
| 2187     return ast_node_.native_c_function_name(); | 2066     return ast_node_.native_c_function_name(); | 
| 2188   } | 2067   } | 
| 2189 | 2068 | 
| 2190   NativeFunction native_c_function() const { | 2069   NativeFunction native_c_function() const { | 
| 2191     return ast_node_.native_c_function(); | 2070     return ast_node_.native_c_function(); | 
| 2192   } | 2071   } | 
| 2193 | 2072 | 
| 2194   intptr_t argument_count() const { return ast_node_.argument_count(); } | 2073   intptr_t argument_count() const { return ast_node_.argument_count(); } | 
| 2195 | 2074 | 
| 2196   bool has_optional_parameters() const { | 2075   bool has_optional_parameters() const { | 
| 2197     return ast_node_.has_optional_parameters(); | 2076     return ast_node_.has_optional_parameters(); | 
| 2198   } | 2077   } | 
| 2199 | 2078 | 
| 2200   bool is_native_instance_closure() const { | 2079   bool is_native_instance_closure() const { | 
| 2201     return ast_node_.is_native_instance_closure(); | 2080     return ast_node_.is_native_instance_closure(); | 
| 2202   } | 2081   } | 
| 2203 | 2082 | 
| 2204   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2083   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2205 | 2084 | 
| 2206   virtual bool CanDeoptimize() const { return false; } | 2085   virtual bool CanDeoptimize() const { return false; } | 
| 2207   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2086   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2208 | 2087 | 
| 2209  private: | 2088  private: | 
| 2210   const NativeBodyNode& ast_node_; | 2089   const NativeBodyNode& ast_node_; | 
| 2211 | 2090 | 
| 2212   DISALLOW_COPY_AND_ASSIGN(NativeCallComp); | 2091   DISALLOW_COPY_AND_ASSIGN(NativeCallInstr); | 
| 2213 }; | 2092 }; | 
| 2214 | 2093 | 
| 2215 | 2094 | 
| 2216 class LoadInstanceFieldComp : public TemplateComputation<1> { | 2095 class LoadInstanceFieldInstr : public TemplateDefinition<1> { | 
| 2217  public: | 2096  public: | 
| 2218   LoadInstanceFieldComp(const Field& field, Value* instance) : field_(field) { | 2097   LoadInstanceFieldInstr(const Field& field, Value* instance) : field_(field) { | 
| 2219     ASSERT(instance != NULL); | 2098     ASSERT(instance != NULL); | 
| 2220     inputs_[0] = instance; | 2099     inputs_[0] = instance; | 
| 2221   } | 2100   } | 
| 2222 | 2101 | 
| 2223   DECLARE_COMPUTATION(LoadInstanceField) | 2102   DECLARE_INSTRUCTION(LoadInstanceField) | 
|  | 2103   virtual RawAbstractType* CompileType() const; | 
| 2224 | 2104 | 
| 2225   const Field& field() const { return field_; } | 2105   const Field& field() const { return field_; } | 
| 2226   Value* instance() const { return inputs_[0]; } | 2106   Value* instance() const { return inputs_[0]; } | 
| 2227 | 2107 | 
| 2228   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2108   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2229 | 2109 | 
| 2230   virtual bool CanDeoptimize() const { return false; } | 2110   virtual bool CanDeoptimize() const { return false; } | 
| 2231   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2111   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2232 | 2112 | 
| 2233  private: | 2113  private: | 
| 2234   const Field& field_; | 2114   const Field& field_; | 
| 2235 | 2115 | 
| 2236   DISALLOW_COPY_AND_ASSIGN(LoadInstanceFieldComp); | 2116   DISALLOW_COPY_AND_ASSIGN(LoadInstanceFieldInstr); | 
| 2237 }; | 2117 }; | 
| 2238 | 2118 | 
| 2239 | 2119 | 
| 2240 class StoreInstanceFieldComp : public TemplateComputation<2> { | 2120 class StoreInstanceFieldInstr : public TemplateDefinition<2> { | 
| 2241  public: | 2121  public: | 
| 2242   StoreInstanceFieldComp(const Field& field, | 2122   StoreInstanceFieldInstr(const Field& field, Value* instance, Value* value) | 
| 2243                          Value* instance, |  | 
| 2244                          Value* value) |  | 
| 2245       : field_(field) { | 2123       : field_(field) { | 
| 2246     ASSERT(instance != NULL); | 2124     ASSERT(instance != NULL); | 
| 2247     ASSERT(value != NULL); | 2125     ASSERT(value != NULL); | 
| 2248     inputs_[0] = instance; | 2126     inputs_[0] = instance; | 
| 2249     inputs_[1] = value; | 2127     inputs_[1] = value; | 
| 2250   } | 2128   } | 
| 2251 | 2129 | 
| 2252   DECLARE_COMPUTATION(StoreInstanceField) | 2130   DECLARE_INSTRUCTION(StoreInstanceField) | 
|  | 2131   virtual RawAbstractType* CompileType() const; | 
| 2253 | 2132 | 
| 2254   const Field& field() const { return field_; } | 2133   const Field& field() const { return field_; } | 
| 2255 | 2134 | 
| 2256   Value* instance() const { return inputs_[0]; } | 2135   Value* instance() const { return inputs_[0]; } | 
| 2257   Value* value() const { return inputs_[1]; } | 2136   Value* value() const { return inputs_[1]; } | 
| 2258 | 2137 | 
| 2259   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2138   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2260 | 2139 | 
| 2261   virtual bool CanDeoptimize() const { return false; } | 2140   virtual bool CanDeoptimize() const { return false; } | 
| 2262   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2141   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2263 | 2142 | 
| 2264  private: | 2143  private: | 
| 2265   const Field& field_; | 2144   const Field& field_; | 
| 2266 | 2145 | 
| 2267   DISALLOW_COPY_AND_ASSIGN(StoreInstanceFieldComp); | 2146   DISALLOW_COPY_AND_ASSIGN(StoreInstanceFieldInstr); | 
| 2268 }; | 2147 }; | 
| 2269 | 2148 | 
| 2270 | 2149 | 
| 2271 class LoadStaticFieldComp : public TemplateComputation<0> { | 2150 class LoadStaticFieldInstr : public TemplateDefinition<0> { | 
| 2272  public: | 2151  public: | 
| 2273   explicit LoadStaticFieldComp(const Field& field) : field_(field) {} | 2152   explicit LoadStaticFieldInstr(const Field& field) : field_(field) {} | 
| 2274 | 2153 | 
| 2275   DECLARE_COMPUTATION(LoadStaticField); | 2154   DECLARE_INSTRUCTION(LoadStaticField); | 
|  | 2155   virtual RawAbstractType* CompileType() const; | 
| 2276 | 2156 | 
| 2277   const Field& field() const { return field_; } | 2157   const Field& field() const { return field_; } | 
| 2278 | 2158 | 
| 2279   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2159   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2280 | 2160 | 
| 2281   virtual bool CanDeoptimize() const { return false; } | 2161   virtual bool CanDeoptimize() const { return false; } | 
| 2282   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2162   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2283 | 2163 | 
| 2284  private: | 2164  private: | 
| 2285   const Field& field_; | 2165   const Field& field_; | 
| 2286 | 2166 | 
| 2287   DISALLOW_COPY_AND_ASSIGN(LoadStaticFieldComp); | 2167   DISALLOW_COPY_AND_ASSIGN(LoadStaticFieldInstr); | 
| 2288 }; | 2168 }; | 
| 2289 | 2169 | 
| 2290 | 2170 | 
| 2291 class StoreStaticFieldComp : public TemplateComputation<1> { | 2171 class StoreStaticFieldInstr : public TemplateDefinition<1> { | 
| 2292  public: | 2172  public: | 
| 2293   StoreStaticFieldComp(const Field& field, Value* value) | 2173   StoreStaticFieldInstr(const Field& field, Value* value) | 
| 2294       : field_(field) { | 2174       : field_(field) { | 
| 2295     ASSERT(field.IsZoneHandle()); | 2175     ASSERT(field.IsZoneHandle()); | 
| 2296     ASSERT(value != NULL); | 2176     ASSERT(value != NULL); | 
| 2297     inputs_[0] = value; | 2177     inputs_[0] = value; | 
| 2298   } | 2178   } | 
| 2299 | 2179 | 
| 2300   DECLARE_COMPUTATION(StoreStaticField); | 2180   DECLARE_INSTRUCTION(StoreStaticField); | 
|  | 2181   virtual RawAbstractType* CompileType() const; | 
| 2301 | 2182 | 
| 2302   const Field& field() const { return field_; } | 2183   const Field& field() const { return field_; } | 
| 2303   Value* value() const { return inputs_[0]; } | 2184   Value* value() const { return inputs_[0]; } | 
| 2304 | 2185 | 
| 2305   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2186   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2306 | 2187 | 
| 2307   virtual bool CanDeoptimize() const { return false; } | 2188   virtual bool CanDeoptimize() const { return false; } | 
| 2308   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2189   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2309 | 2190 | 
| 2310  private: | 2191  private: | 
| 2311   const Field& field_; | 2192   const Field& field_; | 
| 2312 | 2193 | 
| 2313   DISALLOW_COPY_AND_ASSIGN(StoreStaticFieldComp); | 2194   DISALLOW_COPY_AND_ASSIGN(StoreStaticFieldInstr); | 
| 2314 }; | 2195 }; | 
| 2315 | 2196 | 
| 2316 | 2197 | 
| 2317 class LoadIndexedComp : public TemplateComputation<2> { | 2198 class LoadIndexedInstr : public TemplateDefinition<2> { | 
| 2318  public: | 2199  public: | 
| 2319   LoadIndexedComp(Value* array, | 2200   LoadIndexedInstr(Value* array, Value* index, intptr_t receiver_type) | 
| 2320                   Value* index, |  | 
| 2321                   intptr_t receiver_type) |  | 
| 2322       : receiver_type_(receiver_type) { | 2201       : receiver_type_(receiver_type) { | 
| 2323     ASSERT(array != NULL); | 2202     ASSERT(array != NULL); | 
| 2324     ASSERT(index != NULL); | 2203     ASSERT(index != NULL); | 
| 2325     inputs_[0] = array; | 2204     inputs_[0] = array; | 
| 2326     inputs_[1] = index; | 2205     inputs_[1] = index; | 
| 2327   } | 2206   } | 
| 2328 | 2207 | 
| 2329   DECLARE_COMPUTATION(LoadIndexed) | 2208   DECLARE_INSTRUCTION(LoadIndexed) | 
|  | 2209   virtual RawAbstractType* CompileType() const; | 
| 2330 | 2210 | 
| 2331   Value* array() const { return inputs_[0]; } | 2211   Value* array() const { return inputs_[0]; } | 
| 2332   Value* index() const { return inputs_[1]; } | 2212   Value* index() const { return inputs_[1]; } | 
| 2333 | 2213 | 
| 2334   intptr_t receiver_type() const { return receiver_type_; } | 2214   intptr_t receiver_type() const { return receiver_type_; } | 
| 2335 | 2215 | 
| 2336   virtual bool CanDeoptimize() const { return false; } | 2216   virtual bool CanDeoptimize() const { return false; } | 
| 2337   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2217   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2338 | 2218 | 
| 2339  private: | 2219  private: | 
| 2340   intptr_t receiver_type_; | 2220   intptr_t receiver_type_; | 
| 2341 | 2221 | 
| 2342   DISALLOW_COPY_AND_ASSIGN(LoadIndexedComp); | 2222   DISALLOW_COPY_AND_ASSIGN(LoadIndexedInstr); | 
| 2343 }; | 2223 }; | 
| 2344 | 2224 | 
| 2345 | 2225 | 
| 2346 class StoreIndexedComp : public TemplateComputation<3> { | 2226 class StoreIndexedInstr : public TemplateDefinition<3> { | 
| 2347  public: | 2227  public: | 
| 2348   StoreIndexedComp(Value* array, | 2228   StoreIndexedInstr(Value* array, | 
| 2349                    Value* index, | 2229                     Value* index, | 
| 2350                    Value* value, | 2230                     Value* value, | 
| 2351                    intptr_t receiver_type) | 2231                     intptr_t receiver_type) | 
| 2352         : receiver_type_(receiver_type) { | 2232         : receiver_type_(receiver_type) { | 
| 2353     ASSERT(array != NULL); | 2233     ASSERT(array != NULL); | 
| 2354     ASSERT(index != NULL); | 2234     ASSERT(index != NULL); | 
| 2355     ASSERT(value != NULL); | 2235     ASSERT(value != NULL); | 
| 2356     inputs_[0] = array; | 2236     inputs_[0] = array; | 
| 2357     inputs_[1] = index; | 2237     inputs_[1] = index; | 
| 2358     inputs_[2] = value; | 2238     inputs_[2] = value; | 
| 2359   } | 2239   } | 
| 2360 | 2240 | 
| 2361   DECLARE_COMPUTATION(StoreIndexed) | 2241   DECLARE_INSTRUCTION(StoreIndexed) | 
|  | 2242   virtual RawAbstractType* CompileType() const; | 
| 2362 | 2243 | 
| 2363   Value* array() const { return inputs_[0]; } | 2244   Value* array() const { return inputs_[0]; } | 
| 2364   Value* index() const { return inputs_[1]; } | 2245   Value* index() const { return inputs_[1]; } | 
| 2365   Value* value() const { return inputs_[2]; } | 2246   Value* value() const { return inputs_[2]; } | 
| 2366 | 2247 | 
| 2367   intptr_t receiver_type() const { return receiver_type_; } | 2248   intptr_t receiver_type() const { return receiver_type_; } | 
| 2368 | 2249 | 
| 2369   virtual bool CanDeoptimize() const { return false; } | 2250   virtual bool CanDeoptimize() const { return false; } | 
| 2370   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2251   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2371 | 2252 | 
| 2372  private: | 2253  private: | 
| 2373   intptr_t receiver_type_; | 2254   intptr_t receiver_type_; | 
| 2374 | 2255 | 
| 2375   DISALLOW_COPY_AND_ASSIGN(StoreIndexedComp); | 2256   DISALLOW_COPY_AND_ASSIGN(StoreIndexedInstr); | 
| 2376 }; | 2257 }; | 
| 2377 | 2258 | 
| 2378 | 2259 | 
| 2379 // Note overrideable, built-in: value? false : true. | 2260 // Note overrideable, built-in: value? false : true. | 
| 2380 class BooleanNegateComp : public TemplateComputation<1> { | 2261 class BooleanNegateInstr : public TemplateDefinition<1> { | 
| 2381  public: | 2262  public: | 
| 2382   explicit BooleanNegateComp(Value* value) { | 2263   explicit BooleanNegateInstr(Value* value) { | 
| 2383     ASSERT(value != NULL); | 2264     ASSERT(value != NULL); | 
| 2384     inputs_[0] = value; | 2265     inputs_[0] = value; | 
| 2385   } | 2266   } | 
| 2386 | 2267 | 
| 2387   DECLARE_COMPUTATION(BooleanNegate) | 2268   DECLARE_INSTRUCTION(BooleanNegate) | 
|  | 2269   virtual RawAbstractType* CompileType() const; | 
| 2388 | 2270 | 
| 2389   Value* value() const { return inputs_[0]; } | 2271   Value* value() const { return inputs_[0]; } | 
| 2390 | 2272 | 
| 2391   virtual bool CanDeoptimize() const { return false; } | 2273   virtual bool CanDeoptimize() const { return false; } | 
| 2392   virtual intptr_t ResultCid() const { return kBoolCid; } | 2274   virtual intptr_t ResultCid() const { return kBoolCid; } | 
| 2393 | 2275 | 
| 2394  private: | 2276  private: | 
| 2395   DISALLOW_COPY_AND_ASSIGN(BooleanNegateComp); | 2277   DISALLOW_COPY_AND_ASSIGN(BooleanNegateInstr); | 
| 2396 }; | 2278 }; | 
| 2397 | 2279 | 
| 2398 | 2280 | 
| 2399 class InstanceOfComp : public TemplateComputation<3> { | 2281 class InstanceOfInstr : public TemplateDefinition<3> { | 
| 2400  public: | 2282  public: | 
| 2401   InstanceOfComp(intptr_t token_pos, | 2283   InstanceOfInstr(intptr_t token_pos, | 
| 2402                  Value* value, | 2284                   Value* value, | 
| 2403                  Value* instantiator, | 2285                   Value* instantiator, | 
| 2404                  Value* instantiator_type_arguments, | 2286                   Value* instantiator_type_arguments, | 
| 2405                  const AbstractType& type, | 2287                   const AbstractType& type, | 
| 2406                  bool negate_result) | 2288                   bool negate_result) | 
| 2407       : token_pos_(token_pos), | 2289       : token_pos_(token_pos), | 
| 2408         type_(type), | 2290         type_(type), | 
| 2409         negate_result_(negate_result) { | 2291         negate_result_(negate_result) { | 
| 2410     ASSERT(value != NULL); | 2292     ASSERT(value != NULL); | 
| 2411     ASSERT(instantiator != NULL); | 2293     ASSERT(instantiator != NULL); | 
| 2412     ASSERT(instantiator_type_arguments != NULL); | 2294     ASSERT(instantiator_type_arguments != NULL); | 
| 2413     ASSERT(!type.IsNull()); | 2295     ASSERT(!type.IsNull()); | 
| 2414     inputs_[0] = value; | 2296     inputs_[0] = value; | 
| 2415     inputs_[1] = instantiator; | 2297     inputs_[1] = instantiator; | 
| 2416     inputs_[2] = instantiator_type_arguments; | 2298     inputs_[2] = instantiator_type_arguments; | 
| 2417   } | 2299   } | 
| 2418 | 2300 | 
| 2419   DECLARE_COMPUTATION(InstanceOf) | 2301   DECLARE_INSTRUCTION(InstanceOf) | 
|  | 2302   virtual RawAbstractType* CompileType() const; | 
| 2420 | 2303 | 
| 2421   Value* value() const { return inputs_[0]; } | 2304   Value* value() const { return inputs_[0]; } | 
| 2422   Value* instantiator() const { return inputs_[1]; } | 2305   Value* instantiator() const { return inputs_[1]; } | 
| 2423   Value* instantiator_type_arguments() const { return inputs_[2]; } | 2306   Value* instantiator_type_arguments() const { return inputs_[2]; } | 
| 2424 | 2307 | 
| 2425   bool negate_result() const { return negate_result_; } | 2308   bool negate_result() const { return negate_result_; } | 
| 2426   const AbstractType& type() const { return type_; } | 2309   const AbstractType& type() const { return type_; } | 
| 2427   intptr_t token_pos() const { return token_pos_; } | 2310   intptr_t token_pos() const { return token_pos_; } | 
| 2428 | 2311 | 
| 2429   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2312   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2430 | 2313 | 
| 2431   virtual bool CanDeoptimize() const { return false; } | 2314   virtual bool CanDeoptimize() const { return false; } | 
| 2432   virtual intptr_t ResultCid() const { return kBoolCid; } | 2315   virtual intptr_t ResultCid() const { return kBoolCid; } | 
| 2433 | 2316 | 
| 2434  private: | 2317  private: | 
| 2435   const intptr_t token_pos_; | 2318   const intptr_t token_pos_; | 
| 2436   Value* value_; | 2319   Value* value_; | 
| 2437   Value* instantiator_; | 2320   Value* instantiator_; | 
| 2438   Value* type_arguments_; | 2321   Value* type_arguments_; | 
| 2439   const AbstractType& type_; | 2322   const AbstractType& type_; | 
| 2440   const bool negate_result_; | 2323   const bool negate_result_; | 
| 2441 | 2324 | 
| 2442   DISALLOW_COPY_AND_ASSIGN(InstanceOfComp); | 2325   DISALLOW_COPY_AND_ASSIGN(InstanceOfInstr); | 
| 2443 }; | 2326 }; | 
| 2444 | 2327 | 
| 2445 | 2328 | 
| 2446 class AllocateObjectComp : public TemplateComputation<0> { | 2329 class AllocateObjectInstr : public TemplateDefinition<0> { | 
| 2447  public: | 2330  public: | 
| 2448   AllocateObjectComp(ConstructorCallNode* node, | 2331   AllocateObjectInstr(ConstructorCallNode* node, | 
| 2449                      ZoneGrowableArray<PushArgumentInstr*>* arguments) | 2332                       ZoneGrowableArray<PushArgumentInstr*>* arguments) | 
| 2450       : ast_node_(*node), arguments_(arguments) { | 2333       : ast_node_(*node), arguments_(arguments) { | 
| 2451     // Either no arguments or one type-argument and one instantiator. | 2334     // Either no arguments or one type-argument and one instantiator. | 
| 2452     ASSERT(arguments->is_empty() || (arguments->length() == 2)); | 2335     ASSERT(arguments->is_empty() || (arguments->length() == 2)); | 
| 2453   } | 2336   } | 
| 2454 | 2337 | 
| 2455   DECLARE_CALL_COMPUTATION(AllocateObject) | 2338   DECLARE_INSTRUCTION(AllocateObject) | 
|  | 2339   virtual RawAbstractType* CompileType() const; | 
| 2456 | 2340 | 
| 2457   virtual intptr_t ArgumentCount() const { return arguments_->length(); } | 2341   virtual intptr_t ArgumentCount() const { return arguments_->length(); } | 
| 2458   PushArgumentInstr* ArgumentAt(intptr_t index) const { | 2342   PushArgumentInstr* ArgumentAt(intptr_t index) const { | 
| 2459     return (*arguments_)[index]; | 2343     return (*arguments_)[index]; | 
| 2460   } | 2344   } | 
| 2461 | 2345 | 
| 2462   const Function& constructor() const { return ast_node_.constructor(); } | 2346   const Function& constructor() const { return ast_node_.constructor(); } | 
| 2463   intptr_t token_pos() const { return ast_node_.token_pos(); } | 2347   intptr_t token_pos() const { return ast_node_.token_pos(); } | 
| 2464 | 2348 | 
| 2465   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2349   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2466 | 2350 | 
| 2467   virtual bool CanDeoptimize() const { return false; } | 2351   virtual bool CanDeoptimize() const { return false; } | 
| 2468   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2352   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2469 | 2353 | 
| 2470  private: | 2354  private: | 
| 2471   const ConstructorCallNode& ast_node_; | 2355   const ConstructorCallNode& ast_node_; | 
| 2472   ZoneGrowableArray<PushArgumentInstr*>* const arguments_; | 2356   ZoneGrowableArray<PushArgumentInstr*>* const arguments_; | 
| 2473 | 2357 | 
| 2474   DISALLOW_COPY_AND_ASSIGN(AllocateObjectComp); | 2358   DISALLOW_COPY_AND_ASSIGN(AllocateObjectInstr); | 
| 2475 }; | 2359 }; | 
| 2476 | 2360 | 
| 2477 | 2361 | 
| 2478 class AllocateObjectWithBoundsCheckComp : public TemplateComputation<2> { | 2362 class AllocateObjectWithBoundsCheckInstr : public TemplateDefinition<2> { | 
| 2479  public: | 2363  public: | 
| 2480   AllocateObjectWithBoundsCheckComp(ConstructorCallNode* node, | 2364   AllocateObjectWithBoundsCheckInstr(ConstructorCallNode* node, | 
| 2481                                     Value* type_arguments, | 2365                                      Value* type_arguments, | 
| 2482                                     Value* instantiator) | 2366                                      Value* instantiator) | 
| 2483       : ast_node_(*node) { | 2367       : ast_node_(*node) { | 
| 2484     ASSERT(type_arguments != NULL); | 2368     ASSERT(type_arguments != NULL); | 
| 2485     ASSERT(instantiator != NULL); | 2369     ASSERT(instantiator != NULL); | 
| 2486     inputs_[0] = type_arguments; | 2370     inputs_[0] = type_arguments; | 
| 2487     inputs_[1] = instantiator; | 2371     inputs_[1] = instantiator; | 
| 2488   } | 2372   } | 
| 2489 | 2373 | 
| 2490   DECLARE_COMPUTATION(AllocateObjectWithBoundsCheck) | 2374   DECLARE_INSTRUCTION(AllocateObjectWithBoundsCheck) | 
|  | 2375   virtual RawAbstractType* CompileType() const; | 
| 2491 | 2376 | 
| 2492   const Function& constructor() const { return ast_node_.constructor(); } | 2377   const Function& constructor() const { return ast_node_.constructor(); } | 
| 2493   intptr_t token_pos() const { return ast_node_.token_pos(); } | 2378   intptr_t token_pos() const { return ast_node_.token_pos(); } | 
| 2494 | 2379 | 
| 2495   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2380   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2496 | 2381 | 
| 2497   virtual bool CanDeoptimize() const { return false; } | 2382   virtual bool CanDeoptimize() const { return false; } | 
| 2498   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2383   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2499 | 2384 | 
| 2500  private: | 2385  private: | 
| 2501   const ConstructorCallNode& ast_node_; | 2386   const ConstructorCallNode& ast_node_; | 
| 2502 | 2387 | 
| 2503   DISALLOW_COPY_AND_ASSIGN(AllocateObjectWithBoundsCheckComp); | 2388   DISALLOW_COPY_AND_ASSIGN(AllocateObjectWithBoundsCheckInstr); | 
| 2504 }; | 2389 }; | 
| 2505 | 2390 | 
| 2506 | 2391 | 
| 2507 class CreateArrayComp : public TemplateComputation<1> { | 2392 class CreateArrayInstr : public TemplateDefinition<1> { | 
| 2508  public: | 2393  public: | 
| 2509   CreateArrayComp(intptr_t token_pos, | 2394   CreateArrayInstr(intptr_t token_pos, | 
| 2510                   ZoneGrowableArray<PushArgumentInstr*>* arguments, | 2395                    ZoneGrowableArray<PushArgumentInstr*>* arguments, | 
| 2511                   const AbstractType& type, | 2396                    const AbstractType& type, | 
| 2512                   Value* element_type) | 2397                    Value* element_type) | 
| 2513       : token_pos_(token_pos), | 2398       : token_pos_(token_pos), | 
| 2514         arguments_(arguments), | 2399         arguments_(arguments), | 
| 2515         type_(type) { | 2400         type_(type) { | 
| 2516 #if defined(DEBUG) | 2401 #if defined(DEBUG) | 
| 2517     for (int i = 0; i < ArgumentCount(); ++i) { | 2402     for (int i = 0; i < ArgumentCount(); ++i) { | 
| 2518       ASSERT(ArgumentAt(i) != NULL); | 2403       ASSERT(ArgumentAt(i) != NULL); | 
| 2519     } | 2404     } | 
| 2520     ASSERT(element_type != NULL); | 2405     ASSERT(element_type != NULL); | 
| 2521     ASSERT(type_.IsZoneHandle()); | 2406     ASSERT(type_.IsZoneHandle()); | 
| 2522     ASSERT(!type_.IsNull()); | 2407     ASSERT(!type_.IsNull()); | 
| 2523     ASSERT(type_.IsFinalized()); | 2408     ASSERT(type_.IsFinalized()); | 
| 2524 #endif | 2409 #endif | 
| 2525     inputs_[0] = element_type; | 2410     inputs_[0] = element_type; | 
| 2526   } | 2411   } | 
| 2527 | 2412 | 
| 2528   DECLARE_CALL_COMPUTATION(CreateArray) | 2413   DECLARE_INSTRUCTION(CreateArray) | 
|  | 2414   virtual RawAbstractType* CompileType() const; | 
| 2529 | 2415 | 
| 2530   virtual intptr_t ArgumentCount() const { return arguments_->length(); } | 2416   virtual intptr_t ArgumentCount() const { return arguments_->length(); } | 
| 2531 | 2417 | 
| 2532   intptr_t token_pos() const { return token_pos_; } | 2418   intptr_t token_pos() const { return token_pos_; } | 
| 2533   PushArgumentInstr* ArgumentAt(intptr_t i) const { return (*arguments_)[i]; } | 2419   PushArgumentInstr* ArgumentAt(intptr_t i) const { return (*arguments_)[i]; } | 
| 2534   const AbstractType& type() const { return type_; } | 2420   const AbstractType& type() const { return type_; } | 
| 2535   Value* element_type() const { return inputs_[0]; } | 2421   Value* element_type() const { return inputs_[0]; } | 
| 2536 | 2422 | 
| 2537   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2423   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2538 | 2424 | 
| 2539   virtual bool CanDeoptimize() const { return false; } | 2425   virtual bool CanDeoptimize() const { return false; } | 
| 2540   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2426   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2541 | 2427 | 
| 2542  private: | 2428  private: | 
| 2543   const intptr_t token_pos_; | 2429   const intptr_t token_pos_; | 
| 2544   ZoneGrowableArray<PushArgumentInstr*>* const arguments_; | 2430   ZoneGrowableArray<PushArgumentInstr*>* const arguments_; | 
| 2545   const AbstractType& type_; | 2431   const AbstractType& type_; | 
| 2546 | 2432 | 
| 2547   DISALLOW_COPY_AND_ASSIGN(CreateArrayComp); | 2433   DISALLOW_COPY_AND_ASSIGN(CreateArrayInstr); | 
| 2548 }; | 2434 }; | 
| 2549 | 2435 | 
| 2550 | 2436 | 
| 2551 class CreateClosureComp : public TemplateComputation<0> { | 2437 class CreateClosureInstr : public TemplateDefinition<0> { | 
| 2552  public: | 2438  public: | 
| 2553   CreateClosureComp(ClosureNode* node, | 2439   CreateClosureInstr(ClosureNode* node, | 
| 2554                     ZoneGrowableArray<PushArgumentInstr*>* arguments) | 2440                      ZoneGrowableArray<PushArgumentInstr*>* arguments) | 
| 2555       : ast_node_(*node), | 2441       : ast_node_(*node), | 
| 2556         arguments_(arguments) { } | 2442         arguments_(arguments) { } | 
| 2557 | 2443 | 
| 2558   DECLARE_CALL_COMPUTATION(CreateClosure) | 2444   DECLARE_INSTRUCTION(CreateClosure) | 
|  | 2445   virtual RawAbstractType* CompileType() const; | 
| 2559 | 2446 | 
| 2560   intptr_t token_pos() const { return ast_node_.token_pos(); } | 2447   intptr_t token_pos() const { return ast_node_.token_pos(); } | 
| 2561   const Function& function() const { return ast_node_.function(); } | 2448   const Function& function() const { return ast_node_.function(); } | 
| 2562 | 2449 | 
| 2563   virtual intptr_t ArgumentCount() const { return arguments_->length(); } | 2450   virtual intptr_t ArgumentCount() const { return arguments_->length(); } | 
| 2564   PushArgumentInstr* ArgumentAt(intptr_t index) const { | 2451   PushArgumentInstr* ArgumentAt(intptr_t index) const { | 
| 2565     return (*arguments_)[index]; | 2452     return (*arguments_)[index]; | 
| 2566   } | 2453   } | 
| 2567 | 2454 | 
| 2568   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2455   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2569 | 2456 | 
| 2570   virtual bool CanDeoptimize() const { return false; } | 2457   virtual bool CanDeoptimize() const { return false; } | 
| 2571   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2458   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2572 | 2459 | 
| 2573  private: | 2460  private: | 
| 2574   const ClosureNode& ast_node_; | 2461   const ClosureNode& ast_node_; | 
| 2575   ZoneGrowableArray<PushArgumentInstr*>* arguments_; | 2462   ZoneGrowableArray<PushArgumentInstr*>* arguments_; | 
| 2576 | 2463 | 
| 2577   DISALLOW_COPY_AND_ASSIGN(CreateClosureComp); | 2464   DISALLOW_COPY_AND_ASSIGN(CreateClosureInstr); | 
| 2578 }; | 2465 }; | 
| 2579 | 2466 | 
| 2580 | 2467 | 
| 2581 class LoadVMFieldComp : public TemplateComputation<1> { | 2468 class LoadVMFieldInstr : public TemplateDefinition<1> { | 
| 2582  public: | 2469  public: | 
| 2583   LoadVMFieldComp(Value* value, | 2470   LoadVMFieldInstr(Value* value, | 
| 2584                   intptr_t offset_in_bytes, | 2471                    intptr_t offset_in_bytes, | 
| 2585                   const AbstractType& type) | 2472                    const AbstractType& type) | 
| 2586       : offset_in_bytes_(offset_in_bytes), | 2473       : offset_in_bytes_(offset_in_bytes), | 
| 2587         type_(type), | 2474         type_(type), | 
| 2588         result_cid_(kDynamicCid) { | 2475         result_cid_(kDynamicCid) { | 
| 2589     ASSERT(value != NULL); | 2476     ASSERT(value != NULL); | 
| 2590     ASSERT(type.IsZoneHandle());  // May be null if field is not an instance. | 2477     ASSERT(type.IsZoneHandle());  // May be null if field is not an instance. | 
| 2591     inputs_[0] = value; | 2478     inputs_[0] = value; | 
| 2592   } | 2479   } | 
| 2593 | 2480 | 
| 2594   DECLARE_COMPUTATION(LoadVMField) | 2481   DECLARE_INSTRUCTION(LoadVMField) | 
|  | 2482   virtual RawAbstractType* CompileType() const; | 
| 2595 | 2483 | 
| 2596   Value* value() const { return inputs_[0]; } | 2484   Value* value() const { return inputs_[0]; } | 
| 2597   intptr_t offset_in_bytes() const { return offset_in_bytes_; } | 2485   intptr_t offset_in_bytes() const { return offset_in_bytes_; } | 
| 2598   const AbstractType& type() const { return type_; } | 2486   const AbstractType& type() const { return type_; } | 
| 2599   void set_result_cid(intptr_t value) { result_cid_ = value; } | 2487   void set_result_cid(intptr_t value) { result_cid_ = value; } | 
| 2600 | 2488 | 
| 2601   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2489   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2602 | 2490 | 
| 2603   virtual bool CanDeoptimize() const { return false; } | 2491   virtual bool CanDeoptimize() const { return false; } | 
| 2604   virtual intptr_t ResultCid() const { return result_cid_; } | 2492   virtual intptr_t ResultCid() const { return result_cid_; } | 
| 2605 | 2493 | 
| 2606  private: | 2494  private: | 
| 2607   const intptr_t offset_in_bytes_; | 2495   const intptr_t offset_in_bytes_; | 
| 2608   const AbstractType& type_; | 2496   const AbstractType& type_; | 
| 2609   intptr_t result_cid_; | 2497   intptr_t result_cid_; | 
| 2610 | 2498 | 
| 2611   DISALLOW_COPY_AND_ASSIGN(LoadVMFieldComp); | 2499   DISALLOW_COPY_AND_ASSIGN(LoadVMFieldInstr); | 
| 2612 }; | 2500 }; | 
| 2613 | 2501 | 
| 2614 | 2502 | 
| 2615 class StoreVMFieldComp : public TemplateComputation<2> { | 2503 class StoreVMFieldInstr : public TemplateDefinition<2> { | 
| 2616  public: | 2504  public: | 
| 2617   StoreVMFieldComp(Value* dest, | 2505   StoreVMFieldInstr(Value* dest, | 
| 2618                    intptr_t offset_in_bytes, | 2506                     intptr_t offset_in_bytes, | 
| 2619                    Value* value, | 2507                     Value* value, | 
| 2620                    const AbstractType& type) | 2508                     const AbstractType& type) | 
| 2621       : offset_in_bytes_(offset_in_bytes), type_(type) { | 2509       : offset_in_bytes_(offset_in_bytes), type_(type) { | 
| 2622     ASSERT(value != NULL); | 2510     ASSERT(value != NULL); | 
| 2623     ASSERT(dest != NULL); | 2511     ASSERT(dest != NULL); | 
| 2624     ASSERT(type.IsZoneHandle());  // May be null if field is not an instance. | 2512     ASSERT(type.IsZoneHandle());  // May be null if field is not an instance. | 
| 2625     inputs_[0] = value; | 2513     inputs_[0] = value; | 
| 2626     inputs_[1] = dest; | 2514     inputs_[1] = dest; | 
| 2627   } | 2515   } | 
| 2628 | 2516 | 
| 2629   DECLARE_COMPUTATION(StoreVMField) | 2517   DECLARE_INSTRUCTION(StoreVMField) | 
|  | 2518   virtual RawAbstractType* CompileType() const; | 
| 2630 | 2519 | 
| 2631   Value* value() const { return inputs_[0]; } | 2520   Value* value() const { return inputs_[0]; } | 
| 2632   Value* dest() const { return inputs_[1]; } | 2521   Value* dest() const { return inputs_[1]; } | 
| 2633   intptr_t offset_in_bytes() const { return offset_in_bytes_; } | 2522   intptr_t offset_in_bytes() const { return offset_in_bytes_; } | 
| 2634   const AbstractType& type() const { return type_; } | 2523   const AbstractType& type() const { return type_; } | 
| 2635 | 2524 | 
| 2636   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2525   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2637 | 2526 | 
| 2638   virtual bool CanDeoptimize() const { return false; } | 2527   virtual bool CanDeoptimize() const { return false; } | 
| 2639   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2528   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2640 | 2529 | 
| 2641  private: | 2530  private: | 
| 2642   const intptr_t offset_in_bytes_; | 2531   const intptr_t offset_in_bytes_; | 
| 2643   const AbstractType& type_; | 2532   const AbstractType& type_; | 
| 2644 | 2533 | 
| 2645   DISALLOW_COPY_AND_ASSIGN(StoreVMFieldComp); | 2534   DISALLOW_COPY_AND_ASSIGN(StoreVMFieldInstr); | 
| 2646 }; | 2535 }; | 
| 2647 | 2536 | 
| 2648 | 2537 | 
| 2649 class InstantiateTypeArgumentsComp : public TemplateComputation<1> { | 2538 class InstantiateTypeArgumentsInstr : public TemplateDefinition<1> { | 
| 2650  public: | 2539  public: | 
| 2651   InstantiateTypeArgumentsComp(intptr_t token_pos, | 2540   InstantiateTypeArgumentsInstr(intptr_t token_pos, | 
| 2652                                const AbstractTypeArguments& type_arguments, | 2541                                 const AbstractTypeArguments& type_arguments, | 
| 2653                                Value* instantiator) | 2542                                 Value* instantiator) | 
| 2654       : token_pos_(token_pos), | 2543       : token_pos_(token_pos), | 
| 2655         type_arguments_(type_arguments) { | 2544         type_arguments_(type_arguments) { | 
| 2656     ASSERT(type_arguments.IsZoneHandle()); | 2545     ASSERT(type_arguments.IsZoneHandle()); | 
| 2657     ASSERT(instantiator != NULL); | 2546     ASSERT(instantiator != NULL); | 
| 2658     inputs_[0] = instantiator; | 2547     inputs_[0] = instantiator; | 
| 2659   } | 2548   } | 
| 2660 | 2549 | 
| 2661   DECLARE_COMPUTATION(InstantiateTypeArguments) | 2550   DECLARE_INSTRUCTION(InstantiateTypeArguments) | 
|  | 2551   virtual RawAbstractType* CompileType() const; | 
| 2662 | 2552 | 
| 2663   Value* instantiator() const { return inputs_[0]; } | 2553   Value* instantiator() const { return inputs_[0]; } | 
| 2664   const AbstractTypeArguments& type_arguments() const { | 2554   const AbstractTypeArguments& type_arguments() const { | 
| 2665     return type_arguments_; | 2555     return type_arguments_; | 
| 2666   } | 2556   } | 
| 2667   intptr_t token_pos() const { return token_pos_; } | 2557   intptr_t token_pos() const { return token_pos_; } | 
| 2668 | 2558 | 
| 2669   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2559   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2670 | 2560 | 
| 2671   virtual bool CanDeoptimize() const { return false; } | 2561   virtual bool CanDeoptimize() const { return false; } | 
| 2672   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2562   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2673 | 2563 | 
| 2674  private: | 2564  private: | 
| 2675   const intptr_t token_pos_; | 2565   const intptr_t token_pos_; | 
| 2676   const AbstractTypeArguments& type_arguments_; | 2566   const AbstractTypeArguments& type_arguments_; | 
| 2677 | 2567 | 
| 2678   DISALLOW_COPY_AND_ASSIGN(InstantiateTypeArgumentsComp); | 2568   DISALLOW_COPY_AND_ASSIGN(InstantiateTypeArgumentsInstr); | 
| 2679 }; | 2569 }; | 
| 2680 | 2570 | 
| 2681 | 2571 | 
| 2682 class ExtractConstructorTypeArgumentsComp : public TemplateComputation<1> { | 2572 class ExtractConstructorTypeArgumentsInstr : public TemplateDefinition<1> { | 
| 2683  public: | 2573  public: | 
| 2684   ExtractConstructorTypeArgumentsComp( | 2574   ExtractConstructorTypeArgumentsInstr( | 
| 2685       intptr_t token_pos, | 2575       intptr_t token_pos, | 
| 2686       const AbstractTypeArguments& type_arguments, | 2576       const AbstractTypeArguments& type_arguments, | 
| 2687       Value* instantiator) | 2577       Value* instantiator) | 
| 2688       : token_pos_(token_pos), | 2578       : token_pos_(token_pos), | 
| 2689         type_arguments_(type_arguments) { | 2579         type_arguments_(type_arguments) { | 
| 2690     ASSERT(instantiator != NULL); | 2580     ASSERT(instantiator != NULL); | 
| 2691     inputs_[0] = instantiator; | 2581     inputs_[0] = instantiator; | 
| 2692   } | 2582   } | 
| 2693 | 2583 | 
| 2694   DECLARE_COMPUTATION(ExtractConstructorTypeArguments) | 2584   DECLARE_INSTRUCTION(ExtractConstructorTypeArguments) | 
|  | 2585   virtual RawAbstractType* CompileType() const; | 
| 2695 | 2586 | 
| 2696   Value* instantiator() const { return inputs_[0]; } | 2587   Value* instantiator() const { return inputs_[0]; } | 
| 2697   const AbstractTypeArguments& type_arguments() const { | 2588   const AbstractTypeArguments& type_arguments() const { | 
| 2698     return type_arguments_; | 2589     return type_arguments_; | 
| 2699   } | 2590   } | 
| 2700   intptr_t token_pos() const { return token_pos_; } | 2591   intptr_t token_pos() const { return token_pos_; } | 
| 2701 | 2592 | 
| 2702   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2593   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2703 | 2594 | 
| 2704   virtual bool CanDeoptimize() const { return false; } | 2595   virtual bool CanDeoptimize() const { return false; } | 
| 2705   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2596   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2706 | 2597 | 
| 2707  private: | 2598  private: | 
| 2708   const intptr_t token_pos_; | 2599   const intptr_t token_pos_; | 
| 2709   const AbstractTypeArguments& type_arguments_; | 2600   const AbstractTypeArguments& type_arguments_; | 
| 2710 | 2601 | 
| 2711   DISALLOW_COPY_AND_ASSIGN(ExtractConstructorTypeArgumentsComp); | 2602   DISALLOW_COPY_AND_ASSIGN(ExtractConstructorTypeArgumentsInstr); | 
| 2712 }; | 2603 }; | 
| 2713 | 2604 | 
| 2714 | 2605 | 
| 2715 class ExtractConstructorInstantiatorComp : public TemplateComputation<1> { | 2606 class ExtractConstructorInstantiatorInstr : public TemplateDefinition<1> { | 
| 2716  public: | 2607  public: | 
| 2717   ExtractConstructorInstantiatorComp(ConstructorCallNode* ast_node, | 2608   ExtractConstructorInstantiatorInstr(ConstructorCallNode* ast_node, | 
| 2718                                      Value* instantiator) | 2609                                       Value* instantiator) | 
| 2719       : ast_node_(*ast_node) { | 2610       : ast_node_(*ast_node) { | 
| 2720     ASSERT(instantiator != NULL); | 2611     ASSERT(instantiator != NULL); | 
| 2721     inputs_[0] = instantiator; | 2612     inputs_[0] = instantiator; | 
| 2722   } | 2613   } | 
| 2723 | 2614 | 
| 2724   DECLARE_COMPUTATION(ExtractConstructorInstantiator) | 2615   DECLARE_INSTRUCTION(ExtractConstructorInstantiator) | 
|  | 2616   virtual RawAbstractType* CompileType() const; | 
| 2725 | 2617 | 
| 2726   Value* instantiator() const { return inputs_[0]; } | 2618   Value* instantiator() const { return inputs_[0]; } | 
| 2727   const AbstractTypeArguments& type_arguments() const { | 2619   const AbstractTypeArguments& type_arguments() const { | 
| 2728     return ast_node_.type_arguments(); | 2620     return ast_node_.type_arguments(); | 
| 2729   } | 2621   } | 
| 2730   const Function& constructor() const { return ast_node_.constructor(); } | 2622   const Function& constructor() const { return ast_node_.constructor(); } | 
| 2731   intptr_t token_pos() const { return ast_node_.token_pos(); } | 2623   intptr_t token_pos() const { return ast_node_.token_pos(); } | 
| 2732 | 2624 | 
| 2733   virtual bool CanDeoptimize() const { return false; } | 2625   virtual bool CanDeoptimize() const { return false; } | 
| 2734   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2626   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2735 | 2627 | 
| 2736  private: | 2628  private: | 
| 2737   const ConstructorCallNode& ast_node_; | 2629   const ConstructorCallNode& ast_node_; | 
| 2738 | 2630 | 
| 2739   DISALLOW_COPY_AND_ASSIGN(ExtractConstructorInstantiatorComp); | 2631   DISALLOW_COPY_AND_ASSIGN(ExtractConstructorInstantiatorInstr); | 
| 2740 }; | 2632 }; | 
| 2741 | 2633 | 
| 2742 | 2634 | 
| 2743 class AllocateContextComp : public TemplateComputation<0> { | 2635 class AllocateContextInstr : public TemplateDefinition<0> { | 
| 2744  public: | 2636  public: | 
| 2745   AllocateContextComp(intptr_t token_pos, | 2637   AllocateContextInstr(intptr_t token_pos, | 
| 2746                       intptr_t num_context_variables) | 2638                        intptr_t num_context_variables) | 
| 2747       : token_pos_(token_pos), | 2639       : token_pos_(token_pos), | 
| 2748         num_context_variables_(num_context_variables) {} | 2640         num_context_variables_(num_context_variables) {} | 
| 2749 | 2641 | 
| 2750   DECLARE_COMPUTATION(AllocateContext); | 2642   DECLARE_INSTRUCTION(AllocateContext); | 
|  | 2643   virtual RawAbstractType* CompileType() const; | 
| 2751 | 2644 | 
| 2752   intptr_t token_pos() const { return token_pos_; } | 2645   intptr_t token_pos() const { return token_pos_; } | 
| 2753   intptr_t num_context_variables() const { return num_context_variables_; } | 2646   intptr_t num_context_variables() const { return num_context_variables_; } | 
| 2754 | 2647 | 
| 2755   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2648   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2756 | 2649 | 
| 2757   virtual bool CanDeoptimize() const { return false; } | 2650   virtual bool CanDeoptimize() const { return false; } | 
| 2758   virtual intptr_t ResultCid() const { return kDynamicCid; } | 2651   virtual intptr_t ResultCid() const { return kDynamicCid; } | 
| 2759 | 2652 | 
| 2760  private: | 2653  private: | 
| 2761   const intptr_t token_pos_; | 2654   const intptr_t token_pos_; | 
| 2762   const intptr_t num_context_variables_; | 2655   const intptr_t num_context_variables_; | 
| 2763 | 2656 | 
| 2764   DISALLOW_COPY_AND_ASSIGN(AllocateContextComp); | 2657   DISALLOW_COPY_AND_ASSIGN(AllocateContextInstr); | 
| 2765 }; | 2658 }; | 
| 2766 | 2659 | 
| 2767 | 2660 | 
| 2768 class ChainContextComp : public TemplateComputation<1> { | 2661 class ChainContextInstr : public TemplateDefinition<1> { | 
| 2769  public: | 2662  public: | 
| 2770   explicit ChainContextComp(Value* context_value) { | 2663   explicit ChainContextInstr(Value* context_value) { | 
| 2771     ASSERT(context_value != NULL); | 2664     ASSERT(context_value != NULL); | 
| 2772     inputs_[0] = context_value; | 2665     inputs_[0] = context_value; | 
| 2773   } | 2666   } | 
| 2774 | 2667 | 
| 2775   DECLARE_COMPUTATION(ChainContext) | 2668   DECLARE_INSTRUCTION(ChainContext) | 
|  | 2669   virtual RawAbstractType* CompileType() const; | 
| 2776 | 2670 | 
| 2777   Value* context_value() const { return inputs_[0]; } | 2671   Value* context_value() const { return inputs_[0]; } | 
| 2778 | 2672 | 
| 2779   virtual bool CanDeoptimize() const { return false; } | 2673   virtual bool CanDeoptimize() const { return false; } | 
| 2780   virtual intptr_t ResultCid() const { return kIllegalCid; } | 2674   virtual intptr_t ResultCid() const { return kIllegalCid; } | 
| 2781 | 2675 | 
| 2782  private: | 2676  private: | 
| 2783   DISALLOW_COPY_AND_ASSIGN(ChainContextComp); | 2677   DISALLOW_COPY_AND_ASSIGN(ChainContextInstr); | 
| 2784 }; | 2678 }; | 
| 2785 | 2679 | 
| 2786 | 2680 | 
| 2787 class CloneContextComp : public TemplateComputation<1> { | 2681 class CloneContextInstr : public TemplateDefinition<1> { | 
| 2788  public: | 2682  public: | 
| 2789   CloneContextComp(intptr_t token_pos, | 2683   CloneContextInstr(intptr_t token_pos, Value* context_value) | 
| 2790                    Value* context_value) |  | 
| 2791       : token_pos_(token_pos) { | 2684       : token_pos_(token_pos) { | 
| 2792     ASSERT(context_value != NULL); | 2685     ASSERT(context_value != NULL); | 
| 2793     inputs_[0] = context_value; | 2686     inputs_[0] = context_value; | 
| 2794   } | 2687   } | 
| 2795 | 2688 | 
| 2796   intptr_t token_pos() const { return token_pos_; } | 2689   intptr_t token_pos() const { return token_pos_; } | 
| 2797   Value* context_value() const { return inputs_[0]; } | 2690   Value* context_value() const { return inputs_[0]; } | 
| 2798 | 2691 | 
| 2799   DECLARE_COMPUTATION(CloneContext) | 2692   DECLARE_INSTRUCTION(CloneContext) | 
|  | 2693   virtual RawAbstractType* CompileType() const; | 
| 2800 | 2694 | 
| 2801   virtual bool CanDeoptimize() const { return false; } | 2695   virtual bool CanDeoptimize() const { return false; } | 
| 2802   virtual intptr_t ResultCid() const { return kIllegalCid; } | 2696   virtual intptr_t ResultCid() const { return kIllegalCid; } | 
| 2803 | 2697 | 
| 2804  private: | 2698  private: | 
| 2805   const intptr_t token_pos_; | 2699   const intptr_t token_pos_; | 
| 2806 | 2700 | 
| 2807   DISALLOW_COPY_AND_ASSIGN(CloneContextComp); | 2701   DISALLOW_COPY_AND_ASSIGN(CloneContextInstr); | 
| 2808 }; | 2702 }; | 
| 2809 | 2703 | 
| 2810 | 2704 | 
| 2811 class CatchEntryComp : public TemplateComputation<0> { | 2705 class CatchEntryInstr : public TemplateDefinition<0> { | 
| 2812  public: | 2706  public: | 
| 2813   CatchEntryComp(const LocalVariable& exception_var, | 2707   CatchEntryInstr(const LocalVariable& exception_var, | 
| 2814                  const LocalVariable& stacktrace_var) | 2708                   const LocalVariable& stacktrace_var) | 
| 2815       : exception_var_(exception_var), stacktrace_var_(stacktrace_var) {} | 2709       : exception_var_(exception_var), stacktrace_var_(stacktrace_var) {} | 
| 2816 | 2710 | 
| 2817   const LocalVariable& exception_var() const { return exception_var_; } | 2711   const LocalVariable& exception_var() const { return exception_var_; } | 
| 2818   const LocalVariable& stacktrace_var() const { return stacktrace_var_; } | 2712   const LocalVariable& stacktrace_var() const { return stacktrace_var_; } | 
| 2819 | 2713 | 
| 2820   DECLARE_COMPUTATION(CatchEntry) | 2714   DECLARE_INSTRUCTION(CatchEntry) | 
|  | 2715   virtual RawAbstractType* CompileType() const; | 
| 2821 | 2716 | 
| 2822   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2717   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2823 | 2718 | 
| 2824   virtual bool CanDeoptimize() const { return false; } | 2719   virtual bool CanDeoptimize() const { return false; } | 
| 2825   virtual intptr_t ResultCid() const { return kIllegalCid; } | 2720   virtual intptr_t ResultCid() const { return kIllegalCid; } | 
| 2826 | 2721 | 
| 2827  private: | 2722  private: | 
| 2828   const LocalVariable& exception_var_; | 2723   const LocalVariable& exception_var_; | 
| 2829   const LocalVariable& stacktrace_var_; | 2724   const LocalVariable& stacktrace_var_; | 
| 2830 | 2725 | 
| 2831   DISALLOW_COPY_AND_ASSIGN(CatchEntryComp); | 2726   DISALLOW_COPY_AND_ASSIGN(CatchEntryInstr); | 
| 2832 }; | 2727 }; | 
| 2833 | 2728 | 
| 2834 | 2729 | 
| 2835 class CheckEitherNonSmiComp : public TemplateComputation<2> { | 2730 class CheckEitherNonSmiInstr : public TemplateDefinition<2> { | 
| 2836  public: | 2731  public: | 
| 2837   CheckEitherNonSmiComp(Value* left, | 2732   CheckEitherNonSmiInstr(Value* left, | 
| 2838                         Value* right, | 2733                          Value* right, | 
| 2839                         InstanceCallComp* instance_call) | 2734                          InstanceCallInstr* instance_call) { | 
| 2840       : instance_call_(instance_call) { |  | 
| 2841     ASSERT(left != NULL); | 2735     ASSERT(left != NULL); | 
| 2842     ASSERT(right != NULL); | 2736     ASSERT(right != NULL); | 
| 2843     inputs_[0] = left; | 2737     inputs_[0] = left; | 
| 2844     inputs_[1] = right; | 2738     inputs_[1] = right; | 
|  | 2739     deopt_id_ = instance_call->deopt_id(); | 
| 2845   } | 2740   } | 
| 2846 | 2741 | 
| 2847   DECLARE_COMPUTATION(CheckEitherNonSmi) | 2742   DECLARE_INSTRUCTION(CheckEitherNonSmi) | 
|  | 2743   virtual RawAbstractType* CompileType() const; | 
| 2848 | 2744 | 
| 2849   virtual bool CanDeoptimize() const { return true; } | 2745   virtual bool CanDeoptimize() const { return true; } | 
| 2850   virtual intptr_t ResultCid() const { return kIllegalCid; } | 2746   virtual intptr_t ResultCid() const { return kIllegalCid; } | 
| 2851 | 2747 | 
| 2852   virtual bool AttributesEqual(Computation* other) const { return true; } | 2748   virtual bool AttributesEqual(Definition* other) const { return true; } | 
| 2853 | 2749 | 
| 2854   virtual bool HasSideEffect() const { return false; } | 2750   virtual bool HasSideEffect() const { return false; } | 
| 2855 | 2751 | 
| 2856   Value* left() const { return inputs_[0]; } | 2752   Value* left() const { return inputs_[0]; } | 
| 2857 | 2753 | 
| 2858   Value* right() const { return inputs_[1]; } | 2754   Value* right() const { return inputs_[1]; } | 
| 2859 | 2755 | 
| 2860   virtual Definition* TryReplace(BindInstr* instr) const; | 2756   virtual Definition* Canonicalize(); | 
| 2861 | 2757 | 
| 2862  private: | 2758  private: | 
| 2863   InstanceCallComp* instance_call_; | 2759   DISALLOW_COPY_AND_ASSIGN(CheckEitherNonSmiInstr); | 
| 2864 |  | 
| 2865   DISALLOW_COPY_AND_ASSIGN(CheckEitherNonSmiComp); |  | 
| 2866 }; | 2760 }; | 
| 2867 | 2761 | 
| 2868 | 2762 | 
| 2869 class BoxDoubleComp : public TemplateComputation<1> { | 2763 class BoxDoubleInstr : public TemplateDefinition<1> { | 
| 2870  public: | 2764  public: | 
| 2871   BoxDoubleComp(Value* value, InstanceCallComp* instance_call) | 2765   BoxDoubleInstr(Value* value, InstanceCallInstr* instance_call) | 
| 2872       : token_pos_((instance_call != NULL) ? instance_call->token_pos() : 0) { | 2766       : token_pos_((instance_call != NULL) ? instance_call->token_pos() : 0) { | 
| 2873     ASSERT(value != NULL); | 2767     ASSERT(value != NULL); | 
| 2874     inputs_[0] = value; | 2768     inputs_[0] = value; | 
| 2875   } | 2769   } | 
| 2876 | 2770 | 
| 2877   Value* value() const { return inputs_[0]; } | 2771   Value* value() const { return inputs_[0]; } | 
| 2878 | 2772 | 
| 2879   intptr_t token_pos() const { return token_pos_; } | 2773   intptr_t token_pos() const { return token_pos_; } | 
| 2880 | 2774 | 
| 2881   virtual bool CanDeoptimize() const { return false; } | 2775   virtual bool CanDeoptimize() const { return false; } | 
| 2882   virtual bool HasSideEffect() const { return false; } | 2776   virtual bool HasSideEffect() const { return false; } | 
| 2883   virtual bool AttributesEqual(Computation* other) const { return true; } | 2777   virtual bool AttributesEqual(Definition* other) const { return true; } | 
| 2884 | 2778 | 
| 2885   virtual intptr_t ResultCid() const; | 2779   virtual intptr_t ResultCid() const; | 
| 2886 | 2780 | 
| 2887   virtual Representation RequiredInputRepresentation(intptr_t idx) const { | 2781   virtual Representation RequiredInputRepresentation(intptr_t idx) const { | 
| 2888     ASSERT(idx == 0); | 2782     ASSERT(idx == 0); | 
| 2889     return kUnboxedDouble; | 2783     return kUnboxedDouble; | 
| 2890   } | 2784   } | 
| 2891 | 2785 | 
| 2892   DECLARE_COMPUTATION(BoxDouble) | 2786   DECLARE_INSTRUCTION(BoxDouble) | 
|  | 2787   virtual RawAbstractType* CompileType() const; | 
| 2893 | 2788 | 
| 2894  private: | 2789  private: | 
| 2895   const intptr_t token_pos_; | 2790   const intptr_t token_pos_; | 
| 2896 | 2791 | 
| 2897   DISALLOW_COPY_AND_ASSIGN(BoxDoubleComp); | 2792   DISALLOW_COPY_AND_ASSIGN(BoxDoubleInstr); | 
| 2898 }; | 2793 }; | 
| 2899 | 2794 | 
| 2900 | 2795 | 
| 2901 class UnboxDoubleComp : public TemplateComputation<1> { | 2796 class UnboxDoubleInstr : public TemplateDefinition<1> { | 
| 2902  public: | 2797  public: | 
| 2903   UnboxDoubleComp(Value* value, intptr_t deopt_id) | 2798   UnboxDoubleInstr(Value* value, intptr_t deopt_id) { | 
| 2904       : deopt_id_(deopt_id) { |  | 
| 2905     ASSERT(value != NULL); | 2799     ASSERT(value != NULL); | 
| 2906     inputs_[0] = value; | 2800     inputs_[0] = value; | 
|  | 2801     deopt_id_ = deopt_id; | 
| 2907   } | 2802   } | 
| 2908 | 2803 | 
| 2909   Value* value() const { return inputs_[0]; } | 2804   Value* value() const { return inputs_[0]; } | 
| 2910 | 2805 | 
| 2911   virtual bool CanDeoptimize() const { | 2806   virtual bool CanDeoptimize() const { | 
| 2912     return value()->ResultCid() != kDoubleCid; | 2807     return value()->ResultCid() != kDoubleCid; | 
| 2913   } | 2808   } | 
| 2914 | 2809 | 
| 2915   // The output is not an instance but when it is boxed it becomes double. | 2810   // The output is not an instance but when it is boxed it becomes double. | 
| 2916   virtual intptr_t ResultCid() const { return kDoubleCid; } | 2811   virtual intptr_t ResultCid() const { return kDoubleCid; } | 
| 2917 | 2812 | 
| 2918   virtual Representation representation() const { | 2813   virtual Representation representation() const { | 
| 2919     return kUnboxedDouble; | 2814     return kUnboxedDouble; | 
| 2920   } | 2815   } | 
| 2921 | 2816 | 
| 2922   virtual bool HasSideEffect() const { return false; } | 2817   virtual bool HasSideEffect() const { return false; } | 
| 2923   virtual bool AttributesEqual(Computation* other) const { return true; } | 2818   virtual bool AttributesEqual(Definition* other) const { return true; } | 
| 2924 | 2819 | 
| 2925   DECLARE_COMPUTATION(UnboxDouble) | 2820   DECLARE_INSTRUCTION(UnboxDouble) | 
|  | 2821   virtual RawAbstractType* CompileType() const; | 
| 2926 | 2822 | 
| 2927  private: | 2823  private: | 
| 2928   const intptr_t deopt_id_; | 2824   DISALLOW_COPY_AND_ASSIGN(UnboxDoubleInstr); | 
| 2929 |  | 
| 2930   DISALLOW_COPY_AND_ASSIGN(UnboxDoubleComp); |  | 
| 2931 }; | 2825 }; | 
| 2932 | 2826 | 
| 2933 | 2827 | 
| 2934 class UnboxedDoubleBinaryOpComp : public TemplateComputation<2> { | 2828 class UnboxedDoubleBinaryOpInstr : public TemplateDefinition<2> { | 
| 2935  public: | 2829  public: | 
| 2936   UnboxedDoubleBinaryOpComp(Token::Kind op_kind, | 2830   UnboxedDoubleBinaryOpInstr(Token::Kind op_kind, | 
| 2937                             Value* left, | 2831                              Value* left, | 
| 2938                             Value* right, | 2832                              Value* right, | 
| 2939                             InstanceCallComp* call) | 2833                              InstanceCallInstr* instance_call) | 
| 2940       : op_kind_(op_kind), deopt_id_(call->deopt_id()) { | 2834       : op_kind_(op_kind) { | 
| 2941     ASSERT(left != NULL); | 2835     ASSERT(left != NULL); | 
| 2942     ASSERT(right != NULL); | 2836     ASSERT(right != NULL); | 
| 2943     inputs_[0] = left; | 2837     inputs_[0] = left; | 
| 2944     inputs_[1] = right; | 2838     inputs_[1] = right; | 
|  | 2839     deopt_id_ = instance_call->deopt_id(); | 
| 2945   } | 2840   } | 
| 2946 | 2841 | 
| 2947   Value* left() const { return inputs_[0]; } | 2842   Value* left() const { return inputs_[0]; } | 
| 2948   Value* right() const { return inputs_[1]; } | 2843   Value* right() const { return inputs_[1]; } | 
| 2949 | 2844 | 
| 2950   Token::Kind op_kind() const { return op_kind_; } | 2845   Token::Kind op_kind() const { return op_kind_; } | 
| 2951 | 2846 | 
| 2952   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2847   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 2953 | 2848 | 
| 2954   virtual bool CanDeoptimize() const { return false; } | 2849   virtual bool CanDeoptimize() const { return false; } | 
| 2955   virtual bool HasSideEffect() const { return false; } | 2850   virtual bool HasSideEffect() const { return false; } | 
| 2956 | 2851 | 
| 2957   virtual bool AttributesEqual(Computation* other) const { | 2852   virtual bool AttributesEqual(Definition* other) const { | 
| 2958     return op_kind() == other->AsUnboxedDoubleBinaryOp()->op_kind(); | 2853     return op_kind() == other->AsUnboxedDoubleBinaryOp()->op_kind(); | 
| 2959   } | 2854   } | 
| 2960 | 2855 | 
| 2961   // The output is not an instance but when it is boxed it becomes double. | 2856   // The output is not an instance but when it is boxed it becomes double. | 
| 2962   virtual intptr_t ResultCid() const { return kDoubleCid; } | 2857   virtual intptr_t ResultCid() const { return kDoubleCid; } | 
| 2963 | 2858 | 
| 2964   virtual Representation representation() const { | 2859   virtual Representation representation() const { | 
| 2965     return kUnboxedDouble; | 2860     return kUnboxedDouble; | 
| 2966   } | 2861   } | 
| 2967 | 2862 | 
| 2968   virtual Representation RequiredInputRepresentation(intptr_t idx) const { | 2863   virtual Representation RequiredInputRepresentation(intptr_t idx) const { | 
| 2969     ASSERT((idx == 0) || (idx == 1)); | 2864     ASSERT((idx == 0) || (idx == 1)); | 
| 2970     return kUnboxedDouble; | 2865     return kUnboxedDouble; | 
| 2971   } | 2866   } | 
| 2972 | 2867 | 
| 2973   virtual intptr_t DeoptimizationTarget() const { | 2868   virtual intptr_t DeoptimizationTarget() const { | 
| 2974     return deopt_id_; | 2869     return deopt_id(); | 
| 2975   } | 2870   } | 
| 2976 | 2871 | 
| 2977   DECLARE_COMPUTATION(UnboxedDoubleBinaryOp) | 2872   DECLARE_INSTRUCTION(UnboxedDoubleBinaryOp) | 
|  | 2873   virtual RawAbstractType* CompileType() const; | 
| 2978 | 2874 | 
| 2979  private: | 2875  private: | 
| 2980   const Token::Kind op_kind_; | 2876   const Token::Kind op_kind_; | 
| 2981   const intptr_t deopt_id_; |  | 
| 2982 | 2877 | 
| 2983   DISALLOW_COPY_AND_ASSIGN(UnboxedDoubleBinaryOpComp); | 2878   DISALLOW_COPY_AND_ASSIGN(UnboxedDoubleBinaryOpInstr); | 
| 2984 }; | 2879 }; | 
| 2985 | 2880 | 
| 2986 | 2881 | 
| 2987 class BinarySmiOpComp : public TemplateComputation<2> { | 2882 class BinarySmiOpInstr : public TemplateDefinition<2> { | 
| 2988  public: | 2883  public: | 
| 2989   BinarySmiOpComp(Token::Kind op_kind, | 2884   BinarySmiOpInstr(Token::Kind op_kind, | 
| 2990                   InstanceCallComp* instance_call, | 2885                    InstanceCallInstr* instance_call, | 
| 2991                   Value* left, | 2886                    Value* left, | 
| 2992                   Value* right) | 2887                    Value* right) | 
| 2993       : op_kind_(op_kind), | 2888       : op_kind_(op_kind), | 
| 2994         instance_call_(instance_call) { | 2889         instance_call_(instance_call) { | 
| 2995     ASSERT(left != NULL); | 2890     ASSERT(left != NULL); | 
| 2996     ASSERT(right != NULL); | 2891     ASSERT(right != NULL); | 
| 2997     inputs_[0] = left; | 2892     inputs_[0] = left; | 
| 2998     inputs_[1] = right; | 2893     inputs_[1] = right; | 
| 2999   } | 2894   } | 
| 3000 | 2895 | 
| 3001   Value* left() const { return inputs_[0]; } | 2896   Value* left() const { return inputs_[0]; } | 
| 3002   Value* right() const { return inputs_[1]; } | 2897   Value* right() const { return inputs_[1]; } | 
| 3003 | 2898 | 
| 3004   Token::Kind op_kind() const { return op_kind_; } | 2899   Token::Kind op_kind() const { return op_kind_; } | 
| 3005 | 2900 | 
| 3006   InstanceCallComp* instance_call() const { return instance_call_; } | 2901   InstanceCallInstr* instance_call() const { return instance_call_; } | 
| 3007 | 2902 | 
| 3008   const ICData* ic_data() const { return instance_call()->ic_data(); } | 2903   const ICData* ic_data() const { return instance_call()->ic_data(); } | 
| 3009 | 2904 | 
| 3010   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2905   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 3011 | 2906 | 
| 3012   DECLARE_COMPUTATION(BinarySmiOp) | 2907   DECLARE_INSTRUCTION(BinarySmiOp) | 
|  | 2908   virtual RawAbstractType* CompileType() const; | 
| 3013 | 2909 | 
| 3014   virtual bool CanDeoptimize() const; | 2910   virtual bool CanDeoptimize() const; | 
| 3015 | 2911 | 
| 3016   virtual intptr_t ResultCid() const; | 2912   virtual intptr_t ResultCid() const; | 
| 3017 | 2913 | 
| 3018  private: | 2914  private: | 
| 3019   const Token::Kind op_kind_; | 2915   const Token::Kind op_kind_; | 
| 3020   InstanceCallComp* instance_call_; | 2916   InstanceCallInstr* instance_call_; | 
| 3021 | 2917 | 
| 3022   DISALLOW_COPY_AND_ASSIGN(BinarySmiOpComp); | 2918   DISALLOW_COPY_AND_ASSIGN(BinarySmiOpInstr); | 
| 3023 }; | 2919 }; | 
| 3024 | 2920 | 
| 3025 | 2921 | 
| 3026 class BinaryMintOpComp : public TemplateComputation<2> { | 2922 class BinaryMintOpInstr : public TemplateDefinition<2> { | 
| 3027  public: | 2923  public: | 
| 3028   BinaryMintOpComp(Token::Kind op_kind, | 2924   BinaryMintOpInstr(Token::Kind op_kind, | 
| 3029                    InstanceCallComp* instance_call, | 2925                     InstanceCallInstr* instance_call, | 
| 3030                    Value* left, | 2926                     Value* left, | 
| 3031                    Value* right) | 2927                     Value* right) | 
| 3032       : op_kind_(op_kind), | 2928       : op_kind_(op_kind), | 
| 3033         instance_call_(instance_call) { | 2929         instance_call_(instance_call) { | 
| 3034     ASSERT(left != NULL); | 2930     ASSERT(left != NULL); | 
| 3035     ASSERT(right != NULL); | 2931     ASSERT(right != NULL); | 
| 3036     inputs_[0] = left; | 2932     inputs_[0] = left; | 
| 3037     inputs_[1] = right; | 2933     inputs_[1] = right; | 
| 3038   } | 2934   } | 
| 3039 | 2935 | 
| 3040   Value* left() const { return inputs_[0]; } | 2936   Value* left() const { return inputs_[0]; } | 
| 3041   Value* right() const { return inputs_[1]; } | 2937   Value* right() const { return inputs_[1]; } | 
| 3042 | 2938 | 
| 3043   Token::Kind op_kind() const { return op_kind_; } | 2939   Token::Kind op_kind() const { return op_kind_; } | 
| 3044 | 2940 | 
| 3045   InstanceCallComp* instance_call() const { return instance_call_; } | 2941   InstanceCallInstr* instance_call() const { return instance_call_; } | 
| 3046 | 2942 | 
| 3047   const ICData* ic_data() const { return instance_call()->ic_data(); } | 2943   const ICData* ic_data() const { return instance_call()->ic_data(); } | 
| 3048 | 2944 | 
| 3049   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2945   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 3050 | 2946 | 
| 3051   DECLARE_COMPUTATION(BinaryMintOp) | 2947   DECLARE_INSTRUCTION(BinaryMintOp) | 
|  | 2948   virtual RawAbstractType* CompileType() const; | 
| 3052 | 2949 | 
| 3053   virtual bool CanDeoptimize() const { return true; } | 2950   virtual bool CanDeoptimize() const { return true; } | 
| 3054   virtual intptr_t ResultCid() const; | 2951   virtual intptr_t ResultCid() const; | 
| 3055 | 2952 | 
| 3056  private: | 2953  private: | 
| 3057   const Token::Kind op_kind_; | 2954   const Token::Kind op_kind_; | 
| 3058   InstanceCallComp* instance_call_; | 2955   InstanceCallInstr* instance_call_; | 
| 3059 | 2956 | 
| 3060   DISALLOW_COPY_AND_ASSIGN(BinaryMintOpComp); | 2957   DISALLOW_COPY_AND_ASSIGN(BinaryMintOpInstr); | 
| 3061 }; | 2958 }; | 
| 3062 | 2959 | 
| 3063 | 2960 | 
| 3064 // Handles both Smi operations: BIT_OR and NEGATE. | 2961 // Handles both Smi operations: BIT_OR and NEGATE. | 
| 3065 class UnarySmiOpComp : public TemplateComputation<1> { | 2962 class UnarySmiOpInstr : public TemplateDefinition<1> { | 
| 3066  public: | 2963  public: | 
| 3067   UnarySmiOpComp(Token::Kind op_kind, | 2964   UnarySmiOpInstr(Token::Kind op_kind, | 
| 3068                  InstanceCallComp* instance_call, | 2965                   InstanceCallInstr* instance_call, | 
| 3069                  Value* value) | 2966                   Value* value) | 
| 3070       : op_kind_(op_kind), instance_call_(instance_call) { | 2967       : op_kind_(op_kind), instance_call_(instance_call) { | 
| 3071     ASSERT((op_kind == Token::kNEGATE) || (op_kind == Token::kBIT_NOT)); | 2968     ASSERT((op_kind == Token::kNEGATE) || (op_kind == Token::kBIT_NOT)); | 
| 3072     ASSERT(value != NULL); | 2969     ASSERT(value != NULL); | 
| 3073     inputs_[0] = value; | 2970     inputs_[0] = value; | 
| 3074   } | 2971   } | 
| 3075 | 2972 | 
| 3076   Value* value() const { return inputs_[0]; } | 2973   Value* value() const { return inputs_[0]; } | 
| 3077   Token::Kind op_kind() const { return op_kind_; } | 2974   Token::Kind op_kind() const { return op_kind_; } | 
| 3078 | 2975 | 
| 3079   InstanceCallComp* instance_call() const { return instance_call_; } | 2976   InstanceCallInstr* instance_call() const { return instance_call_; } | 
| 3080 | 2977 | 
| 3081   virtual void PrintOperandsTo(BufferFormatter* f) const; | 2978   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 3082 | 2979 | 
| 3083   DECLARE_COMPUTATION(UnarySmiOp) | 2980   DECLARE_INSTRUCTION(UnarySmiOp) | 
|  | 2981   virtual RawAbstractType* CompileType() const; | 
| 3084 | 2982 | 
| 3085   virtual bool CanDeoptimize() const { return op_kind() == Token::kNEGATE; } | 2983   virtual bool CanDeoptimize() const { return op_kind() == Token::kNEGATE; } | 
| 3086   virtual intptr_t ResultCid() const { return kSmiCid; } | 2984   virtual intptr_t ResultCid() const { return kSmiCid; } | 
| 3087 | 2985 | 
| 3088  private: | 2986  private: | 
| 3089   const Token::Kind op_kind_; | 2987   const Token::Kind op_kind_; | 
| 3090   InstanceCallComp* instance_call_; | 2988   InstanceCallInstr* instance_call_; | 
| 3091 | 2989 | 
| 3092   DISALLOW_COPY_AND_ASSIGN(UnarySmiOpComp); | 2990   DISALLOW_COPY_AND_ASSIGN(UnarySmiOpInstr); | 
| 3093 }; | 2991 }; | 
| 3094 | 2992 | 
| 3095 | 2993 | 
| 3096 // Handles non-Smi NEGATE operations | 2994 // Handles non-Smi NEGATE operations | 
| 3097 class NumberNegateComp : public TemplateComputation<1> { | 2995 class NumberNegateInstr : public TemplateDefinition<1> { | 
| 3098  public: | 2996  public: | 
| 3099   NumberNegateComp(InstanceCallComp* instance_call, | 2997   NumberNegateInstr(InstanceCallInstr* instance_call, Value* value) | 
| 3100                    Value* value) : instance_call_(instance_call) { | 2998       : instance_call_(instance_call) { | 
| 3101     ASSERT(value != NULL); | 2999     ASSERT(value != NULL); | 
| 3102     inputs_[0] = value; | 3000     inputs_[0] = value; | 
| 3103   } | 3001   } | 
| 3104 | 3002 | 
| 3105   Value* value() const { return inputs_[0]; } | 3003   Value* value() const { return inputs_[0]; } | 
| 3106 | 3004 | 
| 3107   InstanceCallComp* instance_call() const { return instance_call_; } | 3005   InstanceCallInstr* instance_call() const { return instance_call_; } | 
| 3108 | 3006 | 
| 3109   const ICData* ic_data() const { return instance_call()->ic_data(); } | 3007   const ICData* ic_data() const { return instance_call()->ic_data(); } | 
| 3110 | 3008 | 
| 3111   DECLARE_COMPUTATION(NumberNegate) | 3009   DECLARE_INSTRUCTION(NumberNegate) | 
|  | 3010   virtual RawAbstractType* CompileType() const; | 
| 3112 | 3011 | 
| 3113   virtual bool CanDeoptimize() const { return true; } | 3012   virtual bool CanDeoptimize() const { return true; } | 
| 3114   virtual intptr_t ResultCid() const { return kDoubleCid; } | 3013   virtual intptr_t ResultCid() const { return kDoubleCid; } | 
| 3115 | 3014 | 
| 3116  private: | 3015  private: | 
| 3117   InstanceCallComp* instance_call_; | 3016   InstanceCallInstr* instance_call_; | 
| 3118 | 3017 | 
| 3119   DISALLOW_COPY_AND_ASSIGN(NumberNegateComp); | 3018   DISALLOW_COPY_AND_ASSIGN(NumberNegateInstr); | 
| 3120 }; | 3019 }; | 
| 3121 | 3020 | 
| 3122 | 3021 | 
| 3123 class CheckStackOverflowComp : public TemplateComputation<0> { | 3022 class CheckStackOverflowInstr : public TemplateDefinition<0> { | 
| 3124  public: | 3023  public: | 
| 3125   explicit CheckStackOverflowComp(intptr_t token_pos) | 3024   explicit CheckStackOverflowInstr(intptr_t token_pos) | 
| 3126       : token_pos_(token_pos) {} | 3025       : token_pos_(token_pos) {} | 
| 3127 | 3026 | 
| 3128   intptr_t token_pos() const { return token_pos_; } | 3027   intptr_t token_pos() const { return token_pos_; } | 
| 3129 | 3028 | 
| 3130   DECLARE_COMPUTATION(CheckStackOverflow) | 3029   DECLARE_INSTRUCTION(CheckStackOverflow) | 
|  | 3030   virtual RawAbstractType* CompileType() const; | 
| 3131 | 3031 | 
| 3132   virtual bool CanDeoptimize() const { return false; } | 3032   virtual bool CanDeoptimize() const { return false; } | 
| 3133   virtual intptr_t ResultCid() const { return kIllegalCid; } | 3033   virtual intptr_t ResultCid() const { return kIllegalCid; } | 
| 3134 | 3034 | 
| 3135  private: | 3035  private: | 
| 3136   const intptr_t token_pos_; | 3036   const intptr_t token_pos_; | 
| 3137 | 3037 | 
| 3138   DISALLOW_COPY_AND_ASSIGN(CheckStackOverflowComp); | 3038   DISALLOW_COPY_AND_ASSIGN(CheckStackOverflowInstr); | 
| 3139 }; | 3039 }; | 
| 3140 | 3040 | 
| 3141 | 3041 | 
| 3142 class DoubleToDoubleComp : public TemplateComputation<1> { | 3042 class DoubleToDoubleInstr : public TemplateDefinition<1> { | 
| 3143  public: | 3043  public: | 
| 3144   DoubleToDoubleComp(Value* value, InstanceCallComp* instance_call) | 3044   DoubleToDoubleInstr(Value* value, InstanceCallInstr* instance_call) | 
| 3145       : instance_call_(instance_call) { | 3045       : instance_call_(instance_call) { | 
| 3146     ASSERT(value != NULL); | 3046     ASSERT(value != NULL); | 
| 3147     inputs_[0] = value; | 3047     inputs_[0] = value; | 
| 3148   } | 3048   } | 
| 3149 | 3049 | 
| 3150   Value* value() const { return inputs_[0]; } | 3050   Value* value() const { return inputs_[0]; } | 
| 3151 | 3051 | 
| 3152   InstanceCallComp* instance_call() const { return instance_call_; } | 3052   InstanceCallInstr* instance_call() const { return instance_call_; } | 
| 3153 | 3053 | 
| 3154   DECLARE_COMPUTATION(DoubleToDouble) | 3054   DECLARE_INSTRUCTION(DoubleToDouble) | 
|  | 3055   virtual RawAbstractType* CompileType() const; | 
| 3155 | 3056 | 
| 3156   virtual bool CanDeoptimize() const { return true; } | 3057   virtual bool CanDeoptimize() const { return true; } | 
| 3157   virtual intptr_t ResultCid() const { return kDoubleCid; } | 3058   virtual intptr_t ResultCid() const { return kDoubleCid; } | 
| 3158 | 3059 | 
| 3159  private: | 3060  private: | 
| 3160   InstanceCallComp* instance_call_; | 3061   InstanceCallInstr* instance_call_; | 
| 3161 | 3062 | 
| 3162   DISALLOW_COPY_AND_ASSIGN(DoubleToDoubleComp); | 3063   DISALLOW_COPY_AND_ASSIGN(DoubleToDoubleInstr); | 
| 3163 }; | 3064 }; | 
| 3164 | 3065 | 
| 3165 | 3066 | 
| 3166 class SmiToDoubleComp : public TemplateComputation<0> { | 3067 class SmiToDoubleInstr : public TemplateDefinition<0> { | 
| 3167  public: | 3068  public: | 
| 3168   explicit SmiToDoubleComp(InstanceCallComp* instance_call) | 3069   explicit SmiToDoubleInstr(InstanceCallInstr* instance_call) | 
| 3169       : instance_call_(instance_call) { } | 3070       : instance_call_(instance_call) { } | 
| 3170 | 3071 | 
| 3171   InstanceCallComp* instance_call() const { return instance_call_; } | 3072   InstanceCallInstr* instance_call() const { return instance_call_; } | 
| 3172 | 3073 | 
| 3173   DECLARE_CALL_COMPUTATION(SmiToDouble) | 3074   DECLARE_INSTRUCTION(SmiToDouble) | 
|  | 3075   virtual RawAbstractType* CompileType() const; | 
| 3174 | 3076 | 
| 3175   virtual intptr_t ArgumentCount() const { return 1; } | 3077   virtual intptr_t ArgumentCount() const { return 1; } | 
| 3176 | 3078 | 
| 3177   virtual bool CanDeoptimize() const { return true; } | 3079   virtual bool CanDeoptimize() const { return true; } | 
| 3178   virtual intptr_t ResultCid() const { return kDoubleCid; } | 3080   virtual intptr_t ResultCid() const { return kDoubleCid; } | 
| 3179 | 3081 | 
| 3180  private: | 3082  private: | 
| 3181   InstanceCallComp* instance_call_; | 3083   InstanceCallInstr* instance_call_; | 
| 3182 | 3084 | 
| 3183   DISALLOW_COPY_AND_ASSIGN(SmiToDoubleComp); | 3085   DISALLOW_COPY_AND_ASSIGN(SmiToDoubleInstr); | 
| 3184 }; | 3086 }; | 
| 3185 | 3087 | 
| 3186 | 3088 | 
| 3187 class CheckClassComp : public TemplateComputation<1> { | 3089 class CheckClassInstr : public TemplateDefinition<1> { | 
| 3188  public: | 3090  public: | 
| 3189   CheckClassComp(Value* value, | 3091   CheckClassInstr(Value* value, | 
| 3190                  InstanceCallComp* instance_call, | 3092                   InstanceCallInstr* instance_call, | 
| 3191                  const ICData& unary_checks) | 3093                   const ICData& unary_checks) | 
| 3192       : instance_call_(instance_call), | 3094       : unary_checks_(unary_checks) { | 
| 3193         unary_checks_(unary_checks) { |  | 
| 3194     ASSERT(value != NULL); | 3095     ASSERT(value != NULL); | 
| 3195     inputs_[0] = value; | 3096     inputs_[0] = value; | 
|  | 3097     deopt_id_ = instance_call->deopt_id(); | 
| 3196   } | 3098   } | 
| 3197 | 3099 | 
| 3198   DECLARE_COMPUTATION(CheckClass) | 3100   DECLARE_INSTRUCTION(CheckClass) | 
|  | 3101   virtual RawAbstractType* CompileType() const; | 
| 3199 | 3102 | 
| 3200   virtual bool CanDeoptimize() const { return true; } | 3103   virtual bool CanDeoptimize() const { return true; } | 
| 3201   virtual intptr_t ResultCid() const { return kIllegalCid; } | 3104   virtual intptr_t ResultCid() const { return kIllegalCid; } | 
| 3202 | 3105 | 
| 3203   virtual bool AttributesEqual(Computation* other) const; | 3106   virtual bool AttributesEqual(Definition* other) const; | 
| 3204 | 3107 | 
| 3205   virtual bool HasSideEffect() const { return false; } | 3108   virtual bool HasSideEffect() const { return false; } | 
| 3206 | 3109 | 
| 3207   Value* value() const { return inputs_[0]; } | 3110   Value* value() const { return inputs_[0]; } | 
| 3208 | 3111 | 
| 3209   const ICData& unary_checks() const { return unary_checks_; } | 3112   const ICData& unary_checks() const { return unary_checks_; } | 
| 3210 | 3113 | 
| 3211   virtual intptr_t deopt_id() const { return instance_call_->deopt_id(); } | 3114   virtual Definition* Canonicalize(); | 
| 3212 |  | 
| 3213   virtual Definition* TryReplace(BindInstr* instr) const; |  | 
| 3214 | 3115 | 
| 3215   virtual void PrintOperandsTo(BufferFormatter* f) const; | 3116   virtual void PrintOperandsTo(BufferFormatter* f) const; | 
| 3216 | 3117 | 
| 3217  private: | 3118  private: | 
| 3218   InstanceCallComp* instance_call_; |  | 
| 3219   const ICData& unary_checks_; | 3119   const ICData& unary_checks_; | 
| 3220 | 3120 | 
| 3221   DISALLOW_COPY_AND_ASSIGN(CheckClassComp); | 3121   DISALLOW_COPY_AND_ASSIGN(CheckClassInstr); | 
| 3222 }; | 3122 }; | 
| 3223 | 3123 | 
| 3224 | 3124 | 
| 3225 class CheckSmiComp : public TemplateComputation<1> { | 3125 class CheckSmiInstr : public TemplateDefinition<1> { | 
| 3226  public: | 3126  public: | 
| 3227   CheckSmiComp(Value* value, intptr_t original_deopt_id) | 3127   CheckSmiInstr(Value* value, intptr_t original_deopt_id) { | 
| 3228       : original_deopt_id_(original_deopt_id) { |  | 
| 3229     ASSERT(value != NULL); | 3128     ASSERT(value != NULL); | 
| 3230     ASSERT(original_deopt_id != Isolate::kNoDeoptId); | 3129     ASSERT(original_deopt_id != Isolate::kNoDeoptId); | 
| 3231     inputs_[0] = value; | 3130     inputs_[0] = value; | 
|  | 3131     deopt_id_ = original_deopt_id; | 
| 3232   } | 3132   } | 
| 3233 | 3133 | 
| 3234   DECLARE_COMPUTATION(CheckSmi) | 3134   DECLARE_INSTRUCTION(CheckSmi) | 
|  | 3135   virtual RawAbstractType* CompileType() const; | 
| 3235 | 3136 | 
| 3236   virtual bool CanDeoptimize() const { return true; } | 3137   virtual bool CanDeoptimize() const { return true; } | 
| 3237   virtual intptr_t ResultCid() const { return kIllegalCid; } | 3138   virtual intptr_t ResultCid() const { return kIllegalCid; } | 
| 3238 | 3139 | 
| 3239   virtual bool AttributesEqual(Computation* other) const { return true; } | 3140   virtual bool AttributesEqual(Definition* other) const { return true; } | 
| 3240 | 3141 | 
| 3241   virtual bool HasSideEffect() const { return false; } | 3142   virtual bool HasSideEffect() const { return false; } | 
| 3242 | 3143 | 
| 3243   virtual Definition* TryReplace(BindInstr* instr) const; | 3144   virtual Definition* Canonicalize(); | 
| 3244 | 3145 | 
| 3245   Value* value() const { return inputs_[0]; } | 3146   Value* value() const { return inputs_[0]; } | 
| 3246 | 3147 | 
| 3247   virtual intptr_t deopt_id() const { return original_deopt_id_; } |  | 
| 3248 |  | 
| 3249  private: | 3148  private: | 
| 3250   const intptr_t original_deopt_id_; | 3149   DISALLOW_COPY_AND_ASSIGN(CheckSmiInstr); | 
| 3251 |  | 
| 3252   DISALLOW_COPY_AND_ASSIGN(CheckSmiComp); |  | 
| 3253 }; | 3150 }; | 
| 3254 | 3151 | 
| 3255 | 3152 | 
| 3256 class CheckArrayBoundComp : public TemplateComputation<2> { | 3153 class CheckArrayBoundInstr : public TemplateDefinition<2> { | 
| 3257  public: | 3154  public: | 
| 3258   CheckArrayBoundComp(Value* array, | 3155   CheckArrayBoundInstr(Value* array, | 
| 3259                       Value* index, | 3156                        Value* index, | 
| 3260                       intptr_t array_type, | 3157                        intptr_t array_type, | 
| 3261                       InstanceCallComp* instance_call) | 3158                        InstanceCallInstr* instance_call) | 
| 3262       : array_type_(array_type), instance_call_(instance_call) { | 3159       : array_type_(array_type) { | 
| 3263     ASSERT(array != NULL); | 3160     ASSERT(array != NULL); | 
| 3264     ASSERT(index != NULL); | 3161     ASSERT(index != NULL); | 
| 3265     inputs_[0] = array; | 3162     inputs_[0] = array; | 
| 3266     inputs_[1] = index; | 3163     inputs_[1] = index; | 
|  | 3164     deopt_id_ = instance_call->deopt_id(); | 
| 3267   } | 3165   } | 
| 3268 | 3166 | 
| 3269   DECLARE_COMPUTATION(CheckArrayBound) | 3167   DECLARE_INSTRUCTION(CheckArrayBound) | 
|  | 3168   virtual RawAbstractType* CompileType() const; | 
| 3270 | 3169 | 
| 3271   virtual bool CanDeoptimize() const { return true; } | 3170   virtual bool CanDeoptimize() const { return true; } | 
| 3272   virtual intptr_t ResultCid() const { return kIllegalCid; } | 3171   virtual intptr_t ResultCid() const { return kIllegalCid; } | 
| 3273 | 3172 | 
| 3274   virtual bool AttributesEqual(Computation* other) const; | 3173   virtual bool AttributesEqual(Definition* other) const; | 
| 3275 | 3174 | 
| 3276   virtual bool HasSideEffect() const { return false; } | 3175   virtual bool HasSideEffect() const { return false; } | 
| 3277 | 3176 | 
| 3278   Value* array() const { return inputs_[0]; } | 3177   Value* array() const { return inputs_[0]; } | 
| 3279   Value* index() const { return inputs_[1]; } | 3178   Value* index() const { return inputs_[1]; } | 
| 3280 | 3179 | 
| 3281   intptr_t array_type() const { return array_type_; } | 3180   intptr_t array_type() const { return array_type_; } | 
| 3282 | 3181 | 
| 3283   virtual intptr_t deopt_id() const { return instance_call_->deopt_id(); } |  | 
| 3284 |  | 
| 3285  private: | 3182  private: | 
| 3286   intptr_t array_type_; | 3183   intptr_t array_type_; | 
| 3287   InstanceCallComp* instance_call_; |  | 
| 3288 | 3184 | 
| 3289   DISALLOW_COPY_AND_ASSIGN(CheckArrayBoundComp); | 3185   DISALLOW_COPY_AND_ASSIGN(CheckArrayBoundInstr); | 
| 3290 }; | 3186 }; | 
| 3291 | 3187 | 
| 3292 | 3188 | 
| 3293 #undef DECLARE_COMPUTATION | 3189 #undef DECLARE_INSTRUCTION | 
| 3294 |  | 
| 3295 |  | 
| 3296 // Implementation of type testers and cast functins. |  | 
| 3297 #define DEFINE_COMPUTATION_PREDICATE(ShortName, ClassName)                     \ |  | 
| 3298 bool Computation::Is##ShortName() const {                                      \ |  | 
| 3299   return computation_kind() == k##ShortName;                                   \ |  | 
| 3300 }                                                                              \ |  | 
| 3301 const ClassName* Computation::As##ShortName() const {                          \ |  | 
| 3302   if (!Is##ShortName()) return NULL;                                           \ |  | 
| 3303   return static_cast<const ClassName*>(this);                                  \ |  | 
| 3304 }                                                                              \ |  | 
| 3305 ClassName* Computation::As##ShortName() {                                      \ |  | 
| 3306   if (!Is##ShortName()) return NULL;                                           \ |  | 
| 3307   return static_cast<ClassName*>(this);                                        \ |  | 
| 3308 } |  | 
| 3309 FOR_EACH_COMPUTATION(DEFINE_COMPUTATION_PREDICATE) |  | 
| 3310 #undef DEFINE_COMPUTATION_PREDICATE |  | 
| 3311 | 3190 | 
| 3312 | 3191 | 
| 3313 class Environment : public ZoneAllocated { | 3192 class Environment : public ZoneAllocated { | 
| 3314  public: | 3193  public: | 
| 3315   // Construct an environment by constructing uses from an array of definitions. | 3194   // Construct an environment by constructing uses from an array of definitions. | 
| 3316   Environment(const GrowableArray<Definition*>& definitions, | 3195   Environment(const GrowableArray<Definition*>& definitions, | 
| 3317               intptr_t fixed_parameter_count); | 3196               intptr_t fixed_parameter_count); | 
| 3318 | 3197 | 
| 3319   void set_locations(Location* locations) { | 3198   void set_locations(Location* locations) { | 
| 3320     ASSERT(locations_ == NULL); | 3199     ASSERT(locations_ == NULL); | 
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 3370   virtual ~FlowGraphVisitor() { } | 3249   virtual ~FlowGraphVisitor() { } | 
| 3371 | 3250 | 
| 3372   ForwardInstructionIterator* current_iterator() const { | 3251   ForwardInstructionIterator* current_iterator() const { | 
| 3373     return current_iterator_; | 3252     return current_iterator_; | 
| 3374   } | 3253   } | 
| 3375 | 3254 | 
| 3376   // Visit each block in the block order, and for each block its | 3255   // Visit each block in the block order, and for each block its | 
| 3377   // instructions in order from the block entry to exit. | 3256   // instructions in order from the block entry to exit. | 
| 3378   virtual void VisitBlocks(); | 3257   virtual void VisitBlocks(); | 
| 3379 | 3258 | 
| 3380   // Visit functions for instruction and computation classes, with empty | 3259   // Visit functions for instruction classes, with an empty default | 
| 3381   // default implementations. | 3260   // implementation. | 
| 3382 #define DECLARE_VISIT_COMPUTATION(ShortName, ClassName)                        \ |  | 
| 3383   virtual void Visit##ShortName(ClassName* comp, BindInstr* instr) { } |  | 
| 3384 |  | 
| 3385 #define DECLARE_VISIT_INSTRUCTION(ShortName)                                   \ | 3261 #define DECLARE_VISIT_INSTRUCTION(ShortName)                                   \ | 
| 3386   virtual void Visit##ShortName(ShortName##Instr* instr) { } | 3262   virtual void Visit##ShortName(ShortName##Instr* instr) { } | 
| 3387 | 3263 | 
| 3388   FOR_EACH_COMPUTATION(DECLARE_VISIT_COMPUTATION) |  | 
| 3389   FOR_EACH_INSTRUCTION(DECLARE_VISIT_INSTRUCTION) | 3264   FOR_EACH_INSTRUCTION(DECLARE_VISIT_INSTRUCTION) | 
| 3390 | 3265 | 
| 3391 #undef DECLARE_VISIT_COMPUTATION |  | 
| 3392 #undef DECLARE_VISIT_INSTRUCTION | 3266 #undef DECLARE_VISIT_INSTRUCTION | 
| 3393 | 3267 | 
| 3394  protected: | 3268  protected: | 
| 3395   const GrowableArray<BlockEntryInstr*>& block_order_; | 3269   const GrowableArray<BlockEntryInstr*>& block_order_; | 
| 3396   ForwardInstructionIterator* current_iterator_; | 3270   ForwardInstructionIterator* current_iterator_; | 
| 3397 | 3271 | 
| 3398  private: | 3272  private: | 
| 3399   DISALLOW_COPY_AND_ASSIGN(FlowGraphVisitor); | 3273   DISALLOW_COPY_AND_ASSIGN(FlowGraphVisitor); | 
| 3400 }; | 3274 }; | 
| 3401 | 3275 | 
| 3402 | 3276 | 
| 3403 }  // namespace dart | 3277 }  // namespace dart | 
| 3404 | 3278 | 
| 3405 #endif  // VM_INTERMEDIATE_LANGUAGE_H_ | 3279 #endif  // VM_INTERMEDIATE_LANGUAGE_H_ | 
| OLD | NEW | 
|---|