From: Erik Arvidsson Date: Thu, 5 Feb 2015 23:34:16 +0000 (-0500) Subject: Accessor functions should have no prototype property X-Git-Tag: upstream/4.7.83~4568 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=b67b3c54011351bde23656fc650a6398829851d8;p=platform%2Fupstream%2Fv8.git Accessor functions should have no prototype property This also removes some convenience functions that were not used. BUG=v8:3700 LOG=N R=adamk@chromium.org, adamk Review URL: https://codereview.chromium.org/883073008 Cr-Commit-Position: refs/heads/master@{#26472} --- diff --git a/src/arm/full-codegen-arm.cc b/src/arm/full-codegen-arm.cc index f6a7414fb..a4a17efee 100644 --- a/src/arm/full-codegen-arm.cc +++ b/src/arm/full-codegen-arm.cc @@ -153,7 +153,7 @@ void FullCodeGenerator::Generate() { { Comment cmnt(masm_, "[ Allocate locals"); int locals_count = info->scope()->num_stack_slots(); // Generators allocate locals, if any, in context slots. - DCHECK(!info->function()->is_generator() || locals_count == 0); + DCHECK(!IsGeneratorFunction(info->function()->kind()) || locals_count == 0); if (locals_count > 0) { if (locals_count >= 128) { Label ok; diff --git a/src/arm64/full-codegen-arm64.cc b/src/arm64/full-codegen-arm64.cc index c5a71b519..c6d32670e 100644 --- a/src/arm64/full-codegen-arm64.cc +++ b/src/arm64/full-codegen-arm64.cc @@ -155,7 +155,7 @@ void FullCodeGenerator::Generate() { { Comment cmnt(masm_, "[ Allocate locals"); int locals_count = info->scope()->num_stack_slots(); // Generators allocate locals, if any, in context slots. - DCHECK(!info->function()->is_generator() || locals_count == 0); + DCHECK(!IsGeneratorFunction(info->function()->kind()) || locals_count == 0); if (locals_count > 0) { if (locals_count >= 128) { diff --git a/src/ast.h b/src/ast.h index fca3aabf3..4e1fb26c2 100644 --- a/src/ast.h +++ b/src/ast.h @@ -2548,18 +2548,6 @@ class FunctionLiteral FINAL : public Expression { } FunctionKind kind() { return FunctionKindBits::decode(bitfield_); } - bool is_arrow() { - return IsArrowFunction(FunctionKindBits::decode(bitfield_)); - } - bool is_generator() { - return IsGeneratorFunction(FunctionKindBits::decode(bitfield_)); - } - bool is_concise_method() { - return IsConciseMethod(FunctionKindBits::decode(bitfield_)); - } - bool is_default_constructor() { - return IsDefaultConstructor(FunctionKindBits::decode(bitfield_)); - } int ast_node_count() { return ast_properties_.node_count(); } AstProperties::Flags* flags() { return ast_properties_.flags(); } @@ -2630,7 +2618,7 @@ class FunctionLiteral FINAL : public Expression { class HasDuplicateParameters : public BitField {}; class IsFunction : public BitField {}; class IsParenthesized : public BitField {}; - class FunctionKindBits : public BitField {}; + class FunctionKindBits : public BitField {}; }; diff --git a/src/code-stubs.h b/src/code-stubs.h index 2edeb8f39..f284a344c 100644 --- a/src/code-stubs.h +++ b/src/code-stubs.h @@ -587,15 +587,11 @@ class FastNewClosureStub : public HydrogenCodeStub { FunctionKind kind() const { return FunctionKindBits::decode(sub_minor_key()); } - bool is_arrow() const { return IsArrowFunction(kind()); } - bool is_generator() const { return IsGeneratorFunction(kind()); } - bool is_concise_method() const { return IsConciseMethod(kind()); } - bool is_default_constructor() const { return IsDefaultConstructor(kind()); } private: STATIC_ASSERT(LANGUAGE_END == 3); class LanguageModeBits : public BitField {}; - class FunctionKindBits : public BitField {}; + class FunctionKindBits : public BitField {}; DEFINE_CALL_INTERFACE_DESCRIPTOR(FastNewClosure); DEFINE_HYDROGEN_CODE_STUB(FastNewClosure, HydrogenCodeStub); diff --git a/src/compiler.cc b/src/compiler.cc index 9aab688c6..e9cc11172 100644 --- a/src/compiler.cc +++ b/src/compiler.cc @@ -804,7 +804,7 @@ static bool CheckSuperConstructorCall(CompilationInfo* info) { FunctionLiteral* function = info->function(); if (FLAG_experimental_classes) return true; if (!function->uses_super_constructor_call()) return true; - if (function->is_default_constructor()) return true; + if (IsDefaultConstructor(function->kind())) return true; ZoneList* body = function->body(); CHECK(body->length() > 0); diff --git a/src/contexts.h b/src/contexts.h index 83510e93c..f932c6009 100644 --- a/src/contexts.h +++ b/src/contexts.h @@ -574,7 +574,8 @@ class Context: public FixedArray { : SLOPPY_GENERATOR_FUNCTION_MAP_INDEX; } - if (IsArrowFunction(kind) || IsConciseMethod(kind)) { + if (IsArrowFunction(kind) || IsConciseMethod(kind) || + IsAccessorFunction(kind)) { return is_strict(language_mode) ? STRICT_FUNCTION_WITHOUT_PROTOTYPE_MAP_INDEX : SLOPPY_FUNCTION_WITHOUT_PROTOTYPE_MAP_INDEX; diff --git a/src/globals.h b/src/globals.h index 761a85d01..3f2c33593 100644 --- a/src/globals.h +++ b/src/globals.h @@ -814,12 +814,13 @@ enum Signedness { kSigned, kUnsigned }; enum FunctionKind { kNormalFunction = 0, - kArrowFunction = 1, - kGeneratorFunction = 2, - kConciseMethod = 4, + kArrowFunction = 1 << 0, + kGeneratorFunction = 1 << 1, + kConciseMethod = 1 << 2, kConciseGeneratorMethod = kGeneratorFunction | kConciseMethod, - kDefaultConstructor = 8, - kSubclassConstructor = 16 + kAccessorFunction = 1 << 3, + kDefaultConstructor = 1 << 4, + kSubclassConstructor = 1 << 5 }; @@ -829,6 +830,7 @@ inline bool IsValidFunctionKind(FunctionKind kind) { kind == FunctionKind::kGeneratorFunction || kind == FunctionKind::kConciseMethod || kind == FunctionKind::kConciseGeneratorMethod || + kind == FunctionKind::kAccessorFunction || kind == FunctionKind::kDefaultConstructor || kind == FunctionKind::kSubclassConstructor; } @@ -852,11 +854,18 @@ inline bool IsConciseMethod(FunctionKind kind) { } +inline bool IsAccessorFunction(FunctionKind kind) { + DCHECK(IsValidFunctionKind(kind)); + return kind & FunctionKind::kAccessorFunction; +} + + inline bool IsDefaultConstructor(FunctionKind kind) { DCHECK(IsValidFunctionKind(kind)); return kind & FunctionKind::kDefaultConstructor; } + inline bool IsSubclassConstructor(FunctionKind kind) { DCHECK(IsValidFunctionKind(kind)); return kind & FunctionKind::kSubclassConstructor; diff --git a/src/hydrogen-instructions.h b/src/hydrogen-instructions.h index dd7bbfdb2..1c54fa5ba 100644 --- a/src/hydrogen-instructions.h +++ b/src/hydrogen-instructions.h @@ -7591,10 +7591,6 @@ class HFunctionLiteral FINAL : public HTemplateInstruction<1> { bool has_no_literals() const { return HasNoLiteralsField::decode(bit_field_); } - bool is_arrow() const { return IsArrowFunction(kind()); } - bool is_generator() const { return IsGeneratorFunction(kind()); } - bool is_concise_method() const { return IsConciseMethod(kind()); } - bool is_default_constructor() const { return IsDefaultConstructor(kind()); } FunctionKind kind() const { return FunctionKindField::decode(bit_field_); } LanguageMode language_mode() const { return LanguageModeField::decode(bit_field_); @@ -7616,11 +7612,11 @@ class HFunctionLiteral FINAL : public HTemplateInstruction<1> { bool IsDeletable() const OVERRIDE { return true; } - class FunctionKindField : public BitField {}; - class PretenureField : public BitField {}; - class HasNoLiteralsField : public BitField {}; + class FunctionKindField : public BitField {}; + class PretenureField : public BitField {}; + class HasNoLiteralsField : public BitField {}; STATIC_ASSERT(LANGUAGE_END == 3); - class LanguageModeField : public BitField {}; + class LanguageModeField : public BitField {}; Handle shared_info_; uint32_t bit_field_; diff --git a/src/ia32/full-codegen-ia32.cc b/src/ia32/full-codegen-ia32.cc index 611a2c5c3..8ab3763e7 100644 --- a/src/ia32/full-codegen-ia32.cc +++ b/src/ia32/full-codegen-ia32.cc @@ -143,7 +143,7 @@ void FullCodeGenerator::Generate() { { Comment cmnt(masm_, "[ Allocate locals"); int locals_count = info->scope()->num_stack_slots(); // Generators allocate locals, if any, in context slots. - DCHECK(!info->function()->is_generator() || locals_count == 0); + DCHECK(!IsGeneratorFunction(info->function()->kind()) || locals_count == 0); if (locals_count == 1) { __ push(Immediate(isolate()->factory()->undefined_value())); } else if (locals_count > 1) { diff --git a/src/mips/full-codegen-mips.cc b/src/mips/full-codegen-mips.cc index 2909655c0..7fc5e5c22 100644 --- a/src/mips/full-codegen-mips.cc +++ b/src/mips/full-codegen-mips.cc @@ -161,7 +161,7 @@ void FullCodeGenerator::Generate() { { Comment cmnt(masm_, "[ Allocate locals"); int locals_count = info->scope()->num_stack_slots(); // Generators allocate locals, if any, in context slots. - DCHECK(!info->function()->is_generator() || locals_count == 0); + DCHECK(!IsGeneratorFunction(info->function()->kind()) || locals_count == 0); if (locals_count > 0) { if (locals_count >= 128) { Label ok; diff --git a/src/mips64/full-codegen-mips64.cc b/src/mips64/full-codegen-mips64.cc index 9f4be7036..79052b958 100644 --- a/src/mips64/full-codegen-mips64.cc +++ b/src/mips64/full-codegen-mips64.cc @@ -158,7 +158,7 @@ void FullCodeGenerator::Generate() { { Comment cmnt(masm_, "[ Allocate locals"); int locals_count = info->scope()->num_stack_slots(); // Generators allocate locals, if any, in context slots. - DCHECK(!info->function()->is_generator() || locals_count == 0); + DCHECK(!IsGeneratorFunction(info->function()->kind()) || locals_count == 0); if (locals_count > 0) { if (locals_count >= 128) { Label ok; diff --git a/src/objects-inl.h b/src/objects-inl.h index 13f8427c3..31439039d 100644 --- a/src/objects-inl.h +++ b/src/objects-inl.h @@ -5871,6 +5871,8 @@ BOOL_ACCESSORS(SharedFunctionInfo, compiler_hints, is_arrow, kIsArrow) BOOL_ACCESSORS(SharedFunctionInfo, compiler_hints, is_generator, kIsGenerator) BOOL_ACCESSORS(SharedFunctionInfo, compiler_hints, is_concise_method, kIsConciseMethod) +BOOL_ACCESSORS(SharedFunctionInfo, compiler_hints, is_accessor_function, + kIsAccessorFunction) BOOL_ACCESSORS(SharedFunctionInfo, compiler_hints, is_default_constructor, kIsDefaultConstructor) diff --git a/src/objects.h b/src/objects.h index 06c490cfe..61daada4b 100644 --- a/src/objects.h +++ b/src/objects.h @@ -6940,6 +6940,9 @@ class SharedFunctionInfo: public HeapObject { // Indicates that this function is a concise method. DECL_BOOLEAN_ACCESSORS(is_concise_method) + // Indicates that this function is an accessor (getter or setter). + DECL_BOOLEAN_ACCESSORS(is_accessor_function) + // Indicates that this function is a default constructor. DECL_BOOLEAN_ACCESSORS(is_default_constructor) @@ -7190,6 +7193,7 @@ class SharedFunctionInfo: public HeapObject { kIsArrow, kIsGenerator, kIsConciseMethod, + kIsAccessorFunction, kIsDefaultConstructor, kIsSubclassConstructor, kIsAsmFunction, @@ -7199,7 +7203,7 @@ class SharedFunctionInfo: public HeapObject { // Add hints for other modes when they're added. STATIC_ASSERT(LANGUAGE_END == 3); - class FunctionKindBits : public BitField {}; + class FunctionKindBits : public BitField {}; class DeoptCountBits : public BitField {}; class OptReenableTriesBits : public BitField {}; diff --git a/src/ppc/full-codegen-ppc.cc b/src/ppc/full-codegen-ppc.cc index b7a5d3e33..45133617e 100644 --- a/src/ppc/full-codegen-ppc.cc +++ b/src/ppc/full-codegen-ppc.cc @@ -158,7 +158,7 @@ void FullCodeGenerator::Generate() { Comment cmnt(masm_, "[ Allocate locals"); int locals_count = info->scope()->num_stack_slots(); // Generators allocate locals, if any, in context slots. - DCHECK(!info->function()->is_generator() || locals_count == 0); + DCHECK(!IsGeneratorFunction(info->function()->kind()) || locals_count == 0); if (locals_count > 0) { if (locals_count >= 128) { Label ok; diff --git a/src/preparser.h b/src/preparser.h index 5be009d66..29a2b55e8 100644 --- a/src/preparser.h +++ b/src/preparser.h @@ -2194,7 +2194,7 @@ ParserBase::ParsePropertyDefinition(ObjectLiteralCheckerBase* checker, typename Traits::Type::FunctionLiteral value = this->ParseFunctionLiteral( name, scanner()->location(), false, // reserved words are allowed here - FunctionKind::kNormalFunction, RelocInfo::kNoPosition, + FunctionKind::kAccessorFunction, RelocInfo::kNoPosition, FunctionLiteral::ANONYMOUS_EXPRESSION, is_get ? FunctionLiteral::GETTER_ARITY : FunctionLiteral::SETTER_ARITY, CHECK_OK_CUSTOM(EmptyObjectLiteralProperty)); diff --git a/src/x64/full-codegen-x64.cc b/src/x64/full-codegen-x64.cc index 917764bd9..b248dd1eb 100644 --- a/src/x64/full-codegen-x64.cc +++ b/src/x64/full-codegen-x64.cc @@ -143,7 +143,7 @@ void FullCodeGenerator::Generate() { { Comment cmnt(masm_, "[ Allocate locals"); int locals_count = info->scope()->num_stack_slots(); // Generators allocate locals, if any, in context slots. - DCHECK(!info->function()->is_generator() || locals_count == 0); + DCHECK(!IsGeneratorFunction(info->function()->kind()) || locals_count == 0); if (locals_count == 1) { __ PushRoot(Heap::kUndefinedValueRootIndex); } else if (locals_count > 1) { diff --git a/src/x87/full-codegen-x87.cc b/src/x87/full-codegen-x87.cc index 84df83b1b..7cd503e58 100644 --- a/src/x87/full-codegen-x87.cc +++ b/src/x87/full-codegen-x87.cc @@ -143,7 +143,7 @@ void FullCodeGenerator::Generate() { { Comment cmnt(masm_, "[ Allocate locals"); int locals_count = info->scope()->num_stack_slots(); // Generators allocate locals, if any, in context slots. - DCHECK(!info->function()->is_generator() || locals_count == 0); + DCHECK(!IsGeneratorFunction(info->function()->kind()) || locals_count == 0); if (locals_count == 1) { __ push(Immediate(isolate()->factory()->undefined_value())); } else if (locals_count > 1) { diff --git a/test/mjsunit/accessors-no-prototype.js b/test/mjsunit/accessors-no-prototype.js new file mode 100644 index 000000000..9c429fc48 --- /dev/null +++ b/test/mjsunit/accessors-no-prototype.js @@ -0,0 +1,51 @@ +// Copyright 2014 the V8 project authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + + +(function TestGetter() { + var o = { + get x() {} + }; + var desc = Object.getOwnPropertyDescriptor(o, 'x'); + assertEquals('function', typeof desc.get); + assertFalse('prototype' in desc.get); + + assertThrows(function() { + new desc.get(); + }, TypeError); +})(); + + +(function TestSetter() { + var o = { + set x(_) {} + }; + var desc = Object.getOwnPropertyDescriptor(o, 'x'); + assertEquals('function', typeof desc.set); + assertFalse('prototype' in desc.set); + + assertThrows(function() { + new desc.set(); + }, TypeError); +})(); + + +(function TestBoth() { + var o = { + get x() {}, + set x(_) {} + }; + var desc = Object.getOwnPropertyDescriptor(o, 'x'); + assertEquals('function', typeof desc.get); + assertEquals('function', typeof desc.set); + assertFalse('prototype' in desc.get); + assertFalse('prototype' in desc.set); + + assertThrows(function() { + new desc.get(); + }, TypeError); + assertThrows(function() { + new desc.set(); + }, TypeError); +})(); diff --git a/test/mjsunit/harmony/classes.js b/test/mjsunit/harmony/classes.js index f57a1bad1..a28cddf4d 100644 --- a/test/mjsunit/harmony/classes.js +++ b/test/mjsunit/harmony/classes.js @@ -198,6 +198,7 @@ function assertGetterDescriptor(object, name) { assertTrue(descr.configurable); assertFalse(descr.enumerable); assertEquals('function', typeof descr.get); + assertFalse('prototype' in descr.get); assertEquals(undefined, descr.set); } @@ -208,6 +209,7 @@ function assertSetterDescriptor(object, name) { assertFalse(descr.enumerable); assertEquals(undefined, descr.get); assertEquals('function', typeof descr.set); + assertFalse('prototype' in descr.set); } @@ -217,6 +219,8 @@ function assertAccessorDescriptor(object, name) { assertFalse(descr.enumerable); assertEquals('function', typeof descr.get); assertEquals('function', typeof descr.set); + assertFalse('prototype' in descr.get); + assertFalse('prototype' in descr.set); }