// SpruceFiles.D -- file and stream-level declarations

get "streams.d"

manifest
[
//Must be ne 0 for WindowChangeType
FILERW=1
//Read-write
FILERO=2
//Read only
FILEWO=3
//Write only
FILEPress = #1000
//First (or only) Press File -- in Server system,
FILEPressMask = #777
// To limit subfile names -- see SPruceFile.fileCode
// Press Subfiles are labelled from
// (FILEPress .. FILEPress+FILEPressMask]
]

manifest
[
DISK31=0
//File resides on Model 31
DISK31B=1
//Second model 31 disk
DISKT80=2
//File resides on T80 disk
maxSpooled = 20//temp!!!!!
]

manifest stTypeSpruce = #10301

// Isf operation codes, Spruce File access codes
manifest [
// op codes to Schedule level of Spruce Concurrent Files
opRead = 0
opWrite = 1
opReschedule = 2 // reschedule previous operation for this page

// op codes for ISF, file access codes, etc.
isfRead = 0
isfReadExtend = 1
isfWrite = -1
spruceReadAccess = 1
spruceWriteAccess = -1
forward = 1 // Spruce Stream Directions
backward = -1
maxBUFFERS = 10
maxFmapLen = 256//biggest reasonable map
ksTypeWriteBeforeRead = 4 // June 9, 1977 2:49 PM, not implemented yet
]

// Checkpoint levels
manifest [
LEVSharedVersions = 0// versions from both systems, for validity checking
LEVSharedInstStatics = 1// trans-system defaults after inst.
LEVSharedPrinterAttr =2//[inst modified] printer descriptions
LEVEternalStatics = 3// values saved between complete re-initializations
LEVInstallationStatics = 4// defaults after installation
LEVSharedInitStatics = 5// trans-system defaults after init.
LEVInitialStatics = 6// defaults after initialization
LEVSharedRun = 7// spooler to printer information
LEVRun = 8// spooler information saved during printing
LEVRunDocs = 9// File printing requests
LEVReport = 10// printer to spooler reporting information
maxLEV = 11
]

structure FPOS: [ msAddr word; lsAddr word ]
structure Q: [ head word; tail word ]

// note that the length of this structure (lFSp) is known globally as 12.
// this declaration must agree with the machine-language declaration
// in streamsml.a
structure FSp[
charPtr word// 1 for left byte, 0 for right
wordPtr word// points to word containing the
// last byte, not the next one
count word// -(number of items left+1)
dirty word
eof word
putOverflow word// overflow on output
getOverflow word// overflow on input
putTwoBytesOverflow word
// ** getTwoBytesOverflow moved into SS, where there’s room
itemSize word// in bytes; must be 1 or 2
endPos word// (relative) address of first
// byte not included in count
savedGets word
]

// We now use the declaration of FSp to expand the declaration of FS
structure FSx[
@FS =
[
blank word offset FS.fsp/16
@FSp
]
]
manifest lFSx=size FSx/16

structure SS:
[
fS: @FS
// ** should be in FSp, but there’s not room
getTwoBytesOverflow word
savedPuts word// SetSpruceEof stores things here
spruceFile word// >>SPruceFile -- map, memory buffers
sprucePage word// For page stream occupies
lowPage word// below this is "eof"
lowChars word// char pos. of 1st infile char in lowPage
highPage word// above this is "eof"
highChars word// char pos. of 1st eof char in highPage
ahead word// hint of direction pages will be read, number of pages ahead/behind to stay
type word
stepSize word// # pages to advance on Put or Get overflow
]
manifest lSS = size SS/16

// N.B. Machine code in SpruceFilesMl depends on the placement of entries in above
// structure and in SPruceFile; they must be changed together.

structure SPrucePage:
[
link word
status word =
[
dirty bit 1// allows delayed writing of dirty pages -- may not be needed
valid bit 1
scheduled bit 1// this page has been scheduled for disk activity
accessors bit 4 // # streams intruding upon this page (max 15)
operation bit 9// operation in progress or last performed on this page
]
pageNumber word// 0 if not allocated --about 16000 pp. max.
numChars word// in this page (0-#4000)
cb word// cb from file’s cbzone while page is undergoing disk activity
buffer word// address of buffer for page (lv .+1)
// data↑0,pagesize-1 word// buffer data goes here
]
manifest minLenSPrucePage = size SPrucePage/16

structure SPruceFile:
[
map word// >>FM: Isf file map, includes FP
offSet word// alto file page corresp. to Spruce (sub)file page 1
maxPages word// numPages in superFile
lvSuperFile word = isSubFile word// pointer to static with file pointer for subfiles, 0 for main
numPages word// page length of file
numChars word// in last page -- eof pos in last page
// word boundary
backwards bit// pages arranged backwards (applies only to subfiles)
numCbs bit 7// disk cbs to be allocated for file when active
numBuffers byte// max resident disk pages
// word boundary
fileCode bit 12// FILEMeter, FILEBands, Press subfile indices, etc.
reschedule bit// when on, some or all disk operations need to be rescheduled
deviceCode bit 3// DISK31, DISK31B, DISKT80
pageSize word// in words of disk pages
lnPageSize word
zone word = valid word// for allocating buffers; 0 => file not initialized
readers word// >0 to count readers, -1 for one writer, 0 if no access
[ memQ @Q// resident buffers
diskQ @Q// buffers scheduled for disk activity
cbQ @Q ] =// cb queue, for rescuing cbz entries at earliest opportunity
bufQs↑0,2 @Q
cbz word// cb zone, allocated while streams are open
fParams word
]
manifest lenSPruceFile = size SPruceFile/16

structure FParams:
[
InitializeCbStorage word
GetCb word
DoDiskCommand word
lvDefaultErrorRtn word
lCB word
lCBZ word
offsetCleanup word
offsetRetry word
offsetLabelAddress word
offsetLabelNumChars word
nextDiskCommand word // address of nextDiskCommand for this device
]

// checkpoint record structure

structure CHecord:
[
type bit 4; length bit 12
//time: word 2 // time entire checkpoint operation started
//checkData ↑1,1 word
]
// manifest minLenCHecord = (offset CHecord.checkData)/16
manifest LenCHecord = size CHecord/16

// DCS, July 8, 1977 10:39 AM, DCS Spruce.Decl stuff added
// July 11, 1977 5:59 PM, SPrucePage structure CONTAINS buffer data
// July 14, 1977 9:45 AM, truncate deviceCode to add status byte to SPruceFile
// July 14, 1977 1:38 PM, modify SPruceFile to allow wrap around
// July 15, 1977 4:56 PM, add link, fileCode to SPruceFile
// July 19, 1977 2:21 PM, revise CHecord format!
// July 22, 1977 2:32 PM, add LEVRun, LEVRunDocs checkpoint levels
// July 25, 1977 12:57 PM, add FILEPressMask, rename InLd/OutLd msg structs.
// August 5, 1977 9:05 AM, add backwards indicator in SpruceFile
// August 7, 1977 8:16 AM, modify TOSpoolerMsg
// August 7, 1977 10:18 AM, move InLd/OutLd structures, completion,
// error codes to Spruce.D
// September 3, 1978 6:42 PM, superFile -> lvSuperFile in SPruceFile
// September 15, 1978 8:56 AM, comment out FILE... manifests -- now obsolete
// October 11, 1978 3:28 PM, delete direction, change ahead
// October 12, 1978 12:07 AM, rearrange SPrucePage
// October 24, 1978 1:27 PM, add stepSize to streams (what a kludge!)
// October 27, 1978 1:58 PM, add fs base level routines to file structure
// October 31, 1978 11:10 PM, add FParam structure, ref to it in SPruceFile
// November 30, 1978 10:31 AM, add checkpoint level for printer attributes
// February 3, 1981 2:42 PM, change comments in FILEPressMask area
// September 23, 1982 5:31 PM Add LEVLocalDocs - bumped other levels
// September 30, 1982 5:17 PM Restore original checkpoint levels, changed
// CHecord structure (removing useless fields)