-- Transport mechanism: FSP implementation of R-Lists -- [Juniper]<dms>ms>FSPRList.mesa -- Andrew Birrell 15-Oct-80 15:26:14 DIRECTORY BodyDefs USING [maxRNameLength, RName, RNameSize], ProtocolDefs USING [Handle, ReceiveCount, ReceiveRName], RListDefs USING [], Storage USING [Free, FreeString, Node, String], String USING [AppendString]; FSPRList: PROGRAM IMPORTS BodyDefs, ProtocolDefs, String, Storage EXPORTS RListDefs = BEGIN RListHandle: PUBLIC TYPE = POINTER TO RListItem; RListItem: TYPE = RECORD[next: RListHandle, name: BodyDefs.RName]; noList: RListHandle = NIL; Receive: PUBLIC PROC[str: ProtocolDefs.Handle] RETURNS[list: RListHandle] = BEGIN buffer: BodyDefs.RName = [BodyDefs.maxRNameLength]; count: CARDINAL ← ProtocolDefs.ReceiveCount[str]; tail: POINTER TO RListHandle ← @list; list ← noList; WHILE count > 0 DO ENABLE UNWIND => Close[list]; ProtocolDefs.ReceiveRName[str, buffer]; count ← count - BodyDefs.RNameSize[buffer]; BEGIN new: RListHandle = Storage.Node[SIZE[RListItem]]; new↑ ← [name: Storage.String[buffer.length], next: noList]; String.AppendString[new.name, buffer]; tail↑ ← new; tail ← @(new.next); END; ENDLOOP; END; Enumerate: PUBLIC PROC[list: RListHandle, work: PROC[BodyDefs.RName]RETURNS[done:BOOLEAN] ] = BEGIN FOR list ← list, list.next UNTIL list = noList OR work[list.name] DO NULL ENDLOOP; END; Close: PUBLIC PROC[list: RListHandle] = BEGIN WHILE list # noList DO next: RListHandle = list.next; Storage.FreeString[list.name]; Storage.Free[list]; list ← next; ENDLOOP; END; END.