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

Side by Side Diff: src/hydrogen-instructions.h

Issue 19562003: Add support for IncrementCounter in Hydrogen. (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: More code style Created 7 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 193 matching lines...) Expand 10 before | Expand all | Expand 10 after
204 V(BackingStoreFields) \ 204 V(BackingStoreFields) \
205 V(Calls) \ 205 V(Calls) \
206 V(ContextSlots) \ 206 V(ContextSlots) \
207 V(DoubleArrayElements) \ 207 V(DoubleArrayElements) \
208 V(DoubleFields) \ 208 V(DoubleFields) \
209 V(ElementsKind) \ 209 V(ElementsKind) \
210 V(ElementsPointer) \ 210 V(ElementsPointer) \
211 V(GlobalVars) \ 211 V(GlobalVars) \
212 V(InobjectFields) \ 212 V(InobjectFields) \
213 V(OsrEntries) \ 213 V(OsrEntries) \
214 V(SpecializedArrayElements) 214 V(ExternalMemory)
215 215
216 216
217 #define DECLARE_ABSTRACT_INSTRUCTION(type) \ 217 #define DECLARE_ABSTRACT_INSTRUCTION(type) \
218 virtual bool Is##type() const { return true; } \ 218 virtual bool Is##type() const { return true; } \
219 static H##type* cast(HValue* value) { \ 219 static H##type* cast(HValue* value) { \
220 ASSERT(value->Is##type()); \ 220 ASSERT(value->Is##type()); \
221 return reinterpret_cast<H##type*>(value); \ 221 return reinterpret_cast<H##type*>(value); \
222 } 222 }
223 223
224 224
(...skipping 120 matching lines...) Expand 10 before | Expand all | Expand 10 after
345 345
346 private: 346 private:
347 Address raw_address_; 347 Address raw_address_;
348 }; 348 };
349 349
350 350
351 class HType { 351 class HType {
352 public: 352 public:
353 HType() : type_(kUninitialized) { } 353 HType() : type_(kUninitialized) { }
354 354
355 static HType None() { return HType(kNone); }
355 static HType Tagged() { return HType(kTagged); } 356 static HType Tagged() { return HType(kTagged); }
356 static HType TaggedPrimitive() { return HType(kTaggedPrimitive); } 357 static HType TaggedPrimitive() { return HType(kTaggedPrimitive); }
357 static HType TaggedNumber() { return HType(kTaggedNumber); } 358 static HType TaggedNumber() { return HType(kTaggedNumber); }
358 static HType Smi() { return HType(kSmi); } 359 static HType Smi() { return HType(kSmi); }
359 static HType HeapNumber() { return HType(kHeapNumber); } 360 static HType HeapNumber() { return HType(kHeapNumber); }
360 static HType String() { return HType(kString); } 361 static HType String() { return HType(kString); }
361 static HType Boolean() { return HType(kBoolean); } 362 static HType Boolean() { return HType(kBoolean); }
362 static HType NonPrimitive() { return HType(kNonPrimitive); } 363 static HType NonPrimitive() { return HType(kNonPrimitive); }
363 static HType JSArray() { return HType(kJSArray); } 364 static HType JSArray() { return HType(kJSArray); }
364 static HType JSObject() { return HType(kJSObject); } 365 static HType JSObject() { return HType(kJSObject); }
(...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after
440 ASSERT(type_ != kUninitialized); 441 ASSERT(type_ != kUninitialized);
441 return IsHeapNumber() || IsString() || IsBoolean() || IsNonPrimitive(); 442 return IsHeapNumber() || IsString() || IsBoolean() || IsNonPrimitive();
442 } 443 }
443 444
444 static HType TypeFromValue(Handle<Object> value); 445 static HType TypeFromValue(Handle<Object> value);
445 446
446 const char* ToString(); 447 const char* ToString();
447 448
448 private: 449 private:
449 enum Type { 450 enum Type {
451 kNone = 0x0, // 0000 0000 0000 0000
450 kTagged = 0x1, // 0000 0000 0000 0001 452 kTagged = 0x1, // 0000 0000 0000 0001
451 kTaggedPrimitive = 0x5, // 0000 0000 0000 0101 453 kTaggedPrimitive = 0x5, // 0000 0000 0000 0101
452 kTaggedNumber = 0xd, // 0000 0000 0000 1101 454 kTaggedNumber = 0xd, // 0000 0000 0000 1101
453 kSmi = 0x1d, // 0000 0000 0001 1101 455 kSmi = 0x1d, // 0000 0000 0001 1101
454 kHeapNumber = 0x2d, // 0000 0000 0010 1101 456 kHeapNumber = 0x2d, // 0000 0000 0010 1101
455 kString = 0x45, // 0000 0000 0100 0101 457 kString = 0x45, // 0000 0000 0100 0101
456 kBoolean = 0x85, // 0000 0000 1000 0101 458 kBoolean = 0x85, // 0000 0000 1000 0101
457 kNonPrimitive = 0x101, // 0000 0001 0000 0001 459 kNonPrimitive = 0x101, // 0000 0001 0000 0001
458 kJSObject = 0x301, // 0000 0011 0000 0001 460 kJSObject = 0x301, // 0000 0011 0000 0001
459 kJSArray = 0x701, // 0000 0111 0000 0001 461 kJSArray = 0x701, // 0000 0111 0000 0001
(...skipping 2215 matching lines...) Expand 10 before | Expand all | Expand 10 after
2675 // change. The external array of a specialized array elements object cannot 2677 // change. The external array of a specialized array elements object cannot
2676 // change once set, so it's no necessary to introduce any additional 2678 // change once set, so it's no necessary to introduce any additional
2677 // dependencies on top of the inputs. 2679 // dependencies on top of the inputs.
2678 SetFlag(kUseGVN); 2680 SetFlag(kUseGVN);
2679 } 2681 }
2680 2682
2681 virtual Representation RequiredInputRepresentation(int index) { 2683 virtual Representation RequiredInputRepresentation(int index) {
2682 return Representation::Tagged(); 2684 return Representation::Tagged();
2683 } 2685 }
2684 2686
2687 virtual HType CalculateInferredType() {
2688 return HType::None();
2689 }
2690
2685 DECLARE_CONCRETE_INSTRUCTION(LoadExternalArrayPointer) 2691 DECLARE_CONCRETE_INSTRUCTION(LoadExternalArrayPointer)
2686 2692
2687 protected: 2693 protected:
2688 virtual bool DataEquals(HValue* other) { return true; } 2694 virtual bool DataEquals(HValue* other) { return true; }
2689 2695
2690 private: 2696 private:
2691 virtual bool IsDeletable() const { return true; } 2697 virtual bool IsDeletable() const { return true; }
2692 }; 2698 };
2693 2699
2694 2700
(...skipping 769 matching lines...) Expand 10 before | Expand all | Expand 10 after
3464 bool is_not_in_new_space = true, 3470 bool is_not_in_new_space = true,
3465 Handle<Object> optional_handle = Handle<Object>::null()); 3471 Handle<Object> optional_handle = Handle<Object>::null());
3466 HConstant(Handle<Object> handle, 3472 HConstant(Handle<Object> handle,
3467 UniqueValueId unique_id, 3473 UniqueValueId unique_id,
3468 Representation r, 3474 Representation r,
3469 HType type, 3475 HType type,
3470 bool is_internalized_string, 3476 bool is_internalized_string,
3471 bool is_not_in_new_space, 3477 bool is_not_in_new_space,
3472 bool is_cell, 3478 bool is_cell,
3473 bool boolean_value); 3479 bool boolean_value);
3480 explicit HConstant(ExternalReference reference);
3474 3481
3475 Handle<Object> handle() { 3482 Handle<Object> handle() {
3476 if (handle_.is_null()) { 3483 if (handle_.is_null()) {
3477 Factory* factory = Isolate::Current()->factory(); 3484 Factory* factory = Isolate::Current()->factory();
3478 // Default arguments to is_not_in_new_space depend on this heap number 3485 // Default arguments to is_not_in_new_space depend on this heap number
3479 // to be tenured so that it's guaranteed not be be located in new space. 3486 // to be tenured so that it's guaranteed not be be located in new space.
3480 handle_ = factory->NewNumber(double_value_, TENURED); 3487 handle_ = factory->NewNumber(double_value_, TENURED);
3481 } 3488 }
3482 AllowDeferredHandleDereference smi_check; 3489 AllowDeferredHandleDereference smi_check;
3483 ASSERT(has_int32_value_ || !handle_->IsSmi()); 3490 ASSERT(has_int32_value_ || !handle_->IsSmi());
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
3528 } 3535 }
3529 3536
3530 virtual Representation RequiredInputRepresentation(int index) { 3537 virtual Representation RequiredInputRepresentation(int index) {
3531 return Representation::None(); 3538 return Representation::None();
3532 } 3539 }
3533 3540
3534 virtual Representation KnownOptimalRepresentation() { 3541 virtual Representation KnownOptimalRepresentation() {
3535 if (HasSmiValue() && kSmiValueSize == 31) return Representation::Smi(); 3542 if (HasSmiValue() && kSmiValueSize == 31) return Representation::Smi();
3536 if (HasInteger32Value()) return Representation::Integer32(); 3543 if (HasInteger32Value()) return Representation::Integer32();
3537 if (HasNumberValue()) return Representation::Double(); 3544 if (HasNumberValue()) return Representation::Double();
3545 if (HasExternalReferenceValue()) return Representation::External();
3538 return Representation::Tagged(); 3546 return Representation::Tagged();
3539 } 3547 }
3540 3548
3541 virtual bool EmitAtUses(); 3549 virtual bool EmitAtUses();
3542 virtual void PrintDataTo(StringStream* stream); 3550 virtual void PrintDataTo(StringStream* stream);
3543 virtual HType CalculateInferredType(); 3551 virtual HType CalculateInferredType();
3544 bool IsInteger() { return handle()->IsSmi(); } 3552 bool IsInteger() { return handle()->IsSmi(); }
3545 HConstant* CopyToRepresentation(Representation r, Zone* zone) const; 3553 HConstant* CopyToRepresentation(Representation r, Zone* zone) const;
3546 Maybe<HConstant*> CopyToTruncatedInt32(Zone* zone); 3554 Maybe<HConstant*> CopyToTruncatedInt32(Zone* zone);
3547 Maybe<HConstant*> CopyToTruncatedNumber(Zone* zone); 3555 Maybe<HConstant*> CopyToTruncatedNumber(Zone* zone);
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
3580 return type_from_value_.IsString(); 3588 return type_from_value_.IsString();
3581 } 3589 }
3582 Handle<String> StringValue() const { 3590 Handle<String> StringValue() const {
3583 ASSERT(HasStringValue()); 3591 ASSERT(HasStringValue());
3584 return Handle<String>::cast(handle_); 3592 return Handle<String>::cast(handle_);
3585 } 3593 }
3586 bool HasInternalizedStringValue() const { 3594 bool HasInternalizedStringValue() const {
3587 return HasStringValue() && is_internalized_string_; 3595 return HasStringValue() && is_internalized_string_;
3588 } 3596 }
3589 3597
3598 bool HasExternalReferenceValue() const {
3599 return has_external_reference_value_;
3600 }
3601 ExternalReference ExternalReferenceValue() const {
3602 return external_reference_value_;
3603 }
3604
3590 bool BooleanValue() const { return boolean_value_; } 3605 bool BooleanValue() const { return boolean_value_; }
3591 3606
3592 virtual intptr_t Hashcode() { 3607 virtual intptr_t Hashcode() {
3593 if (has_int32_value_) { 3608 if (has_int32_value_) {
3594 return static_cast<intptr_t>(int32_value_); 3609 return static_cast<intptr_t>(int32_value_);
3595 } else if (has_double_value_) { 3610 } else if (has_double_value_) {
3596 return static_cast<intptr_t>(BitCast<int64_t>(double_value_)); 3611 return static_cast<intptr_t>(BitCast<int64_t>(double_value_));
3612 } else if (has_external_reference_value_) {
3613 return reinterpret_cast<intptr_t>(external_reference_value_.address());
3597 } else { 3614 } else {
3598 ASSERT(!handle_.is_null()); 3615 ASSERT(!handle_.is_null());
3599 return unique_id_.Hashcode(); 3616 return unique_id_.Hashcode();
3600 } 3617 }
3601 } 3618 }
3602 3619
3603 virtual void FinalizeUniqueValueId() { 3620 virtual void FinalizeUniqueValueId() {
3604 if (!has_double_value_) { 3621 if (!has_double_value_ && !has_external_reference_value_) {
3605 ASSERT(!handle_.is_null()); 3622 ASSERT(!handle_.is_null());
3606 unique_id_ = UniqueValueId(handle_); 3623 unique_id_ = UniqueValueId(handle_);
3607 } 3624 }
3608 } 3625 }
3609 3626
3610 bool UniqueValueIdsMatch(UniqueValueId other) { 3627 bool UniqueValueIdsMatch(UniqueValueId other) {
3611 return !has_double_value_ && unique_id_ == other; 3628 return !has_double_value_ && !has_external_reference_value_ &&
3629 unique_id_ == other;
3612 } 3630 }
3613 3631
3614 #ifdef DEBUG 3632 #ifdef DEBUG
3615 virtual void Verify() { } 3633 virtual void Verify() { }
3616 #endif 3634 #endif
3617 3635
3618 DECLARE_CONCRETE_INSTRUCTION(Constant) 3636 DECLARE_CONCRETE_INSTRUCTION(Constant)
3619 3637
3620 protected: 3638 protected:
3621 virtual Range* InferRange(Zone* zone); 3639 virtual Range* InferRange(Zone* zone);
3622 3640
3623 virtual bool DataEquals(HValue* other) { 3641 virtual bool DataEquals(HValue* other) {
3624 HConstant* other_constant = HConstant::cast(other); 3642 HConstant* other_constant = HConstant::cast(other);
3625 if (has_int32_value_) { 3643 if (has_int32_value_) {
3626 return other_constant->has_int32_value_ && 3644 return other_constant->has_int32_value_ &&
3627 int32_value_ == other_constant->int32_value_; 3645 int32_value_ == other_constant->int32_value_;
3628 } else if (has_double_value_) { 3646 } else if (has_double_value_) {
3629 return other_constant->has_double_value_ && 3647 return other_constant->has_double_value_ &&
3630 BitCast<int64_t>(double_value_) == 3648 BitCast<int64_t>(double_value_) ==
3631 BitCast<int64_t>(other_constant->double_value_); 3649 BitCast<int64_t>(other_constant->double_value_);
3650 } else if (has_external_reference_value_) {
3651 return other_constant->has_external_reference_value_ &&
3652 external_reference_value_ ==
3653 other_constant->external_reference_value_;
3632 } else { 3654 } else {
3633 ASSERT(!handle_.is_null()); 3655 ASSERT(!handle_.is_null());
3634 return !other_constant->handle_.is_null() && 3656 return !other_constant->handle_.is_null() &&
3635 unique_id_ == other_constant->unique_id_; 3657 unique_id_ == other_constant->unique_id_;
3636 } 3658 }
3637 } 3659 }
3638 3660
3639 private: 3661 private:
3640 void Initialize(Representation r); 3662 void Initialize(Representation r);
3641 3663
3642 virtual bool IsDeletable() const { return true; } 3664 virtual bool IsDeletable() const { return true; }
3643 3665
3644 // If this is a numerical constant, handle_ either points to to the 3666 // If this is a numerical constant, handle_ either points to to the
3645 // HeapObject the constant originated from or is null. If the 3667 // HeapObject the constant originated from or is null. If the
3646 // constant is non-numeric, handle_ always points to a valid 3668 // constant is non-numeric, handle_ always points to a valid
3647 // constant HeapObject. 3669 // constant HeapObject.
3648 Handle<Object> handle_; 3670 Handle<Object> handle_;
3649 UniqueValueId unique_id_; 3671 UniqueValueId unique_id_;
3650 3672
3651 // We store the HConstant in the most specific form safely possible. 3673 // We store the HConstant in the most specific form safely possible.
3652 // The two flags, has_int32_value_ and has_double_value_ tell us if 3674 // The two flags, has_int32_value_ and has_double_value_ tell us if
3653 // int32_value_ and double_value_ hold valid, safe representations 3675 // int32_value_ and double_value_ hold valid, safe representations
3654 // of the constant. has_int32_value_ implies has_double_value_ but 3676 // of the constant. has_int32_value_ implies has_double_value_ but
3655 // not the converse. 3677 // not the converse.
3656 bool has_smi_value_ : 1; 3678 bool has_smi_value_ : 1;
3657 bool has_int32_value_ : 1; 3679 bool has_int32_value_ : 1;
3658 bool has_double_value_ : 1; 3680 bool has_double_value_ : 1;
3681 bool has_external_reference_value_ : 1;
3659 bool is_internalized_string_ : 1; // TODO(yangguo): make this part of HType. 3682 bool is_internalized_string_ : 1; // TODO(yangguo): make this part of HType.
3660 bool is_not_in_new_space_ : 1; 3683 bool is_not_in_new_space_ : 1;
3661 bool is_cell_ : 1; 3684 bool is_cell_ : 1;
3662 bool boolean_value_ : 1; 3685 bool boolean_value_ : 1;
3663 int32_t int32_value_; 3686 int32_t int32_value_;
3664 double double_value_; 3687 double double_value_;
3688 ExternalReference external_reference_value_;
3665 HType type_from_value_; 3689 HType type_from_value_;
3666 }; 3690 };
3667 3691
3668 3692
3669 class HBinaryOperation: public HTemplateInstruction<3> { 3693 class HBinaryOperation: public HTemplateInstruction<3> {
3670 public: 3694 public:
3671 HBinaryOperation(HValue* context, HValue* left, HValue* right) 3695 HBinaryOperation(HValue* context, HValue* left, HValue* right)
3672 : observed_output_representation_(Representation::None()) { 3696 : observed_output_representation_(Representation::None()) {
3673 ASSERT(left != NULL && right != NULL); 3697 ASSERT(left != NULL && right != NULL);
3674 SetOperandAt(0, context); 3698 SetOperandAt(0, context);
(...skipping 1871 matching lines...) Expand 10 before | Expand all | Expand 10 after
5546 int slot_index_; 5570 int slot_index_;
5547 Mode mode_; 5571 Mode mode_;
5548 }; 5572 };
5549 5573
5550 5574
5551 // Represents an access to a portion of an object, such as the map pointer, 5575 // Represents an access to a portion of an object, such as the map pointer,
5552 // array elements pointer, etc, but not accesses to array elements themselves. 5576 // array elements pointer, etc, but not accesses to array elements themselves.
5553 class HObjectAccess { 5577 class HObjectAccess {
5554 public: 5578 public:
5555 inline bool IsInobject() const { 5579 inline bool IsInobject() const {
5556 return portion() != kBackingStore; 5580 return portion() != kBackingStore && portion() != kExternalMemory;
5581 }
5582
5583 inline bool IsExternalMemory() const {
5584 return portion() == kExternalMemory;
5557 } 5585 }
5558 5586
5559 inline int offset() const { 5587 inline int offset() const {
5560 return OffsetField::decode(value_); 5588 return OffsetField::decode(value_);
5561 } 5589 }
5562 5590
5563 inline Representation representation() const { 5591 inline Representation representation() const {
5564 return Representation::FromKind(RepresentationField::decode(value_)); 5592 return Representation::FromKind(RepresentationField::decode(value_));
5565 } 5593 }
5566 5594
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after
5620 } 5648 }
5621 5649
5622 static HObjectAccess ForCellValue() { 5650 static HObjectAccess ForCellValue() {
5623 return HObjectAccess(kInobject, Cell::kValueOffset); 5651 return HObjectAccess(kInobject, Cell::kValueOffset);
5624 } 5652 }
5625 5653
5626 static HObjectAccess ForAllocationMementoSite() { 5654 static HObjectAccess ForAllocationMementoSite() {
5627 return HObjectAccess(kInobject, AllocationMemento::kAllocationSiteOffset); 5655 return HObjectAccess(kInobject, AllocationMemento::kAllocationSiteOffset);
5628 } 5656 }
5629 5657
5658 static HObjectAccess ForCounter() {
5659 return HObjectAccess(kExternalMemory, 0, Representation::Integer32());
5660 }
5661
5630 // Create an access to an offset in a fixed array header. 5662 // Create an access to an offset in a fixed array header.
5631 static HObjectAccess ForFixedArrayHeader(int offset); 5663 static HObjectAccess ForFixedArrayHeader(int offset);
5632 5664
5633 // Create an access to an in-object property in a JSObject. 5665 // Create an access to an in-object property in a JSObject.
5634 static HObjectAccess ForJSObjectOffset(int offset, 5666 static HObjectAccess ForJSObjectOffset(int offset,
5635 Representation representation = Representation::Tagged()); 5667 Representation representation = Representation::Tagged());
5636 5668
5637 // Create an access to an in-object property in a JSArray. 5669 // Create an access to an in-object property in a JSArray.
5638 static HObjectAccess ForJSArrayOffset(int offset); 5670 static HObjectAccess ForJSArrayOffset(int offset);
5639 5671
(...skipping 18 matching lines...) Expand all
5658 void SetGVNFlags(HValue *instr, bool is_store); 5690 void SetGVNFlags(HValue *instr, bool is_store);
5659 5691
5660 private: 5692 private:
5661 // internal use only; different parts of an object or array 5693 // internal use only; different parts of an object or array
5662 enum Portion { 5694 enum Portion {
5663 kMaps, // map of an object 5695 kMaps, // map of an object
5664 kArrayLengths, // the length of an array 5696 kArrayLengths, // the length of an array
5665 kElementsPointer, // elements pointer 5697 kElementsPointer, // elements pointer
5666 kBackingStore, // some field in the backing store 5698 kBackingStore, // some field in the backing store
5667 kDouble, // some double field 5699 kDouble, // some double field
5668 kInobject // some other in-object field 5700 kInobject, // some other in-object field
5701 kExternalMemory // some field in external memory
5669 }; 5702 };
5670 5703
5671 HObjectAccess(Portion portion, int offset, 5704 HObjectAccess(Portion portion, int offset,
5672 Representation representation = Representation::Tagged(), 5705 Representation representation = Representation::Tagged(),
5673 Handle<String> name = Handle<String>::null()) 5706 Handle<String> name = Handle<String>::null())
5674 : value_(PortionField::encode(portion) | 5707 : value_(PortionField::encode(portion) |
5675 RepresentationField::encode(representation.kind()) | 5708 RepresentationField::encode(representation.kind()) |
5676 OffsetField::encode(offset)), 5709 OffsetField::encode(offset)),
5677 name_(name) { 5710 name_(name) {
5678 // assert that the fields decode correctly 5711 // assert that the fields decode correctly
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
5736 HValue* typecheck = NULL) 5769 HValue* typecheck = NULL)
5737 : access_(access) { 5770 : access_(access) {
5738 ASSERT(object != NULL); 5771 ASSERT(object != NULL);
5739 SetOperandAt(0, object); 5772 SetOperandAt(0, object);
5740 SetOperandAt(1, typecheck != NULL ? typecheck : object); 5773 SetOperandAt(1, typecheck != NULL ? typecheck : object);
5741 5774
5742 Representation representation = access.representation(); 5775 Representation representation = access.representation();
5743 if (representation.IsSmi()) { 5776 if (representation.IsSmi()) {
5744 set_type(HType::Smi()); 5777 set_type(HType::Smi());
5745 set_representation(representation); 5778 set_representation(representation);
5746 } else if (representation.IsDouble()) { 5779 } else if (representation.IsDouble() ||
5780 representation.IsExternal() ||
5781 representation.IsInteger32()) {
5747 set_representation(representation); 5782 set_representation(representation);
5748 } else if (FLAG_track_heap_object_fields && 5783 } else if (FLAG_track_heap_object_fields &&
5749 representation.IsHeapObject()) { 5784 representation.IsHeapObject()) {
5750 set_type(HType::NonPrimitive()); 5785 set_type(HType::NonPrimitive());
5751 set_representation(Representation::Tagged()); 5786 set_representation(Representation::Tagged());
5752 } else { 5787 } else {
5753 set_representation(Representation::Tagged()); 5788 set_representation(Representation::Tagged());
5754 } 5789 }
5755 access.SetGVNFlags(this, false); 5790 access.SetGVNFlags(this, false);
5756 } 5791 }
5757 5792
5758 HValue* object() { return OperandAt(0); } 5793 HValue* object() { return OperandAt(0); }
5759 HValue* typecheck() { 5794 HValue* typecheck() {
5760 ASSERT(HasTypeCheck()); 5795 ASSERT(HasTypeCheck());
5761 return OperandAt(1); 5796 return OperandAt(1);
5762 } 5797 }
5763 5798
5764 bool HasTypeCheck() const { return OperandAt(0) != OperandAt(1); } 5799 bool HasTypeCheck() const { return OperandAt(0) != OperandAt(1); }
5765 HObjectAccess access() const { return access_; } 5800 HObjectAccess access() const { return access_; }
5766 Representation field_representation() const { 5801 Representation field_representation() const {
5767 return access_.representation(); 5802 return access_.representation();
5768 } 5803 }
5769 5804
5770 virtual bool HasEscapingOperandAt(int index) { return false; } 5805 virtual bool HasEscapingOperandAt(int index) { return false; }
5771 virtual Representation RequiredInputRepresentation(int index) { 5806 virtual Representation RequiredInputRepresentation(int index) {
5807 if (index == 0 && access().IsExternalMemory()) {
5808 // object must be external in case of external memory access
5809 return Representation::External();
5810 }
5772 return Representation::Tagged(); 5811 return Representation::Tagged();
5773 } 5812 }
5774 virtual void PrintDataTo(StringStream* stream); 5813 virtual void PrintDataTo(StringStream* stream);
5775 5814
5776 DECLARE_CONCRETE_INSTRUCTION(LoadNamedField) 5815 DECLARE_CONCRETE_INSTRUCTION(LoadNamedField)
5777 5816
5778 protected: 5817 protected:
5779 virtual bool DataEquals(HValue* other) { 5818 virtual bool DataEquals(HValue* other) {
5780 HLoadNamedField* b = HLoadNamedField::cast(other); 5819 HLoadNamedField* b = HLoadNamedField::cast(other);
5781 return access_.Equals(b->access_); 5820 return access_.Equals(b->access_);
(...skipping 153 matching lines...) Expand 10 before | Expand all | Expand 10 after
5935 SetGVNFlag(kDependsOnDoubleArrayElements); 5974 SetGVNFlag(kDependsOnDoubleArrayElements);
5936 } 5975 }
5937 } else { 5976 } else {
5938 if (elements_kind == EXTERNAL_FLOAT_ELEMENTS || 5977 if (elements_kind == EXTERNAL_FLOAT_ELEMENTS ||
5939 elements_kind == EXTERNAL_DOUBLE_ELEMENTS) { 5978 elements_kind == EXTERNAL_DOUBLE_ELEMENTS) {
5940 set_representation(Representation::Double()); 5979 set_representation(Representation::Double());
5941 } else { 5980 } else {
5942 set_representation(Representation::Integer32()); 5981 set_representation(Representation::Integer32());
5943 } 5982 }
5944 5983
5945 SetGVNFlag(kDependsOnSpecializedArrayElements); 5984 SetGVNFlag(kDependsOnExternalMemory);
5946 // Native code could change the specialized array. 5985 // Native code could change the specialized array.
5947 SetGVNFlag(kDependsOnCalls); 5986 SetGVNFlag(kDependsOnCalls);
5948 } 5987 }
5949 5988
5950 SetFlag(kUseGVN); 5989 SetFlag(kUseGVN);
5951 } 5990 }
5952 5991
5953 bool is_external() const { 5992 bool is_external() const {
5954 return IsExternalArrayElementsKind(elements_kind()); 5993 return IsExternalArrayElementsKind(elements_kind());
5955 } 5994 }
(...skipping 136 matching lines...) Expand 10 before | Expand all | Expand 10 after
6092 write_barrier_mode_(UPDATE_WRITE_BARRIER) { 6131 write_barrier_mode_(UPDATE_WRITE_BARRIER) {
6093 SetOperandAt(0, obj); 6132 SetOperandAt(0, obj);
6094 SetOperandAt(1, val); 6133 SetOperandAt(1, val);
6095 access.SetGVNFlags(this, true); 6134 access.SetGVNFlags(this, true);
6096 } 6135 }
6097 6136
6098 DECLARE_CONCRETE_INSTRUCTION(StoreNamedField) 6137 DECLARE_CONCRETE_INSTRUCTION(StoreNamedField)
6099 6138
6100 virtual bool HasEscapingOperandAt(int index) { return index == 1; } 6139 virtual bool HasEscapingOperandAt(int index) { return index == 1; }
6101 virtual Representation RequiredInputRepresentation(int index) { 6140 virtual Representation RequiredInputRepresentation(int index) {
6102 if (index == 1 && field_representation().IsDouble()) { 6141 if (index == 0 && access().IsExternalMemory()) {
6103 return field_representation(); 6142 // object must be external in case of external memory access
6104 } else if (index == 1 && field_representation().IsSmi()) { 6143 return Representation::External();
6144 } else if (index == 1 &&
6145 (field_representation().IsDouble() ||
6146 field_representation().IsSmi() ||
6147 field_representation().IsInteger32())) {
6105 return field_representation(); 6148 return field_representation();
6106 } 6149 }
6107 return Representation::Tagged(); 6150 return Representation::Tagged();
6108 } 6151 }
6109 virtual void HandleSideEffectDominator(GVNFlag side_effect, 6152 virtual void HandleSideEffectDominator(GVNFlag side_effect,
6110 HValue* dominator) { 6153 HValue* dominator) {
6111 ASSERT(side_effect == kChangesNewSpacePromotion); 6154 ASSERT(side_effect == kChangesNewSpacePromotion);
6112 new_space_dominator_ = dominator; 6155 new_space_dominator_ = dominator;
6113 } 6156 }
6114 virtual void PrintDataTo(StringStream* stream); 6157 virtual void PrintDataTo(StringStream* stream);
(...skipping 17 matching lines...) Expand all
6132 transition_ = map; 6175 transition_ = map;
6133 } 6176 }
6134 HValue* new_space_dominator() const { return new_space_dominator_; } 6177 HValue* new_space_dominator() const { return new_space_dominator_; }
6135 6178
6136 bool NeedsWriteBarrier() { 6179 bool NeedsWriteBarrier() {
6137 ASSERT(!(FLAG_track_double_fields && field_representation().IsDouble()) || 6180 ASSERT(!(FLAG_track_double_fields && field_representation().IsDouble()) ||
6138 transition_.is_null()); 6181 transition_.is_null());
6139 if (IsSkipWriteBarrier()) return false; 6182 if (IsSkipWriteBarrier()) return false;
6140 if (field_representation().IsDouble()) return false; 6183 if (field_representation().IsDouble()) return false;
6141 if (field_representation().IsSmi()) return false; 6184 if (field_representation().IsSmi()) return false;
6185 if (field_representation().IsInteger32()) return false;
6142 return StoringValueNeedsWriteBarrier(value()) && 6186 return StoringValueNeedsWriteBarrier(value()) &&
6143 ReceiverObjectNeedsWriteBarrier(object(), new_space_dominator()); 6187 ReceiverObjectNeedsWriteBarrier(object(), new_space_dominator());
6144 } 6188 }
6145 6189
6146 bool NeedsWriteBarrierForMap() { 6190 bool NeedsWriteBarrierForMap() {
6147 if (IsSkipWriteBarrier()) return false; 6191 if (IsSkipWriteBarrier()) return false;
6148 return ReceiverObjectNeedsWriteBarrier(object(), new_space_dominator()); 6192 return ReceiverObjectNeedsWriteBarrier(object(), new_space_dominator());
6149 } 6193 }
6150 6194
6151 virtual void FinalizeUniqueValueId() { 6195 virtual void FinalizeUniqueValueId() {
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after
6212 new_space_dominator_(NULL) { 6256 new_space_dominator_(NULL) {
6213 SetOperandAt(0, obj); 6257 SetOperandAt(0, obj);
6214 SetOperandAt(1, key); 6258 SetOperandAt(1, key);
6215 SetOperandAt(2, val); 6259 SetOperandAt(2, val);
6216 6260
6217 if (IsFastObjectElementsKind(elements_kind)) { 6261 if (IsFastObjectElementsKind(elements_kind)) {
6218 SetFlag(kTrackSideEffectDominators); 6262 SetFlag(kTrackSideEffectDominators);
6219 SetGVNFlag(kDependsOnNewSpacePromotion); 6263 SetGVNFlag(kDependsOnNewSpacePromotion);
6220 } 6264 }
6221 if (is_external()) { 6265 if (is_external()) {
6222 SetGVNFlag(kChangesSpecializedArrayElements); 6266 SetGVNFlag(kChangesExternalMemory);
6223 SetFlag(kAllowUndefinedAsNaN); 6267 SetFlag(kAllowUndefinedAsNaN);
6224 } else if (IsFastDoubleElementsKind(elements_kind)) { 6268 } else if (IsFastDoubleElementsKind(elements_kind)) {
6225 SetGVNFlag(kChangesDoubleArrayElements); 6269 SetGVNFlag(kChangesDoubleArrayElements);
6226 } else if (IsFastSmiElementsKind(elements_kind)) { 6270 } else if (IsFastSmiElementsKind(elements_kind)) {
6227 SetGVNFlag(kChangesArrayElements); 6271 SetGVNFlag(kChangesArrayElements);
6228 } else { 6272 } else {
6229 SetGVNFlag(kChangesArrayElements); 6273 SetGVNFlag(kChangesArrayElements);
6230 } 6274 }
6231 6275
6232 // EXTERNAL_{UNSIGNED_,}{BYTE,SHORT,INT}_ELEMENTS are truncating. 6276 // EXTERNAL_{UNSIGNED_,}{BYTE,SHORT,INT}_ELEMENTS are truncating.
(...skipping 714 matching lines...) Expand 10 before | Expand all | Expand 10 after
6947 virtual bool IsDeletable() const { return true; } 6991 virtual bool IsDeletable() const { return true; }
6948 }; 6992 };
6949 6993
6950 6994
6951 #undef DECLARE_INSTRUCTION 6995 #undef DECLARE_INSTRUCTION
6952 #undef DECLARE_CONCRETE_INSTRUCTION 6996 #undef DECLARE_CONCRETE_INSTRUCTION
6953 6997
6954 } } // namespace v8::internal 6998 } } // namespace v8::internal
6955 6999
6956 #endif // V8_HYDROGEN_INSTRUCTIONS_H_ 7000 #endif // V8_HYDROGEN_INSTRUCTIONS_H_
OLDNEW
« no previous file with comments | « src/hydrogen.cc ('k') | src/hydrogen-instructions.cc » ('j') | src/ia32/lithium-codegen-ia32.cc » ('J')

Powered by Google App Engine
This is Rietveld 408576698