<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://pickwiki.org/index.php?action=history&amp;feed=atom&amp;title=UdtService</id>
	<title>UdtService - Revision history</title>
	<link rel="self" type="application/atom+xml" href="https://pickwiki.org/index.php?action=history&amp;feed=atom&amp;title=UdtService"/>
	<link rel="alternate" type="text/html" href="https://pickwiki.org/index.php?title=UdtService&amp;action=history"/>
	<updated>2026-04-28T22:25:07Z</updated>
	<subtitle>Revision history for this page on the wiki</subtitle>
	<generator>MediaWiki 1.43.0</generator>
	<entry>
		<id>https://pickwiki.org/index.php?title=UdtService&amp;diff=2340&amp;oldid=prev</id>
		<title>Conversion script: link fix</title>
		<link rel="alternate" type="text/html" href="https://pickwiki.org/index.php?title=UdtService&amp;diff=2340&amp;oldid=prev"/>
		<updated>2015-02-26T23:48:56Z</updated>

		<summary type="html">&lt;p&gt;link fix&lt;/p&gt;
&lt;p&gt;&lt;b&gt;New page&lt;/b&gt;&lt;/p&gt;&lt;div&gt;This program is designed to run as a phantom service on a UD server.  It has run successfully on D3 and currently runs on UD.  This routine needs one file to run, (DTASERVICES).  I&amp;#039;m not a very good programmer so if anyone has suggestions to improve this code, please let me know by posting onto the U2 mail list.&lt;br /&gt;
&lt;br /&gt;
The general idea of this process is to start a service as a phantom within U2.  Then, every minute, wake up, read the services file to see if a service needs to be run, if it does phantom that, then go back to sleep.  This following file contains the defined service and looks like:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;PRE&amp;gt;&lt;br /&gt;
Dictionary of File: DTASERVICES                                                        10:15:38 Jun 27 2007&lt;br /&gt;
Dict Name...... Typ # Col-Heading. Field-Definition.............. Conversion............... Formt Assoc...&lt;br /&gt;
&lt;br /&gt;
@UQ             Phr                USER CDATE ACCOUNT COMMANDS &lt;br /&gt;
                                   OKTORUN OPTIONS&lt;br /&gt;
@ID             D 0   SERVICES                                                              12L   S&lt;br /&gt;
USER            D 1   USER                                                                  10L   S&lt;br /&gt;
DATETIME        D 2   CREATED                                                               12L   S&lt;br /&gt;
ACCOUNT         D 3   ACCOUNT                                                               12L   S&lt;br /&gt;
PASSWORD        D 4   PASSWORD                                                              12L   S&lt;br /&gt;
COMMANDS        D 5   COMMAND(S)                                                            17L   S&lt;br /&gt;
CRON            D 6   CRON                                                                  5L    M&lt;br /&gt;
DESC            D 7   DESC                                                                  30L   S&lt;br /&gt;
OKTORUN         D 8   OK                                                                    1R    S&lt;br /&gt;
OPTIONS         D 9   OPTIONS                                                               10L   S&lt;br /&gt;
JOBSID          D 10  JOBSID                                                                12L   S&lt;br /&gt;
STATUS          D 11  STATUS                                                                30L   S&lt;br /&gt;
CAPTURE         D 12  CAPTURE                                                               30L   M&lt;br /&gt;
CDATE           I     CDATE        EXTRACT(@RECORD, 2, 0, 0)[1,5] D2                        9R    S&lt;br /&gt;
CTIME           I     CTIME        EXTRACT(@RECORD, 2, 0, 0)[6,5] MTH                       7R    S&lt;br /&gt;
&amp;lt;/PRE&amp;gt;&lt;br /&gt;
&lt;br /&gt;
A record in this file would look like:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;PRE&amp;gt;&lt;br /&gt;
Top of &amp;quot;[[CABFTP_HAM]]&amp;quot; in &amp;quot;DTASERVICES&amp;quot;, 12 lines, 268 characters.&lt;br /&gt;
*--: P&lt;br /&gt;
001: wph&lt;br /&gt;
002: 1432900782&lt;br /&gt;
003: E:\UDAccounts\Ham&lt;br /&gt;
004:&lt;br /&gt;
005: RUN DTABP TRINFO.CAB FTP&lt;br /&gt;
006: 00&lt;br /&gt;
     22&lt;br /&gt;
     *&lt;br /&gt;
     *&lt;br /&gt;
     5&lt;br /&gt;
007: The Local Community Bank Ftp process&lt;br /&gt;
008: 1&lt;br /&gt;
009:&lt;br /&gt;
010: command&lt;br /&gt;
011: Process last run at 22:00:00 Jun 22 2007&lt;br /&gt;
012: The command completed successfully.&lt;br /&gt;
     PHANTOM Process  3184 started.&lt;br /&gt;
     COMO file is&amp;#039;_PH_\dtaservices79200_3184&amp;#039;.&lt;br /&gt;
Bottom.&lt;br /&gt;
*--:&lt;br /&gt;
&amp;lt;/PRE&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The service program has several includes in it.  These includes are used throughout our application to setup common variables, open a couple of files, and initialize variables.  An example of one of the variables initialized is PATHSEP$.  This variable is a &amp;amp;quot;/&amp;amp;quot; in .nix and a &amp;amp;quot;\&amp;amp;quot; in Windows.  Other general variables are NULL$ (empty string), HLDMSG (a common message variable), WKAMT (a common scratch variable), and a few others.  Two subroutine calls are to &amp;quot;LOGMSG&amp;quot; (a centralized logging subroutine) and &amp;quot;SERVICE.ISRUNNING&amp;quot;, which is a subroutine that looks like:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;PRE&amp;gt;&lt;br /&gt;
SUBROUTINE SERVICE.ISRUNNING ([[ServiceName]], [[IsRunning]])&lt;br /&gt;
** [[DataTrust]] phantom service manager&lt;br /&gt;
** (C) Copyright 1985-2007, Advantos Systems, Inc.  All Rights Reserved.&lt;br /&gt;
!&lt;br /&gt;
** Last Modified: 08 Feb 2007, wph&lt;br /&gt;
** First Created: 28 Sep 2004, wph&lt;br /&gt;
** Program Type-: Utility&lt;br /&gt;
!&lt;br /&gt;
** Notes:&lt;br /&gt;
**&lt;br /&gt;
** This subroutine tests if a particular service is running in the&lt;br /&gt;
** mvDbms environment.&lt;br /&gt;
**&lt;br /&gt;
** Input-:&lt;br /&gt;
**   [[ServiceName]] - the name of the service to test for&lt;br /&gt;
**&lt;br /&gt;
** Output:&lt;br /&gt;
**   [[IsRunning]]   - is the service running? 0-No, 1-Yes&lt;br /&gt;
**&lt;br /&gt;
** it is read from the DTA,SYSTBL, as the default.&lt;br /&gt;
**&lt;br /&gt;
**-------------------------------------------------------------------**&lt;br /&gt;
**                                                                   **&lt;br /&gt;
**                    I N I T I A L I Z A T I O N                    **&lt;br /&gt;
**                                                                   **&lt;br /&gt;
**-------------------------------------------------------------------**&lt;br /&gt;
*&lt;br /&gt;
** Initialization&lt;br /&gt;
INCLUDE DTABP,INCLUDES SET.COMMON&lt;br /&gt;
*&lt;br /&gt;
[[IsRunning]] = 0              ; ** initialize progress cnt&lt;br /&gt;
*&lt;br /&gt;
**------------------------------------------------------------------**&lt;br /&gt;
**                                                                  **&lt;br /&gt;
**                 S T A R T   P R O G R A M   R U N                **&lt;br /&gt;
**                                                                  **&lt;br /&gt;
**------------------------------------------------------------------**&lt;br /&gt;
*&lt;br /&gt;
** Test if service is running&lt;br /&gt;
*[[TclCmd]]  = \COUNT JOBS WITH TCL-COMMAND = &amp;quot;[\      ; ** D3 version&lt;br /&gt;
*[[TclCmd]] :=  [[ServiceName]] : \]&amp;quot;\                     ; ** D3 version&lt;br /&gt;
*[[TclCmd]] := \ AND WITH A1 = &amp;quot;R&amp;quot;\                    ; ** D3 version&lt;br /&gt;
*EXECUTE [[TclCmd]] CAPTURING Output                   ; ** D3 version&lt;br /&gt;
*&lt;br /&gt;
** Extract count from captured output&lt;br /&gt;
*[[ItemCount]] = FIELD(TRIM(Output), SP1, 2)           ; ** D3 version&lt;br /&gt;
*IF NOT(NUM([[ItemCount]])) THEN [[ItemCount]] = 0         ; ** D3 version&lt;br /&gt;
*IF [[ItemCount]] THEN [[IsRunning]] = 1                   ; ** D3 version&lt;br /&gt;
*&lt;br /&gt;
IF [[ServiceName]] = &amp;#039;DTA.SERVICE&amp;#039; THEN                           ; ** UD version&lt;br /&gt;
   [[PhPortID]] = OCONV(&amp;#039;DTA.SERVICE&amp;#039;, &amp;#039;TDICT DTASERVICES;X;;2&amp;#039;)  ; ** UD version&lt;br /&gt;
   [[PhIDLoc]]  = COUNT([[PhPortID]], PATHSEP$) + 1                   ; ** UD version&lt;br /&gt;
   [[PhPortID]] = TRIM(FIELD([[PhPortID]], PATHSEP$, [[PhIDLoc]]))        ; ** UD version&lt;br /&gt;
   [[PhPortID]] = FIELD([[PhPortID]], &amp;#039;_&amp;#039;, 2)                         ; ** UD version&lt;br /&gt;
END ELSE                                                      ; ** UD version&lt;br /&gt;
   [[PhPortID]] = OCONV([[ServiceName]], &amp;#039;TDTASERVICES;X2;;10&amp;#039;)       ; ** UD version&lt;br /&gt;
END                                                           ; ** UD version&lt;br /&gt;
IF [[PhPortID]] NE NULL$ THEN                                     ; ** UD version&lt;br /&gt;
   EXECUTE \PORT.STATUS PID \ : [[PhPortID]] CAPTURING OUTPUT     ; ** UD version&lt;br /&gt;
   IF TRIM(OUTPUT&amp;lt;7&amp;gt;) NE NULL$ THEN [[IsRunning]] = 1             ; ** UD version&lt;br /&gt;
END                                                           ; ** UD version&lt;br /&gt;
*&lt;br /&gt;
**------------------------------------------------------------------**&lt;br /&gt;
**                                                                  **&lt;br /&gt;
**                    E N D   O F   P R O G R A M                   **&lt;br /&gt;
**                                                                  **&lt;br /&gt;
**------------------------------------------------------------------**&lt;br /&gt;
*&lt;br /&gt;
***************&lt;br /&gt;
END.OF.PROGRAM:&lt;br /&gt;
***************&lt;br /&gt;
*&lt;br /&gt;
RETURN&lt;br /&gt;
END&lt;br /&gt;
&amp;lt;/PRE&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This service manager needs to be started when the dbms starts.  In D3, this was very simple as &amp;quot;RUN DTABP DTA.SERVICE&amp;quot; only had to be added to the &amp;quot;dm,, user-coldstart&amp;quot; macro.  In U2, however, it&amp;#039;s much more complex and I end up having to start it manually every time I restart UD (fortunately, this isn&amp;#039;t too often).&lt;br /&gt;
&lt;br /&gt;
&amp;lt;PRE&amp;gt;&lt;br /&gt;
!&lt;br /&gt;
** [[DataTrust]] phantom service manager&lt;br /&gt;
** (C) Copyright 1985-2007, Advantos Systems, Inc.  All Rights Reserved.&lt;br /&gt;
!&lt;br /&gt;
** Last Modified: 21 Jun 2007, wph&lt;br /&gt;
** First Created: 24 Sep 2004, wph&lt;br /&gt;
** Program Type-: Utility&lt;br /&gt;
!&lt;br /&gt;
** Notes:&lt;br /&gt;
**&lt;br /&gt;
** This process runs and phantoms any (SERVICES) entry specified.  It&lt;br /&gt;
** wakes up every minute (on the minute) and checks if a job should&lt;br /&gt;
** be started.  If so, it does.  Then it goes back to sleep.&lt;br /&gt;
**&lt;br /&gt;
** The meaning and format of the Cron field in the (SERVICES) file&lt;br /&gt;
** is as follows:&lt;br /&gt;
**    1 - Minute    0-59&lt;br /&gt;
**    2 - Hour      0-23 (0=midnight)&lt;br /&gt;
**    3 - Day       1-31&lt;br /&gt;
**    4 - Month     1-12&lt;br /&gt;
**    5 - Weekday   0-6  (0=Sunday)&lt;br /&gt;
**&lt;br /&gt;
** When this service starts it updates the DICT item in (DTASERVICES)&lt;br /&gt;
** named &amp;quot;DTA.SERVICE&amp;quot;, with a &amp;quot;1&amp;quot; in field# 1, the _PH_ item in field#&lt;br /&gt;
** 2, and the time/date started in field# 3.  It looks like:&lt;br /&gt;
**&lt;br /&gt;
** &amp;#039;DTA.SERVICE&amp;#039;&lt;br /&gt;
** 001: 1&lt;br /&gt;
** 002: _PH_\wphaskett51560_3884&lt;br /&gt;
** 003: 16:16:00 Jan 08 2007&lt;br /&gt;
**&lt;br /&gt;
** In order to terminate this program, simply change field# 1 to &amp;quot;0&amp;quot;.&lt;br /&gt;
**&lt;br /&gt;
** This process should be started from within the USER-COLDSTART, or&lt;br /&gt;
** from the &amp;#039;DM&amp;#039; account, in D3.&lt;br /&gt;
**&lt;br /&gt;
**-------------------------------------------------------------------**&lt;br /&gt;
**                                                                   **&lt;br /&gt;
**                    I N I T I A L I Z A T I O N                    **&lt;br /&gt;
**                                                                   **&lt;br /&gt;
**-------------------------------------------------------------------**&lt;br /&gt;
*&lt;br /&gt;
CRT &amp;quot;...DTA.SERVICE is now starting at &amp;quot; : TIMEDATE() : &amp;quot;...&amp;quot;&lt;br /&gt;
*&lt;br /&gt;
** Initialization&lt;br /&gt;
INCLUDE DTABP,INCLUDES SET.COMMON&lt;br /&gt;
INCLUDE DTABP,INCLUDES SET.FILES&lt;br /&gt;
INCLUDE DTABP,INCLUDES SET.INIT&lt;br /&gt;
*&lt;br /&gt;
[[DisplayCnt]] = 0              ; ** initialize progress cnt&lt;br /&gt;
*&lt;br /&gt;
** assign phantom command&lt;br /&gt;
[[JobsName]]   = &amp;#039;_PH_&amp;#039;         ; ** UD version&lt;br /&gt;
[[PhantomCmd]] = &amp;#039;PHANTOM &amp;#039;     ; ** U2 version&lt;br /&gt;
*[[PhantomCmd]] = &amp;#039;Z&amp;#039;            ; ** D3 version&lt;br /&gt;
*[[JobsName]]   = &amp;#039;JOBS&amp;#039;         ; ** D3 version&lt;br /&gt;
*&lt;br /&gt;
** # of seconds to divide into the current time.  The remainder is&lt;br /&gt;
** subtracted from the sleep time to determine exactly for how long&lt;br /&gt;
** the process must sleep for to wake up right on the proper time.&lt;br /&gt;
** Don&amp;#039;t set for less than a 60 seconds, as this process CANNOT&lt;br /&gt;
** run at less than a 60 second interval.&lt;br /&gt;
[[SleepValue]] = 60&lt;br /&gt;
*&lt;br /&gt;
** Open File(s)&lt;br /&gt;
[[FileErr]]  = NULL$&lt;br /&gt;
OPEN &amp;#039;DICT&amp;#039;, &amp;#039;DTASERVICES&amp;#039; TO DTASERVICES.D ELSE [[FileErr]] := &amp;#039; Dict DTASERVICES&amp;#039;&lt;br /&gt;
OPEN     &amp;#039;&amp;#039;, &amp;#039;DTASERVICES&amp;#039; TO DTASERVICES   ELSE [[FileErr]] := &amp;#039; DTASERVICES&amp;#039;&lt;br /&gt;
OPEN     &amp;#039;&amp;#039;, [[JobsName]]      TO JOBS.FV       ELSE [[FileErr]] := SP1:[[JobsName]]&lt;br /&gt;
IF [[FileErr]] NE NULL$ THEN&lt;br /&gt;
   HLDMSG = &amp;quot;No file(s):&amp;quot; : [[FileErr]]&lt;br /&gt;
   GOTO ABORT.PROGRAM&lt;br /&gt;
END&lt;br /&gt;
*&lt;br /&gt;
**-------------------------------------------------------------------**&lt;br /&gt;
**                                                                   **&lt;br /&gt;
**           R E A D   C O N F I G U R A T I O N   D A T A           **&lt;br /&gt;
**                                                                   **&lt;br /&gt;
**-------------------------------------------------------------------**&lt;br /&gt;
*&lt;br /&gt;
** synchronize mvDbms service status with [[DataTrust]] service flag&lt;br /&gt;
[[PhantomID]] = SYSTEM(48)                                  ; ** UD version&lt;br /&gt;
[[IsRunning]] = NULL$&lt;br /&gt;
CALL SERVICE.ISRUNNING (&amp;#039;DTA.SERVICE&amp;#039;, [[IsRunning]])&lt;br /&gt;
READU [[ServiceRec]] FROM DTASERVICES.D, &amp;#039;DTA.SERVICE&amp;#039; THEN&lt;br /&gt;
   [[ServiceRun]] = TRIM([[ServiceRec]]&amp;lt;1&amp;gt;)&lt;br /&gt;
   [[PhantomID]]  = TRIM([[ServiceRec]]&amp;lt;2&amp;gt;)&lt;br /&gt;
   [[PhIDLoc]]    = COUNT([[PhantomID]], PATHSEP$) + 1&lt;br /&gt;
   [[PhantomID]]  = TRIM(FIELD([[PhantomID]], PATHSEP$, [[PhIDLoc]]))&lt;br /&gt;
   IF NOT([[IsRunning]]) THEN&lt;br /&gt;
      HLDMSG = &amp;quot;[[DataTrust]] service manager flag deleted because service not running.&amp;quot;&lt;br /&gt;
      CALL LOGMSG (&amp;#039;&amp;#039;, &amp;#039;N[[/A]]&amp;#039;, HLDMSG, &amp;#039;&amp;#039;)&lt;br /&gt;
      DELETE DTASERVICES.D, &amp;#039;DTA.SERVICE&amp;#039;&lt;br /&gt;
      IF [[PhantomID]] NE NULL$ THEN                        ; ** UD version&lt;br /&gt;
         DELETE JOBS.FV, [[PhantomID]]                      ; ** UD version&lt;br /&gt;
      END                                               ; ** UD version&lt;br /&gt;
   END ELSE&lt;br /&gt;
      RELEASE DTASERVICES.D, &amp;#039;DTA.SERVICE&amp;#039;&lt;br /&gt;
   END&lt;br /&gt;
END ELSE&lt;br /&gt;
   [[ServiceRec]] = NULL$&lt;br /&gt;
   IF [[IsRunning]] THEN&lt;br /&gt;
      HLDMSG = &amp;quot;[[DataTrust]] service manager flag created because service is running.&amp;quot;&lt;br /&gt;
      CALL LOGMSG (&amp;#039;&amp;#039;, &amp;#039;N[[/A]]&amp;#039;, HLDMSG, &amp;#039;&amp;#039;)&lt;br /&gt;
      [[ServiceRec]]&amp;lt;1&amp;gt; = 1&lt;br /&gt;
      [[ServiceRec]]&amp;lt;2&amp;gt; = SYSTEM(48)                        ; ** UD version&lt;br /&gt;
   END&lt;br /&gt;
   WRITE [[ServiceRec]] ON DTASERVICES.D, &amp;#039;DTA.SERVICE&amp;#039;&lt;br /&gt;
END&lt;br /&gt;
*&lt;br /&gt;
** log process start&lt;br /&gt;
[[SleepFor]] = [[SleepValue]] - MOD(TIME(), [[SleepValue]])&lt;br /&gt;
HLDMSG   = &amp;quot;[[DataTrust]] background service started to &amp;quot; : [[PhantomID]]&lt;br /&gt;
CALL LOGMSG (&amp;#039;&amp;#039;, &amp;#039;N[[/A]]&amp;#039;, HLDMSG, &amp;#039;&amp;#039;)&lt;br /&gt;
*&lt;br /&gt;
**-------------------------------------------------------------------**&lt;br /&gt;
**                                                                   **&lt;br /&gt;
**                 S T A R T   P R O G R A M   R U N                 **&lt;br /&gt;
**                                                                   **&lt;br /&gt;
**-------------------------------------------------------------------**&lt;br /&gt;
*&lt;br /&gt;
***************&lt;br /&gt;
START.PROGRAM:&lt;br /&gt;
***************&lt;br /&gt;
*&lt;br /&gt;
LOOP&lt;br /&gt;
*&lt;br /&gt;
** test if we should shut down the service&lt;br /&gt;
   READU [[ServiceRec]] FROM DTASERVICES.D, &amp;#039;DTA.SERVICE&amp;#039; THEN&lt;br /&gt;
      [[ServiceRun]] = TRIM([[ServiceRec]]&amp;lt;1&amp;gt;)&lt;br /&gt;
      [[PhantomID]]  = TRIM([[ServiceRec]]&amp;lt;2&amp;gt;)&lt;br /&gt;
      [[PhIDLoc]]    = COUNT([[PhantomID]], PATHSEP$) + 1&lt;br /&gt;
      [[PhantomID]]  = TRIM(FIELD([[PhantomID]], PATHSEP$, [[PhIDLoc]]))&lt;br /&gt;
      IF NOT([[ServiceRun]]) THEN&lt;br /&gt;
         HLDMSG = &amp;quot;[[DataTrust]] service manager terminated by stop flag.&amp;quot;&lt;br /&gt;
         [[ServiceRec]] = NULL$&lt;br /&gt;
         WRITE [[ServiceRec]] ON DTASERVICES.D, &amp;#039;DTA.SERVICE&amp;#039;&lt;br /&gt;
         IF [[PhantomID]] NE NULL$ THEN                ; ** UD version&lt;br /&gt;
            DELETE JOBS.FV, [[PhantomID]]              ; ** UD version&lt;br /&gt;
         END                                       ; ** UD version&lt;br /&gt;
         GOTO ABORT.PROGRAM&lt;br /&gt;
      END&lt;br /&gt;
      [[ServiceRec]]&amp;lt;3&amp;gt; = TIMEDATE()&lt;br /&gt;
      WRITE [[ServiceRec]] ON DTASERVICES.D, &amp;#039;DTA.SERVICE&amp;#039;&lt;br /&gt;
   END ELSE&lt;br /&gt;
      [[ServiceRec]]    = NULL$&lt;br /&gt;
      [[ServiceRec]]&amp;lt;1&amp;gt; = 1&lt;br /&gt;
      [[ServiceRec]]&amp;lt;2&amp;gt; = SYSTEM(48)                   ; ** UD version&lt;br /&gt;
      [[ServiceRec]]&amp;lt;3&amp;gt; = TIMEDATE()&lt;br /&gt;
      WRITE [[ServiceRec]] ON DTASERVICES.D, &amp;#039;DTA.SERVICE&amp;#039;&lt;br /&gt;
      GOTO CONTINUE.SLEEP&lt;br /&gt;
   END&lt;br /&gt;
*  &lt;br /&gt;
** select services to process&lt;br /&gt;
   [[ServiceList]] = NULL$&lt;br /&gt;
   EXECUTE \SSELECT DTASERVICES\ CAPTURING Output&lt;br /&gt;
   [[NoOfItems]]   = SYSTEM(11)&lt;br /&gt;
   IF [[NoOfItems]] THEN&lt;br /&gt;
      SELECT DTASERVICES TO [[ServiceList]]&lt;br /&gt;
   END ELSE&lt;br /&gt;
      GOTO CONTINUE.SLEEP&lt;br /&gt;
   END&lt;br /&gt;
*&lt;br /&gt;
** read services selected&lt;br /&gt;
   LOOP&lt;br /&gt;
      READNEXT [[ServiceId]] FROM [[ServiceList]] ELSE EXIT&lt;br /&gt;
      READ [[ServiceRec]] FROM DTASERVICES, [[ServiceId]] THEN&lt;br /&gt;
         [[LogToAccount]]   = TRIM([[ServiceRec]]&amp;lt;3&amp;gt;)&lt;br /&gt;
         [[LogToPassword]]  = TRIM([[ServiceRec]]&amp;lt;4&amp;gt;)&lt;br /&gt;
         [[ProgramToRun]]   = [[ServiceRec]]&amp;lt;5&amp;gt;&lt;br /&gt;
         [[CronTab]]        = [[ServiceRec]]&amp;lt;6&amp;gt;&lt;br /&gt;
         [[OkToStart]]      = [[ServiceRec]]&amp;lt;8&amp;gt; + 0&lt;br /&gt;
         [[PhantomOptions]] = [[ServiceRec]]&amp;lt;9&amp;gt;&lt;br /&gt;
         [[PhantomId]]      = [[ServiceRec]]&amp;lt;10&amp;gt;&lt;br /&gt;
*&lt;br /&gt;
** read if phantom currently running&lt;br /&gt;
         READ [[PhantomRec]] FROM JOBS.FV, [[PhantomId]] ELSE [[PhantomRec]] = NULL$&lt;br /&gt;
         [[PhStatus]] = OCONV([[PhantomRec]]&amp;lt;1&amp;gt;[1,1], &amp;#039;MCU&amp;#039;)&lt;br /&gt;
         IF [[PhStatus]] = &amp;#039;R&amp;#039; THEN&lt;br /&gt;
            HLDMSG = &amp;quot;Service &amp;quot; : [[ServiceId]] : &amp;quot; already running as job# &amp;quot; : [[PhantomId]]&lt;br /&gt;
            GOTO EXIT.CASE&lt;br /&gt;
         END&lt;br /&gt;
*&lt;br /&gt;
** assign current time&lt;br /&gt;
         setTime  = OCONV(TIME(), &amp;#039;MTS&amp;#039;)&lt;br /&gt;
         setDate  = DATE()&lt;br /&gt;
         [[CurrMon]]  = OCONV(setDate, &amp;#039;DM&amp;#039;) + 0&lt;br /&gt;
         [[CurrDom]]  = OCONV(setDate, &amp;#039;DD&amp;#039;) + 0&lt;br /&gt;
         [[CurrDow]]  = OCONV(setDate, &amp;#039;DW&amp;#039;) + 0 ; IF [[CurrDow]] = 7 THEN [[CurrDow]] = 0&lt;br /&gt;
         [[CurrHour]] = FIELD(setTime, &amp;#039;:&amp;#039;, 1) + 0&lt;br /&gt;
         [[CurrMin]]  = FIELD(setTime, &amp;#039;:&amp;#039;, 2) + 0&lt;br /&gt;
         [[CurrSec]]  = FIELD(setTime, &amp;#039;:&amp;#039;, 3) + 0&lt;br /&gt;
*&lt;br /&gt;
** test conditions to either process or abort.&lt;br /&gt;
         [[CronSkip]] = 0                     ; ** not yet time to run?&lt;br /&gt;
         [[UpdSw]]    = 0                     ; ** update services record?&lt;br /&gt;
         HLDMSG   = NULL$                 ; ** initialize error message&lt;br /&gt;
         BEGIN CASE&lt;br /&gt;
            CASE NOT([[OkToStart]])&lt;br /&gt;
               HLDMSG = &amp;quot;Service &amp;quot; : [[ServiceId]] : &amp;quot; is on Hold.&amp;quot;&lt;br /&gt;
            CASE [[CronTab]] = NULL$&lt;br /&gt;
               HLDMSG = &amp;quot;No CRON Table for Service &amp;quot; : [[ServiceId]] : &amp;quot;.&amp;quot;&lt;br /&gt;
            CASE DCOUNT([[CronTab]], @VM) NE 5&lt;br /&gt;
               HLDMSG = &amp;quot;Cron format requires five (5) values for Service &amp;quot; : [[ServiceId]] : &amp;quot;.&amp;quot;&lt;br /&gt;
*&lt;br /&gt;
** test service for starting&lt;br /&gt;
            CASE 1&lt;br /&gt;
               Minutes = [[CronTab]]&amp;lt;1,1&amp;gt;&lt;br /&gt;
               Hours   = [[CronTab]]&amp;lt;1,2&amp;gt;&lt;br /&gt;
               DOMs    = [[CronTab]]&amp;lt;1,3&amp;gt;   ; IF DOMs   = 0 THEN DOMs   = &amp;#039;*&amp;#039;&lt;br /&gt;
               Months  = [[CronTab]]&amp;lt;1,4&amp;gt;   ; IF Months = 0 THEN Months = &amp;#039;*&amp;#039;&lt;br /&gt;
               DOWs    = [[CronTab]]&amp;lt;1,5&amp;gt;   ; ** this ORs the DOMs&lt;br /&gt;
*&lt;br /&gt;
** start building actual command(s) to execute&lt;br /&gt;
               [[LogToCmd]] = NULL$          ; ** initialize cron commands&lt;br /&gt;
               IF [[LogToAccount]] NE NULL$ THEN&lt;br /&gt;
                  [[LogToCmd]] = \LOGTO \ : [[LogToAccount]]&lt;br /&gt;
                  IF [[LogToPassword]] NE NULL$ THEN&lt;br /&gt;
                     [[LogToCmd]] := &amp;#039;,&amp;#039; : [[LogToPassword]]&lt;br /&gt;
                  END&lt;br /&gt;
*&lt;br /&gt;
** add an extra @AM in [[LogTo]] command so [[D3Linux]] works.  It doesn&amp;#039;t&lt;br /&gt;
** matter for [[D3NT]].&lt;br /&gt;
*                 [[LogToCmd]] := @AM        ; ** D3 version&lt;br /&gt;
               END&lt;br /&gt;
*&lt;br /&gt;
** test if we&amp;#039;re in a configured month&lt;br /&gt;
               IF Months NE &amp;#039;*&amp;#039; THEN&lt;br /&gt;
                  [[CronVal]] = Months ; [[TestVal]] = [[CurrMon]]&lt;br /&gt;
                  [[MinVal]]  = 1      ; [[MaxVal]]  = 12&lt;br /&gt;
                  GOSUB BUILD.CRON.VALUE&lt;br /&gt;
                  IF [[CronSkip]] THEN GOTO EXIT.CASE&lt;br /&gt;
               END&lt;br /&gt;
*&lt;br /&gt;
** test if we&amp;#039;re in a configured day of month or day of week&lt;br /&gt;
               IF DOMs NE &amp;#039;*&amp;#039; THEN&lt;br /&gt;
                  [[CronVal]] = DOMs ; [[TestVal]] = [[CurrDom]]&lt;br /&gt;
                  [[MinVal]]  = 1    ; [[MaxVal]]  = 31&lt;br /&gt;
                  GOSUB BUILD.CRON.VALUE&lt;br /&gt;
               END         &lt;br /&gt;
               IF DOWs NE &amp;#039;*&amp;#039; THEN&lt;br /&gt;
                  [[CronVal]] = DOWs ; [[TestVal]] = [[CurrDow]]&lt;br /&gt;
                  [[MinVal]]  = 0    ; [[MaxVal]]  = 6&lt;br /&gt;
                  GOSUB BUILD.CRON.VALUE&lt;br /&gt;
               END         &lt;br /&gt;
               IF [[CronSkip]] THEN GOTO EXIT.CASE&lt;br /&gt;
*&lt;br /&gt;
** test if we&amp;#039;re in a configured hour of the day&lt;br /&gt;
               IF Hours NE &amp;#039;*&amp;#039; THEN&lt;br /&gt;
                  [[CronVal]] = Hours ; [[TestVal]] = [[CurrHour]]&lt;br /&gt;
                  [[MinVal]]  = 0     ; [[MaxVal]]  = 23&lt;br /&gt;
                  GOSUB BUILD.CRON.VALUE&lt;br /&gt;
                  IF [[CronSkip]] THEN GOTO EXIT.CASE&lt;br /&gt;
               END&lt;br /&gt;
*&lt;br /&gt;
** test if we&amp;#039;re in a configured minute of the current hour&lt;br /&gt;
               IF Minutes NE &amp;#039;*&amp;#039; THEN&lt;br /&gt;
                  [[CronVal]] = Minutes ; [[TestVal]] = [[CurrMin]]&lt;br /&gt;
                  [[MinVal]]  = 0       ; [[MaxVal]]  = 59&lt;br /&gt;
                  GOSUB BUILD.CRON.VALUE&lt;br /&gt;
                  IF [[CronSkip]] THEN GOTO EXIT.CASE&lt;br /&gt;
               END&lt;br /&gt;
         END CASE&lt;br /&gt;
*&lt;br /&gt;
***************&lt;br /&gt;
EXIT.CASE:&lt;br /&gt;
***************&lt;br /&gt;
*&lt;br /&gt;
** update log if we have an error&lt;br /&gt;
         IF HLDMSG NE NULL$ THEN&lt;br /&gt;
            READVU Attr FROM DTASERVICES, [[ServiceId]], 11 ELSE Attr = NULL$&lt;br /&gt;
            WRITEV HLDMSG ON DTASERVICES, [[ServiceId]], 11&lt;br /&gt;
            GOTO CONTINUE.LOOP&lt;br /&gt;
         END&lt;br /&gt;
         IF [[CronSkip]] THEN GOTO CONTINUE.LOOP&lt;br /&gt;
*&lt;br /&gt;
** Run the command(s)&lt;br /&gt;
         IF [[LogToCmd]] NE NULL$ THEN&lt;br /&gt;
            [[TclCmd]] = [[LogToCmd]]&lt;br /&gt;
         END ELSE&lt;br /&gt;
            [[TclCmd]] = NULL$&lt;br /&gt;
         END&lt;br /&gt;
         [[TclCmd]]&amp;lt;-1&amp;gt; = [[PhantomCmd]] : [[PhantomOptions]] : SP1 : [[ProgramToRun]]&lt;br /&gt;
         EXECUTE [[TclCmd]] CAPTURING Output&lt;br /&gt;
*&lt;br /&gt;
** prepare commands for output to log&lt;br /&gt;
         o[[TclCmd]] = CONVERT(@AM, &amp;#039;^&amp;#039;, [[TclCmd]])  ; ** U2 version&lt;br /&gt;
*        o[[TclCmd]] = CONVERT([[TclCmd]], @AM, &amp;#039;^&amp;#039;)  ; ** D3 version&lt;br /&gt;
         oOutput = CONVERT(@AM, @VM, Output)   ; ** U2 version&lt;br /&gt;
*        oOutput = CONVERT(Output, @AM, @VM)   ; ** D3 version&lt;br /&gt;
*&lt;br /&gt;
** calculate job#&lt;br /&gt;
         [[ColStart]] = INDEX(Output, &amp;#039;Job #&amp;#039;, 1) + 5&lt;br /&gt;
         IF [[ColStart]] THEN&lt;br /&gt;
            [[JobNo]] = FIELD(Output[[[ColStart]],99], &amp;#039; &amp;#039;, 1)&lt;br /&gt;
         END ELSE&lt;br /&gt;
            [[JobNo]] = NULL$&lt;br /&gt;
         END&lt;br /&gt;
         HLDMSG = o[[TclCmd]] : @VM : &amp;quot;Phantomed as Job# &amp;quot; : [[JobNo]]&lt;br /&gt;
*&lt;br /&gt;
** update service item&lt;br /&gt;
         READU [[ServiceRec]] FROM DTASERVICES, [[ServiceId]] ELSE [[ServiceRec]] = NULL$&lt;br /&gt;
         [[ServiceRec]]&amp;lt;10&amp;gt; = [[JobNo]]&lt;br /&gt;
         [[ServiceRec]]&amp;lt;11&amp;gt; = &amp;quot;Process last run at &amp;quot; : TIMEDATE()&lt;br /&gt;
         [[ServiceRec]]&amp;lt;12&amp;gt; = oOutput&lt;br /&gt;
         WRITE [[ServiceRec]] ON DTASERVICES, [[ServiceId]]&lt;br /&gt;
*&lt;br /&gt;
** log job run&lt;br /&gt;
         CALL LOGMSG (&amp;#039;&amp;#039;, &amp;#039;N[[/A]]&amp;#039;, HLDMSG, &amp;#039;&amp;#039;)&lt;br /&gt;
      END&lt;br /&gt;
*&lt;br /&gt;
***************&lt;br /&gt;
CONTINUE.LOOP:&lt;br /&gt;
***************&lt;br /&gt;
*&lt;br /&gt;
   REPEAT&lt;br /&gt;
*&lt;br /&gt;
** sleep until the next [[SleepValue]] (usually the next minute)&lt;br /&gt;
***************&lt;br /&gt;
CONTINUE.SLEEP:&lt;br /&gt;
***************&lt;br /&gt;
*&lt;br /&gt;
   [[DisplayCnt]]  += 1&lt;br /&gt;
   [[SleepFor]] = [[SleepValue]] - MOD(TIME(), [[SleepValue]])&lt;br /&gt;
   SLEEP [[SleepFor]]&lt;br /&gt;
REPEAT&lt;br /&gt;
*&lt;br /&gt;
GOTO END.OF.PROGRAM&lt;br /&gt;
*&lt;br /&gt;
**------------------------------------------------------------------**&lt;br /&gt;
**                                                                  **&lt;br /&gt;
**                       S U B R O U T I N E S                      **&lt;br /&gt;
**                                                                  **&lt;br /&gt;
**------------------------------------------------------------------**&lt;br /&gt;
*&lt;br /&gt;
***************&lt;br /&gt;
BUILD.CRON.VALUE:&lt;br /&gt;
***************&lt;br /&gt;
*&lt;br /&gt;
** convert to comma-delimited data&lt;br /&gt;
IF COUNT([[CronVal]], &amp;#039;-&amp;#039;) THEN&lt;br /&gt;
   [[FrNo]]    = FIELD([[CronVal]], &amp;#039;-&amp;#039;, 1)&lt;br /&gt;
   [[ToNo]]    = FIELD([[CronVal]], &amp;#039;-&amp;#039;, 2)&lt;br /&gt;
   [[CronVal]] = NULL$&lt;br /&gt;
   FOR X = [[FrNo]] TO [[ToNo]]&lt;br /&gt;
      [[CronVal]]&amp;lt;1,-1&amp;gt; = X&lt;br /&gt;
   NEXT X&lt;br /&gt;
   [[CronVal]] = CONVERT(@VM, &amp;#039;,&amp;#039;, [[CronVal]])  ; ** U2 version&lt;br /&gt;
*  [[CronVal]] = CONVERT([[CronVal]], @VM, &amp;#039;,&amp;#039;)  ; ** D3 version&lt;br /&gt;
END&lt;br /&gt;
*&lt;br /&gt;
** initialize variables&lt;br /&gt;
[[CronSkip]]  = 1                 ; ** default an error&lt;br /&gt;
[[NewVal]]  = [[CronVal]]             ; ** save it to read values&lt;br /&gt;
[[CronVal]] = NULL$               ; ** clear to rebuild&lt;br /&gt;
*&lt;br /&gt;
** test for valid data (else abort program)&lt;br /&gt;
xHigh = DCOUNT([[NewVal]], &amp;#039;,&amp;#039;)&lt;br /&gt;
FOR X = 1 TO xHigh&lt;br /&gt;
   wkVal = FIELD([[NewVal]], &amp;#039;,&amp;#039;, X)&lt;br /&gt;
   IF NUM(wkVal) THEN&lt;br /&gt;
      IF wkVal &amp;gt; [[MaxVal]] THEN wkVal = [[MaxVal]]&lt;br /&gt;
      IF wkVal &amp;lt; [[MinVal]] THEN wkVal = [[MinVal]]&lt;br /&gt;
   END ELSE&lt;br /&gt;
      HLDMSG = &amp;quot;Non-numeric format for Cron value in &amp;quot; : [[NewVal]] : &amp;quot;. Service stopped.&amp;quot;&lt;br /&gt;
      RETURN TO ABORT.PROGRAM&lt;br /&gt;
   END&lt;br /&gt;
   [[CronVal]]&amp;lt;1,-1&amp;gt; = wkVal&lt;br /&gt;
NEXT X&lt;br /&gt;
[[CronVal]] = CONVERT(@VM, &amp;#039;,&amp;#039;, [[CronVal]])  ; ** U2 version&lt;br /&gt;
*[[CronVal]] = CONVERT([[CronVal]], @VM, &amp;#039;,&amp;#039;)  ; ** D3 version&lt;br /&gt;
*&lt;br /&gt;
xHigh = DCOUNT([[CronVal]], &amp;#039;,&amp;#039;)&lt;br /&gt;
FOR X = 1 TO xHigh&lt;br /&gt;
   wkVal = FIELD([[CronVal]], &amp;#039;,&amp;#039;, X)&lt;br /&gt;
   IF wkVal = [[TestVal]] THEN [[CronSkip]] = 0&lt;br /&gt;
NEXT X&lt;br /&gt;
RETURN&lt;br /&gt;
*&lt;br /&gt;
**------------------------------------------------------------------**&lt;br /&gt;
**                                                                  **&lt;br /&gt;
**                    E N D   O F   P R O G R A M                   **&lt;br /&gt;
**                                                                  **&lt;br /&gt;
**------------------------------------------------------------------**&lt;br /&gt;
*&lt;br /&gt;
***************&lt;br /&gt;
ABORT.PROGRAM:&lt;br /&gt;
***************&lt;br /&gt;
*&lt;br /&gt;
CALL LOGMSG (&amp;#039;&amp;#039;, &amp;#039;N[[/A]]&amp;#039;, HLDMSG, &amp;#039;&amp;#039;)&lt;br /&gt;
*&lt;br /&gt;
***************&lt;br /&gt;
END.OF.PROGRAM:&lt;br /&gt;
***************&lt;br /&gt;
*&lt;br /&gt;
END&lt;br /&gt;
&amp;lt;/PRE&amp;gt;&lt;/div&gt;</summary>
		<author><name>Conversion script</name></author>
	</entry>
</feed>