tldm-universe/Ardent/UV/APP.PROGS/LOAD.PIO.B

317 lines
8.5 KiB
Plaintext
Raw Permalink Normal View History

2024-09-09 21:51:08 +00:00
********************************************************************************
*
* LOAD.PIOPEN.B - Load utility to get PI/open unloaded files.
*
* Module %M% Version %I% Date %H%
*
* (c) Copyright 1998 Ardent Software Inc. - All Rights Reserved
* This is unpublished proprietary source code of Ardent Software Inc.
* The copyright notice above does not evidence any actual or intended
* publication of such source code.
*
*******************************************************************************
*
* Maintenence log - insert most recent change descriptions at top
*
* Date.... GTAR# WHO Description.........................................
* 10/14/98 23801 SAP Change copyrights.
* 02/08/94 14513 JC Changed so that records do not get overwritten.
* 06/27/94 12303 JC Inital code release
*
*******************************************************************************
*
*
* This program will load data into a file from a text file created
* by the UNLOAD.PIOPEN utility. For the format of the text file,
* see the file UNLD.PIOPEN.B.
*
* Command format:
*
* LOAD.PIOPEN [DICT] file.name [[source.dir] text.file.name]
*
EQUATE ASCII.DATA.CODE TO "A"
EQUATE FM.DATA.CODE TO "F"
EQUATE HEX.DATA.CODE TO "H"
EQUATE REC.ID.CODE TO "I"
EQUATE REC.ID.HEX.CODE TO "J"
line.type.list = ASCII.DATA.CODE
line.type.list := FM.DATA.CODE
line.type.list := HEX.DATA.CODE
line.type.list := REC.ID.CODE
line.type.list := REC.ID.HEX.CODE
GOSUB parse.command.line
GOSUB open.files
PRINT "Loading ":target.desc:" from ":source.desc:"."
* Main processing loop
end.of.input = 0
data.error = 0
lines.read = 0
records.written = 0
rec.id = ""
rec.data = ""
LOOP
READSEQ line FROM text.file ELSE end.of.input = 1
UNTIL end.of.input DO
lines.read += 1
line.type = INDEX(line.type.list, line[1,1], 1)
* This ON ... GOSUB must match the order of line.type.list
ON line.type + 1 GOSUB invalid.line,
ascii.data.line,
fm.data.line,
hex.data.line,
rec.id.line,
rec.id.hex.line
IF data.error THEN STOP
REPEAT
GOSUB end.of.record
* All done: close files, etc.
CLOSE target.file
CLOSESEQ text.file
PRINT lines.read:" lines read from ":source.desc:"."
PRINT records.written:" records written to ":target.desc:"."
STOP
**********************************************************************
*
parse.command.line:
*
* Parse the command line
*
cmd = CONVERT(" ", @FM, TRIM(@SENTENCE))
field.count = DCOUNT(cmd, @FM)
IF field.count < 2 THEN
GOSUB print.usage.message
STOP
END
dict.spec = ""
default.suffix = "_DATA"
target.file.name = cmd<2>
IF target.file.name = "DICT" THEN
dict.spec = "DICT"
default.suffix = "_DICT"
target.file.name = cmd<3>
target.desc = "the dictionary of " : target.file.name
next.field = 4
END ELSE
target.desc = target.file.name
next.field = 3
END
source.dir = "&UFD&"
BEGIN CASE
CASE next.field > field.count
* Source not specified; assume &UFD&, file.name_[DICT | DATA]
text.file.name = target.file.name : default.suffix
source.desc = text.file.name
CASE next.field = field.count
* Directory not specified, assume &UFD&
text.file.name = cmd<next.field>
source.desc = text.file.name
CASE next.field < field.count
* More to come; extract directory and file name
IF field.count > (next.field + 1) THEN
GOSUB print.usage.message
STOP
END
source.dir = cmd<next.field>
text.file.name = cmd<next.field + 1>
source.desc = text.file.name:" in ":source.dir
END CASE
RETURN
**********************************************************************
*
open.files:
*
* Open the files
*
OPENSEQ source.dir, text.file.name TO text.file ELSE
IF STATUS() = 0 THEN
PRINT "Error: ":source.desc:" does not exist!"
END ELSE
PRINT "Error opening ":source.desc:"!"
PRINT "Status code ":STATUS()
END
STOP
END
OPEN dict.spec, target.file.name TO target.file ELSE
PRINT "Can't open ":target.desc
PRINT "Status code ":STATUS()
STOP
END
RETURN
**********************************************************************
*
print.usage.message:
*
* In case of error, print a message giving the command syntax.
*
PRINT "Usage: ":cmd<1>:" [DICT] file.name [[source.dir] text.file.name]"
RETURN
**********************************************************************
*
invalid.line:
*
error.type = "invalid line type ":line[1,1]
GOSUB got.data.error
RETURN
**********************************************************************
*
got.data.error:
*
PRINT "Error: ":error.type:"."
PRINT "At line ":lines.read:" of ":source.desc:"."
data.error = 1
RETURN
**********************************************************************
*
ascii.data.line:
*
* Key A
* What ASCII data
* Format data characters <period>
rec.data := line[2, LEN(line) - 2]
RETURN
**********************************************************************
*
fm.data.line:
*
* Key F
* What ASCII data with implied field mark
* Format data characters <period>
rec.data := @FM : line[2, LEN(line) - 2]
RETURN
**********************************************************************
*
hex.data.line:
*
* Key H
* What Hexadecimal data
* Format hex codes for data characters
rec.data := ICONV(line[2, LEN(line)], "MX0C")
RETURN
**********************************************************************
*
rec.id.line:
*
* Key I
* What Record ID, in plain text
* Format <record length> <record ID> <period>
*
GOSUB end.of.record
IF data.error THEN RETURN
GOSUB extract.record.length
IF data.error THEN RETURN
rec.id = line[first.space + 1, (len(line) - first.space - 1)]
RETURN
**********************************************************************
*
extract.record.length:
*
* Extract the record length field from a record ID line.
*
* Inputs: line
*
* Outputs: first.space Position of delimiting space
* rec.length Record length
* data.error Set if line format is wrong
*
first.space = INDEX(line, " ", 1)
IF first.space = 0 THEN
error.type = "incorrect line format; no spaces"
GOSUB got.data.error
RETURN
END
rec.length = line[2, first.space - 2]
IF NUM(rec.length) THEN
rec.length += 0
END ELSE
error.type = "non-numeric record length '":rec.length:"'"
GOSUB got.data.error
RETURN
END
RETURN
**********************************************************************
*
rec.id.hex.line:
*
* Key J
* What Hex-encoded record ID
* Format <record length> <record ID>
*
GOSUB end.of.record
IF data.error THEN RETURN
GOSUB extract.record.length
IF data.error THEN RETURN
rec.id = ICONV(line[first.space + 1, len(line)], "MX0C")
RETURN
**********************************************************************
*
end.of.record:
*
* This routine is called whenever there may be a record to be written.
* It expects the following variables to be set up:
*
* rec.id record ID, or empty if there is no record
* rec.length expected length of record
* rec.data record data read in so far
*
IF LEN(rec.id) = 0 THEN
* Nothing to do
RETURN
END
IF rec.length # LEN(rec.data) THEN
error.type = "data length error: expected ":rec.length
error.type := ", found ":LEN(rec.data)
GOSUB got.data.error
RETURN
END
READ dummy FROM target.file, rec.id
ELSE
WRITE rec.data ON target.file, rec.id
END
records.written += 1
rec.id = ""
rec.length = 0
rec.data = ""
RETURN
END