Application Development


Chapter 42 . Building Application Executables

Several executables are provided to get Panther and Panther applications up and running. Depending on your application's architecture and the way Panther itself resides on your network, you will probably build and rebuild executables to meet a variety of development and deployment requirements.

There are executables (include .exe extension under Windows) used solely by the client:

And for JetNet/Oracle Tuxedo executables that are specific to the server:

For the most part, you can use the executables provided with your installation. However, if any of the following conditions apply, either at the outset or during development, or when you are ready to deploy your application, you need to build new executables:

This chapter describes:


Steps for Creating an Executable

The steps for building an executable assume that SMBASE, SMVARS, and SMPATH settings are the same as your development setup (for prodev) and are in effect.

Prepare the Application Directory

  1. Create an application directory (if one doesn't already exist).
  2. Copy all files from the distributed link directory to your application directory.
  3. If you want to link your own C modules to the executable, copy them to your application directory.

Determine the Executables to Build

To specify which executables to build, either edit the makefile in your application directory or specify the target.

If you edit the makefile, make sure the appropriate client executables are commented or uncommented as needed (these are uncommented by default):

PRORUN=prorun

Runtime executable (prorun32.exe under Windows)

PRODEV=prodev

Development executable (prodev32.exe under Windows)

For JetNet and Oracle Tuxedo which support application servers, make sure the appropriate server executables are commented or uncommented as needed:

PROSERV=proserv

Server executable (uncommented by default)

PRODSERV=prodserv

Debuggable server executable (commented out by default)

PROGSERV=progserv

Conversion server executable (commented out by default)

Notes: To use Panther's debugger on an application server with your particular database, uncomment PRODSERV.

Link the Database Engine

You must link in your database engine to the executable if you are:

Edit the makefile in order to identify the desired database for the executable. Uncomment the appropriate include statement for your particular database. The include statements are listed under the SELECT DATABASE SOFTWARE heading.

To link your database engine:

Uncomment the appropriate include statement for your database. You will also need to edit the file you uncomment (makevars.dbs) to indicate the correct version of your database software (refer to page 42-5 for details on editing makevars.dbs).

To exclude the JDB database from the executable:

Comment out the JDB include statement.

To link JDB and your database engine:

Leave the JDB database specification uncommented and uncomment the appropriate include statement for your database.

Include C Modules in the Executable

If your application uses user-written C modules, you'll want to link them into the application's executable.

To link your own C modules to the executable:

  1. Copy the modules to the application directory.
  2. Add the filenames to the SRCMODS macro of the makefile.

For example, if your application's C source code modules are mymod1.c and mymod2.c, change the SRCMODS line of the makefile to list the modules. For example:

UNIX: SRCMODS = mymod1.o mymod2.o funclist.o

Windows: SRCMODS = mymod1.obj mymod3.obj funclist.obj

When you include files within the executable, you don't have to include them in the deployed distribution.

Identify the Database Version

When you build an executable to include your database, once you edit the makefile, you must also ensure that the uncommented makevars file includes the appropriate information.

Refer to Database Drivers for your specific engine before changing these values.

To verify (or update) database-specific information:

Access the makevars.dbs, and ensure that the following settings are correct for your database engine:

Compile the Changes

Once you have copy all required files to your application directory, and make the appropriate edits to the makefile (and optionally, to makevars and jmain.c), from the application directory, run the appropriate compiler utility at the command line: make under UNIX; nmake under Windows.

A compiling message and then the linking message are displayed. When the operating system returns you to the command prompt (with no errors), the executables have been built.

For more about makefiles, refer to your compiler's documentation on make or nmake.

If you are building executables for distribution, you can package them with the other required files for application release. Refer to page 43-1 for details.

Rename the Executables

The result of running the make or nmake utility is compiled executables ready for distribution. You can rename executables to reflect your application's name; there are no naming restrictions, except perhaps those imposed by your specific operating system.


Customizing Source Code for an Application

You can edit the source, jmain.c, for the Panther executable to change the default behavior of your application. jmain.c is located in the link directory and you should copy it to your application directory. Edit the source file prior to creating the executable if you want to do any of the following:

Whenever you edit jmain.c you must remember to rebuild your runtime executable (prorun) in order for changes to take effect.

Source Code Structure

jmain.c has three functions defined in it:

If a finer granularity is needed, you can edit initialize and clean_up themselves. Do so only if you understand Panther thoroughly.

Notes: In general, you should not modify jmain.c to install event functions. You can declare most event functions in funclist.c. A few event function types, however, must be installed before or during initialization in jmain.c. For more information on event function installation, refer to page 44-4.

Specifying an Application Startup Screen

To identify a startup screen that will display when your application is first initialized, you must edit the jmain.c file you copied to your application directory.

Change the start_screen_name setting from 0 to the name of your top screen; for example, start_screen_name = "login.scr"; Include the specification after the comment for TOPSCREEN:

/* to hard code the name of the first screen, for */
/* example, "TOPSCREEN", replace the following line */
/* with start_screen_name = "TOPSCREEN"; */
start_screen_name = "login.scr";
start_up (argc, argv);

Rebuild your runtime executable to have the change in jmain.c take effect.

Specifying an Application Icon

To ensure that an icon that will display when your application is installed on a Windows client machine, specify the name of the application icon in the prorun.rc resource file that you copied to your application directory.

In jmain.c, change the ICONFILE specification from prolific.ico to the name of your icon image.

Rebuild your runtime executable to have the change in jmain.c take effect.

Including Memory-Resident Components

All Panther components can be made memory resident: screens, menus, configuration files, and JPL modules. When a component is made memory resident, it means it is compiled as part of the executable. This can enhance application performance by minimizing its need to access the disk. It can also reduce the number of files in the distribution. Once these components are compiled into the executable, the individual components can then be eliminated from the distribution.

In function, memory residency means the component is loaded into memory when your application starts up. However, it's also important to recognize that your application would consume more memory at startup.

In general, the process of making a component memory-resident involves:

Screens, Menus, and JPL

Panther creates binary files that are stored in Panther libraries. These include your screens and service components, JPL modules, menus, and any file created with and used by Panther (such as smjgbls, the global variables file used by Panther). Memory-resident files are installed by way of a memory-resident list. The list is maintained by Panther and specifies the components you indicate in the source file.

To make screens, menus, or JPL modules memory-resident:

  1. Extract the desired binary component from its library using formlib. Or run jpl2bin against the ASCII version of the component to get a binary file.
  2. Convert the binary file to a C structure with bin2c, for example:
    bin2c filename.h filename.bin
  3. In jmain.c, after the lines:
    #include "smdef.h"
    #include "smerror.h"
    #include "smuprdb.h"

    add the filename.h specification

    #include filename.h
  4. In jmain.c, before the line:
    /* THE FOLLOWING FUNCTIONS ARE IN THIS MODULE */

    include the C structure:

    struct form_list mrforms[] =
    {
    "source_filename.ext", filename
    "", (char *)0
    };

    All memory-resident files, modules, etc. should be listed, one per line, immediately before the line:

     "",             (char *)0

    This last entry in the list indicates the end of the list and is required.

  5. In jmain.c, after the line:
    /* Place code...any Panther initializations here */

    add the following line:

    sm_formlist(mrforms);

    The call to sm_formlist dynamically adds the specified components in the form_list structure to Panther's internal memory-resident list.

  6. Make sure the edited jmain.c source is in your application directory and create your application executable (refer to "Steps for Creating an Executable").

    Notes: Because the screen editor can only operate on library files, altering memory-resident screens and JPL during program development requires a cycle of test—edit—extract from library—reconvert with bin2c—recompile. Therefore you should make components memory-resident only at the very end of your development process.

At runtime, when Panther attempts to open a screen, it first looks in the memory-resident screen list for the requested screen; if found there, it's displayed from memory, while screens not in the list are sought in open libraries. In this way, you can open screens irrespective of their actual location—for example, with sm_r_form. You can later change the location of the screen without changing the calls to open them, simply by changing the memory-resident list.

filename extensions and case conversion

If you have specified the setup variable SMFEXTENSION, Panther appends its value to screen names that do not already contain an extension; take this into account when creating the screen list. For UNIX systems, Panther can also convert the name to uppercase before searching the screen list, as determined by the FCASE variable.

Alternatively, if you are using a custom executive, sm_d_form and related library functions can be used to display memory-resident screens; each takes as one of its parameters the address of the global array containing the screen data, which usually have the same name as the file in which the original screen was originally stored.

Configuration Files

Any or all of the required configuration files as well as optional configuration files used by Panther can be made memory-resident. These files include:

To make configuration files memory-resident:

  1. Copy the desired binary files from the config directory or extract (using formlib) them from the common library (if they are already associated with your application).
  2. Convert the binary file to C structure with bin2c, for example:
    bin2c filename.h filename.bin
  3. In jmain.c, after the lines:
    #include "smdef.h"
    #include "smerror.h"
    #include "smuprdb.h"

    add the filename.h specification:

    #include "filename.h"
  4. In jmain.c, after the line:
    /* Place code to...any Panther initializations here */

    add the following line or lines, specific to each configuration file type:

    sm_n_msg_read ("SM", SM_MSGS, MSG_MEMORY|MSG_INIT,
    msgfile);
    sm_vinit (videofile);
    sm_load_colormap (cmapfile);
    sm_keyinit (keyfile);

If a configuration file is memory-resident, the corresponding environment variable or SMVARS entry is unnecessary and the binary files needn't be included in the common library of your distribution.

Rename the Distributed Panther Library

The distributed library, prorun5.lib, contains the support routines and screens used by Panther. It is required in your application's distribution as well. In addition to renaming executables, you can also rename this library to conform to your application's name.

To rename the Panther library:

  1. Copy prorun5.lib from the config directory to your application directory and rename the copied file.
  2. In jmain.c, replace the line:
    if ((lib = sm_l_open (p = RUNTIME_LIBRARY)) < 0)

    with:

    if ((lib = sm_l_open (p = "myapp.lib")) < 0)

Subsystem Installation

After the definition of the main function, there is a JTERM_COMPRESSION subsystem macro definition. This subsystem increases the communication efficiency and execution speed for applications when they are accessed by the Panther terminal emulator. It increases the application's memory requirements. By default, it is set to 0. To turn the subsystem on, set the macro to 1.

Oracle Tuxedo Executables

You need to update the Oracle Tuxedo XA RM file before you can use the provided makefile to relink executables. This is done by appending the contents of $SMBASE/samples/Oracle Tuxedo/RM to $TUXDIR/udataobj/RM and confirming the appropriate section for your database and version.