Skip to content

Commit

Permalink
Stop emitting AllocObjectLiteral for object literals (facebook#135)
Browse files Browse the repository at this point in the history
Summary:
Now that the general case is fast, and generates much better code in
debug mode, stop emitting `AllocObjectLiteral` for object literals in
IRGen. This allows us to compile large JSON files with reasonable
performance and output in both release and debug builds.

Closes facebook#135

Reviewed By: tmikov

Differential Revision: D47724425

fbshipit-source-id: 903eec6828043828965f8afa8e751ead67470d14
  • Loading branch information
neildhar authored and facebook-github-bot committed Aug 24, 2023
1 parent 201aade commit bbe7966
Show file tree
Hide file tree
Showing 13 changed files with 199 additions and 214 deletions.
39 changes: 0 additions & 39 deletions lib/IRGen/ESTreeIRGen-expr.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -886,13 +886,9 @@ Value *ESTreeIRGen::genObjectExpr(ESTree::ObjectExpressionNode *Expr) {
ESTree::PropertyNode *protoProperty = nullptr;

uint32_t numComputed = 0;
bool hasSpread = false;
bool hasAccessor = false;
bool hasDuplicateProperty = false;

for (auto &P : Expr->_properties) {
if (llvh::isa<ESTree::SpreadElementNode>(&P)) {
hasSpread = true;
continue;
}

Expand Down Expand Up @@ -929,10 +925,8 @@ Value *ESTreeIRGen::genObjectExpr(ESTree::ObjectExpressionNode *Expr) {
PropertyValue *propValue = &propMap[propName];
if (prop->_kind->str() == "get") {
propValue->setGetter(cast<ESTree::FunctionExpressionNode>(prop->_value));
hasAccessor = true;
} else if (prop->_kind->str() == "set") {
propValue->setSetter(cast<ESTree::FunctionExpressionNode>(prop->_value));
hasAccessor = true;
} else {
assert(prop->_kind->str() == "init" && "invalid PropertyNode kind");
// We record the propValue if this is a regular property
Expand All @@ -942,7 +936,6 @@ Value *ESTreeIRGen::genObjectExpr(ESTree::ObjectExpressionNode *Expr) {
std::string key = (prop->_kind->str() + propName).str();
auto iterAndSuccess = firstLocMap.try_emplace(key, prop->getSourceRange());
if (!iterAndSuccess.second) {
hasDuplicateProperty = true;
Builder.getModule()->getContext().getSourceErrorManager().warning(
prop->getSourceRange(),
Twine("the property \"") + propName +
Expand All @@ -953,38 +946,6 @@ Value *ESTreeIRGen::genObjectExpr(ESTree::ObjectExpressionNode *Expr) {
}
}

// Heuristically determine if we emit AllocObjectLiteral.
// We do so if there is no computed key, no __proto__, no spread element
// node, no duplicate properties, no accessors, and object literal is not
// empty.
if (numComputed == 0 && !protoProperty && !hasSpread &&
!hasDuplicateProperty && !hasAccessor && propMap.size()) {
AllocObjectLiteralInst::ObjectPropertyMap objPropMap;
// It is safe to assume that there is no computed keys, and
// no __proto__.
for (auto &P : Expr->_properties) {
auto *prop = cast<ESTree::PropertyNode>(&P);
assert(
!prop->_computed &&
"Cannot handle computed key in AllocObjectLiteral");

// We are reusing the storage, so make sure it is cleared at every
// iteration.
stringStorage.clear();

llvh::StringRef keyStr = propertyKeyAsString(stringStorage, prop->_key);
auto *Key = Builder.getLiteralString(keyStr);
assert(
propMap[keyStr].valueNode == prop->_value &&
"Should only have one value for each property.");
auto value =
genExpression(prop->_value, Builder.createIdentifier(keyStr));
objPropMap.push_back(std::pair<LiteralString *, Value *>(Key, value));
}

return Builder.createAllocObjectLiteralInst(objPropMap);
}

/// Attempt to determine whether we can directly use the value of the
/// __proto__ property as a parent when creating the object for an object
/// initializer, instead of setting it later with
Expand Down
18 changes: 9 additions & 9 deletions test/BCGen/HBC/callbuiltin.js
Original file line number Diff line number Diff line change
Expand Up @@ -65,15 +65,15 @@ print(foo({a: 10, b: 20, lastKey:30, 5:6}))
// CHKRA:function shadows#0#1()#2 : undefined
// CHKRA-NEXT:S{shadows#0#1()#2} = []
// CHKRA-NEXT:%BB0:
// CHKRA-NEXT: %0 = HBCGetGlobalObjectInst
// CHKRA-NEXT: %1 = TryLoadGlobalPropertyInst %0 : object, "print" : string
// CHKRA-NEXT: %2 = AllocObjectInst 1 : number, empty
// CHKRA-NEXT: %3 = StoreNewOwnPropertyInst %1, %2 : object, "keys" : string, true : boolean
// CHKRA-NEXT: %4 = LoadPropertyInst %2 : object, "keys" : string
// CHKRA-NEXT: %0 = AllocObjectInst 1 : number, empty
// CHKRA-NEXT: %1 = HBCGetGlobalObjectInst
// CHKRA-NEXT: %2 = TryLoadGlobalPropertyInst %1 : object, "print" : string
// CHKRA-NEXT: %3 = StoreNewOwnPropertyInst %2, %0 : object, "keys" : string, true : boolean
// CHKRA-NEXT: %4 = LoadPropertyInst %0 : object, "keys" : string
// CHKRA-NEXT: %5 = HBCLoadConstInst "evil" : string
// CHKRA-NEXT: %6 = ImplicitMovInst %2 : object
// CHKRA-NEXT: %6 = ImplicitMovInst %0 : object
// CHKRA-NEXT: %7 = ImplicitMovInst %5 : string
// CHKRA-NEXT: %8 = HBCCallNInst %4, undefined : undefined, %2 : object, %5 : string
// CHKRA-NEXT: %8 = HBCCallNInst %4, undefined : undefined, %0 : object, %5 : string
// CHKRA-NEXT: %9 = HBCLoadConstInst undefined : undefined
// CHKRA-NEXT: %10 = ReturnInst %9 : undefined
// CHKRA-NEXT:function_end
Expand Down Expand Up @@ -162,9 +162,9 @@ print(foo({a: 10, b: 20, lastKey:30, 5:6}))

// CHKBC:Function<shadows>(1 params, 11 registers, 0 symbols):
// CHKBC-NEXT:Offset in debug table: source 0x0034, scope 0x0000, textified callees 0x0000
// CHKBC-NEXT: NewObject r2
// CHKBC-NEXT: GetGlobalObject r0
// CHKBC-NEXT: TryGetById r0, r0, 1, "print"
// CHKBC-NEXT: NewObject r2
// CHKBC-NEXT: PutNewOwnByIdShort r2, r0, "keys"
// CHKBC-NEXT: GetByIdShort r1, r2, 2, "keys"
// CHKBC-NEXT: LoadConstString r0, "evil"
Expand Down Expand Up @@ -200,7 +200,7 @@ print(foo({a: 10, b: 20, lastKey:30, 5:6}))
// CHKBC-NEXT: 0x0027 function idx 1, starts at line 12 col 1
// CHKBC-NEXT: bc 3: line 13 col 23 scope offset 0x0000 env none
// CHKBC-NEXT: 0x0034 function idx 2, starts at line 17 col 1
// CHKBC-NEXT: bc 2: line 18 col 25 scope offset 0x0000 env none
// CHKBC-NEXT: bc 4: line 18 col 25 scope offset 0x0000 env none
// CHKBC-NEXT: bc 10: line 18 col 18 scope offset 0x0000 env none
// CHKBC-NEXT: bc 14: line 19 col 16 scope offset 0x0000 env none
// CHKBC-NEXT: bc 23: line 19 col 16 scope offset 0x0000 env none
Expand Down
11 changes: 7 additions & 4 deletions test/IRGen/__proto__-shorthand.js
Original file line number Diff line number Diff line change
Expand Up @@ -64,11 +64,14 @@ function protoShorthandMix2(func) {
// CHECK-NEXT: %1 = StoreFrameInst %func, [func#2], %0
// CHECK-NEXT: %2 = StoreFrameInst undefined : undefined, [__proto__#2], %0
// CHECK-NEXT: %3 = StoreFrameInst 42 : number, [__proto__#2], %0
// CHECK-NEXT: %4 = LoadFrameInst [__proto__#2], %0
// CHECK-NEXT: %5 = AllocObjectLiteralInst "__proto__" : string, %4, "a" : string, 2 : number, "b" : string, 3 : number
// CHECK-NEXT: %6 = ReturnInst %5 : object
// CHECK-NEXT: %4 = AllocObjectInst 3 : number, empty
// CHECK-NEXT: %5 = LoadFrameInst [__proto__#2], %0
// CHECK-NEXT: %6 = StoreNewOwnPropertyInst %5, %4 : object, "__proto__" : string, true : boolean
// CHECK-NEXT: %7 = StoreNewOwnPropertyInst 2 : number, %4 : object, "a" : string, true : boolean
// CHECK-NEXT: %8 = StoreNewOwnPropertyInst 3 : number, %4 : object, "b" : string, true : boolean
// CHECK-NEXT: %9 = ReturnInst %4 : object
// CHECK-NEXT:%BB1:
// CHECK-NEXT: %7 = ReturnInst undefined : undefined
// CHECK-NEXT: %10 = ReturnInst undefined : undefined
// CHECK-NEXT:function_end

// CHECK:function protoShorthandDup#0#1(func)#3
Expand Down
24 changes: 13 additions & 11 deletions test/IRGen/array_object.js
Original file line number Diff line number Diff line change
Expand Up @@ -40,16 +40,18 @@ function foo(param) {
// CHECK-NEXT: %1 = StoreFrameInst %param, [param#2], %0
// CHECK-NEXT: %2 = StoreFrameInst undefined : undefined, [obj#2], %0
// CHECK-NEXT: %3 = StoreFrameInst undefined : undefined, [foo#2], %0
// CHECK-NEXT: %4 = LoadFrameInst [param#2], %0
// CHECK-NEXT: %5 = AllocObjectLiteralInst "1" : string, 2 : number, "key" : string, %4
// CHECK-NEXT: %6 = StoreFrameInst %5 : object, [obj#2], %0
// CHECK-NEXT: %7 = AllocArrayInst 4 : number, 1 : number, 2 : number, 3 : number, 4 : number
// CHECK-NEXT: %8 = StoreFrameInst %7 : object, [foo#2], %0
// CHECK-NEXT: %9 = LoadFrameInst [obj#2], %0
// CHECK-NEXT: %10 = LoadFrameInst [foo#2], %0
// CHECK-NEXT: %11 = StorePropertyInst %10, %9, "field" : string
// CHECK-NEXT: %4 = AllocObjectInst 2 : number, empty
// CHECK-NEXT: %5 = StoreNewOwnPropertyInst 2 : number, %4 : object, "1" : string, true : boolean
// CHECK-NEXT: %6 = LoadFrameInst [param#2], %0
// CHECK-NEXT: %7 = StoreNewOwnPropertyInst %6, %4 : object, "key" : string, true : boolean
// CHECK-NEXT: %8 = StoreFrameInst %4 : object, [obj#2], %0
// CHECK-NEXT: %9 = AllocArrayInst 4 : number, 1 : number, 2 : number, 3 : number, 4 : number
// CHECK-NEXT: %10 = StoreFrameInst %9 : object, [foo#2], %0
// CHECK-NEXT: %11 = LoadFrameInst [obj#2], %0
// CHECK-NEXT: %12 = LoadFrameInst [foo#2], %0
// CHECK-NEXT: %13 = LoadFrameInst [obj#2], %0
// CHECK-NEXT: %14 = StorePropertyInst %13, %12, 5 : number
// CHECK-NEXT: %15 = ReturnInst undefined : undefined
// CHECK-NEXT: %13 = StorePropertyInst %12, %11, "field" : string
// CHECK-NEXT: %14 = LoadFrameInst [foo#2], %0
// CHECK-NEXT: %15 = LoadFrameInst [obj#2], %0
// CHECK-NEXT: %16 = StorePropertyInst %15, %14, 5 : number
// CHECK-NEXT: %17 = ReturnInst undefined : undefined
// CHECK-NEXT:function_end
19 changes: 10 additions & 9 deletions test/IRGen/es6/tagged-template.js
Original file line number Diff line number Diff line change
Expand Up @@ -169,16 +169,17 @@ function helloWorld() {
// CHECK-NEXT:%BB0:
// CHECK-NEXT: %0 = CreateScopeInst %S{memberExpr#0#1()#8}
// CHECK-NEXT: %1 = StoreFrameInst undefined : undefined, [obj#8], %0
// CHECK-NEXT: %2 = LoadPropertyInst globalObject : object, "dummy" : string
// CHECK-NEXT: %3 = AllocObjectLiteralInst "func" : string, %2
// CHECK-NEXT: %4 = StoreFrameInst %3 : object, [obj#8], %0
// CHECK-NEXT: %5 = CallBuiltinInst [HermesBuiltin.getTemplateObject] : number, undefined : undefined, undefined : undefined, 5 : number, true : boolean, "hello world!" : string
// CHECK-NEXT: %6 = LoadFrameInst [obj#8], %0
// CHECK-NEXT: %7 = LoadPropertyInst %6, "func" : string
// CHECK-NEXT: %8 = CallInst %7, undefined : undefined, %6, %5
// CHECK-NEXT: %9 = ReturnInst %8
// CHECK-NEXT: %2 = AllocObjectInst 1 : number, empty
// CHECK-NEXT: %3 = LoadPropertyInst globalObject : object, "dummy" : string
// CHECK-NEXT: %4 = StoreNewOwnPropertyInst %3, %2 : object, "func" : string, true : boolean
// CHECK-NEXT: %5 = StoreFrameInst %2 : object, [obj#8], %0
// CHECK-NEXT: %6 = CallBuiltinInst [HermesBuiltin.getTemplateObject] : number, undefined : undefined, undefined : undefined, 5 : number, true : boolean, "hello world!" : string
// CHECK-NEXT: %7 = LoadFrameInst [obj#8], %0
// CHECK-NEXT: %8 = LoadPropertyInst %7, "func" : string
// CHECK-NEXT: %9 = CallInst %8, undefined : undefined, %7, %6
// CHECK-NEXT: %10 = ReturnInst %9
// CHECK-NEXT:%BB1:
// CHECK-NEXT: %10 = ReturnInst undefined : undefined
// CHECK-NEXT: %11 = ReturnInst undefined : undefined
// CHECK-NEXT:function_end

// CHECK:function callExpr#0#1()#9
Expand Down
2 changes: 1 addition & 1 deletion test/IRGen/hbc_object_literals-lowering.js
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,7 @@ function accessorObjectLiteral(func) {
// IRGEN-NEXT:%BB0:
// IRGEN-NEXT: %0 = HBCAllocObjectFromBufferInst 4 : number, "a" : string, 10 : number, "c" : string, "hello" : string, "d" : string, null : null
// IRGEN-NEXT: %1 = HBCAllocObjectFromBufferInst 2 : number, 1 : number, 100 : number, 2 : number, 200 : number
// IRGEN-NEXT: %2 = StoreOwnPropertyInst %1 : object, %0 : object, 42 : number, true : boolean
// IRGEN-NEXT: %2 = StoreNewOwnPropertyInst %1 : object, %0 : object, 42 : number, true : boolean
// IRGEN-NEXT: %3 = ReturnInst %0 : object
// IRGEN-NEXT:function_end

Expand Down
86 changes: 43 additions & 43 deletions test/IRGen/hbc_object_literals.js
Original file line number Diff line number Diff line change
Expand Up @@ -73,41 +73,41 @@ var obj4 = {
// IRGEN-NEXT:S{global#0()#1} = []
// IRGEN-NEXT:%BB0:
// IRGEN-NEXT: %0 = HBCAllocObjectFromBufferInst 7 : number, "a" : string, "hello" : string, "b" : string, 1 : number, "c" : string, null : null, "d" : string, null : null, "e" : string, true : boolean, "f" : string, null : null, "g" : string, 2 : number
// IRGEN-NEXT: %1 = HBCLoadConstInst undefined : undefined
// IRGEN-NEXT: %2 = StorePropertyInst %1 : undefined, %0 : object, "d" : string
// IRGEN-NEXT: %3 = HBCCreateEnvironmentInst %S{global#0()#1}
// IRGEN-NEXT: %4 = HBCCreateFunctionInst %f#0#1()#2 : undefined, %3
// IRGEN-NEXT: %5 = StorePropertyInst %4 : closure, %0 : object, "f" : string
// IRGEN-NEXT: %6 = HBCGetGlobalObjectInst
// IRGEN-NEXT: %7 = StorePropertyInst %0 : object, %6 : object, "obj1" : string
// IRGEN-NEXT: %8 = AllocObjectInst 18 : number, empty
// IRGEN-NEXT: %9 = StoreNewOwnPropertyInst %1 : undefined, %8 : object, "a" : string, true : boolean
// IRGEN-NEXT: %10 = StoreNewOwnPropertyInst %1 : undefined, %8 : object, "b" : string, true : boolean
// IRGEN-NEXT: %11 = StoreNewOwnPropertyInst %1 : undefined, %8 : object, "c" : string, true : boolean
// IRGEN-NEXT: %12 = StoreNewOwnPropertyInst %1 : undefined, %8 : object, "d" : string, true : boolean
// IRGEN-NEXT: %13 = StoreNewOwnPropertyInst %1 : undefined, %8 : object, "e" : string, true : boolean
// IRGEN-NEXT: %14 = StoreNewOwnPropertyInst %1 : undefined, %8 : object, "r" : string, true : boolean
// IRGEN-NEXT: %15 = HBCLoadConstInst 1 : number
// IRGEN-NEXT: %16 = StoreNewOwnPropertyInst %15 : number, %8 : object, "f" : string, true : boolean
// IRGEN-NEXT: %17 = StoreNewOwnPropertyInst %15 : number, %8 : object, "g" : string, true : boolean
// IRGEN-NEXT: %18 = StoreNewOwnPropertyInst %15 : number, %8 : object, "h" : string, true : boolean
// IRGEN-NEXT: %19 = StoreNewOwnPropertyInst %15 : number, %8 : object, "i" : string, true : boolean
// IRGEN-NEXT: %20 = StoreNewOwnPropertyInst %15 : number, %8 : object, "j" : string, true : boolean
// IRGEN-NEXT: %21 = StoreNewOwnPropertyInst %15 : number, %8 : object, "k" : string, true : boolean
// IRGEN-NEXT: %22 = StoreNewOwnPropertyInst %15 : number, %8 : object, "l" : string, true : boolean
// IRGEN-NEXT: %23 = StoreNewOwnPropertyInst %15 : number, %8 : object, "m" : string, true : boolean
// IRGEN-NEXT: %24 = StoreNewOwnPropertyInst %15 : number, %8 : object, "n" : string, true : boolean
// IRGEN-NEXT: %25 = StoreNewOwnPropertyInst %15 : number, %8 : object, "o" : string, true : boolean
// IRGEN-NEXT: %26 = StoreNewOwnPropertyInst %15 : number, %8 : object, "p" : string, true : boolean
// IRGEN-NEXT: %27 = StoreNewOwnPropertyInst %15 : number, %8 : object, "q" : string, true : boolean
// IRGEN-NEXT: %28 = StorePropertyInst %8 : object, %6 : object, "obj2" : string
// IRGEN-NEXT: %1 = HBCLoadConstInst 1 : number
// IRGEN-NEXT: %2 = HBCLoadConstInst undefined : undefined
// IRGEN-NEXT: %3 = StorePropertyInst %2 : undefined, %0 : object, "d" : string
// IRGEN-NEXT: %4 = HBCCreateEnvironmentInst %S{global#0()#1}
// IRGEN-NEXT: %5 = HBCCreateFunctionInst %f#0#1()#2 : undefined, %4
// IRGEN-NEXT: %6 = StorePropertyInst %5 : closure, %0 : object, "f" : string
// IRGEN-NEXT: %7 = HBCGetGlobalObjectInst
// IRGEN-NEXT: %8 = StorePropertyInst %0 : object, %7 : object, "obj1" : string
// IRGEN-NEXT: %9 = AllocObjectInst 18 : number, empty
// IRGEN-NEXT: %10 = StoreNewOwnPropertyInst %2 : undefined, %9 : object, "a" : string, true : boolean
// IRGEN-NEXT: %11 = StoreNewOwnPropertyInst %2 : undefined, %9 : object, "b" : string, true : boolean
// IRGEN-NEXT: %12 = StoreNewOwnPropertyInst %2 : undefined, %9 : object, "c" : string, true : boolean
// IRGEN-NEXT: %13 = StoreNewOwnPropertyInst %2 : undefined, %9 : object, "d" : string, true : boolean
// IRGEN-NEXT: %14 = StoreNewOwnPropertyInst %2 : undefined, %9 : object, "e" : string, true : boolean
// IRGEN-NEXT: %15 = StoreNewOwnPropertyInst %2 : undefined, %9 : object, "r" : string, true : boolean
// IRGEN-NEXT: %16 = StoreNewOwnPropertyInst %1 : number, %9 : object, "f" : string, true : boolean
// IRGEN-NEXT: %17 = StoreNewOwnPropertyInst %1 : number, %9 : object, "g" : string, true : boolean
// IRGEN-NEXT: %18 = StoreNewOwnPropertyInst %1 : number, %9 : object, "h" : string, true : boolean
// IRGEN-NEXT: %19 = StoreNewOwnPropertyInst %1 : number, %9 : object, "i" : string, true : boolean
// IRGEN-NEXT: %20 = StoreNewOwnPropertyInst %1 : number, %9 : object, "j" : string, true : boolean
// IRGEN-NEXT: %21 = StoreNewOwnPropertyInst %1 : number, %9 : object, "k" : string, true : boolean
// IRGEN-NEXT: %22 = StoreNewOwnPropertyInst %1 : number, %9 : object, "l" : string, true : boolean
// IRGEN-NEXT: %23 = StoreNewOwnPropertyInst %1 : number, %9 : object, "m" : string, true : boolean
// IRGEN-NEXT: %24 = StoreNewOwnPropertyInst %1 : number, %9 : object, "n" : string, true : boolean
// IRGEN-NEXT: %25 = StoreNewOwnPropertyInst %1 : number, %9 : object, "o" : string, true : boolean
// IRGEN-NEXT: %26 = StoreNewOwnPropertyInst %1 : number, %9 : object, "p" : string, true : boolean
// IRGEN-NEXT: %27 = StoreNewOwnPropertyInst %1 : number, %9 : object, "q" : string, true : boolean
// IRGEN-NEXT: %28 = StorePropertyInst %9 : object, %7 : object, "obj2" : string
// IRGEN-NEXT: %29 = HBCAllocObjectFromBufferInst 13 : number, "f" : string, 1 : number, "g" : string, 1 : number, "h" : string, 1 : number, "i" : string, 1 : number, "j" : string, 1 : number, "k" : string, 1 : number, "l" : string, 1 : number, "m" : string, 1 : number, "n" : string, 1 : number, "o" : string, 1 : number, "p" : string, 1 : number, "q" : string, 1 : number
// IRGEN-NEXT: %30 = StoreOwnPropertyInst %1 : undefined, %29 : object, 1 : number, true : boolean
// IRGEN-NEXT: %31 = StorePropertyInst %29 : object, %6 : object, "obj3" : string
// IRGEN-NEXT: %30 = StoreNewOwnPropertyInst %2 : undefined, %29 : object, 1 : number, true : boolean
// IRGEN-NEXT: %31 = StorePropertyInst %29 : object, %7 : object, "obj3" : string
// IRGEN-NEXT: %32 = HBCAllocObjectFromBufferInst 13 : number, "f" : string, 1 : number, "g" : string, 1 : number, "h" : string, 1 : number, "i" : string, 1 : number, "j" : string, 1 : number, "k" : string, 1 : number, "l" : string, 1 : number, "m" : string, 1 : number, "n" : string, 1 : number, "o" : string, 1 : number, "p" : string, 1 : number, "q" : string, 1 : number
// IRGEN-NEXT: %33 = StoreOwnPropertyInst %1 : undefined, %32 : object, 1 : number, true : boolean
// IRGEN-NEXT: %34 = StorePropertyInst %32 : object, %6 : object, "obj4" : string
// IRGEN-NEXT: %35 = ReturnInst %1 : undefined
// IRGEN-NEXT: %33 = StoreNewOwnPropertyInst %2 : undefined, %32 : object, 1 : number, true : boolean
// IRGEN-NEXT: %34 = StorePropertyInst %32 : object, %7 : object, "obj4" : string
// IRGEN-NEXT: %35 = ReturnInst %2 : undefined
// IRGEN-NEXT:function_end

// IRGEN:function f#0#1()#2 : undefined
Expand Down Expand Up @@ -206,6 +206,7 @@ var obj4 = {
// BCGEN-NEXT: DeclareGlobalVar "obj3"
// BCGEN-NEXT: DeclareGlobalVar "obj4"
// BCGEN-NEXT: NewObjectWithBuffer r1, 7, 7, 0, 0
// BCGEN-NEXT: LoadConstUInt8 r3, 1
// BCGEN-NEXT: LoadConstUndefined r0
// BCGEN-NEXT: PutById r1, r0, 1, "d"
// BCGEN-NEXT: CreateEnvironment r2
Expand All @@ -220,7 +221,6 @@ var obj4 = {
// BCGEN-NEXT: PutNewOwnByIdShort r1, r0, "d"
// BCGEN-NEXT: PutNewOwnByIdShort r1, r0, "e"
// BCGEN-NEXT: PutNewOwnByIdShort r1, r0, "r"
// BCGEN-NEXT: LoadConstUInt8 r3, 1
// BCGEN-NEXT: PutNewOwnByIdShort r1, r3, "f"
// BCGEN-NEXT: PutNewOwnByIdShort r1, r3, "g"
// BCGEN-NEXT: PutNewOwnByIdShort r1, r3, "h"
Expand Down Expand Up @@ -254,15 +254,15 @@ var obj4 = {

// BCGEN:Debug source table:
// BCGEN-NEXT: 0x0000 function idx 0, starts at line 11 col 1
// BCGEN-NEXT: bc 32: line 11 col 12 scope offset 0x0000 env r2
// BCGEN-NEXT: bc 45: line 11 col 12 scope offset 0x0000 env r2
// BCGEN-NEXT: bc 53: line 11 col 10 scope offset 0x0000 env r1
// BCGEN-NEXT: bc 61: line 15 col 12 scope offset 0x0000 env r3
// BCGEN-NEXT: bc 65: line 15 col 12 scope offset 0x0000 env r3
// BCGEN-NEXT: bc 69: line 15 col 12 scope offset 0x0000 env r3
// BCGEN-NEXT: bc 73: line 15 col 12 scope offset 0x0000 env r3
// BCGEN-NEXT: bc 77: line 15 col 12 scope offset 0x0000 env r3
// BCGEN-NEXT: bc 81: line 15 col 12 scope offset 0x0000 env r3
// BCGEN-NEXT: bc 35: line 11 col 12 scope offset 0x0000 env r2
// BCGEN-NEXT: bc 48: line 11 col 12 scope offset 0x0000 env r2
// BCGEN-NEXT: bc 56: line 11 col 10 scope offset 0x0000 env r1
// BCGEN-NEXT: bc 64: line 15 col 12 scope offset 0x0000 env r4
// BCGEN-NEXT: bc 68: line 15 col 12 scope offset 0x0000 env r4
// BCGEN-NEXT: bc 72: line 15 col 12 scope offset 0x0000 env r4
// BCGEN-NEXT: bc 76: line 15 col 12 scope offset 0x0000 env r4
// BCGEN-NEXT: bc 80: line 15 col 12 scope offset 0x0000 env r4
// BCGEN-NEXT: bc 84: line 15 col 12 scope offset 0x0000 env r4
// BCGEN-NEXT: bc 88: line 15 col 12 scope offset 0x0000 env r4
// BCGEN-NEXT: bc 92: line 15 col 12 scope offset 0x0000 env r4
// BCGEN-NEXT: bc 96: line 15 col 12 scope offset 0x0000 env r4
Expand Down
Loading

0 comments on commit bbe7966

Please sign in to comment.