EXTOL RPG Program: ADDDAYS

EXTOL RPG - External Call ADDDAYS - Add or Subtract Days From Date

      *****************************************************************
      /TITLE API: Add Days to a Date -- External Process Code Table
      ********************************************************************
      * SYNOPSIS: Convert date from/to format and optionally add/sub
      *           number of days to the date.  This program makes use
      *           of the DATECONV code table, which must also exist in
      *           the *LIBL.
      *
      * USE:      Standard Code Table Parms (Parm List 1 short)
      *               Inbound ( P1CDTT = "I" )
      *                   P0RTN = *BLANKS when valid conversion
      *                   STD   = From Date (unchanged)
      *                   QUAL  = Fmts & # Days (see below)
      *                   LCL   = To Date (when valid STD & QUAL passed)
      *               Outbound ( P1CDTT = "O" )
      *                   P0RTN = *BLANKS when valid conversion
      *                   STD   = To Date (when valid LCL & QUAL passed)
      *                   QUAL  = Fmts & # Days (see below)
      *                   LCL   = From Date (unchanged)
      *           QUAL -- positional values
      *                   Any formats supported by DATECONV code table
      *                   can be used for Std or Lcl here, including
      *                   but not limited to YMD, MDY, ZMD.
      *                   01-03: Std Format
      *                   04-06: Lcl Format
      *                   07-12: Days to Add/Subtract
      *                          Integer followed by optional minus sign
      *                          Eg. 015 00015 15 are all the same
      *                              1- 01- 00001- are all the same
      *           Ex: Inbound  QUAL YMDZMD0015
      *               Convert YYMMDD to CCYYMMDD and add 15 days.
      *           Ex: Outbound QUAL YMDZMD30-
      *               Convert CCYYMMDD to YYMMDD and subtract 30 days.
      ********************************************************************
      * Company       : ExtoL, Inc.
      * System        : ExtoL EDI Integrator
      * Programmer    : DJS
      * Date          : 11/23/1999
      * (C) Copyright : ExtoL, Inc.  1999
      ********************************************************************
     H            Y
      *****************************************************************
     E                    LY         49  3 0A            Leap Year List
      *****************************************************************
     IDAY#DS      DS
     I                                        1  150DAY#
      *****************************************************************
     IJYYDDD      DS
     I                                        1   30JYY
     I                                        4   60DDD
      *****************************************************************
     I              '0123456789'          C         $DIGIT
      *****************************************************************
      * Entry parameters
     C           *ENTRY    PLIST
     C                     PARM           P0RTN   7
     C                     PARM           P1CDTT  1        Code trans dire
     C                     PARM           P2TABL 10        Code table refe
     C                     PARM           P3CDST 80        Code in standar
     C                     PARM           P4CDQD 80        Code qualifier
     C                     PARM           P5CDLC 80        Code in local f
      *
     C                     EXSR @TOJUL                     Cvt Usr to Jul
     C           P0RTN     IFEQ *BLANK
     C                     EXSR @PARSE                     Parse # of Days
     C                     EXSR @ADD                       Add # of Days
     C                     EXSR @TOUSR                     Cvt Jul to Usr
     C                     ENDIF
      *
     C                     MOVE *OFF      *INLR
     C                     RETRN
      *****************************************************************
     C           @TOJUL    BEGSR                           Cvt Usr to Jul
      * Use Date Convert Code Table to get any date in Julian format.
      *   Regardless of whether doing Inbound or Outbound, the from
      *   date is left justified.  'CJL' is hardcoded and right justified
      *   in FRMFMT which is used as "code qualifier" to DATECONV pgm.
     C           P1CDTT    IFEQ 'I'
     C           3         SUBSTP4CDQD:1  IFMT    3
     C           IFMT      CAT  'CJL'     FRMFMT  6
     C                     MOVELP3CDST    FRMDAT 80
     C                     ENDIF
     C           P1CDTT    IFEQ 'O'
     C           3         SUBSTP4CDQD:4  OFMT    3
     C           OFMT      CAT  'CJL'     FRMFMT  6
     C                     MOVELP5CDLC    FRMDAT 80
     C                     ENDIF
      *
      * Use DATECONV code table to convert date to julian.
      *   "I" is used regardless of the direction of previous caller.
     C                     MOVE *BLANKS   JULDAT 80
     C                     CALL 'DATECONV'
     C                     PARM *BLANK    P0RTN   7        Return Code
     C                     PARM 'I'       O#CDTT  1        "Inbound"
     C                     PARM P2TABL    O#TABL 10        Code table ref
     C                     PARM FRMDAT    O#CDST 80        Original Fmt
     C                     PARM FRMFMT    O#CDQD 80        Code qualifier
     C           JULDAT    PARM           I#CDLC 80        Code in local
      *
     C           TOJUL@    ENDSR                           Cvt Usr to Jul
      *****************************************************************
     C           @PARSE    BEGSR                           Parse # Days
      * Parse # of days from code qualifier.
      *   In: P4CDQD
      *  Out: DAY# Number of Days to Add to date (can be negative)
     C                     Z-ADD0         DAY#
      *
      * Strip leading 6 characters (StdLcl formats).
     C                     SUBSTP4CDQD:7  DAYC    6
      *
      * Find first non-digit.
     C           $DIGIT    CHECKDAYC      IX
      *
      * Sign (if any) is first non-digit.
     C           IX        IFGE 1
     C           IX        ANDLE31
     C                     SUBSTDAYC:IX   SIGN    1
     C                     ELSE
     C                     MOVE *BLANK    SIGN    1
     C                     ENDIF
      *
      * Get integer days.
     C           IX        IFGT 1
     C           IX        ANDLE15
     C           16        SUB  IX        IX
     C                     MOVE *BLANK    DAY#DS
     C                     CAT  DAYC:IX   DAY#DS
     C           ' ':'0'   XLATEDAYC      DAYC
      *
      * Reverse numeric sign if '-' appended to integer.
     C           SIGN      IFEQ '-'
     C                     Z-SUBDAY#      DAY#
     C                     ENDIF
     C                     ENDIF
      *
     C           PARSE@    ENDSR                           Parse # Days
      *****************************************************************
     C           @ADD      BEGSR                           Add Days to Dat
      * Add # of days offset to julian date.
      *   In: JULDAT
      *       DAY#
      *  Out: JULDAT adjust by DAY#
      *
      * Load to *DS to break out year and days.
     C                     MOVELJULDAT    JYYDDD
      *
      * Determine if leap year.
     C                     EXSR @LEAP
      *
      * Add day number from julian date to # of days to add.
     C                     ADD  DDD       DAY#
      *
      * Increment year while subtracting days per year.
      *   Note: Leap is determined after subtracting MAXDAY from year.
     C           DAY#      DOWGTMAXDAY
     C                     SUB  MAXDAY    DAY#
     C                     ADD  1         JYY
     C                     EXSR @LEAP
     C                     ENDDO
      *
      * Decrement year while adding days per year.
      *   Note: Leap is determined before adding MAXDAY to year.
     C           DAY#      DOWLE0
     C                     SUB  1         JYY
     C                     EXSR @LEAP
     C                     ADD  MAXDAY    DAY#
     C                     ENDDO
      *
      * Put normalized number days back in Julian Date *DS.
     C                     Z-ADDDAY#      DDD
      *
      * Move *DS to user date work field.
     C                     MOVELJYYDDD    JULDAT    P
      *
     C           ADD@      ENDSR                           Add Days to Dat
      *****************************************************************
     C           @TOUSR    BEGSR                           Cvt Jul to Usr
      * Use Date Convert Code Table to convert Julian format to user Fmt.
      *   Regardless of whether doing Inbound or Outbound, the from
      *   date is left justified and 'CJL' hardcoded and right justified
      *   in TOFMT which is used as "code qualifier to DATECONV pgm.
     C           P1CDTT    IFEQ 'I'
     C           3         SUBSTP4CDQD:4  IFMT    3
     C           'CJL'     CAT  IFMT      TOFMT   6
     C                     MOVELJYYDDD    FRMDAT 80 P
     C                     ENDIF
     C           P1CDTT    IFEQ 'O'
     C           3         SUBSTP4CDQD:1  OFMT    3
     C           'CJL'     CAT  OFMT      TOFMT   6
     C                     MOVELJYYDDD    FRMDAT 80 P
     C                     ENDIF
      *
      * Use DATECONV code table to convert date from julian.
      *   "I" is used regardless of the direction of previous caller.
     C                     MOVE *BLANKS   TODATE 80
     C                     CALL 'DATECONV'
     C                     PARM *BLANK    P0RTN   7        Return Code
     C                     PARM 'I'       O#CDTT  1        "Inbound"
     C                     PARM P2TABL    O#TABL 10        Code table ref
     C                     PARM JULDAT    O#CDST 80        Original Fmt
     C                     PARM TOFMT     O#CDQD 80        Code qualifier
     C           TODATE    PARM           I#CDLC 80        Code in local
      *
     C           P1CDTT    IFEQ 'I'
     C                     MOVELTODATE    P5CDLC    P
     C                     ENDIF
     C           P1CDTT    IFEQ 'O'
     C                     MOVELTODATE    P3CDST    P
     C                     ENDIF
      *
     C           TOUSR@    ENDSR                           Cvt Jul to Usr
      *****************************************************************
     C           @LEAP     BEGSR                           Chk if Leap Yr
      * Determine if leap year
      *   In: JYY
      *  Out: ISLY   = *ON/*OFF
      *       MAXDAY = 365 or 366
      *
     C                     Z-ADD1         IX      30
     C           JYY       LOKUPLY,IX                    60
     C                     MOVE *IN60     ISLY    1
     C           ISLY      IFEQ *ON
     C                     Z-ADD366       MAXDAY  30       Leap Year Days
     C                     ELSE
     C                     Z-ADD365       MAXDAY  30       Not Leap Year
     C                     ENDIF
     C           LEAP@     ENDSR                           Chk if Leap Yr
      *****************************************************************
     C           *INZSR    BEGSR
      *
      * Build list of leap years from 1904--2096.
      *    (JYY format 004 -- 196)
     C                     Z-ADD04        LEAP    30
     C                     Z-ADD1         IX      30
     C           IX        DOWLE49
     C                     Z-ADDLEAP      LY,IX
     C                     ADD  4         LEAP
     C                     ADD  1         IX
     C                     ENDDO
     C                     SORTALY
      *
     C           INZSR@    ENDSR
      *****************************************************************



By: on