1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2 * vim: set ts=8 sts=2 et sw=2 tw=80:
3 * This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7 #ifndef frontend_StencilXdr_h
8 #define frontend_StencilXdr_h
10 #include "mozilla/RefPtr.h" // RefPtr
12 #include "frontend/ParserAtom.h" // ParserAtom, ParserAtomSpan
13 #include "frontend/Stencil.h" // BitIntStencil, ScopeStencil, BaseParserScopeData
14 #include "vm/Xdr.h" // XDRMode, XDRResult, XDRState
18 class ReadOnlyDecodeOptions
;
25 class ObjLiteralStencil
;
27 class SharedImmutableScriptData
;
29 class XDRStencilDecoder
;
30 class XDRStencilEncoder
;
34 struct CompilationStencil
;
35 struct ExtensibleCompilationStencil
;
36 struct SharedDataContainer
;
38 // Check that we can copy data to disk and restore it in another instance of
39 // the program in a different address space.
40 template <typename DataT
>
41 struct CanCopyDataToDisk
{
42 // Check that the object is fully packed, to save disk space.
43 #ifdef __cpp_lib_has_unique_object_representations
44 static constexpr bool unique_repr
=
45 std::has_unique_object_representations
<DataT
>();
47 static constexpr bool unique_repr
= true;
50 // Approximation which assumes that 32bits variant of the class would not
51 // have pointers if the 64bits variant does not have pointer.
52 static constexpr bool no_pointer
=
53 alignof(DataT
) < alignof(void*) || sizeof(void*) == sizeof(uint32_t);
55 static constexpr bool value
= unique_repr
&& no_pointer
;
58 // This is just a namespace class that can be used in friend declarations,
59 // so that the statically declared XDR methods within have access to the
60 // relevant struct internals.
63 template <XDRMode mode
>
64 [[nodiscard
]] static XDRResult
codeSourceUnretrievableUncompressed(
65 XDRState
<mode
>* xdr
, ScriptSource
* ss
, uint8_t sourceCharSize
,
66 uint32_t uncompressedLength
);
68 template <typename Unit
,
69 template <typename U
, SourceRetrievable CanRetrieve
> class Data
,
71 static void codeSourceRetrievable(ScriptSource
* ss
);
73 template <typename Unit
, XDRMode mode
>
74 [[nodiscard
]] static XDRResult
codeSourceUncompressedData(
75 XDRState
<mode
>* const xdr
, ScriptSource
* const ss
);
77 template <typename Unit
, XDRMode mode
>
78 [[nodiscard
]] static XDRResult
codeSourceCompressedData(
79 XDRState
<mode
>* const xdr
, ScriptSource
* const ss
);
81 template <typename Unit
, XDRMode mode
>
82 static void codeSourceRetrievableData(ScriptSource
* ss
);
84 template <XDRMode mode
>
85 [[nodiscard
]] static XDRResult
codeSourceData(XDRState
<mode
>* const xdr
,
86 ScriptSource
* const ss
);
89 template <XDRMode mode
>
90 static XDRResult
codeSource(XDRState
<mode
>* xdr
,
91 const JS::ReadOnlyDecodeOptions
* maybeOptions
,
92 RefPtr
<ScriptSource
>& source
);
94 template <XDRMode mode
>
95 static XDRResult
codeBigInt(XDRState
<mode
>* xdr
, LifoAlloc
& alloc
,
96 BigIntStencil
& stencil
);
98 template <XDRMode mode
>
99 static XDRResult
codeObjLiteral(XDRState
<mode
>* xdr
, LifoAlloc
& alloc
,
100 ObjLiteralStencil
& stencil
);
102 template <XDRMode mode
>
103 static XDRResult
codeScopeData(XDRState
<mode
>* xdr
, LifoAlloc
& alloc
,
104 ScopeStencil
& stencil
,
105 BaseParserScopeData
*& baseScopeData
);
107 template <XDRMode mode
>
108 static XDRResult
codeSharedData(XDRState
<mode
>* xdr
,
109 RefPtr
<SharedImmutableScriptData
>& sisd
);
111 template <XDRMode mode
>
112 static XDRResult
codeSharedDataContainer(XDRState
<mode
>* xdr
,
113 SharedDataContainer
& sharedData
);
115 template <XDRMode mode
>
116 static XDRResult
codeParserAtom(XDRState
<mode
>* xdr
, LifoAlloc
& alloc
,
119 template <XDRMode mode
>
120 static XDRResult
codeParserAtomSpan(XDRState
<mode
>* xdr
, LifoAlloc
& alloc
,
121 ParserAtomSpan
& parserAtomData
);
123 template <XDRMode mode
>
124 static XDRResult
codeModuleRequest(XDRState
<mode
>* xdr
,
125 StencilModuleRequest
& stencil
);
127 template <XDRMode mode
>
128 static XDRResult
codeModuleRequestVector(
129 XDRState
<mode
>* xdr
, StencilModuleMetadata::RequestVector
& vector
);
131 template <XDRMode mode
>
132 static XDRResult
codeModuleEntry(XDRState
<mode
>* xdr
,
133 StencilModuleEntry
& stencil
);
135 template <XDRMode mode
>
136 static XDRResult
codeModuleEntryVector(
137 XDRState
<mode
>* xdr
, StencilModuleMetadata::EntryVector
& vector
);
139 template <XDRMode mode
>
140 static XDRResult
codeModuleMetadata(XDRState
<mode
>* xdr
,
141 StencilModuleMetadata
& stencil
);
143 static XDRResult
checkCompilationStencil(XDRStencilEncoder
* encoder
,
144 const CompilationStencil
& stencil
);
146 static XDRResult
checkCompilationStencil(
147 const ExtensibleCompilationStencil
& stencil
);
149 template <XDRMode mode
>
150 static XDRResult
codeCompilationStencil(XDRState
<mode
>* xdr
,
151 CompilationStencil
& stencil
);
154 } /* namespace frontend */
157 * The structure of the Stencil XDR buffer is:
160 * 2. length of content
161 * 3. checksum of content
164 * b. CompilationStencil
168 * The stencil decoder accepts `range` as input.
170 * The decoded stencils are outputted to the default-initialized
171 * `stencil` parameter of `codeStencil` method.
173 * The decoded stencils borrow the input `buffer`/`range`, and the consumer
174 * has to keep the buffer alive while the decoded stencils are alive.
176 class XDRStencilDecoder
: public XDRState
<XDR_DECODE
> {
177 using Base
= XDRState
<XDR_DECODE
>;
180 XDRStencilDecoder(FrontendContext
* fc
, const JS::TranscodeRange
& range
)
182 MOZ_ASSERT(JS::IsTranscodingBytecodeAligned(range
.begin().get()));
185 XDRResult
codeStencil(const JS::ReadOnlyDecodeOptions
& options
,
186 frontend::CompilationStencil
& stencil
);
188 const JS::ReadOnlyDecodeOptions
& options() {
189 MOZ_ASSERT(options_
);
194 const JS::ReadOnlyDecodeOptions
* options_
= nullptr;
197 class XDRStencilEncoder
: public XDRState
<XDR_ENCODE
> {
198 using Base
= XDRState
<XDR_ENCODE
>;
201 XDRStencilEncoder(FrontendContext
* fc
, JS::TranscodeBuffer
& buffer
)
202 : Base(fc
, buffer
, buffer
.length()) {
203 // NOTE: If buffer is empty, buffer.begin() doesn't point valid buffer.
204 MOZ_ASSERT_IF(!buffer
.empty(),
205 JS::IsTranscodingBytecodeAligned(buffer
.begin()));
206 MOZ_ASSERT(JS::IsTranscodingBytecodeOffsetAligned(buffer
.length()));
209 XDRResult
codeStencil(const RefPtr
<ScriptSource
>& source
,
210 const frontend::CompilationStencil
& stencil
);
212 XDRResult
codeStencil(const frontend::CompilationStencil
& stencil
);
217 #endif /* frontend_StencilXdr_h */