Have sign-extend-complex deal correctly with bytes of size 0.
[movitz-ia-x86.git] / README
bloba96fb7816f37b1714a8e28301ad0b293db789201
1 ######################################################################
2 ## 
3 ##    Copyright (C) 2003, 2005, 
4 ##    Department of Computer Science, University of Tromso, Norway.
5 ## 
6 ##    For distribution policy, see the accompanying file COPYING.
7 ## 
8 ## Filename:      README
9 ## Description:   Describes the ia-x86 package.
10 ## Author:        Frode Vatvedt Fjeld <frodef@acm.org>
11 ## Created at:    Sat Jan 29 16:48:42 2005
12 ##                
13 ## $Id: README,v 1.5 2005/01/31 22:58:48 ffjeld Exp $
14 ##                
15 ######################################################################
18                           The ia-x86 package
20 The ia-x86 package implements assembler and disassembler functionality
21 for 16 and 32-bit x86 code. It is primarily intended as a backend for
22 the Movitz compiler. The following documents the most interesting API
23 operators for this package.
25 A few terms requires explanation. A "program" is a representation of
26 an assembly program that is reasonably convenient to work with for
27 humans. This is a list, whose elements are either a symbol that
28 represents a label, or a list that represents an instruction.  The
29 format of these instructions is something like (:movl :eax (:ebx 1)),
30 which means "move EAX to the memory location pointed to by EBX offset
31 by 1" (more on this syntax below). However, instructions are also
32 represented internally ia-x86 by instances of the various subclasses
33 of the "instruction" standard-class, and lists of such objects are
34 referred to as "proglists".
37                                Assembly
39 The function read-proglist reads a program into proglist form, which
40 is typically the first step in producing machine code. This function
41 (and its helper functions, in read.lisp) defines the human-readable
42 syntax for assembly programs. This is an example program (or rather, a
43 lisp function that produces an assembly program):
45   (defun mkasm16-bios-print ()
46     "Print something to the terminal.  [es:si] points to the text"
47     `((:movzxb (:si) :cx)
48       (:incw :si)
49       (:movb #xe :ah)
50       (:movw 7 :bx)
51      print-loop
52       (:lodsb)
53       (:int #x10)
54       (:loop 'print-loop)
55       (:ret)))
57 I personally tend to use keywords for instruction names, although the
58 instructions are recognized by name rather than identity, so any
59 package will do. Labels, however, are recognized by identity. Label
60 references are on the form (quote <label>), so that the loop
61 instruction above will transfer control to the print-loop label two
62 instructions before it. Indirect memory references are writen by
63 placing the pointer inside parens, such as in the first movzxb above.
64 If the first element of an instructon is a list (rather than an
65 instruction name), this is interpreted as a list of instruction
66 prefixes (such as REP, LOCK, etc.).
68 This is a more-or-less exact description of the syntax:
70 ---------------------------------------------------------
72        program ::= (<sexpr>*)
74          sexpr ::= ( <expr> ) | <label> | (% <inline-data> %) | (:include . <program>)
75           expr ::= <instro> | ( { <prefix> } ) <instro>
76         instro ::= <instruction> { <operand> }
78        operand ::= <concrete> | <abstract>
80       concrete ::= <immediate> | <register> | <indirect>
81      immediate ::= <number>
82       register ::= eax | ecx | ...
83       indirect ::= ( iexpr )
84          iexpr ::=   <address>
85                    | (quote <label>)
86                    | <segment> <address> 
87                    | pc+ <offset>
88                    | pc  <address>
89                    | { (quote <label>) } <offset> <scaled-register> <register>
90      scaled-register ::= <register> | ( <register> <scale> )
91                scale ::= 1 | 2 | 4 | 8
92              address ::= <number>
93               offset ::= <signed-number>
95       abstract ::= (quote <absexpr>)
96        absexpr ::= <label> | <number> | append-prg
97     append-prg ::= program
99         prefix ::= <segment-override> | (:size <size>)
101 ---------------------------------------------------------
103 One of the original intentions of having proglists as the intermediate
104 representation of assembly programs, was to facilitate computational
105 reasoning about the program (hence the class hierarchy rooted at
106 "instruction").  I don't really know how well this idea worked out, I
107 suspect most people will just pass the proglists directly to
108 proglist-encode.
111 The function proglist-encode takes a proglist and produces
112 machine-code in the form of e.g. a vector of 8-bit bytes. A typical
113 usage would be this:
115   (proglist-encode :octet-vector :16-bit #x7c00
116                    (read-proglist (mkasm16-bios-print)))
118 The first agument, :octet-vector, requests that the result be in the
119 form of a vector of octets. The second argument says to prodce machine
120 code for the 16-bit mode of x86. Next is the address to assume the
121 code is located in memory (if the program is position-independent,
122 just pass zero). Finally, there is the proglist to be encoded to
123 machine code. Additionally, the keyword argument :symtab-lookup can
124 provide a function that proglist-encode will use to map (otherwise
125 undefined) labels to integers: The function should expect one symbol
126 argument and return a suitable integer. The primary return value is
127 the byte vector, while the secondary return value is an (assoc)
128 symbol-table:
130   IA-X86(7): (proglist-encode :octet-vector :16-bit #x7c00
131                               (read-proglist (mkasm16-bios-print)))
132   => #(#xf #xb6 #xc #x46 #xb4 #xe #xbb #x7 #x0 #xac ...)
133   => ((PRINT-LOOP . #x7c09))
136 Another operator that can be useful for interactive and experimental
137 use, is the macro "asm" which encodes a single instruction. This can
138 be used e.g. to verify syntax or the encoded size of an instruction:
140   IA-X86(8): (asm :movl :eax (:ebx 1))
141   => #c(#x894301 #x3)
143 The return value is a complex, whose real component is the
144 (big-endian) binary encoding of the instruction, and the imaginary
145 component is the number of bytes.
149                              Disassembly
151 [To be written.]