Forth 内部解释程序工作流程
body, table{font-family: 微软雅黑; font-size: 13.5pt}
table{border-collapse: collapse; border: solid gray; border-width: 2px 0 2px 0;}
th{border: 1px solid gray; padding: 4px; background-color: #DDD;}
td{border: 1px solid gray; padding: 4px;}
tr:nth-child(2n){background-color: #f8f8f8;}
| CODE EXECUTE ( cfa - ) 执行编译地址(即 cfa )在参数栈顶的定义 W POP 把在堆栈上的 cfa 送入到现行词指针 W 中 0 [W] JMP 经由 W 进行一次间接转移 END-CODE |
| NEXT 是一个 CODE 词。执行 NEXT 就是执行由 IP 所指着的下一个词。在执行 NEXT 中要做三件事: 1、((IP)) -> W 使 W 指着由 IP 当前内容所指着的词; 2、(IP)+2 -> IP 使 IP 的内容递增 2; 3、间接转移执行由 W 所指着的词; 解释指针 IP (有时又称为指令指针)的值由 NEXT 来设置和更新,所以每一个 CODE 词的最后都无例外地一定要执行 NEXT 。执行 NEXT 就去执行由 IP 所指的下一个 cfa 所代表的子程序,同时更新 IP 的值指向再下一个地址,一直重复直到执行完毕一个定义中的所有编译地址。 |
| NEST 在执行 NEST 之前,IP 含有待返回的地址,而 W 含有要被调用的冒号定义的 cfa 。执行 NEST 要做四件事: 1、(IP) -> 返回栈顶(即保存好的 IP 原来的内容); 2、(W)+2 -> W 使 W 指向要被调用的定义的 pfa (即参数域地址); 3、(W) -> IP 把所要执行的词的地址送入 IP; 4、执行 NEXT。 NEST 在不同的 FORTH 系统中可能有不同的名字,如(NEST)、DO_COLON等。NEST 所代表的子程序是所有的冒号定义在一开始执行时都要首先执行的共同子程序。 |
| UNNEST 是一个 CODE 词。它把返回栈顶的首项移入到解释指针中,结束一冒号定义的执行和返回到它的调用者。执行 UNNEST 时要做两件事: 1、把返回堆栈顶第一个单元的内容送入 IP 中; 2、执行 NEXT ; UNNEST 在不同的 FORTH 版本中也可能有不同的名字,比如 ;S 、EXIT 等。在词典中的每一个冒号定义的最后一个成分一定是 UNNEST ,它来源于冒号源定义中最后的分号。 |
冒号定义的执行过程:
| NOTHING | ^nest | ^unnest(14B) | |
| 66DE | 66E0 ( lfa ) | 66E8 | 66EA ( pfa ) |
| STEP1 | ^NEST | ^DUP(3C4) | ^OVER(3E4) | ^NOTHING(66E8) | ^+(582) | ^+(582) | ^UNNEST(14B) |
| 66F2 | 66F6 | 66F8 | 66FA | 66FC | 66FE | 6700 | 6702 |
| 当执行 DUP 时,(IP)=66FA指向OVER,DUP词本身的最后一个成分是NEXT,于是当执行DUP的NEXT时发生: 1、((IP)) -> W ,也即IP的内容的内容进入到 W 中,于是 (W)=3E4,它是词 OVER 的 cfa; 2、(IP)+2 -> IP,于是 (IP)=66FC,指向词NOTHING; 3、执行 W 所指的词,即执行 OVER 。OVER 是一个 CODE 词,它的 cfa 单元的内容就是它的 pfa ,于是就跳去执行其词身内的机器指令。 |
| 执行 OVER 的最后一个成分又是 NEXT,当执行此 NEXT 时发生: 1、((IP)) -> W,于是 (W) = 66E8,它是 NOTHING 的 cfa; 2、(IP)+2 -> IP,于是 (IP) = 66FE,它指着第一个 +; 3、执行 W 所指的词 NOTHING; |
| NOTHING 是以冒号定义,所以它的 cfa 单元的内容是 NEST 的地址,于是就跳去执行 NEST,执行 NEST 时发生: 1、(IP) -> 返回堆栈栈顶,返回地址 66FE 就被保存在返回栈中。 2、(W)+2 -> W,(W)=66EA,它是 NOTHING 的 pfa。 3、(W) -> IP,(IP)=66EA,指着 NOTHING 内的 UNNEST。 4、执行 NEXT 1)、((IP)) -> W,(W)=14B,它是 UNNEST 的地址。 2)、(IP)+2 -> IP,(IP)=66EC,这个地址是分号后的一个地址,没有任何意义,后面执行UNNEST会被修改,直接丢弃 3)、执行W所指的词,也即执行UNNEST |
| 执行 UNNEST 时发生: 1、返回栈顶的内容 -> IP,于是(IP)=66FE,指着 STEP1 内的第一个 +; //每执行一次UNNEST,程序执行嵌套就减少一层,返回到原来的调用层中。 2、执行 NEXT 1)、((IP)) -> W,(W) = 582 2)、(IP)+2 -> IP,(IP) = 6700,指着 STEP1 中的第二个 +; 2)、执行由W所指的词,也即此时 STEP1 中的第一个 + 被执行。 //由于 + 是CODE词,它不会进入更深一层的嵌套。 |
| ……等执行完STEP1的UNNEST之后就返回到STEP1的调用者,也就是返回到外部解释程序INTERPRET,由于执行完STEP1后输入流耗尽,于是跳转到FORTH循环中的外循环 QUIT 。在显示屏上打印出“ok”后,FORTH 又等待使用者从键盘上输入下一行命令。 |
Forth 内部解释程序工作流程的更多相关文章
- Spark基本工作流程及YARN cluster模式原理(读书笔记)
Spark基本工作流程及YARN cluster模式原理 转载请注明出处:http://www.cnblogs.com/BYRans/ Spark基本工作流程 相关术语解释 Spark应用程序相关的几 ...
- 前端工作流程自动化——Grunt/Gulp 自动化
什么是自动化 先来说说为什么要自动化.凡是要考虑到自动化时,你所做的工作必然是存在很多重复乏味的劳作,很有必要通过程序来完成这些任务.这样一来就可以解放生产力,将更多的精力和时间投入到更多有意义的事情 ...
- Struts2 工作流程
Struts2使用了WebWork的设计核心(XWork),在内部使用拦截器处理用户请求,从而允许用户业务逻辑控制器和ServletAPI分离.Struts2内部是一个MVC架构,Struts2 的核 ...
- docker工作流程
Docker提供一种方法在容器中运行安全隔离的应用程序,应用程序与所有依赖项和库一起打包在容器中.因为你的应用程序总是可以使用它在构建镜像中期望的环境运行,测试和部署比以往任何时候都更简单,因为你的构 ...
- SpringMVC第一篇【介绍、入门、工作流程、控制器】
什么是SpringMVC? SpringMVC是Spring家族的一员,Spring是将现在开发中流行的组件进行组合而成的一个框架!它用在基于MVC的表现层开发,类似于struts2框架 为什么要使用 ...
- Struts2学习---拦截器+struts的工作流程+struts声明式异常处理
这一节我们来看看拦截器,在讲这个之前我是准备先看struts的声明式异常处理的,但是我发现这个声明式异常处理就是由拦截器实现的,所以就将拦截器的内容放到了前面. 这一节的内容是这样的: 拦截器的介绍 ...
- 【嵌入式开发】 Bootloader 详解 ( 代码环境 | ARM 启动流程 | uboot 工作流程 | 架构设计)
作者 : 韩曙亮 博客地址 : http://blog.csdn.net/shulianghan/article/details/42462795 转载请著名出处 相关资源下载 : -- u-boo ...
- [Inside HotSpot] C1编译器工作流程及中间表示
1. C1编译器线程 C1编译器(aka Client Compiler)的代码位于hotspot\share\c1.C1编译线程(C1 CompilerThread)会阻塞在任务队列,当发现队列有编 ...
- kafka工作流程| 命令行操作
1. 概述 数据层:结构化数据+非结构化数据+日志信息(大部分为结构化) 传输层:flume(采集日志--->存储性框架(如HDFS.kafka.Hive.Hbase))+sqoop(关系型数 ...
随机推荐
- Windows Server Backup(2016) 备份
1. 使用 Windows Server Backup 备份 如果服务器没有启用 Windows Server Backup,需要打开服务器管理器,如下图 点击添加角色和功能,根据向导,添加 Wind ...
- 关于javaweb项目红叉报错可但项目可以正常运行的解决办法
有时候导入的项目工程,文件夹左下角永远有一个红叉,但是由于不影响程序运行,所以之前一直忽略了,但是强迫症患者表示不解决巨蓝瘦,网上有些方法没有讲清楚,所以今天做了个总结来教大家如何详细解 ...
- 单元测试系列之五:Mock工具之Mockito实战
更多原创测试技术文章同步更新到微信公众号 :三国测,敬请扫码关注个人的微信号,感谢! 原文链接:http://www.cnblogs.com/zishi/p/6780719.html 在实际项目中写单 ...
- jmeter 学习笔记
beanshell内置对象 vars是针对单线程,使用${varName}访问var变量值 props是所有线程共享,使用${__P(propName,)}访问prop变量值 如何让variable在 ...
- 【python】 迭代器、生成器、列表推导式
一.可迭代对象.迭代器 1.可以被for循环的数据类型(可迭代对象): 字符串(str).列表(list).字典(dict).元祖(tuple).range() 2.迭代器 2.1 将可迭代对象==& ...
- php接口签名验证
在做一些api接口设计时候会遇到设置权限问题,比如我这个接口只有指定的用户才能访问. 很多时候api接口是属于无状态的,没办法获取session,就不能够用登录的机制去验证,那么 大概的思路是在请求包 ...
- Apache Solr入门教程(转)
1.为什么选择Apache Solr Apache Solr是一个功能强大的搜索服务器,它支持REST风格API.Solr是基于Lucene的,Lucene 支持强大的匹配能力,如短语,通配符,连接, ...
- 显示等待 (web自动化测试)
from selenium.webdriver.common.keys import Keys from selenium.webdriver.common.by import By from sel ...
- 【安卓进阶】Scroller理解与应用
项目中有个需求,就是在RecyclerView的item中进行侧滑,一开始同事推荐了一个开源库,使用起来确实也方便好用,直接在布局作为父布局即可实现侧滑. 自己也非常好奇这个开源库到底用了什么API能 ...
- 二十八、linux下权限管理chmod
(1)查看权限 终端下需要查看文件或文件夹的权限时,可以使用ll查看当前目录的各文件权限. 如图,r代表读取权限,w代表写入权限,x代表执行权限:-代表普通文件,d代表文件夹.使用命令chmod可以修 ...