The Fire Application Compiler enables developers to compile sets of application files into a single application library. When an application library is created it is assigned a product name and a version number which can be used to control access to the application using the Fire licensing system. The Application Compiler produces a single deliverable binary library which contains all the component files of the application in a compiled and encrypted form. In addition, the compiler stamps a unique developer identification number into the library to identify the application owner.
Once an application library has been created it can be considered as a mini file system and mounted by Fire. Once mounted, the files inside it (the library members) can be accessed like any other file in the normal file system. Library members are accessed from the application library root "@" - the virtual mount point for all application libraries. The product name, assigned to the library when it is created, is used by the Fire licensing system to control access to the application.
The application compiling system consists of:
The application compiling system is a licensed Fire product and requires the installation of a Fire Application Compiler license (mxappdev). When an mxappdev license is issued to a developer, a unique developer identification number (the developer ID) is assigned to the developer and is subsequently stamped into all compiled libraries created by the Application Compiler. This unique developer IDidentifies the application owner and is used to control access to the library. Only if the developer ID of a library matches the developer ID associated with a development system’s mxappdev license, is the user regarded as the owner. Only the owner of an application library can view its contents or extract any member files.
The Application Compiler Utility - applib - is used to create and maintain application libraries. Refer to the Utility Programs section in the Fire Reference Manual for full details of the applib utility program command parameters.
applib is similar to the Unix "tar" command and is used to:
When creating a library, applib copies all specified files and directories recursively into the library. Any text files encountered are encrypted and any Fire command files and menu files are pre-compiled before insertion into the library. All other files are copied verbatim.
Binary executable program files (i.e. linked C programs) may be added to the library, but there are no means of running them. The Operating System is not able to access Fire library members directly. It is possible for an application to copy a file from the library to an external file, e.g. as part of an installation setup procedure. When such a file is installed the application should ensure that the file has been given the correct access permissions - execute permission for the appropriate users.
Library members have access modes just like files in the normal UNIX file system. The access mode of a library member is derived from the access mode of the original source file and is modified (write permission is not allowed) to reflect the access permission of the library member when the library becomes mounted. Like normal file access modes, library member access modes define access permissions for User (Owner), Group and World users. However, for library members, Fire uses the following interpretations of Owner, Group and World:
The Application Compiler automatically grants the owner read permission to all members of the library. The owner is also granted execute access to the command macro (.cmd) and menu (.men) files. This means that any command macro file in the library may call any other in the same library. In addition, when the library is mounted on the original development system - where the mxappdev license is available and the developer ID associated with the license matches that embedded in the library, the Fire development system user is regarded as the owner and therefore is granted complete (read and execute) access to the library members.
Group access controls access by applications created by the same developer. This means that when a command macro file from one mounted application invokes a command macro file in another mounted application, it is granted whatever group permission is specified by the file access mode of the invoked library member. This facility could allow the development of a library of common procedures, toolkit for other applications, or anything else by the same developer. By allowing only group access, the toolkit is available only to applications by the same developer. The group access mode for the library member is copied from the group access mode of the source file - with write permission removed.
World access defines access by all other categories of user. World access permissions can be used to distinguish between public and private library members. The world access mode for the library member is copied from the world (other) access mode of the source file - with write permission removed. The world access modes of start.cmd and stop.cmd determine if the application is a public or private application. For a private application (i.e. only accessible from another of your applications) set the group permissions of the source file to execute (x) and the world access to none before compilation. For a public application, ensure that start.cmd and stop.cmd have world execute permission.
The application compiler applib compiles all the application files into one application library. When the library is created, the developer specifies the product name and version number of the application and whether or not the application is licensed.
The product name is used in two ways:
All applications must have start and stop command files at the top-most directory level. The Application Compiler will check that these files (start.cmd and stop.cmd) are part of the application source files when it compiles the application.
It will not produce any output if they are not present.
The presence of an auxiliary button macro (button.cmd) will be recorded in the library file header. If present, the Fire applications command will display the auxiliary button when the applications menu is presented.
Fire application files which are intended for deployment as browser-based or ActiveX components are run under the control of an application manager known as WAM. Such applications (.fsa files) are invoked via a Fire appstart command. There are guidelines for writing such applications outlined in Building An Application.
Applications files can also be run independent of WAM. This method is for developers who not wish to deploy them as web applications or ActiveX controls. We shall refer to such applications (.mxa files) as non-WAM.
Following some simple rules and guidelines will ensure that application source files will be able to be run un-modified when compiled into an application library.
There are some mandatory rules:
In addition, for applications which are to be deployed under WAM, the following rules also apply:
The following guidelines will enable the application to run in both source and compiled form without modification:
The Application Compiler inserts files into the application library so that when the application is started, the member files of the library appear as though mounted under the virtual application mount point "@". Each member file can be referenced using its absolute mounted name which will be @product_name/filename. The product_name part of the path will be taken from the product_name specified when the application was compiled. Fire provides the facility to switch between compiled applications and application source files by converting references to @product_name/filename which cannot be resolved (because the compiled application has not been mounted) to $product_name/filename - using the environment variable product_name to locate the source files.
Application files and directories are mounted read-only. The applications should not try to create any application sub-directories at run-time. The application should not change the current directory (using the path command) to any part of the application file system.
Refer to the previous section on file access permissions. The access permissions of the library members are derived from the access permissions of the original source files. When an application is running, the end-user will have World access to the library members. Remember to grant the appropriate access to the start and stop command files to group and world, otherwise you might create an application which nobody can run!
If your application creates an application atable containing variables, symbology, etc. which may be modified by the end-user or other applications, remember to set the .access of the variable or the .def_access of the atable appropriately. In most cases, applications use application atables for private data and the default access permissions will be adequate.
It is possible for a Fire user to run, in the same session, products from more than one developer - for example a Management Information System from one developer and a Message Handling System from another. Although each application is independent of the other, it is possible that atable names or product names may conflict with each other. This problem can be avoided by each developer using a unique prefix to atable and product names. Xmarc coordinates the issue of unique prefixes (a maximum of four characters) when a developer ID is assigned to each developer.
As an example, consider a simple form of a complete non-WAM application (called myapp) which consists of start and stop command files and some sub-directories containing internal command files, installation data files, and on-line help files.
Also in the source directory is a test sub-directory which will not form part of the compiled application. The source files may reside in a sub-directory of a development source tree which, say, reflects the current version of the application.
The file start.cmd would typically contain something like the following:
# Name @myapp/start.cmd # Usage exec @myapp/start # Create application atable, data types, symbology etc. exec @myapp/cmd/definitions # Create applications windows, menus, panels etc. exec @myapp/cmd/create_windows # Wait for user input poll # End @myapp/start.cmd
During the source development phase, the developer will want Fire to run the actual source files. To achieve this, the developer will set the environment variable MYAPP to point to the root of the application source files. In a Unix C-Shell development environment this might be:
setenv MYAPP /disk/users/dev_src/myapp_v1
For Windows it might be:
set MYAPP=c:\dev_src\myapp_v1
In this case, when Fire tries to locate the file @myapp/cmd/definitions.cmd, and finds that no application library has been mounted, it will convert the file name to $MYAPP/cmd/definitions.cmd and resolve the name through the environment name setting.
On Unix systems, the Unix make utility is recommended to control creation and maintenance of application libraries.
An example Makefile is shown below:
# @myapp/Makefile # Creates the application archive library. # These define the product name and version number for>license control PRODUCT=myapp RELEASE=1 VERSION=01 # The patch number can be checked using the Unix "what" command PATCH=00 # This defines the directory where the library file will be created. DESTDIR=/home/acme/product/distribution # Define the source file set. FILES=*.cmd cmd/* help/* install/templates/* install/data/* # The dependency of the library on the source files and # the "make" instructions ... ${DESTDIR}/myapp.mxa: ${FILES} Makefile chmod a+x start.cmd stop.cmd applib -c $@ \ -p ${PRODUCT} -v ${RELEASE}.${VERSION}.${PATCH} \ -d "ACME Map Management System" ${FILES} # Create a summary listing of the application library ... applib -q -t $@ what $@ # End @myapp/Makefile
The result of this make
file will be a compiled application library myapp.mxa.
For WAM deployed applications, the extension .fsa should be used instead of .mxa.
Without the use of a makefile, the applib utility can be used in a simple shell script to produce an application file.
Consider the following example to build a WAM application:
applib -c myapp.fsa -p myapp -v 1.0 -P -d "Test Application" -l filelist.txt
In this example, the application file (myapp.fsa) is created "privileged" (discussed later) via the -P switch, and the files making up the archive are specified in a text file (filelist.txt).
Compiled application libraries are normally installed in the site-specific application library directory which the program locates using the environment variable MXAPP. In addition, the program looks at the file mxapps.def (first in the current, then $HOME, then $MXSITE directories) for definitions of applications which have been installed, and from this creates a menu of applications when either the "applications" command is issued or the Fire applications button in the monitor window is clicked.
Compiled applications are started by either selecting the application from the Fire applications menu or by issuing the command:
start <application_name>
In the above example, this would be:
start myapp
This is equivalent to issuing the commands:
mount $MXAPP/myapp.mxa exec @myapp/start
which will mount all application library members on the "@" application mountpoint, and then invoke the application start procedure. At this point all the member files of the application library will be accessible via the mounted application root @myapp.
Similar to starting the application, it may be stopped using the Fire applications menubutton or by issuing the command
stop <application_name>
for our example this would be:
stop myapp
which is equivalent to the commands:
exec @myapp/stop unmount @myapp
Most applications will provide their own option/menu button to stop the application. Once the application has been unmounted, its member files will no longer be accessible.
The Application Compiler provides the facility for a developer to make use of the Fire licensing system to control access to a compiled application. Specifying that the compiled application is licensed will result in Fire requiring a license for both the application and a Fire run-time license when the application is started. If the licenses for either the application or the Fire run-time are not present in the end-user’s license database the application will terminate. The license for the application (a set of license keys for the named product and version number) is issued by the developer using the application license code generating utility appgen. The Fire run-time license is issued by Xmarc Ltd and is a prerequisite for any licensed application.
License keys are generated (whether by Xmarc or by developers using appgen) for a particular product name and version number of that product. The product and version number are recorded in the application library when it is created. When license keys are issued for the product/version combination, they are valid only for the specified product and for the specified version number or earlier - they will not be valid for any later (higher) version number of the product.
License keys for both the application and the run-time are installed into the end-user’s license database in the same way as Fire licenses.
A Fire run-time license is required in order to run any licensed application. These are issued by Xmarc. The product name of the run-time license is "mx/rt". Only one Fire run-time license is required per user per session regardless of the number of applications the user is running.
Fire provides the facility to compile a demonstration application. Such applications have an embedded expiration date in the application library file and, when started, do not require any licenses to run up to the expiration date. After the expiration date, the application will not run at all. The expiration date of the demonstration application is derived from the expiration date of the mxdemo license issued periodically to holders of the Fire Application Compiler license. To create a demonstration application library the -D switch is used with the applib command. For example:
applib -D -c $MXAPP/myapp.mxa -p myapp -v 1.1 *.cmd help cmd install
. . . will create a demonstration version of the example application. The expiration date will be obtained from the expiration date of the mxdemo license in the developer's license database.
In addition to licensed and demonstration applications, a developer may create an unlicensed application library. An unlicensed application library does not require any license codes BUT it can only be started by a licensed application created by the same developer. The principal aim in creating unlicensed application libraries is to create reusable sub-modules which can be combined to make end-user applications without the administrative overhead of having to license each and every sub-module within the final application. Once an unlicensed application is mounted it can be considered an extension of the licensed application and as such is considered a licensed application which in turn can start other unlicensed applications.
To create an unlicensed application, the -u switch is used with the applib command. For example:
applib -u -c $MXAPP/myapp.mxa -p myapp -v 1.1 *.cmd help cmd install
To check if an application library started successfully you would include the following code fragment within your application code.
start myapp unless (aexist(myapp)) { tell -err,'Could not start myapp' exit }
A privileged application is one which any Fire user can run. They do not need any licences at all, just a copy of Fire. WAM applications are examples of privileged applications. To create a privileged application, a user must have an mxprivileged licence, available from Xmarc.
To create an unlicensed application, the -P switch is used with the applib command. For example:
applib -p -c $MXAPP/myapp.mxa -P myapp -v 1.1 *.cmd help cmd install
When testing an application under development, the application developer can easily switch between running the original source files and the compiled application. However, when running the compiled application on the development system, you should be aware that this environment will be slightly different from the environment when the application is run at the end-user’s site. These differences are:
When the compiled application is started on the developer’s system, Fire will determine (via the developer ID embedded in the developer’s mxappdev license) that the application user - in this case the developer - is the application owner. In this case Fire will not look for an application and run-time license.
Because the application user is deemed to be the application owner, the application user will have owner access to the application member files (at least read access) and also owner access to all application atables and variables in them.
Testing a compiled application under the above circumstances can obscure the fact that at the end-user’s site the following will apply:
For licensedapplications, Fire will require both an application license and a run-time license - otherwise it will not run at all.
The application user will be allowed world access to the application library member files and world access to the application atables and variables in them.
The Fire capability command allows the application developer to simulate the license capability of the prospective end-user. The command allows the developer to simulate:
Refer to the Fire Reference Manualfor full details of the capability command.
An example of using the capability command to test the licensed application myapp might be as follows:
capability; # Simulate a user with no licenses. start myapp; # Check application requires licenses! capability runtime; # Simulate a user with only a run-time license start myapp; # Should fail because myapp license missing. capability runtime,myapp; # Simulate both runtime and myapp licenses. start myapp; # Should run OK. capability reset; # Restore development licenses.
The utility appgen is used by the developer to generate license codes for licensed applications. appgen takes as input the product name, product version number, details of the host at the end-user’s site, number of concurrent users, expiration date information and generates license keys which are then installed into the end-user’s license database using the Fire license file management utility licman.
appgen may be run interactively - where it prompts for its input from the user terminal and prints out the license keys - or as a server - where it reads a single command line from its stdin and outputs a single response to its stdout. Running appgenin its server mode enables it to be easily driven by a Fire application which the developer could use to integrate license code generation with accounting databases.
Refer to the Fire Reference Manual for full details of the appgen utility.