Changeset 244300 in webkit


Ignore:
Timestamp:
Apr 15, 2019 3:23:38 PM (5 years ago)
Author:
Tadeu Zagallo
Message:

Bytecode cache should not encode the SourceProvider for UnlinkedFunctionExecutable's classSource
https://bugs.webkit.org/show_bug.cgi?id=196878

Reviewed by Saam Barati.

Every time we encode an (Unlinked)SourceCode, we encode its SourceProvider,
including the full source if it's a StringSourceProvider. This wasn't an issue,
since the SourceCode contains a RefPtr to the SourceProvider, and the Encoder
would avoid encoding the provider multiple times. With the addition of the
incremental cache, each UnlinkedFunctionCodeBlock is encoded in isolation, which
means we can no longer deduplicate it and the full program text was being encoded
multiple times in the cache.
As a work around, this patch adds a custom cached type for encoding the SourceCode
without its provider, and later injects the SourceProvider through the Decoder.

  • parser/SourceCode.h:
  • parser/UnlinkedSourceCode.h:

(JSC::UnlinkedSourceCode::provider const):

  • runtime/CachedTypes.cpp:

(JSC::Decoder::Decoder):
(JSC::Decoder::create):
(JSC::Decoder::provider const):
(JSC::CachedSourceCodeWithoutProvider::encode):
(JSC::CachedSourceCodeWithoutProvider::decode const):
(JSC::decodeCodeBlockImpl):

  • runtime/CachedTypes.h:
Location:
trunk/Source/JavaScriptCore
Files:
5 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/JavaScriptCore/ChangeLog

    r244298 r244300  
     12019-04-15  Tadeu Zagallo  <tzagallo@apple.com>
     2
     3        Bytecode cache should not encode the SourceProvider for UnlinkedFunctionExecutable's classSource
     4        https://bugs.webkit.org/show_bug.cgi?id=196878
     5
     6        Reviewed by Saam Barati.
     7
     8        Every time we encode an (Unlinked)SourceCode, we encode its SourceProvider,
     9        including the full source if it's a StringSourceProvider. This wasn't an issue,
     10        since the SourceCode contains a RefPtr to the SourceProvider, and the Encoder
     11        would avoid encoding the provider multiple times. With the addition of the
     12        incremental cache, each UnlinkedFunctionCodeBlock is encoded in isolation, which
     13        means we can no longer deduplicate it and the full program text was being encoded
     14        multiple times in the cache.
     15        As a work around, this patch adds a custom cached type for encoding the SourceCode
     16        without its provider, and later injects the SourceProvider through the Decoder.
     17
     18        * parser/SourceCode.h:
     19        * parser/UnlinkedSourceCode.h:
     20        (JSC::UnlinkedSourceCode::provider const):
     21        * runtime/CachedTypes.cpp:
     22        (JSC::Decoder::Decoder):
     23        (JSC::Decoder::create):
     24        (JSC::Decoder::provider const):
     25        (JSC::CachedSourceCodeWithoutProvider::encode):
     26        (JSC::CachedSourceCodeWithoutProvider::decode const):
     27        (JSC::decodeCodeBlockImpl):
     28        * runtime/CachedTypes.h:
     29
    1302019-04-15  Robin Morisset  <rmorisset@apple.com>
    231
  • trunk/Source/JavaScriptCore/parser/SourceCode.h

    r240255 r244300  
    3535    class SourceCode : public UnlinkedSourceCode {
    3636        friend class CachedSourceCode;
     37        friend class CachedSourceCodeWithoutProvider;
    3738
    3839    public:
  • trunk/Source/JavaScriptCore/parser/UnlinkedSourceCode.h

    r243163 r244300  
    3737        template<typename SourceType>
    3838        friend class CachedUnlinkedSourceCodeShape;
     39        friend class CachedSourceCodeWithoutProvider;
    3940
    4041    public:
     
    7475        bool isHashTableDeletedValue() const { return m_provider.isHashTableDeletedValue(); }
    7576
    76         const SourceProvider& provider() const
     77        SourceProvider& provider() const
    7778        {
    7879            return *m_provider;
  • trunk/Source/JavaScriptCore/runtime/CachedTypes.cpp

    r244163 r244300  
    221221};
    222222
    223 Decoder::Decoder(VM& vm, Ref<CachedBytecode> cachedBytecode)
     223Decoder::Decoder(VM& vm, Ref<CachedBytecode> cachedBytecode, RefPtr<SourceProvider> provider)
    224224    : m_vm(vm)
    225225    , m_cachedBytecode(WTFMove(cachedBytecode))
     226    , m_provider(provider)
    226227{
    227228}
     
    233234}
    234235
    235 Ref<Decoder> Decoder::create(VM& vm, Ref<CachedBytecode> cachedBytecode)
    236 {
    237     return adoptRef(*new Decoder(vm, WTFMove(cachedBytecode)));
     236Ref<Decoder> Decoder::create(VM& vm, Ref<CachedBytecode> cachedBytecode, RefPtr<SourceProvider> provider)
     237{
     238    return adoptRef(*new Decoder(vm, WTFMove(cachedBytecode), WTFMove(provider)));
    238239}
    239240
     
    293294{
    294295    m_finalizers.append(fn);
     296}
     297
     298RefPtr<SourceProvider> Decoder::provider() const
     299{
     300    return m_provider;
    295301}
    296302
     
    15481554};
    15491555
     1556class CachedSourceCodeWithoutProvider : public CachedObject<SourceCode> {
     1557public:
     1558    void encode(Encoder&, const SourceCode& sourceCode)
     1559    {
     1560        m_hasProvider = !!sourceCode.provider();
     1561        m_startOffset = sourceCode.startOffset();
     1562        m_endOffset = sourceCode.endOffset();
     1563        m_firstLine = sourceCode.firstLine().zeroBasedInt();
     1564        m_startColumn = sourceCode.startColumn().zeroBasedInt();
     1565    }
     1566
     1567    void decode(Decoder& decoder, SourceCode& sourceCode) const
     1568    {
     1569        if (m_hasProvider)
     1570            sourceCode.m_provider = decoder.provider();
     1571        sourceCode.m_startOffset = m_startOffset;
     1572        sourceCode.m_endOffset = m_endOffset;
     1573        sourceCode.m_firstLine = OrdinalNumber::fromZeroBasedInt(m_firstLine);
     1574        sourceCode.m_startColumn = OrdinalNumber::fromZeroBasedInt(m_startColumn);
     1575    }
     1576
     1577private:
     1578    bool m_hasProvider;
     1579    int m_startOffset;
     1580    int m_endOffset;
     1581    int m_firstLine;
     1582    int m_startColumn;
     1583};
     1584
    15501585class CachedFunctionExecutableRareData : public CachedObject<UnlinkedFunctionExecutable::RareData> {
    15511586public:
     
    15661601
    15671602private:
    1568     CachedSourceCode m_classSource;
     1603    CachedSourceCodeWithoutProvider m_classSource;
    15691604    CachedCompactVariableMapHandle m_parentScopeTDZVariables;
    15701605};
     
    22982333{
    22992334    const auto* cachedEntry = bitwise_cast<const GenericCacheEntry*>(cachedBytecode->data());
    2300     Ref<Decoder> decoder = Decoder::create(vm, WTFMove(cachedBytecode));
     2335    Ref<Decoder> decoder = Decoder::create(vm, WTFMove(cachedBytecode), &key.source().provider());
    23012336    std::pair<SourceCodeKey, UnlinkedCodeBlock*> entry;
    23022337    {
  • trunk/Source/JavaScriptCore/runtime/CachedTypes.h

    r244143 r244300  
    7878
    7979public:
    80     static Ref<Decoder> create(VM&, Ref<CachedBytecode>);
     80    static Ref<Decoder> create(VM&, Ref<CachedBytecode>, RefPtr<SourceProvider> = nullptr);
    8181
    8282    ~Decoder();
     
    9292    void setHandleForEnvironment(CompactVariableEnvironment*, const CompactVariableMap::Handle&);
    9393    void addLeafExecutable(const UnlinkedFunctionExecutable*, ptrdiff_t);
     94    RefPtr<SourceProvider> provider() const;
    9495
    9596    template<typename Functor>
     
    9798
    9899private:
    99     Decoder(VM&, Ref<CachedBytecode>);
     100    Decoder(VM&, Ref<CachedBytecode>, RefPtr<SourceProvider>);
    100101
    101102    VM& m_vm;
     
    104105    Vector<std::function<void()>> m_finalizers;
    105106    HashMap<CompactVariableEnvironment*, CompactVariableMap::Handle> m_environmentToHandleMap;
     107    RefPtr<SourceProvider> m_provider;
    106108};
    107109
Note: See TracChangeset for help on using the changeset viewer.