PACKET dos manager multi DEFINES (* Copyright (C) 1985 *) (* Frank Klapper *) provide channel, (* 25.03.86 *) dos manager: LET std archive channel = 31, ack = 0, second phase ack = 5, false code = 6, fetch code = 11, save code = 12, exists code = 13, erase code = 14, list code = 15, all code = 17, clear code = 18, reserve code = 19, free code = 20, check read code = 22, quote = """"; BOUND STRUCT (TEXT name, pass) VAR msg; TASK VAR order task; INT VAR dos channel; REAL VAR last access time := 0.0; TASK VAR disk owner := niltask; PROC provide channel (INT CONST channel): dos channel := channel END PROC provide channel; (*COND FLOPPY provide channel (std archive channel); ENDCOND*) (*COND HDU*) provide channel (29) (*ENDCOND*) PROC dos manager: dos manager (dos channel) END PROC dos manager; PROC dos manager (INT CONST channel): (*COND FLOPPY load shard interface table; ENDCOND*) dos channel := channel; task password ("-"); global manager (PROC (DATASPACE VAR, INT CONST, INT CONST, TASK CONST) dos manager) END PROC dos manager; PROC dos manager (DATASPACE VAR ds, INT CONST order code, phase, TASK CONST from task): enable stop; order task := from task; msg := ds; IF NOT (order task = disk owner) AND order code <> free code AND order code <> reserve code THEN errorstop ("DOS nicht angemeldet") FI; SELECT order code OF CASE fetch code : fetch file CASE save code : save file CASE erase code : erase file CASE clear code : clear disk CASE exists code : exists file CASE list code : list disk CASE all code : deliver directory CASE reserve code : reserve CASE free code : free CASE check read code: check OTHERWISE errorstop ("unbekannter Auftrag für Task: " + name (myself)) END SELECT. fetch file: disk fetch (msg.name, ds); manager ok (ds). check: disk check (msg.name); manager message (expanded name (msg.name, TRUE) + " ohne Fehler gelesen"). save file: IF phase = 1 THEN save first phase ELSE save second phase FI. save first phase: BOOL VAR overwrite question; disk save first phase (msg.name, overwrite question); IF overwrite question THEN manager question (expanded name (msg.name, FALSE) + " auf der MS-DOS Disk ueberschreiben") ELSE send (order task, second phase ack, ds) FI. save second phase: disable stop; disk save second phase (ds); forget (ds) ; ds := nilspace ; enable stop; manager ok (ds). clear disk: IF NOT (from task = disk owner) THEN error stop ("DOS nicht angemeldet") FI; IF phase = 1 THEN manager question ("Diskette loeschen") ELSE disk clear; manager ok (ds) FI. erase file: IF disk exists (msg.name) THEN IF phase = 1 THEN manager question (expanded name (msg.name, TRUE) + " auf der MS-DOS Disk loeschen") ELSE disk erase (msg.name); manager ok (ds) FI ELSE manager message ("die Datei " + expanded name (msg.name, TRUE) + " gibt es nicht auf der MS-DOS Disk") FI. exists file: IF disk exists (msg.name) THEN manager ok (ds) ELSE send (order task, false code, ds) FI. list disk: disk list (ds); manager ok (ds). deliver directory: forget (ds); ds := nilspace; BOUND THESAURUS VAR all names := ds; all names := disk all; manager ok (ds). reserve: IF reserve or free permitted THEN do continue channel; disk owner := from task; disk reserve (msg.name); manager ok (ds) ELSE errorstop ("Archivlaufwerk wird von Task """+ name (disk owner) + """ benutzt") FI. do continue channel: IF channel <> dos channel THEN continue channel (dos channel) FI. reserve or free permitted : from task = disk owner OR last access more than five minutes ago OR disk owner = niltask OR NOT (exists (disk owner) OR station(disk owner) <> station (myself)). last access more than five minutes ago : abs (last access time - clock (1)) > 300.0. free: IF reserve or free permitted THEN disk free; disk owner := niltask; break (quiet); manager ok (ds) ELSE manager message ("DOS nicht angemeldet") FI. END PROC dos manager; PROC manager ok (DATASPACE VAR ds): send (order task, ack, ds); last access time := clock (1). END PROC manager ok; TEXT PROC expanded name (TEXT CONST name, BOOL CONST status): text (quote + adapted name (name, status) + quote, 14) END PROC expanded name; END PACKET dos manager multi;