SharedArrayBuffer
とは何か
(Web Worker - メインプロセス間などの)スレッド間で参照を共有することが出来る版のArrayBuffer。
(通常のArrayBufferは他のスレッドに参照を渡したら、自スレッドからはアクセスできなくなる。一方、ShareArrayBufferは渡した後でもアクセスできる。)
使用上の注意点
セキュリティ
Spectreの脆弱性の発見に伴い、SharedArrayBufferの「スレッド間で値を参照し合える」という特性が当該攻撃についてセキュリティリスクを孕むことが判明したため、現在ではcross-origin isolatedな状態でない限りブラウザのセキュリティ機構によってSharedArrayBufferの使用をブロックされるようになった。
(※ cross-origin isolated: ざっくり言うと、自サイトが<iframe>
, <script>
, <img>
, XMLHttpRequest(XHR)
, etc. で他サイトから取得されれたり、したりするときの利用ポリシー(何を、どうするのがOK/NGか)を設計・設定・管理されている状態にであるということ。)
参照
- SharedArrayBuffer updates in Android Chrome 88 and Desktop Chrome 91 - Chrome Developers
- 「Google Chrome 91」でSharedArrayBufferの制限が強化 ~COEP/COOPヘッダーの明示的な指定が必要に - 窓の杜
- Security consideration: Multi-threading helps cache-based side channel attacks · Issue #1 · tc39/ecmascript_sharedmem · GitHub
- Cross-Origin Resource Policy (CORP) - HTTP | MDN
マルチスレッド処理における排他処理
SharedArrayBufferも、マルチスレッド処理における類似の他例に漏れず、値の取り扱いには排他処理への考慮が必須となる。
(もし要らないとしたら、もしかしてそれArrayBufferで事足りる要件だったりしませんか?)
JavaScriptにおける排他処理、つまり不可分操作は、Atomics
を使って実装することが出来る。
不可分操作とは
マルチスレッドで1つの変数を共有している場合、その変数に両方のプロセスのアクセスタイミングが重なるとデータ整合性上のトラブルが発生し、バグの原因となる。
これを防ぐために、不可分操作を施し、他のスレッドの割り込みを禁止して、値の書き込みと読み出しの整合性(書き込み処理と読み出し処理の間に別スレッドによる別の書き込み処理が割り込んでいないこと)が確実に担保された区間を作ることが出来る、というもの。