Commit Graph

246 Commits

Author SHA1 Message Date
Ryan Macnak 91cef061c7 [vm, compiler] Create a proper frame in the FFI callback trampoline.
TEST=ci
Bug: https://github.com/dart-lang/sdk/issues/62932
Change-Id: I2b8de8555b3810e4838f4ac36d590a24159291ec
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/490740
Reviewed-by: Alexander Aprelev <aam@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2026-03-31 11:13:00 -07:00
Ryan Macnak 1d91605c25 [vm, compiler] Handle 32-bit constant indices for Load/StoreIndexedInstr on ARM64 and RISC-V.
This extends the set of indices that are not processed by the register allocator to match X64. This avoids slowness in the register allocator for large list literals. For some cases, it also reduces code size.

TEST=ci
Bug: https://github.com/dart-lang/sdk/issues/62411
Change-Id: Iab71a6dea2f2f75b06c51e4b23626bc991e1a20f
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/475720
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2026-01-26 14:37:58 -08:00
Ryan Macnak 0a1678c06c [vm] Record stack for JIT TSAN.
The main interesting thing is that deopt can expand one optimized frame to multiple unoptimized frames, so deopt needs to call  __tsan_func_entry enough times to rebalance the stack.

Also fixes stack balance for throw error slow paths for AOT.

TEST=tsan
Bug: https://github.com/dart-lang/sdk/issues/61352
Change-Id: I3fdc8481bc8db7a3aec0fa1938ac3e0e96ac13a5
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/452943
Commit-Queue: Ryan Macnak <rmacnak@google.com>
Reviewed-by: Alexander Markov <alexmarkov@google.com>
2025-10-20 10:49:20 -07:00
Ryan Macnak c59549e957 [vm, compiler] More specific assembly comments for runtime calls.
TEST=ci
Change-Id: Iaabdbceedbddffd2f980fb0828a8fc211524a3d5
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/455180
Commit-Queue: Ryan Macnak <rmacnak@google.com>
Reviewed-by: Alexander Markov <alexmarkov@google.com>
2025-10-15 09:21:52 -07:00
Ryan Macnak 78d280a2df [vm] Symbolize JIT Dart frames for TSAN.
TEST=tsan
Bug: https://github.com/dart-lang/sdk/issues/61352
Change-Id: I0e64e563b19bbd7b67e6f275dbc373db08b9d2c7
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/449980
Reviewed-by: Alexander Aprelev <aam@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2025-09-24 13:14:32 -07:00
Ryan Macnak 08964e235b [vm, compiler] Make the leaf runtime call spill set more consistent between architectures.
Remove unnecessary spill of FpuTMP.
Remove unnecessary spill of TMP on x64.

TEST=ci
Change-Id: I6e56e4dfe1a817ff2c1f53229be305640b89eee6
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/446740
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2025-08-26 14:05:27 -07:00
Ryan Macnak e01d4b3cc6 [vm, compiler] Get the full Dart stack in TSAN reports.
Call __tsan_func_entry/__tsan_func_exit in functions that use __tsan_read/__tsan_write or call other functions. Call __tsan_func_exit once per frame when unwinding for exceptions. Do so only in AOT, since TSAN won't be able to symbolize JIT functions anyway.

TEST=ci
Bug: https://github.com/dart-lang/sdk/issues/61352
Cq-Include-Trybots: luci.dart.try:vm-tsan-linux-release-arm64-try,vm-tsan-linux-release-x64-try
Change-Id: Ie52c978c25664d78b834e9b72ecf7eb2a12cc2ba
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/444181
Reviewed-by: Alexander Aprelev <aam@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2025-08-26 11:50:13 -07:00
Alexander Markov 8f41c9194b [vm] Fix msvc build
Use standard constant instead of gcc/clang specific extension.

TEST=ci

Change-Id: I4b6a8e2ad62f180bebac39c90fff62cd60857d2d
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/444440
Reviewed-by: Alexander Aprelev <aam@google.com>
Commit-Queue: Alexander Markov <alexmarkov@google.com>
2025-08-08 08:27:19 -07:00
Ryan Macnak 5f375954d4 [vm, compiler] Handle up to 32-bit offsets for pool loads on ARM64.
TEST=vm/dart/generated/many_double_literals_test, in later CL
Cq-Include-Trybots: luci.dart.try:vm-aot-linux-debug-arm64-try,vm-aot-linux-release-arm64-try,vm-linux-release-arm64-try,vm-linux-debug-arm64-try
Change-Id: I367c6a0298aba28fb6883d8ee62815e15a0c01de
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/443900
Commit-Queue: Ryan Macnak <rmacnak@google.com>
Reviewed-by: Alexander Markov <alexmarkov@google.com>
2025-08-06 09:19:14 -07:00
Ryan Macnak e6053248c3 [vm, compiler] Add TSAN instrumentation to Dart field access.
Allows TSAN to detect data races involving Dart fields.

TEST=tsan
Cq-Include-Trybots: luci.dart.try:vm-tsan-linux-release-x64-try,vm-tsan-linux-release-arm64-try,iso-stress-linux-arm64-try,iso-stress-linux-x64-try
Change-Id: Ic7a6c7e6c1810adf79b41e5c0ae891132f368a61
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/439143
Reviewed-by: Alexander Aprelev <aam@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2025-08-06 09:18:43 -07:00
Ryan Macnak dc97aa7fb9 [vm, compiler] Update TSAN instrumentation.
TEST=tsan
Cq-Include-Trybots: luci.dart.try:vm-tsan-linux-release-x64-try,vm-tsan-linux-release-arm64-try,iso-stress-linux-arm64-try,iso-stress-linux-x64-try
Change-Id: I0c49b501c53f9a5117bb14800e342e6fe9b4eba6
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/442730
Reviewed-by: Alexander Aprelev <aam@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2025-08-04 15:29:04 -07:00
Vyacheslav Egorov 8085a97a63 [vm] Fix JumpToFrame execution state transition
Instead of handling FFI related execution state and safepoint
in assembly handle it in runtime code.

The transition needs to be done before JumpToFrame unwinds
stack because unwinding destroys exit frame and this can't
be done at safepoint as GC might be traversing the stack.

An incorrect order of operation was manifesting as crashes in
GC when one isolate in a group was encountering a lot of
exceptions thrown from an FFI call and another isolate is
triggering GCs.

To catch this in the future added a bit of validation to
ExitSafepoint runtime call which triggers when --use-slow-path
is enabled. Though after refactoring this code does not
trigger this code path anymore because it was completely
removed - but it is better than nothing.

This CL also removes a lot of unnecessary complexity which
was associated with handling this transition in the stub
itself.

TEST=ffi/vmspecific_handle_test

Bug: b/408377905
Cq-Include-Trybots: dart/try:vm-aot-android-release-arm64c-try,vm-aot-android-release-arm_x64-try,vm-aot-asan-linux-release-x64-try,vm-aot-linux-debug-x64-try,vm-aot-linux-debug-x64c-try,vm-aot-mac-release-arm64-try,vm-aot-msan-linux-release-x64-try,vm-aot-obfuscate-linux-release-x64-try,vm-aot-optimization-level-linux-release-x64-try,vm-aot-tsan-linux-release-x64-try,vm-aot-ubsan-linux-release-x64-try,vm-aot-win-debug-x64-try,vm-aot-win-debug-x64c-try,vm-appjit-linux-debug-x64-try,vm-asan-linux-release-arm64-try,vm-asan-linux-release-x64-try,vm-checked-mac-release-arm64-try,vm-eager-optimization-linux-release-ia32-try,vm-eager-optimization-linux-release-x64-try,vm-ffi-android-debug-arm-try,vm-ffi-android-debug-arm64c-try,vm-ffi-mac-debug-simarm64_arm64-try,vm-ffi-qemu-linux-release-arm-try,vm-ffi-qemu-linux-release-riscv64-try,vm-fuchsia-release-x64-try,vm-linux-debug-ia32-try,vm-linux-debug-x64-try,vm-linux-debug-x64c-try,vm-mac-debug-arm64-try,vm-mac-debug-x64-try,vm-msan-linux-release-arm64-try,vm-msan-linux-release-x64-try,vm-reload-linux-debug-x64-try,vm-reload-rollback-linux-debug-x64-try,vm-tsan-linux-release-arm64-try,vm-tsan-linux-release-x64-try,vm-ubsan-linux-release-arm64-try,vm-ubsan-linux-release-x64-try,vm-win-debug-x64-try,vm-win-debug-x64c-try,vm-win-release-ia32-try
Change-Id: Ia073cb6bb9e1b5a0ea8514c7e048cee6019b84d6
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/420324
Commit-Queue: Slava Egorov <vegorov@google.com>
Reviewed-by: Daco Harkes <dacoharkes@google.com>
2025-04-07 05:22:56 -07:00
Ryan Macnak 2a08770912 [vm] If waiting for an active mutator slot for too long, steal a slot from a thread at a native safepoint.
The thread whose slot was stolen will take the slow path attempting to exit its safepoint and wait to reacquire an active mutator slot.

TEST=ci
Bug: https://github.com/dart-lang/sdk/issues/54687
Change-Id: I49c4c12b38d38d7afa4df6b346c2a464f75ef6e0
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/406404
Commit-Queue: Ryan Macnak <rmacnak@google.com>
Reviewed-by: Alexander Aprelev <aam@google.com>
2025-02-10 09:38:42 -08:00
Alexander Markov f2d70cec04 [vm,arm64] Fix AddImmediate in case of CSP
Use extended register variant of add instruction when Rd or Rn
register is CSP (SP). Also fix assertion which was incorrectly
testing that Rd cannot be CSP if extended register operand is used
(actually it cannot be ZR).

TEST=vm/cc/Assembler_Drop
Fixes https://github.com/dart-lang/sdk/issues/46433

Change-Id: I542dd7bc0661b3195fa466e43cd65998c1c4ac81
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/408141
Commit-Queue: Alexander Markov <alexmarkov@google.com>
Reviewed-by: Ryan Macnak <rmacnak@google.com>
2025-02-05 12:32:39 -08:00
Daco Harkes 5984cc8c24 [vm] Verify transitions in generated code
The transitions in C++ have asserts which run in debug mode to validate
that the transitions are happening in the right order.

The transitions in the generated code had no equivalent. This CL
introduces the equivalent for the generated code.

The transitions to generated code are misnamed currently. They come
from either VM or Native, not only Native. For example the FFI
callbacks and call return sequence can already transition from native
into the VM when entering the safepoint.

These checks don't catch the invalid FFI callbacks.
Bug: https://github.com/dart-lang/sdk/issues/60021
These are caught when looking up the FFI metadata:
https://dart-review.googlesource.com/c/sdk/+/407023

This CL omits to implement the check in ia32, since ia32 is scheduled
for removal.

The check is only enabled in debug mode. The asserts for the C++ are
also only run in debug mode. And enabling this check in release for
AOT regresses the parent CL benchmark by ~30% on Mac Arm64.

TEST=test/ffi

Change-Id: Ieaf1e43533baae294af37b2e171b68bd314fdbe0
Cq-Include-Trybots: dart/try:vm-aot-android-release-arm64c-try,vm-aot-android-release-arm_x64-try,vm-aot-asan-linux-release-x64-try,vm-aot-linux-debug-x64-try,vm-aot-linux-debug-x64c-try,vm-aot-mac-release-arm64-try,vm-aot-mac-release-x64-try,vm-aot-msan-linux-release-x64-try,vm-aot-obfuscate-linux-release-x64-try,vm-aot-optimization-level-linux-release-x64-try,vm-aot-tsan-linux-release-x64-try,vm-aot-ubsan-linux-release-x64-try,vm-aot-win-debug-arm64-try,vm-aot-win-debug-x64-try,vm-aot-win-debug-x64c-try,vm-appjit-linux-debug-x64-try,vm-asan-linux-release-arm64-try,vm-asan-linux-release-x64-try,vm-checked-mac-release-arm64-try,vm-ffi-android-debug-arm-try,vm-ffi-android-debug-arm64c-try,vm-ffi-qemu-linux-release-arm-try,vm-ffi-qemu-linux-release-riscv64-try,vm-fuchsia-release-arm64-try,vm-fuchsia-release-x64-try,vm-linux-debug-ia32-try,vm-linux-debug-x64-try,vm-linux-debug-x64c-try,vm-mac-debug-arm64-try,vm-mac-debug-x64-try,vm-msan-linux-release-arm64-try,vm-msan-linux-release-x64-try,vm-reload-linux-debug-x64-try,vm-reload-rollback-linux-debug-x64-try,vm-tsan-linux-release-arm64-try,vm-tsan-linux-release-x64-try,vm-ubsan-linux-release-arm64-try,vm-ubsan-linux-release-x64-try,vm-win-debug-arm64-try,vm-win-debug-x64-try,vm-win-debug-x64c-try,vm-win-release-ia32-try
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/407021
Reviewed-by: Liam Appelbe <liama@google.com>
Reviewed-by: Slava Egorov <vegorov@google.com>
2025-02-04 03:36:29 -08:00
Ryan Macnak 598de0a21e [vm] MSAN ARM64 fixes.
- Fix early exit from MemoryCopyInstr bypassing MsanUnpoison
 - Fix missing MsanUnpoison for unrolled case
 - Fix flakey failure from safepointing clobbering MsanUnpoisonParam

TEST=msan
Bug: https://github.com/dart-lang/sdk/issues/55783
Bug: https://github.com/dart-lang/sdk/issues/55794
Change-Id: Ifbf440fa8741d426643414c530c8876543451697
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/394580
Commit-Queue: Ryan Macnak <rmacnak@google.com>
Reviewed-by: Alexander Aprelev <aam@google.com>
2024-11-11 20:41:51 +00:00
Ryan Macnak 949eb447a4 [vm, gc] Add write-write fence after initializing object headers, or defer marking new-space objects in an active TLAB.
On architectures with a weak memory model, there is the possibility that the concurrent marker can see the publishing store of a new object before it sees the initializing store of that object's header. On an M1, the barrier to prevent reordering these stores is fairly cheap, so we emit this barrier on Mac/iOS ARM64. Otherwise, this barrier is very expensive (or at least expensive for some hardware within the ABI), so instead we avoid the race by deferring marking of objects inside an active TLAB.

Disable TSAN instrumentation on the marker setting the mark bit, as TSAN does not understand fences.

TEST=ooo arm64 machines
Bug: https://github.com/dart-lang/sdk/issues/56845
Change-Id: I0676661a7cf941fdc6b451e516d890c26826bb3b
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/389265
Commit-Queue: Ryan Macnak <rmacnak@google.com>
Reviewed-by: Siva Annamalai <asiva@google.com>
2024-10-28 22:41:39 +00:00
Tess Strickland b23584eaa0 [vm/compiler] Add reg, reg, imm forms for lsl/asr/and assembler macros.
For non-x86 architectures, these forms directly translate to a
single instruction when possible. On x86 architectures,
XImmediate(dst, src, imm) where X is in {Lsl, ArithmeticShiftRight, And}
can be translated to:

  MoveRegister(dst, src);
  XImmediate(dst, imm);

in the general case since MoveRegister(dst, src) is a no-op if dst and
src are the same.

Also add versions of these assembler macros that take an OperandSize
and handle 32-bit OperandSizes appropriately on 64-bit architectures.

Ensure the implementation for LslImmediate and
ArithmeticShiftRightImmediate emits no instructions if shift == 0,
dst == src, and OperandSizeInBits(sz) == kBitsPerWord on all
architectures.

-----

Other changes:

Fix ConstantExpression::EmitMoveToLocation on ARM64 to match
other architectures, which allow any word-sized or less unboxed
integer representation.

Fill out ExtendValue on RISCV for previously unimplemented
OperandSizes, using the Zba and Zbb extensions when possible.

-----

TEST=vm/cc/Assembler_AndImmediate vm/cc/Assembler_LslImmediate
     vm/cc/Assembler_ArithmeticShiftRightImmediate

Separated out of https://dart-review.googlesource.com/c/sdk/+/378706
for easier debugging/reviewing.

Change-Id: I721f1334784f7011a958ea8af29f0e56c620726c
Cq-Include-Trybots: luci.dart.try:vm-aot-linux-release-simarm_x64-try,vm-aot-linux-debug-x64-try,vm-aot-mac-release-arm64-try,vm-aot-mac-product-arm64-try,vm-aot-linux-product-x64-try,vm-aot-dwarf-linux-product-x64-try,vm-aot-linux-debug-simarm_x64-try,vm-linux-debug-x64-try,vm-mac-debug-arm64-try,vm-mac-release-arm64-try,vm-linux-debug-ia32-try,vm-aot-android-release-arm64c-try,vm-ffi-android-debug-arm64c-try,vm-aot-linux-debug-x64c-try,vm-linux-debug-x64c-try,vm-ffi-qemu-linux-release-arm-try,vm-ffi-qemu-linux-release-riscv64-try
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/386180
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Commit-Queue: Tess Strickland <sstrickl@google.com>
2024-10-04 10:07:51 +00:00
Ryan Macnak c3b2672a19 [vm, compiler] Make use of the zero register for unboxed stores too.
dart2js.aot.rv64 19942240 -> 19925848 (-16k)

TEST=ci
Change-Id: If3d0792e28dbfa5a4183ef4363f155f7c068db47
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/385660
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2024-09-23 21:51:31 +00:00
Alexander Aprelev 4138277ee6 [vm/shared] Introduce 'vm:shared' pragma.
Decorating a field with 'vm:shared' pragma makes values in this field accessible to all isolates in an isolate group.

Introduce `channel` to the `Version` class so that the pragma can only be enabled on main and dev channels.

TEST=shared_test, shared_fail_without_flag_test
BUG=https://github.com/dart-lang/sdk/issues/55991

Change-Id: I843c9f0d2ffc9f2ced7ddc4006bb6f9ca4e2ddf4
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/370064
Reviewed-by: Slava Egorov <vegorov@google.com>
Commit-Queue: Alexander Aprelev <aam@google.com>
2024-06-14 23:24:19 +00:00
Ryan Macnak 6694cae4d7 [vm, gc] Incremental compaction, take 3.
- Use atomics to mark remembered cards in the write barrier stub.

TEST=ci
Bug: https://github.com/dart-lang/sdk/issues/52513
Bug: https://github.com/dart-lang/sdk/issues/55754
Change-Id: I1f78c6b680a6ae9170613ba328a244335a6343e2
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/368480
Reviewed-by: Siva Annamalai <asiva@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2024-05-30 21:01:39 +00:00
Ryan Macnak 1a9acb9171 [vm, ffi] Make callbacks profiler-safe.
Delay changing Thread::vm_tag on callback entry and restore the tag early on callback return so that the profiler doesn't see the "running Dart" tag unless it can also see the fake return address marking the entry frame.

TEST=ffi/async_void_function_callbacks, ffi/function_callbacks_subtype, ffi/function_callbacks, ffi/isolate_local_function_callbacks
Bug: https://github.com/dart-lang/sdk/issues/52814
Change-Id: I40d80ec7c44063d078db0e211565e2d127c6b81e
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/367460
Reviewed-by: Daco Harkes <dacoharkes@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2024-05-28 21:16:41 +00:00
Daco Harkes b732c96e8a Revert "[vm, gc] Incremental compaction, take 2."
This reverts commit 9077bf991f.

Reason for revert: CBuild and TGP crashes in random Dart code which
look a lot like arbitrary memory corruption.

Original change's description:
> [vm, gc] Incremental compaction, take 2.
>
> - Fix missing store buffer flush when --marker_tasks=0.
> - Fix passing untagged pointer to store barrier check on ARM/ARM64 (6bc417dd17).
> - Fix passing uninitialized header to store barrier check on ARM64/RISCV (1447193053).
>
> TEST=ci
> Bug: https://github.com/dart-lang/sdk/issues/52513
> Bug: https://github.com/dart-lang/sdk/issues/55754
> Change-Id: Id2aa95b6d776b82d83464cde0d00e6f3b29b7b77
> Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/367202
> Commit-Queue: Ryan Macnak <rmacnak@google.com>
> Reviewed-by: Alexander Aprelev <aam@google.com>

Bug: https://github.com/dart-lang/sdk/issues/52513
Bug: https://github.com/dart-lang/sdk/issues/55754
Change-Id: I1d70d33c65fe6bf7089b8c1422d59f9146ae7ebf
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/367962
Bot-Commit: Rubber Stamper <rubber-stamper@appspot.gserviceaccount.com>
Reviewed-by: Slava Egorov <vegorov@google.com>
Auto-Submit: Daco Harkes <dacoharkes@google.com>
Commit-Queue: Slava Egorov <vegorov@google.com>
2024-05-23 19:00:50 +00:00
Ryan Macnak 9077bf991f [vm, gc] Incremental compaction, take 2.
- Fix missing store buffer flush when --marker_tasks=0.
- Fix passing untagged pointer to store barrier check on ARM/ARM64 (6bc417dd17).
- Fix passing uninitialized header to store barrier check on ARM64/RISCV (1447193053).

TEST=ci
Bug: https://github.com/dart-lang/sdk/issues/52513
Bug: https://github.com/dart-lang/sdk/issues/55754
Change-Id: Id2aa95b6d776b82d83464cde0d00e6f3b29b7b77
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/367202
Commit-Queue: Ryan Macnak <rmacnak@google.com>
Reviewed-by: Alexander Aprelev <aam@google.com>
2024-05-21 16:33:00 +00:00
Ryan Macnak 42ec219908 Revert "[vm, gc] Incremental compaction."
This reverts commit bc0f02e4c8.

Reason for revert: https://github.com/dart-lang/sdk/issues/55754

Original change's description:
> [vm, gc] Incremental compaction.
>
> At the beginning of a major GC cycle, select some mostly-empty pages to be evacuated. Mark the pages and the objects on these pages. Apply a write barrier for stores creating old -> evacuation candidate pointers, and discover any such pointers that already exist during marking.
>
> At the end of a major GC cycle, evacuate objects from these pages. Forward pointers of objects in the remembered set and new-space. Free the evacuated pages.
>
> This compaction is incremental in the sense that creating the remembered set is interleaved with mutator execution. The evacuation step, however, is stop-the-world.
>
> Write-barrier elimination for x.slot = x is removed. Write-barrier elimination for x.slot = constant is removed in the JIT, kept for AOT but snapshot pages are marked as never-evacuate.
>
> TEST=ci
> Bug: https://github.com/dart-lang/sdk/issues/52513
> Change-Id: Icbc29ef7cb662ef8759b8c1d7a63b7af60766281
> Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/357760
> Reviewed-by: Alexander Aprelev <aam@google.com>
> Commit-Queue: Ryan Macnak <rmacnak@google.com>

Bug: https://github.com/dart-lang/sdk/issues/52513
Change-Id: I565ad6c0fca283d33f605c10f181bc0a59e7d2b2
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/366965
Reviewed-by: Ryan Macnak <rmacnak@google.com>
Bot-Commit: Rubber Stamper <rubber-stamper@appspot.gserviceaccount.com>
Commit-Queue: Alexander Aprelev <aam@google.com>
Auto-Submit: Ryan Macnak <rmacnak@google.com>
Reviewed-by: Alexander Aprelev <aam@google.com>
2024-05-17 18:03:42 +00:00
Ryan Macnak bc0f02e4c8 [vm, gc] Incremental compaction.
At the beginning of a major GC cycle, select some mostly-empty pages to be evacuated. Mark the pages and the objects on these pages. Apply a write barrier for stores creating old -> evacuation candidate pointers, and discover any such pointers that already exist during marking.

At the end of a major GC cycle, evacuate objects from these pages. Forward pointers of objects in the remembered set and new-space. Free the evacuated pages.

This compaction is incremental in the sense that creating the remembered set is interleaved with mutator execution. The evacuation step, however, is stop-the-world.

Write-barrier elimination for x.slot = x is removed. Write-barrier elimination for x.slot = constant is removed in the JIT, kept for AOT but snapshot pages are marked as never-evacuate.

TEST=ci
Bug: https://github.com/dart-lang/sdk/issues/52513
Change-Id: Icbc29ef7cb662ef8759b8c1d7a63b7af60766281
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/357760
Reviewed-by: Alexander Aprelev <aam@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2024-05-16 23:26:08 +00:00
Ryan Macnak 8c1de038e0 [vm, compiler] Allow targeting TSAN or MSAN by passing a flag to gen_snapshot.
Add check that the snapshot and runtime agree on whether to use MSAN. We already have this check for TSAN.

TEST=vm/dart/sanitizer_compatibility_test
Bug: https://github.com/dart-lang/sdk/issues/55637
Bug: https://github.com/dart-lang/sdk/issues/55638
Change-Id: I320e6f55cd59209ce6e58a82ac205a87c8a60a84
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/365487
Reviewed-by: Daco Harkes <dacoharkes@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
Reviewed-by: Ivan Inozemtsev <iinozemtsev@google.com>
Reviewed-by: Siva Annamalai <asiva@google.com>
2024-05-08 17:03:59 +00:00
Vyacheslav Egorov 2a2781edff [vm] Add vm:align-loops pragma
This pragma forces compiler to align loop headers within the
function by architecture specific boundary: 32 bytes on X64
and ARM64 (with the exception of Apple Silicon, which explicitly
discourages aligning branch targets in the optimization manual).

Current implementation is rather naive and does not do any
attempt to decide whether aligning is actually profitable
based on loop body itself.

I have found this pragma to be helpful both to stabilize
benchmark results and achieve better performance
for tight loops on Intel hardware.

Issue https://github.com/dart-lang/sdk/issues/55522

TEST=vm/dart/align_loops_test

Cq-Include-Trybots: luci.dart.try:vm-aot-linux-product-x64-try,vm-aot-linux-debug-x64c-try,vm-aot-linux-debug-x64-try,vm-aot-linux-release-arm64-try,vm-aot-linux-release-simarm_x64-try,vm-aot-linux-release-x64-try,vm-aot-mac-product-arm64-try,vm-aot-mac-release-arm64-try,vm-aot-mac-release-x64-try,vm-aot-obfuscate-linux-release-x64-try,vm-aot-optimization-level-linux-release-x64-try,vm-aot-win-release-x64-try,vm-aot-win-debug-arm64-try,vm-aot-win-debug-x64-try,vm-aot-win-debug-x64c-try,vm-aot-win-product-x64-try,vm-aot-win-release-arm64-try,vm-aot-linux-debug-simarm_x64-try,vm-aot-linux-debug-simriscv64-try,vm-aot-dwarf-linux-product-x64-try,vm-aot-android-release-arm64c-try,vm-aot-android-release-arm_x64-try
Change-Id: Ic22fb90d85e7fdebeeaa3908a43328c59436ab58
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/364121
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Commit-Queue: Slava Egorov <vegorov@google.com>
2024-04-24 08:52:18 +00:00
Tess Strickland 671f271f58 [vm/compiler] More consolidation of Store assembler methods.
Add OperandSize arguments to the non-compressed Store methods so that
the compressed Store methods can be implemented as calls to the
corresponding non-compressed method using kObjectBytes. This makes it
so that all compressed Store methods are now non-virtual.

Add a scratch register argument to all Store methods that involve a
write barrier that defaults to TMP. Originally only the IA32
implementation took a scratch register, with the others using TMP or
TMP2 internally.

Since all architectures can represent a register/offset pair as an
Address without losing information, make all the offset-based load
and store methods have an implementation that creates an Address or
FieldAddress and calls the corresponding address-based store method.
This makes all the offset-based load and store methods non-virtual.

After this, most of the Store methods are non-virtual, with
only the base methods used to implement them as virtual:

* Store
* StoreRelease
* StoreObjectIntoObjectNoBarrier
* StoreBarrier
* ArrayStoreBarrier
* VerifyStoreNeedsNoWriteBarrier (for DEBUG use only)

The Load methods can't be consolidated quite so much, as the
base methods for handling non-Smi compressed pointers must be defined
per-architecture, as each compressed pointer architecture handles
adding the upper bits for the heap separately.

Have LoadFieldInstr::EmitNativeCode use Assembler::LoadToSlot when the
result location is a single integer register and
StoreFieldInstr::EmitNativeCode use Assembler::StoreToSlot and
Assembler::StoreToSlotNoBarrier when the value location is a single
integer register to avoid code duplication between those methods.

Handle both compressed and uncompressed Smi fields in LoadFromSlot.

TEST=ci (refactoring)

Cq-Include-Trybots: luci.dart.try:vm-aot-android-release-arm64c-try,vm-aot-linux-debug-x64-try,vm-aot-linux-debug-x64c-try,vm-aot-mac-release-arm64-try,vm-aot-mac-release-x64-try,vm-aot-obfuscate-linux-release-x64-try,vm-aot-optimization-level-linux-release-x64-try,vm-aot-win-debug-arm64-try,vm-appjit-linux-debug-x64-try,vm-asan-linux-release-x64-try,vm-checked-mac-release-arm64-try,vm-eager-optimization-linux-release-ia32-try,vm-eager-optimization-linux-release-x64-try,vm-ffi-android-debug-arm-try,vm-ffi-android-debug-arm64c-try,vm-ffi-qemu-linux-release-arm-try,vm-ffi-qemu-linux-release-riscv64-try,vm-linux-debug-ia32-try,vm-linux-debug-x64c-try,vm-mac-debug-arm64-try,vm-mac-debug-x64-try,vm-msan-linux-release-x64-try,vm-reload-linux-debug-x64-try,vm-reload-rollback-linux-debug-x64-try,vm-ubsan-linux-release-x64-try,vm-win-debug-x64-try,vm-win-release-ia32-try
Change-Id: I60cc03776af220ed87918664bb4b9abafff2788a
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/360641
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Commit-Queue: Tess Strickland <sstrickl@google.com>
Reviewed-by: Daco Harkes <dacoharkes@google.com>
2024-04-04 10:41:15 +00:00
Tess Strickland 9fc280a7f6 [vm/compiler] Add all Compressed Assembler methods to AssemblerBase.
Remove CompareWithCompressedFieldFromOffset, which has no uses.

Rename the LoadFromOffset and StoreFromOffset methods that took
Addresses to Load and Store, respectively. This makes the names
of the Assembler methods more uniform:

  * Takes an address: Load, Store, LoadField, LoadCompressedField,
    StoreIntoObject, StoreCompressedIntoObject, LoadSmi,
    LoadCompressedSmi, etc.
  * Takes a base register and an offset: LoadFromOffset, StoreToOffset,
    LoadFieldFromOffset, LoadCompressedFieldFromOffset,
    StoreIntoObjectOffset, StoreCompressedIntoObjectOffset,
    LoadSmiFromOffset, LoadCompressedSmiFromOffset, etc.

Create AssemblerBase methods for loading and storing compressed
pointers that weren't already there, as well as the corresponding
methods for loading and storing uncompressed values.

Make non-virtual methods that load and store uncompressed fields
that call the corresponding method for loading from and storing to
memory regions, adjusting the address or offset accordingly. This
avoids needing per-architecture overrides for these.

Make non-virtual methods that load compressed fields, calling the
corresponding method for loading a compressed value from a memory
region. (Since compressed pointers are only stored in Dart objects,
and stores into a Dart object may require a barrier, there is no
method for storing a compressed value into an arbitrary memory region.)

Create pure virtual methods for loading from or storing to an Address
or any method that does not have both an Address-taking and a
base register and offset pair-taking version (e.g., LoadAcquire).

Create methods for loading from or storing to a base register
and an offset. The base implementation takes the base register and
offset and creates an Address from it, then calls the Address-taking
equivalent. These methods are non-virtual when the implementation is
the same on all architectures and virtual to allow overriding when
necessary.

Make a non-virtual method for loading uncompressed Smis, since all
architectures have the same code for this, including the DEBUG check.

If compressed pointers are not being used, all the methods for
compressed pointers are non-virtual methods that call the
corresponding method for uncompressed values.

If compressed pointers are being used:

* Install pure virtual methods for loading compressed values from
  and storing compressed values to an Address or any method that does
  not have both an Address-taking and a base register and offset
  pair-taking version (e.g., LoadAcquireCompressed).

* Install virtual methods for loading compressed values from and
  storing compressed values to a base register and offset. Like the
  uncompressed implementation, the base implementation of these
  create an Address and call the Address-taking equivalent, and these
  implementations are overridden on ARM64.

* Install a non-virtual method for loading compressed Smis, since the
  only difference is that it loads a zero-extended 32-bit value, which
  AssemblerBase can do.

TEST=ci (refactoring only)

Change-Id: I934791d26a6e2cdaa6ac5f188b0fd89dbdc491d1
Cq-Include-Trybots: luci.dart.try:vm-aot-android-release-arm64c-try,vm-aot-android-release-arm_x64-try,vm-aot-linux-debug-x64-try,vm-aot-linux-debug-x64c-try,vm-aot-mac-release-arm64-try,vm-aot-mac-release-x64-try,vm-aot-obfuscate-linux-release-x64-try,vm-aot-optimization-level-linux-release-x64-try,vm-aot-win-debug-arm64-try,vm-appjit-linux-debug-x64-try,vm-asan-linux-release-x64-try,vm-checked-mac-release-arm64-try,vm-eager-optimization-linux-release-ia32-try,vm-eager-optimization-linux-release-x64-try,vm-ffi-android-debug-arm-try,vm-ffi-android-debug-arm64c-try,vm-ffi-qemu-linux-release-arm-try,vm-ffi-qemu-linux-release-riscv64-try,vm-linux-debug-ia32-try,vm-linux-debug-x64c-try,vm-mac-debug-arm64-try,vm-mac-debug-x64-try,vm-msan-linux-release-x64-try,vm-reload-linux-debug-x64-try,vm-reload-rollback-linux-debug-x64-try,vm-ubsan-linux-release-x64-try,vm-win-debug-arm64-try,vm-win-debug-x64-try,vm-win-release-ia32-try
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/359861
Reviewed-by: Daco Harkes <dacoharkes@google.com>
Commit-Queue: Tess Strickland <sstrickl@google.com>
Reviewed-by: Alexander Markov <alexmarkov@google.com>
2024-04-02 14:54:13 +00:00
Ryan Macnak a6dff920eb [vm, compiler] Remove dead branch from ARM64 large offset generation.
This looks like it started as a copy of the MIPS code or LoadImmediate.

TEST=ci
Bug: https://github.com/dart-lang/sdk/issues/55191
Change-Id: I3bd78a45d6de5efbbed52d3a7d1e7cd5ca19ddb8
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/359701
Reviewed-by: Alexander Aprelev <aam@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2024-03-25 22:07:13 +00:00
Tess Strickland 0d3ade255b [vm/compiler] Limit exposure of untagged pointers to managed memory.
After https://dart-review.googlesource.com/c/sdk/+/330600, there were
more chances for the optimizing compiler to introduce or move
GC-triggering instructions like allocations or boxings between the
retrieval of an untagged pointer to GC-moveable memory and its use.

To limit the chance of this happening, this CL removes the explicit
loading of the untagged payload address when building the initial
flow graph in most cases when the array is not known to be an external
array (an external string, an external typed data object, or an FFI
Pointer).

The remaining case is during view allocation, which extracts the
payload address of the base typed data object underlying the view
(which may be GC-movable) to calculate the payload address that should
be stored in the data field of the view object. See
https://github.com/dart-lang/sdk/issues/54884.

During canonicalization of LoadIndexed, StoreIndexed, and MemoryCopy
instructions, if the cid of an array input is an external array
(external string, external typed data object, or Pointer), then a
LoadField instruction that extracts the untagged payload address
is inserted before the instruction and the corresponding input is
rebound to that LoadField instruction.

Once all compiler passes that involve code motion have been performed,
a new pass looks for LoadIndexed, StoreIndexed, or MemoryCopy where
the cid stored in the instruction for the array is a typed data cid.
In these cases, if the array is not an internal typed data object,
then the payload address is extracted. Waiting until this point ensures
that no GC-triggering instructions are inserted between the extraction
of the payload address and the use. (Internal typed data objects are
left as-is because the payload address is inside the object itself
and doesn't require indirection through the data field of the object).

This CL also replaces code conditional on the array cid with code
that is instead conditional on the array element representation in
cases where it makes sense to do so, since this is a less brittle
check than checking the array cid (e.g., checking for kUnboxedInt8
to load, store, or copy an signed byte from an array instead of
listing all possible array cids that store signed bytes).

This CL also fixes an issue with the ARM64 assembler where calling
LoadFromOffset with an Address that has a non-Offset type would
silently generate bad code instead of triggering the ASSERT in
PrepareLargeOffset.

TEST=vm/dart/typed_list_index_checkbound_il_test

Issue: https://github.com/dart-lang/sdk/issues/54710
Cq-Include-Trybots: luci.dart.try:vm-aot-android-release-arm64c-try,vm-aot-android-release-arm_x64-try,vm-aot-linux-debug-x64-try,vm-aot-linux-debug-x64c-try,vm-aot-mac-release-arm64-try,vm-aot-mac-release-x64-try,vm-aot-obfuscate-linux-release-x64-try,vm-aot-optimization-level-linux-release-x64-try,vm-aot-win-debug-arm64-try,vm-appjit-linux-debug-x64-try,vm-asan-linux-release-x64-try,vm-checked-mac-release-arm64-try,vm-eager-optimization-linux-release-ia32-try,vm-eager-optimization-linux-release-x64-try,vm-ffi-android-debug-arm-try,vm-ffi-android-debug-arm64c-try,vm-ffi-qemu-linux-release-arm-try,vm-ffi-qemu-linux-release-riscv64-try,vm-fuchsia-release-x64-try,vm-linux-debug-ia32-try,vm-linux-debug-x64-try,vm-linux-debug-x64c-try,vm-mac-debug-arm64-try,vm-mac-debug-x64-try,vm-msan-linux-release-x64-try,vm-reload-linux-debug-x64-try,vm-reload-rollback-linux-debug-x64-try,vm-ubsan-linux-release-x64-try,vm-win-debug-arm64-try,vm-win-debug-x64-try,vm-win-release-ia32-try
Change-Id: I25b5f314943e9254d3d28986d720a5d47f12feeb
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/352363
Reviewed-by: Daco Harkes <dacoharkes@google.com>
Reviewed-by: Ryan Macnak <rmacnak@google.com>
Commit-Queue: Tess Strickland <sstrickl@google.com>
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Reviewed-by: Martin Kustermann <kustermann@google.com>
2024-03-22 10:12:39 +00:00
Tess Strickland ecf5abcbd3 [vm/compiler] Better handle small array element representations.
Moves RepresentationOfArrayElement out of LoadIndexed and StoreIndexed
into RepresentationUtils. Adjusts RepresentationOfArrayElement
to work for all concrete typed data classes. Changes
RepresentationOfArrayElement to return the precise representation of
the array element, which requires adding two new representations,
kUnboxedInt8 and kUnboxedInt16.

Remove Address::OperandSizeFor and its only (ignored) use in the
RISCV assembler and change Address::OperandSizeFor in the ARM and
ARM64 assemblers to use RepresentationUtils::OperandSize and RepresentationUtils::RepresentationOfArrayElement appropriately.

Add Boxing::NativeRepresentation, which converts representations for
unboxed integers smaller than 4 bytes to kUnboxedIntPtr and otherwise
returns the original representation. This mimics the current semantics
for LoadIndexed and StoreIndexed where returned values represented by
unboxed integer values smaller than 4 bytes are zero or sign extended
to word size appropriately, and received values represented by unboxed
integer values smaller than 4 bytes are appropriately truncated from a
word sized signed integer.

Create LoadIndexedInstr::ReturnRepresentation and
StoreIndexedInstr::ValueRepresentation, which use
Boxing::NativeRepresentation to convert the precise representation
returned by RepresentationUtils::RepresentationOfArrayElement to
the actual returned/expected representation for those instructions.
Also use Boxing::NativeRepresentation to appropriately adjust
the representations used for SIMD operations returning int8_t.

Add checks that unboxing and integer conversion never get
representations which result in a different representation when
passed to Boxing::NativeRepresentation, as those instructions do
not currently work with unboxed integer representations smaller than
4 bytes. (Adding such support can be done in a future CL.)

Inside the optimizing compiler, use the precise representation of the
array element where appropriate. That is:

* Range analysis
* Type propagation
* Redundancy elimination

This CL also cleans up how Representations are printed to C, making
that part of RepresentationUtils. It also removes the representation
printing and parsing utils from Location since they were only used by
the original IL serializer and deserializer, which has been removed.
It also renames RepresentationUtils::IsUnsigned to IsUnsignedInteger,
to make it clear that it only returns true for unboxed integer
representations.

TEST=standalone/bytedata_test

Fixes: https://github.com/dart-lang/sdk/issues/54622
Cq-Include-Trybots: luci.dart.try:vm-aot-android-release-arm64c-try,vm-aot-android-release-arm_x64-try,vm-aot-linux-debug-x64-try,vm-aot-linux-debug-x64c-try,vm-aot-mac-release-arm64-try,vm-aot-mac-release-x64-try,vm-aot-obfuscate-linux-release-x64-try,vm-aot-optimization-level-linux-release-x64-try,vm-aot-win-debug-arm64-try,vm-aot-win-debug-x64-try,vm-appjit-linux-debug-x64-try,vm-asan-linux-release-x64-try,vm-checked-mac-release-arm64-try,vm-eager-optimization-linux-release-ia32-try,vm-eager-optimization-linux-release-x64-try,vm-ffi-android-debug-arm-try,vm-ffi-android-debug-arm64c-try,vm-ffi-qemu-linux-release-arm-try,vm-ffi-qemu-linux-release-riscv64-try,vm-fuchsia-release-x64-try,vm-linux-debug-ia32-try,vm-linux-debug-x64-try,vm-linux-debug-x64c-try,vm-mac-debug-arm64-try,vm-mac-debug-x64-try,vm-msan-linux-release-x64-try,vm-reload-linux-debug-x64-try,vm-reload-rollback-linux-debug-x64-try,vm-ubsan-linux-release-x64-try,vm-win-debug-arm64-try,vm-win-debug-x64-try,vm-win-release-ia32-try
Change-Id: I8c0dab911463ee4d0c55cd59ffea9d01e0f0bb7c
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/354885
Reviewed-by: Slava Egorov <vegorov@google.com>
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Commit-Queue: Tess Strickland <sstrickl@google.com>
2024-03-13 14:14:55 +00:00
Ryan Macnak 58bf203064 [VM] Add support for allocation tracing in AOT
TEST=Manual
Bug: https://github.com/dart-lang/sdk/issues/51234
Change-Id: I4ab75bb85898a41dfb091b38402711170fd3b972
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/271420
Reviewed-by: Ryan Macnak <rmacnak@google.com>
Commit-Queue: Ben Konyi <bkonyi@google.com>
2024-01-17 13:50:49 +00:00
Tess Strickland 1827fcbf68 [vm/compiler] Fix uses of constant indexes in LoadIndexed/StoreIndexed.
Previously, CanBeImmediateIndex calculated the scaling factor for the
index using Instance::ElementSizeFor. However, the LoadIndexed and
StoreIndexed instructions which use this function have an index_scale_
field that is not necessarily the same as the element size for the
class id. This means the displacement calculated within
CanBeImmediateIndex can differ from the actual displacement calculated
within ElementAddressForIntIndex, causing the bug seen by the fuzzer.

This CL moves the check in CanBeImmediateIndex to a new static
method Assembler::AddressCanHoldConstantIndex. In addition to the
original arguments to CanBeImmediateIndex, the new static method takes
an index_scale argument, so the field value can be passed appropriately.

It also adds an is_external argument on X64 and IA32 to match the other
architectures, since assuming a non-external typed data object could
cause a register to be used in cases where it isn't necessary.

TEST=vm/dart/regress_54486

Fixes: https://github.com/dart-lang/sdk/issues/54486
Change-Id: Ia553fb7da0500113b35f8d9af91a52df55437a3c
Cq-Include-Trybots: luci.dart.try:vm-aot-linux-debug-x64-try,vm-linux-debug-ia32-try,vm-aot-linux-debug-simarm_x64-try,vm-aot-linux-debug-simriscv64-try,vm-aot-mac-release-arm64-try
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/345002
Reviewed-by: Daco Harkes <dacoharkes@google.com>
2024-01-08 15:46:01 +00:00
Vyacheslav Egorov dcac60b672 [vm/aot] Fix BoxInt64 in deferred units
When generating code for deferred units compiler
can't emit PC relative call to the shared Mint allocation
stub. This causes compiler to emit an indirect call
through a Code object. Such calls clobber CODE_REG
which is actually an allocatable register.

Fix this by using non-allocatable register instead of
CODE_REG when generating indirect calls through
Code object in AOT mode. Callees don't expect
anything useful in CODE_REG anyway because AOT
calling convetion does not use it.

TEST=vm/cc/{BranchLinkPreservesRegisters,JumpAndLinkPreservesRegisters,CallCodePreservesRegisters}

Bug: b/242559057
Cq-Include-Trybots: luci.dart.try:vm-aot-linux-release-arm64-try,vm-aot-linux-release-simarm_x64-try,vm-aot-linux-release-x64-try,vm-aot-linux-product-x64-try,vm-aot-obfuscate-linux-release-x64-try,vm-aot-optimization-level-linux-release-x64-try,vm-aot-linux-debug-simriscv64-try,vm-ffi-qemu-linux-release-riscv64-try
Change-Id: Ib1fdc1c104d0269d41bb1ab9cbe292ad28c7cd49
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/338127
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Commit-Queue: Slava Egorov <vegorov@google.com>
2023-11-28 13:15:56 +00:00
Daco Harkes 0cd55a18c1 [vm] Introduce cachable idempotent calls
Adds a `CachableIdempotentCallInstr` that can be invoked via
`@pragma('vm:cachable-idempotent')` if the call-sites is force
optimized.

The object pool is not visited by the scavenger. So, we store the
results as unboxed integers. Consequently, only dart functions that
return integers can be cached.

Cachable idempotent calls should never be inlined. After the first
call the function not be called again.

The call itself is on a slow path to avoid register spilling on the
fast path.

TEST=vm/cc/IRTest_CachableIdempotentCall
TEST=runtime/tests/vm/dart/cachable_idempotent_test.dart

Bug: https://github.com/dart-lang/sdk/issues/51618
Change-Id: I612e896f27add76f57796c060157e14cc687a0fd
Cq-Include-Trybots: luci.dart.try:vm-aot-android-release-arm64c-try,vm-aot-android-release-arm_x64-try,vm-aot-asan-linux-release-x64-try,vm-aot-linux-debug-simarm_x64-try,vm-aot-linux-debug-simriscv64-try,vm-aot-mac-release-arm64-try,vm-aot-mac-release-x64-try,vm-aot-msan-linux-release-x64-try,vm-aot-obfuscate-linux-release-x64-try,vm-aot-tsan-linux-release-x64-try,vm-aot-ubsan-linux-release-x64-try,vm-aot-win-debug-arm64-try,vm-aot-win-debug-x64c-try,vm-aot-win-release-x64-try,vm-appjit-linux-debug-x64-try,vm-asan-linux-release-x64-try,vm-checked-mac-release-arm64-try,vm-eager-optimization-linux-release-ia32-try,vm-eager-optimization-linux-release-x64-try,vm-kernel-linux-debug-x64-try,vm-kernel-precomp-linux-release-x64-try,vm-linux-debug-ia32-try,vm-linux-debug-simriscv64-try,vm-linux-debug-x64-try,vm-mac-debug-arm64-try,vm-mac-debug-x64-try,vm-msan-linux-release-x64-try,vm-reload-linux-debug-x64-try,vm-reload-rollback-linux-debug-x64-try,vm-tsan-linux-release-x64-try,vm-ubsan-linux-release-x64-try,vm-win-debug-arm64-try,vm-win-debug-x64-try,vm-win-debug-x64c-try,vm-win-release-ia32-try
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/301601
Reviewed-by: Ryan Macnak <rmacnak@google.com>
Reviewed-by: Martin Kustermann <kustermann@google.com>
2023-10-27 07:55:47 +00:00
Daco Harkes 243cf59776 [vm] Object pool SnapshotBehavior for bootstrapping native functions
`NativeCallInstr::EmitNativeCode` `link_lazily` code path uses the
new snapshotting behavior, and the non-`link_lazily` checks that it's
never snapshotted.

The snapshot behavior argument is threaded from the the EmitNativeCode
to the places where the pool entry is constructed.

Does not yet migrate `kSwitchableCallMissEntryPoint` and
`kMegamorphicCallEntryPoint`.

TEST=CI

Change-Id: I8dd1dc5aa525f888b493856c60ae385087463d02
Cq-Include-Trybots: luci.dart.try:vm-ffi-qemu-linux-release-riscv64-try,vm-linux-debug-simriscv64-try,vm-aot-linux-release-arm64-try,vm-aot-android-release-arm64c-try,vm-aot-win-debug-arm64-try,vm-aot-mac-product-arm64-try,vm-mac-debug-arm64-try,vm-ffi-android-debug-arm-try,vm-ffi-qemu-linux-release-arm-try,vm-linux-debug-ia32-try,vm-linux-debug-x64-try,vm-aot-linux-debug-x64-try
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/328861
Commit-Queue: Daco Harkes <dacoharkes@google.com>
Reviewed-by: Martin Kustermann <kustermann@google.com>
2023-10-18 13:27:26 +00:00
Ryan Macnak ef1c3098a1 [vm, compiler] Implement unboxed SIMD for RISC-V via lowering.
This relands commit 460bd7a03a.

TEST=ci
Change-Id: I0b5e91a3b8b6e8afa3f889afa21afed7c1a7e62c
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/327821
Reviewed-by: Slava Egorov <vegorov@google.com>
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2023-09-27 16:23:38 +00:00
Ryan Macnak 139ff289db [vm, compiler] Allocation canaries.
Before each allocation, check the memory hasn't been touched since page initialization. This more reliably detects the issue fixed in a4381f127c.

TEST=ci
Change-Id: I5c0ed0a18a32515eab2ae90110b5a7e7f48779dc
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/325366
Commit-Queue: Ryan Macnak <rmacnak@google.com>
Reviewed-by: Siva Annamalai <asiva@google.com>
2023-09-15 17:04:55 +00:00
Martin Kustermann 9d876d12b2 [vm] Rename kUsingThreadSanitizer->kTargetUsesThreadSanitizer, include tsan in snapshot flags
TEST=ci
Issue b/287638965

Change-Id: I649b28ac0181761d0927e80b8eff7c8af5fe305a
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/312840
Commit-Queue: Martin Kustermann <kustermann@google.com>
Reviewed-by: Slava Egorov <vegorov@google.com>
2023-07-07 14:42:22 +00:00
Martin Kustermann 2287c76724 [vm] Make AOT compiler use TARGET_USES_THREAD_SANITIZER
The VM has two parts related to TSAN: compiler & runtime.

So far both parts used self-detection whether running with TSAN. This
implies that if AOT runtime runs under TSAN that the AOT compiler then
also has to run under TSAN (which is slow).

We separate the two by making the compiler use
`TARGET_USES_THREAD_SANITIZER`. It will be auto-detected by-default
except when `DART_PRECOPMILER` is set. In the precompiler case we
require the build rules to pass in whether the target runs under
TSAN or not.

Issue b/287638965

TEST=ci

Change-Id: Ib333a8a69ed2d7bdca7596014a0d25b103af25b6
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/312480
Commit-Queue: Martin Kustermann <kustermann@google.com>
Reviewed-by: Slava Egorov <vegorov@google.com>
2023-07-06 08:44:33 +00:00
Ryan Macnak c4795a7550 [vm, compiler] Don't do safepoint transitions in generated code under TSAN.
Go to the runtime so TSAN sees the instrumented access to Thread::safepoint_state_, avoiding false data race reports.

TEST=tsan
Bug: https://github.com/dart-lang/sdk/issues/52024
Change-Id: Ic686bac2221d8ac6b9865ce9c82a4c36711037a7
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/295740
Reviewed-by: Alexander Aprelev <aam@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2023-04-17 22:37:57 +00:00
Ryan Macnak de2abc6091 [vm] Update NULL to nullptr in runtime/vm/compiler.
TEST=build
Change-Id: I54cd75bbc942e11c4d719edcc64640da67077634
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/291965
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2023-03-30 18:23:53 +00:00
Vyacheslav Egorov 65f4a733bb [vm/compiler] Stop pushing arguments in optimized code.
After this change we no longer push outgoing arguments for normal
Dart calls, but instead simply move them into an area reserved for
outgoing arguments at the top of the frame. This allows us to stop
mutating SP and avoid explicit Drop(argc) after each call.

There are still other places in the generated code where we
push something onto the stack either to free a temporary
register or spill a value across a slow-path call.

This is the first step towards switching to native SP on ARM64.

# Code Size Impact

I have tested this on a large internal application and got the
following size delta

## ARM

|        | Before   | After    | Delta   |       |
|--------|----------|----------|---------|-------|
| ROData | 6366632  | 6463680  | +97048  | +1.5% |
| Code   | 22714192 | 22043984 | -670208 | -2.9% |
| Total  | 33723701 | 33150477 | -573224 | -1.6% |

## ARM64

|        | Before   | After    | Delta   |       |
|--------|----------|----------|---------|-------|
| ROData | 7122032  | 7214288  | +92256  | +1.3% |
| Code   | 21607196 | 20741788 | -865408 | -4.0% |
| Total  | 33375769 | 32602544 | -773225 | -2.3% |

TEST=ci

Cq-Include-Trybots: luci.dart.try:vm-kernel-precomp-nnbd-linux-release-x64-try,vm-kernel-precomp-linux-release-simarm-try,vm-kernel-precomp-linux-debug-x64-try,vm-kernel-precomp-linux-debug-x64c-try,vm-kernel-precomp-linux-product-x64-try,vm-precomp-ffi-qemu-linux-release-riscv64-try,vm-precomp-ffi-qemu-linux-release-arm-try,vm-kernel-precomp-nnbd-linux-release-simarm64-try,vm-kernel-nnbd-linux-release-simarm64-try
Bug: https://github.com/dart-lang/sdk/issues/39083
Change-Id: Icace0c986285b9c16e41786cded44f88277bd25f
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/282029
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Commit-Queue: Slava Egorov <vegorov@google.com>
2023-02-16 19:22:45 +00:00
Ryan Macnak 8a37b70a53 [vm, compiler] More consistently support large load/store offsets.
TEST=ci
Change-Id: I7691808679c57c6f16f3859641cf52b9e606e304
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/275381
Reviewed-by: Alexander Markov <alexmarkov@google.com>
Commit-Queue: Ryan Macnak <rmacnak@google.com>
2022-12-14 22:17:35 +00:00
Alexander Aprelev e07321ec9d [vm] Factor StringEqual out of platform-specific intrinsifiers into single asm_intrinsifier.
TEST=ci
Change-Id: Iaab92c4a4c5a04355778c17ce564672c1e97814c
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/272349
Reviewed-by: Martin Kustermann <kustermann@google.com>
Commit-Queue: Alexander Aprelev <aam@google.com>
2022-12-11 02:49:28 +00:00
Tess Strickland a43d3cb993 [vm/compiler] Use CombineHashes/FinalizeHash methods in intrinsifier.
AsmIntrinsifier::OneByteString_getHashCode now uses the CombineHashes
and FinalizeHash Assembler methods introduced in 49f998dc31.

To avoid having to check for 0 again after masking the result of
FinalizeHash to fit the desired bit size, we create a more general
FinalizeHashForSize that also takes the desired bit size of the result.

The intrinsified versions for ARM/ARM64/RISCV are also modified to
remove the special casing for the empty string, and instead just check
the size of the string against the loop counter at the start of the
loop, similarly to X64/IA32. This is less efficient for the empty
string case, but avoids the need to create a version of FinalizeHash
that elides the zero check.

TEST=ci

Cq-Include-Trybots: luci.dart.try:vm-kernel-precomp-dwarf-linux-product-x64-try,vm-kernel-precomp-linux-product-x64-try,vm-kernel-precomp-linux-release-x64-try,vm-kernel-precomp-nnbd-mac-release-arm64-try,vm-kernel-precomp-nnbd-linux-release-simarm_x64-try,vm-kernel-precomp-linux-release-simarm-try,vm-kernel-precomp-nnbd-linux-release-x64-try,vm-kernel-precomp-nnbd-linux-release-simarm64-try,vm-kernel-precomp-nnbd-linux-debug-simriscv64-try,vm-kernel-precomp-linux-debug-x64c-try,vm-kernel-nnbd-linux-debug-simriscv64-try,vm-kernel-linux-release-simarm-try,vm-kernel-linux-release-simarm64-try,vm-kernel-linux-release-ia32-try,vm-kernel-nnbd-linux-release-simarm-try,vm-kernel-nnbd-linux-release-simarm64-try,vm-kernel-nnbd-linux-release-ia32-try,vm-kernel-nnbd-mac-release-arm64-try,vm-kernel-linux-debug-x64c-try
Change-Id: I53db731acb8bf35d16efb55fa2c5a79d8302399f
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/272800
Reviewed-by: Daco Harkes <dacoharkes@google.com>
Commit-Queue: Tess Strickland <sstrickl@google.com>
2022-12-08 12:58:28 +00:00
Tess Strickland 49f998dc31 [vm/compiler] Handle hash caches in the InstantiateTypeArguments stubs.
Lower the threshold for converting from a linear to a hash-based cache
on most architectures from 500 to 10.

Due to register pressure, the InstantiateTypeArguments stub on IA32
continues to go to the runtime for hash caches, and so we do not
lower the threshold for converting to a hash-based cache there.

The following are benchmark results for those benchmark that use enough
Instantiations to trigger the use of hash-based caches. In the following
tables, "Results 1" denotes the benchmark results from only this change,
whereas "Results 2" include from comparing to the results prior to
4f925105cf, when only linear caches were used.

Dart AOT:

* InstantiateTypeArguments.Instantiate100

Arch   | CPU            | Results 1 | Results 2
-------|----------------|-----------------------
ARM    | Odroid-C2      |   382.8%  |   381.5%
ARM    | Raspberry Pi 4 |   486.7%  |   449.2%
ARM64  | Odroid-C2      |   328.1%  |   372.8%
ARM64  | Raspberry Pi 4 |  1283%    |  1281%
ARM64C | Raspberry Pi 4 |  2353%    |  2811%
X64    | Intel Xeon     |   568.7%  |   584.9%

* InstantiateTypeArguments.Instantiate1000

Arch   | CPU            | Results 1  | Results 2
-------|----------------|------------------------
ARM    | Odroid-C2      |   743.7%   |  3821%
ARM    | Raspberry Pi 4 |   486.7%   |  3218%
ARM64  | Odroid-C2      |   584.7%   |  3222%
ARM64  | Raspberry Pi 4 |   430.7%   |  8172%
ARM64C | Raspberry Pi 4 |   491.4%   | 16699%
X64    | Intel Xeon     |   954.1%   |  5528%


Dart JIT:

* InstantiateTypeArguments.Instantiate100

Arch   | CPU            | Results 1 | Results 2
-------|----------------|-----------------------
ARM    | Raspberry Pi 4 |   315.7%  |   295.1%
ARM64  | Raspberry Pi 4 |  1070%    |  1058%
ARM64C | Raspberry Pi 4 |  1769%    |  2095%
X64    | Intel Xeon     |   507.4%  |   496.2%

* InstantiateTypeArguments.Instantiate1000

Arch   | CPU            | Results 1 | Results 2
-------|----------------|-----------------------
ARM    | Raspberry Pi 4 |   565.2%  |  2550%
ARM64  | Raspberry Pi 4 |   406.8%  |  7375%
ARM64C | Raspberry Pi 4 |   379.6%  | 12996%
X64    | Intel Xeon     |   807.9%  |  4459%

During work on this change, an issue was found where cache lookups
in the stub on ARM64C always failed and went to runtime, even with
the old linear-only caches, hence the much larger performance gains
in those rows above.

TEST=vm/cc/TypeArguments_Cache_{Some,Many}Instantiations

Fixes: https://github.com/dart-lang/sdk/issues/48344
Change-Id: I3d29566ba0582502954c9fc59626ceb8fd40317a
Cq-Include-Trybots: luci.dart.try:vm-kernel-precomp-dwarf-linux-product-x64-try,vm-kernel-precomp-linux-product-x64-try,vm-kernel-precomp-linux-release-x64-try,vm-kernel-precomp-nnbd-mac-release-arm64-try,vm-kernel-precomp-nnbd-linux-release-simarm_x64-try,vm-kernel-precomp-linux-release-simarm-try,vm-kernel-precomp-nnbd-linux-release-x64-try,vm-kernel-precomp-nnbd-linux-release-simarm64-try,vm-kernel-precomp-nnbd-linux-debug-simriscv64-try,vm-kernel-precomp-tsan-linux-release-x64-try,vm-kernel-tsan-linux-release-x64-try,vm-kernel-precomp-linux-debug-x64c-try,vm-kernel-nnbd-linux-debug-simriscv64-try,vm-kernel-linux-release-simarm-try,vm-kernel-linux-release-simarm64-try,vm-kernel-linux-release-ia32-try,vm-kernel-nnbd-linux-release-simarm-try,vm-kernel-nnbd-linux-release-simarm64-try,vm-kernel-nnbd-linux-release-ia32-try,vm-kernel-nnbd-mac-release-arm64-try,vm-kernel-linux-debug-x64c-try
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/270702
Reviewed-by: Ryan Macnak <rmacnak@google.com>
Commit-Queue: Tess Strickland <sstrickl@google.com>
Reviewed-by: Martin Kustermann <kustermann@google.com>
2022-12-01 10:15:58 +00:00
Tess Strickland 333d924504 [vm/compiler] Make InstantiateTypeArgs stubs architecture independent.
TEST=ci

Bug: https://github.com/dart-lang/sdk/issues/48344
Change-Id: I7c0cee827a09d981e6e65802304a361ace7ce501
Cq-Include-Trybots: luci.dart.try:vm-kernel-precomp-dwarf-linux-product-x64-try,vm-kernel-precomp-linux-product-x64-try,vm-kernel-precomp-linux-release-x64-try,vm-kernel-precomp-nnbd-mac-release-arm64-try,vm-kernel-precomp-nnbd-linux-release-simarm_x64-try,vm-kernel-precomp-linux-release-simarm-try,vm-kernel-precomp-nnbd-linux-release-x64-try,vm-kernel-precomp-nnbd-linux-release-simarm64-try,vm-kernel-precomp-nnbd-linux-debug-simriscv64-try
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/270102
Reviewed-by: Martin Kustermann <kustermann@google.com>
Reviewed-by: Ryan Macnak <rmacnak@google.com>
2022-11-28 15:00:20 +00:00