Skip to content

Share SimpleTypeHandler types on function objects. - #4748

Merged
chakrabot merged 1 commit into
chakra-core:masterfrom
pleath:sharesimpletypes
Mar 14, 2018
Merged

Share SimpleTypeHandler types on function objects. #4748
chakrabot merged 1 commit into
chakra-core:masterfrom
pleath:sharesimpletypes

Conversation

@pleath

@pleath pleath commented Feb 27, 2018

Copy link
Copy Markdown
Contributor

Currently when we transition from DeferredTypeHandler to SimpleTypeHandler on first access to a function object's properties, we don't share the new type we create. Track an undeferred type along with the deferredPrototypeType on FunctionProxy and re-use it whenever possible for multiple instances of the same function. (This is a first step in broader sharing of function object types.)

typeHandler->SetInstanceTypeHandler(instance);
if (functionProxy && typeHandler->GetMayBecomeShared())
{
functionProxy->SetUndeferredFunctionType(ScriptFunction::FromVar(instance)->GetScriptFunctionType());

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ScriptFunction::FromVar(instance) [](start = 57, length = 33)

How do we know that instance is a ScriptFunction? (Not saying it's wrong, I'm just curious.)

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ScriptFunction's are the only JavascriptFunction's with non-null FunctionProxy.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could use ScriptFunction::UnsafeFromVar.


In reply to: 171357540 [](ancestors = 171357540)

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done. Thanks.

@sethbrenith sethbrenith left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

:shipit:


friend class JavascriptArray; // for xplat offsetof field access
friend class JavascriptNativeArray; // for xplat offsetof field access
friend class JavascriptOperators; // for ReplaceType

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks like the xplat builds are failing because JavascriptOperators is trying to access a protected member function DynamicObject::BoxStackInstance, so this friend wasn't just for ReplaceType

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

True. So the different compilers are enforcing different rules?

@pleath
pleath force-pushed the sharesimpletypes branch from 77e351e to 0b25d43 Compare March 1, 2018 19:20

this->functionInfo = newFunctionInfo->GetFunctionInfo();

if (type->GetIsShared())

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@curtisman If we're allowing shared types on function objects with non-default state, then we can't revert to the deferredPrototypeType here. I think we want to go ahead and change the entry point on the current shared type. Is there a reason we can't?

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My guess here is because originally, we would have swiitch out the functionInfo reference with the the undeferred function body in the scriptFunction. So undeferring would only be fully done for one script function but not the other instance. (Thus can't change the shared entry point)

Since you have changed it that the switching is done in the function proxy, it's probably OK to do.

But I wonder whether we need the line above any more as well. Shouldn't this->functionInfo should equals to newFunctionInfo->GetFunctionInfo() always?


In reply to: 171666256 [](ancestors = 171666256)

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think you're right. I've replaced the copy with an assert. I think the only other thing we need to do is to copy the deferredPrototypeType and undeferredFunctionType pointers on un-defer/re-defer now that we don't make new types for the new FunctionProxy.

if (undeferredFunctionType)
{
Assert(undeferredFunctionType->GetIsShared());
instance->ReplaceType(undeferredFunctionType);

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should assert that undeferredFunctionType->GetTypeHandler() == typeHandler?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think we can do that. JavascriptLibrary::ConvertFunction calls this function with the shared SimpleTypeHandler from the library. That won't match the PathTypeHandler pointed to by undeferredFunctionType if we've done that conversion already.

Comment thread lib/Runtime/Base/FunctionBody.cpp Outdated
{
func(this->deferredPrototypeType);
}
if (this->undeferredFunctionType)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since this is a path type, we should be able to enumerate those by walking that tree, instead of registering it to the functionObjectTypeList.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This change isn't making the undeferredFunctionType into a path type. It's still a simple type. In any case, it will get registered as a function object type when we create it, so we probably don't need these lines.

@pleath
pleath force-pushed the sharesimpletypes branch from 0b25d43 to 77bb304 Compare March 2, 2018 20:42
@pleath

pleath commented Mar 2, 2018

Copy link
Copy Markdown
Contributor Author

@dotnet-bot test OSX static_osx_osx_debug

@pleath
pleath force-pushed the sharesimpletypes branch from 77bb304 to 45ffb1b Compare March 7, 2018 18:57
DynamicObject *protoObject = javascriptLibrary->CreateConstructorPrototypeObject(function);
if (scriptFunction && scriptFunction->GetFunctionInfo()->IsClassConstructor())
{
function->SetPropertyWithAttributes(PropertyIds::prototype, protoObject, PropertyNone, nullptr);

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

SetPropertyWithAttributes [](start = 26, length = 25)

Unless I'm misreading something, isn't this changing the semantics? Previously we were only setting writable to false, now we'll be setting enumerable and configurable to false as well, no?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We've always set the attributes this way for the prototype property of a class constructor. (See the class member defaults.)

@pleath
pleath force-pushed the sharesimpletypes branch from 45ffb1b to f77daf6 Compare March 10, 2018 03:04
@rajatd

rajatd commented Mar 12, 2018

Copy link
Copy Markdown
Contributor

:shipit:

@pleath
pleath force-pushed the sharesimpletypes branch 2 times, most recently from 88f006e to 2ad5e2b Compare March 13, 2018 00:36
…transition from DeferredTypeHandler to SimpleTypeHandler on first access to a function object's properties, we don't share the new type we create. Track an undeferred type along with the deferredPrototypeType on FunctionProxy and re-use it whenever possible for multiple instances of the same function. (This is a first step in broader sharing of function object types.)
@pleath
pleath force-pushed the sharesimpletypes branch from 2ad5e2b to b748a70 Compare March 13, 2018 23:08
@chakrabot
chakrabot merged commit b748a70 into chakra-core:master Mar 14, 2018
chakrabot pushed a commit that referenced this pull request Mar 14, 2018
Merge pull request #4748 from pleath:sharesimpletypes

Currently when we transition from DeferredTypeHandler to SimpleTypeHandler on first access to a function object's properties, we don't share the new type we create. Track an undeferred type along with the deferredPrototypeType on FunctionProxy and re-use it whenever possible for multiple instances of the same function. (This is a first step in broader sharing of function object types.)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

7 participants