# HG changeset patch # User Takahiro SHIMIZU # Date 1547170884 -32400 # Node ID c3b973a23fee76518edadd65f3612cd847d40bff # Parent 2387a5edfd585c171c396397267d679f3d95575f update diff -r 2387a5edfd58 -r c3b973a23fee Slide/slide.html --- a/Slide/slide.html Fri Jan 11 10:07:22 2019 +0900 +++ b/Slide/slide.html Fri Jan 11 10:41:24 2019 +0900 @@ -189,21 +189,16 @@ - - - - - -
- -

MVM_interp_run

- -
DISPATCH(NEXT_OP) {
@@ -224,6 +219,9 @@
 

MVM_interp_runで使用されているマクロ

    +
  • + マクロDISPATCHでは +
  • MVM_interp_runではマクロを利用してMoarVMの環境などにアクセスしている
  • 頻出するマクロに GET_REG があり, 次のような使い方をする
@@ -234,13 +232,41 @@
+ +
        reg_base[*((MVMuint16 *)(cur_op + 0))].i64 = MVM_BC_get_I64(cur_op, 2);
+
+
+ + -
    (i->reg_base[*((MVMuint16 *)(i->cur_op + 0))]).i64 = MVM_BC_get_I64(i->cur_op, 2);
-    i->cur_op += 10;
-    goto cbc_next(i);
+
+
+
+ +
+ +

MVM_interp_runで使用されているマクロ

+ +
    +
  • 次のバイトコード命令に遷移するマクロ NEXT は, ラベルgotoが使用可能な場合次の様に記述されている
  • +
  • NEXT自体はラベルテーブルにアクセスし, ラベルを取り出す
  • +
  • 次のバイトコードを取り出すのは, NEXT_OP というマクロが担っている
  • +
+ +
#define NEXT_OP (op = *(MVMuint16 *)(cur_op), cur_op += 2, op)
+#define NEXT *LABELS[NEXT_OP]
+
+
+
    +
  • マクロ NEXT は次の様に展開される
  • +
+ +
goto *LABELS[(op = *(MVMuint16 *)(cur_op), cur_op += 2, op)];
 
@@ -249,33 +275,7 @@
-

MVM_interp_run

- -
    -
  • MVM_interp_runでは次のオペコードをフェッチする際に NEXT_OP マクロを介して計算を行う.
  • -
  • オペコードが対応する命令を実行する際は, MVM_CGOTO フラグが立っている場合はCのラベルgotoを利用し, 使えない場合はswitch文を利用して遷移する.
  • -
- -
#define NEXT_OP (op = *(MVMuint16 *)(cur_op), cur_op += 2, op)
-
-#if MVM_CGOTO
-#define DISPATCH(op)
-#define OP(name) OP_ ## name
-#define NEXT *LABELS[NEXT_OP]
-#else
-#define DISPATCH(op) switch (op)
-#define OP(name) case MVM_OP_ ## name
-#define NEXT runloop
-#endif
-
- - - -
- -
- -

MVM_interp_run

+

MVM_interp_run

  • ラベル遷移を利用する場合は配列LABELSにアクセスし, ラベル情報を取得する
  • @@ -304,7 +304,7 @@
    -

    MVM_interp_run

    +

    MVM_interp_run

    • Cの実装の場合, switch文に展開される可能性がある為, 命令ディスパッチが書かれているCソース・ファイルの指定の場所にのみ処理を記述せざるを得ない @@ -410,6 +410,9 @@ i->cur_op += 10; goto cbc_next(i); } + (i->reg_base[*((MVMuint16 *)(i->cur_op + 0))]).i64 = MVM_BC_get_I64(i->cur_op, 2); + i->cur_op += 10; + goto cbc_next(i); diff -r 2387a5edfd58 -r c3b973a23fee Slide/slide.md --- a/Slide/slide.md Fri Jan 11 10:07:22 2019 +0900 +++ b/Slide/slide.md Fri Jan 11 10:41:24 2019 +0900 @@ -63,11 +63,10 @@ - レジスタマシンとして実装されている. - MoarVMはバイトコードインタプリタを `src/core/interp.c` で定義しており, この中の関数 `MVM_interp_run` でバイトコードに応じた処理を実行する -## MVM_interp_run - -- DISPATCHマクロは次の様に記述されており, この中の `OP` で宣言されたブロックがそれぞれオペコードに対応する処理となっている. +- マクロDISPATCHで, ラベルgotoかcase文に, バイトコードに対応した処理を行う + - この中の `OP` で宣言されたブロックがそれぞれバイトコードに対応する処理となっている. - この中では `GET_REG` などのマクロを用いてMoarVMのレジスタにアクセスする. -- `cur_op`は次のオペコード列が登録されており, マクロ `NEXT` で決められた方法で次のオペコードに遷移する. +- `cur_op`は次のバイトコード列が登録されており, マクロ `NEXT` で決められた方法で次のバイトコードに対応した処理に遷移する. ``` DISPATCH(NEXT_OP) { @@ -81,6 +80,8 @@ ## MVM_interp_runで使用されているマクロ +- マクロDISPATCHでは + - MVM_interp_runではマクロを利用してMoarVMの環境などにアクセスしている - 頻出するマクロに `GET_REG` があり, 次のような使い方をする @@ -90,36 +91,34 @@ cur_op += 10; ``` -- これはバイトコードに埋められた数値を利用して, レジスタ情報を取得/設定などをする -- `reg_base` はMoarVMの現在のフレームのレジスタ情報が保存されたポインタであり, 本来のMVM_interp_runではローカル変数として利用している +- `GET_REG`はバイトコードに埋められた数値を利用して, レジスタ情報を取得/設定などをする +- `GET_REG`は次の様に展開される + +``` + reg_base[*((MVMuint16 *)(cur_op + 0))].i64 = MVM_BC_get_I64(cur_op, 2); ``` - (i->reg_base[*((MVMuint16 *)(i->cur_op + 0))]).i64 = MVM_BC_get_I64(i->cur_op, 2); - i->cur_op += 10; - goto cbc_next(i); -``` +- `reg_base` はMoarVMの現在のフレームのレジスタ情報が保存されたポインタであり, MVM_interp_runではローカル変数として利用している -## MVM_interp_run +## MVM_interp_runで使用されているマクロ -- MVM_interp_runでは次のオペコードをフェッチする際に `NEXT_OP` マクロを介して計算を行う. -- オペコードが対応する命令を実行する際は, `MVM_CGOTO` フラグが立っている場合はCのラベルgotoを利用し, 使えない場合はswitch文を利用して遷移する. - +- 次のバイトコード命令に遷移するマクロ `NEXT` は, ラベルgotoが使用可能な場合次の様に記述されている +- `NEXT`自体はラベルテーブルにアクセスし, ラベルを取り出す +- 次のバイトコードを取り出すのは, `NEXT_OP` というマクロが担っている ``` #define NEXT_OP (op = *(MVMuint16 *)(cur_op), cur_op += 2, op) +#define NEXT *LABELS[NEXT_OP] -#if MVM_CGOTO -#define DISPATCH(op) -#define OP(name) OP_ ## name -#define NEXT *LABELS[NEXT_OP] -#else -#define DISPATCH(op) switch (op) -#define OP(name) case MVM_OP_ ## name -#define NEXT runloop -#endif +``` +- マクロ `NEXT` は次の様に展開される + ``` +goto *LABELS[(op = *(MVMuint16 *)(cur_op), cur_op += 2, op)]; +``` + ## MVM_interp_run @@ -229,6 +228,9 @@ i->cur_op += 10; goto cbc_next(i); } + (i->reg_base[*((MVMuint16 *)(i->cur_op + 0))]).i64 = MVM_BC_get_I64(i->cur_op, 2); + i->cur_op += 10; + goto cbc_next(i); ``` ## NQP diff -r 2387a5edfd58 -r c3b973a23fee Slide/slide.pdf.html --- a/Slide/slide.pdf.html Fri Jan 11 10:07:22 2019 +0900 +++ b/Slide/slide.pdf.html Fri Jan 11 10:41:24 2019 +0900 @@ -173,21 +173,16 @@
      • Perl6専用のVMであり, Cで記述されている
      • レジスタマシンとして実装されている.
      • -
      • MoarVMはバイトコードインタプリタを src/core/interp.c で定義しており, この中の関数 MVM_interp_run でバイトコードに応じた処理を実行する
      • -
      - - - -
    - -
    - -

    MVM_interp_run

    - -
      -
    • DISPATCHマクロは次の様に記述されており, この中の OP で宣言されたブロックがそれぞれオペコードに対応する処理となっている.
    • +
    • +

      MoarVMはバイトコードインタプリタを src/core/interp.c で定義しており, この中の関数 MVM_interp_run でバイトコードに応じた処理を実行する

      +
    • +
    • マクロDISPATCHで, ラベルgotoかcase文に, バイトコードに対応した処理を行う +
        +
      • この中の OP で宣言されたブロックがそれぞれバイトコードに対応する処理となっている.
      • +
      +
    • この中では GET_REG などのマクロを用いてMoarVMのレジスタにアクセスする.
    • -
    • cur_opは次のオペコード列が登録されており, マクロ NEXT で決められた方法で次のオペコードに遷移する.
    • +
    • cur_opは次のバイトコード列が登録されており, マクロ NEXT で決められた方法で次のバイトコードに対応した処理に遷移する.
    DISPATCH(NEXT_OP) {
    @@ -208,6 +203,9 @@
     

    MVM_interp_runで使用されているマクロ

      +
    • +

      マクロDISPATCHでは

      +
    • MVM_interp_runではマクロを利用してMoarVMの環境などにアクセスしている
    • 頻出するマクロに GET_REG があり, 次のような使い方をする
    @@ -218,13 +216,41 @@
      -
    • これはバイトコードに埋められた数値を利用して, レジスタ情報を取得/設定などをする
    • -
    • reg_base はMoarVMの現在のフレームのレジスタ情報が保存されたポインタであり, 本来のMVM_interp_runではローカル変数として利用している
    • +
    • GET_REGはバイトコードに埋められた数値を利用して, レジスタ情報を取得/設定などをする
    • +
    • GET_REGは次の様に展開される
    • +
    + +
            reg_base[*((MVMuint16 *)(cur_op + 0))].i64 = MVM_BC_get_I64(cur_op, 2);
    +
    +
    + +
      +
    • reg_base はMoarVMの現在のフレームのレジスタ情報が保存されたポインタであり, MVM_interp_runではローカル変数として利用している
    -
        (i->reg_base[*((MVMuint16 *)(i->cur_op + 0))]).i64 = MVM_BC_get_I64(i->cur_op, 2);
    -    i->cur_op += 10;
    -    goto cbc_next(i);
    +
    +
    +
    + +
    + +

    MVM_interp_runで使用されているマクロ

    + +
      +
    • 次のバイトコード命令に遷移するマクロ NEXT は, ラベルgotoが使用可能な場合次の様に記述されている
    • +
    • NEXT自体はラベルテーブルにアクセスし, ラベルを取り出す
    • +
    • 次のバイトコードを取り出すのは, NEXT_OP というマクロが担っている
    • +
    + +
    #define NEXT_OP (op = *(MVMuint16 *)(cur_op), cur_op += 2, op)
    +#define NEXT *LABELS[NEXT_OP]
    +
    +
    +
      +
    • マクロ NEXT は次の様に展開される
    • +
    + +
    goto *LABELS[(op = *(MVMuint16 *)(cur_op), cur_op += 2, op)];
     
    @@ -233,33 +259,7 @@
    -

    MVM_interp_run

    - -
      -
    • MVM_interp_runでは次のオペコードをフェッチする際に NEXT_OP マクロを介して計算を行う.
    • -
    • オペコードが対応する命令を実行する際は, MVM_CGOTO フラグが立っている場合はCのラベルgotoを利用し, 使えない場合はswitch文を利用して遷移する.
    • -
    - -
    #define NEXT_OP (op = *(MVMuint16 *)(cur_op), cur_op += 2, op)
    -
    -#if MVM_CGOTO
    -#define DISPATCH(op)
    -#define OP(name) OP_ ## name
    -#define NEXT *LABELS[NEXT_OP]
    -#else
    -#define DISPATCH(op) switch (op)
    -#define OP(name) case MVM_OP_ ## name
    -#define NEXT runloop
    -#endif
    -
    - - - -
    - -
    - -

    MVM_interp_run

    +

    MVM_interp_run

    • ラベル遷移を利用する場合は配列LABELSにアクセスし, ラベル情報を取得する
    • @@ -288,7 +288,7 @@
      -

      MVM_interp_run

      +

      MVM_interp_run

      • Cの実装の場合, switch文に展開される可能性がある為, 命令ディスパッチが書かれているCソース・ファイルの指定の場所にのみ処理を記述せざるを得ない @@ -394,6 +394,9 @@ i->cur_op += 10; goto cbc_next(i); } + (i->reg_base[*((MVMuint16 *)(i->cur_op + 0))]).i64 = MVM_BC_get_I64(i->cur_op, 2); + i->cur_op += 10; + goto cbc_next(i);