Important Notice
The pages on this site contain documentation for very old MS-DOS software,
purely for historical purposes.
If you're looking for up-to-date documentation, particularly for programming,
you should not rely on the information found here, as it will be woefully
out of date.
INLINE Keyword
◄Keywords► ◄Contents► ◄Index► ◄Back►
INLINE( <element list> )
Description
The INLINE keyword initiates a sequence of machine code. This is
convenient for optimizing code or handling tasks that cannot be
done in Pascal. The INLINE keyword can be used in two different
contexts:
■ INLINE sequences of assembly-language code in the inline
format (described below) can be used inside normal functions
or procedures.
■ INLINE directives can be used to insert functions or
procedures in inline format directly into the instruction
stream. This feature is similar to assembly-language macros.
Each inline element can be either a constant representing part of
an encoded assembly-language instruction or a variable identifier.
Elements must be separated from each other by slashes.
Each constant element generates one byte of code if it is in the
8-bit range (0..255) or one word (least-significant byte first)
if it is in the 16-bit range. Variable identifiers in the data
segment generate the offset of the variable. Constant values may
be added or subtracted from the identifier to encode relative
offsets. Variable identifiers in the stack segment generate a word
offset from SS:BP.
In the following examples, assume that the hexadecimal offset of
DVar is 10C2 and that SVar is a word argument at SS:[BP+4]:
INLINE
( { Inline code Assembly code Hex Bytes Encoded }
$59/ { pop cx 59 }
$B8/$1A07/ { mov ax, 1A07h B8 07 1A }
$89/$16/DVar/ { mov DVar, dx 89 16 C2 10 }
$8B/$1E/DVar+2/ { mov bx, DVar 8B 1E C4 10 }
$FF/$86/SVar/ { inc WORD PTR [bp+4] FF 46 04 00 }
$CD/$10 { int 10h CD 10 }
);
Default size assumptions can be overridden with the (<) and (>)
operators. The (<) operator specifies a byte element; the (>)
operator specifies a word. For example, <$3C79 is encoded as $3C
and >$F2 is encoded as $F2, $00.
An inline sequence must preserve BP, SP, SS, and DS. Other
registers may be safely modified within the sequence.
The INLINE keyword can be applied to a procedure or function to
make it insert instructions directly into the instruction stream
without the normal entry and exit sequence. For example, the
following procedure generates one byte of code, an STI
instruction:
PROCEDURE Enable; INLINE( $FB { sti } );
INLINE functions and procedures can have arguments, but these
arguments cannot be accessed by name. The compiler pushes the
arguments onto the stack. They can be accessed by popping them
into registers in reverse order. Values returned by INLINE
functions must be returned in the normal registers (AX for 2-byte
values or DX:AX for four-byte values). For example,
FUNCTION Power2( Value : Word; Count : BYTE ) : WORD;
INLINE
(
$59/ { pop cx ; Load Value }
$58/ { pop ax ; Load Power }
$D3/$E0 { shl ax, cl ; Multiply by power of 2 }
);
This code could be written as a normal function as shown below:
FUNCTION Power2( Value : Word; Count : BYTE ) : WORD;
VAR
Ret : WORD;
BEGIN
INLINE
(
$8B/$86/Value/ { mov ax, Value ; Load Value }
$8A/$8E/Power/ { mov cl, Count ; Load Count }
$D3/$E0/ { shl ax, cl ; Multiply by power of 2 }
$89/$86/Ret { mov Reg, ax ; Put in Ret variable }
);
Power2 := Ret;
END;
Note that the first example generates less code and will thus be
faster, but the code is generated each time the function is used.
The second example generates more code, but the code appears only
once in the executable program regardless of how many times the
function is called. Because of the potential overhead involved,
INLINE functions and procedures should be short--normally less
than 10 bytes.
See also: EXTERNAL, {$L}