NEOVM 是什么,以及它如何工作

neovm 就是 neo's vm文中提到手游传奇发布网天生有着强韧的生命力,经过风吹雨打也能化茧成蝶成为最优秀的自己。
拆开就很清楚了,neo区块链系统中使用的虚拟机。
虚拟机就是虚拟的电脑,现在我们通常提到的虚拟机有两种典型的形式。
11一种是对一台电脑完整的模拟
比如hyper-v,vmware
还有街机模拟器
12另一种是仅仅作为执行环境
比如jvm 比如dotnet framework 比如v8\lua
对于开发者来说,面对的执行环境又分为两大类情况。
121 公用执行环境
公用执行环境,比如java c# python
122 一种是嵌入式执行环境
举个例子,比如lua 就是一种典型的嵌入式脚本。
当然也有通过mono 和 v8,把c# 和 js 作为嵌入式脚本使用的情况。
2 neovm是什么
neovm的形式就是上文 122 这种,和lua相似,是一种嵌入式的执行环境。
neovm是一种基于图灵机模式的虚拟机,通过磁头在磁带上的移动改变状态,以此来实现逻辑运算。
neovm 是 不依赖于neo项目的一个单独系统,neovm只提供纯粹的逻辑计算能力,采用可扩展的互操作方式,后插入虚拟机可以调用的功能。
neovm的设计更贴近机器,执行的代码段是一个内存块,执行时即时将数据解析为指令。
3 neovm的执行方式
要说明这件事情我们必须得复习一下图灵机了
忽略我丑陋的字迹
这里就假设你了解磁带式音乐播放器的工作原理,要不然head 和 tape 就变成一个晦涩的概念了。
1在一条磁带tape上写上指令。
2磁头head负责读取当前指令
3指令集是已知的 图中展示了四条指令
nop 啥也不做 push [n] 将一个数字推到calcstack 中 add 从calcstack中取两个值,将他们相加,再放回calcstack中 ret 结束当前执行。
4寄存器空间来管理状态,对neovm来说寄存器是两个stack,calcstack 和 altstack。
有磁带,有磁头,指令集,状态空间,这就是一个图灵机了。
4 talk is cheap
让我们来研究一下代码吧
代码在 samplesturing01
不到100行代码,模拟了那副丑陋的画里的图灵机执行过程。
首先是准备好写着代码的磁带
nop
push 1
push 2
add
ret
然后滚动磁带,让代码一条条滚到磁头下面
while(!vmstop)
{
}
这里涉及到图灵机的停机问题,ret指令就是来通知停机的,要不然我们就会一直滚动下去。当然也可以依赖纸带的长度来停机,实际上neovm是设计为纸带用完自动停机的 相信不会有人怀疑这个程序得到的retvalue是3。
让我们来分析一下发生了什么。
这只是模拟程序,一次说明一个问题,我们用class head表示磁头,用list表示磁带
滚动磁带是通过headpos的累加
状态空间 是 stop变量 和 calcstack 栈
执行指令的步骤写在函数stepone中
stepone 的过程是 1读取磁带上位于磁头处的代码 2执行代码 3滚动磁头 headpos++;
执行代码时就是操作状态空间
nop 什么也不干,但nop依然是最重要的指令之一,你就把他当作空格就好了。
ret 直接导致停机,磁头也不再滚动, 磁头位置也是状态空间的一部分,指令可以导致磁头位置变化,这一点很重要,因为流程控制的本质就是磁头位置变化,所有 的 if for while 逻辑,最后落实到vm上都是在改变磁头位置。
push 往calcstack上推一个值
add 从calcstack取两个值,相加后再放回去
如果你跑起这个程序,断点,一步步stepone,观察calcstack,你会发现:
1nop 之后,什么也没有发生 2push 1 之后,calcstack里面是 [1] 3push 2 之后,calcstack里面是 [2,1] 4add 之后,calcstack 里面是 [3] 5ret 之后,stop 变成true了,于是循环就结束了。
这就是neovm的工作原理了。
对neovm来说 avm 就是这条tape了,不同之处在于avm是byte[],不是像我们这里使用的list 这么结构化。
这篇的目的是解释neovm是什么,是怎么工作的,先用这个简单的程序进行说明。
更多问题,下一篇继续
参考源码位置 githubcomlightszeroneovmbooktreemastersamplesturing01