94400d50d4
作为子目录纳入系统,与核心测试管道协同 Co-Authored-By: Claude <noreply@anthropic.com>
643 lines
25 KiB
COBOL
643 lines
25 KiB
COBOL
*> Input: FILE-IN.DAT Output: FILE-OUT-NN.DAT, AUDIT-11.RPT
|
|
*> Original DIVIDE + expansions: I/O recovery, hash totals,
|
|
*> header/trailer recs, split stats, audit trail, boundary
|
|
*> checks, trailing recs, naming validation, file inventory,
|
|
*> error severity levels (WARNING/ERROR/FATAL)
|
|
IDENTIFICATION DIVISION.
|
|
PROGRAM-ID. Divide25.
|
|
|
|
ENVIRONMENT DIVISION.
|
|
INPUT-OUTPUT SECTION.
|
|
FILE-CONTROL.
|
|
SELECT FILE-IN
|
|
ASSIGN TO "FILE-IN.DAT"
|
|
ORGANIZATION IS LINE SEQUENTIAL
|
|
FILE STATUS IS WS-FILE-STATUS-IN.
|
|
|
|
SELECT FILE-OUT
|
|
ASSIGN TO WS-OUT-FILE
|
|
ORGANIZATION IS LINE SEQUENTIAL
|
|
FILE STATUS IS WS-FILE-STATUS-OUT.
|
|
|
|
SELECT FILE-AUDIT
|
|
ASSIGN TO "AUDIT-11.RPT"
|
|
ORGANIZATION IS LINE SEQUENTIAL
|
|
FILE STATUS IS WS-FILE-STATUS-AUD.
|
|
|
|
DATA DIVISION.
|
|
FILE SECTION.
|
|
FD FILE-IN.
|
|
01 FILE-IN-REC.
|
|
05 IN-RECORD PIC X(30).
|
|
|
|
FD FILE-OUT.
|
|
01 FILE-OUT-REC.
|
|
05 OUT-RECORD PIC X(30).
|
|
|
|
FD FILE-AUDIT.
|
|
01 FILE-AUDIT-REC PIC X(80).
|
|
|
|
WORKING-STORAGE SECTION.
|
|
01 WS-TELECOM-REC.
|
|
COPY "telecom/TEL-INVOICE.cpy".
|
|
|
|
01 WS-STATUS.
|
|
05 WS-EOF-FLAG PIC X VALUE 'N'.
|
|
88 WS-EOF VALUE 'Y' FALSE 'N'.
|
|
05 WS-FILE-STATUS-IN PIC X(2).
|
|
05 WS-FILE-STATUS-OUT PIC X(2).
|
|
05 WS-FILE-STATUS-AUD PIC X(2).
|
|
|
|
01 WS-COUNTERS.
|
|
05 WS-REC-COUNT PIC 9(5) VALUE 0.
|
|
05 WS-FILE-NUM PIC 9(2) VALUE 0.
|
|
05 WS-DIVISOR PIC 9(2) VALUE 25.
|
|
05 WS-QUOTIENT PIC 9(5).
|
|
05 WS-REMAINDER PIC 9(5).
|
|
05 WS-REC-IN-FILE PIC 9(5) VALUE 0.
|
|
05 WS-TOTAL-RECS-WRITTEN PIC 9(5) VALUE 0.
|
|
|
|
01 WS-OUT-FILE PIC X(30).
|
|
01 WS-FILE-NUM-ED PIC 99.
|
|
01 WS-DISPLAY-COUNT PIC Z(9)9.
|
|
|
|
01 WS-INVOICE-REC.
|
|
COPY "telecom/TEL-INVOICE.cpy".
|
|
|
|
01 WS-TIMESTAMP.
|
|
05 WS-TS-DATE PIC 9(8).
|
|
05 WS-TS-TIME PIC 9(8).
|
|
05 WS-TS-EDITED PIC X(19).
|
|
|
|
01 WS-OPEN-RETRY-COUNT PIC 9(2) VALUE 0.
|
|
01 WS-ALT-SUFFIX PIC X(4) VALUE ".ALT".
|
|
01 WS-OPEN-OK PIC X VALUE 'N'.
|
|
88 WS-OPEN-SUCCESS VALUE 'Y' FALSE 'N'.
|
|
88 WS-OPEN-FAILED VALUE 'N'.
|
|
|
|
01 WS-FILE-NAME-VALID PIC X VALUE 'Y'.
|
|
88 WS-FILE-NAME-OK VALUE 'Y' FALSE 'N'.
|
|
|
|
01 WS-HASH-TOTAL-IN PIC 9(9) VALUE 0.
|
|
01 WS-HASH-OUT-TABLE.
|
|
05 WS-HASH-OUT PIC 9(9) OCCURS 99.
|
|
01 WS-HASH-SUM-OUT PIC 9(9) VALUE 0.
|
|
01 WS-HASH-VERIFIED PIC X VALUE 'N'.
|
|
88 WS-HASH-VERIFIED-YES VALUE 'Y' FALSE 'N'.
|
|
|
|
01 WS-SPLIT-STATS.
|
|
05 WS-SPLIT-MIN-RECS PIC 9(5) VALUE 99999.
|
|
05 WS-SPLIT-MAX-RECS PIC 9(5) VALUE 0.
|
|
05 WS-SPLIT-TOTAL-FILES PIC 9(5) VALUE 0.
|
|
05 WS-SPLIT-TOTAL-RECS PIC 9(9) VALUE 0.
|
|
05 WS-SPLIT-AVG-RECS PIC 9(5) VALUE 0.
|
|
|
|
01 WS-BOUNDARY-FLAG PIC X.
|
|
88 WS-BOUNDARY-EMPTY VALUE 'E'.
|
|
88 WS-BOUNDARY-SINGLE VALUE 'S'.
|
|
88 WS-BOUNDARY-EXACT VALUE 'M'.
|
|
88 WS-BOUNDARY-NORMAL VALUE 'N'.
|
|
|
|
01 WS-TRAILER-COUNT PIC 9(5) VALUE 0.
|
|
01 WS-TRAILER-FLAG PIC X VALUE 'N'.
|
|
88 WS-TRAILER-WRITTEN VALUE 'Y' FALSE 'N'.
|
|
01 WS-TRAIL-RECS-LAST PIC 9(5) VALUE 0.
|
|
|
|
01 WS-SEVERITY PIC X(7).
|
|
88 WS-SEVERITY-WARN VALUE 'WARNING'.
|
|
88 WS-SEVERITY-ERR VALUE 'ERROR'.
|
|
88 WS-SEVERITY-FATAL VALUE 'FATAL'.
|
|
01 WS-ERROR-MSG PIC X(60).
|
|
|
|
01 WS-SPLIT-HEADER.
|
|
05 FILLER PIC X(6) VALUE 'HEADER'.
|
|
05 FILLER PIC X VALUE SPACE.
|
|
05 WS-HDR-FILE PIC 9(2).
|
|
05 FILLER PIC X VALUE SPACE.
|
|
05 WS-HDR-DATE PIC 9(8).
|
|
05 FILLER PIC X VALUE SPACE.
|
|
05 WS-HDR-TIME PIC 9(8).
|
|
05 FILLER PIC X VALUE SPACE.
|
|
05 WS-HDR-EXPREC PIC 9(5).
|
|
|
|
01 WS-SPLIT-TRAILER.
|
|
05 FILLER PIC X(7) VALUE 'TRAILER'.
|
|
05 FILLER PIC X VALUE SPACE.
|
|
05 WS-TRL-FILE PIC 9(2).
|
|
05 FILLER PIC X VALUE SPACE.
|
|
05 WS-TRL-COUNT PIC 9(5).
|
|
05 FILLER PIC X VALUE SPACE.
|
|
05 WS-TRL-HASH PIC 9(9).
|
|
|
|
01 WS-HASH-WORK.
|
|
05 WS-H-CHAR-IDX PIC 99.
|
|
05 WS-H-CHAR PIC X.
|
|
05 WS-H-SUM PIC 9(9).
|
|
05 WS-H-ORD PIC 9(3).
|
|
|
|
01 WS-INVENTORY-REC.
|
|
05 WS-INV-FILE PIC 9(2).
|
|
05 FILLER PIC X(3) VALUE SPACES.
|
|
05 WS-INV-RECS PIC 9(5).
|
|
05 FILLER PIC X(3) VALUE SPACES.
|
|
05 WS-INV-HASH PIC 9(9).
|
|
|
|
01 WS-REPORT-LINE PIC X(80).
|
|
01 WS-I PIC 99.
|
|
01 WS-NEXT-REM PIC 9(5).
|
|
01 WS-HASH-DISP PIC Z(9)9.
|
|
|
|
PROCEDURE DIVISION.
|
|
MAIN SECTION.
|
|
MAIN-PROCEDURE.
|
|
PERFORM 1000-INIT-SECTION
|
|
PERFORM 2000-OPEN-FILES-SECTION
|
|
|
|
*> === Original code: banner ===
|
|
DISPLAY "=== 25-DIVISION PROCESSING ==="
|
|
DISPLAY "Records per file: " WS-DIVISOR
|
|
|
|
*> === Original code: processing loop ===
|
|
PERFORM 3000-PROCESS-SECTION
|
|
|
|
PERFORM 3500-TRAILING-HANDLE-SECTION
|
|
PERFORM 4000-REPORT-SECTION
|
|
PERFORM 5000-AUDIT-SECTION
|
|
PERFORM 9000-EXIT-SECTION
|
|
STOP RUN.
|
|
|
|
*> ============================================================
|
|
*> 1000-INIT-SECTION
|
|
*> ============================================================
|
|
1000-INIT-SECTION.
|
|
1000-INIT-PROC.
|
|
ACCEPT WS-TS-DATE FROM DATE YYYYMMDD
|
|
ACCEPT WS-TS-TIME FROM TIME
|
|
STRING WS-TS-DATE(1:4) '-' WS-TS-DATE(5:2) '-'
|
|
WS-TS-DATE(7:2) ' '
|
|
WS-TS-TIME(1:2) ':' WS-TS-TIME(3:2) ':'
|
|
WS-TS-TIME(5:2)
|
|
INTO WS-TS-EDITED
|
|
END-STRING
|
|
DISPLAY "=== Divide25 v2 Started " WS-TS-EDITED " ==="
|
|
MOVE 'N' TO WS-BOUNDARY-FLAG
|
|
MOVE 0 TO WS-SPLIT-TOTAL-FILES WS-SPLIT-TOTAL-RECS
|
|
MOVE 99999 TO WS-SPLIT-MIN-RECS
|
|
MOVE 0 TO WS-SPLIT-MAX-RECS WS-TRAILER-COUNT
|
|
MOVE 'N' TO WS-TRAILER-FLAG WS-HASH-VERIFIED
|
|
MOVE 0 TO WS-TRAIL-RECS-LAST WS-HASH-TOTAL-IN
|
|
MOVE 'Y' TO WS-FILE-NAME-VALID
|
|
DISPLAY "1000-INIT: All counters zeroed"
|
|
.
|
|
|
|
*> ============================================================
|
|
*> 2000-OPEN-FILES-SECTION — Retry + alt fallback for input
|
|
*> ============================================================
|
|
2000-OPEN-FILES-SECTION.
|
|
2000-OPEN-FILES-PROC.
|
|
MOVE 0 TO WS-OPEN-RETRY-COUNT
|
|
MOVE 'N' TO WS-OPEN-OK
|
|
PERFORM UNTIL WS-OPEN-SUCCESS
|
|
OR WS-OPEN-RETRY-COUNT > 3
|
|
OPEN INPUT FILE-IN
|
|
IF WS-FILE-STATUS-IN = '00'
|
|
MOVE 'Y' TO WS-OPEN-OK
|
|
DISPLAY "2000-OPEN: FILE-IN.DAT OK"
|
|
ELSE
|
|
ADD 1 TO WS-OPEN-RETRY-COUNT
|
|
MOVE 'WARNING' TO WS-SEVERITY
|
|
STRING "2000: FILE-IN retry "
|
|
WS-OPEN-RETRY-COUNT
|
|
" sts=" WS-FILE-STATUS-IN
|
|
INTO WS-ERROR-MSG
|
|
END-STRING
|
|
PERFORM 6000-ERROR-HANDLE-SECTION
|
|
END-IF
|
|
END-PERFORM
|
|
IF WS-OPEN-FAILED
|
|
STRING "FILE-IN" WS-ALT-SUFFIX
|
|
INTO WS-OUT-FILE
|
|
END-STRING
|
|
OPEN INPUT FILE-IN
|
|
IF WS-FILE-STATUS-IN = '00'
|
|
MOVE 'Y' TO WS-OPEN-OK
|
|
DISPLAY "2000-OPEN: ALT file opened"
|
|
ELSE
|
|
MOVE 'FATAL' TO WS-SEVERITY
|
|
STRING "2000: FILE-IN open failed all retry"
|
|
INTO WS-ERROR-MSG
|
|
END-STRING
|
|
PERFORM 6000-ERROR-HANDLE-SECTION
|
|
PERFORM 9000-EXIT-SECTION
|
|
END-IF
|
|
END-IF
|
|
OPEN OUTPUT FILE-AUDIT
|
|
IF WS-FILE-STATUS-AUD NOT = '00'
|
|
MOVE 'FATAL' TO WS-SEVERITY
|
|
STRING "2000: AUDIT open fail sts="
|
|
WS-FILE-STATUS-AUD
|
|
INTO WS-ERROR-MSG
|
|
END-STRING
|
|
PERFORM 6000-ERROR-HANDLE-SECTION
|
|
PERFORM 9000-EXIT-SECTION
|
|
ELSE
|
|
DISPLAY "2000-OPEN: AUDIT-11.RPT OK"
|
|
STRING "*** Divide25 v2 START *** " WS-TS-EDITED
|
|
INTO WS-REPORT-LINE
|
|
WRITE FILE-AUDIT-REC FROM WS-REPORT-LINE
|
|
END-IF
|
|
.
|
|
|
|
*> ============================================================
|
|
*> 3000-PROCESS-SECTION — Read/validate/apply/write loop
|
|
*> ============================================================
|
|
3000-PROCESS-SECTION.
|
|
3000-PROCESS-PROC.
|
|
PERFORM VARYING WS-REC-COUNT FROM 1 BY 1
|
|
UNTIL WS-EOF
|
|
PERFORM 3100-READ-INPUT-SECTION
|
|
IF NOT WS-EOF
|
|
PERFORM 3200-VALIDATE-SECTION
|
|
PERFORM 3300-APPLY-RULES-SECTION
|
|
PERFORM 3400-WRITE-OUTPUT-SECTION
|
|
END-IF
|
|
END-PERFORM
|
|
.
|
|
|
|
*> ============================================================
|
|
*> 3100-READ-INPUT-SECTION — Read + FILE STATUS check
|
|
*> ============================================================
|
|
3100-READ-INPUT-SECTION.
|
|
3100-READ-INPUT-PROC.
|
|
READ FILE-IN INTO FILE-IN-REC
|
|
AT END
|
|
SET WS-EOF TO TRUE
|
|
DISPLAY "3100-READ: EOF at " WS-REC-COUNT
|
|
NOT AT END
|
|
IF WS-FILE-STATUS-IN NOT = '00'
|
|
MOVE 'ERROR' TO WS-SEVERITY
|
|
STRING "3100: FILE-IN read err sts="
|
|
WS-FILE-STATUS-IN
|
|
INTO WS-ERROR-MSG
|
|
END-STRING
|
|
PERFORM 6000-ERROR-HANDLE-SECTION
|
|
END-IF
|
|
END-READ
|
|
.
|
|
|
|
*> ============================================================
|
|
*> 3200-VALIDATE-SECTION — Hash sum + boundary detect
|
|
*> ============================================================
|
|
3200-VALIDATE-SECTION.
|
|
3200-VALIDATE-PROC.
|
|
MOVE 0 TO WS-H-SUM
|
|
PERFORM VARYING WS-H-CHAR-IDX FROM 1 BY 1
|
|
UNTIL WS-H-CHAR-IDX > 30
|
|
MOVE IN-RECORD(WS-H-CHAR-IDX:1) TO WS-H-CHAR
|
|
IF WS-H-CHAR NOT = SPACE
|
|
COMPUTE WS-H-ORD = FUNCTION ORD(WS-H-CHAR)
|
|
ADD WS-H-ORD TO WS-H-SUM
|
|
END-IF
|
|
END-PERFORM
|
|
ADD WS-H-SUM TO WS-HASH-TOTAL-IN
|
|
IF WS-REC-COUNT = 1
|
|
MOVE 'S' TO WS-BOUNDARY-FLAG
|
|
END-IF
|
|
.
|
|
|
|
*> ============================================================
|
|
*> 3300-APPLY-RULES-SECTION
|
|
*> *** ORIGINAL DIVIDE LOGIC — PRESERVED VERBATIM ***
|
|
*> ============================================================
|
|
3300-APPLY-RULES-SECTION.
|
|
3300-APPLY-RULES-PROC.
|
|
DIVIDE WS-REC-COUNT BY WS-DIVISOR
|
|
GIVING WS-QUOTIENT REMAINDER WS-REMAINDER
|
|
IF WS-REMAINDER = 1
|
|
IF WS-FILE-NUM > 0
|
|
CLOSE FILE-OUT
|
|
DISPLAY " Closed: " WS-OUT-FILE
|
|
END-IF
|
|
ADD 1 TO WS-FILE-NUM
|
|
MOVE WS-FILE-NUM TO WS-FILE-NUM-ED
|
|
STRING "FILE-OUT-" DELIMITED BY SIZE
|
|
WS-FILE-NUM-ED DELIMITED BY SIZE
|
|
".DAT" DELIMITED BY SIZE
|
|
INTO WS-OUT-FILE
|
|
OPEN OUTPUT FILE-OUT
|
|
DISPLAY " Opened: " WS-OUT-FILE
|
|
END-IF
|
|
.
|
|
|
|
*> ============================================================
|
|
*> 3400-WRITE-OUTPUT-SECTION — Header/data/trailer + hash
|
|
*> ============================================================
|
|
3400-WRITE-OUTPUT-SECTION.
|
|
3400-WRITE-OUTPUT-PROC.
|
|
IF WS-REMAINDER = 1
|
|
MOVE WS-FILE-NUM TO WS-HDR-FILE
|
|
MOVE WS-TS-DATE TO WS-HDR-DATE
|
|
MOVE WS-TS-TIME TO WS-HDR-TIME
|
|
MOVE WS-DIVISOR TO WS-HDR-EXPREC
|
|
MOVE WS-SPLIT-HEADER TO FILE-OUT-REC
|
|
WRITE FILE-OUT-REC
|
|
IF WS-FILE-STATUS-OUT NOT = '00'
|
|
MOVE 'ERROR' TO WS-SEVERITY
|
|
STRING "3400: HDR write fail file="
|
|
WS-FILE-NUM " sts=" WS-FILE-STATUS-OUT
|
|
INTO WS-ERROR-MSG
|
|
END-STRING
|
|
PERFORM 6000-ERROR-HANDLE-SECTION
|
|
END-IF
|
|
MOVE 0 TO WS-REC-IN-FILE
|
|
MOVE 0 TO WS-HASH-OUT(WS-FILE-NUM)
|
|
MOVE 'N' TO WS-TRAILER-FLAG
|
|
END-IF
|
|
|
|
*> Write data record (original MOVE/WRITE preserved)
|
|
MOVE IN-RECORD TO OUT-RECORD
|
|
WRITE FILE-OUT-REC
|
|
IF WS-FILE-STATUS-OUT NOT = '00'
|
|
MOVE 'ERROR' TO WS-SEVERITY
|
|
STRING "3400: Write fail file=" WS-FILE-NUM
|
|
" rec=" WS-REC-COUNT
|
|
" sts=" WS-FILE-STATUS-OUT
|
|
INTO WS-ERROR-MSG
|
|
END-STRING
|
|
PERFORM 6000-ERROR-HANDLE-SECTION
|
|
ELSE
|
|
ADD 1 TO WS-REC-IN-FILE
|
|
ADD 1 TO WS-TOTAL-RECS-WRITTEN
|
|
ADD WS-H-SUM TO WS-HASH-OUT(WS-FILE-NUM)
|
|
END-IF
|
|
|
|
*> Write trailer when next record starts new file
|
|
COMPUTE WS-NEXT-REM =
|
|
FUNCTION MOD(WS-REC-COUNT + 1, WS-DIVISOR)
|
|
IF WS-NEXT-REM = 1
|
|
MOVE WS-FILE-NUM TO WS-TRL-FILE
|
|
MOVE WS-REC-IN-FILE TO WS-TRL-COUNT
|
|
MOVE WS-HASH-OUT(WS-FILE-NUM) TO WS-TRL-HASH
|
|
MOVE WS-SPLIT-TRAILER TO FILE-OUT-REC
|
|
WRITE FILE-OUT-REC
|
|
IF WS-FILE-STATUS-OUT NOT = '00'
|
|
MOVE 'ERROR' TO WS-SEVERITY
|
|
STRING "3400: TRL write fail file="
|
|
WS-FILE-NUM " sts=" WS-FILE-STATUS-OUT
|
|
INTO WS-ERROR-MSG
|
|
END-STRING
|
|
PERFORM 6000-ERROR-HANDLE-SECTION
|
|
END-IF
|
|
ADD 1 TO WS-TRAILER-COUNT
|
|
MOVE 'Y' TO WS-TRAILER-FLAG
|
|
ADD 1 TO WS-SPLIT-TOTAL-FILES
|
|
ADD WS-REC-IN-FILE TO WS-SPLIT-TOTAL-RECS
|
|
IF WS-REC-IN-FILE < WS-SPLIT-MIN-RECS
|
|
MOVE WS-REC-IN-FILE TO WS-SPLIT-MIN-RECS
|
|
END-IF
|
|
IF WS-REC-IN-FILE > WS-SPLIT-MAX-RECS
|
|
MOVE WS-REC-IN-FILE TO WS-SPLIT-MAX-RECS
|
|
END-IF
|
|
END-IF
|
|
.
|
|
|
|
*> ============================================================
|
|
*> 3500-TRAILING-HANDLE-SECTION — Last file trailer,
|
|
*> boundary classification
|
|
*> ============================================================
|
|
3500-TRAILING-HANDLE-SECTION.
|
|
3500-TRAILING-HANDLE-PROC.
|
|
IF WS-FILE-NUM > 0
|
|
IF WS-TRAILER-FLAG = 'N'
|
|
MOVE WS-FILE-NUM TO WS-TRL-FILE
|
|
MOVE WS-REC-IN-FILE TO WS-TRL-COUNT
|
|
MOVE WS-HASH-OUT(WS-FILE-NUM) TO WS-TRL-HASH
|
|
MOVE WS-SPLIT-TRAILER TO FILE-OUT-REC
|
|
WRITE FILE-OUT-REC
|
|
IF WS-FILE-STATUS-OUT NOT = '00'
|
|
MOVE 'ERROR' TO WS-SEVERITY
|
|
STRING "3500: TRL write fail last file"
|
|
INTO WS-ERROR-MSG
|
|
END-STRING
|
|
PERFORM 6000-ERROR-HANDLE-SECTION
|
|
END-IF
|
|
ADD 1 TO WS-TRAILER-COUNT
|
|
MOVE 'Y' TO WS-TRAILER-FLAG
|
|
MOVE WS-REC-IN-FILE TO WS-TRAIL-RECS-LAST
|
|
ADD 1 TO WS-SPLIT-TOTAL-FILES
|
|
ADD WS-REC-IN-FILE TO WS-SPLIT-TOTAL-RECS
|
|
IF WS-REC-IN-FILE < WS-SPLIT-MIN-RECS
|
|
MOVE WS-REC-IN-FILE TO WS-SPLIT-MIN-RECS
|
|
END-IF
|
|
IF WS-REC-IN-FILE > WS-SPLIT-MAX-RECS
|
|
MOVE WS-REC-IN-FILE TO WS-SPLIT-MAX-RECS
|
|
END-IF
|
|
DISPLAY "3500-TRAIL: Last trailer written"
|
|
END-IF
|
|
ELSE
|
|
MOVE 'E' TO WS-BOUNDARY-FLAG
|
|
DISPLAY "3500-TRAIL: Empty input file"
|
|
END-IF
|
|
IF WS-TOTAL-RECS-WRITTEN = 0
|
|
MOVE 'E' TO WS-BOUNDARY-FLAG
|
|
END-IF
|
|
IF WS-TOTAL-RECS-WRITTEN = 1
|
|
MOVE 'S' TO WS-BOUNDARY-FLAG
|
|
DISPLAY "3500-TRAIL: Single-record file"
|
|
END-IF
|
|
IF WS-SPLIT-TOTAL-FILES > 1
|
|
IF WS-SPLIT-MIN-RECS = WS-SPLIT-MAX-RECS
|
|
MOVE 'M' TO WS-BOUNDARY-FLAG
|
|
DISPLAY "3500-TRAIL: Exact multiple split"
|
|
END-IF
|
|
END-IF
|
|
.
|
|
|
|
*> ============================================================
|
|
*> 4000-REPORT-SECTION — Display + audit file stats/inventory
|
|
*> ============================================================
|
|
4000-REPORT-SECTION.
|
|
4000-REPORT-PROC.
|
|
DISPLAY " "
|
|
DISPLAY "=== SPLIT STATISTICS REPORT ==="
|
|
MOVE WS-REC-COUNT TO WS-DISPLAY-COUNT
|
|
DISPLAY "Total records read: " WS-DISPLAY-COUNT
|
|
DISPLAY "Total records written: " WS-TOTAL-RECS-WRITTEN
|
|
DISPLAY "Output files created: " WS-FILE-NUM
|
|
DISPLAY "Divisor: " WS-DIVISOR
|
|
IF WS-SPLIT-TOTAL-FILES > 0
|
|
COMPUTE WS-SPLIT-AVG-RECS =
|
|
WS-SPLIT-TOTAL-RECS / WS-SPLIT-TOTAL-FILES
|
|
ELSE
|
|
MOVE 0 TO WS-SPLIT-AVG-RECS
|
|
END-IF
|
|
DISPLAY "Split files counted: " WS-SPLIT-TOTAL-FILES
|
|
DISPLAY "Min recs per file: " WS-SPLIT-MIN-RECS
|
|
DISPLAY "Max recs per file: " WS-SPLIT-MAX-RECS
|
|
DISPLAY "Avg recs per file: " WS-SPLIT-AVG-RECS
|
|
DISPLAY "Trailer recs written: " WS-TRAILER-COUNT
|
|
DISPLAY "Trailing recs last file: " WS-TRAIL-RECS-LAST
|
|
DISPLAY "Boundary condition: " WS-BOUNDARY-FLAG
|
|
|
|
STRING "*** SPLIT STATS *** Total=" WS-SPLIT-TOTAL-RECS
|
|
" Files=" WS-SPLIT-TOTAL-FILES
|
|
" Min=" WS-SPLIT-MIN-RECS
|
|
" Max=" WS-SPLIT-MAX-RECS
|
|
INTO WS-REPORT-LINE
|
|
WRITE FILE-AUDIT-REC FROM WS-REPORT-LINE
|
|
IF WS-FILE-STATUS-AUD NOT = '00'
|
|
MOVE 'WARNING' TO WS-SEVERITY
|
|
STRING "4000: Audit write sts=" WS-FILE-STATUS-AUD
|
|
INTO WS-ERROR-MSG
|
|
END-STRING
|
|
PERFORM 6000-ERROR-HANDLE-SECTION
|
|
END-IF
|
|
|
|
STRING "*** OUTPUT FILE INVENTORY ***"
|
|
INTO WS-REPORT-LINE
|
|
WRITE FILE-AUDIT-REC FROM WS-REPORT-LINE
|
|
|
|
PERFORM VARYING WS-I FROM 1 BY 1
|
|
UNTIL WS-I > WS-FILE-NUM
|
|
MOVE WS-I TO WS-INV-FILE
|
|
IF WS-I < WS-FILE-NUM
|
|
MOVE WS-DIVISOR TO WS-INV-RECS
|
|
ELSE
|
|
MOVE WS-REC-IN-FILE TO WS-INV-RECS
|
|
END-IF
|
|
MOVE WS-HASH-OUT(WS-I) TO WS-INV-HASH
|
|
STRING "FILE " WS-INV-FILE " RECS=" WS-INV-RECS
|
|
" HASH=" WS-INV-HASH
|
|
INTO WS-REPORT-LINE
|
|
WRITE FILE-AUDIT-REC FROM WS-REPORT-LINE
|
|
END-PERFORM
|
|
.
|
|
|
|
*> ============================================================
|
|
*> 5000-AUDIT-SECTION — Hash total verification
|
|
*> ============================================================
|
|
5000-AUDIT-SECTION.
|
|
5000-AUDIT-PROC.
|
|
DISPLAY "=== HASH TOTAL VERIFICATION ==="
|
|
MOVE 0 TO WS-HASH-SUM-OUT
|
|
PERFORM VARYING WS-I FROM 1 BY 1
|
|
UNTIL WS-I > WS-FILE-NUM
|
|
ADD WS-HASH-OUT(WS-I) TO WS-HASH-SUM-OUT
|
|
END-PERFORM
|
|
MOVE WS-HASH-TOTAL-IN TO WS-HASH-DISP
|
|
DISPLAY "Input hash: " WS-HASH-DISP
|
|
MOVE WS-HASH-SUM-OUT TO WS-HASH-DISP
|
|
DISPLAY "Output hash: " WS-HASH-DISP
|
|
DISPLAY "Files hashed: " WS-FILE-NUM
|
|
IF WS-HASH-TOTAL-IN = WS-HASH-SUM-OUT
|
|
MOVE 'Y' TO WS-HASH-VERIFIED
|
|
DISPLAY "Hash verification: PASSED"
|
|
STRING "*** HASH VERIFICATION PASSED ***"
|
|
INTO WS-REPORT-LINE
|
|
ELSE
|
|
MOVE 'N' TO WS-HASH-VERIFIED
|
|
DISPLAY "Hash verification: FAILED"
|
|
MOVE 'ERROR' TO WS-SEVERITY
|
|
STRING "5000: Hash mismatch IN=" WS-HASH-TOTAL-IN
|
|
" OUT=" WS-HASH-SUM-OUT
|
|
INTO WS-ERROR-MSG
|
|
END-STRING
|
|
PERFORM 6000-ERROR-HANDLE-SECTION
|
|
STRING "*** HASH VERIFICATION FAILED ***"
|
|
INTO WS-REPORT-LINE
|
|
END-IF
|
|
WRITE FILE-AUDIT-REC FROM WS-REPORT-LINE
|
|
.
|
|
|
|
*> ============================================================
|
|
*> 6000-ERROR-HANDLE-SECTION — Log with severity level
|
|
*> ============================================================
|
|
6000-ERROR-HANDLE-SECTION.
|
|
6000-ERROR-HANDLE-PROC.
|
|
DISPLAY "*** " WS-SEVERITY " *** " WS-ERROR-MSG
|
|
STRING "*** " WS-SEVERITY " *** " WS-ERROR-MSG
|
|
INTO WS-REPORT-LINE
|
|
WRITE FILE-AUDIT-REC FROM WS-REPORT-LINE
|
|
IF WS-FILE-STATUS-AUD NOT = '00'
|
|
DISPLAY "6000: Audit write also failed"
|
|
END-IF
|
|
IF WS-SEVERITY-FATAL
|
|
DISPLAY "6000: FATAL — terminating"
|
|
PERFORM 9000-EXIT-SECTION
|
|
END-IF
|
|
.
|
|
|
|
*> ============================================================
|
|
*> 9000-EXIT-SECTION — Close files, original summary
|
|
*> *** ORIGINAL CLOSE / DISPLAY LOGIC PRESERVED ***
|
|
*> ============================================================
|
|
9000-EXIT-SECTION.
|
|
9000-EXIT-PROC.
|
|
ACCEPT WS-TS-TIME FROM TIME
|
|
STRING WS-TS-TIME(1:2) ':' WS-TS-TIME(3:2) ':'
|
|
WS-TS-TIME(5:2) INTO WS-TS-EDITED
|
|
END-STRING
|
|
|
|
IF WS-FILE-NUM > 0
|
|
CLOSE FILE-OUT
|
|
IF WS-FILE-STATUS-OUT NOT = '00'
|
|
MOVE 'WARNING' TO WS-SEVERITY
|
|
STRING "9000: FILE-OUT close sts="
|
|
WS-FILE-STATUS-OUT
|
|
INTO WS-ERROR-MSG
|
|
END-STRING
|
|
PERFORM 6000-ERROR-HANDLE-SECTION
|
|
END-IF
|
|
DISPLAY "Closed final file: " WS-OUT-FILE
|
|
END-IF
|
|
|
|
MOVE WS-REC-COUNT TO WS-DISPLAY-COUNT
|
|
DISPLAY " "
|
|
DISPLAY "Total records read: " WS-DISPLAY-COUNT
|
|
DISPLAY "Output files created: " WS-FILE-NUM
|
|
|
|
CLOSE FILE-IN
|
|
IF WS-FILE-STATUS-IN NOT = '00'
|
|
MOVE 'WARNING' TO WS-SEVERITY
|
|
STRING "9000: FILE-IN close sts="
|
|
WS-FILE-STATUS-IN
|
|
INTO WS-ERROR-MSG
|
|
END-STRING
|
|
PERFORM 6000-ERROR-HANDLE-SECTION
|
|
END-IF
|
|
|
|
STRING "*** Divide25 v2 END *** " WS-TS-EDITED
|
|
INTO WS-REPORT-LINE
|
|
WRITE FILE-AUDIT-REC FROM WS-REPORT-LINE
|
|
CLOSE FILE-AUDIT
|
|
|
|
DISPLAY " "
|
|
DISPLAY "--- Boundary condition ---"
|
|
EVALUATE TRUE
|
|
WHEN WS-BOUNDARY-EMPTY
|
|
DISPLAY " EMPTY FILE (0 records)"
|
|
WHEN WS-BOUNDARY-SINGLE
|
|
DISPLAY " SINGLE-RECORD FILE"
|
|
WHEN WS-BOUNDARY-EXACT
|
|
DISPLAY " EXACT MULTIPLE of " WS-DIVISOR
|
|
WHEN WS-BOUNDARY-NORMAL
|
|
DISPLAY " NORMAL (trailing partial batch)"
|
|
WHEN OTHER
|
|
DISPLAY " NOT DETERMINED"
|
|
END-EVALUATE
|
|
|
|
DISPLAY "--- Data Integrity ---"
|
|
MOVE WS-HASH-TOTAL-IN TO WS-HASH-DISP
|
|
DISPLAY " Input hash: " WS-HASH-DISP
|
|
MOVE WS-HASH-SUM-OUT TO WS-HASH-DISP
|
|
DISPLAY " Output hash: " WS-HASH-DISP
|
|
IF WS-HASH-VERIFIED-YES
|
|
DISPLAY " Integrity: PASSED"
|
|
ELSE
|
|
DISPLAY " Integrity: FAILED"
|
|
END-IF
|
|
DISPLAY " "
|
|
DISPLAY "=== Divide25 v2 Ended at "
|
|
WS-TS-EDITED " ==="
|
|
STOP RUN.
|