home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
PC World Komputer 1996 September
/
pcwk_09_96.iso
/
demo
/
elmark
/
cupl
/
manual
/
sb1.txt
< prev
next >
Wrap
Text File
|
1992-01-20
|
61KB
|
1,527 lines
.C1. CUPL LANGUAGE 1
This chapter explains CUPL language elements and CUPL language
syntax.
o .C2.LANGUAGE ELEMENTS
This section describes the elements that comprise the CUPL logic
description language.
o .C3.VARIABLES
Variables are strings of alphanumeric characters that specify device
pins, internal nodes, constants, input signals, output signals,
intermediate signals, or sets of signals. This section explains the
rules for creating variables.
Variables can start with a numeric digit, alphabet character, or
underscore, but must contain at least one alphabet character.
Variables are case sensitive; that is, they distinguish between
uppercase and lowercase letters.
Do not use spaces within a variable name. Use the underscore
character to separate words.
Variables can contain up to 31 characters. Longer variables are
truncated to 31 characters.
Variables cannot contain any of the CUPL reserved symbols (see Table
1-2). Variables cannot be the same as a CUPL reserved keyword (see
Table 1-1).
Examples of some VALID variable names are:
a0
A0
8250_ENABLE
Real_time_clock_interrupt
_address
Note how the use of the underscore in the above examples makes the
variable names easier to read. Also, note the difference between
uppercase and lowercase variable names. The variable A0 is not the
same as a0.
Examples of some INVALID variable names are:
99 does not contain an alpha character
I/O enable contains a special character (/)
out 6a contains a space; the system reads it as two
separate variables
tbl-2 contains a dash; the system reads it as two
variables.
o .C3.INDEXED VARIABLES
Variable names can be used to represent a group of address lines,
data lines, or other sequentially numbered items. For example, the
following variable names could be assigned to the eight LO-order
address lines of a microprocessor: A0 A1 A2 A3 A4 A5 A6 A7
Variable names that end in a number, as shown above, are
referred to as indexed variables.
==================================================
Note
It is best to start indexed variables from zero
(0).e.g. Use X0...4 instead of X1...5.
==================================================
The index numbers are always decimal numbers between 0 and 31. When
used in bit field operations (see the subtopic, Bit Field
Declaration Statements in this chapter) the variable with index
number 0 is always the lowest order bit.
==================================================
Note
Variables ending in numbers greater than 31 are
not indexed variables
==================================================
Examples of some valid indexed variable names are as follows:
a23
D07
D7
counter_bit_3
Note the difference between index variables with leading zeroes; the
variable D07 is not the same as D7.
Examples of some invalid indexed variable names are as follows:
D0F index number is not decimal
a36 index number out of range
These are valid variable names, but they are not
considered indexed.
o .C3.RESERVED WORDS AND SYMBOLS
CUPL uses certain character strings with predefined meanings called
keywords. These keywords cannot be used as names in CUPL. Table 1-1
lists these keywords.
Table 1-1. CUPL Reserved Keywords
--------------------------------------------------
APPEND ASSEMBLY ASSY
COMPANY CONDITION DATE
DEFAULT DESIGNER DEVICE
ELSE FIELD FLD
FORMAT FUNCTION FUSE
GROUP IF JUMP
LOC LOCATION MACRO
MIN NAME NODE
OUT PARTNO PIN
PINNNODE PRESENT REV
REVISION SEQUENCE SEQUENCED
SEQUENCEJK SEQUENCERS SEQUENCET
TABLE
--------------------------------------------------
CUPL also reserves certain symbols for its use that cannot be used
in variable names. Table 1-2 lists these reserved symbols.
Table 1-2. CUPL Reserved Symbols
----------------------------
& # ( )
- * + [
] / : .
.. /* */ ;
, ! ' =
@ $ ^
----------------------------
o .C3.NUMBERS
All operations involving numbers in the CUPL compiler are done with
32-bit accuracy. Therefore, the numbers may have a value from 0 to
232 -1. Numbers may be represented in any one of the four common
bases: binary, octal, decimal, or hexadecimal. The default base
for all numbers used in the source file is hexadecimal, except for
device pin numbers and indexed variables, which are always decimal.
Numbers for a different base may be used by preceding them with a
prefix listed in Table 1-3. Once a base change has occurred, that
new base is the default base.
Table 1-3. Number Base Prefixes Base
Name Base Prefix
Binary 2 'b'
Octal 8 'o'
Decimal 10 'd'
Hexadecimal 16 'h'
The base letter is enclosed in single quotes and can be either
uppercase or lowercase. Some examples of valid number specifications
are listed in Table 1-4.
Table 1-4 Sample Base Conversions
--------------------------------------------------
Number Base Decimal Value
'b'0 Binary 0
'B'1101 Binary 13
'O'663 Octal 435
'D'92 Decimal 92
'h'BA Hexadecimal 186
'O'[300..477] Octal (range) 192..314
--------------------------------------------------
Binary, octal, and hexadecimal numbers can have don't-care values
("X") and numerical values. Some examples of valid number
specifications with don't-care values are listed in Table 1-5.
Table 1-5. Sample Don't-Care Numbers
---------------------------------------
Number Base
'b'1X11 Binary
'O'0X6 Octal
'H'[3FXX..7FFF] Hexadecimal (range)
---------------------------------------
o .C3.COMMENTS
Comments are an important part of the logic description file. They
improve the readability of the code and document the intentions, but
do not significantly affect the compile time, as they are removed by
the preprocessor before any syntax checking is done. Use the symbols
/* and */ to enclose comments; the program ignores everything
between these symbols.
Comments may span multiple lines and are not terminated by the end
of a line. Comments cannot be nested. Some examples of valid
comments are shown in Figure 1-1.
-----------------------------------------------------------------
/*******************************************/
/* This is one way to create a title or */
/* an information block */
/*******************************************/
/*
This is another way to create an
information block
*/
out1=in1 # in2; /* A Simple OR Function */
out2=in1 & in2; /* A Simple AND Function */
out3=in1 $ in2; /* A Simple XOR Function */
-----------------------------------------------------------------
Figure 1-1. Sample Comments.i.comments:sample;
o .C3.LIST NOTATION
Shorthand notations are an important feature of the CUPL language.
The most frequently used shorthand notation is the list. It is
commonly used in pin and node declarations, bit field declarations,
logic equations, and set operations. The list format is as follows:
[variable, variable, ... variable]
where
[ ] are brackets used to delimit items in the list as a set of
variables.
Two examples of the list notation are as follows:
[UP, DOWN, LEFT, RIGHT]
[A0, A1, A2, A3, A4, A5, A6, A7]
When all the variable names are sequentially numbered, either
from lowest to highest or vice versa, the following format
may be used:
[variablem..n]
where
m is the first index number in the list of variables.
n is the last number in the list of variables; n can be written
without the variable name.
For example, the second line from the example above could be written
as follows:
[A0..7]
Index numbers are assumed to be decimal and contiguous. Any leading
zeros in the variable index are removed from the variable name that
is created. For example:
[A00..07]
is shorthand for:
[A0, A1, A2, A3, A4, A5, A6, A7]
not for:
[A00, A01, A02, A03, A04, A05, A06, A07]
The two forms for the list notation may be mixed in any combination.
For example, the following two list notations are equivalent:
[A0..2, A3, A4, A5..7]
[A0, A1, A2, A3, A4, A5, A6, A7]
o .C3.TEMPLATE FILE
When a logic description source file is created using the CUPL
language, certain information must be entered, such as header
information, pin declarations, and logic equations. For assistance,
CUPL provides a template file that contains the proper structure for
the source file.
Figure 1-2 shows the contents of the template file.
-----------------------------------------------------------------
Name XXXXX;
Partno XXXXX;
Date XX/XX/XX;
Revision XX;
Designer XXXXX;
Company XXXXX;
Assembly XXXXX;
Location XXXXX;
/*************************************************************/
/* place description of design here */
/*************************************************************/
/* Allowable Target Device Types: */
/*************************************************************/
/** Inputs **/
Pin = ; /* */
Pin = ; /* */
Pin = ; /* */
Pin = ; /* */
/** Outputs **/
Pin = ; /* */
Pin = ; /* */
Pin = ; /* */
Pin = ; /* */
/** Declarations and Intermediate Variable Definitions **/
/** Logic Equations **/
-----------------------------------------------------------------
Figure 1-2. Template File
The template file provides the following sections:
Header Information - Keywords followed by XXXs that are replaced
with text to identify the file for archival and revision purposes.
Title Block - Comment symbols that enclose space for describing the
function of the design and allowable target devices.
Pin Declaration - Keywords and operators in the proper format for
input and output pin declarations and comment space to describe the
pin assignments. After pin declarations are made, remove any extra
"pin = ;" lines. Otherwise, a syntax error will occur during
compilation. The /* Inputs */ and /* Outputs */ are comments that
provide groupings for readability only. Assign any pin type in any
order, no matter how it is used in the logic description file.
Declaration and Intermediate Variable - Space for making
declarations, such as bit field declarations (see the subtopics, Bit
Field Declaration Statements and Node Declaration Statements in this
chapter) and for writing intermediate equations (see the subtopic,
Logic Equations in this chapter).
Logic Equation - Space for writing logic equations describing the
function of the device (see the subtopic, Logic Equations in this
chapter).
.C4.HEADER INFORMATION
The header information section of the source file identifies the
file for revision and archival purposes. Normally place it at the
beginning of the file. CUPL provides 10 keywords to use in header
information statements. Begin each statement with a keyword which
can be followed by any valid ASCII characters, including spaces and
special characters. End each statement with a semicolon. Table 1-6
lists the CUPL header keywords and the information to provide with
each keyword.
Table 1-6. Header Information Keywords
Keyword Information
NAME Normally use the source logic description
filename. Use only character strings that are
valid for the operating system. The name
specified here determines the name for any JEDEC,
ASCII - hex, or HL download files. The NAME field
accommodate s filenames up to 32 characters long.
When using systems such as DOS which allow
filenames of only eight characters, the filename
will be truncated.
PARTNO Specify a company's proprietary part number
(usually issued by manufacturi ng) for a
particular PLD design. The part number is not
the type of target PLD.
For GAL devices, the first eight characters are
encoded using seven-bit ASCII in the User
Signature Fuses of the devices' fuse map.
REVISION Begin with 01 when first creating a file and
increment each time a file is altered. REV can be
used for an abbreviatio n.
DATE Change to the current date each time a source
file is altered.
DESIGNER Specify the designer's name.
COMPANY Specify the company's name for proper
documentation practice and because specifications
may be sent to semiconduct or manufacturers for
high volume PLD orders.
ASSEMBLY Give the assembly name or number of the PC
board on which the PLD will be used. The
abbreviatio n ASSY can be used.
LOCATION Indicate the PC board reference or coordinate
where the PLD is located. The abbreviatio n
LOC can be used.
DEVICE Set the default device type for the
compilation. A device type specified on the
command line overrides all device types set in
the source file. For multi-device source
files, DEVICE must be used with each section
if the device types are different.
FORMAT Set a download output format override for the
current logic description section. The valid
values to use for the output format are: h
produce ASCII-hex output i produce Signetics HL
output j produce JEDEC output
FORMAT overrides any option flag on the command
line. It is useful in multi-devic e source
files where different parts have incompatibl e
output formats. More than one format value at a
time may be specified to produce more than one
type of output. The format value must be a
lowercase letter.
The template file provides all the header keywords except DEVICE and
FORMAT. An example of proper CUPL header information is as follows:
Name WAITGEN;
Partno P9000183;
Revision 02;
Date 1/11/89;
Designer Osann;
Company Logical Devices, Inc. ;
Assembly PC Memory Board ;
Location U106 ;
Device F155;
Format ij ;
If any header information is omitted, CUPL issues a
warning message, but continues with compilation.
.c4.Pin Declaration Statements
Pin declaration statements declare the pin numbers and assign them
symbolic variable names. The format for a pin declaration is as
follows:
PIN pin_n=[!]var ;
where
PIN is a keyword to declare the pin numbers and assign them variable
names.
pin_n is a decimal pin number or a list of pin numbers grouped using
the list notation; that is,
[pin_n 1, pin_n 2 ... pin_nn]
! is an optional exclamation point to define the polarity of the
input or output signal.
= is the assignment operator.
var is a single variable name or a list of variables grouped using
the list notation; that is,
[var, var ... var]
; is a semicolon to mark the end of the pin declaration statement.
The template file provides a section for entering the pin variables
individually or in groups using the list notation.
The concept of polarity can often be a confusing one. In any PLD
design, the designer is primarily concerned with whether a signal is
true or false. The designer should not have to care whether this
means that the signal is high or low. For a variety of reasons a
board design may require a signal to be considered true when it is
logic level 0(low) and false when it is logic 1(high). This signal
is considered active-low since it is activated when it is low. This
might also be called low-true. If a signal is changed from
active-high to active low then the polarity has been changed.
For this reason, CUPL allows you to declare signal polarity in the
pin definition and then you do not have to be concerned with it
again. When writing equations in CUPL syntax, the designer should
not be concerned with the polarity of the signal. The pin
declarations declare a translation that will handle the signal
polarity.
Suppose that we wanted the following function.
Y = A & B;
What this statement means is that Y will be true when A is true and
B is true. We can implement this in a P22V10 device very easily.
Pin 2 = A;
Pin 3 = B;
Pin 16 = Y;
Y = A & B;
When the device is plugged into a circuit, if a logic 1 is
asserted at pins 2 and 3 then the signal at pin 16 will be high.
Let us assume that for some reason we wanted the inputs to read
logic 0 as true. We could modify the design to behave this way.
Pin 2 = !A;
Pin 3 = !B;
Pin 16 = Y;
Y = A & B;
Now even though the ! symbol was placed in the pin declaration to
indicate the inverted polarity, the equation still reads as "Y is
true when A is true and B is true". All that has been changed is the
translation of true=0 and false=1. So at the design level nothing
has changed but in the pin declarations we now map 0 to true and 1
to false. This promotes the designer to separate the design into
layers so as to minimize confusion related to polarity. It is
important also that CUPL will modify the feedback signal so that the
true/false layer is maintained.
[Picture]
Figure 1-3. Relationship Between Pin Declaration and Signal
Polarity
Use the exclamation point (!) to define the polarity of an input or
output signal. If an input signal is active-level LO (that is, the
asserted TTL signal voltage level is 0 volts), put an exclamation
point before the variable name in the pin declaration. The
exclamation point informs the compiler to choose the inverted sense
of the signal when it is listed as active in the logic equations.
The virtual device is an exception to this rule, however. When using
the virtual device, CUPL ignores the polarity in the pin
declaration. In this case, the equation itself must be negated.
Similarly, if an output signal is active-level LO, define the
variable with an exclamation point in the pin declaration and write
the logic equation in a logically true form. Use of the exclamation
point permits declaring pins without regard to the limitations of
the type of target device. With the virtual device, the equation
itself must be inverted, since the compiler ignores the polarity in
the pin declaration.
If a pin declaration specifying an active-level HI output is
compiled for a target device (such as a PAL16L8) that has only
inverting outputs, CUPL automatically performs DeMorgan's Theorem on
the logic equation to fit the function into the device. Consider
the following example. The logic description file is written for a
PAL16L8 device. All output pins are declared as active-HI. The
following equation has been written to specify an OR function:
c = a # b ;
However, because the PAL16L8 contains a fixed inverting buffer on
the output pins, CUPL must perform DeMorganization to fit the logic
to the device. CUPL generates the following product term in the
documentation file (see Documentation File Formats in Appendix C):
c => ! a & ! b
Figure 1-4 shows the process described above.
[Picture]
Figure 1-4. Active-HI Pin Declaration for Inverting Buffer
If a design has excessive product terms, CUPL displays an error
message and the compilation stops. The documentation file
(filename.DOC) lists the number of product terms required to
implement the logic function and the number of product terms the
device physically has for the particular output pin. Some examples
of valid pin declarations are:
pin 1 = clock; /* Register Clock */
pin 2 = !enable; /* Enable I/O Port */
pin [3,4] = ![stop,go]; /* Control Signals */
pin [5..7] = [a0..2]; /* Address Bits 0-2 */
The last two lines in the example above are shorthand notations for
the following:
pin 3 = !stop; /* Control Signal */
pin 4 = !go; /* Control Signal */
pin 5 = a0; /* Address Bit 0 */
pin 6 = a1; /* Address Bit 1 */
pin 7 = a2; /* Address Bit 2 */
For the virtual device, the pin numbers may be left out. This
provides a way to do a design without regard for any device related
restrictions. The designer can then examine the results and thereby
determine the requirements for implementation. The target device
can then be chosen. The following are valid pin declarations when
using the virtual device.
pin = !stop; /* Control Signal */
pin = !go; /* Control Signal */
pin = a0; /* Address Bit 0 */
pin = a1; /* Address Bit 1 */
pin = a2; /* Address Bit 2 */
The input, output, or bi-directional nature of a device pin is not
specified in the pin declaration. The compiler infers the nature of
a pin from the way the pin variable name is used in the logic
specification. If the logic specification and the physical
characteristics of the target device are incompatible, CUPL displays
an error message denoting the improper use of the pin.
.c4.Node Declaration Statements
Some devices contain functions that are not available on external
pins, but logic equations must be written for these capabilities.
For example, the 82S105 contains both buried state registers
(flip-flops) and a mechanism for inverting any transition term
through a complement array. Before writing equations for these
flip-flops (or complement arrays), they must be assigned variable
names. Since there are no pins associated with these functions, the
PIN keyword cannot be used. Use the NODE keyword to declare
variable names for buried functions. The format for node
declarations is as follows:
NODE [!] var ;
NODE is a keyword to declare a variable name for a buried
function.
! is an optional exclamation point to define the polarity of the
internal signal.
var is a single variable name or list of variables grouped using
the list notation.
; is a semicolon to mark the end of the statement.
Place node declarations in the "Declarations and Intermediate
Variables Definitions" section of the source file provided by the
template file. Most internal nodes are active-level HI, therefore,
the exclamation point should not be used to define the polarity of
an internal signal as active-level LO. Using the exclamation point
almost always causes the compiler to generate a significantly
greater number of product terms. An exception is the complement
array node, which, by definition, is an active-level LO signal.
Although no pin numbers are given in the declaration statement, CUPL
assigns the variable name to an internal pseudo-pin number. These
numbers begin with lowest possible number and are sequentially
defined even if a node was assigned with the PINNODE statement. The
assignment is automatic and determined by usage (flip-flop,
complement array, and so on), so variable order is not a concern.
However, once a node variable is declared, a logic equation must be
created for the variable, or a compilation error results.
CUPL uses the node declaration to distinguish between a logic
equation for a buried function and an intermediate expression.
Examples of the use
of the NODE keyword
are:
NODE [State0..5]; /* Internal State Bit */
NODE !Invert; /* For Complement Array */
An alternative for assigning buried functions instead of allowing
CUPL to automatically assign them via the NODE keyword, is to use
the PINNODE keyword. The PINNODE keyword is used for explicitly
defining buried nodes by assigning a node number to a symbolic
variable name. This is similar to the way the pin declaration
statements work. The format for a pinnode declaration is as
follows:
PINNODE node_n = [!]var;
where
PINNODE is a keyword to declare the node numbers and assign them
variable names. node_n is a decimal node number or a list of
node numbers grouped using the list notation; that is,
[node_n1,node_n2 ... node_nn]
! is an optional exclamation point to define the polarity of the
internal signal.
= is the assignment operator.
var is a single variable name or list of variables grouped using
the list notation; that is,
[var,var ... var]
; is a semicolon used to mark the end of the statement.
Place pinnode declarations in the "Declarations and Intermediate
Variables Definitions" section of the source file provided by the
template file. As with node declarations, most internal nodes are
active-level HI; therefore, the exclamation point should not be used
to define the polarity of an internal signal as active level LO.
Using the exclamation point almost always causes the compiler to
generate a significantly greater number of product terms. An
exception is the complement array node, which by definition is an
active-level LO signal. A list of node numbers for all devices
containing internal nodes is included in Appendix D. Please
reference these node numbers for pinnode declarations.
Examples of the use of the PINNODE keyword are:
PINNODE [29..34] = [State0..5]; /* Internal State Bits */
PINNODE 35 = !Invert; /* For Complement Array */
PINNODE 25 = Buried; /* For Buried register part */
/* of an I/O macrocell with */
/* multiple feedback paths */
.c4.Bit Field Declaration Statements
A bit field declaration assigns a single variable name to a group of
bits. The format is as follows:
FIELD var = [var, var, ... var] ;
where
FIELD is a keyword. var is any valid variable name.
[var, var, ... var] is a list of variable
names in list notation.
= is the assignment operator.
; is a semicolon used to mark the end of
the statement.
Note
==================================================
The square brackets do not indicate optional
items. They are used to delimit items in a list.
==================================================
Place bit field declarations in the "Declarations and Intermediate
Variable Definitions" section of the source file provided by the
template file. After assigning a variable name to a group of bits,
the name can be used in an expression; the operation specified in
the expression is applied to each bit in the group. See the
subtopic, Set Operations in this chapter for a description of the
operations allowed for FIELD statements. The example below shows
two ways to reference the eight address input bits (A0 through A7)
of an I/O decoder as the single variable named ADDRESS.
FIELD ADDRESS = [A7,A6,A5,A4,A3,A2,A1,A0] ;
or
FIELD ADDRESS = [A7..0] ;
When a FIELD statement is used, the compiler generates a single
32-bit field internally. This is used to represent the variables in
the bit field. Each bit represents one member of the bit field. The
bit number which represents a member of a bit field is the same as
the index number if indexed variables are used. This means that A0
will always occupy bit 0 in the bitfield. This also means that the
order of appearance of indexed variables in a bit field has no
significance. A bit field declared as [A0..7] is exactly the same
as a bit field declared as [A7..0]. Because of this mechanism,
different indexed variables should not be included in the same bit
field. A bit field containing A2 and B2 will assign both of these
variables to the same bit position. This will result in the
generation of erroneous equations. Also, bit fields should never
contain both indexed and non-indexed variables. This will almost
certainly result in erroneous generation of equations.
Note
==================================================
Do not mix indexed and non-indexed variables in a
field statement. The compiler may produce
unexpected results.
==================================================
.c4.MIN Declaration Statements
The MIN declaration statement overrides, for specified variables,
the minimization level specified on the command line when running
CUPL. The format is as follows:
MIN var [.ext] = level ;
where
MIN is a keyword to override the command line minimization
level.
var is a single variable declared in the file or a list of
variables grouped using the list notation; that is,
[var, var, ... var]
.ext is an optional extension that identifies the function of
the variable.
level is an integer between 0 and 4.
; is a semicolon to mark the end of the statement.
The levels 0 to 4 correspond to the option flags on the command
line, -m0 through -m4. The MIN declaration permits specifying
different levels for different outputs in the same design, such as
no reduction for outputs requiring redundant or contained product
terms (to avoid asynchronous hazard conditions), and maximum
reduction for a state machine application. The following are
examples of valid MIN declarations.
MIN async_out = 0; /* no reduction */
MIN [outa, outb] = 2; /* level 2 reduction */
MIN count.d = 4; /* level 4 reduction */
Note that the last declaration in the example above uses the .d
extension to specify that the registered output variable is the one
to be reduced.
.c4.FUSE Statement
The FUSE statement provides for special cases where it is necessary
to blow TURBO or MISER bits. This statement should be used with
utmost care, as it can lead to unpredictable results if used
incorrectly.
FUSE (fusenumber, x)
where
fusenumber is the fuse number corresponding to the MISER Bit or
TURBO Bit that must be blown, and x is either 0 or 1. Specify 0 if
the bit must not be blown. Specify 1 to blow the bit. Use this
statement with extreme caution. In this example, fuse 101 is a
MISER Bit or TURBO Bit. This blows fuse number 101. example:
FUSE(101,1)
DO NOT ATTEMPT TO USE THIS STATEMENT TO BLOW ARBITRARY FUSES!
The fuse statement was designed to blow MISER bits and TURBO Bits
only. The exact fuse number for the TURBO or MISER Bit must be
specified. Every time this statement is used, CUPL will generate a
warning. This is a reminder to double check that the fuse number
specified is correct. If a wrong fuse number is specified,
disastrous results can occur. Be very careful using this statement.
If the FUSE statement is used in a design and strange results occur,
check the fuse number specified and make sure that it is a MISER or
TURBO Bit.
o .c3.Preprocessor Commands
The preprocessor portion of CUPL operates on the source file before
it is passed to the parser and other sections of the compiler. The
preprocessor commands add file inclusion, conditional compilation,
and string substitution capabilities to the source processing
features of CUPL. Table 1-7 lists the available preprocessor
commands. Each command is described in detail in this section.
Table 1-7. Preprocessor Commands
-----------------
$DEFINE
$IFDEF
$UNDEF
$ELSE
$IFNDEF
$REPEAT
$ENDIF
$INCLUDE
$REPEND
$MACRO
$MEND
-----------------
The dollar sign ($) is the first character in all preprocessor
commands and must be used in column one of the line. Any combination
of uppercase or lowercase letters may be used to type these
commands.
.c4.$DEFINE
This command replaces a character string by another specified
operator, number, or symbol. The format is as follows:
$DEFINE argument1 argument2
where
argument1 is a variable name or special ASCII character.
argument2 is a valid operator, a number, or a variable name.
"Argument1" is replaced by "argument2" at all locations in the
source specification after the $DEFINE command is given (or until
the preprocessor encounters an $UNDEF command). The replacement is
a literal string substitution made on the input file before being
processed by the CUPL compiler. Note that no semicolon or equal sign
is used for this command. The $DEFINE command allows numbers or
constants to be replaced with symbolic names, for example:
$DEFINE ON 'b'1
$DEFINE OFF 'b'0
$DEFINE PORTC 'h'3F0
The $DEFINE command also allows creation of a personal set of
logical operators. For example, the following define an alternate
set of operators for logic specification:
$DEFINE { /* Alternate Start Comment
$DEFINE } */ Alternate End Comment
$DEFINE / ! Alternate Negation
$DEFINE * & Alternate AND
$DEFINE + # Alternate OR
$DEFINE :+: $ Alternate XOR
Note
==================================================
The above definitions are contained in the
PALASM.OPR file included with the CUPL
software package. This file may be included
in the source file (see $INCLUDE
command) to allow logic equations using
the PALASM set of logical operator
symbols, as well as the standard CUPL
operator symbols.
==================================================
.c4.$UNDEF
This command reverses a $DEFINE command. The format is as follows:
$UNDEF argument
where
argument is an argument previously used in a $DEFINE command.
Before redefining a character string or symbol defined with the
$DEFINE command, use the $UNDEF command to undo the previous
definition.
.c4.$INCLUDE
This command includes a specified file in the source to be processed
by CUPL. The format is as follows:
$INCLUDE filename
where
filename is the name of a file in the current directory.
File inclusion allows standardizing a portion of a commonly used
specification. It is also useful for keeping a separate parameter
file that defines constants that are commonly used in many source
specifications. The files that are included may also contain
$INCLUDE commands, allowing for "nested" include files. The named
file is included at the location of the $INCLUDE command. For
example, the following command includes the PALASM.OPR file in a
source file.
$INCLUDE PALASM.OPR
PALASM.OPR is included with the CUPL software and contains $DEFINE
commands that specify the following alternate set of logical
operators.
$DEFINE / ! Alternate Negation
$DEFINE * & Alternate AND
$DEFINE + # Alternate OR
$DEFINE :+: $ Alternate XOR
$DEFINE { /* Alternate Start Comment
$DEFINE } */ Alternate End Comment
.c4.$IFDEF
This command conditionally compiles sections of a source file. The
format is as follows:
$IFDEF argument
where
argument may or may not have previously been defined with a
$DEFINE command.
When the argument has previously been defined, the source statements
following the $IFDEF command are compiled until the occurrence of an
$ELSE or $ENDIF command.
When the argument has not previously been defined, the source
statements following the $IFDEF command are ignored. No additional
source statements are compiled until the occurrence of an $ELSE or
$ENDIF command.
One use of $IFDEF is to temporarily remove source equations
containing comments from the file. It is not possible to "comment
out" the equations because comments do not nest. The following
example illustrates this technique. NEVER is an undefined argument.
$IFDEF NEVER
out1=in1 & in2; /* A Simple AND Function */
out2=in3 # in4; /* A Simple OR Function */
$ENDIF
Because NEVER is undefined, the equations are ignored during
compilation; that is, they function as comments.
.c4.$IFNDEF
This command sets conditions for compiling sections of the source
file.
$IFNDEF argument
where
argument may or may not have previously been defined with a
$DEFINE command.
The $IFNDEF command works in the opposite manner of the $IFDEF
command. When the argument has not previously been defined, the
source statements following the $IFNDEF command are compiled until
the occurrence of an $ELSE or $ENDIF command.
If the argument has previously been defined, the source statements
following the $IFNDEF command are ignored. No additional source
statements are compiled until the occurrence of an $ELSE or $ENDIF
command.
One use of $IFNDEF is to create a single source file containing two
mutually exclusive sets of equations. Using an $IFNDEF and $ENDIF
command to set off one of the sets of equations, quick toggling is
possible between the two sets of equations by defining or not
defining the argument specified in the $IFNDEF command.
For example, some devices contain common output enable pins that
directly control all the tri-state buffers, whereas other devices
contain single product terms to enable each tri-state buffer
individually. In the following example, the argument, COMMON_OE has
not been defined, so the equations that follow are compiled. Any
equations following $ENDIF are not compiled.
$IFNDEF COMMON_OE
pin 11 = !enable; /* input pin for OE*/
[q3,q2,q1,q0].oe = enable; /* assign tri-state*/
/* equation for 4*/
/* outputs */
$ENDIF
If the device has common output enables, no equations are required
to describe it. Therefore, in the above example, for a device with
common output enables, define COMMON_OE so the compiler skips the
equations between $IFNDEF and $ENDIF.
.c4.$ENDIF
This command ends a conditional compilation started with the $IFDEF
or $IFNDEF commands. The format is as follows:
$ENDIF
The statements following the $ENDIF command are compiled in the same
way as the statements preceding the $IFDEF or $IFNDEF commands.
Conditional compilation may be nested, and for each level of nesting
of the $IFDEF or $IFNDEF command, an associated $ENDIF must be used.
The following example illustrates the use of $ENDIF with multiple
levels of nesting.
$IFDEF prototype_1
pin 1 = set; /* Set on pin 1 */
pin 2 = reset; /* Reset on pin 2 */
$IFDEF prototype_2
pin 3 = enable; /* Enable on pin 3 */
pin 4 = disable; /* Disable on pin 4 */
$ENDIF
pin 5 = run; /* Run on pin 5 */
pin 6 = halt; /* Halt on pin 6 */
$ENDIF
.c4.$ELSE
This command reverses the state of conditional compilation as
defined with $IFDEF or $IFNDEF. The format is as follows:
$ELSE
If the tested condition of the $IFDEF or $IFNDEF commands is true
(that is, the statements following the command are compiled), then
any source statements between an $ELSE and $ENDIF command are
ignored.
If the tested condition is false, then any source statements between
the $IFDEF or $IFNDEF and $ELSE command are ignored, and statements
following $ELSE are compiled.
For example, many times the production printed circuit board uses a
different pinout than does the wire-wrap prototype. In the
following example, since Prototype has been defined, the source
statements following $IFDEF are compiled and the statements
following $ELSE are ignored.
$DEFINE Prototype X /* define Prototype*/
$IFDEF Prototype
pin 1 = memreq; /* memory request on */
/* pin 1 of prototype*/
pin 2 = ioreq; /* I/O request on */
/* pin 2 of prototype*/
$ELSE
pin 1 = ioreq; /* I/O request on*/
/* pin 1 of PCB*/
pin 2 = memreq; /* memory request on */
/* pin 2 of PCB*/
$ENDIF
To compile the statements following $ELSE, remove the definition of
Prototype.
.c4.$REPEAT
This command is similar to the FOR statement in C language
and DO statements in FORTRAN language. It allows the
user to duplicate repeat body by index. The format is as
follows:
$REPEAT index=[number1,number2,...,numbern]
repeat body
$REPEND
where n can be any number in the range 0 to 1023 In preprocessing,
the repeat body will be duplicated from number1 to numbern. The
index number can be written in short form as [number1..numbern] if
the number is consecutive. The repeat body can be any CUPL
statement. Arithmetic operations can be performed in the repeat
body. The arithmetic expression must be enclosed by braces { }.
For example, design a three to eight decoder.
FIELD sel = [in2..0]
$REPEAT i = [0..7]
!out{i} = sel:'h'{i} & enable;
$REPEND
Where index variable i goes from 0 to 7, so the statement
"out{i} = sel:'h'{i} &enable;" will be repeated during
preprocessing and create the following statements:
FIELD sel = [in2..0];
!out0 = sel:'h'0 & enable;
!out1 = sel:'h'1 & enable;
!out2 = sel:'h'2 & enable;
!out3 = sel:'h'3 & enable;
!out4 = sel:'h'4 & enable;
!out5 = sel:'h'5 & enable;
!out6 = sel:'h'6 & enable;
!out7 = sel:'h'7 & enable;
The following example shows how the arithmetic operation addition
(+) and modulus (%) are used in the repeat body.
/* Design a five bit counter with a control signal advance.If
advance is high, counter is increased by one.*/
FIELD count[out4..0].i.sequence;
SEQUENCE count {
$REPEAT i = [0..31]
PRESENT S{i}
IF advance & !reset NEXT S{(i+1)%(32)};
IF reset NEXT S{0};
DEFAULT NEXT S{i};
$REPEND
}
.c4.$REPEND
This command ends a repeat body that was started with $REPEAT. The
format is as follows: $REPEND
The statements following the $REPEND command are compiled in the
same way as the statements preceding the $REPEAT command. For each
$REPEAT command, an associated $REPEND command must be used.
.c4.$MACRO
This command creates user-defined macros. The format is as follows:
$MACRO name argument1 argument2...argumentn
macro function body
$MEND
The macro function body will not be compiled until the macro name is
called. The function is called by stating function name and passing
the parameters to the function.
Like the $REPEAT command, the arithmetic operation can be used
inside the macro function body and must be enclosed in braces.
The following example illustrates how to use the $MACRO command.
Use the $MACRO command to define a decoder function with an
arbitrary number of bits. This example places the macro definition
and call in the same file.
$MACRO decoder bits MY_X MY_Y MY_enable;
FIELD select = [MY_Y{bits-1}..0];
$REPEAT i = [0..{2**(bits-1)}]
!MY_X{i} = select:'h'{i} & MY_enable;
$REPEND
$MEND
/* Other statements */
decoder(3, out, in, enable); /* macro invocation */
Calling function decoder will create the following statements by
macro expansion.
FIELD sel = [in2..0];
!out0 = sel:'h'0 & enable;
!out1 = sel:'h'1 & enable;
!out2 = sel:'h'2 & enable;
!out3 = sel:'h'3 & enable;
!out4 = sel:'h'4 & enable;
!out5 = sel:'h'5 & enable;
!out6 = sel:'h'6 & enable;
!out7 = sel:'h'7 & enable;
When macros are called, the keyword NC is used to represent no
connection. Because NC is a keyword, the letters NC should not be
used as a variable elsewhere in CUPL.
A macro expansion file can be created by using the -e flad when
compiling the PLD file. CUPL will create an expanded macro file
with the same name as the PLD file, with the extension ".mx".
The macro definition can be stored in a separate file with a ".m"
extension. Using the $INCLUDE command, specify the file. All the
macro functions in that file will then be accessible. The following
example shows the macro definition and calling statement stored in
different files. The macro definition of decoder is stored in the
file "macrolib.m"
$INCLUDE macrolib.m
/*specify the macro library */
/* other statements */
decoder(4, out, in, enable);
/* other statements */
More examples can be found in the example files provided on
diskette.
.c4.$MEND
This command ends a macro function body started with $MACRO. The
format is as follows: $MEND
The statements following the $MEND command are compiled in the same
way as the statements preceding the $MACRO command. For each $MACRO
command, an associated $MEND command.must be used.
o .c2.LANGUAGE SYNTAX
This section describes the CUPL language syntax. It explains how to
use logic equations, truth tables, state machine syntax, condition
syntax and user-defined functions to create a PLD design.
o .c3.Logical Operators
CUPL supports the four standard logical operators used for boolean
expressions. Table 1-8 lists these operators and their order of
precedence, from highest to lowest.
Table 1-8. Precedence of Logical Operators
Operator Example Description Precedence
! !A NOT 1
& A & B AND 2
# A # B OR 3
$ A $ B XOR 4
The truth tables in Figure 1-5 list the Boolean Logic rules for each
operator.
-----------------------------------------------------------------
AND OR XOR NOT
------ ------ ------ -----
00 | 0 00 | 0 00 | 0 0 | 1
01 | 0 01 | 1 01 | 1 1 | 0
10 | 0 10 | 1 10 | 1
11 | 1 11 | 1 11 | 0
-----------------------------------------------------------------
Figure 1-5. Truth Tables
o .c3.Arithmetic Operators
CUPL supports six standard arithmetic operators used for arithmetic
expressions. The arithmetic expressions can only be used in the
$REPEAT and $MACRO commands. Arithmetic expressions must appear in
braces { }. Table 1-9 lists these operators and their order of
precedence, from highest to lowest.
Table 1-9 Precedence of Arithmetic Operators
-----------------------------------------------------------------
Operator Example Description Precedence
** 2**3 Exponentiation 1
* 2*i Multiplication 2
/ 4/2 Division 2
% 9%8 Modulus 2
+ 2+4 Addition 3
- 4-i Subtraction 3
-----------------------------------------------------------------
o .c3.Arithmetic Function
CUPL supports one arithmetic function used for arithmetic
expressions. The arithmetic expressions can only be used in the
$REPEAT and $MACRO commands. Table 1-10 lists the function.
Table 1-10 Arithmetic Function
Function Base
LOG2 Binary
LOG8 Octal
LOG16 Hexadecimal
LOG Decimal
The LOG function returns an integer value. For example:
LOG2(32) = 5 <==> 2**5 = 32
LOG2(33) = ceil(5.0444) = 6 <==> 2**6 = 64
Ceil(x) returns the smallest integer not less than x.
o .c3.Extensions
Extensions can be added to variable names to indicate specific
functions associated with the major nodes inside a programmable
device, including such capabilities as flip-flop description and
programmable three-state enables. Table 1-11 lists the extensions
that are supported by CUPL and on which side of the equal sign (=)
they are used. The compiler checks the usage of the extension to
determine whether it is valid for the specified device and whether
its usage conflicts with some other extension used.
Table 1-11 Extensions
Extension Side Description
Used
.AP L Asynchronous preset of flip-flop
.AR L Asynchronous reset of flip-flop
.APMUX L Asynchronous preset multiplexer selection
.ARMUX L Asynchronous reset multiplexer selection
.BYP L Programmable register bypass
.CA L Complement array
.CE L CE input of enabled D-CE type flip-flop
.CK L Programmable clock of flip-flop
.CKMUX L Clock multiplexer selection
.D L D input of D-type flip-flop
.DFB R D registered feedback path selection
.DQ R Q output of D-type flip-flop
.IMUX L Input multiplexer selection of two pins
.INT R Internal feedback path for registered macrocell
.IO R Pin feedback path selection
.IOAR L Asynchronous reset for pin feedback register
.IOAP L Asynchronous preset for pin feedback register
.IOCK L Clock for pin feedback register
.IOD R Pin feedback path through D register
.IOL R Pin feedback path through latch
.IOSP L Synchronous preset for pin feedback register
.IOSR L Synchronous reset for pin feedback register
.J L J input of JK-type output flip-flop
.K L K input of JK-type output flip-flop
.L L D input of transparent latch
.LE L Programmable latch enable
.LEMUX L Latch enable multiplexer selection
.LFB R Latched feedback path selection
.LQ R Q output of transparent input latch
.OBS L Programmable observability of buried nodes
.OE L Programmable output enable
.OEMUX L Tri-state multiplexer selection
.PR L Programmable preload
.R L R input of SR-type output flip-flop
.S L S input of SR-type output flip-flop
.SP L Synchronous preset of flip-flop
.SR L Synchronous reset of flip-flop
.T L T input of toggle output flip-flop
.TEC L Technology-dependent fuse selection
.TFB R T registered feedback path selection
.T1 L T1 input of 2-T flip-flop
.T2 L T2 input of 2-T flip-flop
Each extension provides access to a specific function. For example,
to specify an equation for output enable (on a device that has the
capability) use the .OE extension. The equation will look as
follows:
PIN 2 = A;
PIN 3 = B;
PIN 4 = C;
PIN 15 = VARNAME;
VARNAME.OE = A & B;
Note that the compiler supports only the flip-flop capabilities that
are physically implemented in the device. For example, the compiler
does not attempt to emulate a JK-type flip-flop in a device that
only has D-type registers. Any attempt to use capabilities not
present in a device will cause the compiler to report an error.
For those devices containing bi-directional I/O pins with
programmable output enables, CUPL automatically generates the output
enable expression according to the usage of the pin. If the variable
name is used on the left side of an equation, the pin is assumed to
be an output and is assigned binary value 1; that is, the output
enable expression is defaulted to the following:
PIN_NAME.OE = 'b'1; /* Tri-state buffer always ON */
Those pins that are used only as inputs (that is, the variable name
appears only on the right side of an equation) are assigned binary
value 0; the output enable expression is defaulted to the following:
PIN_NAME.OE = 'b'0; /* Tri-state buffer Always OFF */
When the I/O pin is to be used as both an input and output, any new
output enable expression that the user specifies overrides the
default to enable the tri-state buffer at the desired time.
When using a JK or SR-type flip-flop, an equation must be written
for both the J and K (or S and R) inputs. If the design does not
require an equation for one of the inputs, use the following
construct to turn off the input:
COUNT0.J='b'0 ; /* J input not used */
Control functions such as asynchronous resets and presets are
commonly connected to a group (or all) of the registers in a device.
When an equation is written for one of these control functions, it
is actually being written for all of the registers in the group.
For documentation purposes, CUPL checks for the presence of such an
equation for each register in the group and generates a warning
message for any member of the group that does not have an identical
equation. If all the control functions for a given group are
defined with different equations, the compiler will generate an
error since it cannot decide which equation is the correct one.
Remember that this is a device specific issue and it is a good idea
to understand the capability of the device being used.
Figure 1-6 shows the use of extensions. Note that this figure does
not represent an actual circuit, but shows how to use extensions to
write equations for different functions in a circuit.
[Picture]
Figure 1-6. Circuit Illustrating Extensions
The figure shows an equation with a .D extension that has been
written for the output to specify it as a registered output. Note
that when feedback (OUT_VAR) is used in an equation, it does not
have an extension.
Note
==================================================
The .DQ extension is used for input pins only.
==================================================
Additional equations can be written to specify other types of
controls and control points. For example, an equation for the output
enable can be written as follows:
OUT_VAR.OE = IN_VAR1 # IN_VAR2