Skip to content

Commit bc76fd7

Browse files
sygioannadMs2ger
committed
[js-api] Integrate with the ResizableArrayBuffer proposal (#1300)
Co-authored-by: Ioanna M. Dimitriou H <idimitriou@igalia.com> Co-authored-by: Ms2ger <Ms2ger@igalia.com>
1 parent cd77040 commit bc76fd7

File tree

1 file changed

+98
-12
lines changed

1 file changed

+98
-12
lines changed

document/js-api/index.bs

Lines changed: 98 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,7 @@ urlPrefix: https://tc39.github.io/ecma262/; spec: ECMASCRIPT
4545
text: NativeError Object Structure; url: sec-nativeerror-object-structure
4646
text: 𝔽; url: #𝔽
4747
text: ℤ; url: #ℤ
48+
text: SameValue; url: sec-samevalue
4849
urlPrefix: https://webassembly.github.io/spec/core/; spec: WebAssembly; type: dfn
4950
url: valid/modules.html#valid-module
5051
text: valid
@@ -102,6 +103,7 @@ urlPrefix: https://webassembly.github.io/spec/core/; spec: WebAssembly; type: df
102103
text: memory address; url: exec/runtime.html#syntax-memaddr
103104
text: global address; url: exec/runtime.html#syntax-globaladdr
104105
text: extern address; url: exec/runtime.html#syntax-externaddr
106+
text: page size; url: exec/runtime.html#page-size
105107
url: syntax/types.html#syntax-numtype
106108
text: i32
107109
text: i64
@@ -148,6 +150,11 @@ urlPrefix: https://webassembly.github.io/spec/core/; spec: WebAssembly; type: df
148150
urlPrefix: https://heycam.github.io/webidl/; spec: WebIDL
149151
type: dfn
150152
text: create a namespace object; url: create-a-namespace-object
153+
urlPrefix: https://tc39.es/proposal-resizablearraybuffer/; spec: ResizableArrayBuffer proposal
154+
type: dfn
155+
text: handled; url: sec-hostresizearraybuffer
156+
text: IsFixedLengthArrayBuffer; url: sec-isfixedarraybuffer
157+
text: HostResizeArrayBuffer; url: sec-hostresizearraybuffer
151158
</pre>
152159

153160
<pre class='link-defaults'>
@@ -586,6 +593,8 @@ dictionary MemoryDescriptor {
586593
interface Memory {
587594
constructor(MemoryDescriptor descriptor);
588595
unsigned long grow([EnforceRange] unsigned long delta);
596+
ArrayBuffer toFixedLengthBuffer();
597+
ArrayBuffer toResizableBuffer();
589598
readonly attribute ArrayBuffer buffer;
590599
};
591600
</pre>
@@ -598,10 +607,27 @@ which can be simultaneously referenced by multiple {{Instance}} objects. Each
598607
* \[[BufferObject]] : an {{ArrayBuffer}} whose [=Data Block=] is [=identified with=] the above memory address
599608

600609
<div algorithm>
601-
To <dfn>create a memory buffer</dfn> from a [=memory address=] |memaddr|, perform the following steps:
610+
To <dfn>create a fixed length memory buffer</dfn> from a [=memory address=] |memaddr|, perform the following steps:
611+
612+
1. Let |block| be a [=Data Block=] which is [=identified with=] the underlying memory of |memaddr|.
613+
1. Let |buffer| be a new {{ArrayBuffer}} with the internal slots \[[ArrayBufferData]], \[[ArrayBufferByteLength]], and \[[ArrayBufferDetachKey]].
614+
1. Set |buffer|.\[[ArrayBufferData]] to |block|.
615+
1. Set |buffer|.\[[ArrayBufferByteLength]] to the length of |block|.
616+
1. Set |buffer|.\[[ArrayBufferDetachKey]] to "WebAssembly.Memory".
617+
1. Return |buffer|.
618+
</div>
619+
620+
<div algorithm>
621+
To <dfn>create a resizable memory buffer</dfn> from a [=memory address=] |memaddr| and a |maxsize|, perform the following steps:
602622

603623
1. Let |block| be a [=Data Block=] which is [=identified with=] the underlying memory of |memaddr|.
604-
1. Let |buffer| be a new {{ArrayBuffer}} whose \[[ArrayBufferData]] is |block| and \[[ArrayBufferByteLength]] is set to the length of |block|.
624+
1. Let |length| be the length of |block|.
625+
1. If |maxsize| &gt; (65536 &times; 65536),
626+
1. Throw a {{RangeError}} exception.
627+
1. Let |buffer| be a new {{ArrayBuffer}} with the internal slots \[[ArrayBufferData]], \[[ArrayBufferByteLength]], \[[ArrayBufferMaxByteLength]], and \[[ArrayBufferDetachKey]].
628+
1. Set |buffer|.\[[ArrayBufferData]] to |block|.
629+
1. Set |buffer|.\[[ArrayBufferByteLength]] to |length|.
630+
1. Set |buffer|.\[[ArrayBufferMaxByteLength]] is |maxsize|.
605631
1. Set |buffer|.\[[ArrayBufferDetachKey]] to "WebAssembly.Memory".
606632
1. Return |buffer|.
607633
</div>
@@ -610,7 +636,7 @@ which can be simultaneously referenced by multiple {{Instance}} objects. Each
610636
To <dfn>initialize a memory object</dfn> |memory| from a [=memory address=] |memaddr|, perform the following steps:
611637
1. Let |map| be the [=surrounding agent=]'s associated [=Memory object cache=].
612638
1. Assert: |map|[|memaddr|] doesn't [=map/exist=].
613-
1. Let |buffer| be the result of [=create a memory buffer|creating a memory buffer=] from |memaddr|.
639+
1. Let |buffer| be the result of [=create a fixed length memory buffer|creating a fixed length memory buffer=] from |memaddr|.
614640
1. Set |memory|.\[[Memory]] to |memaddr|.
615641
1. Set |memory|.\[[BufferObject]] to |buffer|.
616642
1. [=map/Set=] |map|[|memaddr|] to |memory|.
@@ -640,36 +666,96 @@ which can be simultaneously referenced by multiple {{Instance}} objects. Each
640666
</div>
641667

642668
<div algorithm>
643-
To <dfn>reset the Memory buffer</dfn> of |memaddr|, perform the following steps:
669+
To <dfn>refresh the Memory buffer</dfn> of |memaddr|, perform the following steps:
644670

645671
1. Let |map| be the [=surrounding agent=]'s associated [=Memory object cache=].
646672
1. Assert: |map|[|memaddr|] [=map/exists=].
647673
1. Let |memory| be |map|[|memaddr|].
648-
1. Perform [=!=] [$DetachArrayBuffer$](|memory|.\[[BufferObject]], "WebAssembly.Memory").
649-
1. Let |buffer| be the result of [=create a memory buffer|creating a memory buffer=] from |memaddr|.
650-
1. Set |memory|.\[[BufferObject]] to |buffer|.
674+
1. Let |buffer| be |memory|.\[[BufferObject]].
675+
1. If [=IsFixedLengthArrayBuffer=](|buffer|) is true,
676+
1. Perform [=!=] [$DetachArrayBuffer$](|buffer|, "WebAssembly.Memory").
677+
1. Let |buffer| be the result of [=create a fixed length memory buffer|creating a fixed length memory buffer=] from |memaddr|.
678+
1. Set |memory|.\[[BufferObject]] to |buffer|.
679+
1. Otherwise,
680+
1. Let |block| be a [=Data Block=] which is [=identified with=] the underlying memory of |memaddr|.
681+
1. Set |buffer|.\[[ArrayBufferData]] to |block|.
682+
1. Set |buffer|.\[[ArrayBufferByteLength]] to the length of |block|.
651683
</div>
652684

653-
<div algorithm=dom-Memory-grow>
654-
The <dfn method for="Memory">grow(|delta|)</dfn> method, when invoked, performs the following steps:
685+
<div algorithm>
686+
To <dfn>grow the memory buffer</dfn> associated with a [=memory address=] |memaddr| by |delta|, perform the following steps:
687+
655688
1. Let |store| be the [=surrounding agent=]'s [=associated store=].
656-
1. Let |memaddr| be **this**.\[[Memory]].
657689
1. Let |ret| be the [=mem_size=](|store|, |memaddr|).
658690
1. Let |store| be [=mem_grow=](|store|, |memaddr|, |delta|).
659691
1. If |store| is [=error=], throw a {{RangeError}} exception.
660692
1. Set the [=surrounding agent=]'s [=associated store=] to |store|.
661-
1. [=Reset the memory buffer=] of |memaddr|.
693+
1. [=Refresh the memory buffer=] of |memaddr|.
662694
1. Return |ret|.
663695
</div>
664696

697+
<div algorithm=dom-Memory-grow>
698+
The <dfn method for="Memory">grow(|delta|)</dfn> method, when invoked, performs the following steps:
699+
1. Let |memaddr| be **this**.\[[Memory]].
700+
1. Return the result of [=grow the memory buffer|growing the memory buffer=] associated with |memaddr| by |delta|.
701+
</div>
702+
665703
Immediately after a WebAssembly [=memory.grow=] instruction executes, perform the following steps:
666704

667705
<div algorithm="memory.grow">
668706
1. If the top of the stack is not [=i32.const=] (−1),
669707
1. Let |frame| be the [=current frame=].
670708
1. Assert: due to validation, |frame|.[=frame/module=].[=moduleinst/memaddrs=][0] exists.
671709
1. Let |memaddr| be the memory address |frame|.[=frame/module=].[=moduleinst/memaddrs=][0].
672-
1. [=Reset the memory buffer=] of |memaddr|.
710+
1. [=Refresh the memory buffer=] of |memaddr|.
711+
</div>
712+
713+
<div algorithm=dom-Memory-toFixedLengthBuffer>
714+
The <dfn method for="Memory">toFixedLengthBuffer()</dfn> method, when invoked, performs the following steps:
715+
1. Let |buffer| be **this**.\[[BufferObject]].
716+
1. If [=IsFixedLengthArrayBuffer=](|buffer|) is true, return |buffer|.
717+
1. Let |memaddr| be **this**.\[[Memory]].
718+
1. Let |fixedBuffer| be the result of [=create a fixed length memory buffer|creating a fixed length memory buffer=] from |memaddr|.
719+
1. Perform [=!=] [$DetachArrayBuffer$](|buffer|, "WebAssembly.Memory").
720+
1. Set **this**.\[[BufferObject]] to |fixedBuffer|.
721+
1. Return |fixedBuffer|.
722+
</div>
723+
724+
<div algorithm=dom-Memory-toResizableBuffer>
725+
The <dfn method for="Memory">toResizableBuffer()</dfn> method, when invoked, performs the following steps:
726+
1. Let |buffer| be **this**.\[[BufferObject]].
727+
1. If [=IsFixedLengthArrayBuffer=](|buffer|) is false, return |buffer|.
728+
1. Let |memaddr| be **this**.\[[Memory]].
729+
1. Let |store| be the [=surrounding agent=]'s [=associated store=].
730+
1. Let |memtype| be [=mem_type=](|store|, |memaddr|).
731+
1. If |memtype| has a max,
732+
1. Let |maxsize| be the max value in |memtype|.
733+
1. Otherwise,
734+
1. Let |maxsize| be 65536 &times; 65536.
735+
1. Let |resizableBuffer| be the result of [=create a resizable memory buffer|creating a resizable memory buffer=] from |memaddr| and |maxsize|.
736+
1. Perform [=!=] [$DetachArrayBuffer$](|buffer|, "WebAssembly.Memory").
737+
1. Set **this**.\[[BufferObject]] to |resizableBuffer|.
738+
1. Return |resizableBuffer|.
739+
</div>
740+
741+
{{ArrayBuffer}} objects returned by a {{Memory}} object must have a size that is a multiple of a WebAssembly [=page size=] (the constant 65536). For this reason [=HostResizeArrayBuffer=] is redefined as follows.
742+
743+
<div algorithm>
744+
The <dfn>abstract operation [=HostResizeArrayBuffer=]</dfn> takes arguments |buffer| (an {{ArrayBuffer}}) and |newLength|. It performs the following steps when called.
745+
746+
1. If |buffer|.\[[ArrayBufferDetachKey]] is "WebAssembly.Memory",
747+
1. Let |map| be the [=surrounding agent=]'s associated [=Memory object cache=].
748+
1. Assert: |buffer| is the \[[BufferObject]] of exactly one value in |map|.
749+
1. [=map/iterate|For each=] |memaddr| &rarr; |mem| in |map|,
750+
1. If [=SameValue=](|mem|.\[[BufferObject]], |buffer|) is true,
751+
1. Assert: |buffer|.\[[ArrayBufferByteLength]] modulo 65536 is 0.
752+
1. Let |lengthDelta| be |newLength| - |buffer|.\[[ArrayBufferByteLength]].
753+
1. If |lengthDelta| &lt; 0 or |lengthDelta| modulo 65536 is not 0,
754+
1. Throw a {{RangeError}} exception.
755+
1. Let |delta| be |lengthDelta| &div; 65536.
756+
1. [=Grow the memory buffer=] associated with |memaddr| by |delta|.
757+
1. Return <emu-const>handled</emu-const>.
758+
1. Otherwise, return <emu-const>unhandled</emu-const>.
673759
</div>
674760

675761
<div algorithm>

0 commit comments

Comments
 (0)