Gauche:YAGHG:VM:フレームのヒープへのコピー

Gauche:YAGHG:VM:フレームのヒープへのコピー

スタックに保存されているフレームは次の時にヒープへ移される。

save_env

環境フレームをヒープにコピーしたあと、スタックに残っている環境フレームのsizeフィールドにフォーワードされたことを示す-1を設定する。 ヒープに移す対象となるのは現在の環境の直系のものだけである。

          BEFORE                             AFTER
         +=========+                        +=========+
         :         :                        :         :
         :         :                        :         :
         +=========+<---+                   +=========+
         |         |    |                   |         |
         | E#0     |    |                   | E#0     |
         |         |    |                   |         |
      up | NULL    |    |                up |       --+---------->+=========+<---+
         +=========+    |              size | -1      |           |         |    |
         :         :    |                   +=========+           | E#0'    |    |
         :         :    |                   :         :           |         |    |
         :         :    |                   :         :        up | NULL    |    |
         +=========+    |                   +=========+           +=========+    |
         |         |    |                   |         |                          |
         | E#1     |    |                   | E#1     |                          |
         |         |    |                   |         |                          |
         +=========+    |                   +=========+                          |
         :         :    |                   :         :                          |
         :         :    |                   :         :                          |
env ---->+=========+    |          env ---->+=========+                          |
         |         |    |                   |         |                          |
         | E#2     |    |                   | E#2     |                          |
         |         |    |                   |         |                          |
      up |       --+----+                up |       --+---------->+=========+    |
         +=========+                   size | -1      |           |         |    |
         |         |                        +=========+           | E#2'    |    |
         |         |                        |         |           |         |    |
                                            |         |        up |       --+----+
                                                                  +=========+

envレジスタやコンティニュエーションフレームが指す環境フレームを、 新しく作られたそれを指すように設定し直すのはsave_envを呼び出す次の関数の仕事である。

save_cont

save_envしてからコンティニュエーションフレームをヒープにコピーする。各コンティニュエーションフレームごとに環境フレームの保存を行うため、 最終的にはスタックに含まれる(最後の引数フレームを除いた)すべてのフレームがヒープに移される(はず)。

           BEFORE                             AFTER
          +=========+<---+                   +=========+
          |         |    |                   |         |
          | C#0     |    |                   | C#0     |
          |         |    |                   |         |
     prev | NULL    |    |              prev |       --+---------->+=========+<--------+
          +=========+    |              size | -1      |           |         |         |
          :         :    |                   +=========+           | C#0'    |         |
          :         :    |                   :         :           |         |         |
          :         :    |                   :         :      prev | NULL    |         |
          :         :    |                   :         :           +=========+         |
          :         :    |                   :         :                               |
          +=========+<---+----+              +=========+           +=========+<--------+----+
          |         |    |    |              |         |   copy    |         |         |    |
          | E#0     |    |    |              | E#0     |   ====>   | E#0'    |         |    |
          |         |    |    |              |         |           |         |         |    |
          +=========+    |    |              +=========+           +=========+         |    |
          :         :    |    |              :         :                               |    |
          :         :    |    |              :         :                               |    |
cont ---->+=========+    |    |              +=========+                               |    |
          |         |    |    |              |         |                               |    |
          | C#1     |    |    |              | C#1     |                               |    |
          |         |    |    |              |         |                               |    |
     prev |       --+----+    |         prev |       --+-------+------>+=========+     |    |
      env |       --+---------+         size | -1      |       |       |         |     |    |
          +=========+                        +=========+       |       | C#1'    |     |    |
          |         |                        |         |       |       |         |     |    |
          |         |                        |         |       |  prev |       --+-----+    |
                                                               |   env |       --+----------+
                                                               |       +=========+
                                                               |
                                                       cont ---+

注意点として、ここでいうコンティニュエーションフレームとは積みかけの引数フレームも含むと言うことが挙げられる。そういったフレームは コピー時に引数フレームの場所が変更される。

      TARGET                              COPIED
     +=========+<---+                    +=========+
     | arg#1   |    |               prev |         |
     +---------+    |                env |         |
     :         :    |               argp |       --+----+
     +---------+    |               size |         |    |
     | arg#N   |    |                 pc |         |    |
     +=========+    |               base |         |    |
prev |         |    |                    +=========+<---+
 env |         |    |                    | arg#1   |
argp |       --+----+                    +---------+
size |         |                         :         :
  pc |         |                         +---------+
base |         |                         | arg#N   |
     +=========+                         +=========+

(他にEscapePointの処理もあり。Gauche:EscapeHandlerAndFrameRelocation)

More ...