⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 tutorial.text

📁 idel虚拟机源码
💻 TEXT
字号:
I'm assuming you've already built and installed the system:	$ ./configure && make && make install(I'll show shell command lines indented with a $ prompt, and codesnippets indented without the prompt.)1. ASSEMBLY BASICSNow let's write some programs in Idel assembly.  The simplest possibleprogram does nothing:	def 0 1 main   0 ;You can try that out at the prompt this way:	$ echo "def 0 1 main   0 ;" | idelrun	$ So that successfully did nothing, hurray!  How did it work?  The `def'introduces a function definition, the `0 1' means it takes noarguments and returns one value (a status code), `main' is the name ofthe function, `0' is the value returned, and `;' ends it.  The extraspaces after the function name aren't significant, they're just forreadability.Now to do something useful: output the letter A.	def 0 1 main   'A' emit  0 ;First the ASCII code for `A' is pushed on the stack, then `emit' popsit off and outputs that byte.  The overall stack effect of `main' isstill 0 inputs and 1 output (`0 1') since the push is balanced by apop.  What happens when we violate that balance?  Let's see:	$ echo "def 0 1 main   'A'  0 ;" | idelrun	idelvm: Bad object file in defn #0: Inaccurate stack effect declaration (more results are yielded than declared)	$ echo "def 0 1 main   emit  0 ;" | idelrun	idelvm: Bad object file in defn #0: Inaccurate stack effect declaration (inferred 1 arguments, not 0)Let's dissect that.  First, the error messages came from idelvm ratherthan idelasm, because the assembler will happily pass along your badstack declarations without checking them.  Someday after I get aroundto adding that check into the assembler, the virtual machine loaderstill could not assume its input came from a friendly assembler.Second, the error messages refer to `defn #0' rather than `main'because the object file is stripped of names and other debug info.(Such info is an optional feature not yet done.)Just for practice, let's see what an error message from the assemblerlooks like:	$ echo "def 0 1 main   'A' remit  0 ;" | idelrun	1.27: Unresolved reference to remitWe made a typo for `emit', and the assembler took it for a functioncall to an undefined function.  The `1.27' is the source position ofthe offending token: line 1, column 27.Now we define multiple functions in the same file:	def 0 1 main   letter  0 ;		def 1 0 letter   'A' emit ;	\ Print an `A'The `\' character starts a comment that continues to the end of theline.  Line breaks don't matter otherwise -- source code is free-form.The `main' function is where execution starts because of its positionat the start, not its name.  We could have called it `flooby' instead.Next feature: local variables!	\ Emit an `A' in a fancy way.  (It's ASCII code 65.)	def 0 1 main   8 squared  1 +  emit  0 ;	\ Take a number n and return its square.	def 1 1 squared { n -- n n * } ;`squared' is a function taking 1 argument and returning 1 result.  Inits body is the block structure ``{ <variables> -- <code> }''.  Theoverall effect of the block is to pop as many elements off the stackas there are variables to the left of the `--' and put them in thenamed local variables, then perform the <code>.  After the `}' thevariables fall out of scope.  So `squared' pops the stack top into`n', then pushes `n' twice and multiplies (with `*').There's an if-then-else construct, only like in Forth it's spelledif-else-then:	def 0 1 main   -65 abs emit  0 ;	def 1 1 abs   	  { n -- n 0 < if  0 n -  else  n  then } ;The ``n 0 <'' pushes a flag on the stack, and `if' pops it off andexecutes either ``0 n -'' (if the flag is true) or ``n'' (if the flagis false).  Like in C, any nonzero value is considered true.  Unlikein C, the canonical true value is -1 (not 1): ``0 1 <'' yields -1 asits value.We now know enough to write a loop!  Let's print out 50 stars:	def 0 1 main   50 stars  0 ;	def 1 0 stars	  { n -- 0 n < if                     star  	           n 1 - stars                 then } ;	def 0 0 star   '*' emit ;The recursive call inside `stars' does *not* grow the stack, becauseit's in tail position -- it's the last thing the function does.  Callsin tail position are how this virtual machine provides the equivalentof GOTOs.  You can think of each function as a label in a conventionalassembly language, with the arguments on the stack being those localvariables that are live at that label.  Translating an imperativeprogram into this form is called the SSA transformation.  Manyoptimizing compilers and functional programmers prefer to work on codein this form.One more feature: string literals.	string: hello "Hello, world!\n"	def 0 1 main   hello.addr hello.size type  0 ;	\ Print out the string starting at a of length n.	def 2 0 type 	  { a n --  0 n < if  	              a c@ emit	              a 1 +  n 1 -  type  	            then } ;2. THE COOL STUFFOK, so why would anyone want to use this system?  The best reasons arenot yet implemented, but here's one thing to try: you can save thestate of a running program, including its full stack, into a portableobject file that can be resumed on another machine.	string: hello "Hello, "	string: world "world!\n"	def 0 0 main   	  hello.addr hello.size type	  save if  world.addr world.size type  then ;	\ Print out the string starting at a of length n.	def 2 0 type 	  { a n --  0 n < if  	              a c@ emit	              a 1 +  n 1 -  type  	            then } ;The `save' instruction in this version of the architecture stores thestate into a file named `frozen' and pushes 0 on the stack.  Thefrozen state will resume on the next instruction, only with -1 on thestack instead.  (Kind of like fork() or setjmp().)	$ idelasm tmp2 | idelvm -development	Hello, $ scp frozen remote-host	$ ssh darius@remote-host idelvm -development frozen	world!This demonstrates running a program partway, freezing it, transportingthe state to another machine, and resuming.  (We had to use the-development flag because, er... the security and resource managementfor this feature are currently broken and it's not important enough tofix.  And I'm thinking of taking it out completely.  Oh, well.)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -