Commit 9b6ff3a8 authored by jochen's avatar jochen Committed by Commit bot

Store the scope info in catch contexts

Since the extension field is already used for the catch name, store a
ContextExtension there instead.

In the future, this will allow for chaining ScopeInfos together, so we
no longer need a context chain for lazy parsing / compilation.

BUG=v8:5215
R=bmeurer@chromium.org,neis@chromium.org,marja@chromium.org

Review-Url: https://codereview.chromium.org/2302013002
Cr-Commit-Position: refs/heads/master@{#39164}
parent 5fd798af
......@@ -224,17 +224,22 @@ DeclarationScope::DeclarationScope(Zone* zone, ScopeType scope_type,
SetDefaults();
}
Scope::Scope(Zone* zone, const AstRawString* catch_variable_name)
Scope::Scope(Zone* zone, const AstRawString* catch_variable_name,
Handle<ScopeInfo> scope_info)
: zone_(zone),
outer_scope_(nullptr),
variables_(zone),
locals_(0, zone),
decls_(0, zone),
scope_info_(scope_info),
scope_type_(CATCH_SCOPE) {
SetDefaults();
#ifdef DEBUG
already_resolved_ = true;
#endif
// Cache the catch variable, even though it's also available via the
// scope_info, as the parser expects that a catch scope always has the catch
// variable as first and only variable.
Variable* variable = Declare(zone, this, catch_variable_name, VAR,
Variable::NORMAL, kCreatedInitialized);
AllocateHeapSlot(variable);
......@@ -368,7 +373,8 @@ Scope* Scope::DeserializeScopeChain(Isolate* isolate, Zone* zone,
DCHECK(context->IsCatchContext());
String* name = context->catch_name();
outer_scope = new (zone)
Scope(zone, ast_value_factory->GetString(handle(name, isolate)));
Scope(zone, ast_value_factory->GetString(handle(name, isolate)),
Handle<ScopeInfo>(context->scope_info()));
}
if (current_scope != nullptr) {
outer_scope->AddInnerScope(current_scope);
......
......@@ -539,7 +539,8 @@ class Scope: public ZoneObject {
Scope(Zone* zone, ScopeType type, Handle<ScopeInfo> scope_info);
// Construct a catch scope with a binding for the name.
Scope(Zone* zone, const AstRawString* catch_variable_name);
Scope(Zone* zone, const AstRawString* catch_variable_name,
Handle<ScopeInfo> scope_info);
void AddInnerScope(Scope* inner_scope) {
inner_scope->sibling_ = inner_scope_;
......
......@@ -632,6 +632,25 @@ FieldAccess AccessBuilder::ForPropertyCellValue(Type* type) {
return access;
}
// static
FieldAccess AccessBuilder::ForContextExtensionScopeInfo() {
FieldAccess access = {kTaggedBase,
ContextExtension::kScopeInfoOffset,
Handle<Name>(),
Type::OtherInternal(),
MachineType::AnyTagged(),
kFullWriteBarrier};
return access;
}
// static
FieldAccess AccessBuilder::ForContextExtensionExtension() {
FieldAccess access = {
kTaggedBase, ContextExtension::kExtensionOffset, Handle<Name>(),
Type::Any(), MachineType::AnyTagged(), kFullWriteBarrier};
return access;
}
// static
ElementAccess AccessBuilder::ForFixedArrayElement() {
ElementAccess access = {kTaggedBase, FixedArray::kHeaderSize, Type::Tagged(),
......
......@@ -199,6 +199,10 @@ class AccessBuilder final : public AllStatic {
static FieldAccess ForPropertyCellValue();
static FieldAccess ForPropertyCellValue(Type* type);
// Provides access to ContextExtension fields.
static FieldAccess ForContextExtensionScopeInfo();
static FieldAccess ForContextExtensionExtension();
// Provides access to FixedArray elements.
static ElementAccess ForFixedArrayElement();
static ElementAccess ForFixedArrayElement(ElementsKind kind);
......
......@@ -1480,7 +1480,8 @@ void AstGraphBuilder::VisitTryCatchStatement(TryCatchStatement* stmt) {
// Create a catch scope that binds the exception.
Node* exception = try_control.GetExceptionNode();
Handle<String> name = stmt->variable()->name();
const Operator* op = javascript()->CreateCatchContext(name);
Handle<ScopeInfo> scope_info = stmt->scope()->scope_info();
const Operator* op = javascript()->CreateCatchContext(name, scope_info);
Node* context = NewNode(op, exception, GetFunctionClosureForContext());
// Evaluate the catch-block.
......
......@@ -952,9 +952,11 @@ void BytecodeGraphBuilder::VisitCreateCatchContext() {
Node* exception = environment()->LookupRegister(reg);
Handle<String> name =
Handle<String>::cast(bytecode_iterator().GetConstantForIndexOperand(1));
Handle<ScopeInfo> scope_info = Handle<ScopeInfo>::cast(
bytecode_iterator().GetConstantForIndexOperand(2));
Node* closure = environment()->LookupAccumulator();
const Operator* op = javascript()->CreateCatchContext(name);
const Operator* op = javascript()->CreateCatchContext(name, scope_info);
Node* context = NewNode(op, exception, closure);
environment()->BindAccumulator(context);
}
......
......@@ -838,7 +838,8 @@ Reduction JSCreateLowering::ReduceJSCreateWithContext(Node* node) {
Reduction JSCreateLowering::ReduceJSCreateCatchContext(Node* node) {
DCHECK_EQ(IrOpcode::kJSCreateCatchContext, node->opcode());
Handle<String> name = OpParameter<Handle<String>>(node);
const CreateCatchContextParameters& parameters =
CreateCatchContextParametersOf(node->op());
Node* exception = NodeProperties::GetValueInput(node, 0);
Node* closure = NodeProperties::GetValueInput(node, 1);
Node* effect = NodeProperties::GetEffectInput(node);
......@@ -847,13 +848,23 @@ Reduction JSCreateLowering::ReduceJSCreateCatchContext(Node* node) {
Node* native_context = effect = graph()->NewNode(
javascript()->LoadContext(0, Context::NATIVE_CONTEXT_INDEX, true),
context, context, effect);
AllocationBuilder a(jsgraph(), effect, control);
AllocationBuilder aa(jsgraph(), effect, control);
aa.Allocate(ContextExtension::kSize);
aa.Store(AccessBuilder::ForMap(), factory()->context_extension_map());
aa.Store(AccessBuilder::ForContextExtensionScopeInfo(),
parameters.scope_info());
aa.Store(AccessBuilder::ForContextExtensionExtension(),
parameters.catch_name());
Node* extension = aa.Finish();
AllocationBuilder a(jsgraph(), extension, control);
STATIC_ASSERT(Context::MIN_CONTEXT_SLOTS == 4); // Ensure fully covered.
a.AllocateArray(Context::MIN_CONTEXT_SLOTS + 1,
factory()->catch_context_map());
a.Store(AccessBuilder::ForContextSlot(Context::CLOSURE_INDEX), closure);
a.Store(AccessBuilder::ForContextSlot(Context::PREVIOUS_INDEX), context);
a.Store(AccessBuilder::ForContextSlot(Context::EXTENSION_INDEX), name);
a.Store(AccessBuilder::ForContextSlot(Context::EXTENSION_INDEX), extension);
a.Store(AccessBuilder::ForContextSlot(Context::NATIVE_CONTEXT_INDEX),
native_context);
a.Store(AccessBuilder::ForContextSlot(Context::THROWN_OBJECT_INDEX),
......
......@@ -509,8 +509,12 @@ void JSGenericLowering::LowerJSCreateLiteralRegExp(Node* node) {
void JSGenericLowering::LowerJSCreateCatchContext(Node* node) {
Handle<String> name = OpParameter<Handle<String>>(node);
node->InsertInput(zone(), 0, jsgraph()->HeapConstant(name));
const CreateCatchContextParameters& parameters =
CreateCatchContextParametersOf(node->op());
node->InsertInput(zone(), 0,
jsgraph()->HeapConstant(parameters.catch_name()));
node->InsertInput(zone(), 2,
jsgraph()->HeapConstant(parameters.scope_info()));
ReplaceWithRuntimeCall(node, Runtime::kPushCatchContext);
}
......
......@@ -157,6 +157,37 @@ ContextAccess const& ContextAccessOf(Operator const* op) {
return OpParameter<ContextAccess>(op);
}
CreateCatchContextParameters::CreateCatchContextParameters(
Handle<String> catch_name, Handle<ScopeInfo> scope_info)
: catch_name_(catch_name), scope_info_(scope_info) {}
bool operator==(CreateCatchContextParameters const& lhs,
CreateCatchContextParameters const& rhs) {
return lhs.catch_name().location() == rhs.catch_name().location() &&
lhs.scope_info().location() == rhs.scope_info().location();
}
bool operator!=(CreateCatchContextParameters const& lhs,
CreateCatchContextParameters const& rhs) {
return !(lhs == rhs);
}
size_t hash_value(CreateCatchContextParameters const& parameters) {
return base::hash_combine(parameters.catch_name().location(),
parameters.scope_info().location());
}
std::ostream& operator<<(std::ostream& os,
CreateCatchContextParameters const& parameters) {
return os << Brief(*parameters.catch_name()) << ", "
<< Brief(*parameters.scope_info());
}
CreateCatchContextParameters const& CreateCatchContextParametersOf(
Operator const* op) {
DCHECK_EQ(IrOpcode::kJSCreateCatchContext, op->opcode());
return OpParameter<CreateCatchContextParameters>(op);
}
bool operator==(NamedAccess const& lhs, NamedAccess const& rhs) {
return lhs.name().location() == rhs.name().location() &&
......@@ -809,14 +840,14 @@ const Operator* JSOperatorBuilder::CreateFunctionContext(int slot_count) {
slot_count); // parameter
}
const Operator* JSOperatorBuilder::CreateCatchContext(
const Handle<String>& name) {
return new (zone()) Operator1<Handle<String>>( // --
const Handle<String>& name, const Handle<ScopeInfo>& scope_info) {
CreateCatchContextParameters parameters(name, scope_info);
return new (zone()) Operator1<CreateCatchContextParameters>(
IrOpcode::kJSCreateCatchContext, Operator::kNoProperties, // opcode
"JSCreateCatchContext", // name
2, 1, 1, 1, 1, 2, // counts
name); // parameter
parameters); // parameter
}
......
......@@ -178,6 +178,33 @@ std::ostream& operator<<(std::ostream&, ContextAccess const&);
ContextAccess const& ContextAccessOf(Operator const*);
// Defines the name and ScopeInfo for a new catch context. This is used as a
// parameter by the JSCreateCatchContext operator.
class CreateCatchContextParameters final {
public:
CreateCatchContextParameters(Handle<String> catch_name,
Handle<ScopeInfo> scope_info);
Handle<String> catch_name() const { return catch_name_; }
Handle<ScopeInfo> scope_info() const { return scope_info_; }
private:
Handle<String> const catch_name_;
Handle<ScopeInfo> const scope_info_;
};
bool operator==(CreateCatchContextParameters const& lhs,
CreateCatchContextParameters const& rhs);
bool operator!=(CreateCatchContextParameters const& lhs,
CreateCatchContextParameters const& rhs);
size_t hash_value(CreateCatchContextParameters const& parameters);
std::ostream& operator<<(std::ostream& os,
CreateCatchContextParameters const& parameters);
CreateCatchContextParameters const& CreateCatchContextParametersOf(
Operator const*);
// Defines the property of an object for a named access. This is
// used as a parameter by the JSLoadNamed and JSStoreNamed operators.
......@@ -481,7 +508,8 @@ class JSOperatorBuilder final : public ZoneObject {
const Operator* StackCheck();
const Operator* CreateFunctionContext(int slot_count);
const Operator* CreateCatchContext(const Handle<String>& name);
const Operator* CreateCatchContext(const Handle<String>& name,
const Handle<ScopeInfo>& scope_info);
const Operator* CreateWithContext();
const Operator* CreateBlockContext(const Handle<ScopeInfo>& scpope_info);
const Operator* CreateModuleContext();
......
......@@ -110,10 +110,11 @@ JSReceiver* Context::extension_receiver() {
ScopeInfo* Context::scope_info() {
DCHECK(IsModuleContext() || IsScriptContext() || IsBlockContext());
DCHECK(IsModuleContext() || IsScriptContext() || IsBlockContext() ||
IsCatchContext());
HeapObject* object = extension();
if (object->IsContextExtension()) {
DCHECK(IsBlockContext());
DCHECK(IsBlockContext() || IsCatchContext());
object = ContextExtension::cast(object)->scope_info();
}
return ScopeInfo::cast(object);
......@@ -122,7 +123,7 @@ ScopeInfo* Context::scope_info() {
String* Context::catch_name() {
DCHECK(IsCatchContext());
return String::cast(extension());
return String::cast(ContextExtension::cast(extension())->extension());
}
......
......@@ -104,7 +104,6 @@ Handle<PrototypeInfo> Factory::NewPrototypeInfo() {
Handle<ContextExtension> Factory::NewContextExtension(
Handle<ScopeInfo> scope_info, Handle<Object> extension) {
DCHECK(scope_info->is_declaration_scope());
Handle<ContextExtension> result =
Handle<ContextExtension>::cast(NewStruct(CONTEXT_EXTENSION_TYPE));
result->set_scope_info(*scope_info);
......@@ -816,18 +815,19 @@ Handle<Context> Factory::NewFunctionContext(int length,
return context;
}
Handle<Context> Factory::NewCatchContext(Handle<JSFunction> function,
Handle<Context> previous,
Handle<ScopeInfo> scope_info,
Handle<String> name,
Handle<Object> thrown_object) {
STATIC_ASSERT(Context::MIN_CONTEXT_SLOTS == Context::THROWN_OBJECT_INDEX);
Handle<ContextExtension> extension = NewContextExtension(scope_info, name);
Handle<FixedArray> array = NewFixedArray(Context::MIN_CONTEXT_SLOTS + 1);
array->set_map_no_write_barrier(*catch_context_map());
Handle<Context> context = Handle<Context>::cast(array);
context->set_closure(*function);
context->set_previous(*previous);
context->set_extension(*name);
context->set_extension(*extension);
context->set_native_context(previous->native_context());
context->set(Context::THROWN_OBJECT_INDEX, *thrown_object);
return context;
......
......@@ -265,6 +265,7 @@ class Factory final {
// Create a catch context.
Handle<Context> NewCatchContext(Handle<JSFunction> function,
Handle<Context> previous,
Handle<ScopeInfo> scope_info,
Handle<String> name,
Handle<Object> thrown_object);
......
......@@ -1333,6 +1333,7 @@ void FullCodeGenerator::VisitTryCatchStatement(TryCatchStatement* stmt) {
{ Comment cmnt(masm_, "[ Extend catch context");
PushOperand(stmt->variable()->name());
PushOperand(result_register());
PushOperand(stmt->scope()->scope_info());
PushFunctionArgumentForContextAllocation();
CallRuntimeWithOperands(Runtime::kPushCatchContext);
StoreToFrameField(StandardFrameConstants::kContextOffset,
......
......@@ -350,10 +350,11 @@ BytecodeArrayBuilder& BytecodeArrayBuilder::CreateBlockContext(
}
BytecodeArrayBuilder& BytecodeArrayBuilder::CreateCatchContext(
Register exception, Handle<String> name) {
Register exception, Handle<String> name, Handle<ScopeInfo> scope_info) {
size_t name_index = GetConstantPoolEntry(name);
size_t scope_info_index = GetConstantPoolEntry(scope_info);
Output(Bytecode::kCreateCatchContext, RegisterOperand(exception),
UnsignedOperand(name_index));
UnsignedOperand(name_index), UnsignedOperand(scope_info_index));
return *this;
}
......
......@@ -139,10 +139,11 @@ class BytecodeArrayBuilder final : public ZoneObject {
// in the accumulator.
BytecodeArrayBuilder& CreateBlockContext(Handle<ScopeInfo> scope_info);
// Create a new context for a catch block with |exception| and |name| and the
// closure in the accumulator.
// Create a new context for a catch block with |exception|, |name|,
// |scope_info|, and the closure in the accumulator.
BytecodeArrayBuilder& CreateCatchContext(Register exception,
Handle<String> name);
Handle<String> name,
Handle<ScopeInfo> scope_info);
// Create a new context with size |slots|.
BytecodeArrayBuilder& CreateFunctionContext(int slots);
......
......@@ -1386,7 +1386,7 @@ void BytecodeGenerator::VisitTryCatchStatement(TryCatchStatement* stmt) {
try_control_builder.EndTry();
// Create a catch scope that binds the exception.
VisitNewLocalCatchContext(stmt->variable());
VisitNewLocalCatchContext(stmt->variable(), stmt->scope());
builder()->StoreAccumulatorInRegister(context);
// If requested, clear message object as we enter the catch block.
......@@ -3210,14 +3210,16 @@ void BytecodeGenerator::VisitNewLocalWithContext() {
execution_result()->SetResultInAccumulator();
}
void BytecodeGenerator::VisitNewLocalCatchContext(Variable* variable) {
void BytecodeGenerator::VisitNewLocalCatchContext(Variable* variable,
Scope* scope) {
AccumulatorResultScope accumulator_execution_result(this);
DCHECK(variable->IsContextSlot());
Register exception = register_allocator()->NewRegister();
builder()->StoreAccumulatorInRegister(exception);
VisitFunctionClosureForContext();
builder()->CreateCatchContext(exception, variable->name());
builder()->CreateCatchContext(exception, variable->name(),
scope->scope_info());
execution_result()->SetResultInAccumulator();
}
......
......@@ -140,7 +140,7 @@ class BytecodeGenerator final : public AstVisitor<BytecodeGenerator> {
void VisitBuildLocalActivationContext();
void VisitBlockDeclarationsAndStatements(Block* stmt);
void VisitNewLocalBlockContext(Scope* scope);
void VisitNewLocalCatchContext(Variable* variable);
void VisitNewLocalCatchContext(Variable* variable, Scope* scope);
void VisitNewLocalWithContext();
void VisitFunctionClosureForContext();
void VisitSetHomeObject(Register value, Register home_object,
......
......@@ -245,7 +245,7 @@ namespace interpreter {
/* Context allocation */ \
V(CreateBlockContext, AccumulatorUse::kReadWrite, OperandType::kIdx) \
V(CreateCatchContext, AccumulatorUse::kReadWrite, OperandType::kReg, \
OperandType::kIdx) \
OperandType::kIdx, OperandType::kIdx) \
/* TODO(klaasb) rename Idx or add unsigned Imm OperandType? */ \
V(CreateFunctionContext, AccumulatorUse::kWrite, OperandType::kIdx) \
V(CreateWithContext, AccumulatorUse::kReadWrite, OperandType::kReg) \
......
......@@ -1993,19 +1993,22 @@ void Interpreter::DoCreateBlockContext(InterpreterAssembler* assembler) {
__ Dispatch();
}
// CreateCatchContext <exception> <index>
// CreateCatchContext <exception> <name_idx> <scope_info_idx>
//
// Creates a new context for a catch block with the |exception| in a register,
// the variable name at |index| and the closure in the accumulator.
// the variable name at |name_idx|, the ScopeInfo at |scope_info_idx|, and the
// closure in the accumulator.
void Interpreter::DoCreateCatchContext(InterpreterAssembler* assembler) {
Node* exception_reg = __ BytecodeOperandReg(0);
Node* exception = __ LoadRegister(exception_reg);
Node* index = __ BytecodeOperandIdx(1);
Node* name = __ LoadConstantPoolEntry(index);
Node* name_idx = __ BytecodeOperandIdx(1);
Node* name = __ LoadConstantPoolEntry(name_idx);
Node* scope_info_idx = __ BytecodeOperandIdx(2);
Node* scope_info = __ LoadConstantPoolEntry(scope_info_idx);
Node* closure = __ GetAccumulator();
Node* context = __ GetContext();
__ SetAccumulator(__ CallRuntime(Runtime::kPushCatchContext, context, name,
exception, closure));
exception, scope_info, closure));
__ Dispatch();
}
......
......@@ -701,13 +701,14 @@ RUNTIME_FUNCTION(Runtime_PushWithContext) {
RUNTIME_FUNCTION(Runtime_PushCatchContext) {
HandleScope scope(isolate);
DCHECK_EQ(3, args.length());
DCHECK_EQ(4, args.length());
CONVERT_ARG_HANDLE_CHECKED(String, name, 0);
CONVERT_ARG_HANDLE_CHECKED(Object, thrown_object, 1);
CONVERT_ARG_HANDLE_CHECKED(JSFunction, function, 2);
CONVERT_ARG_HANDLE_CHECKED(ScopeInfo, scope_info, 2);
CONVERT_ARG_HANDLE_CHECKED(JSFunction, function, 3);
Handle<Context> current(isolate->context());
Handle<Context> context = isolate->factory()->NewCatchContext(
function, current, name, thrown_object);
function, current, scope_info, name, thrown_object);
isolate->set_context(*context);
return *context;
}
......
......@@ -475,7 +475,7 @@ namespace internal {
F(NewScriptContext, 2, 1) \
F(NewFunctionContext, 1, 1) \
F(PushWithContext, 2, 1) \
F(PushCatchContext, 3, 1) \
F(PushCatchContext, 4, 1) \
F(PushBlockContext, 2, 1) \
F(DeleteLookupSlot, 1, 1) \
F(LoadLookupSlot, 1, 1) \
......
......@@ -268,7 +268,7 @@ snippet: "
"
frame size: 18
parameter count: 1
bytecode array length: 763
bytecode array length: 765
bytecodes: [
B(Ldar), R(new_target),
B(JumpIfUndefined), U8(28),
......@@ -322,7 +322,7 @@ bytecodes: [
B(Star), R(6),
B(LdaZero),
B(Star), R(5),
B(JumpConstant), U8(17),
B(JumpConstant), U8(19),
B(Ldar), R(10),
/* 11 E> */ B(Throw),
B(Ldar), R(closure),
......@@ -418,7 +418,7 @@ bytecodes: [
B(Star), R(9),
B(LdaZero),
B(Star), R(8),
B(Jump), U8(69),
B(Jump), U8(70),
B(Ldar), R(13),
/* 36 E> */ B(Throw),
B(Ldar), R(13),
......@@ -426,10 +426,10 @@ bytecodes: [
B(LdaZero),
B(StaContextSlot), R(1), U8(9),
B(Wide), B(Jump), U16(-219),
B(Jump), U8(40),
B(Jump), U8(41),
B(Star), R(12),
B(Ldar), R(closure),
B(CreateCatchContext), R(12), U8(11),
B(CreateCatchContext), R(12), U8(11), U8(12),
B(Star), R(11),
B(PushContext), R(2),
B(LdrContextSlot), R(0), U8(9), R(12),
......@@ -452,33 +452,33 @@ bytecodes: [
B(LdrContextSlot), R(1), U8(9), R(11),
B(LdaZero),
B(TestEqualStrict), R(11), U8(14),
B(JumpIfTrueConstant), U8(15),
B(JumpIfTrueConstant), U8(17),
B(LdrContextSlot), R(1), U8(7), R(11),
B(LdaUndefined),
B(TestEqualStrict), R(11), U8(15),
B(JumpIfTrueConstant), U8(16),
B(JumpIfTrueConstant), U8(18),
B(LdrContextSlot), R(1), U8(7), R(11),
B(LdaNamedProperty), R(11), U8(12), U8(16),
B(LdaNamedProperty), R(11), U8(13), U8(16),
B(StaContextSlot), R(1), U8(11),
B(LdrContextSlot), R(1), U8(11), R(11),
B(LdaNull),
B(TestEqual), R(11), U8(18),
B(JumpIfFalse), U8(4),
B(Jump), U8(119),
B(Jump), U8(120),
B(LdrContextSlot), R(1), U8(9), R(11),
B(LdaSmi), U8(1),
B(TestEqualStrict), R(11), U8(19),
B(JumpIfFalse), U8(72),
B(JumpIfFalse), U8(73),
B(LdaContextSlot), R(1), U8(11),
B(TypeOf),
B(Star), R(11),
B(LdaConstant), U8(13),
B(LdaConstant), U8(14),
B(TestEqualStrict), R(11), U8(20),
B(JumpIfFalse), U8(4),
B(Jump), U8(18),
B(Wide), B(LdaSmi), U16(128),
B(Star), R(11),
B(LdaConstant), U8(14),
B(LdaConstant), U8(15),
B(Star), R(12),
B(CallRuntime), U16(Runtime::kNewTypeError), R(11), U8(2),
B(Throw),
......@@ -486,10 +486,10 @@ bytecodes: [
B(LdrContextSlot), R(1), U8(11), R(12),
B(LdrContextSlot), R(1), U8(7), R(13),
B(InvokeIntrinsic), U8(Runtime::k_Call), R(12), U8(2),
B(Jump), U8(22),
B(Jump), U8(23),
B(Star), R(12),
B(Ldar), R(closure),
B(CreateCatchContext), R(12), U8(11),
B(CreateCatchContext), R(12), U8(11), U8(16),
B(Star), R(11),
B(CallRuntime), U16(Runtime::kInterpreterClearPendingMessage), R(0), U8(0),
B(Ldar), R(11),
......@@ -588,17 +588,19 @@ constant pool: [
kInstanceTypeDontCare,
kInstanceTypeDontCare,
InstanceType::ONE_BYTE_INTERNALIZED_STRING_TYPE,
InstanceType::FIXED_ARRAY_TYPE,
InstanceType::ONE_BYTE_INTERNALIZED_STRING_TYPE,
InstanceType::ONE_BYTE_INTERNALIZED_STRING_TYPE,
InstanceType::ONE_BYTE_INTERNALIZED_STRING_TYPE,
InstanceType::FIXED_ARRAY_TYPE,
kInstanceTypeDontCare,
kInstanceTypeDontCare,
kInstanceTypeDontCare,
]
handlers: [
[47, 677, 683],
[147, 432, 438],
[47, 679, 685],
[147, 433, 439],
[150, 392, 394],
[539, 551, 553],
[540, 552, 554],
]
......@@ -3,7 +3,7 @@
#
---
pool type: string
pool type: mixed
execute: yes
wrap: yes
......@@ -13,16 +13,16 @@ snippet: "
"
frame size: 3
parameter count: 1
bytecode array length: 34
bytecode array length: 35
bytecodes: [
/* 30 E> */ B(StackCheck),
B(Mov), R(context), R(1),
/* 40 S> */ B(LdaSmi), U8(1),
/* 75 S> */ B(Return),
B(Jump), U8(25),
B(Jump), U8(26),
B(Star), R(2),
B(Ldar), R(closure),
B(CreateCatchContext), R(2), U8(0),
B(CreateCatchContext), R(2), U8(0), U8(1),
B(Star), R(1),
B(CallRuntime), U16(Runtime::kInterpreterClearPendingMessage), R(0), U8(0),
B(Ldar), R(1),
......@@ -34,7 +34,8 @@ bytecodes: [
/* 75 S> */ B(Return),
]
constant pool: [
"e",
InstanceType::ONE_BYTE_INTERNALIZED_STRING_TYPE,
InstanceType::FIXED_ARRAY_TYPE,
]
handlers: [
[4, 7, 9],
......@@ -48,16 +49,16 @@ snippet: "
"
frame size: 4
parameter count: 1
bytecode array length: 65
bytecode array length: 67
bytecodes: [
/* 30 E> */ B(StackCheck),
B(Mov), R(context), R(2),
/* 47 S> */ B(LdaSmi), U8(1),
B(Star), R(0),
B(Jump), U8(22),
B(Jump), U8(23),
B(Star), R(3),
B(Ldar), R(closure),
/* 49 E> */ B(CreateCatchContext), R(3), U8(0),
/* 49 E> */ B(CreateCatchContext), R(3), U8(0), U8(1),
B(Star), R(2),
B(CallRuntime), U16(Runtime::kInterpreterClearPendingMessage), R(0), U8(0),
B(Ldar), R(2),
......@@ -66,10 +67,10 @@ bytecodes: [
B(Mov), R(context), R(2),
/* 75 S> */ B(LdaSmi), U8(2),
B(Star), R(0),
B(Jump), U8(26),
B(Jump), U8(27),
B(Star), R(3),
B(Ldar), R(closure),
/* 77 E> */ B(CreateCatchContext), R(3), U8(1),
/* 77 E> */ B(CreateCatchContext), R(3), U8(2), U8(3),
B(Star), R(2),
B(CallRuntime), U16(Runtime::kInterpreterClearPendingMessage), R(0), U8(0),
B(Ldar), R(2),
......@@ -81,11 +82,13 @@ bytecodes: [
/* 103 S> */ B(Return),
]
constant pool: [
"e1",
"e2",
InstanceType::ONE_BYTE_INTERNALIZED_STRING_TYPE,
InstanceType::FIXED_ARRAY_TYPE,
InstanceType::ONE_BYTE_INTERNALIZED_STRING_TYPE,
InstanceType::FIXED_ARRAY_TYPE,
]
handlers: [
[4, 8, 10],
[33, 37, 39],
[34, 38, 40],
]
......@@ -3,7 +3,7 @@
#
---
pool type: string
pool type: mixed
execute: yes
wrap: yes
......@@ -55,7 +55,7 @@ snippet: "
"
frame size: 7
parameter count: 1
bytecode array length: 81
bytecode array length: 82
bytecodes: [
/* 30 E> */ B(StackCheck),
/* 42 S> */ B(LdaSmi), U8(1),
......@@ -64,10 +64,10 @@ bytecodes: [
B(Mov), R(context), R(5),
/* 51 S> */ B(LdaSmi), U8(2),
B(Star), R(0),
B(Jump), U8(26),
B(Jump), U8(27),
B(Star), R(6),
B(Ldar), R(closure),
/* 53 E> */ B(CreateCatchContext), R(6), U8(0),
/* 53 E> */ B(CreateCatchContext), R(6), U8(0), U8(1),
B(Star), R(5),
B(CallRuntime), U16(Runtime::kInterpreterClearPendingMessage), R(0), U8(0),
B(Ldar), R(5),
......@@ -96,10 +96,11 @@ bytecodes: [
/* 99 S> */ B(Return),
]
constant pool: [
"e",
InstanceType::ONE_BYTE_INTERNALIZED_STRING_TYPE,
InstanceType::FIXED_ARRAY_TYPE,
]
handlers: [
[8, 41, 47],
[8, 42, 48],
[11, 15, 17],
]
......@@ -111,7 +112,7 @@ snippet: "
"
frame size: 8
parameter count: 1
bytecode array length: 106
bytecode array length: 108
bytecodes: [
/* 30 E> */ B(StackCheck),
B(Mov), R(context), R(4),
......@@ -119,10 +120,10 @@ bytecodes: [
B(Mov), R(context), R(6),
/* 55 S> */ B(LdaSmi), U8(1),
B(Star), R(0),
B(Jump), U8(26),
B(Jump), U8(27),
B(Star), R(7),
B(Ldar), R(closure),
/* 57 E> */ B(CreateCatchContext), R(7), U8(0),
/* 57 E> */ B(CreateCatchContext), R(7), U8(0), U8(1),
B(Star), R(6),
B(CallRuntime), U16(Runtime::kInterpreterClearPendingMessage), R(0), U8(0),
B(Ldar), R(6),
......@@ -130,10 +131,10 @@ bytecodes: [
/* 74 S> */ B(LdaSmi), U8(2),
B(Star), R(0),
B(PopContext), R(1),
B(Jump), U8(26),
B(Jump), U8(27),
B(Star), R(6),
B(Ldar), R(closure),
/* 76 E> */ B(CreateCatchContext), R(6), U8(0),
/* 76 E> */ B(CreateCatchContext), R(6), U8(0), U8(2),
B(Star), R(5),
B(CallRuntime), U16(Runtime::kInterpreterClearPendingMessage), R(0), U8(0),
B(Ldar), R(5),
......@@ -162,11 +163,13 @@ bytecodes: [
/* 123 S> */ B(Return),
]
constant pool: [
"e",
InstanceType::ONE_BYTE_INTERNALIZED_STRING_TYPE,
InstanceType::FIXED_ARRAY_TYPE,
InstanceType::FIXED_ARRAY_TYPE,
]
handlers: [
[4, 66, 72],
[7, 40, 42],
[4, 68, 74],
[7, 41, 43],
[10, 14, 16],
]
......@@ -1250,7 +1250,7 @@ TEST(TopLevelObjectLiterals) {
TEST(TryCatch) {
InitializedIgnitionHandleScope scope;
BytecodeExpectationsPrinter printer(CcTest::isolate(),
ConstantPoolType::kString);
ConstantPoolType::kMixed);
const char* snippets[] = {
"try { return 1; } catch(e) { return 2; }\n",
......@@ -1267,7 +1267,7 @@ TEST(TryCatch) {
TEST(TryFinally) {
InitializedIgnitionHandleScope scope;
BytecodeExpectationsPrinter printer(CcTest::isolate(),
ConstantPoolType::kString);
ConstantPoolType::kMixed);
const char* snippets[] = {
"var a = 1;\n"
"try { a = 2; } finally { a = 3; }\n",
......
......@@ -195,14 +195,15 @@ TEST_F(JSCreateLoweringTest, JSCreateWithContext) {
TEST_F(JSCreateLoweringTest, JSCreateCatchContext) {
Handle<String> name = factory()->length_string();
Handle<ScopeInfo> scope_info(factory()->NewScopeInfo(1));
Node* const exception = Parameter(Type::Receiver());
Node* const closure = Parameter(Type::Function());
Node* const context = Parameter(Type::Any());
Node* const effect = graph()->start();
Node* const control = graph()->start();
Reduction r =
Reduce(graph()->NewNode(javascript()->CreateCatchContext(name), exception,
closure, context, effect, control));
Reduction r = Reduce(
graph()->NewNode(javascript()->CreateCatchContext(name, scope_info),
exception, closure, context, effect, control));
ASSERT_TRUE(r.Changed());
EXPECT_THAT(r.replacement(),
IsFinishRegion(IsAllocate(IsNumberConstant(Context::SizeFor(
......
......@@ -105,7 +105,7 @@ TEST_F(BytecodeArrayBuilderTest, AllBytecodesGenerated) {
// Emit create context operation.
builder.CreateBlockContext(factory->NewScopeInfo(1));
builder.CreateCatchContext(reg, name);
builder.CreateCatchContext(reg, name, factory->NewScopeInfo(1));
builder.CreateFunctionContext(1);
builder.CreateWithContext(reg);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment