Diff for /gforth/doc/vmgen.texi between versions 1.5 and 1.10

version 1.5, 2002/08/01 21:14:25 version 1.10, 2002/08/13 19:33:38
Line 1 Line 1
   \input texinfo    @c -*-texinfo-*-
   @comment %**start of header
   @setfilename vmgen.info
 @include version.texi  @include version.texi
   @settitle Vmgen (Gforth @value{VERSION})
   @c @syncodeindex pg cp
   @comment %**end of header
   @copying
   This manual is for Vmgen
   (version @value{VERSION}, @value{UPDATED}),
   the virtual machine interpreter generator
   
   Copyright @copyright{} 2002 Free Software Foundation, Inc.
   
   @quotation
   Permission is granted to copy, distribute and/or modify this document
   under the terms of the GNU Free Documentation License, Version 1.1 or
   any later version published by the Free Software Foundation; with no
   Invariant Sections, with the Front-Cover texts being ``A GNU Manual,''
   and with the Back-Cover Texts as in (a) below.  A copy of the
   license is included in the section entitled ``GNU Free Documentation
   License.''
   
   (a) The FSF's Back-Cover Text is: ``You have freedom to copy and modify
   this GNU Manual, like GNU software.  Copies published by the Free
   Software Foundation raise funds for GNU development.''
   @end quotation
   @end copying
   
   @dircategory GNU programming tools
   @direntry
   * vmgen: (vmgen).               Interpreter generator
   @end direntry
   
   @titlepage
   @title Vmgen
   @subtitle for Gforth version @value{VERSION}, @value{UPDATED}
   @author M. Anton Ertl (@email{anton@mips.complang.tuwien.ac.at})
   @page
   @vskip 0pt plus 1filll
   @insertcopying
   @end titlepage
   
   @contents
   
   @ifnottex
   @node Top, Introduction, (dir), (dir)
   @top Vmgen
   
   @insertcopying
   @end ifnottex
   
   @menu
   * Introduction::                What can Vmgen do for you?
   * Why interpreters?::           Advantages and disadvantages
   * Concepts::                    VM interpreter background
   * Invoking vmgen::              
   * Example::                     
   * Input File Format::           
   * Using the generated code::    
   * Changes::                     from earlier versions
   * Contact::                     Bug reporting etc.
   * Copying This Manual::         Manual License
   * Index::                       
   
   @detailmenu
    --- The Detailed Node Listing ---
   
   Concepts
   
   * Front end and VM interpreter::  Modularizing an interpretive system
   * Data handling::               Stacks, registers, immediate arguments
   * Dispatch::                    From one VM instruction to the next
   
   Example
   
   * Example overview::            
   * Using profiling to create superinstructions::  
   
   Input File Format
   
   * Input File Grammar::          
   * Simple instructions::         
   * Superinstructions::           
   
   Simple instructions
   
   * C Code Macros::               Macros recognized by Vmgen
   * C Code restrictions::         Vmgen makes assumptions about C code
   
   Using the generated code
   
   * VM engine::                   Executing VM code
   * VM instruction table::        
   * VM code generation::          Creating VM code (in the front-end)
   * Peephole optimization::       Creating VM superinstructions
   * VM disassembler::             for debugging the front end
   * VM profiler::                 for finding worthwhile superinstructions
   
   Copying This Manual
   
   * GNU Free Documentation License::  License for copying this manual.
   
   @end detailmenu
   @end menu
   
 @c @ifnottex  @c @ifnottex
 This file documents vmgen (Gforth @value{VERSION}).  This file documents Vmgen (Gforth @value{VERSION}).
   
   @c ************************************************************
   @node Introduction, Why interpreters?, Top, Top
 @chapter Introduction  @chapter Introduction
   
 Vmgen is a tool for writing efficient interpreters.  It takes a simple  Vmgen is a tool for writing efficient interpreters.  It takes a simple
Line 29  machine code. Line 135  machine code.
 @end itemize  @end itemize
   
 Such a division is usually used in interpreters, for modularity as well  Such a division is usually used in interpreters, for modularity as well
 as for efficiency reasons.  The virtual machine code is typically passed  as for efficiency.  The virtual machine code is typically passed between
 between front end and virtual machine interpreter in memory, like in a  front end and virtual machine interpreter in memory, like in a
 load-and-go compiler; this avoids the complexity and time cost of  load-and-go compiler; this avoids the complexity and time cost of
 writing the code to a file and reading it again.  writing the code to a file and reading it again.
   
Line 101  we will implement new features if someon Line 207  we will implement new features if someon
 list above is not exhaustive.  list above is not exhaustive.
   
 @c *********************************************************************  @c *********************************************************************
   @node Why interpreters?, Concepts, Introduction, Top
 @chapter Why interpreters?  @chapter Why interpreters?
   
 Interpreters are a popular language implementation technique because  Interpreters are a popular language implementation technique because
Line 129  Vmgen makes it even easier to implement Line 236  Vmgen makes it even easier to implement
 techniques for building efficient interpreters.  techniques for building efficient interpreters.
   
 @c ********************************************************************  @c ********************************************************************
   @node Concepts, Invoking vmgen, Why interpreters?, Top
 @chapter Concepts  @chapter Concepts
   
   @menu
   * Front end and VM interpreter::  Modularizing an interpretive system
   * Data handling::               Stacks, registers, immediate arguments
   * Dispatch::                    From one VM instruction to the next
   @end menu
   
 @c --------------------------------------------------------------------  @c --------------------------------------------------------------------
 @section Front-end and virtual machine interpreter  @node Front end and VM interpreter, Data handling, Concepts, Concepts
   @section Front end and VM interpreter
   
 @cindex front-end  @cindex front-end
 Interpretive systems are typically divided into a @emph{front end} that  Interpretive systems are typically divided into a @emph{front end} that
Line 165  Vmgen currently has no special support f Line 279  Vmgen currently has no special support f
 information in the instruction descriptions can be helpful, and we are  information in the instruction descriptions can be helpful, and we are
 open for feature requests and suggestions.  open for feature requests and suggestions.
   
   @c --------------------------------------------------------------------
   @node Data handling, Dispatch, Front end and VM interpreter, Concepts
 @section Data handling  @section Data handling
   
 @cindex stack machine  @cindex stack machine
Line 203  harder, but might be possible (contact u Line 319  harder, but might be possible (contact u
 @c reference counting might be possible by including counting code in   @c reference counting might be possible by including counting code in 
 @c the conversion macros.  @c the conversion macros.
   
   @c --------------------------------------------------------------------
   @node Dispatch,  , Data handling, Concepts
   @section Dispatch
   
   Understanding this section is probably not necessary for using vmgen,
   but it may help.  You may want to skip it now, and read it if you find statements about dispatch methods confusing.
   
   After executing one VM instruction, the VM interpreter has to dispatch
   the next VM instruction (vmgen calls the dispatch routine @samp{NEXT}).
   Vmgen supports two methods of dispatch:
   
   @table
   
   @item switch dispatch
   In this method the VM interpreter contains a giant @code{switch}
   statement, with one @code{case} for each VM instruction.  The VM
   instructions are represented by integers (e.g., produced by an
   @code{enum}) in the VM code, and dipatch occurs by loading the next
   integer from the VM code, @code{switch}ing on it, and continuing at the
   appropriate @code{case}; after executing the VM instruction, jump back
   to the dispatch code.
   
   @item threaded code
   This method represents a VM instruction in the VM code by the address of
   the start of the machine code fragment for executing the VM instruction.
   Dispatch consists of loading this address, jumping to it, and
   incrementing the VM instruction pointer.  Typically the threaded-code
   dispatch code is appended directly to the code for executing the VM
   instruction.  Threaded code cannot be implemented in ANSI C, but it can
   be implemented using GNU C's labels-as-values extension (@pxref{labels
   as values}).
   
   @end table
   
 @c *************************************************************  @c *************************************************************
   @node Invoking vmgen, Example, Concepts, Top
 @chapter Invoking vmgen  @chapter Invoking vmgen
   
 The usual way to invoke vmgen is as follows:  The usual way to invoke vmgen is as follows:
Line 240  Print version and exit Line 391  Print version and exit
 @c env vars GFORTHDIR GFORTHDATADIR  @c env vars GFORTHDIR GFORTHDATADIR
   
 @c ****************************************************************  @c ****************************************************************
   @node Example, Input File Format, Invoking vmgen, Top
 @chapter Example  @chapter Example
   
   @menu
   * Example overview::            
   * Using profiling to create superinstructions::  
   @end menu
   
   @c --------------------------------------------------------------------
   @node Example overview, Using profiling to create superinstructions, Example, Example
 @section Example overview  @section Example overview
   
 There are two versions of the same example for using vmgen:  There are two versions of the same example for using vmgen:
Line 311  check}.  You can run run mini programs l Line 470  check}.  You can run run mini programs l
   
 To learn about the options, type @samp{./mini -h}.  To learn about the options, type @samp{./mini -h}.
   
   @c --------------------------------------------------------------------
   @node Using profiling to create superinstructions,  , Example overview, Example
 @section Using profiling to create superinstructions  @section Using profiling to create superinstructions
   
 I have not added rules for this in the @file{Makefile} (there are many  I have not added rules for this in the @file{Makefile} (there are many
Line 361  preceed larger superinstructions. Line 522  preceed larger superinstructions.
 Now you can create a version of mini with superinstructions by just  Now you can create a version of mini with superinstructions by just
 saying @samp{make}  saying @samp{make}
   
   
 @c ***************************************************************  @c ***************************************************************
   @node Input File Format, Using the generated code, Example, Top
 @chapter Input File Format  @chapter Input File Format
   
 Vmgen takes as input a file containing specifications of virtual machine  Vmgen takes as input a file containing specifications of virtual machine
Line 369  instructions.  This file usually has a n Line 532  instructions.  This file usually has a n
   
 Most examples are taken from the example in @file{vmgen-ex}.  Most examples are taken from the example in @file{vmgen-ex}.
   
   @menu
   * Input File Grammar::          
   * Simple instructions::         
   * Superinstructions::           
   @end menu
   
   @c --------------------------------------------------------------------
   @node Input File Grammar, Simple instructions, Input File Format, Input File Format
 @section Input File Grammar  @section Input File Grammar
   
 The grammar is in EBNF format, with @code{@var{a}|@var{b}} meaning  The grammar is in EBNF format, with @code{@var{a}|@var{b}} meaning
Line 409  Vmgen understands a few extensions beyon Line 580  Vmgen understands a few extensions beyon
 these extensions are only useful for building Gforth.  You can find a  these extensions are only useful for building Gforth.  You can find a
 description of the format used for Gforth in @file{prim}.  description of the format used for Gforth in @file{prim}.
   
 @subsection  @subsection Eval escapes
 @c woanders?  @c woanders?
 The text in @code{eval-escape} is Forth code that is evaluated when  The text in @code{eval-escape} is Forth code that is evaluated when
 vmgen reads the line.  If you do not know (and do not want to learn)  vmgen reads the line.  If you do not know (and do not want to learn)
Line 441  stack-prefix ( stack "prefix" -- ) Line 612  stack-prefix ( stack "prefix" -- )
 @end example  @end example
   
   
   @c --------------------------------------------------------------------
   @node Simple instructions, Superinstructions, Input File Grammar, Input File Format
 @section Simple instructions  @section Simple instructions
   
 We will use the following simple VM instruction description as example:  We will use the following simple VM instruction description as example:
Line 517  arguments can only appear to the left of Line 690  arguments can only appear to the left of
 If there are multiple instruction stream arguments, the leftmost is the  If there are multiple instruction stream arguments, the leftmost is the
 first one (just as the intuition suggests).  first one (just as the intuition suggests).
   
 @subsubsection C Code Macros  @menu
   * C Code Macros::               Macros recognized by Vmgen
   * C Code restrictions::         Vmgen makes assumptions about C code
   @end menu
   
   @c --------------------------------------------------------------------
   @node C Code Macros, C Code restrictions, Simple instructions, Simple instructions
   @subsection C Code Macros
   
 Vmgen recognizes the following strings in the C code part of simple  Vmgen recognizes the following strings in the C code part of simple
 instructions:  instructions:
Line 574  presence of these strings; vmgen will no Line 754  presence of these strings; vmgen will no
 a C preprocessor macro.  a C preprocessor macro.
   
   
 @subsubsection C Code restrictions  @c --------------------------------------------------------------------
   @node C Code restrictions,  , C Code Macros, Simple instructions
   @subsection C Code restrictions
   
 Vmgen generates code and performs some optimizations under the  Vmgen generates code and performs some optimizations under the
 assumption that the user-supplied C code does not access the stack  assumption that the user-supplied C code does not access the stack
Line 625  macros can be implemented in several way Line 807  macros can be implemented in several way
 contents.  contents.
   
   
   @c --------------------------------------------------------------------
   @node Superinstructions,  , Simple instructions, Input File Format
 @section Superinstructions  @section Superinstructions
   
   Note: don't invest too much work in (static) superinstructions; a future
   version of vmgen will support dynamic superinstructions (see Ian
   Piumarta and Fabio Riccardi, @cite{Optimizing Direct Threaded Code by
   Selective Inlining}, PLDI'98), and static superinstructions have much
   less benefit in that context.
   
 Here is an example of a superinstruction definition:  Here is an example of a superinstruction definition:
   
 @example  @example
Line 673  not be used as component at all.  Vmgen Line 863  not be used as component at all.  Vmgen
 restrictions, they just result in bugs in your interpreter.  restrictions, they just result in bugs in your interpreter.
   
 @c ********************************************************************  @c ********************************************************************
   @node Using the generated code, Changes, Input File Format, Top
 @chapter Using the generated code  @chapter Using the generated code
   
 The easiest way to create a working VM interpreter with vmgen is  The easiest way to create a working VM interpreter with vmgen is
 probably to start with one of the examples, and modify it for your  probably to start with one of the examples, and modify it for your
 purposes.  This chapter is just the reference manual for the macros  purposes.  This chapter is just the reference manual for the macros
 etc. used by the generated code, and the other context expected by the  etc. used by the generated code, the other context expected by the
 generated code, and what you can do with the various generated files.  generated code, and what you can do with the various generated files.
   
   @menu
   * VM engine::                   Executing VM code
   * VM instruction table::        
   * VM code generation::          Creating VM code (in the front-end)
   * Peephole optimization::       Creating VM superinstructions
   * VM disassembler::             for debugging the front end
   * VM profiler::                 for finding worthwhile superinstructions
   @end menu
   
   @c --------------------------------------------------------------------
   @node VM engine, VM instruction table, Using the generated code, Using the generated code
 @section VM engine  @section VM engine
   
 The VM engine is the VM interpreter that executes the VM code.  It is  The VM engine is the VM interpreter that executes the VM code.  It is
 essential for an interpretive system.  essential for an interpretive system.
   
 The main file generated for the VM interpreter is  Vmgen supports two methods of VM instruction dispatch: @emph{threaded
 @file{@var{name}-vm.i}.  It uses the following macros and variables (and  code} (fast, but gcc-specific), and @emph{switch dispatch} (slow, but
 you have to define them):  portable across C compilers); you can use conditional compilation
   (@samp{defined(__GNUC__)}) to choose between these methods, and our
   example does so.
   
   For both methods, the VM engine is contained in a C-level function.
   Vmgen generates most of the contents of the function for you
   (@file{@var{name}-vm.i}), but you have to define this function, and
   macros and variables used in the engine, and initialize the variables.
   In our example the engine function also includes
   @file{@var{name}-labels.i} (@pxref{VM instruction table}).
   
   The following macros and variables are used in @file{@var{name}-vm.i}:
   
 @table @code  @table @code
   
Line 700  threaded-code dispatch this should just Line 913  threaded-code dispatch this should just
 @var{label}}.  In either case @var{label} is usually the @var{inst_name}  @var{label}}.  In either case @var{label} is usually the @var{inst_name}
 with some prefix or suffix to avoid naming conflicts.  with some prefix or suffix to avoid naming conflicts.
   
   @item LABEL2(@var{inst_name})
   This will be used for dynamic superinstructions; at the moment, this
   should expand to nothing.
   
 @item NAME(@var{inst_name_string})  @item NAME(@var{inst_name_string})
 Called on entering a VM instruction with a string containing the name of  Called on entering a VM instruction with a string containing the name of
 the VM instruction as parameter.  In normal execution this should be a  the VM instruction as parameter.  In normal execution this should be a
Line 738  extreme variant is to pull code up even Line 955  extreme variant is to pull code up even
 the previous VM instruction (prefetching, useful on PowerPCs).  the previous VM instruction (prefetching, useful on PowerPCs).
   
 @item INC_IP(@var{n})  @item INC_IP(@var{n})
 This increments IP by @var{n}.  This increments @code{IP} by @var{n}.
   
   @item SET_IP(@var{target})
   This sets @code{IP} to @var{target}.
   
 @item vm_@var{A}2@var{B}(a,b)  @item vm_@var{A}2@var{B}(a,b)
 Type casting macro that assigns @samp{a} (of type @var{A}) to @samp{b}  Type casting macro that assigns @samp{a} (of type @var{A}) to @samp{b}
Line 788  Macro for executing @var{expr}, if top-o Line 1008  Macro for executing @var{expr}, if top-o
 top-of-stack caching for @var{stackpointer}; otherwise it should do  top-of-stack caching for @var{stackpointer}; otherwise it should do
 nothing.  nothing.
   
   @item SUPER_END
   This is used by the VM profiler (@pxref{VM profiler}); it should not do
   anything in normal operation, and call @code{vm_count_block(IP)} for
   profiling.
   
   @item SUPER_CONTINUE
   This is just a hint to vmgen and does nothing at the C level.
   
 @item VM_DEBUG  @item VM_DEBUG
 If this is defined, the tracing code will be compiled in (slower  If this is defined, the tracing code will be compiled in (slower
 interpretation, but better debugging).  Our example compiles two  interpretation, but better debugging).  Our example compiles two
Line 813  basic type of the stack. Line 1041  basic type of the stack.
   
 @end table  @end table
   
 The file @file{@var{name}-labels.i} is used for enumerating or listing  
 all virtual machine instructions and uses the following macro:  @c --------------------------------------------------------------------
   @node VM instruction table, VM code generation, VM engine, Using the generated code
   @section VM instruction table
   
   For threaded code we also need to produce a table containing the labels
   of all VM instructions.  This is needed for VM code generation
   (@pxref{VM code generation}), and it has to be done in the engine
   function, because the labels are not visible outside.  It then has to be
   passed outside the function (and assigned to @samp{vm_prim}), to be used
   by the VM code generation functions.
   
   This means that the engine function has to be called first to produce
   the VM instruction table, and later, after generating VM code, it has to
   be called again to execute the generated VM code (yes, this is ugly).
   In our example program, these two modes of calling the engine function
   are differentiated by the value of the parameter ip0 (if it equals 0,
   then the table is passed out, otherwise the VM code is executed); in our
   example, we pass the table out by assigning it to @samp{vm_prim} and
   returning from @samp{engine}.
   
   In our example, we also build such a table for switch dispatch; this is
   mainly done for uniformity.
   
   For switch dispatch, we also need to define the VM instruction opcodes
   used as case labels in an @code{enum}.
   
   For both purposes (VM instruction table, and enum), the file
   @file{@var{name}-labels.i} is generated by vmgen.  You have to define
   the following macro used in this file:
   
 @table @samp  @table @samp
   
 @item INST_ADDR(@var{inst_name})  @item INST_ADDR(@var{inst_name})
 For switch dispatch, this is just the name of the switch label (the same  For switch dispatch, this is just the name of the switch label (the same
 name as used in @samp{LABEL(@var{inst_name})}).  For threaded-code  name as used in @samp{LABEL(@var{inst_name})}), for both uses of
 dispatch, this is the address of the label defined in  @file{@var{name}-labels.i}.  For threaded-code dispatch, this is the
 @samp{LABEL(@var{inst_name})}); the address is taken with @samp{&&}  address of the label defined in @samp{LABEL(@var{inst_name})}); the
 (@pxref{labels-as-values}).  address is taken with @samp{&&} (@pxref{labels-as-values}).
   
   @end table
   
   
   @c --------------------------------------------------------------------
   @node VM code generation, Peephole optimization, VM instruction table, Using the generated code
   @section VM code generation
   
   Vmgen generates VM code generation functions in @file{@var{name}-gen.i}
   that the front end can call to generate VM code.  This is essential for
   an interpretive system.
   
   For a VM instruction @samp{x ( #a b #c -- d )}, vmgen generates a
   function with the prototype
   
   @example
   void gen_x(Inst **ctp, a_type a, c_type c)
   @end example
   
   The @code{ctp} argument points to a pointer to the next instruction.
   @code{*ctp} is increased by the generation functions; i.e., you should
   allocate memory for the code to be generated beforehand, and start with
   *ctp set at the start of this memory area.  Before running out of
   memory, allocate a new area, and generate a VM-level jump to the new
   area (this is not implemented in our examples).
   
   The other arguments correspond to the immediate arguments of the VM
   instruction (with their appropriate types as defined in the
   @code{type_prefix} declaration.
   
   The following types, variables, and functions are used in
   @file{@var{name}-gen.i}:
   
   @table @samp
   
   @item Inst
   The type of the VM instruction; if you use threaded code, this is
   @code{void *}; for switch dispatch this is an integer type.
   
   @item vm_prim
   The VM instruction table (type: @code{Inst *}, @pxref{VM instruction table}).
   
   @item gen_inst(Inst **ctp, Inst i)
   This function compiles the instruction @code{i}.  Take a look at it in
   @file{vmgen-ex/peephole.c}.  It is trivial when you don't want to use
   superinstructions (just the last two lines of the example function), and
   slightly more complicated in the example due to its ability to use
   superinstructions (@pxref{Peephole optimization}).
   
   @item genarg_@var{type_prefix}(Inst **ctp, @var{type} @var{type_prefix})
   This compiles an immediate argument of @var{type} (as defined in a
   @code{type-prefix} definition).  These functions are trivial to define
   (see @file{vmgen-ex/support.c}).  You need one of these functions for
   every type that you use as immediate argument.
   
   @end table
   
   In addition to using these functions to generate code, you should call
   @code{BB_BOUNDARY} at every basic block entry point if you ever want to
   use superinstructions (or if you want to use the profiling supported by
   vmgen; however, this is mainly useful for selecting superinstructions).
   If you use @code{BB_BOUNDARY}, you should also define it (take a look at
   its definition in @file{vmgen-ex/mini.y}).
   
   You do not need to call @code{BB_BOUNDARY} after branches, because you
   will not define superinstructions that contain branches in the middle
   (and if you did, and it would work, there would be no reason to end the
   superinstruction at the branch), and because the branches announce
   themselves to the profiler.
   
   
   @c --------------------------------------------------------------------
   @node Peephole optimization, VM disassembler, VM code generation, Using the generated code
   @section Peephole optimization
   
   You need peephole optimization only if you want to use
   superinstructions.  But having the code for it does not hurt much if you
   do not use superinstructions.
   
   A simple greedy peephole optimization algorithm is used for
   superinstruction selection: every time @code{gen_inst} compiles a VM
   instruction, it looks if it can combine it with the last VM instruction
   (which may also be a superinstruction resulting from a previous peephole
   optimization); if so, it changes the last instruction to the combined
   instruction instead of laying down @code{i} at the current @samp{*ctp}.
   
   The code for peephole optimization is in @file{vmgen-ex/peephole.c}.
   You can use this file almost verbatim.  Vmgen generates
   @file{@var{file}-peephole.i} which contains data for the peephoile
   optimizer.
   
   You have to call @samp{init_peeptable()} after initializing
   @samp{vm_prim}, and before compiling any VM code to initialize data
   structures for peephole optimization.  After that, compiling with the VM
   code generation functions will automatically combine VM instructions
   into superinstructions.  Since you do not want to combine instructions
   across VM branch targets (otherwise there will not be a proper VM
   instruction to branch to), you have to call @code{BB_BOUNDARY}
   (@pxref{VM code generation}) at branch targets.
   
   
   @c --------------------------------------------------------------------
   @node VM disassembler, VM profiler, Peephole optimization, Using the generated code
   @section VM disassembler
   
   A VM code disassembler is optional for an interpretive system, but
   highly recommended during its development and maintenance, because it is
   very useful for detecting bugs in the front end (and for distinguishing
   them from VM interpreter bugs).
   
   Vmgen supports VM code disassembling by generating
   @file{@var{file}-disasm.i}.  This code has to be wrapped into a
   function, as is done in @file{vmgen-ex/disasm.i}.  You can use this file
   almost verbatim.  In addition to @samp{vm_@var{A}2@var{B}(a,b)},
   @samp{vm_out}, @samp{printarg_@var{type}(@var{value})}, which are
   explained above, the following macros and variables are used in
   @file{@var{file}-disasm.i} (and you have to define them):
   
   @table @samp
   
   @item ip
   This variable points to the opcode of the current VM instruction.
   
   @item IP IPTOS
   @samp{IPTOS} is the first argument of the current VM instruction, and
   @samp{IP} points to it; this is just as in the engine, but here
   @samp{ip} points to the opcode of the VM instruction (in contrast to the
   engine, where @samp{ip} points to the next cell, or even one further).
   
   @item VM_IS_INST(Inst i, int n)
   Tests if the opcode @samp{i} is the same as the @samp{n}th entry in the
   VM instruction table.
   
 @end table  @end table
   
   
   @c --------------------------------------------------------------------
   @node VM profiler,  , VM disassembler, Using the generated code
   @section VM profiler
   
   The VM profiler is designed for getting execution and occurence counts
   for VM instruction sequences, and these counts can then be used for
   selecting sequences as superinstructions.  The VM profiler is probably
   not useful as profiling tool for the interpretive system.  I.e., the VM
   profiler is useful for the developers, but not the users of the
   interpretive system.
   
   The output of the profiler is: for each basic block (executed at least
   once), it produces the dynamic execution count of that basic block and
   all its subsequences; e.g.,
   
   @example
          9227465  lit storelocal 
          9227465  storelocal branch 
          9227465  lit storelocal branch 
   @end example
   
   I.e., a basic block consisting of @samp{lit storelocal branch} is
   executed 9227465 times.
   
   This output can be combined in various ways.  E.g.,
   @file{vmgen/stat.awk} adds up the occurences of a given sequence wrt
   dynamic execution, static occurence, and per-program occurence.  E.g.,
   
   @example
         2      16        36910041 loadlocal lit 
   @end example
   
   indicates that the sequence @samp{loadlocal lit} occurs in 2 programs,
   in 16 places, and has been executed 36910041 times.  Now you can select
   superinstructions in any way you like (note that compile time and space
   typically limit the number of superinstructions to 100--1000).  After
   you have done that, @file{vmgen/seq2rule.awk} turns lines of the form
   above into rules for inclusion in a vmgen input file.  Note that this
   script does not ensure that all prefixes are defined, so you have to do
   that in other ways.  So, an overall script for turning profiles into
   superinstructions can look like this:
   
   @example
   awk -f stat.awk fib.prof test.prof|
   awk '$3>=10000'|                #select sequences
   fgrep -v -f peephole-blacklist| #eliminate wrong instructions
   awk -f seq2rule.awk|            #turn into superinstructions
   sort -k 3 >mini-super.vmg       #sort sequences
   @end example
   
   Here the dynamic count is used for selecting sequences (preliminary
   results indicate that the static count gives better results, though);
   the third line eliminats sequences containing instructions that must not
   occur in a superinstruction, because they access a stack directly.  The
   dynamic count selection ensures that all subsequences (including
   prefixes) of longer sequences occur (because subsequences have at least
   the same count as the longer sequences); the sort in the last line
   ensures that longer superinstructions occur after their prefixes.
   
   But before using it, you have to have the profiler.  Vmgen supports its
   creation by generating @file{@var{file}-profile.i}; you also need the
   wrapper file @file{vmgen-ex/profile.c} that you can use almost verbatim.
   
   The profiler works by recording the targets of all VM control flow
   changes (through @code{SUPER_END} during execution, and through
   @code{BB_BOUNDARY} in the front end), and counting (through
   @code{SUPER_END}) how often they were targeted.  After the program run,
   the numbers are corrected such that each VM basic block has the correct
   count (originally entering a block without executing a branch does not
   increase the count), then the subsequences of all basic blocks are
   printed.  To get all this, you just have to define @code{SUPER_END} (and
   @code{BB_BOUNDARY}) appropriately, and call @code{vm_print_profile(FILE
   *file)} when you want to output the profile on @code{file}.
   
   The @file{@var{file}-profile.i} is simular to the disassembler file, and
   it uses variables and functions defined in @file{vmgen-ex/profile.c},
   plus @code{VM_IS_INST} already defined for the VM disassembler
   (@pxref{VM disassembler}).
   
   
   @c **********************************************************
   @node Changes, Contact, Using the generated code, Top
   @chapter Changes
   
   Users of the gforth-0.5.9-20010501 version of vmgen need to change
   several things in their source code to use the current version.  I
   recommend keeping the gforth-0.5.9-20010501 version until you have
   completed the change (note that you can have several versions of Gforth
   installed at the same time).  I hope to avoid such incompatible changes
   in the future.
   
   The required changes are:
   
   @table @code
   
   @item vm_@var{A}2@var{B}
   now takes two arguments.
   
   @item vm_two@var{A}2@var{B}(b,a1,a2);
   changed to vm_two@var{A}2@var{B}(a1,a2,b) (note the absence of the @samp{;}).
   
   @end table
   
 @section Stacks, types, and prefixes  Also some new macros have to be defined, e.g., @code{INST_ADDR}, and
   @code{LABEL}; some macros have to be defined in new contexts, e.g.,
   @code{VM_IS_INST} is now also needed in the disassembler.
   
   @node Contact, Copying This Manual, Changes, Top
   @chapter Contact
   
   @node Copying This Manual, Index, Contact, Top
   @appendix Copying This Manual
   
 Invocation  @menu
   * GNU Free Documentation License::  License for copying this manual.
   @end menu
   
 Input Syntax  @include fdl.texi
   
 Concepts: Front end, VM, Stacks,  Types, input stream  
   
 Contact  @node Index,  , Copying This Manual, Top
   @unnumbered Index
   
   @printindex cp
   
 Required changes:  @bye
 vm_...2... -> two arguments  
 "vm_two...2...(arg1,arg2,arg3);" -> "vm_two...2...(arg3,arg1,arg2)" (no ";").  
 define INST_ADDR and LABEL  
 define VM_IS_INST also for disassembler  

Removed from v.1.5  
changed lines
  Added in v.1.10


FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>