XNSPrintCommands.mesa
Copyright Ó 1985, 1986, 1987 by Xerox Corporation. All rights reserved.
Russ Atkinson, April 2, 1985 4:22:08 pm PST
Bill Jackson (bj) February 6, 1987 5:42:53 am PST
Demers, June 6, 1986 3:09:39 pm PDT
DIRECTORY
Args USING [Arg, ArgsGet, NArgs],
BasicTime USING [GMT, ToNSTime],
CHNameP2V0 USING [Name],
Commander USING [CommandProc, Register],
CommandTool USING [ArgumentVector, Failed, Parse],
File USING [GetVolumeName, SystemVolume],
FileNames USING [ResolveRelativePath],
FS USING [ComponentPositions, Error, ErrorDesc, ExpandName, FileInfo, StreamOpen],
FSPseudoServers USING [TranslateForRead, TranslateForWrite],
IO USING [Close, PutF, PutRope, rope, STREAM],
Process USING [CheckForAbort],
Rope USING [Cat, Concat, Equal, Length, ROPE, Substr],
ThisMachine USING [Name],
PrintingP4V3 USING [PrinterProperties, PrinterStatus, RequestID],
PrintingP4V3Aux USING [ExposePrinterProperties, ExposePrinterStatus, ExposeRequestID],
XNSPrintRequestManager;
XNSPrintCommands: CEDAR PROGRAM
IMPORTS Args, BasicTime, Commander, CommandTool, File, FileNames, FS, FSPseudoServers, IO, PrintingP4V3Aux, Process, Rope, ThisMachine, XNSPrintRequestManager ~ {
OPEN CHName: CHNameP2V0, Printing: PrintingP4V3, PrintingAux: PrintingP4V3Aux;
ROPE: TYPE ~ Rope.ROPE;
Commander Constants
GetPrintStatus: ROPE = "GetPrintStatus";
statusdoc: ROPE = "{Printer}*\nFind out the status of an XNS based printer.";
statususage: ROPE = Rope.Concat["Usage: GetPrintStatus ", statusdoc];
Commander Constants
GetPrintProperties: ROPE = "GetPrintProperties";
propdoc: ROPE = "{Printer}*\nFind out the properties of an XNS based printer.\nSwitches: <none yet>";
propusage: ROPE = Rope.Concat["Usage: GetPrintProperties ", propdoc];
SendIPMaster: ROPE ~ "SendIPMaster";
senddoc: ROPE ~ "<IPMaster> [-c <copies> -h <serviceName> -1 -2 -f <firstPageNumber> -l <lastPageNumber>]\nTransmit a master to an XNS based printer.\nSwitches:\n -c <copies> print multiple copies\n -h <serviceName> print on that service\n -1 print one-sided\n -2 print two-sided\n -f <firstPageNumber>\n -l <lastPageNumber>";
sendusage: ROPE ~ Rope.Concat["Usage: SendIPMaster ", senddoc];
Decode Procs
DecodeRequestID: PROC [out: IO.STREAM, request: XNSPrintRequestManager.PrintRequest] ~ {
msg: ROPE;
IO.PutF[out, " Service: [%g:%g:%g]\n ",
IO.rope[request.distinguishedName.object],
IO.rope[request.distinguishedName.domain],
IO.rope[request.distinguishedName.organization]
];
msg ← Rope.Concat[PrintingAux.ExposeRequestID[request.requestID, 1], "\n"]; -- nest 2 spaces
IO.PutRope[out, msg];
};
DecodeProperties: PROC [out: IO.STREAM, service: CHName.Name, status: Printing.PrinterProperties] ~ {
msg: ROPENIL;
IO.PutF[out, " Service: [%g:%g:%g]\n ",
IO.rope[service.object],
IO.rope[service.domain],
IO.rope[service.organization]
];
msg ← Rope.Concat[PrintingAux.ExposePrinterProperties[status, 1], "\n"]; -- nest 2 spaces
IO.PutRope[out, msg];
};
DecodeStatus: PROC [out: IO.STREAM, service: CHName.Name, status: Printing.PrinterStatus] ~ {
msg: ROPENIL;
IO.PutF[out, " Service: [%g:%g:%g]\n ",
IO.rope[service.object],
IO.rope[service.domain],
IO.rope[service.organization]
];
msg ← Rope.Concat[PrintingAux.ExposePrinterStatus[status, 1], "\n"]; -- nest 2 spaces
IO.PutRope[out, msg];
};
Helper PROCs
FSErrorMsg: PROC [error: FS.ErrorDesc] RETURNS [ROPE] ~ {
RETURN[Rope.Concat[FSErrorMsgBrief[error], "\n"]];
};
FSErrorMsgBrief: PROC [error: FS.ErrorDesc] RETURNS [ROPE] ~ {
SELECT error.group FROM
lock => {
RETURN[" -- locked!"];
};
ENDCASE => {
IF (error.code = $unknownFile)
THEN RETURN [" -- not found!"]
ELSE RETURN[Rope.Concat["\n -- FS.Error: ", error.explanation]];
};
};
FixUpFilename: PROC [name: ROPENIL, copyFrom: BOOL] RETURNS [newName: ROPE] ~ {
body: ROPE;
platformHost: ROPE ← ThisMachine.Name[];
platformVolume: ROPE ← File.GetVolumeName[File.SystemVolume[]];
prefix: ROPE;
cp: FS.ComponentPositions;
[fullFName: newName, cp: cp] ← FS.ExpandName[name];
prefix ← Rope.Substr[newName, 0, 4];
body ← Rope.Substr[newName, 4, Rope.Length[newName]];
IF Rope.Equal[prefix, "[]<>"] THEN {
newName ← Rope.Cat["[", platformHost, "]<", platformVolume, ">"];
newName ← Rope.Cat[newName, body];
}
ELSE newName ← Rope.Cat[
"[",
IF copyFrom THEN
FSPseudoServers.TranslateForRead[Rope.Substr[newName, cp.server.start, cp.server.length]].first
ELSE
FSPseudoServers.TranslateForWrite[Rope.Substr[newName, cp.server.start, cp.server.length]],
"]<",
Rope.Substr[newName, cp.dir.start, Rope.Length[newName]]];
};
Commander Procs
GetPrintPropertiesProc: Commander.CommandProc ~ {
argsProcessed: NAT ← 0;
argv: CommandTool.ArgumentVector ← CommandTool.Parse[cmd: cmd, starExpand: FALSE
! CommandTool.Failed => {msg ← errorMsg; GO TO failed}];
out: IO.STREAM ~ cmd.out;
CheckProperties: PROC [arg: ROPE] ~ {
service: CHName.Name;
status: Printing.PrinterProperties;
argsProcessed ← argsProcessed + 1;
Process.CheckForAbort[];
[service, status] ← XNSPrintRequestManager.GetPrinterProperties[arg];
DecodeProperties[out, service, status];
};
FOR i: NAT IN [1..argv.argc) DO
printerName: ROPE ~ argv[i];
Process.CheckForAbort[];
IF (Rope.Length[printerName] = 0) THEN LOOP;
CheckProperties[printerName];
ENDLOOP;
SELECT argsProcessed FROM
0 => {
context: XNSPrintRequestManager.Context;
context ← XNSPrintRequestManager.GetDefaults[];
IF (context.printerName = NIL)
THEN msg ← propusage
ELSE CheckProperties[context.printerName];
};
ENDCASE => { NULL };
EXITS
failed => {result ← $Failure};
};
GetPrintStatusProc: Commander.CommandProc ~ {
argsProcessed: NAT ← 0;
argv: CommandTool.ArgumentVector ← CommandTool.Parse[cmd: cmd, starExpand: FALSE
! CommandTool.Failed => { msg ← errorMsg; GO TO failed; }];
out: IO.STREAM ~ cmd.out;
CheckPrinter: PROC [arg: ROPE] = {
service: CHName.Name;
status: Printing.PrinterStatus;
argsProcessed ← argsProcessed + 1;
Process.CheckForAbort[];
[service, status] ← XNSPrintRequestManager.GetPrinterStatus[arg];
DecodeStatus[out, service, status];
};
FOR i: NAT IN [1..argv.argc) DO
printerName: ROPE ~ argv[i];
Process.CheckForAbort[];
IF (Rope.Length[printerName] = 0) THEN LOOP;
CheckPrinter[printerName];
ENDLOOP;
SELECT argsProcessed FROM
0 => {
context: XNSPrintRequestManager.Context;
context ← XNSPrintRequestManager.GetDefaults[];
IF (context.printerName = NIL)
THEN msg ← statususage
ELSE CheckPrinter[context.printerName];
};
ENDCASE => NULL;
EXITS
failed => {result ← $Failure};
};
SendMasterProc: Commander.CommandProc ~ {
context: XNSPrintRequestManager.Context;
request: XNSPrintRequestManager.PrintRequest;
ok: BOOL;
out: IO.STREAM ~ cmd.out;
name, copies, host, oneSided, twoSided, first, last, pages: Args.Arg;
PrintAFile: PROC [name: ROPE] RETURNS [request: XNSPrintRequestManager.PrintRequest] ~ {
s: IO.STREAM;
Process.CheckForAbort[];
s ← FS.StreamOpen[name
! FS.Error => IF (error.group # $bug)
THEN { msg ← FSErrorMsg[error]; ERROR CommandTool.Failed[msg]; }
];
request ← XNSPrintRequestManager.PrintFromStream[s, context];
DecodeRequestID[out, request];
IF (s # NIL) THEN IO.Close[s];
};
IF Args.NArgs[cmd] = 0 THEN RETURN[$Failure, sendusage];
[ok, name, copies, host, oneSided, twoSided, first, last, pages] ← Args.ArgsGet[cmd, "%s-c%i-h%s-1%b-2%b-f%i-l%i-p%i"];
IF NOT ok THEN RETURN[$Failure, "Command syntax error."];
context ← XNSPrintRequestManager.GetDefaults[];
IF copies.ok THEN context.copyCount ← copies.int;
IF host.ok THEN context.printerName ← host.rope;
IF twoSided.ok AND twoSided.bool THEN context.twoSided ← TRUE;
IF oneSided.ok AND oneSided.bool THEN context.twoSided ← FALSE;
IF first.ok THEN context.pageFirst ← first.int;
IF last.ok THEN context.pageLast ← last.int;
IF pages.ok THEN context.pageLast ← context.pageFirst+pages.int;
name.rope ← FileNames.ResolveRelativePath[name.rope];
context.printObjectName ← FixUpFilename[name.rope, FALSE];
{
fullFName: ROPE;
attachedTo: ROPE;
keep: CARDINAL;
bytes: INT;
created: BasicTime.GMT;
[fullFName, attachedTo, keep, bytes, created] ← FS.FileInfo[name~name.rope, remoteCheck~FALSE];
context.printObjectCreateDate ← BasicTime.ToNSTime[created];
};
IO.PutF[out, " Sending %s to %s\n",
IO.rope[context.printObjectName],
IO.rope[context.printerName]
];
request ← PrintAFile[name.rope];
XNSPrintRequestManager.RegisterPrintRequest[request]; -- registered for later status requests!
request ← NIL;
};
Init: PROC ~ {
Commander.Register[GetPrintProperties, GetPrintPropertiesProc, propdoc];
Commander.Register[GetPrintStatus, GetPrintStatusProc, statusdoc];
Commander.Register[SendIPMaster, SendMasterProc, senddoc];
};
Init[];
}...