Ximage

New Commands


Startup Order

When adding new commands or modifying existing commands in XIMAGE, it is important to realize the order in which commands and variables are defined in the Tcl environment. On startup, command definition occurs in the following order:
  1. Internal C-based ximage commands are loaded
  2. Internal FORTRAN-based ximage commands are loaded
  3. $XANADU/image/ximage/manager/ximage.tcl is sourced
    1. $XANADU/image/ximage/tcl/*.tcl files are sourced
    2. If it exists, ~/.ximagerc is sourced
      • Recommended for global setting and aliases
    3. ~/.ximage/*.tcl files are sourced
      • Note: if enviromental variable XIMAGE_HOME is set, $XIMAGE_HOME/*.tcl files will be sourced instead
      • Recommended for user-defined commands and their associated pfiles

Tcl Commands

Implementing a new XIMAGE Tcl command requires the following steps:

1. Write Tcl proc of form:

Source: newcmd.tcl

proc newcmd {args} {

   parseparm [parmloc newcmd] $args

   if { $cmdargc != 0 } {
      txwrite " Wrong number of arguments: $cmdargv" 10
      error {}
   }
#
#  This is just an example where the command takes no arguments
#  command usage -> command parameter=value parameter=value argument
#  The arguments are stored in a Tcl list called cmdargv, 
#  and the number of arguments is stored in cmdargc
#
#  For example:
#   command parm1=parval1 parm2=parval2 arg1 arg2
#
#  txwrite "   numargs: $cmdargc" 10
#  txwrite "   first: [lindex $cmdargv 0]" 10
#  txwrite "   second: [lindex $cmdargv 1]" 10
#
#  Would print:
#   numargs: 2
#   first: arg1
#   second: arg2
#  
#
#  Retrieve parameters
#
#  Unlike FORTRAN and C routines, Tcl determines data types on
#  the fly, so there is no need for routines that retrieve
#  the parameter values. The parseparm proc creates a parval
#  array which contains the values for all parameters.
#
   set logpar $parval(logpar)
   set strpar $parval(strpar)
   set intpar $parval(intpar)
   set realpar $parval(realpar)
   set dblpar $parval(dblpar)
   set listpar $parval(listpar)
#
#  Command body
#

}
2. Copy file containing Tcl proc to the tcl directory

The file containing the Tcl proc should end in .tcl, and be located in $XANADU/image/ximage/tcl. Note: Tcl commands may also be defined outside of the XIMAGE installation in the user's ~/.ximage directory or the directory defined by the XIMAGE_HOME environmental variable.

3. Create a parameter file for the pfiles directory

See Parameter Files. Note: If a Tcl command resides in ~/.ximage or where XIMAGE_HOME specifies, the parameter files must be there as well.

FORTRAN Commands

Implementing a new XIMAGE FORTRAN command requires the following steps:

1. Add new command name to src/cmd/fcmd.h

The fcmd array defined in this C include file lists all the commands that are implemented in FORTRAN. It is used at startup to link the listed command names with the C routine in src/cmd/procfcmd.c which calls the FORTRAN routine in src/cmd/ximcmd.f.

2. Add test for new command to src/cmd/ximcmd.f

For example:

c
c  New command comments
c
      elseif ( command.eq.'NEWCMD' ) then
         call newcmd(cmdid,status)
All FORTRAN-based commands are routed through this routine. It performs the same function as the FORTRAN program main (ximage.f) from pre-4.0 versions.

Note the cmdid variable. This is an index which communicates the location of the data structure which holds all the parameter information. Command writers need not be concerned with its value, however it is imperative that cmdid be the first argument of the routine which defines the command. Its value is needed by the parameter parsing routines (gpar[lsri]), which replace the qlf0[lsri] routines.

3. Write routine of form:

Source: newcmd.f

      subroutine newcmd(Cmdid,Status)
      implicit none
c
c  Comments here
c
c  I  cmdid        (i) Command id
c  O  status       (i) Error flag (0=OK)
c
      integer Cmdid, Status
c
c  Local variables
c
      logical logpar
      character*100 strpar
      integer intpar, listnum, listmax
      parameter(listmax = 100)
      real*4 realpar, listary(listmax)
      real*8 dblpar

      Status = 0
c
c Check number of arguments here
c
c  Note: wrongargs prints arguments which are unaccounted 
c        for and sets status to -1
c
      call numcarg(cmdid,argc,status)
      if ( argc.ne.0 ) wrongargs(cmdid, status)
c
c  This is just an example where the command takes no arguments
c  command usage -> command parameter=value parameter=value argument
c  A couple of options are available for retrieving arguments:
c
c  Returns next argument as string
c     call nextcarg(cmdid, argument, MAX_STRLEN, status)
c 
c  Returns concatenation of all remaining arguments
c     call catcarg(cmdid, therest, MAX_STRLEN, Status)
c   
c
c  Retrieve parameters
c
      CALL GPARL(Cmdid,'LOGPAR',logpar,status)
      CALL GPARS(Cmdid,'STRPAR',strpar,status)
      CALL GPARI(Cmdid,'INTPAR',intpar,status)
      CALL GPARR(Cmdid,'REALPAR',realpar,status)
      CALL GPARD(Cmdid,'DBLPAR',dblpar,status)
      CALL GPARLR(Cmdid,'LISTPAR',listary,listnum,listmax,status)
      if ( status.ne.0 ) return
c
c  Command body
c
      return
      end

4. Create a parameter file for the pfiles directory

See Parameter Files

C Commands

Implementing a new XIMAGE C command requires the following steps:

1. Add new command name to ccmd array in src/cmd/ccmd.h

The ccmd array defined in this C include file lists all the commands that are implemented in C.

2. Add routine name for new command to ccmdfnc array also in src/cmd/ccmd.h

The position of the command name in the ccmd array and routine name in the ccmdfnc array should match up. At startup, each command name will be linked to its corresponding routine implemented in C.

3. Write routine of form:

Source: newcmd.c


#include <stdlib.h>
#include <stdio.h>
#include <string.h>

#include "../include/xcommon.h"
#include "../include/xmtcl.h"
#include "../include/cmddef.h"

#define STRMAX 256
#define LISTMAX 100

/*
 * newcmd --
 * Command description
 */
int
newcmd(ClientData cdata,Tcl_Interp* interp,int objc, Tcl_Obj* CONST objv[] )
{
   int status;
   cmddef *curcmd;
   pardef *parlist;

   int logpar, intpar, listnum;
   char strpar[STRMAX];
   float realpar, listary[LISTMAX];
   double dblpar;

   curcmd = cdata;
   status = 0;

   if ( !CParseParm(interp, objc, objv, curcmd) ) {
      return TCL_ERROR;
   }
   parlist = curcmd->parlist;
/*
 * Check number of arguments here
 *
 *  cwrongargs prints arguments which are unaccounted for
 */
   if ( curcmd->cmdargc != 0 ) {
      cwrongargs(curcmd->cmdargs);
      return TCL_ERROR;
   }
/*
 *  This is just an example where the command takes no arguments
 *  command usage -> command parameter=value parameter=value argument
 *  The arguments are available as strings in the linked list, 
 *  curcmd->cmdargs.
 *
 *  Tcl provides routines for getting the proper type.  Take the
 *  following example, which assigns the three arguments to a
 *  double array.
 *
 *  See the online manual for Tcl for other object-based routines:
 *  http://dev.scriptics.com/man/
 *  (Use command "puts $tcl_patchLevel" in ximage to determine version)
 *
 *  int i;
 *  double dbl[3];
 *  Tcl_Obj *tmpObj;
 *  argdef *curarg;
 
 *  curarg = curcmd->cmdargs;
 *  i = 0;
 *  while ( curarg ) {
 *     tmpObj = Tcl_NewStringObj(curarg->name, -1);
 *     Tcl_GetDoubleFromObj(xm_interp, tmpObj, &dbl[i]);
 *     curarg = curarg->next;
 *     i++;
 *  }
 */

   cgparl(parlist, "LOGPAR", &logpar, &status);
   cgpars(parlist, "STRPAR", strpar, STRMAX, &status);
   cgpari(parlist, "INTPAR", &intpar, &status);
   cgparr(parlist, "REALPAR", &realpar, &status);
   cgpard(parlist, "DBLPAR", &dblpar, &status);
   cgparlr(parlist, "LISTPAR", listary, &listnum, LISTMAX, &status);

/*
 *  Command body
 */

   if ( status != 0 ) { return TCL_ERROR; }
   return TCL_OK;
}
4. Create a parameter file for the pfiles directory

See Parameter Files

Parameter Files

All commands in XIMAGE which use the syntax "command parameter=value" require a parameter file. These files bear the extension .par and are located in $XANADU/image/ximage/pfiles

Parameter files are of the following format:

Source: newcmd.par

#
#  Parameters for newcmd
#
logpar,b,a,no,,,"Logical parameter[y/n]?"
strpar,s,a,,,,"String parameter"
intpar,i,a,,,,"Integer parameter"
realpar,r,a,,,,"Real parameter"
dblpar,r,a,,,,"Double parameter"
listpar,s,a,,,,"List parameter"
#mode,s,h,"h",,,""
Note that parameter files use 'b' for boolean rather than 'l' for logical. Also, internally 'r' parameters are stored as doubles. The usage of GPARR and GPARD just determines what type you would like returned in FORTRAN.

Also, there is a special type which allows the retrieval of a list of real numbers delimited by spaces. In the parameter file, the string type is used, however, when GPARLR is called from FORTRAN, an array of reals is returned.

If you are familiar with parameter files, the default behavior of 'a' mode is 'h' or hidden mode. It is possible to make parameters behave similar to ftool arguments by giving them a 'q' mode. Each 'q' parameter will claim free arguments in the order that they appear in the parameter file. For example,

#
#  Parameters for othercmd
#
infile,s,q,,,,"Input file"
outfile,s,q,,,,"Output file"
mode,i,a,,,,"Mode"
The following are equivalent:
othercmd mode=1 data.fits result.fits
othercmd mode=1 infile=data.fits outfile=result.fits
Unlike ftools, parameters are never queried or learned. Also, notice that the mode parameter doesn't have any special meaning like in ftools where 'a' modes are replaced with the value for the mode parameter. This was done because an existing command had a 'mode' parameter, and that behavior was unnecessary for ximage anyway.


Ximage Home Page Xanadu Home Page Xanadu ftp site

Please send reports of errors to : xanprob@athena.gsfc.nasa.gov
HEASARC Home | Observatories | Archive | Calibration | Software | Tools | Students/Teachers/Public

Last modified: Wednesday, 29-Mar-2006 14:32:37 EST