<> <> <> DIRECTORY IO, RefTab USING [EachPairAction, Ref, Val, Create, Fetch, Store, Pairs], Rope USING [ROPE], ViewerClasses USING [Viewer], ViewerIO USING [CreateViewerStreams], ViewerOps USING [FindViewer, OpenIcon], WalnutStream USING [Open, PeekEntry]; ScanLog: CEDAR PROGRAM IMPORTS IO, RefTab, ViewerIO, ViewerOps, WalnutStream = BEGIN ROPE: TYPE = Rope.ROPE; STREAM: TYPE = IO.STREAM; out: STREAM _ NIL; Xyz: TYPE = REF ValueObject; ValueObject: TYPE = RECORD[num, bytes: INT _ 0]; DebugStream: PROC RETURNS [IO.STREAM] = { v: ViewerClasses.Viewer _ ViewerOps.FindViewer["NewWalnut ScanLog"]; out: IO.STREAM _ ViewerIO.CreateViewerStreams["NewWalnut ScanLog", v].out; IF v#NIL THEN IF v.iconic THEN ViewerOps.OpenIcon[v]; RETURN[out]; }; Scan: PROC[logFile: ROPE] = { ident: ATOM; at, length: INT; strm: STREAM; table: RefTab.Ref _ RefTab.Create[]; found: BOOL; val: RefTab.Val; count: INT _ 0; ForPrinting: RefTab.EachPairAction = { ident: ATOM _ NARROW[key]; this: Xyz _ NARROW[val]; out.PutF["Ident: %g, num: %g, bytes: %g\n", IO.atom[ident], IO.int[this.num], IO.int[this.bytes] ]; RETURN[FALSE]; -- don't quit }; out _ DebugStream[]; strm _ WalnutStream.Open[name: logFile, readOnly: TRUE]; out.PutF["\n Scanning the logfile: %g\n\n(0)", IO.rope[logFile]]; strm.SetIndex[at _ 0]; DO this: Xyz; [ident, , length] _ WalnutStream.PeekEntry[strm]; IF ident = NIL THEN EXIT; strm.SetIndex[at _ at + length]; [found, val] _ RefTab.Fetch[table, ident]; IF found THEN { this _ NARROW[val]; this.num _ this.num + 1; this.bytes _ this.bytes + length; } ELSE this _ NEW[ValueObject _ [1, length]]; [] _ RefTab.Store[table, ident, this]; IF (count _ count + 1) MOD 10 = 0 THEN { IF count MOD 100 = 0 THEN out.PutF["(%g)", IO.int[count]] ELSE out.PutChar['~]; }; ENDLOOP; out.PutF["\n\n\t\tThe log contained the following %g entries:\n", IO.int[count]]; [] _ RefTab.Pairs[table, ForPrinting]; strm.Close[]; }; END.