3 Using Flick
3.1 Introduction
Flick works in three phases, each implemented as a separate program: the front end, the presentation generator, and the back
end. A Flick front end is simply a parser that translates some IDL input into an intermediate representation
called an AOI (Abstract Object Interface, `.aoi') file. Next, a "presentation generator" determines how the
constructs in the AOI file (the parsed IDL file) are to be mapped onto type and function definitions in the C or
C++ programming language. In other words, the presentation generator determines how the generated stubs
will appear -- e.g., the stubs' function prototypes -- and how they will interact with user code -- e.g., the
stubs' parameter passing conventions. This information about the stubs is written into a PRES_C (Presentation
in C/C++, `.prc') file. The final phase of compilation, the back end, reads a PRES_C file and produces the
C or C++ code for the optimized stubs, written to use a particular transport system (e.g., TCP) and message
format.
Flick has multiple implementations of each of the three phases described above. Flick has three separate front
ends: one to parse CORBA IDL files, one to parse ONC RPC (Sun) IDL files, and one to parse MIG IDL files.
There are five different presentation generators, implementing the CORBA (C and C++), ONC RPC, MIG, and
Fluke1 mappings of
IDL constructs onto C or C++. Finally, there are seven separate back ends for producing stubs that use IIOP (C and C++), ONC/TCP, Mach
messages, Trapeze,2
Khazana-style messages,3
and Fluke IPC.
3.1.1 Flick Programs
Every compiler pass is implemented as a separate program. Once Flick has been built, links to these programs will be located in
the bin subdirectory of your Flick build tree:
Front Ends
-
flick-fe-newcorba
- The CORBA front end. Parses a CORBA IDL (`.idl') file and outputs an
AOI file (`.aoi') to be read by the flick-c-pfe-corba, flick-c-pfe-corbaxx,
or flick-c-pfe-fluke presentation generators.4
-
flick-fe-sun
- The ONC RPC front end. Parses an ONC RPC IDL (`.x') file and outputs
an AOI file to be read by the flick-c-pfe-sun presentation generator.
-
flick-c-fe-mig
- The MIG front end/presentation generator. Parses a MIG IDL (`.defs')
file and outputs a PRES_C file to be read by any back end. Note that
flick-c-fe-mig is unique because it implements both the front end and
presentation generation passes. These passes are combined because MIG
IDL allows users to specify presentation attributes in addition to simply
defining interfaces.
Presentation Generators
-
flick-c-pfe-corba
- The CORBA C language presentation generator. Reads an AOI file
generated by the CORBA front end and outputs a PRES_C (`.prc') file
describing C stubs to be read by any C language back end (i.e., any back
end except flick-c-pbe-iiopxx).
-
flick-c-pfe-corbaxx
- The CORBA C++ presentation generator. Reads an AOI file generated by
the CORBA front end and outputs a PRES_C (`.prc') file describing C++
stubs to be read by any C++ language back end (as of this writing, only
flick-c-pbe-iiopxx).
-
flick-c-pfe-sun
- The ONC RPC presentation generator. Reads an AOI file generated by the
ONC RPC front end and outputs a PRES_C file describing C stubs to be
read by any C language back end.
-
flick-c-pfe-fluke
- The Fluke presentation generator, used with the Fluke operating system.
Reads an AOI file generated by the CORBA front end and outputs a
PRES_C file describing C stubs to be read by any C language back end.
Back Ends
-
flick-c-pbe-iiop
- The IIOP back end for C code. Reads a PRES_C file and outputs either
client stubs or server skeletons for use with Flick's IIOP runtime. The
generated stubs use the IIOP transport and CDR data encoding.
-
flick-c-pbe-iiopxx
- The IIOP back end for C++ stubs. Reads a PRES_C file and outputs either
client stubs or server skeletons for use with TAO. The generated stubs use
the IIOP transport and CDR data encoding.
-
flick-c-pbe-sun
- The ONC/TCP back end for C stubs. Reads a PRES_C file and outputs
either client stubs or server skeletons for use with Flick's ONC/TCP
runtime. The generated stubs use the ONC/TCP transport and XDR data
encoding.
-
flick-c-pbe-mach3mig
- The Mach 3/MIG back end for C stubs. Reads a PRES_C file and outputs
either client stubs or server skeletons for use with Mach. The generated
stubs use Mach IPC and MIG-style typed data encoding.
-
flick-c-pbe-trapeze
- The Trapeze back end for C stubs. Reads a PRES_C file and outputs either
client stubs or server skeletons for use with Trapeze. The generated stubs
use Trapeze messages and either CDR or XDR data encoding, depending
on where the PRES_C file originated. (XDR is used for Sun-style stubs;
CDR is used for CORBA and other stub styles.)
-
flick-c-pbe-khazana
- The Khazana back end for C stubs. Reads a PRES_C file and outputs either
client stubs or server skeletons for use within Khazana. The generated
stubs use TCP and a CDR-like data encoding.
-
flick-c-pbe-fluke
- The Fluke back end for C stubs. Reads a PRES_C file and outputs either
client stubs or server skeletons for use with Fluke. The generated stubs use
Fluke IPC and a CDR-like data encoding.
Other Tools
-
flick-aoid
- The AOI dump utility. Reads an AOI file and outputs a human-readable
dump of the parse tree (an `.aod' file). This program is used primarily to
debug Flick.
-
flick-c-presd
- The PRES_C dump utility. Reads a PRES_C file and outputs a human-
readable dump of the interface presentation (a `.prd' file). This program
is used primarily to debug Flick.
3.1.2 Common Command Line Options
All Flick programs support these command line arguments and options:
-
input
- Read from the named input file. Every Flick program expects to receive
the name of its input file on the command line. If no input file is specified,
input is taken from stdin.
-
-o filename
or
--output filename
- Write output to the specified file. If no output file is specified, the name
of the output file will be constructed by concatenating the base name of
the input file with a new, appropriate extension; e.g., if a presentation
generator was told to read "foo.aoi", the name of the output file would
be "foo.prc". If no input file is specified on the command line, output
will be written to stdout.
-
-u
or
--usage
or
-? or
--help - Print a synopsis of all available flags and quit.
-
-v
or
--version
- Print the version of the program and quit.
Warning: Flick's AOI and PRES_C file formats are binary file formats, not text file formats. Windows NT and
Windows 95 distinguish binary streams from text streams, and set stdin and stdout to be text streams. Thus, under
Windows, it is not possible to pipe AOI and PRES_C data between Flick compiler passes.
3.2 Front Ends
Flick's three front ends translate the CORBA, ONC RPC, and MIG IDLs into intermediate formats used as input to later stages
of the compiler. The simplest way to use any of these front ends is to specify the IDL file on the command
line:
-
flick-fe-newcorba
foo.idl
- Process the CORBA IDL file foo.idl to produce foo.aoi . The output
AOI file can be input to the CORBA or Fluke presentation generators.
-
flick-fe-sun
foo.x
- Process the ONC RPC IDL file foo.x to produce foo.aoi . The resultant
AOI file can be input to the ONC RPC presentation generator.
-
flick-c-fe-mig
foo.defs
- Process the MIG IDL file foo.defs to produce foo.prc . The MIG front
end is special in that it produces a PRES_C file, not an AOI file.
3.2.1 Command Line Options
In addition to the standard flags supported by all Flick programs, the CORBA and ONC RPC front ends support the following
two, mutually exclusive, flags:
-
-c flags
or
--cppflags flags
- Pass flags to the C preprocessor. By default, all IDL files are piped
through the C preprocessor before being parsed.
-
-n
or
--nocpp
- Skip the C preprocessor and pass the IDL input directly to the front end.
The MIG front end supports the following flags in addition to the standard flags listed in Section 3.1.2:
-
-Idir
- Specify an include directory for the C preprocessor.
-
-Dsym
- Pass sym on to the C preprocessor. A value may be specified, e.g.,
-DDEBUG=2. The default value for sym is 1.
-
-Usym
- Undefine symbol sym in the C preprocessor.
-
-Xcpp
opt
- Pass the command line option opt to the C preprocessor.
-
-c
or
--client
- Generate client stubs only. The default is to generate both client stubs and
server skeletons. This option cannot be combined with -s.
-
-s
or
--server
- Generate server skeletons only. This option cannot be combined with -c.
3.2.2 Additional Comments
CORBA
The CORBA front end does not currently support certain CORBA data types (wchar, wstring, fixed, and native types) nor
does it support CORBA contexts. It does, however, support the 64-bit "long long" and "unsigned long long"
types.
ONC RPC
The ONC RPC front end allows only one argument to be passed to each operation. This conforms to the older specification of
the Sun RPC language. (RFC 1831, which defines the "modern" ONC RPC IDL, allows for multiple arguments and
in-argument-list type specifications.) Further, Flick's ONC RPC front end does not recognize the keywords hyper and
quadruple that are described in RFC 1832. Flick's ONC RPC front end does not support the `%' directive that is offered by
Sun's rpcgen IDL compiler.
MIG
The MIG front end/presentation generator is nearly complete but does not yet support all of the MIGisms you may
love (or hate). The list of not-yet-implemented features is contained in the doc/BUGS file in the Flick source
tree.
3.3 Presentation Generators
Flick has four different presentation generators: one to produce CORBA-style C language stubs, a second to produce
CORBA-style C++ stubs, a third to produce ONC RPC (rpcgen-style) stubs, and a fourth to produce special stubs for use in
Utah's Fluke operating system. (As previously mentioned, Flick's MIG-style presentation generator is conjoined with the MIG
front end.) A presentation generator can be invoked to produce either the client-side stubs or the server-side dispatch function,
but not both at the same time. Simply run a presentation generator twice, with different options, to produce both files; for
example:
flick-c-pfe-corba -c -o foo-client.prc foo.aoi # make client
flick-c-pfe-corba -s -o foo-server.prc foo.aoi # make server
|
3.3.1 Command Line Options
Each presentation generator accepts the following options in addition to those described in Section 3.1.2:
-
-c
or
--client
- Generate client stubs. This is the default if neither -c nor -s is specified.
This option cannot be combined with -s.
-
-s
or
--server
- Generate server skeletons. This option cannot be combined with -c.
-
-a
or
--async_stubs
- Generate nonstandard "decomposed" stubs instead of normal, synchronous
RPC stubs. This experimental feature is currently implemented only in the
CORBA C language presentation generator.5
In addition, there are many, many options for changing the printf-like format strings that the presentation generator uses
to produce the names of various presentation elements. (Use --usage to see them all.) These name format options exist only
for short-term use; all of these options will eventually be replaced by a more general presentation-modification
facility.
3.3.2 Additional Comments
General
There are still some unwarranted dependencies between certain front ends and presentation generators. Although the CORBA
and ONC RPC front ends both produce AOI files, the CORBA and ONC RPC presentation generators are still "tuned" to the
AOI constructs generated by the respective front ends. This means that at the moment, the CORBA and Fluke
presentation generators can input only AOI files generated by the CORBA front end, and similarly, that the ONC RPC
presentation generator can input only AOI files generated by the ONC RPC front end. This will eventually be
corrected.
CORBA
The CORBA C language presentation generator does not produce CORBA-style allocator functions for constructed data
types (as described in Section 14.8 of the CORBA 2.0 specification). Flick's CORBA runtime does provide a
generic CORBA_alloc function, however, which takes a single argument indicating the number of bytes to be
allocated.
3.4 Back Ends
Flick has seven separate, optimizing back ends to produce stubs that use IIOP (for C and C++ stubs), ONC/TCP, Mach 3 typed
messages, Trapeze messages, Khazana-style messages, or Fluke IPC. As described in Section 3.3, Flick separates the client-
and server-side presentations into two PRES_C files. This means that in order to generate both client and server code, you must
run a back end twice: once on the client-side `.prc' file and once on the server-side `.prc' file. For instance, the two
commands:
flick-c-pbe-iiop foo-client.prc # make client
flick-c-pbe-iiop foo-server.prc # make server
|
produce the client stubs (foo-client.c, foo-client.h) and then the server skeletons (foo-server.c, foo-server.h)
using Flick's IIOP back end. Of course, it is important to use the same back end to produce both client and server
code.
3.4.1 Command Line Options
All back ends support the following options in addition to the standard flags:
-
-h filename
or
--header filename
- Output the header file to filename . If this is not specified, the name of
the header file will be constructed from the name of the output `.c'/`.cc'
file (which is specified with -o). If the output C/C++ file is stdout, the
header will be inlined into the output.
-
-p prefix
or
--prefix prefix
- Use prefix when including the generated header file from the generated
C or C++ file, i.e.: #include "prefix header.h".
-
-s
or
--system_header
- In the output C or C++ file, include the generated header as a system header
rather than a user header, i.e., using <> rather than "".
-
-n filename
or
--inline filename
- Allow "simple" presentation implementation functions to be inlined. This
option allows us to support fast inline functions similar to those from
TAO's IDL compiler. These functions are placed in filename , and
included by the generated header or source depending on the compile-time
directive __ACE_INLINE__.
-
--no_timestamp
- Do not output timestamp information into the generated header and C/C++
code files. This option is useful for regression testing.
-
-i
or
--no_included_imple-
mentations
- Suppress the definition of stubs that are derived from interfaces that were
#included by the IDL file that was processed by the front end. This
option must be used with caution, as you may unintentionally cause Flick
to omit functions that you need in order to compile your client or server
application.
-
-d
or
--no_included_declarations
- Suppress the declaration of stubs that are derived from interfaces that were
#included by the IDL file that was processed by the front end. This option
must also be used with caution, as you may unintentionally cause Flick to
omit function declarations that you need in order to compile your client or
server application.
-
-m
or
--all_mu_stubs
- Generate all marshal and unmarshal stubs. Normally Flick generates only
those that are actually used by the generated code. This option is useful
mainly for debugging. The generated code is significantly larger if all
marshal and unmarshal stubs are produced -- generally too large for
practical use.
-
-P filename
or
--presentation_imple-
mentation filename
- Read the "presentation implementation"
from filename . The presentation implementation (a `.scml' -- Source
Code Markup Language -- file) describes how certain functions are to be
created and written into the generated code. This option is normally not
required because each back end has its own built-in default.
-
--nostdinc
- Tell the back end not to search in the standard locations for SCML files.
Again, this option is generally not used, unless one is implementing or
testing Flick.
-
-I directory
or
--include directory
- Look in directory for presentation implementation (`.scml') files. This
option may be repeated in order to define a search path. Like -P, this option
is normally not required because each back end automatically looks in the
Flick installation directories for the SCML files it needs.
-
-f filename
or
--file filename
- In the output C or C++ file, output: #include "filename ". This option
is often used with the IIOP C++ back end; see Section 3.4.2 for more
information.
-
-F filename
or
--File filename
- In the output header file, output: #include "filename ". This option
is often used with the IIOP C++ back end; see Section 3.4.2 for more
information.
-
-D vardef
or
--define vardef
- Use the variable definition vardef when reading the presentation
implementation (SCML) files. This option may be repeated in order to
define multiple variables.
3.4.2 Additional Comments
IIOP/C++ Back End Issues
The IIOP back end for C++, flick-c-pbe-iiopxx, is careful to generate client and server code that can be compiled into a
single program (in order to support TAO "collocated" objects). However, a side effect is that the generated C++ files for client
and server each need to #include the other's header file in order to compile. So, the IIOP back end for C++ is normally
invoked like this:
flick-c-pbe-iiopxx -h client.h -f server.h ... # make client
flick-c-pbe-iiopxx -h server.h -F client.h ... # make server
|
where client.h and server.h are replaced with your names for the client and server header files, respectively.
The first command generates the client code and header files; the client's header file is named client.h and the generated
client C++ file will #include "server.h". Similarly, the second command generates the server code and header files; the
server's header file is named server.h and the server's header will #include "client.h". Note that one uses -f when
generating the client and -F when generating the server. This is required in order to sequence the #includes
properly.
Code Generation Issues
All of Flick's back ends produce code that is optimized for speed, and Flick is currently single-minded in pursuit of fast code.
The current version of Flick largely overlooks other code generation issues that may be important to certain application
domains:
-
Code Size.
- Because Flick aggressively inlines code to marshal and unmarshal data, the size of the generated stub
functions can be very large. The generated code becomes larger as the complexity of the IDL-defined interfaces
increases. A future release of Flick will make better inlining decisions.
-
Code Complexity.
- Flick-generated code is not intended to be human-readable, although the code is generally not
too difficult for programmers to understand. Flick makes extensive use of the C preprocessor. Some compilers
may have problems with Flick-generated code; for instance, we discovered that Microsoft Visual C++ 4.2 was
unable to deal with deeply nested switch statements.
-
Thread Safety.
- Flick does not generate thread-safe code. If your application is multithreaded, you will need to provide
explicit locks around the Flick-generated stubs.
-
Error Handling.
- Although the generated stubs generally handle errors in an appropriate manner, Flick's runtimes
may fail an assert or exit in response to certain critical errors. A future release of Flick will better address
error handling and recovery within the runtimes.
The doc/BUGS file in the Flick source tree lists known bugs with Flick's code generators.
Server Main Functions
The IIOP (C only), ONC/TCP, Khazana, and Trapeze back ends each produce a main function for the server,
whereas the IIOP C++, Mach 3, and Fluke back ends do not. The assumption is that the former back ends will be
used to generate "standalone" servers while the latter back ends will generate code for use in a more complex
framework.
Mix-and-Match Problems
While it is possible to combine presentation generators and back ends in unusual ways -- e.g., create Sun-style
ONC/TCP code for a CORBA-style presentation -- Flick's runtime libraries may not be able to handle unusual
combinations. In this release we have focused on code generation for "matched" presentation and code generation,
meaning:
- CORBA-style C stubs using IIOP (flick-c-pfe-corba with flick-c-pbe-iiop);
- CORBA-style C++ stubs using IIOP (flick-c-pfe-corbaxx with flick-c-pbe-iiopxx);
- ONC RPC-style stubs using ONC/TCP (flick-c-pfe-sun with flick-c-pbe-sun);
- MIG-style stubs using Mach 3 (flick-c-fe-mig with flick-c-pbe-mach3mig); and
- Fluke-style stubs using Fluke IPC (flick-c-pfe-fluke with flick-c-pbe-fluke).
These "mixed" combinations have also been tested and should work:
- CORBA-style stubs using Mach 3 (flick-c-pfe-corba with flick-c-pbe-mach3mig)6 ;
- CORBA-style stubs using Trapeze (flick-c-pfe-corba with flick-c-pbe-trapeze); and
- ONC RPC-style stubs using Trapeze (flick-c-pfe-sun with flick-c-pbe-trapeze).