diff --git a/specs/quint/specs/blocksync/blocksync.qnt b/specs/quint/specs/blocksync/blocksync.qnt index b393745ef..57bb4e997 100644 --- a/specs/quint/specs/blocksync/blocksync.qnt +++ b/specs/quint/specs/blocksync/blocksync.qnt @@ -6,100 +6,104 @@ module blocksync { - import types.* from "../types" - export types.* - - type Option[a] = - | Some(a) - | None - - type StatusMsg = { - peer: Address, - base: Height, - top: Height - } - - type BlockRange = { - base: Height, - top: Height - } - - type ReqType = - | SyncCertificate - | SyncBlock - | SyncBlockStoreEntry - - type RequestMsg = { - client: Address, - server: Address, - rtype: ReqType, - height: Height - } - - pure def emptyReqMsg = { - client: "", - server: "", - rtype: SyncCertificate, - height: -1 - } - - type Response = - | RespBlock(Proposal) - | RespCertificate(Set[Vote]) - | RespBlockStoreEntry(BlockStoreEntry) - - type ResponseMsg = { - client: Address, - server: Address, - height: Height, - response: Response, - } - - pure def matchingMessages(req: RequestMsg, resp: ResponseMsg): bool = - and { - req.client == resp.client, - req.server == resp.server, - req.height == resp.height, - } - - - pure val emptyResponseMsg = { - client: "", - server: "", - height: -1, - response: RespBlock(emptyProposal), - } - - // ************* - // State machine - // ************* - - // Messages exchanged by nodes (clients and servers) - var statusBuffer : Address -> Set[StatusMsg] - var requestsBuffer : Address -> Set[RequestMsg] - var responsesBuffer : Address -> Set[ResponseMsg] - - // Auxiliary functions for sending messages - - pure def broadcastStatusMsg(buffer: Address -> Set[StatusMsg], sm: StatusMsg): Address -> Set[StatusMsg] = - buffer.keys().mapBy(x => if (x == sm.peer) // don't send to yourself - buffer.get(x) - else - { ...buffer.get(x).union(Set(sm)) }) - - // put the response message in the buffer of the client - pure def sendResponse(buffer: Address -> Set[ResponseMsg], m: ResponseMsg): Address -> Set[ResponseMsg] = - buffer.put(m.client, { ...buffer.get(m.client).union(Set(m)) }) - - action initBsync(nodes) = all { - statusBuffer' = nodes.mapBy(v => Set()), - requestsBuffer' = nodes.mapBy(v => Set()), - responsesBuffer' = nodes.mapBy (v => Set()), - } - - action unchangedBsync = all { - statusBuffer' = statusBuffer, - requestsBuffer' = requestsBuffer, - responsesBuffer' = responsesBuffer, - } + import types.* from "../types" + export types.* + + type Option[a] = + | Some(a) + | None + + type StatusMsg = { + peer: Address, + base: Height, + top: Height + } + + type BlockRange = { + base: Height, + top: Height + } + + type ReqType = + | SyncCertificate + | SyncBlock + | SyncBlockStoreEntry + + type RequestMsg = { + client: Address, + server: Address, + rtype: ReqType, + height: Height + } + + pure def emptyReqMsg = { + client: "", + server: "", + rtype: SyncCertificate, + height: -1 + } + + type Response = + | RespBlock(Proposal) + | RespCertificate(Set[Vote]) + | RespBlockStoreEntry(BlockStoreEntry) + + type ResponseMsg = { + client: Address, + server: Address, + height: Height, + response: Response, + } + + pure def matchingMessages(req: RequestMsg, resp: ResponseMsg): bool = + and { + req.client == resp.client, + req.server == resp.server, + req.height == resp.height, + } + + + pure val emptyResponseMsg = { + client: "", + server: "", + height: -1, + response: RespBlock(emptyProposal), + } + + // ************* + // State machine + // ************* + + /// Messages exchanged by nodes (clients and servers) + var statusBuffer : Address -> Set[StatusMsg] + var requestsBuffer : Address -> Set[RequestMsg] + var responsesBuffer : Address -> Set[ResponseMsg] + + // Auxiliary functions for sending messages + + /// Put the status message in the buffer of every client. + pure def broadcastStatusMsg(buffer: Address -> Set[StatusMsg], sm: StatusMsg): Address -> Set[StatusMsg] = + buffer.keys().mapBy(x => + if (x == sm.peer) // don't send to yourself + buffer.get(x) + else + { ...buffer.get(x).union(Set(sm)) } + ) + + /// Put the response message in the buffer of the requesting client. + pure def sendResponse(buffer: Address -> Set[ResponseMsg], m: ResponseMsg): Address -> Set[ResponseMsg] = + buffer.put(m.client, { ...buffer.get(m.client).union(Set(m)) }) + + action initBsync(nodes) = all { + statusBuffer' = nodes.mapBy(v => Set()), + requestsBuffer' = nodes.mapBy(v => Set()), + responsesBuffer' = nodes.mapBy (v => Set()), + } + + action unchangedBsync = all { + statusBuffer' = statusBuffer, + requestsBuffer' = requestsBuffer, + responsesBuffer' = responsesBuffer, + } + }