ibc icon indicating copy to clipboard operation
ibc copied to clipboard

ICS4: question on channel close

Open ancazamfir opened this issue 4 years ago • 13 comments

Summary

What is the reason a channel cannot be closed if its connection is not in open state?

For Admin Use

  • [ ] Not duplicate issue
  • [ ] Appropriate labels applied
  • [ ] Appropriate contributors tagged
  • [ ] Contributor assigned/self-assigned

ancazamfir avatar Feb 09 '21 09:02 ancazamfir

This seems like a question for the specification cc @cwgoes

colin-axner avatar Feb 10 '21 11:02 colin-axner

Connections can never be closed, so if a connection is not in OPEN state the connection handshake has not completed and the channel handshake should not have been completed either. It's kinda an edge case I suppose but I don't think it's a problem, unless you have a particular scenario in mind?

(the other reason is that state verification is required to close a channel in the "polite" way which is what we're referring to)

cwgoes avatar Feb 10 '21 21:02 cwgoes

The scenario I had in mind was with the optimistic channel handshake and packet sends. Assume the connection and channel are in Init state and the application sends some packets. Before the connection and channel are open, the application wants to close the connection. In this case the channel close will be rejected. Not sure what is supposed to happen to those packets in this case.

ancazamfir avatar Feb 11 '21 07:02 ancazamfir

The application wants to close the connection, or the application wants to close the channel?

If the connection has never been opened, the packets can never be received, either way, right?

cwgoes avatar Feb 11 '21 10:02 cwgoes

Yes sorry, I meant application wants to close the channel. The packets have not been received but they have been sent. Their commitments are stored on the chain. A relayer will neither send nor timeout those.

ancazamfir avatar Feb 11 '21 11:02 ancazamfir

Good question, I normally would think they could be timed out, but the counterparty channel could probably never close and the timeout verification requires an open channel. I believe we have discussed this previously and the conclusion was that optimistic sends comes with risk of unrecoverable packets. Though now I think I'm discussing something unrelated to your original question

colin-axner avatar Feb 11 '21 12:02 colin-axner

Optimistic sends come with the risk of unrecoverable packets, but this is true regardless of whether a channel close is attempted.

cwgoes avatar Feb 11 '21 12:02 cwgoes

True, here is another scenario and question for normal case:

  • channel is Open on both A and B
  • a send_packet is written on A
  • relayer sends the recv_packet to B which is acknowledged on B
  • A initiates channel close
  • relayer sends packet ack to A which is rejected

So if an application has meaningful actions in OnAcknowledgementPacket (either for positive or regative acks) it should not close a channel with unreceived acks. Sorry if I'm trying to state the obvious here. Also want to make sure it's ok for the relayer to not send the acks to a closed channel (we currently do and retrying many times)

ancazamfir avatar Feb 11 '21 13:02 ancazamfir

Yes, that scenario is possible. Applications may wish to deny or block channel closure for this reason. Perhaps we should consider implementing a "graceful" closure process which is multi-step and e.g. starts closing the channel, waits for all pending packets or acknowledgements to be processed, and finally closes it completely only when they are, but we haven't thought through this in depth yet.

It's fine for the relayer not to send acknowledgements to a closed channel, as least at the moment, since they will fail.

Generally, we need to think more about what the semantics of channel closure ought to be. Without motivating application examples, which we don't have yet (e.g. ICS 20 never closes channels), it's a bit difficult to reason purely in the abstract I think.

cwgoes avatar Feb 13 '21 19:02 cwgoes

should we close this issue?

colin-axner avatar Mar 04 '21 15:03 colin-axner

@ancazamfir Would you like any changes to be made, or any points to be clarified in the spec?

cwgoes avatar Mar 04 '21 15:03 cwgoes

It's still not clear to me why a channel cannot be closed if the connection is not opened. We can start the handshake with the connection not opened but we cannot "stop" it by closing the channel. We have to monitor/wait for the connection to be opened and only then close the channel.

Small inconsistency in ICS04, the state diagram and transition table for channel close mention that a channel can be closed only if in OPEN state. The pseudocode just asserts !CLOSED.

Then in the description Any in-flight packets can be timed-out as soon as a channel is closed. Maybe mention something about in-flight acknowledgments and timeouts.

ancazamfir avatar Mar 04 '21 16:03 ancazamfir

Transferring to the cosmos/ibc repo as this discussion is not ibc-go specific

colin-axner avatar Mar 05 '21 10:03 colin-axner