From 9e204dd5df1cc6d7e748f69528d91ac26d6a6c67 Mon Sep 17 00:00:00 2001 From: "vitalyr@chromium.org" Date: Thu, 13 Jan 2011 00:34:08 +0000 Subject: [PATCH] Simplify CheckPrototypeMaps. This instruction only depends on the prototype and the holder and can completely ignore the receiver and its map. This change also fixes a small bug on arm where a cell was loaded instead of the prototype from new space. Review URL: http://codereview.chromium.org/6094020 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@6290 ce2b1a6d-e550-0410-aec6-3dcde31c8c00 --- src/arm/lithium-arm.h | 5 +++-- src/arm/lithium-codegen-arm.cc | 4 ++-- src/hydrogen-instructions.h | 32 +++++++++++++++----------------- src/hydrogen.cc | 6 +++--- src/ia32/lithium-codegen-ia32.cc | 3 +-- src/ia32/lithium-ia32.h | 4 ++-- 6 files changed, 26 insertions(+), 28 deletions(-) diff --git a/src/arm/lithium-arm.h b/src/arm/lithium-arm.h index 782c2ef..c94c288 100644 --- a/src/arm/lithium-arm.h +++ b/src/arm/lithium-arm.h @@ -76,6 +76,7 @@ class LCodeGen; // LCallNamed // LCallRuntime // LCallStub +// LCheckPrototypeMaps // LConstant // LConstantD // LConstantI @@ -109,7 +110,6 @@ class LCodeGen; // LCheckFunction // LCheckInstanceType // LCheckMap -// LCheckPrototypeMaps // LCheckSmi // LClassOfTest // LClassOfTestAndBranch @@ -1596,8 +1596,9 @@ class LCheckPrototypeMaps: public LInstruction { DECLARE_CONCRETE_INSTRUCTION(CheckPrototypeMaps, "check-prototype-maps") DECLARE_HYDROGEN_ACCESSOR(CheckPrototypeMaps) + Handle prototype() const { return hydrogen()->prototype(); } Handle holder() const { return hydrogen()->holder(); } - Handle receiver_map() const { return hydrogen()->receiver_map(); } + LOperand* temp1() const { return temp1_; } LOperand* temp2() const { return temp2_; } diff --git a/src/arm/lithium-codegen-arm.cc b/src/arm/lithium-codegen-arm.cc index 0e4497f..b5e4284 100644 --- a/src/arm/lithium-codegen-arm.cc +++ b/src/arm/lithium-codegen-arm.cc @@ -2510,6 +2510,7 @@ void LCodeGen::LoadPrototype(Register result, Handle cell = Factory::NewJSGlobalPropertyCell(prototype); __ mov(result, Operand(cell)); + __ ldr(result, FieldMemOperand(result, JSGlobalPropertyCell::kValueOffset)); } else { __ mov(result, Operand(prototype)); } @@ -2521,8 +2522,7 @@ void LCodeGen::DoCheckPrototypeMaps(LCheckPrototypeMaps* instr) { Register temp2 = ToRegister(instr->temp2()); Handle holder = instr->holder(); - Handle receiver_map = instr->receiver_map(); - Handle current_prototype(JSObject::cast(receiver_map->prototype())); + Handle current_prototype = instr->prototype(); // Load prototype object. LoadPrototype(temp1, current_prototype); diff --git a/src/hydrogen-instructions.h b/src/hydrogen-instructions.h index f7eb173..5cc8432 100644 --- a/src/hydrogen-instructions.h +++ b/src/hydrogen-instructions.h @@ -92,6 +92,7 @@ class LChunkBuilder; // HCallNew // HCallRuntime // HCallStub +// HCheckPrototypeMaps // HConstant // HControlInstruction // HDeoptimize @@ -125,7 +126,6 @@ class LChunkBuilder; // HCheckInstanceType // HCheckMap // HCheckNonSmi -// HCheckPrototypeMaps // HCheckSmi // HDeleteProperty // HFixedArrayLength @@ -1622,42 +1622,40 @@ class HCheckNonSmi: public HUnaryOperation { }; -class HCheckPrototypeMaps: public HUnaryOperation { +class HCheckPrototypeMaps: public HInstruction { public: - HCheckPrototypeMaps(HValue* value, - Handle holder, - Handle receiver_map) - : HUnaryOperation(value), - holder_(holder), - receiver_map_(receiver_map) { - set_representation(Representation::Tagged()); + HCheckPrototypeMaps(Handle prototype, Handle holder) + : prototype_(prototype), holder_(holder) { SetFlag(kUseGVN); SetFlag(kDependsOnMaps); } - virtual Representation RequiredInputRepresentation(int index) const { - return Representation::Tagged(); - } - #ifdef DEBUG virtual void Verify() const; #endif + Handle prototype() const { return prototype_; } Handle holder() const { return holder_; } - Handle receiver_map() const { return receiver_map_; } DECLARE_CONCRETE_INSTRUCTION(CheckPrototypeMaps, "check_prototype_maps") + virtual intptr_t Hashcode() const { + ASSERT(!Heap::IsAllocationAllowed()); + intptr_t hash = reinterpret_cast(*prototype()); + hash = 17 * hash + reinterpret_cast(*holder()); + return hash; + } + protected: virtual bool DataEquals(HValue* other) const { HCheckPrototypeMaps* b = HCheckPrototypeMaps::cast(other); - return holder_.is_identical_to(b->holder()) && - receiver_map_.is_identical_to(b->receiver_map()); + return prototype_.is_identical_to(b->prototype()) && + holder_.is_identical_to(b->holder()); } private: + Handle prototype_; Handle holder_; - Handle receiver_map_; }; diff --git a/src/hydrogen.cc b/src/hydrogen.cc index 5da3da5..94137b6 100644 --- a/src/hydrogen.cc +++ b/src/hydrogen.cc @@ -3795,9 +3795,9 @@ void HGraphBuilder::AddCheckConstantFunction(Call* expr, AddInstruction(new HCheckMap(receiver, receiver_map)); } if (!expr->holder().is_null()) { - AddInstruction(new HCheckPrototypeMaps(receiver, - expr->holder(), - receiver_map)); + AddInstruction(new HCheckPrototypeMaps( + Handle(JSObject::cast(receiver_map->prototype())), + expr->holder())); } } diff --git a/src/ia32/lithium-codegen-ia32.cc b/src/ia32/lithium-codegen-ia32.cc index 8759288..775e3a9 100644 --- a/src/ia32/lithium-codegen-ia32.cc +++ b/src/ia32/lithium-codegen-ia32.cc @@ -3155,8 +3155,7 @@ void LCodeGen::DoCheckPrototypeMaps(LCheckPrototypeMaps* instr) { Register reg = ToRegister(instr->temp()); Handle holder = instr->holder(); - Handle receiver_map = instr->receiver_map(); - Handle current_prototype(JSObject::cast(receiver_map->prototype())); + Handle current_prototype = instr->prototype(); // Load prototype object. LoadPrototype(reg, current_prototype); diff --git a/src/ia32/lithium-ia32.h b/src/ia32/lithium-ia32.h index b01ffaf..2518285 100644 --- a/src/ia32/lithium-ia32.h +++ b/src/ia32/lithium-ia32.h @@ -77,6 +77,7 @@ class LCodeGen; // LCallNamed // LCallRuntime // LCallStub +// LCheckPrototypeMaps // LConstant // LConstantD // LConstantI @@ -111,7 +112,6 @@ class LCodeGen; // LCheckFunction // LCheckInstanceType // LCheckMap -// LCheckPrototypeMaps // LCheckSmi // LClassOfTest // LClassOfTestAndBranch @@ -1680,8 +1680,8 @@ class LCheckPrototypeMaps: public LTemplateInstruction<0, 0, 0> { DECLARE_CONCRETE_INSTRUCTION(CheckPrototypeMaps, "check-prototype-maps") DECLARE_HYDROGEN_ACCESSOR(CheckPrototypeMaps) + Handle prototype() const { return hydrogen()->prototype(); } Handle holder() const { return hydrogen()->holder(); } - Handle receiver_map() const { return hydrogen()->receiver_map(); } LOperand* temp() const { return temp_; } -- 2.7.4