blob: b914d8a759d1ad17abdea866ffdb864f28082254 [file] [edit]
// Copyright (c) 2026, 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.
/// Imported definitions that need to be provided to run `dart2wasm` apps
/// without JavaScript.
///
/// These definitions are currently incomplete. Once all externs in the Dart SDK
/// are implemented with these imports, the `dart2wasm_standalone` target can
/// run without `js_interop`. This will enable embedders without JavaScript
/// support to run `dart2wasm` apps by either:
///
/// - providing `dart:` imports when instantiating the module.
/// - using an external tool like `wasm-merge` to link another module that
/// could provide implementations by e.g. delegating to WASI definitions.
library;
import 'dart:core';
import 'dart:core' as core;
import 'dart:_wasm';
/// Instructs the runtime to invoke `callback(arg)` after the delay in
/// microseconds.
///
/// Returns a handle that can be used with [clearSchedule] to abort the timer.
@pragma("wasm:import", "dart.scheduleOnce")
external WasmExternRef scheduleOnce(
WasmI64 delay,
WasmFunction<WasmVoid Function(WasmAnyRef)> callback,
WasmAnyRef arg,
);
/// Instructs the runtime to invoke `callback(arg)` every `interval`
/// microseconds.
///
/// Returns a handle that can be used with [clearSchedule] to abort the timer.
@pragma("wasm:import", "dart.scheduleRepeated")
external WasmExternRef scheduleRepeated(
WasmI64 interval,
WasmFunction<WasmVoid Function(WasmAnyRef)> callback,
WasmAnyRef arg,
);
/// Instructs the runtime to invoke `callback(arg)` before returning to the
/// event loop.
@pragma("wasm:import", "dart.queueMicrotask")
external WasmVoid queueMicrotask(
WasmFunction<WasmVoid Function(WasmAnyRef)> callback,
WasmAnyRef arg,
);
/// Cancels a schedule created through [scheduleOnce] or [scheduleRepeated].
@pragma("wasm:import", "dart.clearSchedule")
external WasmVoid clearSchedule(WasmExternRef? schedule);
@pragma("wasm:import", "dart.currentTime")
external WasmI64 currentTimeMicros();
/// Convert an array of 16-bit char codes into a string.
@pragma("wasm:import", "dart.stringFromCharCodeArray")
@pragma("wasm:entry-point")
external WasmExternRef stringFromCharCodeArray(
WasmArray<WasmI16> charCodes,
WasmI32 start,
WasmI32 length,
);
/// Convert an array of ascii bytes into a string.
@pragma("wasm:import", "dart.stringFromAsciiBytes")
@pragma("wasm:entry-point")
external WasmExternRef stringFromAsciiBytes(
WasmArray<WasmI8> charCodes,
WasmI32 start,
WasmI32 length,
);
@pragma("wasm:import", "dart.stringLength")
external WasmI32 stringLength(WasmExternRef? string);
@pragma("wasm:import", "dart.stringEquals")
external WasmI32 stringEquals(WasmExternRef? a, WasmExternRef? b);
@pragma("wasm:import", "dart.stringCompare")
external WasmI32 stringCompare(WasmExternRef? a, WasmExternRef? b);
@pragma("wasm:import", "dart.stringCodeUnitAt")
external WasmI32 stringCodeUnitAt(WasmExternRef? a, WasmI32 index);
@pragma("wasm:import", "dart.stringIndexOfString")
external WasmI32 stringIndexOfString(
WasmExternRef? a,
WasmExternRef? b,
WasmI32 start,
);
@pragma("wasm:import", "dart.stringLastIndexOfString")
external WasmI32 stringLastIndexOfString(
WasmExternRef? a,
WasmExternRef? b,
WasmI32 start,
);
/// Specialization for [String.replaceAll] where the pattern is an embedder-
/// managed string.
@pragma("wasm:import", "dart.stringReplaceAllString")
external WasmExternRef? stringReplaceAllString(
WasmExternRef? string,
WasmExternRef? needle,
WasmExternRef? replacement,
);
/// Specialization for [String.replaceAll] where the pattern is an embedder-
/// managed regular expression.
@pragma("wasm:import", "dart.stringReplaceAllRegExp")
external WasmExternRef? stringReplaceAllRegExp(
WasmExternRef? string,
WasmExternRef? needle,
WasmExternRef? replacement,
);
@pragma("wasm:import", "dart.stringSubstring")
external WasmExternRef? stringSubstring(
WasmExternRef? a,
WasmI32 start,
WasmI32 end,
);
@pragma("wasm:import", "dart.stringToLowerCase")
external WasmExternRef? stringToLowerCase(WasmExternRef? string);
@pragma("wasm:import", "dart.stringToUpperCase")
external WasmExternRef? stringToUpperCase(WasmExternRef? string);
@pragma("wasm:import", "dart.stringConcat")
external WasmExternRef? stringConcat(WasmExternRef? a, WasmExternRef? b);
@pragma("wasm:import", "dart.stringRepeat")
external WasmExternRef? stringRepeat(WasmExternRef? string, WasmI32 times);
@pragma("wasm:import", "dart.stringReplaceRange")
external WasmExternRef? stringReplaceRange(
WasmExternRef? string,
WasmI32 start,
WasmI32 end,
WasmExternRef? replacement,
);
/// Writes code units of [string] into [outArray], starting at array position
/// [startIndex].
@pragma("wasm:import", "dart.stringToCodeUnits")
external WasmVoid stringToCodeUnits(
WasmExternRef? string,
WasmArray<WasmI16> outArray,
WasmI32 startIndex,
);
/// Get the frequency of ticks reported by [monotonicClockTicks] in Hz.
///
/// Currently, the only supported values are 1kHz and 1MHz. Attempting to use
/// a stopwatch in Dart will fail if the function returns an unsupported value.
///
/// This function must return the same value every time it is called.
@pragma("wasm:import", "dart.monotonicClockFrequency")
external WasmI32 monotonicClockFrequency();
/// An integer incrementing with [monotonicClockFrequency].
@pragma("wasm:import", "dart.monotonicClockTicks")
external WasmI64 monotonicClockTicks();
/// Creates a weak reference wrapping [originalValue].
///
/// The SDK verifies that [originalValue] is a valid target (not a number,
/// boolean, string, record or FFI type) before calling this.
@pragma("wasm:import", "dart.weakRefCreate")
external WasmExternRef weakRefCreate(WasmAnyRef originalValue);
/// Returns the value wrapped in [weakRefCreate], or null.
@pragma("wasm:import", "dart.weakRefGet")
external WasmAnyRef? weakRefGet(WasmExternRef? weakReference);
/// Creates a new [Expando].
@pragma("wasm:import", "dart.expandoCreate")
external WasmExternRef expandoCreate();
/// Lookup a value stored on [target] with [expandoSet].
///
/// The SDK verifies that [target] is a valid target before calling this.
@pragma("wasm:import", "dart.expandoGet")
external WasmAnyRef? expandoGet(
WasmExternRef? expando,
WasmAnyRef target,
WasmI64 targetIdentityHashCode,
);
/// Associates the [value] with the [target] object in the expando.
///
/// The SDK verifies that [target] is a valid target before calling this.
@pragma("wasm:import", "dart.expandoSet")
external WasmVoid expandoSet(
WasmExternRef? expando,
WasmAnyRef target,
WasmI64 targetIdentityHashCode,
WasmAnyRef? value,
);
/// Creates a native finalizer that may invoke the [callback] with the
/// [firstParameter] and a second token when a registered object becomes
/// unreachable.
@pragma("wasm:import", "dart.finalizerCreate")
external WasmExternRef finalizerCreate(
WasmFunction<WasmVoid Function(WasmAnyRef, WasmAnyRef?)> callback,
WasmAnyRef firstParameter,
);
/// Attaches an object to a finalizer.
///
/// After [object] becomes unreachable, the `callback` passed to
/// [finalizerCreate] may be invoked with [token] as a second parameter.
///
/// If [detachToken] is non-null, it can later be passed to [finalizerDetach] to
/// remove the [object] from the finalizer.
@pragma("wasm:import", "dart.finalizerAttach")
external WasmVoid finalizerAttach(
WasmExternRef? finalizer,
WasmAnyRef object,
WasmAnyRef? token,
WasmAnyRef? detachToken,
);
@pragma("wasm:import", "dart.finalizerDetach")
external WasmVoid finalizerDetach(
WasmExternRef? finalizer,
WasmAnyRef detachToken,
);
/// Returns the string value for [Uri.base], or null if no base URI exists.
@pragma("wasm:import", "dart.baseUri")
external WasmExternRef? baseUri();
/// Returns `1` if running on Windows, `0` otherwise.
@pragma("wasm:import", "dart.isWindows")
external WasmI32 isWindows();
/// Creates a stack trace object from the current call stack.
///
/// This backs [StackTrace.current], so implementations should hide calls to
/// this extern from the created stack trace.
@pragma("wasm:import", "dart.stackTraceGetCurrent")
external WasmExternRef stackTraceGetCurrent();
/// Renders a stack trace returned by [stackTraceGetCurrent] as a string.
@pragma("wasm:import", "dart.stackTraceToString")
external WasmExternRef stackTraceToString(WasmExternRef? trace);
/// Attempts to parse a string as a double, following semantics described in
/// [double.parse].
///
/// If the string can't be parsed as a double, return null. Otherwise, returns a
/// structure that can be used by [tryParseResultGetDouble] to extract the
/// parsed double.
@pragma("wasm:import", "dart.doubleTryParse")
external WasmExternRef? doubleTryParse(WasmExternRef? string);
/// Extracts the double parsed from [doubleTryParse] returning a non-nullable
/// value.
@pragma("wasm:import", "dart.tryParseResultGetDouble")
external WasmF64 tryParseResultGetDouble(WasmExternRef? parseResult);
/// Parses a double from a string known to contain a a valid double.
@pragma("wasm:import", "dart.doubleParseInfallible")
external WasmF64 doubleParseInfallible(WasmExternRef? string);
/// The implementation of [int.toRadixString].
///
/// The SDK will only call this with radix values between 2 and 36 (inclusive).
@pragma("wasm:import", "dart.i64ToString")
external WasmExternRef i64ToString(WasmI64 value, WasmI32 radix);
/// This and [f64ToExponentialWithFractionDigits] must behave exactly as
/// `Number.prototype.toExponential` in JavaScript.
@pragma("wasm:import", "dart.f64ToExponential")
external WasmExternRef f64ToExponential(WasmF64 value);
@pragma("wasm:import", "dart.f64ToExponentialWithFractionDigits")
external WasmExternRef f64ToExponentialWithFractionDigits(
WasmF64 value,
WasmI32 fractionDigits,
);
/// Must behave exactly as `Number.prototype.toPrecision` in JavaScript.
@pragma("wasm:import", "dart.f64ToPrecision")
external WasmExternRef f64ToPrecision(WasmF64 value, WasmI32 fractionDigits);
/// Must behave exactly as `Number.prototype.toFixed` in JavaScript.
@pragma("wasm:import", "dart.f64ToFixed")
external WasmExternRef f64ToFixed(WasmF64 value, WasmI32 fractionDigits);
/// Implements [double.toString].
@pragma("wasm:import", "dart.f64ToString")
external WasmExternRef f64ToString(WasmF64 value);
/// Creates a string buffer object.
@pragma("wasm:import", "dart.stringBufferCreate")
external WasmExternRef stringBufferCreate();
/// Appends a string to a string buffer.
@pragma("wasm:import", "dart.stringBufferWriteString")
external WasmVoid stringBufferWriteString(
WasmExternRef? buffer,
WasmExternRef? string,
);
/// Appends a string containing the character with the [code] point to a string
/// buffer.
@pragma("wasm:import", "dart.stringBufferWriteCharCode")
external WasmVoid stringBufferWriteCharCode(
WasmExternRef? buffer,
WasmI32 code,
);
/// Clears the contents of a string buffer.
@pragma("wasm:import", "dart.stringBufferClear")
external WasmVoid stringBufferClear(WasmExternRef? buffer);
/// The current length of a string in a string buffer.
@pragma("wasm:import", "dart.stringBufferLength")
external WasmI32 stringBufferLength(WasmExternRef? buffer);
/// Turn a string buffer into a string.
@pragma("wasm:import", "dart.stringBufferToString")
external WasmExternRef stringBufferToString(WasmExternRef? buffer);
/// Attempts to parse the `string` as a regular expression with the given
/// options.
///
/// Returns a regular expression object if that succeeds, or an error message as
/// a string otherwise.
@pragma("wasm:import", "dart.regexpCreateOrFailWithString")
external WasmExternRef regexpCreateOrFailWithString(
WasmExternRef? string,
WasmI32 multiLine,
WasmI32 caseSensitive,
WasmI32 unicode,
WasmI32 dotAll,
);
/// Called with the return value of [regexpCreateOrFailWithString], returns
/// whether [ref] is a regular expression object.
///
/// If this returns `0`, the return value is interpreted as an error message
/// string instead.
@pragma("wasm:import", "dart.regexpIsRegexp")
external WasmI32 regexpIsRegexp(WasmExternRef? ref);
/// Implementation of [RegExp.escape].
@pragma("wasm:import", "dart.regexpEscape")
external WasmExternRef regexpEscape(WasmExternRef? string);
/// If [asPrefix] is `0`, return the first match of [string] for [regexp] at or
/// after [start] code units.
///
/// If [asPrefix] is `1`, only return the match if it starts exactly at [start].
@pragma("wasm:import", "dart.regexpMatch")
external WasmExternRef? regexpMatch(
WasmExternRef? regexp,
WasmExternRef? string,
WasmI32 start,
WasmI32 asPrefix,
);
/// Implementation of [Match.start] for a [regexpMatch].
@pragma("wasm:import", "dart.regexpMatchGetStart")
external WasmI32 regexpMatchGetStart(WasmExternRef? match);
/// Implementation of [Match.end] for a [regexpMatch].
@pragma("wasm:import", "dart.regexpMatchGetEnd")
external WasmI32 regexpMatchGetEnd(WasmExternRef? match);
/// Implementation of [Match.groupCount] for a [regexpMatch].
@pragma("wasm:import", "dart.regexpMatchGetGroupCount")
external WasmI32 regexpMatchGetGroupCount(WasmExternRef? match);
/// Implementation of [Match.group] for a [regexpMatch].
///
/// This is only called with an index between 0 and [regexpMatchGetGroupCount]
/// (inclusive).
@pragma("wasm:import", "dart.regexpMatchGetGroup")
external WasmExternRef? regexpMatchGetGroup(
WasmExternRef? match,
WasmI32 index,
);
/// The amount of named groups in a regexp match.
@pragma("wasm:import", "dart.regexpMatchGetNamedGroups")
external WasmI32 regexpMatchGetNamedGroups(WasmExternRef? match);
/// For an index between 0 and [regexpMatchGetNamedGroups] (exclusive), returns
/// the name of the regexp group.
@pragma("wasm:import", "dart.regexpMatchGetGroupName")
external WasmExternRef regexpMatchGetGroupName(
WasmExternRef? match,
WasmI32 index,
);
/// For an index of [regexpMatchGetNamedGroups], returns the match of the group
/// named `regexpMatchGetGroupName(match, nameIndex)`.
@pragma("wasm:import", "dart.regexpMatchGetGroupByName")
external WasmExternRef? regexpMatchGetGroupByName(
WasmExternRef? match,
WasmI32 nameIndex,
);
@pragma("wasm:import", "dart.timeZoneNameForClampedSeconds")
external WasmExternRef timeZoneNameForClampedSeconds(WasmI64 secondsSinceEpoch);
@pragma("wasm:import", "dart.timeZoneOffsetInSecondsForClampedSeconds")
external WasmI32 timeZoneOffsetInSecondsForClampedSeconds(
WasmI64 secondsSinceEpoch,
);
@pragma("wasm:import", "dart.mathPow")
external WasmF64 mathPow(WasmF64 base, WasmF64 exponent);
@pragma("wasm:import", "dart.mathAtan2")
external WasmF64 mathAtan2(WasmF64 a, WasmF64 b);
@pragma("wasm:import", "dart.mathSin")
external WasmF64 mathSin(WasmF64 x);
@pragma("wasm:import", "dart.mathCos")
external WasmF64 mathCos(WasmF64 x);
@pragma("wasm:import", "dart.mathTan")
external WasmF64 mathTan(WasmF64 x);
@pragma("wasm:import", "dart.mathAcos")
external WasmF64 mathAcos(WasmF64 x);
@pragma("wasm:import", "dart.mathAsin")
external WasmF64 mathAsin(WasmF64 x);
@pragma("wasm:import", "dart.mathAtan")
external WasmF64 mathAtan(WasmF64 x);
@pragma("wasm:import", "dart.mathExp")
external WasmF64 mathExp(WasmF64 a);
@pragma("wasm:import", "dart.mathLog")
external WasmF64 mathLog(WasmF64 a);
@pragma("wasm:import", "dart.randomInt")
external WasmI64 randomInt();
@pragma("wasm:import", "dart.randomIntSecure")
external WasmI64 randomIntSecure();
@pragma("wasm:import", "dart.print")
external WasmVoid print(WasmExternRef? line);
@pragma("wasm:import", "dart.jsonEncodeString")
external WasmExternRef jsonEncodeString(WasmExternRef? line);
@pragma("wasm:import", "dart.debugger")
external WasmVoid debugger(WasmExternRef? message);
/// Send a reference to [object] to any attached debuggers.
@pragma("wasm:import", "dart.inspect")
external WasmVoid inspect(WasmAnyRef? object);
@pragma("wasm:import", "dart.timelineStreamEnabled")
external WasmI32 dartTimelineStreamEnabled();
@pragma("wasm:import", "dart.reportTaskEvent")
external WasmI32 reportTaskEvent(
WasmI32 taskId,
WasmI32 flowId,
WasmI32 type,
WasmExternRef? name,
WasmExternRef? argumentsAsJson,
);