317 lines
8.5 KiB
Plaintext
317 lines
8.5 KiB
Plaintext
|
********************************************************************************
|
||
|
*
|
||
|
* 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
|
||
|
|