ネオ仮想マシン
3865 ワード
前の「Neoコンパイラ」では、NeoコンパイラがCILをneo仮想マシンのopcodeにどのように変換するかを説明していますが、vm仮想マシンはこれらのコードをどのように処理しているのか、この文章では仮想マシンのコードを見てみましょう.
仮想マシンの場所
フレームワーク図では、Virtual Machineが次のような役割を果たしていることがわかります. Opcode(smart contract)を読み出し、Execution Engineで を実行する. Execution Engine論理演算 Interop ServiceはExternal Data を呼び出すことができる.システム呼び出し(OP_SYSCALL)は、ブロックチェーン帳簿の情報 にアクセスすることができる.
次に、仮想マシンがOpcodeを読み込む方法を見てみましょう.
以下に示す図はUMLではなく、UMLが面倒なのか、それとも脳図が思考論理の発展に合っているのか.
重要なオブジェクト Execution Engine:実行エンジン Execution Context:実行コンテキスト Stack Item:スタックのデータ Crypto:C#の暗号化ライブラリ IScriptTableにはAppCallコマンドで呼び出せる他のcontractのコードが格納されています.このブロックはブロックチェーンの実現を検討する必要があります.これは後で詳しく検討します. InteropServiceはSYSCALLに応答するために使用され、具体的にはシステム呼び出し、何に使用されるかは、後で例を挙げて説明します. InvocationStackは呼び出しスタックであり、パラメータが入力され、他の契約を呼び出すと新しい呼び出しスタック がある. EvaluationStackは、動作 を実行するための計算スタックである. AltStackはスタンバイスタックであり、計算スタックで算出された中間結果はスタンバイスタック に保存することができる.
実行コンテキスト
各変数はよく理解されていますが、ポイントは以下でどのように使うかを見ることです.
vmコード実行プロセス構造で、このときscript container,script tableに入ることができ、後でブロックチェーンでこれらがどこから来たのかを見てみましょう.ここではvmの実行プロセスだけに集中しています. ロード.avm,avmはコンパイラがコンパイルした一連の数字で、engine.LoadScriptはロードできます.
executeが実行を開始します.コードを見てみましょう.
この行のコードを見てください.OpCode opcode=CurrentContext.InstructionPointer >= CurrentContext.Script.Length ? OpCode.RET : (OpCode)CurrentContext.OpReader.ReadByte();コードの実行が完了する後、OpCodeを挿入する.RET RETでない場合、read 1バイトのopcode ExecuteOp関数はOpCodeを実行する具体的な意味であり,一例で説明する.
前回のコードです
仮想マシンのコードのテスト
生成されたコードは長すぎて、少し辛抱強く見ることができて、もし画像がはっきりしないならば、コード倉庫に行ってpdfをダウンロードすることができます
具体的な実行プロセス
文章は簡単なコードを過ぎただけで、後でシステム呼び出しと外部ストレージへのアクセス、スマート契約の間で相互に呼び出される状況を検討する必要があります.
作者:沈寅原文リンク:https://www.jianshu.com/p/b7a...
フレーム
仮想マシンの場所
フレームワーク図では、Virtual Machineが次のような役割を果たしていることがわかります.
次に、仮想マシンがOpcodeを読み込む方法を見てみましょう.
VMオブジェクト関係
以下に示す図はUMLではなく、UMLが面倒なのか、それとも脳図が思考論理の発展に合っているのか.
重要なオブジェクト
実行エンジン
実行コンテキスト
実行コンテキスト
各変数はよく理解されていますが、ポイントは以下でどのように使うかを見ることです.
vm実行プロセス
vmコード実行プロセス
executeが実行を開始します.コードを見てみましょう.
public void Execute()
{
State &= ~VMState.BREAK;
while (!State.HasFlag(VMState.HALT) && !State.HasFlag(VMState.FAULT) && !State.HasFlag(VMState.BREAK))
StepInto();
}
public void StepInto()
{
if (InvocationStack.Count == 0) State |= VMState.HALT;
if (State.HasFlag(VMState.HALT) || State.HasFlag(VMState.FAULT)) return;
OpCode opcode = CurrentContext.InstructionPointer >= CurrentContext.Script.Length ? OpCode.RET : (OpCode)CurrentContext.OpReader.ReadByte();
try
{
ExecuteOp(opcode, CurrentContext);
}
catch
{
State |= VMState.FAULT;
}
}
この行のコードを見てください.OpCode opcode=CurrentContext.InstructionPointer >= CurrentContext.Script.Length ? OpCode.RET : (OpCode)CurrentContext.OpReader.ReadByte();
具体的な例
前回のコードです
using Neo.SmartContract.Framework;
using Neo.SmartContract.Framework.Services.Neo;
public class Sum : SmartContract
{
public static int Main(int a, int b)
{
return a + b;
}
}
仮想マシンのコードのテスト
using System;
using System.IO;
using System.Linq;
using Neo;
using Neo.VM;
using Neo.Cryptography;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
var engine = new ExecutionEngine(null, Crypto.Default);
engine.LoadScript(File.ReadAllBytes(@"C:\……\Test1.avm"));
using (ScriptBuilder sb = new ScriptBuilder())
{
sb.EmitPush(4); // b
sb.EmitPush(3); // a
engine.LoadScript(sb.ToArray());
}
engine.Execute(); //
var result = engine.EvaluationStack.Peek().GetBigInteger(); //
Console.WriteLine($" {result}");
Console.ReadLine();
}
}
}
実行される特定のプロセス
生成されたコードは長すぎて、少し辛抱強く見ることができて、もし画像がはっきりしないならば、コード倉庫に行ってpdfをダウンロードすることができます
具体的な実行プロセス
まとめ
文章は簡単なコードを過ぎただけで、後でシステム呼び出しと外部ストレージへのアクセス、スマート契約の間で相互に呼び出される状況を検討する必要があります.
作者:沈寅原文リンク:https://www.jianshu.com/p/b7a...