2
0
この記事誰得? 私しか得しないニッチな技術で記事投稿!
Qiita Engineer Festa20242024年7月17日まで開催中!

日本語プログラミング言語Mind8のCランタイム起動シーケンスのスタック状態をモニタする(続き3)

Last updated at Posted at 2024-07-14

はじめに

前回の記事にて、Mind開発者@killyさんより情報共有いただいた検証用Consoleをベースにした中間コードのCディスパッチャの処理結果のリターンスタック値をC#代替実装版の互換値に変換することに成功しました。本来の目的はC#版の処理結果がずれはじめた起点を特定することにありましたが、両者の結果を精査した結果C#側の処理結果の出力にも誤りがあることを検出しました。本記事はその点を是正した結果の比較と見えてきた結果のご報告です。

前提条件

Windows11 Pro 22H2
VSCode(Visual Studo Code) 1.86.1
Microsoft Visual C++ 2008 Express Edition
Mind Version 8.0.08 for Windows
C# 12
dotnet-sdk-8.0.204-win-x64

VSCodeの拡張機能

C/C++ for Visual Studio Code 1.18.5 Microsoft
C/C++ Extension Pack 1.3.0 Microsoft
.NET Install Tool 2.0.2 Microsoft
Base language support for C# 2.18.16 Microsoft

C/C++のデバッガはCで実装されているMind8kernelの動作をデバッグ実行で探るために使用します。こちらの記事の環境となります。

お題のMind8の中間コード実行リスト(C#代替版のモニタコード改修版)

下記はC#代替版でお題のステップ数60のhellolevel1.mco中間コードファイルを処理させた結果です。

前回記事でC側のリターンスタック値のアドレス値をC#版のByte配列インデックス値の変換に成功したため、両者を比較することが可能となりました。結果を比較しましたところ、処理単語がC単語(C#版ではC#単語)のステップではなくMind単語のステップ直後のリターンスタック値が異なっており、あたかもスタック動作していないような状態となっていました。(手前のスタック値が消失しているかのように見える。)

そこで、C#側のMind処理単語のリターンスタックへのPUSH操作処理を精査してみましたが、そこには問題なく、結果のモニタ処理でも使用していたスタック値の相対オフセット指定で値をとりだす処理に誤りがありました。下記はその点を修正した結果です。

SqNo mcode mc(dec) mpoint dtp.point  dtp+0   dtp+1 rtp.point  rtp+0  rtp+1
   1 8019  32793    114   1024        0        0   1024        0        0
   2 002F     47    102   1024        0        0   1023      114        0
   3 0012     18   5862   1024        0        0   1023      114        0
   4 0036     54   5864   1024        0        0   1023      114        0
   5 0080    128   5870   1024        0        0   1023      114        0
   6 0036     54   5872   1024        0        0   1023      114        0
   7 0070    112   5878   1024        0        0   1023      114        0
   8 803A  32826   5880   1024        0        0   1023      114        0
   9 002F     47    238   1024        0        0   1022     5880      114
  10 80B8  32952   5858   1024        0        0   1022     5880      114
  11 0012     18   5842   1024        0        0   1021     5858     5880
  12 0036     54   5844   1024        0        0   1021     5858     5880
  13 0071    113   5850   1024        0        0   1021     5858     5880
  14 8046  32838   5852   1024        0        0   1021     5858     5880
  15 8045  32837    326   1024        0        0   1020     5852     5858
  16 0012     18    314   1024        0        0   1019      326     5852
  17 0036     54    316   1024        0        0   1019      326     5852
  18 0074    116    322   1024        0        0   1019      326     5852
  19 0020     32    324   1024        0        0   1019      326     5852
  20 0020     32    328   1024        0        0   1020     5852     5858
  21 80A3  32931   5854   1024        0        0   1021     5858     5880
  22 0036     54   3884   1024        0        0   1020     5854     5858
  23 0012     18   3890   1024        0        0   1020     5854     5858
  24 016E    366   3892   1024        0        0   1020     5854     5858
  25 0020     32   3898   1024        0        0   1020     5854     5858
  26 0020     32   5856   1024        0        0   1021     5858     5880
  27 0020     32   5860   1024        0        0   1022     5880      114
  28 00A5    165   5882   1024        0        0   1023      114        0
  29 803C  32828   5906   1022       20     5884   1023      114        0
  30 002F     47    246   1022       20     5884   1022     5906      114
  31 001A     26   5802   1022       20     5884   1022     5906      114
  32 006E    110   5804   1022       20     5884   1020        0        0
  33 0015     21   5808   1024        0        0   1020       20       20
  34 00ED    237   5810   1022        0        1   1020       20       20
  35 0022     34   5830   1024        0        0   1020       20       20
  36 0020     32   5856   1024        0        0   1023     5858     5906
  37 0020     32   5860   1024        0        0   1024     5906     5884
  38 00A5    165   5908   1024        0        0   1025     5884       20
  39 00C1    193   5926   1022       14     5910   1025     5884       20
$$COLD_FORTH
  40 0020     32   5928   1024        0        0   1025     5884       20
  41 658A  25994   5886   1024        0        0   1026       20       20
例外がスローされました: 'System.IndexOutOfRangeException' (mind8dispatch.dll の中)
プログラム '[11784] mind8dispatch.dll' がコード -1 (0xffffffff) で終了しました。

39ステップ目のmcodeの値が、Cオリジナルでは80C3のところ、C#代替版では従来002Aとなっていたヶ所が今回は658Aとなりました。修正した箇所は下記に説明するオフセット取得関数だけですが、それもC#単語処理中に使われていたかもしれません。

お題のC#ソースコード

StackPointer.cs
namespace Mind8Kernel
{ 
 /// <summary>スタックポインタ</summary>
    public class StackPointer{
    //~略~
        public uint GetUlOffset(int offset){/* for unsigned long access  */
            //アドレス指定で直接セットしている元コードのためポインタインデックスの自動増加はなし
            byte[] int32Byte = new byte[stackSize];
-            uint index=(uint)(stackIndex + offset*stackSize);
+            uint index=0;
+            if((stackIndex - offset*stackSize)>=0){
+                index=(uint)(stackIndex - offset*stackSize);
+            }
            for (ulong i = 0; i < stackSize; i++) int32Byte[i] = dataArray[index + i];
            return BitConverter.ToUInt32(int32Byte, 0);      
        }
    //~略~

下記のC#側モニタ出力のdtp.GetUlOffset(1)がおかしかったわけです。

Dispatcher.cs
namespace Mind8Kernel
{

    /// <summary>Mind8ディスパッチャ</summary>
    public partial class Dispatcher
    {
    //~略~
        /// <summary>ディスパッチャ</summary>
        /// <param name="McodeInfo">MCode情報構造体の参照</param>
        /// <param name="csFunc">C#関数配列の参照</param>
        private int Dispatch(McodeInfoStruct McodeInfo, Action[] csFuncs){
            
            ushort   mcode;

            int retcode=0;//setjmp( RESTARTENV );		/* ←ディスパッチャ再 */
            if ( retcode != 2 )			/* 強制脱出の検査 */
            {
                try{
                    int i=0;
                    for(;;)
                    {
                        mcode = mp.FetchMcode();
                        Console.Write("{0,4:d} {1,4:X4} {2,6:d} {3,6:d}",++i,mcode,mcode,mp.GetMcodeIndex());
                        Console.WriteLine(" {0,6:d} {1,8:d} {2,8:d} {3,6:d} {4,8:d} {5,8:d}",dtp.GetCurrentStackPointer(),dtp.GetUl(),
                                                    dtp.GetUlOffset(1),
                            rtp.GetCurrentStackPointer(),rtp.GetUl(),rtp.GetUlOffset(1));
                        if ( (mcode & 0x8000)==0 )
                        {
                            /* C#関数 */
                            csFuncs[mcode]();
                        }
                        else
                        {
                            /* Mind単語 */
                            //PUSH_R( McodePointer.l );
                            //#define  PUSH_R(addr) *(--RstackPointer)=(ULONG)(addr)
                            rtp.PushUl(mp.GetMcodeIndex());//現在のMCodeポインタの値をリターンスタックにプッシュする
                            //SET_MCODE_POINTER_BY_WORDNO( mcode & 0x7fff );
                            //McodePointer.b = (UCHAR *)(WordOffsetTable[wordNo])
                            mp.ResetMcodeIndex((uint)lp.GetSl((uint)(mcode & 0x7fff)));
                        }
                    }
    //~略~

お題のMind8の中間コード実行リストのリターンスタック値をC#代替互換にEXCELで加工して比較

コンバート結果を今回訂正したC#代替のリターンスタック値(インデックス値)と並べた結果が下記です。rtp+0(C#)とrtp+1(C#)の値が訂正されています。

SqNo mcode rtp.point rtp+0	rtp+0(補正)	rtp+0(C#) rtp+1	rtp+1(補正) rtp+1(C#)
1	8019	1024	       0	 0	      0	       0	       0	   0
2	002F	1023	12533850	114	    114	       0	       0	   0
3	0012	1023	12533850	114	    114	       0	       0	   0
4	0036	1023	12533850	114	    114	       0	       0	   0
5	0080	1023	12533850	114	    114	       0	       0	   0
6	0036	1023	12533850	114	    114	       0	       0	   0
7	0070	1023	12533850	114	    114	       0	       0	   0
8	803A	1023	12533850	114	    114	       0	       0	   0
9	002F	1022	12539616	5880	5880	12533850	 114	 114
10	80B8	1022	12539616	5880	5880	12533850	 114	 114
11	0012	1021	12539594	5858	5858	12539616	 5880	5880
12	0036	1021	12539594	5858	5858	12539616	 5880	5880
13	0071	1021	12539594	5858	5858	12539616	 5880	5880
14	8046	1021	12539594	5858	5858	12539616	 5880	5880
15	8045	1020	12539588	5852	5852	12539594	 5858	5858
16	0012	1019	12534062	326	     326	12539588	5852	5852
17	0036	1019	12534062	326	     326	12539588	5852	5852
18	0074	1019	12534062	326	     326	12539588	5852	5852
19	0020	1019	12534062	326	     326	12539588	5852	5852
20	0020	1020	12539588	5852	5852	12539594	5858	5858
21	80A3	1021	12539594	5858	5858	12539616	5880	5880
22	0036	1020	12539590	5854	5854	12539594	5858	5858
23	0012	1020	12539590	5854	5854	12539594	5858	5858
24	016E	1020	12539590	5854	5854	12539594	5858	5858
25	0020	1020	12539590	5854	5854	12539594	5858	5858
26	0020	1021	12539594	5858	5858	12539616	5880	5880
27	0020	1022	12539616	5880	5880	12533850	114	     114
28	00A5	1023	12533850	114	     114	       0		       0
29	803C	1023	12533850	114	     114	       0		       0
30	002F	1022	12539642	5906	5906	12533850	114	     114
31	001A	1022	12539642	5906	5906	12533850	114	     114
32	006E	1020	12539590	5854	   0	12539594	5858	   0
33	0015	1020	      20		      20	12539620	5884	  20
34	00ED	1020	      20		      20	12539620	5884	  20
35	0022	1020	      20		      20	12539620	5884	  20
36	00A5	1023	12533850	114	    5858	       0		5906
37	00C1	1023	12533850	114	    5906	       0		5884
$$COLD_FORTH					        5884			          20
38	0020	1023	12533850	114	    5884	       0		  20
39	80C3	1024	       0			               0		
40	00A5	1023	12533852	116	    5884	       0		  20
41	8083	1023	12533852	116	      20	       0		  20
42	0012	1022	12540140	6404		12533852	116	
43	004E	1022	12540140	6404		12533852	116	
44	00EC	1022	12540140	6404		12533852	116	
45	0096	1022	12540140	6404		12533852	116	
46	026D	1022	12540140	6404		12533852	116	
Hello by mind8								
47	0020	1022	12540140	6404		12533852	116	
48	0020	1023	12533852	116		       0	0	
49	801A	1024	       0			       0	0	
50	002F	1023	12533854	118		       0	0	
51	00A5	1023	12533854	118		       0	0	
52	00C1	1023	12533854	118		       0	0	
実行終り								
53	801B	1023	12533854	118		       0	0	
54	002F	1022	12539708	5972		12533854	118	
55	00A5	1022	12539708	5972		12533854	118	
56	00C1	1022	12539708	5972		12533854	118	
実行終り時の処理								
57	0020	1022	12539708	5972		12533854	118	
58	0012	1023	12533854	118		       0	0	
59	004E	1023	12533854	118		       0	0	
60	0014	1023	12533854	118		       0	0	

訂正された結果同士で比較しますと、ステップ31の001Aが処理された後のスタック値が一致しなくなっているようです。ステップ36以降も訂正されたC#版実行結果ではC版と異なっていますが、上記表では無視しています。

つづく

生成されたhello.mcoを解釈して、C#側で「Hello by mind8」が出力されるようにするまでの長い道のりですが(初期処理をショートカットすればこの処理自体は処理できていますが、初期処理をどの程度対応するかで道のりの長さは大きく変動しまして、カメの動きとなっております。)、問題個所の特定を引き続き行ってまいります。

2
0
2

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
0