このページはECMAScript® 2020 Language Specification8 Executable Code and Execution Contexts章をJavaScriptの学習目的で私的に日本語訳したものであり、直訳と意訳および推測が混在しています。そのため内容については正確ではない可能性があります。正確な情報を知りたい場合は、原文をご覧ください。また一部訳者によるコメントが含まれていることがあります。※このサイトの内容で損害や不利益を受けたとしても当方は一切の責任を負いません。

8.1 レキシカル環境(Lexical Environments)

レキシカル環境は、ECMAScriptコードの字句のネスト構造に基づいて、特定の変数および関数への識別子の関連付けを定義する仕様タイプです。レキシカル環境は、環境レコードと、外部のレキシカル環境へのnull参照で構成されます。 通常、レキシカル環境は、FunctionDeclarationBlockStatement、またはTryStatementCatch句などのECMAScriptコードの特定の構文構造に関連付けられており、そのようなコードが評価されるたびに新しいレキシカル環境が作成されます。

EnvironmentRecord

環境レコードは、関連付けられたレキシカル環境のスコープ内で作成された識別子バインディングを記録します。レキシカル環境のEnvironmentRecordと呼ばれます。

バインディングとは?という説明はない。

外部環境参照

外部環境参照は、レキシカル環境値の論理的なネストをモデル化するために使用されます。レキシカル環境の外部参照は、レキシカル環境を論理的に囲んでいるレキシカル環境への参照です。 もちろん、外部のレキシカル環境は外部のレキシカル環境を持つことができます。レキシカル環境は、複数のレキシカル環境の外部環境として機能します。たとえば、FunctionDeclaration内にFunctionDeclarationが2つある場合、内側の各関数のレキシカル環境は、周囲の関数のレキシカル環境を外側のレキシカル環境として持ちます。

====レキシカル環境(1)===== function , block{} , Catch ...

   [====レキシカル環境(2)==== function , block{} , Catch ...
   |     外部環境参照=> (1) への参照
   |
   |     [====レキシカル環境(3)==== function , block{} , Catch ...
   |     |       外部環境参照=> (2) への参照
   |     =========================================]
   |
   ==================================================]

   [====レキシカル環境(4)==== function , block{} , Catch ...
   |     
   |    外部環境参照=> (1) への参照
   |
   ==================================================]

==========================================================

グローバル環境

グローバル環境は外部環境を持たない、外部環境参照がnullなレキシカル環境です。グローバル環境のEnvironmentRecordには、識別子バインディングが事前に設定され、プロパティにはグローバル環境の識別子バインディングの一部を提供する関連グローバルオブジェクトが含まれます。グローバルオブジェクトは、ECMAScriptコードの実行により、新しいプロパティが追加されたり、初期プロパティが変更されることがあります。

モジュール環境

モジュール環境は、モジュールのトップレベル宣言のバインディングを含むレキシカル環境です。 また、モジュールによって明示的にインポートされたバインディングも含まれています。 モジュール環境の外部環境はグローバル環境です。

関数環境

関数環境は、ECMAScript関数オブジェクトの呼び出しに対応するレキシカル環境です。 関数環境は、新しいthisバインディングを確立する場合があります。 関数環境は、スーパーメソッドの呼び出しをサポートするために必要な状態もキャプチャします。

レキシカル環境と環境レコードの値は純粋に仕様メカニズムであり、ECMAScript実装の特定のアーティファクトに対応する必要はありません。 ECMAScriptプログラムがそれらに直接アクセスまたは操作することは不可能です。

8.1.1 環境レコード(Environment Records)

この仕様で使用される主な環境レコード値は、宣言型環境レコードとオブジェクト環境レコードの2つです。宣言的環境レコードは、識別子バインディングをECMAScript言語値に直接関連付けるFunctionDeclarationVariableDeclarationCatch句などのECMAScript言語構文要素を定義します。 オブジェクト環境レコードは、IDバインディングをオブジェクトのプロパティに関連付けるWithStatementなどのECMAScript要素を定義します。グローバル環境レコードと関数環境レコードは、特にスクリプトのグローバル宣言と関数内のトップレベル宣言に使用されます。

仕様上、環境レコード値はレコード仕様タイプの値であり、単純なオブジェクト指向階層に存在すると考えることができます。環境レコードは、3つの具象サブクラス、宣言型環境レコード、オブジェクト環境レコード、およびグローバル環境を持つ抽象クラスです。 関数環境レコードとモジュール環境レコードは、宣言型環境レコードのサブクラスです。 抽象クラスには、表16で定義された抽象仕様メソッドが含まれます。これらの抽象メソッドには、具象サブクラスごとに異なる具象アルゴリズムがあります。

表16: 環境レコードの抽象メソッド
メソッド 目的
HasBinding(N) 環境レコードに文字列値Nのバインディングがあるかどうかを確認します。ある場合はtrueを返し、ない場合はfalseを返します。

宣言型環境レコード.HasBinding
オブジェクト環境レコード.HasBinding
グローバル環境レコード.HasBinding
CreateMutableBinding(N, D) 初期化されていない新しい可変バインディングを環境レコードに作成します。 文字列値Nは、バインドされた名前のテキストです。ブール引数Dtrueの場合、バインディングは後で削除される可能性があります。

宣言型環境レコード.CreateMutableBinding
オブジェクト環境レコード.CreateMutableBinding
グローバル環境レコード.CreateMutableBinding
CreateImmutableBinding(N, S) 初期化されていない新しい不変バインディングを環境レコードに作成します。 文字列値Nは、バインドされた名前のテキストです。 Sがtrueの場合、初期化後に設定しようとすると、strictモード設定に関係なく、例外がスローされます。

宣言型環境レコード.CreateImmutableBinding
オブジェクト環境レコード.CreateImmutableBinding
グローバル環境レコード.CreateImmutableBinding
InitializeBinding(N, V) 存在するが初期化されていないバインディングの値を環境レコードに設定します。 文字列値Nは、バインドされた名前のテキストです。 Vはバインディングの値であり、任意のECMAScript言語タイプの値です。

宣言型環境レコード.InitializeBinding
オブジェクト環境レコード.InitializeBinding
グローバル環境レコード.InitializeBinding
SetMutableBinding(N, V, S) 環境レコード内の既存の変更可能なバインディングの値を設定します。文字列値Nは、バインドされた名前のテキストです。 Vはバインディングの値であり、任意のECMAScript言語型の値です。 Sはブールフラグです。 Strueでバインディングを設定できない場合は、TypeError例外をスローします。

宣言型環境レコード.SetMutableBinding
オブジェクト環境レコード.SetMutableBinding
グローバル環境レコード.SetMutableBinding
GetBindingValue(N, S) 環境レコードから既存のバインディングの値を返します。 文字列値Nは、バインドされた名前のテキストです。 Sは、strictモードのコードで発生する参照、またはstrictモードの参照セマンティクスを必要とする参照を識別するために使用されます。 Strueであり、バインディングが存在しない場合は、ReferenceError例外をスローします。 バインディングは存在するが初期化されていない場合、Sの値に関係なく、ReferenceError例外がスローされます。

宣言型環境レコード.GetBindingValue
オブジェクト環境レコード.GetBindingValue
グローバル環境レコード.GetBindingValue
モジュール環境レコード.GetBindingValue
DeleteBinding(N) 環境レコードからバインディングを削除します。文字列値Nは、バインドされた名前のテキストです。 Nのバインディングが存在する場合は、バインディングを削除してtrueを返します。 バインディングは存在するが削除できない場合はfalseを返します。 バインディングが存在しない場合はtrueを返します。

宣言型環境レコード.DeleteBinding
オブジェクト環境レコード.DeleteBinding
グローバル環境レコード.DeleteBinding
モジュール環境レコード.DeleteBinding
HasThisBinding() 環境レコードthisバインディングを作成するどうかを決定します。する場合はtrueを、しない場合はfalseを返します。

宣言型環境レコード.HasThisBinding
オブジェクト環境レコード.HasThisBinding
関数環境レコード.HasThisBinding
グローバル環境レコード.HasThisBinding
モジュール環境レコード.HasThisBinding
HasSuperBinding() 環境レコードsuperメソッドバインディングを作成するどうかを決定します。する場合はtrueを、しない場合はfalseを返します。

宣言型環境レコード.HasSuperBinding
オブジェクト環境レコード.HasSuperBinding
関数環境レコード.HasSuperBinding
グローバル環境レコード.HasSuperBinding
WithBaseObject() 環境レコードwithステートメントに関連付けられている場合は、withオブジェクトを返します。 それ以外の場合は、undefinedを返します。

宣言型環境レコード.WithBaseObject
オブジェクト環境レコード.WithBaseObject
グローバル環境レコード.WithBaseObject

8.1.1.1 宣言的環境レコード(Declarative Environment Records)

宣言型環境レコードは、ECMAScriptプログラムスコープに関連付けられています(プログラムスコープは、変数、定数、let、クラス、モジュール、インポート、および、関数宣言のどれか、または全てが含まれています)。宣言型環境レコードは、そのスコープ内の宣言で定義された識別子をバインドします。

宣言型環境レコードの具体的な仕様メソッドは、次のアルゴリズムによって定義されます。

8.1.1.1.1 HasBinding ( N )

環境レコードメソッドHasBindingは、識別子Nがレコードによってバインドされているかどうかをシンプルな方法で判断します。

  1. 環境レコードメソッドが呼ばれた宣言型環境レコードを、envRec とする
  2. envRec に Nの値である名前と同じ名前のバインディングがある場合、trueを返す。
  3. falseを返す
8.1.1.1.2 CreateMutableBinding ( N, D )

環境レコードメソッドCreateMutableBindingは、初期化されていない名前Nの新しい可変バインディングを作成します。 実行前に、対象となる名前が環境レコード上に存在していてはなりません。ブール引数Dの値がtrueの場合、作成したバインディングを削除対象としてマークします。

  1. 環境レコードメソッドが呼ばれた宣言型環境レコードを、envRec とする
  2. Assert: envRecNのバインディングがない
  3. envRecN の可変バインディングを作成し、初期化されていないことを記録する。 Dtrueの場合、作成したバインディングが後続の DeleteBinding呼び出しによって削除される可能性があることを記録する。
  4. NormalCompletion(empty) を返す
8.1.1.1.3 CreateImmutableBinding ( N, S )

環境レコードメソッドCreateImmutableBindingは、初期化されていない名前Nの不変バインディングを作成します。 実行前に、対象となる名前が環境レコード上に存在していてはなりません。ブール引数Sの値がtrueの場合、新しいバインディングは厳密なバインディングとしてマークされます。

  1. 環境レコードメソッドが呼ばれた宣言型環境レコードを、envRec とする
  2. Assert: envRecNのバインディングがない
  3. envRecN の不変バインディングを作成し、初期化されていないことを記録する。 Strueの場合、作成したバインディングが厳密なバインディングであることを記録する。
  4. NormalCompletion(empty) を返す
8.1.1.1.4 InitializeBinding ( N, V )

環境レコードメソッドInitializeBindingは、Nに対応するバインド値をVの値に設定します。目的のバインドはすでに存在している必要があります。

  1. 環境レコードメソッドが呼ばれた宣言型環境レコードを、envRec とする
  2. Assert: envRecNのバインディングがあり、かつ初期化されていない
  3. venvRecN のバインド値にセット
  4. envRec の N のバインディングが初期化されたことを記録する。
  5. NormalCompletion(empty) を返す
8.1.1.1.5 SetMutableBinding ( N, V, S )

環境レコードメソッドSetMutableBindingは、Nに対応するバインド値をVの値に変更します。Nのバインドは存在していることも、存在していないこともあります。 バインディングが不変バインディングで、Strueなら、TypeErrorがスローされます。

  1. 環境レコードメソッドが呼ばれた宣言型環境レコードを、envRec とする
  2. envRec に N の バインディングが存在しないなら、
    1. S が true ならReferenceError例外をスローする
    2. envRec.CreateMutableBinding(N, true) を実行
    3. envRec.InitializeBinding(N, V) を実行
    4. NormalCompletion(empty) を返す
  3. envRecN のバインディングが厳密なバインディングであるなら、trueS にセット
  4. envRecのNのバインディングがまだ初期化されていないなら、ReferenceError例外をスローします。
  5. 4.ではなく、envRecのNのバインディングが可変バインディングであるなら、そのバインド値を V に変更します。
  6. 3.でも4.でもないなら
    1. Assert: 不変バインディングの値を変更しようとしている
    2. Strue なら TypeError例外をスローする.
  7. NormalCompletion(empty) を返す

手順2でバインディングが失われるECMAScriptコードの例は次のとおりです。

function f() { eval("var x; x = (delete x, 0);"); }
8.1.1.1.6 GetBindingValue ( N, S )

環境レコードメソッドGetBindingValueは、名前が引数Nの値であるバインドされた識別子の値を返します。バインディングが存在するが初期化されていない場合、Sの値に関係なく、ReferenceErrorがスローされます。

  1. 環境レコードメソッドが呼ばれた宣言型環境レコードを、envRec とする
  2. Assert: envRec に N のバインディングがある
  3. envRec の N のバインディングが初期化されていないなら、 ReferenceError例外をスローする.
  4. envRec で N にバインドされている値を返す
8.1.1.1.7 DeleteBinding ( N )

環境レコードメソッドDeleteBindingは、削除対象として明示的に指定されているバインディングのみを削除できます。

削除対象として明示的に指定:
CreateMutableBindingの第二引数にtrueを指定したもの。
  1. 環境レコードメソッドが呼ばれた宣言型環境レコードを、envRec とする
  2. Assert: envRec に N のバインディングがある
  3. envRec の N のバインディングを削除できないなら false を返す
  4. envRec から N のバインディングを削除する。
  5. trueを返す
8.1.1.1.8 HasThisBinding ( )

通常の宣言型環境レコードは、thisバインディングを提供しません。

  1. falseを返す
8.1.1.1.9 HasSuperBinding ( )

通常の宣言型環境レコードはsuperバインディングを提供しません。

  1. falseを返す
8.1.1.1.10 WithBaseObject ( )

宣言型環境レコードは常にWithBaseObjectとしてundefinedを返します。

  1. undefinedを返す

8.1.1.2 オブジェクト環境レコード(Object Environment Records)

オブジェクト環境レコードは、バインディングオブジェクトと呼ばれるオブジェクトに関連付けられています。 オブジェクト環境レコードは、バインディングオブジェクトのプロパティ名に直接対応する文字列識別子名のセットをバインドします。 IdentifierName形式の文字列ではないプロパティキーは、バインドされた識別子のセットに含まれません。 独自プロパティ継承プロパティの両方が、[[Enumerable]]属性の設定に関係なくセットに含まれます。 プロパティは動的にオブジェクトに追加および削除できるため、オブジェクト環境レコードにバインドされている識別子のセットは、プロパティを追加または削除する操作の結果として変更される可能性があります。 このような処理の結果として作成されたバインディングは、対応するプロパティの[[Writable]]属性の値がfalseであっても、可変バインディングと見なされます。 不変バインディングは、オブジェクトの環境レコードには存在しません。

withEnvironment

withステートメント(13.11)用に作成されたオブジェクト環境レコードは、バインディングオブジェクトを関数呼び出しで使用する暗黙のthis値として提供できます。 この機能は、各オブジェクトの環境レコードに関連付けられているwithEnvironmentブール値によって制御されます。 デフォルトでは、withEnvironmentの値は、どのオブジェクト環境レコードでもfalseです。

オブジェクト環境レコードの具体的な指定メソッドは、次のアルゴリズムによって定義されます。

8.1.1.2.1 HasBinding ( N )

オブジェクト環境レコードメソッドHasBindingは、関連付けられたバインディングオブジェクトに、名前が引数Nの値であるプロパティがあるかどうかを決定します。

  1. メソッドが呼び出されたオブジェクト環境レコードを envRec とする。
  2. envRec の バインディングオブジェクトを bindings とする
  3. ? HasProperty(bindings, N)の結果を foundBinding とする
  4. foundBindingfalse なら false を返す.
  5. envRec の withEnvironment フラグが false なら、 true を返す
  6. ? Get(bindings, @@unscopables)の結果を unscopables とする
  7. Type(unscopables) が Object型なら
    1. ! ToBoolean(? Get(unscopables, N)) の結果を blocked とする
    2. blockedtrue なら false を返す
  8. true を返す
8.1.1.2.2 CreateMutableBinding ( N, D )

オブジェクト環境レコードメソッドCreateMutableBindingは、環境レコードに関連付けられたバインディングオブジェクトに、名前が文字列値Nのプロパティを作成し、undefinedの値に初期化します。 ブール引数Dの値は、作成したプロパティの[[Configurable]]属性に設定されます。

  1. メソッドが呼び出されたオブジェクト環境レコードを envRec とする。
  2. envRec の バインディングオブジェクトを bindings とする
  3. ? DefinePropertyOrThrow(bindings, N, プロパティ記述子 { [[Value]]: undefined, [[Writable]]: true, [[Enumerable]]: true, [[Configurable]]: D }) の結果を返す
通常、envRec には N のバインディングはありません。もし N のバインディングがある場合、DefinePropertyOrThrowのセマンティクスにより、既存のバインディングが置換またはシャドウされるか、突然の完了が返される可能性があります。
8.1.1.2.3 CreateImmutableBinding ( N, S )

オブジェクト環境レコードメソッドCreateImmutableBindingは、この仕様内で使用されません。

8.1.1.2.4 InitializeBinding ( N, V )

オブジェクト環境レコードメソッドInitializeBindingは、Nに対応するバインド値をVの値に設定します。目的のバインドはすでに存在している必要があります。

  1. メソッドが呼び出されたオブジェクト環境レコードを envRec とする。
  2. Assert: envRec内の N バインディングは初期化されていなし
  3. envRecNのバインディングが初期化されたことを記録する
  4. ? envRec.SetMutableBinding(N, V, false)の結果を返す
この仕様では、CreateMutableBindingの直後に、InitializeBindingが呼び出されます。 したがって、実装では、個々のオブジェクトの環境レコードバインディングの初期化状態を追跡する必要はありません。
8.1.1.2.5 SetMutableBinding ( N, V, S )

オブジェクト環境レコードメソッドSetMutableBindingは、N に対応するバインド値を V の値に設定します。Nという名前のプロパティが存在している必要があります。存在しない または書き込み不可の場合、SがtrueならTypeErrorがスローされます。

  1. メソッドが呼び出されたオブジェクト環境レコードを envRec とする。
  2. envRec の バインディングオブジェクトを bindings とする
  3. ? Set(bindings, N, V, S) を返す
8.1.1.2.6 GetBindingValue ( N, S )

オブジェクト環境レコードメソッドGetBindingValueは、、N に対応するバインディングオブジェクトのプロパティの値を返します。プロパティが存在しない場合、結果はS引数の値に依存します。

  1. メソッドが呼び出されたオブジェクト環境レコードを envRec とする。
  2. envRec の バインディングオブジェクトを bindings とする
  3. ? HasProperty(bindings, N)の結果を value とする
  4. valuefalse なら、
    1. Sfalse なら undefinedを、それ以外なら ReferenceError例外をスローする.
  5. ? Get(bindings, N)を返す
8.1.1.2.7 DeleteBinding ( N )

オブジェクト環境レコードメソッドDeleteBindingは、[[Configurable]]属性がtrueであるバインディングのみを削除できます。

  1. メソッドが呼び出されたオブジェクト環境レコードを envRec とする。
  2. envRec の バインディングオブジェクトを bindings とする
  3. ? bindings.[[Delete]] (N)を返す
8.1.1.2.8 HasThisBinding ( )

通常のオブジェクト環境レコードは、thisバインディングを提供しません。

  1. false を返す
8.1.1.2.9 HasSuperBinding ( )

通常のオブジェクト環境レコードは、superバインディングを提供しません。

  1. false を返す
8.1.1.2.10 WithBaseObject ( )

オブジェクト環境レコードは、withEnvironmentフラグがtrueでない限り、WithBaseObjectとしてundefined を返します。

  1. メソッドが呼び出されたオブジェクト環境レコードを envRec とする。
  2. envRecwithEnvironmentフラグがtrueなら、envRec のバインディングオブジェクトを返す。
  3. undefined を返す

8.1.1.3 関数環境レコード(Function Environment Records)

関数環境レコードは、関数のトップレベルのスコープを表すために使用される宣言型環境レコードです。関数がArrowFunctionでない場合、このバインディングを使用します。 関数がArrowFunction関数ではなく、さらにsuperが参照される場合、その関数の環境レコードには、関数内からスーパーメソッドの呼び出しを実行するために必要な情報が含まれています。

関数環境レコードには、表17に示す追加フィールドがあります。

表17: 関数環境レコードの追加フィールド
フィールド名 意味
[[ThisValue]] Any 関数の呼び出しに使用される this 値です。
[[ThisBindingStatus]] lexical |
initialized |
uninitialized
値がlexicalの場合、ArrowFunctionであり、
ローカルthis値はありません。
[[FunctionObject]] Object この環境レコードが作成される原因
となった関数オブジェクト
[[HomeObject]] Object |
undefined
関連付けられた関数にsuperプロパティアクセスがあり、
ArrowFunctionではない場合、
[[HomeObject]]は関数がメソッドとしてバインドされているオブジェクトです。
[[HomeObject]]のデフォルト値はundefinedです。
[[NewTarget]] Object |
undefined<
この環境レコードが[[Construct]]内部メソッドによって作成された場合、
[[NewTarget]]は[[Construct]]メソッドの引数newTargetの値です。
それ以外の場合、[[NewTarget]]はundefinedです。

関数環境レコードは、表16にリストされているすべての宣言型環境レコードメソッドをサポートし、HasThisBindingとHasSuperBindingを除くすべてのメソッドで同じ仕様を共有します。 さらに、関数環境レコードは、表18にリストされているメソッドをサポートします。

表18: 関数環境レコードの追加メソッド

メソッド 目的
BindThisValue(V) [[ThisValue]]を設定し、初期化されたことを記録します。

関数環境レコード.BindThisValue
GetThisBinding() 環境レコードのthisバインディングの値を返します。
バインディングが初期化されていない場合、ReferenceErrorをスローします。

関数環境レコード.GetThisBinding
グローバル環境レコード.GetThisBinding
モジュール環境レコード.GetThisBinding
GetSuperBase() 環境レコードにバインドされたsuperプロパティアクセスのベースとなるオブジェクトを返します。オブジェクトは、環境レコードの[[HomeObject]]フィールドから派生しています。 undefined値は、superプロパティアクセスが実行時エラーを生成することを示します。

関数環境レコード.GetSuperBase

関数環境レコードの追加メソッドの動作は、次のアルゴリズムによって定義されます。

8.1.1.3.1 BindThisValue ( V )
  1. メソッドが呼び出された関数環境レコードを envRec とする。
  2. Assert: envRec.[[ThisBindingStatus]] は lexicalではない
  3. envRec.[[ThisBindingStatus]] が initialized なら ReferenceError例外をスローする
  4. envRec.[[ThisValue]] に V をセット
  5. envRec.[[ThisBindingStatus]] に initialized をセット
  6. V を返す
8.1.1.3.2 HasThisBinding ( )
  1. メソッドが呼び出された関数環境レコードを envRec とする。
  2. envRec.[[ThisBindingStatus]] が lexical なら false を、それ以外は true を返す
8.1.1.3.3 HasSuperBinding ( )
  1. メソッドが呼び出された関数環境レコードを envRec とする。
  2. envRec.[[ThisBindingStatus]] が lexical なら false を返す
  3. envRec.[[HomeObject]] が undefined なら false を、それ以外なら true を返す
8.1.1.3.4 GetThisBinding ( )
  1. メソッドが呼び出された関数環境レコードを envRec とする。
  2. Assert: envRec.[[ThisBindingStatus]] は lexical ではない
  3. envRec.[[ThisBindingStatus]] が uninitialized なら ReferenceError例外をスローする.
  4. envRec.[[ThisValue]]を返す
8.1.1.3.5 GetSuperBase ( )
  1. メソッドが呼び出された関数環境レコードを envRec とする。
  2. envRec.[[HomeObject]] を home とする
  3. homeundefined なら undefined を返す
  4. Assert: Type(home) は オブジェクト型
  5. ? home.[[GetPrototypeOf]]() を返す

8.1.1.4 グローバル環境レコード(Global Environment Records)

グローバル環境レコードは、共通のレルムで処理されるすべてのECMAScriptスクリプト要素によって共有される、最も外側のスコープです。 グローバル環境レコードは、組み込みグローバル(18章)、グローバルオブジェクトのプロパティ、およびスクリプト内で発生するすべてのトップレベル宣言(13.2.813.2.10)のバインディングを提供します。

グローバル環境レコードは論理的には単一のレコードです。ただし、オブジェクト環境レコードと宣言型環境レコードをカプセル化し複合化しています。 オブジェクト環境レコードは、関連するレルムレコードのグローバルオブジェクトをベースオブジェクトとして持っています。 このグローバルオブジェクトは、グローバル環境レコードのGetThisBinding具象メソッドが返す値です。 グローバル環境レコードのオブジェクト環境レコードコンポーネントには、すべての組み込みグローバル(18章)のバインディングと、グローバルコードに含まれるFunctionDeclarationGeneratorDeclarationAsyncFunctionDeclarationAsyncGeneratorDeclarationVariableStatementによって導入されたすべてのバインディングが含まれます。 グローバルコード内の他のすべてのECMAScript宣言のバインディングは、グローバル環境レコードの宣言型環境レコードコンポーネントに含まれています。

グローバルオブジェクトにプロパティを直接作成できます。 したがって、グローバル環境レコードのオブジェクト環境レコードコンポーネントには、FunctionDeclarationGeneratorDeclarationAsyncFunctionDeclarationAsyncGeneratorDeclarationVariableDeclaration宣言によって明示的に作成されたバインディングと、グローバルオブジェクトのプロパティとして暗黙的に作成されたバインディングの両方が含まれます。 宣言を使用して明示的に作成されたバインディングを識別するために、グローバル環境レコードは、CreateGlobalVarBindingおよびCreateGlobalFunctionBindingメソッドを使用してバインドされた名前のリストを維持します。

原文中に何度も出てきて煩わしいので、次の文を略記します。略1
FunctionDeclarationGeneratorDeclarationAsyncFunctionDeclarationAsyncGeneratorDeclarationVariableDeclaration

グローバル環境レコードには、表19の追加のフィールドと、表20の追加メソッドがあります。

表19: グローバル環境レコードの追加フィールド
フィールド名 意味
[[ObjectRecord]] オブジェクト環境レコード バインディングオブジェクトはグローバルオブジェクトです。 グローバルな組み込みバインディングに加えて、関連するレルムのグローバルコードに略1のバインディングが含まれています。
[[GlobalThisValue]] Object グローバルスコープの this 値。ホストは ECMAScript オブジェクト値を提供できます。
[[DeclarativeRecord]] 宣言型環境レコード 略1バインディングを除く、関連するレルムコードのグローバルコード内のすべての宣言のバインディングが含まれます。
[[VarNames]] String型のList 関連するレルムのグローバルコードの略1宣言によってバインドされた文字列名。
表20: グローバル環境レコードの追加メソッド
メソッド 目的
GetThisBinding() 環境レコードのthisバインディングの値を返します。

関数環境レコード.GetThisBinding
グローバル環境レコード.GetThisBinding
モジュール環境レコード.GetThisBinding
HasVarDeclaration (N) 略1を使用して作成された環境レコードで、Nのバインディングを持つかどうかを判定します。

グローバル環境レコード.HasVarDeclaration
HasLexicalDeclaration (N) LexicalDeclarationClassDeclarationなどのレキシカル宣言を使用して作成された環境レコードで、Nのバインディングを持つかどうかを判定します。

グローバル環境レコード.HasLexicalDeclaration
HasRestrictedGlobalProperty (N) Nグローバルオブジェクトが持つプロパティ名で、かつ、グローバルレキシカルバインディングによってシャドウされないかどうかを判定します。

グローバル環境レコード.HasRestrictedGlobalProperty
CanDeclareGlobalVar (N) CreateGlobalVarBindingを引数Nで呼び出したとき、呼び出しが成功するかどうかを判断します。

グローバル環境レコード.CanDeclareGlobalVar
CanDeclareGlobalFunction (N) CreateGlobalFunctionBindingを引数Nで呼び出したとき、呼び出しが成功するかどうかを判断します。

グローバル環境レコード.CanDeclareGlobalFunction
CreateGlobalVarBinding(N, D) グローバル環境レコードの[[ObjectRecord]]コンポーネントに、グローバルvarバインディングを作成してundefinedで初期化します。 作成されるバインディングは変更可能です。 対応するグローバルオブジェクトプロパティには、varに適した属性値が設定されます。 文字列値Nはバインドする名前です。 Dtrueの場合、バインディングは削除可能です。 論理的にはCreateMutableBindingの後にSetMutableBindingが続くのと同じですが、var宣言で特別な処理を行うことができます。

グローバル環境レコード.CreateGlobalVarBinding
CreateGlobalFunctionBinding(N, V, D) グローバル環境レコードの[[ObjectRecord]]コンポーネントにグローバル関数バインディングを作成および初期化します。 作成されたバインディングは変更可能です。 対応するグローバルオブジェクトプロパティには、関数に適した属性値が設定されます。 文字列値Nはバインドする名前です。 Vは初期値です。 ブール引数Dtrueの場合、バインディングは削除可能です。 論理的にはCreateMutableBindingとそれに続くSetMutableBindingと同等ですが、関数宣言で特別な処理を行うことができます。

グローバル環境レコード.CreateGlobalFunctionBinding

グローバル環境レコードの具体的な動作は、以下のアルゴリズムで定義されています。

8.1.1.4.1 HasBinding ( N )

グローバル環境レコードメソッドHasBindingは、Nがレコードによってバインドされているかを単純な方法で決定します。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[DeclarativeRecord]] を DclRec とする
  3. DclRec.HasBinding(N) の結果が true なら true を返す
  4. envRec.[[ObjectRecord]] を ObjRec とする
  5. ? ObjRec.HasBinding(N) を返す
8.1.1.4.2 CreateMutableBinding ( N, D )

グローバル環境レコードメソッドCreateMutableBindingは、名前Nの新しい可変バインディングを初期化せずに作成します。 バインディングは、関連するDeclarativeRecordに作成されます。 Nのバインディングは、DeclarativeRecordにすでに存在していてはなりません。 ブール引数Dの値がtrueの場合、作成したバインディングは削除の対象としてマークします。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[DeclarativeRecord]] を DclRec とする
  3. DclRec.HasBinding(N) の結果が true なら TypeError例外をスローする.
  4. DclRec.CreateMutableBinding(N, D)を返す
8.1.1.4.3 CreateImmutableBinding ( N, S )

グローバル環境レコードメソッドCreateImmutableBindingは、名前Nの新しい不変バインディングを初期化せずに作成します。 バインディングは、このNの環境レコードにすでに存在していてはなりません。ブール引数Sの値がtrueの場合、作成したバインディングは厳密なバインディングとしてマークされます。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[DeclarativeRecord]] を DclRec とする
  3. DclRec.HasBinding(N) の結果が true なら TypeError例外をスローする.
  4. DclRec.CreateImmutableBinding(N, S)を返す
8.1.1.4.4 InitializeBinding ( N, V )

グローバル環境レコードメソッドInitializeBindingは、Nに対応するバインド値を引数Vの値に設定します。目的のバインドはすでに存在している必要があります。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[DeclarativeRecord]] を DclRec とする
  3. DclRec.HasBinding(N) の結果が true なら then
    1. DclRec.InitializeBinding(N, V)を返す
  4. Assert: バインディングが存在するなら、それはオブジェクト環境レコードに含まれている
  5. envRec.[[ObjectRecord]] を ObjRec とする
  6. ? ObjRec.InitializeBinding(N, V)を返す
8.1.1.4.5 SetMutableBinding ( N, V, S )

グローバル環境レコードメソッドSetMutableBindingは、引数Nに対応するバインド値を引数Vの値に変更します。バインドが不変バインドでSがtrueのとき、TypeErrorがスローされます。 Nという名前のプロパティが存在しない場合、または現在書き込み可能でない場合、エラー処理はブール引数Sの値によって決定されます。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[DeclarativeRecord]] を DclRec とする
  3. DclRec.HasBinding(N) の結果が true なら then
    1. DclRec.SetMutableBinding(N, V, S)を返す
  4. envRec.[[ObjectRecord]] を ObjRec とする
  5. ? ObjRec.SetMutableBinding(N, V, S) を返す
8.1.1.4.6 GetBindingValue ( N, S )

グローバル環境レコードメソッドGetBindingValueは、引数Nに対応する識別子の値を返します。バインディングが初期化されていない場合、ReferenceError例外をスローします。 Nという名前のプロパティが存在しない場合、または書き込み可能でない場合、エラー処理はブール引数Sの値によって決定されます。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[DeclarativeRecord]] を DclRec とする
  3. DclRec.HasBinding(N) の結果が true なら then
    1. DclRec.GetBindingValue(N, S)を返す
  4. envRec.[[ObjectRecord]] を ObjRec とする
  5. ? ObjRec.GetBindingValue(N, S)を返す
8.1.1.4.7 DeleteBinding ( N )

グローバル環境レコードメソッドDeleteBindingは、削除対象として明示的に指定されているバインディングのみを削除できます。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[DeclarativeRecord]] を DclRec とする
  3. DclRec.HasBinding(N) の結果が true なら then
    1. DclRec.DeleteBinding(N)を返す
  4. envRec.[[ObjectRecord]] を ObjRec とする
  5. ObjRec のバインディングオブジェクトを globalObject とする
  6. ? HasOwnProperty(globalObject, N) を existingProp  とする
  7. existingProptrue なら
    1. ? ObjRec.DeleteBinding(N) を status とする
    2. statustrue なら
      1. envRec.[[VarNames]] を varNames とする
      2. N が varNames の要素なら、その要素を varNames から削除
    3. status を返す
  8. true を返す
8.1.1.4.8 HasThisBinding ( )
  1. true を返す
8.1.1.4.9 HasSuperBinding ( )
  1. false を返す
8.1.1.4.10 WithBaseObject ( )

グローバル環境レコードは常にWithBaseObjectとしてundefinedを返します。

  1. undefined を返す
8.1.1.4.11 GetThisBinding ( )
  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[GlobalThisValue]]を返す
8.1.1.4.12 HasVarDeclaration ( N )

グローバル環境レコードメソッドHasVarDeclarationは、VariableStatementまたはFunctionDeclarationを使用して作成されたレコードが、Nに対応するバインディングを持っているか判定します。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[VarNames]] を varDeclaredNames とする
  3. NvarDeclaredNames に含まれているなら、true を返す
  4. falseを返す
8.1.1.4.13 HasLexicalDeclaration ( N )

グローバル環境レコードメソッドHasLexicalDeclarationは、LexicalDeclarationClassDeclarationなどのレキシカル宣言を使用して作成されたレコードが、Nに対応するバインディングを持っているかどうかを判定します。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[DeclarativeRecord]] を DclRec とする
  3. DclRec.HasBinding(N)を返す
8.1.1.4.14 HasRestrictedGlobalProperty ( N )

グローバル環境レコードメソッドHasRestrictedGlobalPropertyは、引数識別子がグローバルレキシカルバインディングによってシャドウされてはならないグローバルオブジェクトのプロパティ名であるかどうかを判定します。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[ObjectRecord]] を ObjRec とする
  3. ObjRec のバインディングオブジェクト を globalObject とする
  4. ? globalObject.[[GetOwnProperty]](N) を existingProp とする
  5. existingPropundefined なら false を返す
  6. existingProp.[[Configurable]] が true なら false を返す
  7. true を返す
プロパティは、varまたは関数の宣言を使用して宣言されるのではなく、直接作成されたグローバルオブジェクトに存在する場合があります。 グローバルオブジェクトの設定不可能なプロパティと同じ名前を持つグローバルレキシカルバインディングは作成されない場合があります。 グローバルプロパティ「undefined」は、このようなプロパティの例です。
8.1.1.4.15 CanDeclareGlobalVar ( N )

グローバル環境レコードメソッドCanDeclareGlobalVarは、CreateGlobalVarBindingを引数Nで呼び出した場合、成功するかどうかを判定します。冗長なvar宣言と既存のグローバルオブジェクトプロパティのvar宣言が許可されます。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[ObjectRecord]] を ObjRec とする
  3. ObjRec のバインディングオブジェクト を globalObject とする
  4. ? HasOwnProperty(globalObject, N) を hasProperty とする
  5. hasPropertytrue なら true を返す
  6. ? IsExtensible(globalObject)を返す
8.1.1.4.16 CanDeclareGlobalFunction ( N )

グローバル環境レコードメソッドCanDeclareGlobalFunctionは、引数NでCreateGlobalFunctionBindingを呼び出したとき、成功するかどうかを判定します。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[ObjectRecord]] を ObjRec とする
  3. ObjRec のバインディングオブジェクト を globalObject とする
  4. ? globalObject.[[GetOwnProperty]](N) を existingProp とする
  5. existingPropundefined なら ? IsExtensible(globalObject) を返す
  6. existingProp.[[Configurable]] が true なら true を返す
  7. IsDataDescriptor(existingProp) が true で existingPropの属性が { [[Writable]]: true, [[Enumerable]]: true } のなら、 true を返す
  8. falseを返す
8.1.1.4.17 CreateGlobalVarBinding ( N, D )

グローバル環境レコードメソッドCreateGlobalVarBindingは、関連付けられたオブジェクト環境レコードに可変バインディングを作成、初期化し、バインド名を[[VarNames]]リストに記録します。 バインディングがすでに存在する場合は、再利用され、初期化されていると見なされます。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[ObjectRecord]] を ObjRec とする
  3. ObjRec のバインディングオブジェクト を globalObject とする
  4. ? HasOwnProperty(globalObject, N) を hasProperty とする
  5. ? IsExtensible(globalObject) を extensible とする
  6. hasPropertyfalse で extensibletrue なら
    1. ? ObjRec.CreateMutableBinding(N, D)を実行
    2. ? ObjRec.InitializeBinding(N, undefined)を実行
  7. envRec.[[VarNames]] を varDeclaredNames とする
  8. varDeclaredNamesN を含んでいないなら
    1. varDeclaredNames に N を追加する
  9. NormalCompletion(empty)を返す
8.1.1.4.18 CreateGlobalFunctionBinding ( N, V, D )

グローバル環境レコードメソッドCreateGlobalFunctionBindingは、関連付けられたオブジェクト環境レコードに可変バインディングを作成、初期化し、関連付けられた[[VarNames]]リストにバインドされた名前を記録します。 バインディングがすでに存在する場合、置き換えられます。

  1. メソッドが呼び出されたグローバル環境レコードを envRec とする。
  2. envRec.[[ObjectRecord]] を ObjRec とする
  3. ObjRec のバインディングオブジェクト を globalObject とする
  4. ? globalObject.[[GetOwnProperty]](N) を existingProp とする
  5. existingPropundefined または existingProp.[[Configurable]] が true なら
    1. PropertyDescriptor型 { [[Value]]: V, [[Writable]]: true, [[Enumerable]]: true, [[Configurable]]: D } を desc とする
  6. 5.でないなら
    1. PropertyDescriptor型 { [[Value]]: V } を desc とする
  7. ? DefinePropertyOrThrow(globalObject, N, desc)を実行
  8. ObjRec の N のバインディングが初期化されたことを記録する
  9. ? Set(globalObject, N, V, false)を実行
  10. envRec.[[VarNames]] を varDeclaredNames とする
  11. NvarDeclaredNames に含まれていないなら
    1. varDeclaredNames に N を追加する
  12. NormalCompletion(empty)を返す
グローバル関数宣言は、常にグローバルオブジェクトの独自プロパティです。 既存の独自プロパティは、可能であれば、属性値の標準セットを持つように再構成されます。 手順8〜9は、InitializeBindingメソッドを呼び出すことと同じであり、globalObjectがプロキシの場合、同じシーケンスのプロキシトラップ呼び出しが生成されます。

8.1.1.5 モジュール環境レコード(Module Environment Records)

モジュール環境レコードは、ECMAScriptモジュールの外側のスコープを表す宣言型環境レコードです。 モジュール環境レコードは、可変または不変のバインディングに加えて、別の環境レコードに存在するターゲットバインディングへの間接アクセスを提供します。これは不変のインポートバインディングです。

モジュール環境レコードは、表16にリストされているすべての宣言型環境レコードメソッドをサポートします。また、GetBindingValue、DeleteBinding、HasThisBinding、およびGetThisBindingを除いて、それらすべてのメソッドで同じ仕様を共有します。 さらに、モジュール環境レコードは、表21のメソッドをサポートします。

表21: モジュール環境レコードの追加メソッド
メソッド 目的
CreateImportBinding(N, M, N2) モジュール環境レコードで不変の間接バインディングを作成します。
文字列値Nは、バインドされた名前のテキストです。
Mモジュールレコードです。
N2Mのモジュール環境レコードに存在するバインディングです。

モジュール環境レコード.CreateImportBinding
GetThisBinding() 環境レコードのthisバインディングの値を返します。

関数環境レコード.GetThisBinding
グローバル環境レコード.GetThisBinding
モジュール環境レコード.GetThisBinding

モジュール環境レコードの追加メソッドの動作は、次のアルゴリズムによって定義されます。

8.1.1.5.1 GetBindingValue ( N, S )

モジュール環境レコードメソッドGetBindingValueは、名前Nの値であるバインドされた識別子の値を返します。ただし、バインディングが間接バインディングの場合、ターゲットバインディングの値が返されます。 バインディングは存在するが初期化されていない場合、ReferenceErrorがスローされます。

  1. Assert: Strue
  2. メソッドが呼び出されたモジュール環境レコードを envRec とする
  3. Assert: envRecN のバインディングを持っている
  4. N のバインディングが間接バインディングなら、
    1. N のバインディングが作成されたときに提供された間接値を M および N2 とする
    2. M.[[Environment]] を targetEnv とする
    3. targetEnvundefined なら ReferenceError例外をスローする.
    4. targetEnv の EnvironmentRecordtargetER とする
    5. ? targetER.GetBindingValue(N2, true)を返す
  5. envRecNのバインディングが初期化されていないバインディングなら、 ReferenceError例外をスローする
  6. envRecNに現在バインドされている値を返す
モジュールは常にstrictモードであるため、Sは常にtrueになります。
N のバインディングが作成されたときに提供された間接値を M および N2 とする:CreateImportBindingのMとN2か?わかりにくい
8.1.1.5.2 DeleteBinding ( N )

モジュール環境レコードメソッドDeleteBindingは、バインディングの削除を拒否します。

  1. Assert: このメソッドは決して呼び出されません。 12.5.3.1
モジュール環境レコードはstrictコード内でのみ使用されます。このとき初期のエラールールにより、delete演算子が、モジュール環境レコードバインディングへの参照に適用されなくなります。 12.5.3.1を参照してください。
8.1.1.5.3 HasThisBinding ( )

モジュール環境レコードは、このバインディングを提供します。

  1. trueを返す
8.1.1.5.4 GetThisBinding ( )
  1. undefinedを返す
8.1.1.5.5 CreateImportBinding ( N, M, N2 )

モジュール環境レコードメソッドCreateImportBindingは、N という名前で、不変間接バインディングを作成し初期化します。実行前に、環境レコードにバインディング N が存在していてはなりません。Mモジュールレコードで、N2Mのモジュールの環境レコードに存在するバインディング名です。 新しいバインディングの値にアクセスすると、ターゲットバインディングのバインドされた値に間接的にアクセスします。

  1. メソッドが呼び出されたモジュール環境レコードを envRec とする
  2. Assert: envRecにはNのバインディングがない
  3. Assert: Mモジュールレコード
  4. Assert: M.[[Environment]]がインスタンス化されると、N2に直接バインドされる
  5. ターゲットバインディングとしてMN2を参照するNenvRecに不変間接バインディングを作成し、バインディングが初期化されたことを記録する
  6. NormalCompletion(empty)を返す

8.1.2 レキシカル環境操作(Lexical Environment Operations)

この仕様では、次の抽象操作を使用してレキシカル環境を操作します。

8.1.2.1 GetIdentifierReference ( lex, name, strict )

抽象演算GetIdentifierReferenceは、レキシカル環境lex、文字列name、ブールフラグstrictを指定して呼び出されます。 lexの値はnullの可能性があります。 呼び出されると、次の手順が実行されます。

  1. lexnull なら
    1. 次のReference型を返す。基本値コンポーネントがundefined、参照名コンポーネントがname、厳密参照フラグがstrict
  2. lex の EnvironmentRecordenvRec とする
  3. ? envRec.HasBinding(name) を exists とする
  4. existstrue なら
    1. 次のReference型を返す。基本値コンポーネントがenvRec、参照名コンポーネントがname、厳密参照フラグがstrict
  5. 4でないなら、
    1. lex の外部環境参照の値を outer とする
    2. ? GetIdentifierReference(outer, name, strict)を返す
引数の説明だけでメソッドの説明がないためメソッドの目的が把握できないが、コードから想像すると、変数を内側から外側のスコープへ検索する仕組みである。意外と重要なメソッドである。

8.1.2.2 NewDeclarativeEnvironment ( E )

抽象操作New Declarative Environmentがレキシカル環境Eで呼び出されると、次の手順が実行されます。

  1. 新規のレキシカル環境env とする
  2. バインディングを含まない新しい宣言型環境レコードenvRec とする
  3. envRec を envEnvironmentRecord にセットする
  4. Eenv の外部レキシカル環境参照にセットする
  5. envを返す

8.1.2.3 NewObjectEnvironment ( O, E )

抽象操作NewObjectEnvironmentがオブジェクトOレキシカル環境Eを引数として呼び出されると、次の手順が実行されます。

  1. 新規のレキシカル環境env とする
  2. バインディングオブジェクトとして、Oを含む新規のオブジェクト環境レコードenvRec とする
  3. envRec を  env の EnvironmentRecord にセットする
  4. Eenvの外部レキシカル環境参照 にセットする
  5. envを返す

8.1.2.4 NewFunctionEnvironment ( F, newTarget )

抽象操作NewFunctionEnvironmentが引数FnewTargetで呼び出されると、次の手順が実行されます。

  1. Assert: F は ECMAScript関数
  2. Assert: Type(newTarget) は Undefined か Object型
  3. 新規のレキシカル環境env とする
  4. バインディングを含まない新規の関数環境レコードenvRec とする
  5. FenvRec.[[FunctionObject]] にセットする
  6. F.[[ThisMode]] が lexical なら lexical を envRec.[[ThisBindingStatus]] にセット
  7. 6.でなければ、 uninitialized を envRec.[[ThisBindingStatus]] にセット
  8. F.[[HomeObject]] を home とする
  9. homeenvRec.[[HomeObject]] にセットする
  10. newTargetenvRec.[[NewTarget]] にセットする
  11. envRecenv のEnvironmentRecord にセットする
  12. F.[[Environment]] を env の外部レキシカル環境参照 にセットする
  13. envを返す

8.1.2.5 NewGlobalEnvironment ( G, thisValue )

引数GthisValueを指定して抽象操作NewGlobalEnvironmentが呼び出されると、次の手順が実行されます。

  1. 新規のレキシカル環境env とする
  2. バインディングオブジェクトとして、Gを含む新しいオブジェクト環境レコードobjRec とする
  3. バインディングを含まない新しい宣言型環境レコードdclRec とする
  4. 新しいグローバル環境レコードglobalRec とする
  5. objRecglobalRec.[[ObjectRecord]] にセットする
  6. thisValueglobalRec.[[GlobalThisValue]] にセットする
  7. dclRecglobalRec.[[DeclarativeRecord]] にセットする
  8. 空のリスト を globalRec.[[VarNames]] にセットする
  9. globalRec を env's EnvironmentRecord にセットする
  10. nullenv の外部レキシカル環境参照 にセットする
  11. envを返す

8.1.2.6 NewModuleEnvironment ( E )

抽象演算NewModuleEnvironmentがレキシカル環境Eを指定して呼び出されると、次の手順が実行されます。

  1. 新規のレキシカル環境env とする
  2. バインディングを含まない新しいモジュール環境レコードenvRec とする
  3. envRecenvEnvironmentRecord にセットする
  4. Eenv の外部レキシカル環境参照 にセットする
  5. envを返す

8.2 レルム(Realms)

レルム

評価前に、すべてのECMAScriptコードはレルムに関連付けられます。 概念的には、レルムは、組み込みオブジェクトのセット、ECMAScriptグローバル環境、グローバル環境のスコープ内でロードされるすべてのECMAScriptコード、およびその他の関連する状態とリソースで構成されます。

レルムレコード

この仕様でレルムは、表22で指定されたフィールドを持つレルムレコードとして表されます。

表22: レルムレコードのフィールド
フィールド名 意味
[[Intrinsics]] フィールド名が組み込みキーであり、
値がオブジェクトであるレコード
レルムに関連付けられたコードで使用される固有値
[[GlobalObject]] Object レルムのグローバルオブジェクト
[[GlobalEnv]] レキシカル環境 レルムのグローバル環境
[[TemplateMap]] Record
{ [[Site]]: パースノード,
[[Array]]: Object }
List
テンプレートオブジェクトは、レルムレコードの[[TemplateMap]]を使用して、レルムごとに個別に正規化されます。
[[Site]]値は、TemplateLiteralである解析ノードです。
[[Array]]値は、タグ関数に渡される対応するテンプレートオブジェクトです。

解析ノードが到達不能になると、対応する[[Array]]も到達不能になります。
実装が[[TemplateMap]]リストからペアを削除した場合は参照できなくなります。
[[HostDefined]] Any。 規定値はundefined ホスト環境で使用するために予約されているフィールド。追加情報をレルムレコードに関連付けるために使用。

8.2.1 CreateRealm ( )

引数なしの抽象操作CreateRealmは、次の手順を実行します。

  1. 新規のレルムレコードrealmRec とする
  2. CreateIntrinsics(realmRec)を実行
  3. undefinedrealmRec.[[GlobalObject]] にセットする
  4. undefinedrealmRec.[[GlobalEnv]] にセットする
  5. 空のListrealmRec.[[TemplateMap]] にセットする
  6. realmRecを返す

8.2.2 CreateIntrinsics ( realmRec )

引数realmRecを指定した抽象操作CreateIntrinsicsは、次の手順を実行します。

  1. 新規Recordintrinsics とする
  2. intrinsicsrealmRec.[[Intrinsics]] にセットする
  3. 表8を参照して組み込み関数のフィールドを設定します。フィールド名は、表の列1(固有名)です。 各フィールドの値は、18~26章の各オブジェクト仕様で定義されているプロパティ値を完全かつ再帰的に入力した新規オブジェクト値です。すべてのオブジェクトプロパティ値は、新規オブジェクト値です。 組み込み関数オブジェクト値は、CreateBuiltinFunction(<steps>,<slots>,realmRec,<prototype>)によって作成されます。<steps>はこの仕様によって提供されるその関数の定義、<slots>は関数の指定された内部スロットの名前のリストであり、<prototype>は関数の[[Prototype]]内部スロットの指定された値です。 組み込み関数とそのプロパティの作成は、未作成オブジェクトへの依存を避けるために順序付けする必要があります。
  4. AddRestrictedFunctionProperties(intrinsics.[[%Function.prototype%]], realmRec)を実行
  5. intrinsicsを返す

8.2.3 SetRealmGlobalObject ( realmRec, globalObj, thisValue )

引数realmRecglobalObj、およびthisValueを持つ抽象操作SetRealmGlobalObjectは、次の手順を実行します。

  1. globalObjundefined なら、
    1. realmRec.[[Intrinsics]] を intrinsics とする
    2. OrdinaryObjectCreate(intrinsics.[[%Object.prototype%]]) を globalObj にセットする

  2. Assert: Type(globalObj) は Object型
  3. thisValueundefined なら、 globalObj を thisValue にセット
  4. globalObjrealmRec.[[GlobalObject]] にセットする
  5. NewGlobalEnvironment(globalObj, thisValue) を newGlobalEnv とする
  6. newGlobalEnvrealmRec.[[GlobalEnv]] にセットする
  7. realmRecを返す

8.2.4 SetDefaultGlobalBindings ( realmRec )

引数realmRecを指定した抽象オペレーションSetDefaultGlobalBindingsは、次の手順を実行します。

  1. realmRec.[[GlobalObject]] を global とする
  2. 18章で指定されたグローバルオブジェクトの各プロパティに対して、次を実行
    1. プロパティ名の文字列値 を name とする
    2. 属性を含む完全なデータプロパティ記述子desc とする。 18.218.3、または18.4にリストされているプロパティの場合、[[Value]]属性の値は、realmRecの対応する組み込みオブジェクトです。
    3. ? DefinePropertyOrThrow(global, name, desc)を実行
  3. globalを返す

8.3 実行コンテキスト(Execution Contexts)

実行中の実行コンテキスト

実行コンテキストは、ECMAScript実装によるコードのランタイム評価を追跡するために使用される仕様デバイスです。どの時点でも、実際にコードを実行しているエージェントごとに最大1つの実行コンテキストがあります。 これは、エージェントの実行中の実行コンテキストと呼ばれます。 この仕様では、実行中の実行コンテキストへのすべての参照は、周囲のエージェントの実行中の実行コンテキストへの参照です。

実行コンテキストスタック

実行コンテキストスタックは、実行コンテキストを追跡するために使用されます。 実行中の実行コンテキストは、常にこのスタックの最上位の要素です。 現在実行中の実行コンテキストに関連付けられている実行可能コードから、その実行コンテキストに関連付けられていない実行可能コードに制御が移されるたびに、新しい実行コンテキストが作成されます。新しく作成された実行コンテキストがスタックにプッシュされ、実行中の実行コンテキストになります。

実行コンテキストには、関連するコードの実行の進行状況を追跡するために必要な実装固有の状態が含まれます。 各実行コンテキストには、少なくとも表23にリストされている状態コンポーネントがあります。

表23: すべての実行コンテキストの状態コンポーネント
コンポーネント 目的
コード評価ステータスコンポーネント 実行コンテキストに関連付けられたコードの評価をperform(実行)、suspend(一時停止)、およびresume(再開)するために必要な状態。
Function
(関数コンポーネント)
実行コンテキストが関数オブジェクトのコードを評価している場合、コンポーネントの値はその関数オブジェクトです。コンテキストがScriptまたはModuleのコードを評価している場合、値はnullです。
Realm
レルムコンポーネント
関連するコードがECMAScriptリソースにアクセスするレルムレコード
ScriptOrModule 関連するコードの元となるモジュールレコードまたはスクリプトレコードInitializeHostDefinedRealmで作成されたオリジナルの実行コンテキストのように、オリジナルのスクリプトまたはモジュールがない場合、値はnullです。

実行中の実行コンテキストによるコードの評価は、この仕様で定義されているさまざまな時点で一時停止されることがあります。 実行中の実行コンテキストが一時停止されると、別の実行コンテキストが実行中の実行コンテキストになり、そのコードの評価を開始できます。 しばらくして、中断された実行コンテキストが再び実行中の実行コンテキストになり、以前に中断された時点でコードの評価を続行する場合があります。 実行コンテキスト間の実行中の実行コンテキストステータスの遷移は、通常、スタックのような後入れ/先出し(LIFO)で発生します。 ただし、一部のECMAScript機能には、実行中の実行コンテキストの非LIFO遷移が必要です。

現在のレルムレコード

アクティブ関数オブジェクト

実行中の実行コンテキストレルムコンポーネントの値は、現在のレルムレコードとも呼ばれます。 実行中の実行コンテキストの関数コンポーネントの値は、アクティブ関数オブジェクトとも呼ばれます。

ECMAScriptコードの実行コンテキストには、表24に示す追加の状態コンポーネントがあります。

表24: ECMAScriptコード実行コンテキストの追加の状態コンポーネント
コンポーネント 目的
LexicalEnvironment 実行コンテキスト内のコードによる識別子参照を解決するために使用される、レキシカル環境を識別します。
VariableEnvironment 実行コンテキスト内でVariableStatementsによって作成されたバインディングを、EnvironmentRecordが保持する、レキシカル環境を識別します。

実行コンテキストのLexicalEnvironmentおよびVariableEnvironmentコンポーネントは常にレキシカル環境です。

ジェネレーターオブジェクトの評価を表す実行コンテキストには、表25に示す追加の状態コンポーネントがあります。

表25: ジェネレーター実行コンテキストの追加の状態コンポーネント
コンポーネント 目的
Generator 実行コンテキストが評価しているGeneratorObject。

ほとんどの状況では、実行中の実行コンテキスト(実行コンテキストスタックの最上位)のみが、この仕様内のアルゴリズムによって直接操作されます。 したがって、「LexicalEnvironment」および「VariableEnvironment」という用語が条件の説明なしで使用されている場合、それらは実行中の実行コンテキストのコンポーネントを参照しています。

実行コンテキストは純粋に仕様メカニズムであり、ECMAScript実装の特定のアーティファクトに対応する必要はありません。 ECMAScriptコードが実行コンテキストに直接アクセスまたは監視することは不可能です。

8.3.1 GetActiveScriptOrModule ( )

GetActiveScriptOrModule抽象操作は、実行中の実行コンテキストに基づいて、実行中のスクリプトまたはモジュールを取得するために使用されます。 GetActiveScriptOrModuleは、次の手順を実行します。

  1. 実行コンテキストスタックが empty なら、 null を返す
  2. ScriptOrModuleコンポーネントが null でない実行コンテキストスタックの最上位実行コンテキスト を ec とする
  3. そのような実行コンテキストが存在しないなら、nullを返す。 存在するなら ec の ScriptOrModule を返す

8.3.2 ResolveBinding ( name [ , env ] )

ResolveBinding抽象操作は、文字列値nameのバインディングを決定するために使用されます。 オプション引数envは、バインディングを検索するレキシカル環境を明示的に指定します。 ECMAScriptコードの実行中、ResolveBindingは次のアルゴリズムで実行されます。

  1. env の指定なしまたは、 envundefined なら、
    1. 実行中の実行コンテキストLexicalEnvironmentenv にセットする

  2. Assert: env は レキシカル環境
  3. 評価されている構文生成に一致するコードがストリクトモードコードに含まれているなら、true を 、含まれていないなら false を strict とする
  4. ? GetIdentifierReference(env, name, strict)を返す
ResolveBindingの結果は常に参照値であり、その参照名コンポーネントは引数nameと同じです。

8.3.3 GetThisEnvironment ( )

抽象操作GetThisEnvironmentは、キーワードthisのバインディングを現在の環境レコードから検索します。 GetThisEnvironmentは、次の手順を実行します。

  1. 実行中の実行コンテキスト の LexicalEnvironmentlex とする
  2. 以下を繰り返す
    1. lex の EnvironmentRecordenvRec とする
    2. envRec.HasThisBinding() を exists とする
    3. existstrue なら、 envRecを返す
    4. lex の外部環境参照の値 を outer とする
    5. Assert: outernull ではない
    6. outer を lex にセット
環境のリストは常にthisバインディングを持つグローバル環境で終了するため、ステップ2のループは常に終了します。

8.3.4 ResolveThisBinding ( )

抽象操作ResolveThisBindingは、実行中の実行コンテキストLexicalEnvironmentを使用して、キーワードthisのバインディングを決定します。 ResolveThisBindingは次の手順を実行します。

  1. GetThisEnvironment() を envRec とする
  2. ? envRec.GetThisBinding()を返す

8.3.5 GetNewTarget ( )

抽象操作GetNewTargetは、実行中の実行コンテキストLexicalEnvironmentを使用してNewTarget値を決定します。 GetNewTargetは次の手順を実行します。

  1. GetThisEnvironment() を envRec とする
  2. Assert: envRec は [[NewTarget]]フィールドを持っている
  3. envRec.[[NewTarget]]を返す

8.3.6 GetGlobalObject ( )

抽象操作GetGlobalObjectは、現在実行中の実行コンテキストで使用されるグローバルオブジェクトを返します。 GetGlobalObjectは次の手順を実行します。

  1. 現在のレルムレコードcurrentRealm とする
  2. currentRealm.[[GlobalObject]]を返す

8.4 ジョブとジョブをキューに入れるためのホスト操作(Jobs and Host Operations to Enqueue Jobs)

ジョブ

ジョブは、ECMAScript計算が進行中ではないときにECMAScript計算を開始するパラメーターのない抽象クロージャです。

ジョブには、ECMAScriptホスト環境による実行がスケジュールされています。 この仕様では、1種類のジョブをスケジュールするためのホストフックHostEnqueuePromiseJobについて説明しています。 ホスト環境では、ジョブをスケジュールする追加の抽象操作を定義できます。 このような操作は、ジョブの抽象クロージャをパラメータとして受け入れ、将来実行されるようにスケジュールします。 それらの実装は、次の要件に準拠する必要があります。

  • 将来のある時点で、実行中の実行コンテキストがなく、実行コンテキストスタックが空の場合、実装は次のことを行う必要があります。
    1. 実行コンテキスト実行コンテキストスタックにプッシュする
    2. 実装定義の準備手順を実行する
    3. 抽象クロージャを呼び出す
    4. 実装定義のクリーンアップ手順を実行する
    5. プッシュされた実行コンテキスト実行コンテキストスタックからポップする
  • どの時点でも、1つのジョブのみがアクティブに評価を受けることができる
  • ジョブの評価を開始したら、ジョブが完了するまで実行してから、他のジョブの評価を開始する
  • 抽象クロージャは、独自のエラー処理を実装して、通常の完了を返す必要がある
ホスト環境は、スケジューリングに関して全てのジョブを同じレベルで処理する必要はありません。 たとえば、ウェブブラウザとNode.jsは、Promise処理ジョブを他の作業よりも高い優先度として扱います。 今後の機能では、このような高い優先度で処理されないジョブが追加される可能性があります。

8.4.1 HostEnqueuePromiseJob ( job, realm )

HostEnqueuePromiseJobはホスト定義の抽象操作で、将来実行されるジョブ抽象クロージャjobをスケジュールします。 このアルゴリズムで使用される抽象クロージャは、Promiseの処理に関連するか、そうでなければ、Promise処理操作と同じ優先度でスケジュールされることを目的としています。

引数realmは、標準的な要件なしでホストに渡されます。nullまたはレルムのいずれかです。

PromiseResolveThenableJobsのレルムは、then関数オブジェクトGetFunctionRealmを呼び出した結果です。 PromiseReactionJobsのレルムは、ハンドラーが未定義でない場合にハンドラーでGetFunctionRealmを呼び出した結果です。 それ以外の場合、realmnullです。 たとえば、WHATWG HTML仕様では、レルムを使用して、スクリプトを実行する機能をチェックし、スクリプトを実行する準備をします。

HostEnqueuePromiseJobの実装は、8.4の要件に準拠する必要があります。 さらに、ジョブはFIFOの順序でスケジュールする必要があり、ジョブはスケジュールと順序で実行されます。

8.5 InitializeHostDefinedRealm ( )

抽象操作InitializeHostDefinedRealmは、次の手順を実行します。

  1. CreateRealm() を realm とする
  2. 新規実行コンテキストnewContext とする
  3. nullnewContext の 関数コンポーネント に セットする
  4. realmnewContextレルムコンポーネント にセットする
  5. nullnewContextScriptOrModuleコンポーネント にセットする
  6. newContext実行コンテキストスタック にプッシュする。 これにより、newContext が 実行中の実行コンテキスト になる
  7. ホストがrealmグローバルオブジェクトとして機能するためにエキゾチックなオブジェクトを使用するなら、実装定義の方法で作成されたオブジェクトをglobalとする。 それ以外なら、globalundefinedとする(undefined普通のオブジェクトグローバルオブジェクトとして作成する必要があることを示すためにセット)
  8. realmのグローバルスコープ上のthisバインディングがグローバルオブジェクト以外のオブジェクトを返すことを、ホストが要求するなら、thisValueを実装定義の方法で作成されたオブジェクトにする。 それ以外なら、thisValueundefinedとし、realmのグローバルなthisバインディングがグローバルオブジェクトであることを示す。
  9. SetRealmGlobalObject(realm, global, thisValue)を実行
  10. ? SetDefaultGlobalBindings(realm) を globalObj とする
  11. globalObjに実装定義のグローバルオブジェクトプロパティを作成する
  12. NormalCompletion(empty)を返す

8.6 エージェント(Agents)

エージェント

エージェントレコード

実行中のスレッド

エージェントは、ECMAScript実行コンテキストのセット、実行コンテキストスタック実行中の実行コンテキスト、エージェントレコード、および実行中のスレッドで構成されます。 実行中のスレッドを除き、エージェントの構成要素はそのエージェントに排他的に属します。

エージェントの実行スレッドは、他のエージェントとは独立して、エージェントの実行コンテキストでジョブを実行します。ただし、スレッドを共有するどのエージェントにも[[CanBlock]]プロパティがtrueであるエージェントレコードがない場合は、実行中のスレッドを複数のエージェントが実行スレッドとして使用できます。

たとえば、一部のWebブラウザーは、複数のタブ間で単一の実行スレッドを共有します。

周囲のエージェント

あるエージェントAの実行スレッドがジョブを実行しているなら、エージェントAは実行中のジョブ内のコードの周囲のエージェントです。 コードは、周囲のエージェントを使用して、エージェント内に保持されている仕様レベルの実行オブジェクト(実行中の実行コンテキスト実行コンテキストスタック、エージェントレコードのフィールド)にアクセスします。

表26: エージェントレコードのフィールド
フィールド名 意味
[[LittleEndian]] Boolean アルゴリズムGetValueFromBufferおよびSetValueInBufferの引数isLittleEndianのデフォルト値。 選択は実装依存であり、実装にとって最も効率的な代替手段でなければなりません。 いったん値が決まると、変更できません。
[[CanBlock]] Boolean エージェントがブロックできるかどうかを決定します。
[[Signifier]] グローバルに一意の値 エージェントクラスター内のエージェントを一意に識別します。
[[IsLockFree1]] Boolean 1バイト値のアトミック操作がロックフリーの場合はtrue、それ以外の場合はfalse。

[[IsLockFree2]] Boolean 2バイト値のアトミック操作がロックフリーの場合はtrue、それ以外の場合はfalse。
[[IsLockFree8]] Boolean 8バイト値のアトミック操作がロックフリーの場合はtrue、それ以外の場合はfalse。
[[CandidateExecution]] 実行候補レコード メモリモデル参照

[[Signifier]]、[[IsLockFree1]]、および[[IsLockFree2]]の値は、エージェントクラスター内のエージェントによって監視されると、変更できません。

[[IsLockFree1]]と[[IsLockFree2]]の値は、必ずしもハードウェアによって決定されるわけではありません。時間の経過やECMAScript実装で異なる可能性があります。

[[IsLockFree4]]プロパティはありません。4バイトのアトミック操作は常にロックフリーです。

実際には、アトミック操作が任意のタイプのロックで実装されている場合、操作はロックフリーではありません。 ロックフリーは、ウェイトフリーを意味するものではありません。ロックフリーのアトミック操作を完了するために必要なマシンステップの数に上限はありません。

サイズnのアトミックアクセスがロックフリーであることは、サイズnの非アトミックアクセスの(認識された)アトミック性について何も意味しません。具体的には、非アトミックアクセスは、いくつかの個別のメモリアクセスのシーケンスとして実行される場合があります。 詳細については、 ReadSharedMemoryおよびWriteSharedMemoryを参照してください。

エージェントは仕様メカニズムであり、ECMAScript実装の特定のアーティファクトに対応する必要はありません。

8.6.1 AgentSignifier ( )

抽象操作AgentSignifierは引数を取りません。 次の手順を実行します。

  1. 周囲のエージェント の エージェントレコードAR とする
  2. AR.[[Signifier]]を返す

8.6.2 AgentCanSuspend ( )

抽象操作AgentCanSuspendは引数を取りません。 次の手順を実行します。

  1. 周囲のエージェント の エージェントレコードAR とする
  2. AR.[[CanBlock]]を返す
環境によっては、特定のエージェントを一時停止することが適切でない場合があります。 たとえば、Webブラウザー環境では、ワーカーのイベント処理スレッドの中断を許可しながら、ドキュメントのメインイベント処理スレッドの中断を禁止するのが妥当な場合があります。

8.7 エージェントクラスタ(Agent Clusters)

エージェントクラスタは、共有メモリを操作することで通信できるエージェントの最大セットです。

異なるエージェント内のプログラムは、不特定の手段でメモリを共有する場合があります。 少なくとも、SharedArrayBufferオブジェクトのバッキングメモリは、クラスター内のエージェント間で共有できます。

メモリを共有できない状況でメッセージパッシングにより通信するエージェントが存在する可能性があります。それらが同じエージェントクラスタに存在することはありません。

すべてのエージェントは1つのエージェントクラスタに属しています。

クラスタ内のエージェントは、特定の時点ですべてがアクティブである必要はありません。 エージェントAが別のエージェントBを作成した後、Aが終了し、BがエージェントCを作成した場合、AがBと一部のメモリを共有でき、BがCと一部のメモリを共有できる場合、3つのエージェントは同じクラスタにあります。

クラスタ内のすべてのエージェントは、それぞれのエージェントレコードの[[LittleEndian]]プロパティが同じ値である必要があります。

[[LittleEndian]]が異なる場合、共有メモリでマルチバイトデータを使用することが困難になります。

クラスタ内のすべてのエージェントは、それぞれのエージェントレコードの[[IsLockFree1]]プロパティが同じ値である必要があります。、 [[IsLockFree2]]も同様です。

クラスタ内のすべてのエージェントは、それぞれのエージェントレコードの[[Signifier]]プロパティが異なる値である必要があります。

埋め込みでは、エージェントとの連携なしに、エージェントを非アクティブ化 (処理を停止) したり、エージェントをアクティブ化 (処理を再開)することがあります。埋め込みが行われたら、クラスタ内の一部のエージェントが非アクティブになっている間は、クラスタ内の他のエージェントをアクティブにしておかないようにする必要があります。

前述の制限の目的は、非アクティブ化エージェントにより、他のエージェントがデッドロックまたはスタベーション状態を回避することです。 たとえば、ウィンドウ内のドキュメントに依存しない存続期間を持つHTML共有ワーカーが、独立ドキュメントの専用ワーカーとメモリを共有することを許可されたとします。専用ワーカーがロックを保持している間にドキュメントとその専用ワーカーが非アクティブ化された場合(たとえば 、ドキュメントがウィンドウの履歴にプッシュされる状態)、共有ワーカーがロックを取得しようとすると、共有ワーカーは、専用ワーカーが再度アクティブ化されるまでブロックされます。 このとき、他のウィンドウから共有ワーカーにアクセスしようとする他のワーカーはスターベーションが発生します。

制限の影響は、埋め込み内の同じ中断/スリープ解除コレクティブに属していないエージェント間でメモリを共有することができないことです。

埋め込みは、エージェントのクラスターの他のエージェントの事前の知識や協力なしに、エージェントを終了する場合があります。 エージェントがそれ自体またはクラスター内の別のエージェントのプログラムによるアクションではなく、クラスターの外部の力によって終了した場合、埋め込みは次の2つの戦略のいずれかを選択する必要があります。ひとつはクラスター内のすべてのエージェントを終了する、二つ目は信頼できるAPIを提供することです。これにより、クラスター内のエージェントが調整され、クラスターの残りのメンバーが終了を検出できるようになります。終了データには、終了したエージェントを識別するのに十分な情報が含まれています。

そのタイプの終了の例は次のとおりです。オペレーティングシステムまたはユーザーが別のプロセスで実行されているエージェントを終了します。 エージェントごとのリソースアカウンティングがエージェントが暴走していることを示す場合、埋め込み自体が他のエージェントとインプロセスで実行されているエージェントを終了します。

クラスタ内のエージェントによるECMAScriptコードの評価の前に、クラスタ内のすべてのエージェントのエージェントレコードの[[CandidateExecution]]フィールドは、最初の実行候補に設定されています。 最初の実行候補は空の実行候補です。空の実行候補の[[EventsRecords]]フィールドは、エージェントイベントレコードのリストです。各エージェントイベントレコードの[[AgentSignifier]]フィールドはエージェントのSignifierで、[[EventList]]と[[AgentSynchronizesWith]]フィールドはemptyです。

エージェントクラスタ内のすべてのエージェントは、エージェントレコード[[CandidateExecution]]フィールドで同じ実行候補を共有します。 実行候補は、メモリモデルで使用される仕様メカニズムです。
エージェントクラスタは仕様メカニズムであり、ECMAScript実装の特定のアーティファクトに対応する必要はありません。

8.8 Forward Progress

エージェントが前進するためには、この仕様に従って評価ステップを実行する必要があります。

実行中の実行コンテキストが外部イベントの応答を同期的かつ無期限に待つと、エージェントはブロックされます。 この意味で、エージェントレコードの[[CanBlock]]プロパティがtrueであるエージェントのみがブロックされます。 ブロックされていないエージェントとは、ブロックされていないエージェントです。

実装では、次のことを確認する必要があります。

  • 専用の実行中のスレッドを持つすべてのブロックされていないエージェントは、最終的に前進します
  • 実行中のスレッドを共有する一連のエージェントでは、1つのエージェントが最終的に前進します。
  • エージェントは、ブロッキングを提供する明示的なAPIを介する場合を除いて、別のエージェントをブロックすることはありません。
これは、メモリモデルの活性保証とともに、すべてのSeqCst書き込みが最終的にすべてのエージェントから監視可能になることを保証します。