dart-sdk/runtime/vm/kernel.h

230 lines
7.3 KiB
C
Raw Normal View History

// Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.
#ifndef RUNTIME_VM_KERNEL_H_
#define RUNTIME_VM_KERNEL_H_
#include <memory>
#include "platform/assert.h"
#include "vm/allocation.h"
#include "vm/globals.h"
#include "vm/growable_array.h"
#include "vm/object.h"
#include "vm/token_position.h"
namespace dart {
namespace kernel {
class NameIndex {
public:
static const int kInvalidName = -1;
NameIndex() : value_(kInvalidName) {}
explicit NameIndex(int value) : value_(value) {}
operator int() const { return value_; }
private:
int value_;
};
} // namespace kernel
} // namespace dart
#if !defined(DART_PRECOMPILED_RUNTIME)
namespace dart {
class BitVector;
class Field;
class ParsedFunction;
class Zone;
namespace kernel {
class Reader;
struct ProcedureAttributesMetadata;
class StringIndex {
public:
StringIndex() : value_(-1) {}
explicit StringIndex(int value) : value_(value) {}
operator int() const { return value_; }
private:
int value_;
};
const uint8_t kNativeYieldFlags = 0x2;
enum LogicalOperator { kAnd, kOr };
class Program {
public:
// Read a kernel Program from the given Reader. Note the returned Program
// can potentially contain several "sub programs", though the library count
// etc will reference the last "sub program" only.
static std::unique_ptr<Program> ReadFrom(Reader* reader,
const char** error = nullptr);
static std::unique_ptr<Program> ReadFromFile(const char* script_uri,
const char** error = nullptr);
static std::unique_ptr<Program> ReadFromBuffer(const uint8_t* buffer,
intptr_t buffer_length,
const char** error = nullptr);
static std::unique_ptr<Program> ReadFromTypedData(
const ExternalTypedData& typed_data, const char** error = nullptr);
[kernel] Allow VM to load concatenated dill file The kernel format has been designed so that one can concatenate several dill files into one file and then load it. For instance the dart function BinaryBuilder.readProgram supports this. Currently a dill file contains one or more programs. In the VM each of these programs are called either program or subprogram. Technically a dill "program" isn't necessarily a program at all (e.g. it could be missing a library). This naming snafu should probably be cleaned up at some point, but that's for another CL. When loading a dill file via BinaryBuilder.readProgram what happens is this: - Each program in the dill file ends in 4 bytes that indicates the size of the program. - Reading the input from the end one can then read the size, skip back that amount of bytes, if we have more data (i.e. there's another program), read another size and so on, and continue until we have accounted for all bytes in the input. - We then read each program from the start, and basically overwrite any library, class, procedure etc. we find. The first main reference found is the one used though. (Saying that we overwrite is not completely true, but when the library is a non-external library that's basically what happens). This CL introduces (some) support on the C++ side for the same thing. So far the C++ side could only handle single-program-dills, and trying to load anything else would probably crash the VM. The support added is this: - Assume the SDK (i.e. vm_platform.dill) is not a concatenated file (error out if it is). - For user provided input, loop over each contained program one-by-one, for each individual one behave as normal. - The way LibraryLoad is implemented (i.e. it skips if the library is already loaded) this means that it currently would behave differently than the dart version (i.e. the first one is used, not the last one). For now it is assumed that that's not a problem. - There is a possibly snafu if the same script is included several times. This could probably mostly be remedied by not creating scripts up front, but only as needed. By the "keep only one" (and fixing the above point, probably by simply loading in the opposite order, i.e. last program in the binary first) the (theoretical) problem would probably do away. Note that we will have separate string tables, canonical name tables etc per "sub program" and that there might be some duplication. The implementation was tested as indicated below, but introduces no tests. $ cat test_lib1.dart import "test_lib2.dart" as lib2; String lib1field = "lib #1 field!!"; main() { foo(); lib2.foo(); print("From lib2: ${lib2.lib2field}"); } foo() { print("Hello, Foo, from test_lib1!"); var x = 42; print(x); } $ cat test_lib2.dart String lib2field = "Lib #2 field!!!!"; foo() { print("Hello, Foo, from test_lib2!"); var y = 34; print(y); } $ out/ReleaseX64/dart pkg/front_end/tool/_fasta/compile.dart --packages=.packages --platform=out/ReleaseX64/vm_platform.dill test_lib1.dart $ ls -lha test_lib1.dart.dill [...] 4.2M Oct 26 14:42 test_lib1.dart.dill $ dart pkg/kernel/bin/split.dart test_lib1.dart.dill Wrote test_lib1.dart.dill.part1.dill Wrote test_lib1.dart.dill.part2.dill $ ls -lha test_lib1.dart.dill.part{1,2}.dill [...] 811 Oct 26 14:42 test_lib1.dart.dill.part1.dill [...] 582 Oct 26 14:42 test_lib1.dart.dill.part2.dill $ cat test_lib1.dart.dill.part1.dill test_lib1.dart.dill.part2.dill > test_lib1.dart.dill.concat.dill $ ls -lha test_lib1.dart.dill.concat.dill [...] 1.4K Oct 26 14:44 test_lib1.dart.dill.concat.dill $ out/ReleaseX64/dart --kernel-binaries=out/ReleaseX64 --packages=.packages test_lib1.dart.dill.concat.dill Hello, Foo, from test_lib1! 42 Hello, Foo, from test_lib2! 34 From lib2: Lib #2 field!!!! Change-Id: I233a033aa3042b202dd4708908a5be3089474588 Reviewed-on: https://dart-review.googlesource.com/16820 Commit-Queue: Jens Johansen <jensj@google.com> Reviewed-by: Dmitry Stefantsov <dmitryas@google.com>
2017-10-27 12:01:48 +00:00
bool is_single_program() { return single_program_; }
uint32_t binary_version() { return binary_version_; }
NameIndex main_method() { return main_method_reference_; }
intptr_t source_table_offset() const { return source_table_offset_; }
intptr_t string_table_offset() const { return string_table_offset_; }
intptr_t name_table_offset() const { return name_table_offset_; }
intptr_t metadata_payloads_offset() const {
return metadata_payloads_offset_;
}
intptr_t metadata_mappings_offset() const {
return metadata_mappings_offset_;
}
[kernel] Add kernel2kernel constant evaluation, binary format as well as vm support The introduced "constants" transformation can evaluate constant expressions. The original use-sites of constant expressions are replaced by a new [ConstantExpression] node, which points to a subclass of a new [Constant] class hierarchy. Constant [Field]s and [VariableDeclarations]s will be removed, since all use-sites are re-written. The [Constant] class hierarchy is, similarly to the [DartType] class hierarchy, not part of the AST tree (also has no parent pointer). The constants form a DAG (directed acyclic graph). There is no canonicalization requirement of the [Constant] objects referenced by the AST (via [ConstantExpression]). Although it is beneficial to canonicalize them during construction, since it reduces time spent in operator==/hashCode. This CL furthermore adds support for a constant table in the binary format. Similarly to [String]s, we canonicalize the constants before writing the table to the binary. The constant table entries in the binary are written in a post-order way, to ensure easy construction on the backend side. The text format will be augmented with a "constants { ... }" section at the end, which lists the constants in the same order as in the binary format. The transformation can be used by those backends who choose to do so. It is not enabled by default atm. It should therefore not affect analyzer, fasta or other components. Change-Id: I57cd9624fedcf537ab6870db76246149647bed21 Reviewed-on: https://dart-review.googlesource.com/14382 Commit-Queue: Martin Kustermann <kustermann@google.com> Reviewed-by: Kevin Millikin <kmillikin@google.com>
2017-11-16 11:08:02 +00:00
intptr_t constant_table_offset() { return constant_table_offset_; }
Revert "[vm/kernel] Use GC-tracked ExternalTypedData/TypedDataView for kernel buffers" This reverts commit ab6aeaa106ecdc8c8a8793aaaa3e6dce38456d5a. Revert "[vm/compiler] Speed up the compiler part which deals with kernel reading up in DEBUG mode" This reverts commit b316210d94dece7d34cbe69f8f9e2d81de026330. Reason for revert: regression of snapshot sizes (DNO-599). Original change's description: > [vm/kernel] Use GC-tracked ExternalTypedData/TypedDataView for kernel buffers > > Until now we often leaked kernel buffers (e.g. hot reload buffers) because various > objects were referencing ExternalTypedData objects pointing into the middle of > c-allocated memory. This made it impossible for the GC to determine when the last > reference is gone. > > This CL ensures that the actual buffers are *always* made available via > ExternalTypedData and any inner pointers into it are created via TypedDataViews. > > The embedder guarantees to the free kernel buffers it has provided to: > - Dart_CreateIsolateFromKernel > - Dart_LoadScriptFromKernel > - Dart_LoadLibraryFromKernel > - Dart_SetDartLibrarySourcesKernel > on isolate shutdown. > > All other kernel buffers will get a finalizer attached, which ensures the > kernel buffers get freed by the GC once they are no longer referenced: > - Kernel blobs for expression evaluation > - Kernel blobs for Hot-Reload > - Kernel blobs for cc tests > > Fixes https://github.com/dart-lang/sdk/issues/33973 > Fixes https://github.com/dart-lang/sdk/issues/36857 > Issue https://github.com/dart-lang/sdk/issues/37030 > > Change-Id: I1cc410c94c0f4b229413e793728a261afcb10aaf > Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/103130 > Reviewed-by: Ryan Macnak <rmacnak@google.com> > Commit-Queue: Martin Kustermann <kustermann@google.com> TBR=kustermann@google.com,rmacnak@google.com # Not skipping CQ checks because original CL landed > 1 day ago. Change-Id: I49715d2400f4a5c8806b7d6a2912b7258f671a0a Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/104343 Reviewed-by: Alexander Markov <alexmarkov@google.com> Reviewed-by: Siva Annamalai <asiva@google.com> Auto-Submit: Alexander Markov <alexmarkov@google.com>
2019-05-31 22:15:51 +00:00
const uint8_t* kernel_data() { return kernel_data_; }
intptr_t kernel_data_size() { return kernel_data_size_; }
intptr_t library_count() { return library_count_; }
private:
Revert "[vm/kernel] Use GC-tracked ExternalTypedData/TypedDataView for kernel buffers" This reverts commit ab6aeaa106ecdc8c8a8793aaaa3e6dce38456d5a. Revert "[vm/compiler] Speed up the compiler part which deals with kernel reading up in DEBUG mode" This reverts commit b316210d94dece7d34cbe69f8f9e2d81de026330. Reason for revert: regression of snapshot sizes (DNO-599). Original change's description: > [vm/kernel] Use GC-tracked ExternalTypedData/TypedDataView for kernel buffers > > Until now we often leaked kernel buffers (e.g. hot reload buffers) because various > objects were referencing ExternalTypedData objects pointing into the middle of > c-allocated memory. This made it impossible for the GC to determine when the last > reference is gone. > > This CL ensures that the actual buffers are *always* made available via > ExternalTypedData and any inner pointers into it are created via TypedDataViews. > > The embedder guarantees to the free kernel buffers it has provided to: > - Dart_CreateIsolateFromKernel > - Dart_LoadScriptFromKernel > - Dart_LoadLibraryFromKernel > - Dart_SetDartLibrarySourcesKernel > on isolate shutdown. > > All other kernel buffers will get a finalizer attached, which ensures the > kernel buffers get freed by the GC once they are no longer referenced: > - Kernel blobs for expression evaluation > - Kernel blobs for Hot-Reload > - Kernel blobs for cc tests > > Fixes https://github.com/dart-lang/sdk/issues/33973 > Fixes https://github.com/dart-lang/sdk/issues/36857 > Issue https://github.com/dart-lang/sdk/issues/37030 > > Change-Id: I1cc410c94c0f4b229413e793728a261afcb10aaf > Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/103130 > Reviewed-by: Ryan Macnak <rmacnak@google.com> > Commit-Queue: Martin Kustermann <kustermann@google.com> TBR=kustermann@google.com,rmacnak@google.com # Not skipping CQ checks because original CL landed > 1 day ago. Change-Id: I49715d2400f4a5c8806b7d6a2912b7258f671a0a Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/104343 Reviewed-by: Alexander Markov <alexmarkov@google.com> Reviewed-by: Siva Annamalai <asiva@google.com> Auto-Submit: Alexander Markov <alexmarkov@google.com>
2019-05-31 22:15:51 +00:00
Program() : kernel_data_(NULL), kernel_data_size_(-1) {}
[kernel] Allow VM to load concatenated dill file The kernel format has been designed so that one can concatenate several dill files into one file and then load it. For instance the dart function BinaryBuilder.readProgram supports this. Currently a dill file contains one or more programs. In the VM each of these programs are called either program or subprogram. Technically a dill "program" isn't necessarily a program at all (e.g. it could be missing a library). This naming snafu should probably be cleaned up at some point, but that's for another CL. When loading a dill file via BinaryBuilder.readProgram what happens is this: - Each program in the dill file ends in 4 bytes that indicates the size of the program. - Reading the input from the end one can then read the size, skip back that amount of bytes, if we have more data (i.e. there's another program), read another size and so on, and continue until we have accounted for all bytes in the input. - We then read each program from the start, and basically overwrite any library, class, procedure etc. we find. The first main reference found is the one used though. (Saying that we overwrite is not completely true, but when the library is a non-external library that's basically what happens). This CL introduces (some) support on the C++ side for the same thing. So far the C++ side could only handle single-program-dills, and trying to load anything else would probably crash the VM. The support added is this: - Assume the SDK (i.e. vm_platform.dill) is not a concatenated file (error out if it is). - For user provided input, loop over each contained program one-by-one, for each individual one behave as normal. - The way LibraryLoad is implemented (i.e. it skips if the library is already loaded) this means that it currently would behave differently than the dart version (i.e. the first one is used, not the last one). For now it is assumed that that's not a problem. - There is a possibly snafu if the same script is included several times. This could probably mostly be remedied by not creating scripts up front, but only as needed. By the "keep only one" (and fixing the above point, probably by simply loading in the opposite order, i.e. last program in the binary first) the (theoretical) problem would probably do away. Note that we will have separate string tables, canonical name tables etc per "sub program" and that there might be some duplication. The implementation was tested as indicated below, but introduces no tests. $ cat test_lib1.dart import "test_lib2.dart" as lib2; String lib1field = "lib #1 field!!"; main() { foo(); lib2.foo(); print("From lib2: ${lib2.lib2field}"); } foo() { print("Hello, Foo, from test_lib1!"); var x = 42; print(x); } $ cat test_lib2.dart String lib2field = "Lib #2 field!!!!"; foo() { print("Hello, Foo, from test_lib2!"); var y = 34; print(y); } $ out/ReleaseX64/dart pkg/front_end/tool/_fasta/compile.dart --packages=.packages --platform=out/ReleaseX64/vm_platform.dill test_lib1.dart $ ls -lha test_lib1.dart.dill [...] 4.2M Oct 26 14:42 test_lib1.dart.dill $ dart pkg/kernel/bin/split.dart test_lib1.dart.dill Wrote test_lib1.dart.dill.part1.dill Wrote test_lib1.dart.dill.part2.dill $ ls -lha test_lib1.dart.dill.part{1,2}.dill [...] 811 Oct 26 14:42 test_lib1.dart.dill.part1.dill [...] 582 Oct 26 14:42 test_lib1.dart.dill.part2.dill $ cat test_lib1.dart.dill.part1.dill test_lib1.dart.dill.part2.dill > test_lib1.dart.dill.concat.dill $ ls -lha test_lib1.dart.dill.concat.dill [...] 1.4K Oct 26 14:44 test_lib1.dart.dill.concat.dill $ out/ReleaseX64/dart --kernel-binaries=out/ReleaseX64 --packages=.packages test_lib1.dart.dill.concat.dill Hello, Foo, from test_lib1! 42 Hello, Foo, from test_lib2! 34 From lib2: Lib #2 field!!!! Change-Id: I233a033aa3042b202dd4708908a5be3089474588 Reviewed-on: https://dart-review.googlesource.com/16820 Commit-Queue: Jens Johansen <jensj@google.com> Reviewed-by: Dmitry Stefantsov <dmitryas@google.com>
2017-10-27 12:01:48 +00:00
bool single_program_;
uint32_t binary_version_;
NameIndex main_method_reference_; // Procedure.
intptr_t library_count_;
[kernel] Don't scan strings up front when serializing. Currently serializing the ast for kernel is done in two passe: 1) Scan the program to find and index all strings. These are then sorted based on frequency and assigned an id. All string- references are refering to that id. As small numbers use less space in the binary than big numbers, sorting the numbers by frequency saves a certain amount of space. In addition the string indexing is "hijacked" for the "LimitedBinaryPrinter" to also perform some CanonicalName re-indexing. 2) We then serialize the entire thing. This CL gets rid of a pass by not indexing the strings up-front. Whenever it is asked to serialize a string it adds it to the index (if not already there). The serialization is otherwise the same. This means that: 1) Strings are not sorted by frequency, i.e. the binary output size can by bigger (numbers below). 2) The stringindex and canonical names are moved to the end of the binary instead of the front. As we still need it up front for deserialization some additional data is added to the ProgramIndex. 3) The "hijacking" done in "LimitedBinaryPrinter" is replaced by an alternative. 4) We don't spend time on walking the tree twice. The cost is the binary size. Compiling helloworld with fasta, as well as looking at outline.dill, platform.dill and vmservice_io.dill reveals these numbers: * helloworld.dill is 0.657248732% bigger (26573 bytes) * outline.dill is 1.686911399% bigger (9395 bytes) * platform.dill is 0.657062238% bigger (26565 bytes) * vmservice_io.dill is 0.44991899% bigger (19147 bytes) The cost does thus not appear to be very big. The gain is the serialization time. From 20 runs of an instrumented VM/serialization, running numbers through calculations stolens from ministat (https://www.freebsd.org/cgi/man.cgi?query=ministat) reveals the following: * Serialization time: -21.69% +/- 1.44% * Total time spend in relevant parts of bootstrap_nocore.cc, dart_api_impl.cc (Dart_LoadKernel), bootstrap_nocore.cc, dart_api_impl.cc (LoadKernelProgram) as well as serialization: -14.01% +/- 1.58% From 5 runs of "time python tools/test.py -m release -cdartk language -j6" (again run through ministat calculations): * real: -4.18% +/- 0.5% * user: -4.2% +/- 0.29% * sys: No difference at 95% * user+sys: -3.3% +/- 0.36% Change-Id: I1c220eac083496994f0a9f1e2a2445b3707c9a93 Reviewed-on: https://dart-review.googlesource.com/2880 Reviewed-by: Samir Jindel <sjindel@google.com>
2017-09-06 06:38:14 +00:00
// The offset from the start of the binary to the start of the source table.
intptr_t source_table_offset_;
[kernel] Add kernel2kernel constant evaluation, binary format as well as vm support The introduced "constants" transformation can evaluate constant expressions. The original use-sites of constant expressions are replaced by a new [ConstantExpression] node, which points to a subclass of a new [Constant] class hierarchy. Constant [Field]s and [VariableDeclarations]s will be removed, since all use-sites are re-written. The [Constant] class hierarchy is, similarly to the [DartType] class hierarchy, not part of the AST tree (also has no parent pointer). The constants form a DAG (directed acyclic graph). There is no canonicalization requirement of the [Constant] objects referenced by the AST (via [ConstantExpression]). Although it is beneficial to canonicalize them during construction, since it reduces time spent in operator==/hashCode. This CL furthermore adds support for a constant table in the binary format. Similarly to [String]s, we canonicalize the constants before writing the table to the binary. The constant table entries in the binary are written in a post-order way, to ensure easy construction on the backend side. The text format will be augmented with a "constants { ... }" section at the end, which lists the constants in the same order as in the binary format. The transformation can be used by those backends who choose to do so. It is not enabled by default atm. It should therefore not affect analyzer, fasta or other components. Change-Id: I57cd9624fedcf537ab6870db76246149647bed21 Reviewed-on: https://dart-review.googlesource.com/14382 Commit-Queue: Martin Kustermann <kustermann@google.com> Reviewed-by: Kevin Millikin <kmillikin@google.com>
2017-11-16 11:08:02 +00:00
// The offset from the start of the binary to the start of the constant table.
intptr_t constant_table_offset_;
// The offset from the start of the binary to the canonical name table.
intptr_t name_table_offset_;
// The offset from the start of the binary to the metadata payloads.
intptr_t metadata_payloads_offset_;
// The offset from the start of the binary to the metadata mappings.
intptr_t metadata_mappings_offset_;
[kernel] Don't scan strings up front when serializing. Currently serializing the ast for kernel is done in two passe: 1) Scan the program to find and index all strings. These are then sorted based on frequency and assigned an id. All string- references are refering to that id. As small numbers use less space in the binary than big numbers, sorting the numbers by frequency saves a certain amount of space. In addition the string indexing is "hijacked" for the "LimitedBinaryPrinter" to also perform some CanonicalName re-indexing. 2) We then serialize the entire thing. This CL gets rid of a pass by not indexing the strings up-front. Whenever it is asked to serialize a string it adds it to the index (if not already there). The serialization is otherwise the same. This means that: 1) Strings are not sorted by frequency, i.e. the binary output size can by bigger (numbers below). 2) The stringindex and canonical names are moved to the end of the binary instead of the front. As we still need it up front for deserialization some additional data is added to the ProgramIndex. 3) The "hijacking" done in "LimitedBinaryPrinter" is replaced by an alternative. 4) We don't spend time on walking the tree twice. The cost is the binary size. Compiling helloworld with fasta, as well as looking at outline.dill, platform.dill and vmservice_io.dill reveals these numbers: * helloworld.dill is 0.657248732% bigger (26573 bytes) * outline.dill is 1.686911399% bigger (9395 bytes) * platform.dill is 0.657062238% bigger (26565 bytes) * vmservice_io.dill is 0.44991899% bigger (19147 bytes) The cost does thus not appear to be very big. The gain is the serialization time. From 20 runs of an instrumented VM/serialization, running numbers through calculations stolens from ministat (https://www.freebsd.org/cgi/man.cgi?query=ministat) reveals the following: * Serialization time: -21.69% +/- 1.44% * Total time spend in relevant parts of bootstrap_nocore.cc, dart_api_impl.cc (Dart_LoadKernel), bootstrap_nocore.cc, dart_api_impl.cc (LoadKernelProgram) as well as serialization: -14.01% +/- 1.58% From 5 runs of "time python tools/test.py -m release -cdartk language -j6" (again run through ministat calculations): * real: -4.18% +/- 0.5% * user: -4.2% +/- 0.29% * sys: No difference at 95% * user+sys: -3.3% +/- 0.36% Change-Id: I1c220eac083496994f0a9f1e2a2445b3707c9a93 Reviewed-on: https://dart-review.googlesource.com/2880 Reviewed-by: Samir Jindel <sjindel@google.com>
2017-09-06 06:38:14 +00:00
// The offset from the start of the binary to the start of the string table.
intptr_t string_table_offset_;
Revert "[vm/kernel] Use GC-tracked ExternalTypedData/TypedDataView for kernel buffers" This reverts commit ab6aeaa106ecdc8c8a8793aaaa3e6dce38456d5a. Revert "[vm/compiler] Speed up the compiler part which deals with kernel reading up in DEBUG mode" This reverts commit b316210d94dece7d34cbe69f8f9e2d81de026330. Reason for revert: regression of snapshot sizes (DNO-599). Original change's description: > [vm/kernel] Use GC-tracked ExternalTypedData/TypedDataView for kernel buffers > > Until now we often leaked kernel buffers (e.g. hot reload buffers) because various > objects were referencing ExternalTypedData objects pointing into the middle of > c-allocated memory. This made it impossible for the GC to determine when the last > reference is gone. > > This CL ensures that the actual buffers are *always* made available via > ExternalTypedData and any inner pointers into it are created via TypedDataViews. > > The embedder guarantees to the free kernel buffers it has provided to: > - Dart_CreateIsolateFromKernel > - Dart_LoadScriptFromKernel > - Dart_LoadLibraryFromKernel > - Dart_SetDartLibrarySourcesKernel > on isolate shutdown. > > All other kernel buffers will get a finalizer attached, which ensures the > kernel buffers get freed by the GC once they are no longer referenced: > - Kernel blobs for expression evaluation > - Kernel blobs for Hot-Reload > - Kernel blobs for cc tests > > Fixes https://github.com/dart-lang/sdk/issues/33973 > Fixes https://github.com/dart-lang/sdk/issues/36857 > Issue https://github.com/dart-lang/sdk/issues/37030 > > Change-Id: I1cc410c94c0f4b229413e793728a261afcb10aaf > Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/103130 > Reviewed-by: Ryan Macnak <rmacnak@google.com> > Commit-Queue: Martin Kustermann <kustermann@google.com> TBR=kustermann@google.com,rmacnak@google.com # Not skipping CQ checks because original CL landed > 1 day ago. Change-Id: I49715d2400f4a5c8806b7d6a2912b7258f671a0a Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/104343 Reviewed-by: Alexander Markov <alexmarkov@google.com> Reviewed-by: Siva Annamalai <asiva@google.com> Auto-Submit: Alexander Markov <alexmarkov@google.com>
2019-05-31 22:15:51 +00:00
const uint8_t* kernel_data_;
intptr_t kernel_data_size_;
DISALLOW_COPY_AND_ASSIGN(Program);
};
class KernelLineStartsReader {
public:
KernelLineStartsReader(const dart::TypedData& line_starts_data,
dart::Zone* zone);
~KernelLineStartsReader() { delete helper_; }
int32_t DeltaAt(intptr_t index) const {
return helper_->At(line_starts_data_, index);
}
intptr_t LineNumberForPosition(intptr_t position) const;
void LocationForPosition(intptr_t position,
intptr_t* line,
intptr_t* col) const;
void TokenRangeAtLine(intptr_t source_length,
intptr_t line_number,
dart::TokenPosition* first_token_index,
dart::TokenPosition* last_token_index) const;
private:
class KernelLineStartsHelper {
public:
KernelLineStartsHelper() {}
virtual ~KernelLineStartsHelper() {}
virtual int32_t At(const dart::TypedData& data, intptr_t index) const = 0;
private:
DISALLOW_COPY_AND_ASSIGN(KernelLineStartsHelper);
};
class KernelInt8LineStartsHelper : public KernelLineStartsHelper {
public:
KernelInt8LineStartsHelper() {}
virtual int32_t At(const dart::TypedData& data, intptr_t index) const;
private:
DISALLOW_COPY_AND_ASSIGN(KernelInt8LineStartsHelper);
};
class KernelInt16LineStartsHelper : public KernelLineStartsHelper {
public:
KernelInt16LineStartsHelper() {}
virtual int32_t At(const dart::TypedData& data, intptr_t index) const;
private:
DISALLOW_COPY_AND_ASSIGN(KernelInt16LineStartsHelper);
};
class KernelInt32LineStartsHelper : public KernelLineStartsHelper {
public:
KernelInt32LineStartsHelper() {}
virtual int32_t At(const dart::TypedData& data, intptr_t index) const;
private:
DISALLOW_COPY_AND_ASSIGN(KernelInt32LineStartsHelper);
};
const dart::TypedData& line_starts_data_;
KernelLineStartsHelper* helper_;
DISALLOW_COPY_AND_ASSIGN(KernelLineStartsReader);
};
void CollectTokenPositionsFor(const Script& script);
RawObject* EvaluateMetadata(const Field& metadata_field,
bool is_annotations_offset);
RawObject* BuildParameterDescriptor(const Function& function);
// Fills in [is_covariant] and [is_generic_covariant_impl] vectors
// according to covariance attributes of [function] parameters.
//
// [is_covariant] and [is_generic_covariant_impl] should contain bitvectors
// of function.NumParameters() length.
void ReadParameterCovariance(const Function& function,
BitVector* is_covariant,
BitVector* is_generic_covariant_impl);
// Returns true if the given function needs dynamic invocation forwarder:
// that is if any of the arguments require checking on the dynamic
// call-site: if function has no parameters or has only covariant parameters
// as such function already checks all of its parameters.
bool NeedsDynamicInvocationForwarder(const Function& function);
// Returns a list of ParameterTypeChecks needed by a dynamic invocation
// forwarder that targets [function]. Indices in these checks correspond to
// bytecode frame indices.
RawArray* CollectDynamicInvocationChecks(const Function& function);
ProcedureAttributesMetadata ProcedureAttributesOf(const Function& function,
Zone* zone);
ProcedureAttributesMetadata ProcedureAttributesOf(const Field& field,
Zone* zone);
} // namespace kernel
} // namespace dart
#endif // !defined(DART_PRECOMPILED_RUNTIME)
#endif // RUNTIME_VM_KERNEL_H_