diff --git a/.github/mergify.yml b/.github/mergify.yml index 48c27540be8..38f777eb401 100644 --- a/.github/mergify.yml +++ b/.github/mergify.yml @@ -16,8 +16,8 @@ pull_request_rules: name: default method: squash commit_message_template: | - {{ title }} (#{{ number }}) - {{ body }} + {{ title }} (#{{ number }}) + {{ body }} - name: backport patches to v1.0.x capability branch conditions: - base=main diff --git a/.github/workflows/golangci-feature.yml b/.github/workflows/golangci-feature.yml new file mode 100644 index 00000000000..2237a2ea736 --- /dev/null +++ b/.github/workflows/golangci-feature.yml @@ -0,0 +1,31 @@ +# golangci-feature runs on pull requests from branches that do not target main. +# +# Working on feature branches (PRs where the PR base-ref != main) is a common +# workflow used, in order to make the merging of PRs easier certain lints are excluded +# when it makes sense. Currently, unused lints are excluded since many PRs will add +# unused code that will be used in a later PR. +name: golangci-lint feature branch +on: + pull_request: + # Ignore if the target is main. (Negation of golanci-lint.yml) + branches-ignore: + - main +permissions: + contents: read + # Optional: allow read access to pull request. Use with `only-new-issues` option. + # pull-requests: read + +jobs: + golangci: + name: lint + runs-on: ubuntu-latest + steps: + - uses: actions/setup-go@v4 + with: + go-version: '1.21' + - uses: actions/checkout@v4 + - name: golangci-lint + uses: golangci/golangci-lint-action@v3.7.0 + with: + version: v1.54.2 + args: --timeout 10m \ No newline at end of file diff --git a/README.md b/README.md index de2ad497054..13ea7faa040 100644 --- a/README.md +++ b/README.md @@ -41,7 +41,7 @@ This IBC implementation in Golang is built as a Cosmos SDK module. To understand ## Roadmap -For an overview of upcoming changes to ibc-go take a look at the [roadmap](./docs/docs/01-ibc/09-roadmap.md). +For an overview of upcoming changes to ibc-go take a look at the [roadmap](./docs/docs/01-ibc/10-roadmap.md). This roadmap is also available as a [project board](https://github.com/orgs/cosmos/projects/7/views/25). diff --git a/docs/client/swagger-ui/swagger.yaml b/docs/client/swagger-ui/swagger.yaml index aeb0edbb78f..60a43a59c7d 100644 --- a/docs/client/swagger-ui/swagger.yaml +++ b/docs/client/swagger-ui/swagger.yaml @@ -9042,12 +9042,15 @@ paths: - STATE_TRYOPEN - STATE_OPEN - STATE_CLOSED + - STATE_FLUSHING + - STATE_FLUSHCOMPLETE default: STATE_UNINITIALIZED_UNSPECIFIED description: >- State defines if a channel is in one of the following states: - CLOSED, INIT, TRYOPEN, OPEN or UNINITIALIZED. + CLOSED, INIT, TRYOPEN, OPEN, FLUSHING, FLUSHCOMPLETE or + UNINITIALIZED. - STATE_UNINITIALIZED_UNSPECIFIED: Default State - STATE_INIT: A channel has just started the opening handshake. @@ -9056,6 +9059,8 @@ paths: ready to send and receive packets. - STATE_CLOSED: A channel has been closed and can no longer be used to send or receive packets. + - STATE_FLUSHING: A channel has just accepted the upgrade handshake attempt and is flushing in-flight packets. + - STATE_FLUSHCOMPLETE: A channel has just completed flushing any in-flight packets. ordering: title: whether the channel is ordered or unordered type: string @@ -9102,6 +9107,15 @@ paths: channel_id: type: string title: channel identifier + upgrade_sequence: + type: string + format: uint64 + title: >- + upgrade sequence indicates the latest upgrade attempt + performed by this channel + + the value of 0 indicates the channel has never been + upgraded description: >- IdentifiedChannel defines a channel with additional port and channel @@ -9445,12 +9459,15 @@ paths: - STATE_TRYOPEN - STATE_OPEN - STATE_CLOSED + - STATE_FLUSHING + - STATE_FLUSHCOMPLETE default: STATE_UNINITIALIZED_UNSPECIFIED description: >- State defines if a channel is in one of the following states: - CLOSED, INIT, TRYOPEN, OPEN or UNINITIALIZED. + CLOSED, INIT, TRYOPEN, OPEN, FLUSHING, FLUSHCOMPLETE or + UNINITIALIZED. - STATE_UNINITIALIZED_UNSPECIFIED: Default State - STATE_INIT: A channel has just started the opening handshake. @@ -9459,6 +9476,8 @@ paths: ready to send and receive packets. - STATE_CLOSED: A channel has been closed and can no longer be used to send or receive packets. + - STATE_FLUSHING: A channel has just accepted the upgrade handshake attempt and is flushing in-flight packets. + - STATE_FLUSHCOMPLETE: A channel has just completed flushing any in-flight packets. ordering: title: whether the channel is ordered or unordered type: string @@ -9498,6 +9517,15 @@ paths: title: >- opaque channel version, which is agreed upon during the handshake + upgrade_sequence: + type: string + format: uint64 + title: >- + upgrade sequence indicates the latest upgrade attempt + performed by this channel + + the value of 0 indicates the channel has never been + upgraded description: >- Channel defines pipeline for exactly-once packet delivery between specific @@ -10701,7 +10729,7 @@ paths: gets reset title: |- - QuerySequenceResponse is the request type for the + QuerySequenceResponse is the response type for the Query/QueryNextSequenceReceiveResponse RPC method default: description: An unexpected error response. @@ -13252,129 +13280,120 @@ paths: format: uint64 tags: - Query - /ibc/core/channel/v1/connections/{connection}/channels: + /ibc/core/channel/v1/channels/{channel_id}/ports/{port_id}/upgrade: get: - summary: |- - ConnectionChannels queries all the channels associated with a connection - end. - operationId: ConnectionChannels + summary: Upgrade returns the upgrade for a given port and channel id. + operationId: Upgrade responses: '200': description: A successful response. schema: type: object properties: - channels: - type: array - items: - type: object - properties: - state: - title: current state of the channel end - type: string - enum: - - STATE_UNINITIALIZED_UNSPECIFIED - - STATE_INIT - - STATE_TRYOPEN - - STATE_OPEN - - STATE_CLOSED - default: STATE_UNINITIALIZED_UNSPECIFIED - description: >- - State defines if a channel is in one of the following - states: + upgrade: + type: object + properties: + fields: + type: object + properties: + ordering: + type: string + enum: + - ORDER_NONE_UNSPECIFIED + - ORDER_UNORDERED + - ORDER_ORDERED + default: ORDER_NONE_UNSPECIFIED + description: >- + - ORDER_NONE_UNSPECIFIED: zero-value for channel + ordering + - ORDER_UNORDERED: packets can be delivered in any order, which may differ from the order in + which they were sent. + - ORDER_ORDERED: packets are delivered exactly in the order which they were sent + title: Order defines if a channel is ORDERED or UNORDERED + connection_hops: + type: array + items: + type: string + version: + type: string + description: >- + UpgradeFields are the fields in a channel end which may be + changed - CLOSED, INIT, TRYOPEN, OPEN or UNINITIALIZED. + during a channel upgrade. + timeout: + type: object + properties: + height: + title: >- + block height after which the packet or upgrade times + out + type: object + properties: + revision_number: + type: string + format: uint64 + title: the revision that the client is currently on + revision_height: + type: string + format: uint64 + title: the height within the given revision + description: >- + Normally the RevisionHeight is incremented at each + height while keeping - - STATE_UNINITIALIZED_UNSPECIFIED: Default State - - STATE_INIT: A channel has just started the opening handshake. - - STATE_TRYOPEN: A channel has acknowledged the handshake step on the counterparty chain. - - STATE_OPEN: A channel has completed the handshake. Open channels are - ready to send and receive packets. - - STATE_CLOSED: A channel has been closed and can no longer be used to send or receive - packets. - ordering: - title: whether the channel is ordered or unordered - type: string - enum: - - ORDER_NONE_UNSPECIFIED - - ORDER_UNORDERED - - ORDER_ORDERED - default: ORDER_NONE_UNSPECIFIED - description: >- - - ORDER_NONE_UNSPECIFIED: zero-value for channel - ordering - - ORDER_UNORDERED: packets can be delivered in any order, which may differ from the order in - which they were sent. - - ORDER_ORDERED: packets are delivered exactly in the order which they were sent - counterparty: - title: counterparty channel end - type: object - properties: - port_id: - type: string - description: >- - port on the counterparty chain which owns the other - end of the channel. - channel_id: - type: string - title: channel end on the counterparty chain - connection_hops: - type: array - items: + RevisionNumber the same. However some consensus + algorithms may choose to + + reset the height in certain conditions e.g. hard + forks, state-machine + + breaking changes In these cases, the RevisionNumber is + incremented so that + + height continues to be monitonically increasing even + as the RevisionHeight + + gets reset + timestamp: type: string - title: >- - list of connection identifiers, in order, along which - packets sent on + format: uint64 + title: >- + block timestamp (in nanoseconds) after which the + packet or upgrade times out + description: >- + Timeout defines an execution deadline structure for + 04-channel handlers. - this channel will travel - version: - type: string - title: >- - opaque channel version, which is agreed upon during the - handshake - port_id: - type: string - title: port identifier - channel_id: - type: string - title: channel identifier - description: >- - IdentifiedChannel defines a channel with additional port and - channel + This includes packet lifecycle handlers as well as the + upgrade handshake handlers. - identifier fields. - description: list of channels associated with a connection. - pagination: - title: pagination response - type: object - properties: - next_key: - type: string - format: byte - description: |- - next_key is the key to be passed to PageRequest.key to - query the next page most efficiently. It will be empty if - there are no more results. - total: + A valid Timeout contains either one or both of a timestamp + and block height (sequence). + next_sequence_send: type: string format: uint64 - title: >- - total is total number of results available if - PageRequest.count_total - - was set, its value is undefined otherwise description: >- - PageResponse is to be embedded in gRPC response messages where - the + Upgrade is a verifiable type which contains the relevant + information - corresponding request message has used PageRequest. + for an attempted upgrade. It provides the proposed changes to + the channel - message SomeResponse { - repeated Bar results = 1; - PageResponse page = 2; - } - height: - title: query block height + end, the timeout for this upgrade attempt and the next packet + sequence + + which allows the counterparty to efficiently know the highest + sequence it has received. + + The next sequence send is used for pruning and upgrading from + unordered to ordered channels. + proof: + type: string + format: byte + title: merkle proof of existence + proof_height: + title: height at which the proof was retrieved type: object properties: revision_number: @@ -13402,9 +13421,9 @@ paths: RevisionHeight gets reset - title: |- - QueryConnectionChannelsResponse is the Response type for the - Query/QueryConnectionChannels RPC method + title: >- + QueryUpgradeResponse is the response type for the + QueryUpgradeResponse RPC method default: description: An unexpected error response. schema: @@ -13600,106 +13619,1009 @@ paths: "value": "1.212s" } parameters: - - name: connection - description: connection unique identifier + - name: channel_id in: path required: true type: string - - name: pagination.key - description: |- - key is a value returned in PageResponse.next_key to begin - querying the next page most efficiently. Only one of offset or key - should be set. - in: query - required: false - type: string - format: byte - - name: pagination.offset - description: >- - offset is a numeric offset that can be used when key is unavailable. - - It is less efficient than using key. Only one of offset or key - should - - be set. - in: query - required: false - type: string - format: uint64 - - name: pagination.limit - description: >- - limit is the total number of results to be returned in the result - page. - - If left empty it will default to a value to be set by each app. - in: query - required: false + - name: port_id + in: path + required: true type: string - format: uint64 - - name: pagination.count_total - description: >- - count_total is set to true to indicate that the result set should - include - - a count of the total number of items available for pagination in - UIs. - - count_total is only respected when offset is used. It is ignored - when key - - is set. - in: query - required: false - type: boolean - - name: pagination.reverse - description: >- - reverse is set to true if results are to be returned in the - descending order. - - - Since: cosmos-sdk 0.43 - in: query - required: false - type: boolean tags: - Query - /ibc/lightclients/wasm/v1/checksums: + /ibc/core/channel/v1/channels/{channel_id}/ports/{port_id}/upgrade_error: get: - summary: Get all Wasm checksums - operationId: Checksums + summary: UpgradeError returns the error receipt if the upgrade handshake failed. + operationId: UpgradeError responses: '200': description: A successful response. schema: type: object properties: - checksums: - type: array - items: - type: string + error_receipt: + type: object + properties: + sequence: + type: string + format: uint64 + title: the channel upgrade sequence + message: + type: string + title: the error message detailing the cause of failure description: >- - checksums is a list of the hex encoded checksums of all wasm - codes stored. - pagination: - description: pagination defines the pagination in the response. + ErrorReceipt defines a type which encapsulates the upgrade + sequence and error associated with the + + upgrade handshake failure. When a channel upgrade handshake is + aborted both chains are expected to increment to the + + next sequence. + proof: + type: string + format: byte + title: merkle proof of existence + proof_height: + title: height at which the proof was retrieved type: object properties: - next_key: + revision_number: type: string - format: byte - description: |- - next_key is the key to be passed to PageRequest.key to - query the next page most efficiently. It will be empty if - there are no more results. - total: + format: uint64 + title: the revision that the client is currently on + revision_height: type: string format: uint64 - title: >- - total is total number of results available if - PageRequest.count_total + title: the height within the given revision + description: >- + Normally the RevisionHeight is incremented at each height + while keeping - was set, its value is undefined otherwise - description: >- + RevisionNumber the same. However some consensus algorithms may + choose to + + reset the height in certain conditions e.g. hard forks, + state-machine + + breaking changes In these cases, the RevisionNumber is + incremented so that + + height continues to be monitonically increasing even as the + RevisionHeight + + gets reset + title: >- + QueryUpgradeErrorResponse is the response type for the + Query/QueryUpgradeError RPC method + default: + description: An unexpected error response. + schema: + type: object + properties: + error: + type: string + code: + type: integer + format: int32 + message: + type: string + details: + type: array + items: + type: object + properties: + type_url: + type: string + description: >- + A URL/resource name that uniquely identifies the type of + the serialized + + protocol buffer message. This string must contain at + least + + one "/" character. The last segment of the URL's path + must represent + + the fully qualified name of the type (as in + + `path/google.protobuf.Duration`). The name should be in + a canonical form + + (e.g., leading "." is not accepted). + + + In practice, teams usually precompile into the binary + all types that they + + expect it to use in the context of Any. However, for + URLs which use the + + scheme `http`, `https`, or no scheme, one can optionally + set up a type + + server that maps type URLs to message definitions as + follows: + + + * If no scheme is provided, `https` is assumed. + + * An HTTP GET on the URL must yield a + [google.protobuf.Type][] + value in binary format, or produce an error. + * Applications are allowed to cache lookup results based + on the + URL, or have them precompiled into a binary to avoid any + lookup. Therefore, binary compatibility needs to be preserved + on changes to types. (Use versioned type names to manage + breaking changes.) + + Note: this functionality is not currently available in + the official + + protobuf release, and it is not used for type URLs + beginning with + + type.googleapis.com. + + + Schemes other than `http`, `https` (or the empty scheme) + might be + + used with implementation specific semantics. + value: + type: string + format: byte + description: >- + Must be a valid serialized protocol buffer of the above + specified type. + description: >- + `Any` contains an arbitrary serialized protocol buffer + message along with a + + URL that describes the type of the serialized message. + + + Protobuf library provides support to pack/unpack Any values + in the form + + of utility functions or additional generated methods of the + Any type. + + + Example 1: Pack and unpack a message in C++. + + Foo foo = ...; + Any any; + any.PackFrom(foo); + ... + if (any.UnpackTo(&foo)) { + ... + } + + Example 2: Pack and unpack a message in Java. + + Foo foo = ...; + Any any = Any.pack(foo); + ... + if (any.is(Foo.class)) { + foo = any.unpack(Foo.class); + } + // or ... + if (any.isSameTypeAs(Foo.getDefaultInstance())) { + foo = any.unpack(Foo.getDefaultInstance()); + } + + Example 3: Pack and unpack a message in Python. + + foo = Foo(...) + any = Any() + any.Pack(foo) + ... + if any.Is(Foo.DESCRIPTOR): + any.Unpack(foo) + ... + + Example 4: Pack and unpack a message in Go + + foo := &pb.Foo{...} + any, err := anypb.New(foo) + if err != nil { + ... + } + ... + foo := &pb.Foo{} + if err := any.UnmarshalTo(foo); err != nil { + ... + } + + The pack methods provided by protobuf library will by + default use + + 'type.googleapis.com/full.type.name' as the type URL and the + unpack + + methods only use the fully qualified type name after the + last '/' + + in the type URL, for example "foo.bar.com/x/y.z" will yield + type + + name "y.z". + + + JSON + + + The JSON representation of an `Any` value uses the regular + + representation of the deserialized, embedded message, with + an + + additional field `@type` which contains the type URL. + Example: + + package google.profile; + message Person { + string first_name = 1; + string last_name = 2; + } + + { + "@type": "type.googleapis.com/google.profile.Person", + "firstName": , + "lastName": + } + + If the embedded message type is well-known and has a custom + JSON + + representation, that representation will be embedded adding + a field + + `value` which holds the custom JSON in addition to the + `@type` + + field. Example (for message [google.protobuf.Duration][]): + + { + "@type": "type.googleapis.com/google.protobuf.Duration", + "value": "1.212s" + } + parameters: + - name: channel_id + in: path + required: true + type: string + - name: port_id + in: path + required: true + type: string + tags: + - Query + /ibc/core/channel/v1/connections/{connection}/channels: + get: + summary: |- + ConnectionChannels queries all the channels associated with a connection + end. + operationId: ConnectionChannels + responses: + '200': + description: A successful response. + schema: + type: object + properties: + channels: + type: array + items: + type: object + properties: + state: + title: current state of the channel end + type: string + enum: + - STATE_UNINITIALIZED_UNSPECIFIED + - STATE_INIT + - STATE_TRYOPEN + - STATE_OPEN + - STATE_CLOSED + - STATE_FLUSHING + - STATE_FLUSHCOMPLETE + default: STATE_UNINITIALIZED_UNSPECIFIED + description: >- + State defines if a channel is in one of the following + states: + + CLOSED, INIT, TRYOPEN, OPEN, FLUSHING, FLUSHCOMPLETE or + UNINITIALIZED. + + - STATE_UNINITIALIZED_UNSPECIFIED: Default State + - STATE_INIT: A channel has just started the opening handshake. + - STATE_TRYOPEN: A channel has acknowledged the handshake step on the counterparty chain. + - STATE_OPEN: A channel has completed the handshake. Open channels are + ready to send and receive packets. + - STATE_CLOSED: A channel has been closed and can no longer be used to send or receive + packets. + - STATE_FLUSHING: A channel has just accepted the upgrade handshake attempt and is flushing in-flight packets. + - STATE_FLUSHCOMPLETE: A channel has just completed flushing any in-flight packets. + ordering: + title: whether the channel is ordered or unordered + type: string + enum: + - ORDER_NONE_UNSPECIFIED + - ORDER_UNORDERED + - ORDER_ORDERED + default: ORDER_NONE_UNSPECIFIED + description: >- + - ORDER_NONE_UNSPECIFIED: zero-value for channel + ordering + - ORDER_UNORDERED: packets can be delivered in any order, which may differ from the order in + which they were sent. + - ORDER_ORDERED: packets are delivered exactly in the order which they were sent + counterparty: + title: counterparty channel end + type: object + properties: + port_id: + type: string + description: >- + port on the counterparty chain which owns the other + end of the channel. + channel_id: + type: string + title: channel end on the counterparty chain + connection_hops: + type: array + items: + type: string + title: >- + list of connection identifiers, in order, along which + packets sent on + + this channel will travel + version: + type: string + title: >- + opaque channel version, which is agreed upon during the + handshake + port_id: + type: string + title: port identifier + channel_id: + type: string + title: channel identifier + upgrade_sequence: + type: string + format: uint64 + title: >- + upgrade sequence indicates the latest upgrade attempt + performed by this channel + + the value of 0 indicates the channel has never been + upgraded + description: >- + IdentifiedChannel defines a channel with additional port and + channel + + identifier fields. + description: list of channels associated with a connection. + pagination: + title: pagination response + type: object + properties: + next_key: + type: string + format: byte + description: |- + next_key is the key to be passed to PageRequest.key to + query the next page most efficiently. It will be empty if + there are no more results. + total: + type: string + format: uint64 + title: >- + total is total number of results available if + PageRequest.count_total + + was set, its value is undefined otherwise + description: >- + PageResponse is to be embedded in gRPC response messages where + the + + corresponding request message has used PageRequest. + + message SomeResponse { + repeated Bar results = 1; + PageResponse page = 2; + } + height: + title: query block height + type: object + properties: + revision_number: + type: string + format: uint64 + title: the revision that the client is currently on + revision_height: + type: string + format: uint64 + title: the height within the given revision + description: >- + Normally the RevisionHeight is incremented at each height + while keeping + + RevisionNumber the same. However some consensus algorithms may + choose to + + reset the height in certain conditions e.g. hard forks, + state-machine + + breaking changes In these cases, the RevisionNumber is + incremented so that + + height continues to be monitonically increasing even as the + RevisionHeight + + gets reset + title: |- + QueryConnectionChannelsResponse is the Response type for the + Query/QueryConnectionChannels RPC method + default: + description: An unexpected error response. + schema: + type: object + properties: + error: + type: string + code: + type: integer + format: int32 + message: + type: string + details: + type: array + items: + type: object + properties: + type_url: + type: string + description: >- + A URL/resource name that uniquely identifies the type of + the serialized + + protocol buffer message. This string must contain at + least + + one "/" character. The last segment of the URL's path + must represent + + the fully qualified name of the type (as in + + `path/google.protobuf.Duration`). The name should be in + a canonical form + + (e.g., leading "." is not accepted). + + + In practice, teams usually precompile into the binary + all types that they + + expect it to use in the context of Any. However, for + URLs which use the + + scheme `http`, `https`, or no scheme, one can optionally + set up a type + + server that maps type URLs to message definitions as + follows: + + + * If no scheme is provided, `https` is assumed. + + * An HTTP GET on the URL must yield a + [google.protobuf.Type][] + value in binary format, or produce an error. + * Applications are allowed to cache lookup results based + on the + URL, or have them precompiled into a binary to avoid any + lookup. Therefore, binary compatibility needs to be preserved + on changes to types. (Use versioned type names to manage + breaking changes.) + + Note: this functionality is not currently available in + the official + + protobuf release, and it is not used for type URLs + beginning with + + type.googleapis.com. + + + Schemes other than `http`, `https` (or the empty scheme) + might be + + used with implementation specific semantics. + value: + type: string + format: byte + description: >- + Must be a valid serialized protocol buffer of the above + specified type. + description: >- + `Any` contains an arbitrary serialized protocol buffer + message along with a + + URL that describes the type of the serialized message. + + + Protobuf library provides support to pack/unpack Any values + in the form + + of utility functions or additional generated methods of the + Any type. + + + Example 1: Pack and unpack a message in C++. + + Foo foo = ...; + Any any; + any.PackFrom(foo); + ... + if (any.UnpackTo(&foo)) { + ... + } + + Example 2: Pack and unpack a message in Java. + + Foo foo = ...; + Any any = Any.pack(foo); + ... + if (any.is(Foo.class)) { + foo = any.unpack(Foo.class); + } + // or ... + if (any.isSameTypeAs(Foo.getDefaultInstance())) { + foo = any.unpack(Foo.getDefaultInstance()); + } + + Example 3: Pack and unpack a message in Python. + + foo = Foo(...) + any = Any() + any.Pack(foo) + ... + if any.Is(Foo.DESCRIPTOR): + any.Unpack(foo) + ... + + Example 4: Pack and unpack a message in Go + + foo := &pb.Foo{...} + any, err := anypb.New(foo) + if err != nil { + ... + } + ... + foo := &pb.Foo{} + if err := any.UnmarshalTo(foo); err != nil { + ... + } + + The pack methods provided by protobuf library will by + default use + + 'type.googleapis.com/full.type.name' as the type URL and the + unpack + + methods only use the fully qualified type name after the + last '/' + + in the type URL, for example "foo.bar.com/x/y.z" will yield + type + + name "y.z". + + + JSON + + + The JSON representation of an `Any` value uses the regular + + representation of the deserialized, embedded message, with + an + + additional field `@type` which contains the type URL. + Example: + + package google.profile; + message Person { + string first_name = 1; + string last_name = 2; + } + + { + "@type": "type.googleapis.com/google.profile.Person", + "firstName": , + "lastName": + } + + If the embedded message type is well-known and has a custom + JSON + + representation, that representation will be embedded adding + a field + + `value` which holds the custom JSON in addition to the + `@type` + + field. Example (for message [google.protobuf.Duration][]): + + { + "@type": "type.googleapis.com/google.protobuf.Duration", + "value": "1.212s" + } + parameters: + - name: connection + description: connection unique identifier + in: path + required: true + type: string + - name: pagination.key + description: |- + key is a value returned in PageResponse.next_key to begin + querying the next page most efficiently. Only one of offset or key + should be set. + in: query + required: false + type: string + format: byte + - name: pagination.offset + description: >- + offset is a numeric offset that can be used when key is unavailable. + + It is less efficient than using key. Only one of offset or key + should + + be set. + in: query + required: false + type: string + format: uint64 + - name: pagination.limit + description: >- + limit is the total number of results to be returned in the result + page. + + If left empty it will default to a value to be set by each app. + in: query + required: false + type: string + format: uint64 + - name: pagination.count_total + description: >- + count_total is set to true to indicate that the result set should + include + + a count of the total number of items available for pagination in + UIs. + + count_total is only respected when offset is used. It is ignored + when key + + is set. + in: query + required: false + type: boolean + - name: pagination.reverse + description: >- + reverse is set to true if results are to be returned in the + descending order. + + + Since: cosmos-sdk 0.43 + in: query + required: false + type: boolean + tags: + - Query + /ibc/core/channel/v1/params: + get: + summary: ChannelParams queries all parameters of the ibc channel submodule. + operationId: ChannelParams + responses: + '200': + description: A successful response. + schema: + type: object + properties: + params: + description: params defines the parameters of the module. + type: object + properties: + upgrade_timeout: + type: object + properties: + height: + title: >- + block height after which the packet or upgrade times + out + type: object + properties: + revision_number: + type: string + format: uint64 + title: the revision that the client is currently on + revision_height: + type: string + format: uint64 + title: the height within the given revision + description: >- + Normally the RevisionHeight is incremented at each + height while keeping + + RevisionNumber the same. However some consensus + algorithms may choose to + + reset the height in certain conditions e.g. hard + forks, state-machine + + breaking changes In these cases, the RevisionNumber is + incremented so that + + height continues to be monitonically increasing even + as the RevisionHeight + + gets reset + timestamp: + type: string + format: uint64 + title: >- + block timestamp (in nanoseconds) after which the + packet or upgrade times out + description: >- + Timeout defines an execution deadline structure for + 04-channel handlers. + + This includes packet lifecycle handlers as well as the + upgrade handshake handlers. + + A valid Timeout contains either one or both of a timestamp + and block height (sequence). + description: >- + QueryChannelParamsResponse is the response type for the + Query/ChannelParams RPC method. + default: + description: An unexpected error response. + schema: + type: object + properties: + error: + type: string + code: + type: integer + format: int32 + message: + type: string + details: + type: array + items: + type: object + properties: + type_url: + type: string + description: >- + A URL/resource name that uniquely identifies the type of + the serialized + + protocol buffer message. This string must contain at + least + + one "/" character. The last segment of the URL's path + must represent + + the fully qualified name of the type (as in + + `path/google.protobuf.Duration`). The name should be in + a canonical form + + (e.g., leading "." is not accepted). + + + In practice, teams usually precompile into the binary + all types that they + + expect it to use in the context of Any. However, for + URLs which use the + + scheme `http`, `https`, or no scheme, one can optionally + set up a type + + server that maps type URLs to message definitions as + follows: + + + * If no scheme is provided, `https` is assumed. + + * An HTTP GET on the URL must yield a + [google.protobuf.Type][] + value in binary format, or produce an error. + * Applications are allowed to cache lookup results based + on the + URL, or have them precompiled into a binary to avoid any + lookup. Therefore, binary compatibility needs to be preserved + on changes to types. (Use versioned type names to manage + breaking changes.) + + Note: this functionality is not currently available in + the official + + protobuf release, and it is not used for type URLs + beginning with + + type.googleapis.com. + + + Schemes other than `http`, `https` (or the empty scheme) + might be + + used with implementation specific semantics. + value: + type: string + format: byte + description: >- + Must be a valid serialized protocol buffer of the above + specified type. + description: >- + `Any` contains an arbitrary serialized protocol buffer + message along with a + + URL that describes the type of the serialized message. + + + Protobuf library provides support to pack/unpack Any values + in the form + + of utility functions or additional generated methods of the + Any type. + + + Example 1: Pack and unpack a message in C++. + + Foo foo = ...; + Any any; + any.PackFrom(foo); + ... + if (any.UnpackTo(&foo)) { + ... + } + + Example 2: Pack and unpack a message in Java. + + Foo foo = ...; + Any any = Any.pack(foo); + ... + if (any.is(Foo.class)) { + foo = any.unpack(Foo.class); + } + // or ... + if (any.isSameTypeAs(Foo.getDefaultInstance())) { + foo = any.unpack(Foo.getDefaultInstance()); + } + + Example 3: Pack and unpack a message in Python. + + foo = Foo(...) + any = Any() + any.Pack(foo) + ... + if any.Is(Foo.DESCRIPTOR): + any.Unpack(foo) + ... + + Example 4: Pack and unpack a message in Go + + foo := &pb.Foo{...} + any, err := anypb.New(foo) + if err != nil { + ... + } + ... + foo := &pb.Foo{} + if err := any.UnmarshalTo(foo); err != nil { + ... + } + + The pack methods provided by protobuf library will by + default use + + 'type.googleapis.com/full.type.name' as the type URL and the + unpack + + methods only use the fully qualified type name after the + last '/' + + in the type URL, for example "foo.bar.com/x/y.z" will yield + type + + name "y.z". + + + JSON + + + The JSON representation of an `Any` value uses the regular + + representation of the deserialized, embedded message, with + an + + additional field `@type` which contains the type URL. + Example: + + package google.profile; + message Person { + string first_name = 1; + string last_name = 2; + } + + { + "@type": "type.googleapis.com/google.profile.Person", + "firstName": , + "lastName": + } + + If the embedded message type is well-known and has a custom + JSON + + representation, that representation will be embedded adding + a field + + `value` which holds the custom JSON in addition to the + `@type` + + field. Example (for message [google.protobuf.Duration][]): + + { + "@type": "type.googleapis.com/google.protobuf.Duration", + "value": "1.212s" + } + tags: + - Query + /ibc/lightclients/wasm/v1/checksums: + get: + summary: Get all Wasm checksums + operationId: Checksums + responses: + '200': + description: A successful response. + schema: + type: object + properties: + checksums: + type: array + items: + type: string + description: >- + checksums is a list of the hex encoded checksums of all wasm + codes stored. + pagination: + description: pagination defines the pagination in the response. + type: object + properties: + next_key: + type: string + format: byte + description: |- + next_key is the key to be passed to PageRequest.key to + query the next page most efficiently. It will be empty if + there are no more results. + total: + type: string + format: uint64 + title: >- + total is total number of results available if + PageRequest.count_total + + was set, its value is undefined otherwise + description: >- QueryChecksumsResponse is the response type for the Query/Checksums RPC method. default: @@ -18032,10 +18954,12 @@ definitions: - STATE_TRYOPEN - STATE_OPEN - STATE_CLOSED + - STATE_FLUSHING + - STATE_FLUSHCOMPLETE default: STATE_UNINITIALIZED_UNSPECIFIED description: |- State defines if a channel is in one of the following states: - CLOSED, INIT, TRYOPEN, OPEN or UNINITIALIZED. + CLOSED, INIT, TRYOPEN, OPEN, FLUSHING, FLUSHCOMPLETE or UNINITIALIZED. - STATE_UNINITIALIZED_UNSPECIFIED: Default State - STATE_INIT: A channel has just started the opening handshake. @@ -18044,6 +18968,8 @@ definitions: ready to send and receive packets. - STATE_CLOSED: A channel has been closed and can no longer be used to send or receive packets. + - STATE_FLUSHING: A channel has just accepted the upgrade handshake attempt and is flushing in-flight packets. + - STATE_FLUSHCOMPLETE: A channel has just completed flushing any in-flight packets. ordering: title: whether the channel is ordered or unordered type: string @@ -18079,6 +19005,14 @@ definitions: version: type: string title: opaque channel version, which is agreed upon during the handshake + upgrade_sequence: + type: string + format: uint64 + title: >- + upgrade sequence indicates the latest upgrade attempt performed by + this channel + + the value of 0 indicates the channel has never been upgraded description: |- Channel defines pipeline for exactly-once packet delivery between specific modules on separate blockchains, which has at least one end capable of @@ -18095,6 +19029,24 @@ definitions: type: string title: channel end on the counterparty chain title: Counterparty defines a channel end counterparty + ibc.core.channel.v1.ErrorReceipt: + type: object + properties: + sequence: + type: string + format: uint64 + title: the channel upgrade sequence + message: + type: string + title: the error message detailing the cause of failure + description: >- + ErrorReceipt defines a type which encapsulates the upgrade sequence and + error associated with the + + upgrade handshake failure. When a channel upgrade handshake is aborted + both chains are expected to increment to the + + next sequence. ibc.core.channel.v1.IdentifiedChannel: type: object properties: @@ -18107,10 +19059,12 @@ definitions: - STATE_TRYOPEN - STATE_OPEN - STATE_CLOSED + - STATE_FLUSHING + - STATE_FLUSHCOMPLETE default: STATE_UNINITIALIZED_UNSPECIFIED description: |- State defines if a channel is in one of the following states: - CLOSED, INIT, TRYOPEN, OPEN or UNINITIALIZED. + CLOSED, INIT, TRYOPEN, OPEN, FLUSHING, FLUSHCOMPLETE or UNINITIALIZED. - STATE_UNINITIALIZED_UNSPECIFIED: Default State - STATE_INIT: A channel has just started the opening handshake. @@ -18119,6 +19073,8 @@ definitions: ready to send and receive packets. - STATE_CLOSED: A channel has been closed and can no longer be used to send or receive packets. + - STATE_FLUSHING: A channel has just accepted the upgrade handshake attempt and is flushing in-flight packets. + - STATE_FLUSHCOMPLETE: A channel has just completed flushing any in-flight packets. ordering: title: whether the channel is ordered or unordered type: string @@ -18160,6 +19116,14 @@ definitions: channel_id: type: string title: channel identifier + upgrade_sequence: + type: string + format: uint64 + title: >- + upgrade sequence indicates the latest upgrade attempt performed by + this channel + + the value of 0 indicates the channel has never been upgraded description: |- IdentifiedChannel defines a channel with additional port and channel identifier fields. @@ -18198,6 +19162,57 @@ definitions: packet commitments, acknowledgements, and receipts. Caller is responsible for knowing the context necessary to interpret this state as a commitment, acknowledgement, or a receipt. + ibc.core.channel.v1.Params: + type: object + properties: + upgrade_timeout: + type: object + properties: + height: + title: block height after which the packet or upgrade times out + type: object + properties: + revision_number: + type: string + format: uint64 + title: the revision that the client is currently on + revision_height: + type: string + format: uint64 + title: the height within the given revision + description: >- + Normally the RevisionHeight is incremented at each height while + keeping + + RevisionNumber the same. However some consensus algorithms may + choose to + + reset the height in certain conditions e.g. hard forks, + state-machine + + breaking changes In these cases, the RevisionNumber is incremented + so that + + height continues to be monitonically increasing even as the + RevisionHeight + + gets reset + timestamp: + type: string + format: uint64 + title: >- + block timestamp (in nanoseconds) after which the packet or upgrade + times out + description: >- + Timeout defines an execution deadline structure for 04-channel + handlers. + + This includes packet lifecycle handlers as well as the upgrade + handshake handlers. + + A valid Timeout contains either one or both of a timestamp and block + height (sequence). + description: Params defines the set of IBC channel parameters. ibc.core.channel.v1.QueryChannelClientStateResponse: type: object properties: @@ -18623,6 +19638,63 @@ definitions: title: |- QueryChannelClientStateResponse is the Response type for the Query/QueryChannelClientState RPC method + ibc.core.channel.v1.QueryChannelParamsResponse: + type: object + properties: + params: + description: params defines the parameters of the module. + type: object + properties: + upgrade_timeout: + type: object + properties: + height: + title: block height after which the packet or upgrade times out + type: object + properties: + revision_number: + type: string + format: uint64 + title: the revision that the client is currently on + revision_height: + type: string + format: uint64 + title: the height within the given revision + description: >- + Normally the RevisionHeight is incremented at each height + while keeping + + RevisionNumber the same. However some consensus algorithms may + choose to + + reset the height in certain conditions e.g. hard forks, + state-machine + + breaking changes In these cases, the RevisionNumber is + incremented so that + + height continues to be monitonically increasing even as the + RevisionHeight + + gets reset + timestamp: + type: string + format: uint64 + title: >- + block timestamp (in nanoseconds) after which the packet or + upgrade times out + description: >- + Timeout defines an execution deadline structure for 04-channel + handlers. + + This includes packet lifecycle handlers as well as the upgrade + handshake handlers. + + A valid Timeout contains either one or both of a timestamp and + block height (sequence). + description: >- + QueryChannelParamsResponse is the response type for the + Query/ChannelParams RPC method. ibc.core.channel.v1.QueryChannelResponse: type: object properties: @@ -18639,10 +19711,14 @@ definitions: - STATE_TRYOPEN - STATE_OPEN - STATE_CLOSED + - STATE_FLUSHING + - STATE_FLUSHCOMPLETE default: STATE_UNINITIALIZED_UNSPECIFIED - description: |- + description: >- State defines if a channel is in one of the following states: - CLOSED, INIT, TRYOPEN, OPEN or UNINITIALIZED. + + CLOSED, INIT, TRYOPEN, OPEN, FLUSHING, FLUSHCOMPLETE or + UNINITIALIZED. - STATE_UNINITIALIZED_UNSPECIFIED: Default State - STATE_INIT: A channel has just started the opening handshake. @@ -18651,6 +19727,8 @@ definitions: ready to send and receive packets. - STATE_CLOSED: A channel has been closed and can no longer be used to send or receive packets. + - STATE_FLUSHING: A channel has just accepted the upgrade handshake attempt and is flushing in-flight packets. + - STATE_FLUSHCOMPLETE: A channel has just completed flushing any in-flight packets. ordering: title: whether the channel is ordered or unordered type: string @@ -18688,6 +19766,14 @@ definitions: version: type: string title: opaque channel version, which is agreed upon during the handshake + upgrade_sequence: + type: string + format: uint64 + title: >- + upgrade sequence indicates the latest upgrade attempt performed by + this channel + + the value of 0 indicates the channel has never been upgraded description: >- Channel defines pipeline for exactly-once packet delivery between specific @@ -18751,10 +19837,14 @@ definitions: - STATE_TRYOPEN - STATE_OPEN - STATE_CLOSED + - STATE_FLUSHING + - STATE_FLUSHCOMPLETE default: STATE_UNINITIALIZED_UNSPECIFIED - description: |- + description: >- State defines if a channel is in one of the following states: - CLOSED, INIT, TRYOPEN, OPEN or UNINITIALIZED. + + CLOSED, INIT, TRYOPEN, OPEN, FLUSHING, FLUSHCOMPLETE or + UNINITIALIZED. - STATE_UNINITIALIZED_UNSPECIFIED: Default State - STATE_INIT: A channel has just started the opening handshake. @@ -18763,6 +19853,8 @@ definitions: ready to send and receive packets. - STATE_CLOSED: A channel has been closed and can no longer be used to send or receive packets. + - STATE_FLUSHING: A channel has just accepted the upgrade handshake attempt and is flushing in-flight packets. + - STATE_FLUSHCOMPLETE: A channel has just completed flushing any in-flight packets. ordering: title: whether the channel is ordered or unordered type: string @@ -18808,6 +19900,14 @@ definitions: channel_id: type: string title: channel identifier + upgrade_sequence: + type: string + format: uint64 + title: >- + upgrade sequence indicates the latest upgrade attempt performed + by this channel + + the value of 0 indicates the channel has never been upgraded description: |- IdentifiedChannel defines a channel with additional port and channel identifier fields. @@ -18887,10 +19987,14 @@ definitions: - STATE_TRYOPEN - STATE_OPEN - STATE_CLOSED + - STATE_FLUSHING + - STATE_FLUSHCOMPLETE default: STATE_UNINITIALIZED_UNSPECIFIED - description: |- + description: >- State defines if a channel is in one of the following states: - CLOSED, INIT, TRYOPEN, OPEN or UNINITIALIZED. + + CLOSED, INIT, TRYOPEN, OPEN, FLUSHING, FLUSHCOMPLETE or + UNINITIALIZED. - STATE_UNINITIALIZED_UNSPECIFIED: Default State - STATE_INIT: A channel has just started the opening handshake. @@ -18899,6 +20003,8 @@ definitions: ready to send and receive packets. - STATE_CLOSED: A channel has been closed and can no longer be used to send or receive packets. + - STATE_FLUSHING: A channel has just accepted the upgrade handshake attempt and is flushing in-flight packets. + - STATE_FLUSHCOMPLETE: A channel has just completed flushing any in-flight packets. ordering: title: whether the channel is ordered or unordered type: string @@ -18944,6 +20050,14 @@ definitions: channel_id: type: string title: channel identifier + upgrade_sequence: + type: string + format: uint64 + title: >- + upgrade sequence indicates the latest upgrade attempt performed + by this channel + + the value of 0 indicates the channel has never been upgraded description: |- IdentifiedChannel defines a channel with additional port and channel identifier fields. @@ -19046,7 +20160,7 @@ definitions: gets reset title: |- - QuerySequenceResponse is the request type for the + QuerySequenceResponse is the response type for the Query/QueryNextSequenceReceiveResponse RPC method ibc.core.channel.v1.QueryNextSequenceSendResponse: type: object @@ -19482,6 +20596,191 @@ definitions: title: |- QueryUnreceivedPacketsResponse is the response type for the Query/UnreceivedPacketCommitments RPC method + ibc.core.channel.v1.QueryUpgradeErrorResponse: + type: object + properties: + error_receipt: + type: object + properties: + sequence: + type: string + format: uint64 + title: the channel upgrade sequence + message: + type: string + title: the error message detailing the cause of failure + description: >- + ErrorReceipt defines a type which encapsulates the upgrade sequence + and error associated with the + + upgrade handshake failure. When a channel upgrade handshake is aborted + both chains are expected to increment to the + + next sequence. + proof: + type: string + format: byte + title: merkle proof of existence + proof_height: + title: height at which the proof was retrieved + type: object + properties: + revision_number: + type: string + format: uint64 + title: the revision that the client is currently on + revision_height: + type: string + format: uint64 + title: the height within the given revision + description: >- + Normally the RevisionHeight is incremented at each height while + keeping + + RevisionNumber the same. However some consensus algorithms may choose + to + + reset the height in certain conditions e.g. hard forks, state-machine + + breaking changes In these cases, the RevisionNumber is incremented so + that + + height continues to be monitonically increasing even as the + RevisionHeight + + gets reset + title: >- + QueryUpgradeErrorResponse is the response type for the + Query/QueryUpgradeError RPC method + ibc.core.channel.v1.QueryUpgradeResponse: + type: object + properties: + upgrade: + type: object + properties: + fields: + type: object + properties: + ordering: + type: string + enum: + - ORDER_NONE_UNSPECIFIED + - ORDER_UNORDERED + - ORDER_ORDERED + default: ORDER_NONE_UNSPECIFIED + description: |- + - ORDER_NONE_UNSPECIFIED: zero-value for channel ordering + - ORDER_UNORDERED: packets can be delivered in any order, which may differ from the order in + which they were sent. + - ORDER_ORDERED: packets are delivered exactly in the order which they were sent + title: Order defines if a channel is ORDERED or UNORDERED + connection_hops: + type: array + items: + type: string + version: + type: string + description: |- + UpgradeFields are the fields in a channel end which may be changed + during a channel upgrade. + timeout: + type: object + properties: + height: + title: block height after which the packet or upgrade times out + type: object + properties: + revision_number: + type: string + format: uint64 + title: the revision that the client is currently on + revision_height: + type: string + format: uint64 + title: the height within the given revision + description: >- + Normally the RevisionHeight is incremented at each height + while keeping + + RevisionNumber the same. However some consensus algorithms may + choose to + + reset the height in certain conditions e.g. hard forks, + state-machine + + breaking changes In these cases, the RevisionNumber is + incremented so that + + height continues to be monitonically increasing even as the + RevisionHeight + + gets reset + timestamp: + type: string + format: uint64 + title: >- + block timestamp (in nanoseconds) after which the packet or + upgrade times out + description: >- + Timeout defines an execution deadline structure for 04-channel + handlers. + + This includes packet lifecycle handlers as well as the upgrade + handshake handlers. + + A valid Timeout contains either one or both of a timestamp and + block height (sequence). + next_sequence_send: + type: string + format: uint64 + description: >- + Upgrade is a verifiable type which contains the relevant information + + for an attempted upgrade. It provides the proposed changes to the + channel + + end, the timeout for this upgrade attempt and the next packet sequence + + which allows the counterparty to efficiently know the highest sequence + it has received. + + The next sequence send is used for pruning and upgrading from + unordered to ordered channels. + proof: + type: string + format: byte + title: merkle proof of existence + proof_height: + title: height at which the proof was retrieved + type: object + properties: + revision_number: + type: string + format: uint64 + title: the revision that the client is currently on + revision_height: + type: string + format: uint64 + title: the height within the given revision + description: >- + Normally the RevisionHeight is incremented at each height while + keeping + + RevisionNumber the same. However some consensus algorithms may choose + to + + reset the height in certain conditions e.g. hard forks, state-machine + + breaking changes In these cases, the RevisionNumber is incremented so + that + + height continues to be monitonically increasing even as the + RevisionHeight + + gets reset + title: >- + QueryUpgradeResponse is the response type for the QueryUpgradeResponse RPC + method ibc.core.channel.v1.State: type: string enum: @@ -19490,10 +20789,12 @@ definitions: - STATE_TRYOPEN - STATE_OPEN - STATE_CLOSED + - STATE_FLUSHING + - STATE_FLUSHCOMPLETE default: STATE_UNINITIALIZED_UNSPECIFIED description: |- State defines if a channel is in one of the following states: - CLOSED, INIT, TRYOPEN, OPEN or UNINITIALIZED. + CLOSED, INIT, TRYOPEN, OPEN, FLUSHING, FLUSHCOMPLETE or UNINITIALIZED. - STATE_UNINITIALIZED_UNSPECIFIED: Default State - STATE_INIT: A channel has just started the opening handshake. @@ -19502,6 +20803,168 @@ definitions: ready to send and receive packets. - STATE_CLOSED: A channel has been closed and can no longer be used to send or receive packets. + - STATE_FLUSHING: A channel has just accepted the upgrade handshake attempt and is flushing in-flight packets. + - STATE_FLUSHCOMPLETE: A channel has just completed flushing any in-flight packets. + ibc.core.channel.v1.Timeout: + type: object + properties: + height: + title: block height after which the packet or upgrade times out + type: object + properties: + revision_number: + type: string + format: uint64 + title: the revision that the client is currently on + revision_height: + type: string + format: uint64 + title: the height within the given revision + description: >- + Normally the RevisionHeight is incremented at each height while + keeping + + RevisionNumber the same. However some consensus algorithms may choose + to + + reset the height in certain conditions e.g. hard forks, state-machine + + breaking changes In these cases, the RevisionNumber is incremented so + that + + height continues to be monitonically increasing even as the + RevisionHeight + + gets reset + timestamp: + type: string + format: uint64 + title: >- + block timestamp (in nanoseconds) after which the packet or upgrade + times out + description: >- + Timeout defines an execution deadline structure for 04-channel handlers. + + This includes packet lifecycle handlers as well as the upgrade handshake + handlers. + + A valid Timeout contains either one or both of a timestamp and block + height (sequence). + ibc.core.channel.v1.Upgrade: + type: object + properties: + fields: + type: object + properties: + ordering: + type: string + enum: + - ORDER_NONE_UNSPECIFIED + - ORDER_UNORDERED + - ORDER_ORDERED + default: ORDER_NONE_UNSPECIFIED + description: |- + - ORDER_NONE_UNSPECIFIED: zero-value for channel ordering + - ORDER_UNORDERED: packets can be delivered in any order, which may differ from the order in + which they were sent. + - ORDER_ORDERED: packets are delivered exactly in the order which they were sent + title: Order defines if a channel is ORDERED or UNORDERED + connection_hops: + type: array + items: + type: string + version: + type: string + description: |- + UpgradeFields are the fields in a channel end which may be changed + during a channel upgrade. + timeout: + type: object + properties: + height: + title: block height after which the packet or upgrade times out + type: object + properties: + revision_number: + type: string + format: uint64 + title: the revision that the client is currently on + revision_height: + type: string + format: uint64 + title: the height within the given revision + description: >- + Normally the RevisionHeight is incremented at each height while + keeping + + RevisionNumber the same. However some consensus algorithms may + choose to + + reset the height in certain conditions e.g. hard forks, + state-machine + + breaking changes In these cases, the RevisionNumber is incremented + so that + + height continues to be monitonically increasing even as the + RevisionHeight + + gets reset + timestamp: + type: string + format: uint64 + title: >- + block timestamp (in nanoseconds) after which the packet or upgrade + times out + description: >- + Timeout defines an execution deadline structure for 04-channel + handlers. + + This includes packet lifecycle handlers as well as the upgrade + handshake handlers. + + A valid Timeout contains either one or both of a timestamp and block + height (sequence). + next_sequence_send: + type: string + format: uint64 + description: >- + Upgrade is a verifiable type which contains the relevant information + + for an attempted upgrade. It provides the proposed changes to the channel + + end, the timeout for this upgrade attempt and the next packet sequence + + which allows the counterparty to efficiently know the highest sequence it + has received. + + The next sequence send is used for pruning and upgrading from unordered to + ordered channels. + ibc.core.channel.v1.UpgradeFields: + type: object + properties: + ordering: + type: string + enum: + - ORDER_NONE_UNSPECIFIED + - ORDER_UNORDERED + - ORDER_ORDERED + default: ORDER_NONE_UNSPECIFIED + description: |- + - ORDER_NONE_UNSPECIFIED: zero-value for channel ordering + - ORDER_UNORDERED: packets can be delivered in any order, which may differ from the order in + which they were sent. + - ORDER_ORDERED: packets are delivered exactly in the order which they were sent + title: Order defines if a channel is ORDERED or UNORDERED + connection_hops: + type: array + items: + type: string + version: + type: string + description: |- + UpgradeFields are the fields in a channel end which may be changed + during a channel upgrade. ibc.lightclients.wasm.v1.QueryChecksumsResponse: type: object properties: diff --git a/docs/docs/01-ibc/06-channel-upgrades.md b/docs/docs/01-ibc/06-channel-upgrades.md new file mode 100644 index 00000000000..6bc445b2bc7 --- /dev/null +++ b/docs/docs/01-ibc/06-channel-upgrades.md @@ -0,0 +1,92 @@ +--- +title: Channel Upgrades +sidebar_label: Channel Upgrades +sidebar_position: 6 +slug: /ibc/channel-upgrades +--- + +# Channel Upgrades + +:::note Synopsis +Learn how to upgrade existing IBC channels. +::: + +Channel upgradability is an IBC-level protocol that allows chains to leverage new application and channel features without having to create new channels or perform a network-wide upgrade. + +Prior to this feature, developers who wanted to update an application module or add a middleware to their application flow would need to create a new channel in order to use the updated application feature/middleware, resulting in a loss of the accumulated state/liquidity, token fungibility (as the channel ID is encoded in the IBC denom), and any other larger network effects of losing usage of the existing channel from relayers monitoring, etc. + +With channel upgradability, applications will be able to implement features such as but not limited to: potentially adding [denom metadata to tokens](https://github.com/cosmos/ibc/discussions/719), or utilizing the [fee middleware](https://github.com/cosmos/ibc/tree/main/spec/app/ics-029-fee-payment), all while maintaining the channels on which they currently operate. + +This document outlines the channel upgrade feature, and the multiple steps used in the upgrade process. + +## Channel Upgrade Handshake + +Channel upgrades will be achieved using a handshake process that is designed to be similar to the standard connection/channel opening handshake. + +```go +type Channel struct { + // current state of the channel end + State State `protobuf:"varint,1,opt,name=state,proto3,enum=ibc.core.channel.v1.State" json:"state,omitempty"` + // whether the channel is ordered or unordered + Ordering Order `protobuf:"varint,2,opt,name=ordering,proto3,enum=ibc.core.channel.v1.Order" json:"ordering,omitempty"` + // counterparty channel end + Counterparty Counterparty `protobuf:"bytes,3,opt,name=counterparty,proto3" json:"counterparty"` + // list of connection identifiers, in order, along which packets sent on + // this channel will travel + ConnectionHops []string `protobuf:"bytes,4,rep,name=connection_hops,json=connectionHops,proto3" json:"connection_hops,omitempty"` + // opaque channel version, which is agreed upon during the handshake + Version string `protobuf:"bytes,5,opt,name=version,proto3" json:"version,omitempty"` + // upgrade sequence indicates the latest upgrade attempt performed by this channel + // the value of 0 indicates the channel has never been upgraded + UpgradeSequence uint64 `protobuf:"varint,6,opt,name=upgrade_sequence,json=upgradeSequence,proto3" json:"upgrade_sequence,omitempty"` +} +``` + +The version, connection hops, and channel ordering are fields in this channel struct which can be changed. For example, the fee middleware can be added to an application module by updating the version string [shown here](https://github.com/cosmos/ibc-go/blob/995b647381b909e9d6065d6c21004f18fab37f55/modules/apps/29-fee/types/metadata.pb.go#L28). However, although connection hops can change in a channel upgrade, both sides must still be each other's counterparty. This is enforced by the upgrade protocol and upgrade attempts which try to alter an expected counterparty will fail. + +On a high level, successful handshake process for channel upgrades works as follows: + +1. The chain initiating the upgrade process will propose an upgrade. +2. If the counterparty agrees with the proposal, it will block sends and begin flushing any in-flight packets on its channel end. This flushing process will be covered in more detail below. +3. Upon successful completion of the previous step, the initiating chain will also block packet sends and begin flushing any in-flight packets on its channel end. +4. Once both channel ends have completed flushing packets within the upgrade timeout window, both channel ends can be opened and upgraded to the new channel fields. + +Each handshake step will be documented below in greater detail. + +## Initializing a Channel Upgrade + +A channel upgrade is initialised by submitting the `ChanUpgradeInit` message, which can be submitted only by the chain itself upon governance authorization. This message should specify an appropriate timeout window for the upgrade. It is possible to upgrade the channel ordering, the channel connection hops, and the channel version. + +As part of the handling of the `ChanUpgradeInit` message, the application's callbacks `OnChanUpgradeInit` will be triggered as well. + +After this message is handled successfully, the channel's upgrade sequence will be incremented. This upgrade sequence will serve as a nonce for the upgrade process to provide replay protection. + +### Governance gating on `ChanUpgradeInit` + +The message signer for `MsgChanUpgradeInit` must be the address which has been designated as the `authority` of the `IBCKeeper`. If this proposal passes, the counterparty's channel will upgrade by default. + +If chains want to initiate the upgrade of many channels, they will need to submit a governance proposal with multiple `MsgChanUpgradeInit` messages, one for each channel they would like to upgrade, again with message signer as the designated `authority` of the `IBCKeeper` + +## Cancelling a Channel Upgrade + +Channel upgrade cancellation is performed by submitting a `MsgChannelUpgradeCancel` message. + +It is possible for the authority to cancel an in-progress channel upgrade if the following are true: + +- The signer is the authority +- The channel state has not reached FLUSHCOMPLETE +- If the channel state has reached FLUSHCOMPLETE, an existence proof of an `ErrorReceipt` on the counterparty chain is provided at our upgrade sequence or greater + +It is possible for a relayer to cancel an in-progress channel upgrade if the following are true: + +- An existence proof of an `ErrorReceipt` on the counterparty chain is provided at our upgrade sequence or greater + +> Note: if the signer is the authority, e.g. the `gov` address, no `ErrorReceipt` or proof is required if the current channel state is not in FLUSHCOMPLETE. +> These can be left empty in the `MsgChannelUpgradeCancel` message in that case. + +Upon cancelling a channel upgrade, an `ErrorReceipt` will be written with the channel's current upgrade sequence, and +the channel will move back to `OPEN` state keeping its original parameters. + +The application's `OnChanUpgradeRestore` callback method will be invoked. + +It will then be possible to re-initiate an upgrade by sending a `MsgChannelOpenInit` message. diff --git a/docs/docs/01-ibc/06-proposals.md b/docs/docs/01-ibc/07-proposals.md similarity index 99% rename from docs/docs/01-ibc/06-proposals.md rename to docs/docs/01-ibc/07-proposals.md index 13b27fbd364..9a78f0b2aec 100644 --- a/docs/docs/01-ibc/06-proposals.md +++ b/docs/docs/01-ibc/07-proposals.md @@ -1,7 +1,7 @@ --- title: Governance Proposals sidebar_label: Governance Proposals -sidebar_position: 6 +sidebar_position: 7 slug: /ibc/proposals --- diff --git a/docs/docs/01-ibc/07-relayer.md b/docs/docs/01-ibc/08-relayer.md similarity index 99% rename from docs/docs/01-ibc/07-relayer.md rename to docs/docs/01-ibc/08-relayer.md index f40e9e671a3..100d68fc77a 100644 --- a/docs/docs/01-ibc/07-relayer.md +++ b/docs/docs/01-ibc/08-relayer.md @@ -1,7 +1,7 @@ --- title: Relayer sidebar_label: Relayer -sidebar_position: 7 +sidebar_position: 8 slug: /ibc/relayer --- diff --git a/docs/docs/01-ibc/08-proto-docs.md b/docs/docs/01-ibc/09-proto-docs.md similarity index 91% rename from docs/docs/01-ibc/08-proto-docs.md rename to docs/docs/01-ibc/09-proto-docs.md index e1e87fb2845..1666d3b7dd2 100644 --- a/docs/docs/01-ibc/08-proto-docs.md +++ b/docs/docs/01-ibc/09-proto-docs.md @@ -1,7 +1,7 @@ --- title: Protobuf Documentation sidebar_label: Protobuf Documentation -sidebar_position: 8 +sidebar_position: 9 slug: /ibc/proto-docs --- diff --git a/docs/docs/01-ibc/09-roadmap.md b/docs/docs/01-ibc/10-roadmap.md similarity index 99% rename from docs/docs/01-ibc/09-roadmap.md rename to docs/docs/01-ibc/10-roadmap.md index 335e797bbef..ee09125ee33 100644 --- a/docs/docs/01-ibc/09-roadmap.md +++ b/docs/docs/01-ibc/10-roadmap.md @@ -1,7 +1,7 @@ --- title: Roadmap sidebar_label: Roadmap -sidebar_position: 9 +sidebar_position: 10 slug: /ibc/roadmap --- diff --git a/docs/docs/01-ibc/10-troubleshooting.md b/docs/docs/01-ibc/11-troubleshooting.md similarity index 95% rename from docs/docs/01-ibc/10-troubleshooting.md rename to docs/docs/01-ibc/11-troubleshooting.md index 0504a993b17..ba9dde39256 100644 --- a/docs/docs/01-ibc/10-troubleshooting.md +++ b/docs/docs/01-ibc/11-troubleshooting.md @@ -1,7 +1,7 @@ --- title: Troubleshooting sidebar_label: Troubleshooting -sidebar_position: 10 +sidebar_position: 11 slug: /ibc/troubleshooting --- diff --git a/docs/docs/01-ibc/11-capability-module.md b/docs/docs/01-ibc/12-capability-module.md similarity index 99% rename from docs/docs/01-ibc/11-capability-module.md rename to docs/docs/01-ibc/12-capability-module.md index d8bd27108ce..05db8a887eb 100644 --- a/docs/docs/01-ibc/11-capability-module.md +++ b/docs/docs/01-ibc/12-capability-module.md @@ -1,7 +1,7 @@ --- title: Capability Module sidebar_label: Capability Module -sidebar_position: 11 +sidebar_position: 12 slug: /ibc/capability-module --- diff --git a/docs/docs/05-migrations/02-sdk-to-v1.md b/docs/docs/05-migrations/02-sdk-to-v1.md index e24c0f62bb6..88022435f64 100644 --- a/docs/docs/05-migrations/02-sdk-to-v1.md +++ b/docs/docs/05-migrations/02-sdk-to-v1.md @@ -112,7 +112,7 @@ app.IBCKeeper = ibckeeper.NewKeeper( ### UpdateClientProposal -The `UpdateClient` has been modified to take in two client-identifiers and one initial height. Please see the [documentation](../01-ibc/06-proposals.md) for more information. +The `UpdateClient` has been modified to take in two client-identifiers and one initial height. Please see the [documentation](../01-ibc/07-proposals.md) for more information. ### UpgradeProposal diff --git a/e2e/go.mod b/e2e/go.mod index 145551d62ed..ed34baa0542 100644 --- a/e2e/go.mod +++ b/e2e/go.mod @@ -12,7 +12,7 @@ require ( github.com/cosmos/ibc-go/modules/light-clients/08-wasm v0.0.0-00010101000000-000000000000 github.com/cosmos/ibc-go/v8 v8.0.0 github.com/docker/docker v24.0.7+incompatible - github.com/strangelove-ventures/interchaintest/v8 v8.0.0 + github.com/strangelove-ventures/interchaintest/v8 v8.0.1-0.20231206154526-2f014d308bea github.com/stretchr/testify v1.8.4 go.uber.org/zap v1.26.0 golang.org/x/mod v0.14.0 @@ -21,7 +21,7 @@ require ( ) require ( - cloud.google.com/go v0.110.10 // indirect + cloud.google.com/go v0.111.0 // indirect cloud.google.com/go/compute v1.23.3 // indirect cloud.google.com/go/compute/metadata v0.2.3 // indirect cloud.google.com/go/iam v1.1.5 // indirect @@ -37,35 +37,35 @@ require ( cosmossdk.io/x/evidence v0.1.0 // indirect cosmossdk.io/x/feegrant v0.1.0 // indirect cosmossdk.io/x/tx v0.13.0 // indirect - filippo.io/edwards25519 v1.0.0 // indirect + filippo.io/edwards25519 v1.1.0 // indirect github.com/99designs/go-keychain v0.0.0-20191008050251-8e49817e8af4 // indirect github.com/99designs/keyring v1.2.2 // indirect github.com/BurntSushi/toml v1.3.2 // indirect - github.com/ChainSafe/go-schnorrkel v0.0.0-20200405005733-88cbf1b4c40d // indirect + github.com/ChainSafe/go-schnorrkel v1.1.0 // indirect github.com/ChainSafe/go-schnorrkel/1 v0.0.0-00010101000000-000000000000 // indirect github.com/ComposableFi/go-subkey/v2 v2.0.0-tm03420 // indirect github.com/CosmWasm/wasmvm v1.5.0 // indirect - github.com/DataDog/datadog-go v3.2.0+incompatible // indirect + github.com/DataDog/datadog-go v4.8.3+incompatible // indirect github.com/DataDog/zstd v1.5.5 // indirect github.com/FactomProject/basen v0.0.0-20150613233007-fe3947df716e // indirect github.com/FactomProject/btcutilecc v0.0.0-20130527213604-d3a63a5752ec // indirect - github.com/Microsoft/go-winio v0.6.0 // indirect + github.com/Microsoft/go-winio v0.6.1 // indirect github.com/StirlingMarketingGroup/go-namecase v1.0.0 // indirect - github.com/avast/retry-go/v4 v4.5.0 // indirect - github.com/aws/aws-sdk-go v1.44.224 // indirect + github.com/avast/retry-go/v4 v4.5.1 // indirect + github.com/aws/aws-sdk-go v1.49.0 // indirect github.com/beorn7/perks v1.0.1 // indirect github.com/bgentry/go-netrc v0.0.0-20140422174119-9fd32a8b3d3d // indirect github.com/bgentry/speakeasy v0.1.1-0.20220910012023-760eaf8b6816 // indirect - github.com/bits-and-blooms/bitset v1.8.0 // indirect + github.com/bits-and-blooms/bitset v1.12.0 // indirect github.com/btcsuite/btcd/btcec/v2 v2.3.2 // indirect - github.com/cenkalti/backoff/v4 v4.1.3 // indirect + github.com/cenkalti/backoff/v4 v4.2.1 // indirect github.com/cespare/xxhash v1.1.0 // indirect github.com/cespare/xxhash/v2 v2.2.0 // indirect github.com/chzyer/readline v1.5.1 // indirect github.com/cockroachdb/apd/v2 v2.0.2 // indirect github.com/cockroachdb/errors v1.11.1 // indirect github.com/cockroachdb/logtags v0.0.0-20230118201751-21c54148d20b // indirect - github.com/cockroachdb/pebble v0.0.0-20231102162011-844f0582c2eb // indirect + github.com/cockroachdb/pebble v0.0.0-20231211223132-9848bcdb0fe9 // indirect github.com/cockroachdb/redact v1.1.5 // indirect github.com/cockroachdb/tokenbucket v0.0.0-20230807174530-cc333fc44b06 // indirect github.com/cometbft/cometbft-db v0.9.1 // indirect @@ -78,10 +78,10 @@ require ( github.com/cosmos/ibc-go/modules/capability v1.0.0 // indirect github.com/cosmos/ics23/go v0.10.0 // indirect github.com/cosmos/ledger-cosmos-go v0.13.3 // indirect - github.com/danieljoos/wincred v1.1.2 // indirect + github.com/danieljoos/wincred v1.2.0 // indirect github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc // indirect github.com/deckarep/golang-set v1.8.0 // indirect - github.com/decred/base58 v1.0.4 // indirect + github.com/decred/base58 v1.0.5 // indirect github.com/decred/dcrd/crypto/blake256 v1.0.1 // indirect github.com/decred/dcrd/dcrec/secp256k1/v2 v2.0.1 // indirect github.com/decred/dcrd/dcrec/secp256k1/v4 v4.2.0 // indirect @@ -89,25 +89,24 @@ require ( github.com/dgraph-io/badger/v2 v2.2007.4 // indirect github.com/dgraph-io/ristretto v0.1.1 // indirect github.com/dgryski/go-farm v0.0.0-20200201041132-a6ae2369ad13 // indirect - github.com/docker/distribution v2.8.2+incompatible // indirect + github.com/distribution/reference v0.5.0 // indirect + github.com/docker/distribution v2.8.3+incompatible // indirect github.com/docker/go-connections v0.4.0 // indirect github.com/docker/go-units v0.5.0 // indirect github.com/dustin/go-humanize v1.0.1 // indirect github.com/dvsekhvalnov/jose2go v1.5.0 // indirect github.com/emicklei/dot v1.6.0 // indirect - github.com/ethereum/go-ethereum v1.12.1 // indirect - github.com/fatih/color v1.15.0 // indirect + github.com/ethereum/go-ethereum v1.13.5 // indirect + github.com/fatih/color v1.16.0 // indirect github.com/felixge/httpsnoop v1.0.4 // indirect github.com/fsnotify/fsnotify v1.7.0 // indirect github.com/getsentry/sentry-go v0.25.0 // indirect - github.com/go-kit/kit v0.12.0 // indirect + github.com/go-kit/kit v0.13.0 // indirect github.com/go-kit/log v0.2.1 // indirect github.com/go-logfmt/logfmt v0.6.0 // indirect - github.com/go-playground/validator/v10 v10.14.0 // indirect + github.com/go-logr/logr v1.3.0 // indirect + github.com/go-logr/stdr v1.2.2 // indirect github.com/go-stack/stack v1.8.1 // indirect - github.com/gobwas/httphead v0.1.0 // indirect - github.com/gobwas/pool v0.2.1 // indirect - github.com/goccy/go-json v0.10.2 // indirect github.com/godbus/dbus v0.0.0-20190726142602-4481cbc300e2 // indirect github.com/gogo/googleapis v1.4.1 // indirect github.com/gogo/protobuf v1.3.3 // indirect @@ -120,12 +119,12 @@ require ( github.com/google/go-cmp v0.6.0 // indirect github.com/google/orderedcode v0.0.1 // indirect github.com/google/s2a-go v0.1.7 // indirect - github.com/google/uuid v1.4.0 // indirect + github.com/google/uuid v1.5.0 // indirect github.com/googleapis/enterprise-certificate-proxy v0.3.2 // indirect github.com/googleapis/gax-go/v2 v2.12.0 // indirect github.com/gorilla/handlers v1.5.2 // indirect github.com/gorilla/mux v1.8.1 // indirect - github.com/gorilla/websocket v1.5.0 // indirect + github.com/gorilla/websocket v1.5.1 // indirect github.com/grpc-ecosystem/go-grpc-middleware v1.4.0 // indirect github.com/grpc-ecosystem/grpc-gateway v1.16.0 // indirect github.com/gsterjov/go-libsecret v0.0.0-20161001094733-a6f4afe4910c // indirect @@ -133,20 +132,20 @@ require ( github.com/gtank/ristretto255 v0.1.2 // indirect github.com/hashicorp/go-cleanhttp v0.5.2 // indirect github.com/hashicorp/go-getter v1.7.3 // indirect - github.com/hashicorp/go-hclog v1.5.0 // indirect + github.com/hashicorp/go-hclog v1.6.1 // indirect github.com/hashicorp/go-immutable-radix v1.3.1 // indirect github.com/hashicorp/go-metrics v0.5.3 // indirect - github.com/hashicorp/go-plugin v1.5.2 // indirect + github.com/hashicorp/go-plugin v1.6.0 // indirect github.com/hashicorp/go-safetemp v1.0.0 // indirect github.com/hashicorp/go-version v1.6.0 // indirect github.com/hashicorp/golang-lru v1.0.2 // indirect github.com/hashicorp/hcl v1.0.0 // indirect github.com/hashicorp/yamux v0.1.1 // indirect github.com/hdevalence/ed25519consensus v0.1.0 // indirect - github.com/holiman/uint256 v1.2.3 // indirect + github.com/holiman/uint256 v1.2.4 // indirect github.com/huandu/skiplist v1.2.0 // indirect github.com/iancoleman/strcase v0.3.0 // indirect - github.com/icza/dyno v0.0.0-20220812133438-f0b6f8a18845 // indirect + github.com/icza/dyno v0.0.0-20230330125955-09f820a8d9c0 // indirect github.com/improbable-eng/grpc-web v0.15.0 // indirect github.com/inconshreveable/mousetrap v1.1.0 // indirect github.com/ipfs/go-cid v0.4.1 // indirect @@ -154,13 +153,13 @@ require ( github.com/jmhodges/levigo v1.0.0 // indirect github.com/kballard/go-shellquote v0.0.0-20180428030007-95032a82bc51 // indirect github.com/klauspost/compress v1.17.4 // indirect - github.com/klauspost/cpuid/v2 v2.2.5 // indirect + github.com/klauspost/cpuid/v2 v2.2.6 // indirect github.com/kr/pretty v0.3.1 // indirect github.com/kr/text v0.2.0 // indirect - github.com/lib/pq v1.10.7 // indirect + github.com/lib/pq v1.10.9 // indirect github.com/libp2p/go-buffer-pool v0.1.0 // indirect - github.com/libp2p/go-libp2p v0.31.0 // indirect - github.com/linxGnu/grocksdb v1.8.6 // indirect + github.com/libp2p/go-libp2p v0.32.1 // indirect + github.com/linxGnu/grocksdb v1.8.9 // indirect github.com/magiconair/properties v1.8.7 // indirect github.com/manifoldco/promptui v0.9.0 // indirect github.com/mattn/go-colorable v0.1.13 // indirect @@ -177,7 +176,7 @@ require ( github.com/mtibben/percent v0.2.1 // indirect github.com/multiformats/go-base32 v0.1.0 // indirect github.com/multiformats/go-base36 v0.2.0 // indirect - github.com/multiformats/go-multiaddr v0.11.0 // indirect + github.com/multiformats/go-multiaddr v0.12.0 // indirect github.com/multiformats/go-multibase v0.2.0 // indirect github.com/multiformats/go-multicodec v0.9.0 // indirect github.com/multiformats/go-multihash v0.2.3 // indirect @@ -185,10 +184,10 @@ require ( github.com/oasisprotocol/curve25519-voi v0.0.0-20230904125328-1f23a7beb09a // indirect github.com/oklog/run v1.1.0 // indirect github.com/opencontainers/go-digest v1.0.0 // indirect - github.com/opencontainers/image-spec v1.1.0-rc2 // indirect + github.com/opencontainers/image-spec v1.1.0-rc5 // indirect github.com/pelletier/go-toml v1.9.5 // indirect - github.com/pelletier/go-toml/v2 v2.1.0 // indirect - github.com/petermattis/goid v0.0.0-20230904192822-1876fd5063bc // indirect + github.com/pelletier/go-toml/v2 v2.1.1 // indirect + github.com/petermattis/goid v0.0.0-20231207134359-e60b3f734c67 // indirect github.com/pierrec/xxHash v0.1.5 // indirect github.com/pkg/errors v0.9.1 // indirect github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 // indirect @@ -199,7 +198,7 @@ require ( github.com/rcrowley/go-metrics v0.0.0-20201227073835-cf1acfcdf475 // indirect github.com/remyoudompheng/bigfft v0.0.0-20230129092748-24d4a6f8daec // indirect github.com/rogpeppe/go-internal v1.11.0 // indirect - github.com/rs/cors v1.8.3 // indirect + github.com/rs/cors v1.10.1 // indirect github.com/rs/zerolog v1.31.0 // indirect github.com/sagikazarmark/locafero v0.4.0 // indirect github.com/sagikazarmark/slog-shim v0.1.0 // indirect @@ -222,9 +221,14 @@ require ( github.com/zondax/ledger-go v0.14.3 // indirect go.etcd.io/bbolt v1.3.8 // indirect go.opencensus.io v0.24.0 // indirect + go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.46.1 // indirect + go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.46.1 // indirect + go.opentelemetry.io/otel v1.21.0 // indirect + go.opentelemetry.io/otel/metric v1.21.0 // indirect + go.opentelemetry.io/otel/trace v1.21.0 // indirect go.uber.org/multierr v1.11.0 // indirect golang.org/x/crypto v0.16.0 // indirect - golang.org/x/exp v0.0.0-20231006140011-7918f672742d // indirect + golang.org/x/exp v0.0.0-20231206192017-f3f8817b8deb // indirect golang.org/x/net v0.19.0 // indirect golang.org/x/oauth2 v0.15.0 // indirect golang.org/x/sync v0.5.0 // indirect @@ -232,30 +236,30 @@ require ( golang.org/x/term v0.15.0 // indirect golang.org/x/text v0.14.0 // indirect golang.org/x/time v0.5.0 // indirect - golang.org/x/tools v0.14.0 // indirect - golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2 // indirect - google.golang.org/api v0.153.0 // indirect + golang.org/x/tools v0.16.0 // indirect + golang.org/x/xerrors v0.0.0-20231012003039-104605ab7028 // indirect + google.golang.org/api v0.154.0 // indirect google.golang.org/appengine v1.6.8 // indirect - google.golang.org/genproto v0.0.0-20231120223509-83a465c0220f // indirect - google.golang.org/genproto/googleapis/api v0.0.0-20231106174013-bbf56f31fb17 // indirect - google.golang.org/genproto/googleapis/rpc v0.0.0-20231211222908-989df2bf70f3 // indirect + google.golang.org/genproto v0.0.0-20231212172506-995d672761c0 // indirect + google.golang.org/genproto/googleapis/api v0.0.0-20231212172506-995d672761c0 // indirect + google.golang.org/genproto/googleapis/rpc v0.0.0-20231212172506-995d672761c0 // indirect google.golang.org/protobuf v1.31.0 // indirect gopkg.in/ini.v1 v1.67.0 // indirect gopkg.in/natefinch/npipe.v2 v2.0.0-20160621034901-c1b8fa8bdcce // indirect gopkg.in/yaml.v3 v3.0.1 // indirect gotest.tools/v3 v3.5.1 // indirect lukechampine.com/blake3 v1.2.1 // indirect - lukechampine.com/uint128 v1.2.0 // indirect - modernc.org/cc/v3 v3.40.0 // indirect - modernc.org/ccgo/v3 v3.16.13 // indirect - modernc.org/libc v1.29.0 // indirect + lukechampine.com/uint128 v1.3.0 // indirect + modernc.org/cc/v3 v3.41.0 // indirect + modernc.org/ccgo/v3 v3.16.15 // indirect + modernc.org/libc v1.37.1 // indirect modernc.org/mathutil v1.6.0 // indirect modernc.org/memory v1.7.2 // indirect modernc.org/opt v0.1.3 // indirect modernc.org/sqlite v1.27.0 // indirect - modernc.org/strutil v1.1.3 // indirect - modernc.org/token v1.0.1 // indirect - nhooyr.io/websocket v1.8.7 // indirect + modernc.org/strutil v1.2.0 // indirect + modernc.org/token v1.1.0 // indirect + nhooyr.io/websocket v1.8.10 // indirect pgregory.net/rapid v1.1.0 // indirect sigs.k8s.io/yaml v1.4.0 // indirect ) diff --git a/e2e/go.sum b/e2e/go.sum index 70dbcaa1f6b..ab89db3b690 100644 --- a/e2e/go.sum +++ b/e2e/go.sum @@ -30,8 +30,8 @@ cloud.google.com/go v0.100.2/go.mod h1:4Xra9TjzAeYHrl5+oeLlzbM2k3mjVhZh4UqTZ//w9 cloud.google.com/go v0.102.0/go.mod h1:oWcCzKlqJ5zgHQt9YsaeTY9KzIvjyy0ArmiBUgpQ+nc= cloud.google.com/go v0.102.1/go.mod h1:XZ77E9qnTEnrgEOvr4xzfdX5TRo7fB4T2F4O6+34hIU= cloud.google.com/go v0.104.0/go.mod h1:OO6xxXdJyvuJPcEPBLN9BJPD+jep5G1+2U5B5gkRYtA= -cloud.google.com/go v0.110.10 h1:LXy9GEO+timppncPIAZoOj3l58LIU9k+kn48AN7IO3Y= -cloud.google.com/go v0.110.10/go.mod h1:v1OoFqYxiBkUrruItNM3eT4lLByNjxmJSV/xDKJNnic= +cloud.google.com/go v0.111.0 h1:YHLKNupSD1KqjDbQ3+LVdQ81h/UJbJyZG203cEfnQgM= +cloud.google.com/go v0.111.0/go.mod h1:0mibmpKP1TyOOFYQY5izo0LnT+ecvOQ0Sg3OdmMiNRU= cloud.google.com/go/aiplatform v1.22.0/go.mod h1:ig5Nct50bZlzV6NvKaTwmplLLddFx0YReh9WfTO5jKw= cloud.google.com/go/aiplatform v1.24.0/go.mod h1:67UUvRBKG6GTayHKV8DBv2RtR1t93YRu5B1P3x99mYY= cloud.google.com/go/analytics v0.11.0/go.mod h1:DjEWCu41bVbYcKyvlws9Er60YE4a//bK6mnhWvQeFNI= @@ -213,8 +213,8 @@ cosmossdk.io/x/tx v0.13.0/go.mod h1:CpNQtmoqbXa33/DVxWQNx5Dcnbkv2xGUhL7tYQ5wUsY= cosmossdk.io/x/upgrade v0.1.1 h1:aoPe2gNvH+Gwt/Pgq3dOxxQVU3j5P6Xf+DaUJTDZATc= cosmossdk.io/x/upgrade v0.1.1/go.mod h1:MNLptLPcIFK9CWt7Ra//8WUZAxweyRDNcbs5nkOcQy0= dmitri.shuralyov.com/gpu/mtl v0.0.0-20190408044501-666a987793e9/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU= -filippo.io/edwards25519 v1.0.0 h1:0wAIcmJUqRdI8IJ/3eGi5/HwXZWPujYXXlkrQogz0Ek= -filippo.io/edwards25519 v1.0.0/go.mod h1:N1IkdkCkiLB6tki+MYJoSx2JTY9NUlxZE7eHn5EwJns= +filippo.io/edwards25519 v1.1.0 h1:FNf4tywRC1HmFuKW5xopWpigGjJKiJSV0Cqo0cJWDaA= +filippo.io/edwards25519 v1.1.0/go.mod h1:BxyFTGdWcka3PhytdK4V28tE5sGfRvvvRV7EaN4VDT4= github.com/99designs/go-keychain v0.0.0-20191008050251-8e49817e8af4 h1:/vQbFIOMbk2FiG/kXiLl8BRyzTWDw7gX/Hz7Dd5eDMs= github.com/99designs/go-keychain v0.0.0-20191008050251-8e49817e8af4/go.mod h1:hN7oaIRCjzsZ2dE+yG5k+rsdt3qcwykqK6HVGcKwsw4= github.com/99designs/keyring v1.2.2 h1:pZd3neh/EmUzWONb35LxQfvuY7kiSXAq3HQd97+XBn0= @@ -233,8 +233,9 @@ github.com/ComposableFi/go-subkey/v2 v2.0.0-tm03420 h1:oknQF/iIhf5lVjbwjsVDzDByu github.com/ComposableFi/go-subkey/v2 v2.0.0-tm03420/go.mod h1:KYkiMX5AbOlXXYfxkrYPrRPV6EbVUALTQh5ptUOJzu8= github.com/CosmWasm/wasmvm v1.5.0 h1:3hKeT9SfwfLhxTGKH3vXaKFzBz1yuvP8SlfwfQXbQfw= github.com/CosmWasm/wasmvm v1.5.0/go.mod h1:fXB+m2gyh4v9839zlIXdMZGeLAxqUdYdFQqYsTha2hc= -github.com/DataDog/datadog-go v3.2.0+incompatible h1:qSG2N4FghB1He/r2mFrWKCaL7dXCilEuNEeAn20fdD4= github.com/DataDog/datadog-go v3.2.0+incompatible/go.mod h1:LButxg5PwREeZtORoXG3tL4fMGNddJ+vMq1mwgfaqoQ= +github.com/DataDog/datadog-go v4.8.3+incompatible h1:fNGaYSuObuQb5nzeTQqowRAd9bpDIRRV4/gUtIBjh8Q= +github.com/DataDog/datadog-go v4.8.3+incompatible/go.mod h1:LButxg5PwREeZtORoXG3tL4fMGNddJ+vMq1mwgfaqoQ= github.com/DataDog/zstd v1.5.5 h1:oWf5W7GtOLgp6bciQYDmhHHjdhYkALu6S/5Ni9ZgSvQ= github.com/DataDog/zstd v1.5.5/go.mod h1:g4AWEaM3yOg3HYfnJ3YIawPnVdXJh9QME85blwSAmyw= github.com/FactomProject/basen v0.0.0-20150613233007-fe3947df716e h1:ahyvB3q25YnZWly5Gq1ekg6jcmWaGj/vG/MhF4aisoc= @@ -242,16 +243,16 @@ github.com/FactomProject/basen v0.0.0-20150613233007-fe3947df716e/go.mod h1:kGUq github.com/FactomProject/btcutilecc v0.0.0-20130527213604-d3a63a5752ec h1:1Qb69mGp/UtRPn422BH4/Y4Q3SLUrD9KHuDkm8iodFc= github.com/FactomProject/btcutilecc v0.0.0-20130527213604-d3a63a5752ec/go.mod h1:CD8UlnlLDiqb36L110uqiP2iSflVjx9g/3U9hCI4q2U= github.com/Knetic/govaluate v3.0.1-0.20171022003610-9aa49832a739+incompatible/go.mod h1:r7JcOSlj0wfOMncg0iLm8Leh48TZaKVeNIfJntJ2wa0= -github.com/Microsoft/go-winio v0.6.0 h1:slsWYD/zyx7lCXoZVlvQrj0hPTM1HI4+v1sIda2yDvg= -github.com/Microsoft/go-winio v0.6.0/go.mod h1:cTAf44im0RAYeL23bpB+fzCyDH2MJiz2BO69KH/soAE= +github.com/Microsoft/go-winio v0.6.1 h1:9/kr64B9VUZrLm5YYwbGtUJnMgqWVOdUAXu6Migciow= +github.com/Microsoft/go-winio v0.6.1/go.mod h1:LRdKpFKfdobln8UmuiYcKPot9D2v6svN5+sAH+4kjUM= github.com/Nvveen/Gotty v0.0.0-20120604004816-cd527374f1e5 h1:TngWCqHvy9oXAN6lEVMRuU21PR1EtLVZJmdB18Gu3Rw= github.com/Nvveen/Gotty v0.0.0-20120604004816-cd527374f1e5/go.mod h1:lmUJ/7eu/Q8D7ML55dXQrVaamCz2vxCfdQBasLZfHKk= github.com/OneOfOne/xxhash v1.2.2 h1:KMrpdQIwFcEqXDklaen+P1axHaj9BSKzvpUUfnHldSE= github.com/OneOfOne/xxhash v1.2.2/go.mod h1:HSdplMjZKSmBqAxg5vPj2TmRDmfkzw+cTzAElWljhcU= github.com/Shopify/sarama v1.19.0/go.mod h1:FVkBWblsNy7DGZRfXLU0O9RCGt5g3g3yEuWXgklEdEo= github.com/Shopify/toxiproxy v2.1.4+incompatible/go.mod h1:OXgGpZ6Cli1/URJOF1DMxUHB2q5Ap20/P/eIdh4G0pI= -github.com/StackExchange/wmi v0.0.0-20180116203802-5d049714c4a6 h1:fLjPD/aNc3UIOA6tDi6QXUemppXK3P9BI7mr2hd6gx8= -github.com/StackExchange/wmi v0.0.0-20180116203802-5d049714c4a6/go.mod h1:3eOhrUMpNV+6aFIbp5/iudMxNCF27Vw2OZgy4xEx0Fg= +github.com/StackExchange/wmi v1.2.1 h1:VIkavFPXSjcnS+O8yTq7NI32k0R5Aj+v39y29VYDOSA= +github.com/StackExchange/wmi v1.2.1/go.mod h1:rcmrprowKIVzvc+NUiLncP2uuArMWLCbu9SBzvHz7e8= github.com/StirlingMarketingGroup/go-namecase v1.0.0 h1:2CzaNtCzc4iNHirR+5ru9OzGg8rQp860gqLBFqRI02Y= github.com/StirlingMarketingGroup/go-namecase v1.0.0/go.mod h1:ZsoSKcafcAzuBx+sndbxHu/RjDcDTrEdT4UvhniHfio= github.com/VividCortex/gohistogram v1.0.0 h1:6+hBz+qvs0JOrrNhhmR7lFxo5sINxBCGXrdtl/UvroE= @@ -272,13 +273,13 @@ github.com/armon/consul-api v0.0.0-20180202201655-eb2c6b5be1b6/go.mod h1:grANhF5 github.com/armon/go-metrics v0.0.0-20180917152333-f0300d1749da/go.mod h1:Q73ZrmVTwzkszR9V5SSuryQ31EELlFMUz1kKyl939pY= github.com/armon/go-radix v0.0.0-20180808171621-7fddfc383310/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8= github.com/aryann/difflib v0.0.0-20170710044230-e206f873d14a/go.mod h1:DAHtR1m6lCRdSC2Tm3DSWRPvIPr6xNKyeHdqDQSQT+A= -github.com/avast/retry-go/v4 v4.5.0 h1:QoRAZZ90cj5oni2Lsgl2GW8mNTnUCnmpx/iKpwVisHg= -github.com/avast/retry-go/v4 v4.5.0/go.mod h1:7hLEXp0oku2Nir2xBAsg0PTphp9z71bN5Aq1fboC3+I= +github.com/avast/retry-go/v4 v4.5.1 h1:AxIx0HGi4VZ3I02jr78j5lZ3M6x1E0Ivxa6b0pUUh7o= +github.com/avast/retry-go/v4 v4.5.1/go.mod h1:/sipNsvNB3RRuT5iNcb6h73nw3IBmXJ/H3XrCQYSOpc= github.com/aws/aws-lambda-go v1.13.3/go.mod h1:4UKl9IzQMoD+QF79YdCuzCwp8VbmG4VAQwij/eHl5CU= github.com/aws/aws-sdk-go v1.27.0/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo= github.com/aws/aws-sdk-go v1.44.122/go.mod h1:y4AeaBuwd2Lk+GepC1E9v0qOiTws0MIWAX4oIKwKHZo= -github.com/aws/aws-sdk-go v1.44.224 h1:09CiaaF35nRmxrzWZ2uRq5v6Ghg/d2RiPjZnSgtt+RQ= -github.com/aws/aws-sdk-go v1.44.224/go.mod h1:aVsgQcEevwlmQ7qHE9I3h+dtQgpqhFB+i8Phjh7fkwI= +github.com/aws/aws-sdk-go v1.49.0 h1:g9BkW1fo9GqKfwg2+zCD+TW/D36Ux+vtfJ8guF4AYmY= +github.com/aws/aws-sdk-go v1.49.0/go.mod h1:LF8svs817+Nz+DmiMQKTO3ubZ/6IaTpq3TjupRn3Eqk= github.com/aws/aws-sdk-go-v2 v0.18.0/go.mod h1:JWVYvqSMppoMJC0x5wdwiImzgXTI9FuZwxzkQq9wy+g= github.com/benbjohnson/clock v1.1.0/go.mod h1:J11/hYXuz8f4ySSvYwY0FKfm+ezbsZBKZxNJlLklBHA= github.com/beorn7/perks v0.0.0-20180321164747-3a771d992973/go.mod h1:Dwedo/Wpr24TaqPxmxbtue+5NUziq4I4S80YR8gNf3Q= @@ -290,8 +291,8 @@ github.com/bgentry/go-netrc v0.0.0-20140422174119-9fd32a8b3d3d/go.mod h1:6QX/PXZ github.com/bgentry/speakeasy v0.1.0/go.mod h1:+zsyZBPWlz7T6j88CTgSN5bM796AkVf0kBD4zp0CCIs= github.com/bgentry/speakeasy v0.1.1-0.20220910012023-760eaf8b6816 h1:41iFGWnSlI2gVpmOtVTJZNodLdLQLn/KsJqFvXwnd/s= github.com/bgentry/speakeasy v0.1.1-0.20220910012023-760eaf8b6816/go.mod h1:+zsyZBPWlz7T6j88CTgSN5bM796AkVf0kBD4zp0CCIs= -github.com/bits-and-blooms/bitset v1.8.0 h1:FD+XqgOZDUxxZ8hzoBFuV9+cGWY9CslN6d5MS5JVb4c= -github.com/bits-and-blooms/bitset v1.8.0/go.mod h1:7hO7Gc7Pp1vODcmWvKMRA9BNmbv6a/7QIWpPxHddWR8= +github.com/bits-and-blooms/bitset v1.12.0 h1:U/q1fAF7xXRhFCrhROzIfffYnu+dlS38vCZtmFVPHmA= +github.com/bits-and-blooms/bitset v1.12.0/go.mod h1:7hO7Gc7Pp1vODcmWvKMRA9BNmbv6a/7QIWpPxHddWR8= github.com/btcsuite/btcd/btcec/v2 v2.3.2 h1:5n0X6hX0Zk+6omWcihdYvdAlGf2DfasC0GMf7DClJ3U= github.com/btcsuite/btcd/btcec/v2 v2.3.2/go.mod h1:zYzJ8etWJQIv1Ogk7OzpWjowwOdXY1W/17j2MW85J04= github.com/btcsuite/btcd/btcutil v1.1.3 h1:xfbtw8lwpp0G6NwSHb+UE67ryTFHJAiNuipusjXSohQ= @@ -306,8 +307,8 @@ github.com/casbin/casbin/v2 v2.1.2/go.mod h1:YcPU1XXisHhLzuxH9coDNf2FbKpjGlbCg3n github.com/cenkalti/backoff v2.2.1+incompatible h1:tNowT99t7UNflLxfYYSlKYsBpXdEet03Pg2g16Swow4= github.com/cenkalti/backoff v2.2.1+incompatible/go.mod h1:90ReRw6GdpyfrHakVjL/QHaoyV4aDUVVkXQJJJ3NXXM= github.com/cenkalti/backoff/v4 v4.1.1/go.mod h1:scbssz8iZGpm3xbr14ovlUdkxfGXNInqkPWOWmG2CLw= -github.com/cenkalti/backoff/v4 v4.1.3 h1:cFAlzYUlVYDysBEH2T5hyJZMh3+5+WCBvSnK6Q8UtC4= -github.com/cenkalti/backoff/v4 v4.1.3/go.mod h1:scbssz8iZGpm3xbr14ovlUdkxfGXNInqkPWOWmG2CLw= +github.com/cenkalti/backoff/v4 v4.2.1 h1:y4OZtCnogmCPw98Zjyt5a6+QwPLGkiQsYW5oUqylYbM= +github.com/cenkalti/backoff/v4 v4.2.1/go.mod h1:Y3VNntkOUPxTVeUxJ/G5vcM//AlwfmyYozVcomhLiZE= github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= github.com/cespare/xxhash v1.1.0 h1:a6HrQnmkObjyL+Gs60czilIUGqrzKutQD6XZog3p+ko= github.com/cespare/xxhash v1.1.0/go.mod h1:XrSqR1VqqWfGrhpAt58auRo0WTKS1nRRg3ghfAqPWnc= @@ -339,6 +340,8 @@ github.com/cncf/xds/go v0.0.0-20210805033703-aa0b78936158/go.mod h1:eXthEFrGJvWH github.com/cncf/xds/go v0.0.0-20210922020428-25de7278fc84/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20211001041855-01bcc9b48dfe/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20211011173535-cb28da3451f1/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= +github.com/cncf/xds/go v0.0.0-20230607035331-e9ce68804cb4 h1:/inchEIKaYC1Akx+H+gqO04wryn5h75LSazbRlnya1k= +github.com/cncf/xds/go v0.0.0-20230607035331-e9ce68804cb4/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cockroachdb/apd/v2 v2.0.2 h1:weh8u7Cneje73dDh+2tEVLUvyBc89iwepWCD8b8034E= github.com/cockroachdb/apd/v2 v2.0.2/go.mod h1:DDxRlzC2lo3/vSlmSoS7JkqbbrARPuFOGr0B9pvN3Gw= github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa/go.mod h1:zn76sxSg3SzpJ0PPJaLDCu+Bu0Lg3sKTORVIj19EIF8= @@ -348,8 +351,10 @@ github.com/cockroachdb/errors v1.11.1 h1:xSEW75zKaKCWzR3OfxXUxgrk/NtT4G1MiOv5lWZ github.com/cockroachdb/errors v1.11.1/go.mod h1:8MUxA3Gi6b25tYlFEBGLf+D8aISL+M4MIpiWMSNRfxw= github.com/cockroachdb/logtags v0.0.0-20230118201751-21c54148d20b h1:r6VH0faHjZeQy818SGhaone5OnYfxFR/+AzdY3sf5aE= github.com/cockroachdb/logtags v0.0.0-20230118201751-21c54148d20b/go.mod h1:Vz9DsVWQQhf3vs21MhPMZpMGSht7O/2vFW2xusFUVOs= -github.com/cockroachdb/pebble v0.0.0-20231102162011-844f0582c2eb h1:6Po+YYKT5B5ZXN0wd2rwFBaebM0LufPf8p4zxOd48Kg= -github.com/cockroachdb/pebble v0.0.0-20231102162011-844f0582c2eb/go.mod h1:acMRUGd/BK8AUmQNK3spUCCGzFLZU2bSST3NMXSq2Kc= +github.com/cockroachdb/metamorphic v0.0.0-20231108215700-4ba948b56895 h1:XANOgPYtvELQ/h4IrmPAohXqe2pWA8Bwhejr3VQoZsA= +github.com/cockroachdb/metamorphic v0.0.0-20231108215700-4ba948b56895/go.mod h1:aPd7gM9ov9M8v32Yy5NJrDyOcD8z642dqs+F0CeNXfA= +github.com/cockroachdb/pebble v0.0.0-20231211223132-9848bcdb0fe9 h1:f3eH58jJkWd70J3E6BNQPNjMEorA9l72dLBJCoX/UEc= +github.com/cockroachdb/pebble v0.0.0-20231211223132-9848bcdb0fe9/go.mod h1:BHuaMa/lK7fUe75BlsteiiTu8ptIG+qSAuDtGMArP18= github.com/cockroachdb/redact v1.1.5 h1:u1PMllDkdFfPWaNGMyLD1+so+aq3uUItthCFqzwPJ30= github.com/cockroachdb/redact v1.1.5/go.mod h1:BVNblN9mBWFyMyqK1k3AAiSxhvhfK2oOZZ2lK+dpvRg= github.com/cockroachdb/tokenbucket v0.0.0-20230807174530-cc333fc44b06 h1:zuQyyAKVxetITBuuhv3BI9cMrmStnpT18zmgmTxunpo= @@ -396,8 +401,8 @@ github.com/cpuguy83/go-md2man/v2 v2.0.0-20190314233015-f79a8a8ca69d/go.mod h1:ma github.com/cpuguy83/go-md2man/v2 v2.0.3/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46tRHOmNcaadrF8o= github.com/creack/pty v1.1.7/go.mod h1:lj5s0c3V2DBrqTV7llrYr5NG6My20zk30Fl46Y7DoTY= github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= -github.com/danieljoos/wincred v1.1.2 h1:QLdCxFs1/Yl4zduvBdcHB8goaYk9RARS2SgLLRuAyr0= -github.com/danieljoos/wincred v1.1.2/go.mod h1:GijpziifJoIBfYh+S7BbkdUTU4LfM+QnGqR5Vl2tAx0= +github.com/danieljoos/wincred v1.2.0 h1:ozqKHaLK0W/ii4KVbbvluM91W2H3Sh0BncbUNPS7jLE= +github.com/danieljoos/wincred v1.2.0/go.mod h1:FzQLLMKBFdvu+osBrnFODiv32YGwCfx0SkRa/eYHgec= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc h1:U9qPSI2PIWSS1VwoXQT9A3Wy9MM3WgvqSxFWenqJduM= @@ -406,8 +411,8 @@ github.com/deckarep/golang-set v1.8.0 h1:sk9/l/KqpunDwP7pSjUg0keiOOLEnOBHzykLrsP github.com/deckarep/golang-set v1.8.0/go.mod h1:5nI87KwE7wgsBU1F4GKAw2Qod7p5kyS383rP6+o6qqo= github.com/deckarep/golang-set/v2 v2.1.0 h1:g47V4Or+DUdzbs8FxCCmgb6VYd+ptPAngjM6dtGktsI= github.com/deckarep/golang-set/v2 v2.1.0/go.mod h1:VAky9rY/yGXJOLEDv3OMci+7wtDpOF4IN+y82NBOac4= -github.com/decred/base58 v1.0.4 h1:QJC6B0E0rXOPA8U/kw2rP+qiRJsUaE2Er+pYb3siUeA= -github.com/decred/base58 v1.0.4/go.mod h1:jJswKPEdvpFpvf7dsDvFZyLT22xZ9lWqEByX38oGd9E= +github.com/decred/base58 v1.0.5 h1:hwcieUM3pfPnE/6p3J100zoRfGkQxBulZHo7GZfOqic= +github.com/decred/base58 v1.0.5/go.mod h1:s/8lukEHFA6bUQQb/v3rjUySJ2hu+RioCzLukAVkrfw= github.com/decred/dcrd/chaincfg/chainhash v1.0.2 h1:rt5Vlq/jM3ZawwiacWjPa+smINyLRN07EO0cNBV6DGU= github.com/decred/dcrd/chaincfg/chainhash v1.0.2/go.mod h1:BpbrGgrPTr3YJYRN3Bm+D9NuaFd+zGyNeIKgrhCXK60= github.com/decred/dcrd/crypto/blake256 v1.0.0/go.mod h1:sQl2p6Y26YV+ZOcSTP6thNdn47hh8kt6rqSlvmrXFAc= @@ -428,8 +433,10 @@ github.com/dgrijalva/jwt-go v3.2.0+incompatible/go.mod h1:E3ru+11k8xSBh+hMPgOLZm github.com/dgryski/go-farm v0.0.0-20190423205320-6a90982ecee2/go.mod h1:SqUrOPUnsFjfmXRMNPybcSiG0BgUW2AuFH8PAnS2iTw= github.com/dgryski/go-farm v0.0.0-20200201041132-a6ae2369ad13 h1:fAjc9m62+UWV/WAFKLNi6ZS0675eEUC9y3AlwSbQu1Y= github.com/dgryski/go-farm v0.0.0-20200201041132-a6ae2369ad13/go.mod h1:SqUrOPUnsFjfmXRMNPybcSiG0BgUW2AuFH8PAnS2iTw= -github.com/docker/distribution v2.8.2+incompatible h1:T3de5rq0dB1j30rp0sA2rER+m322EBzniBPB6ZIzuh8= -github.com/docker/distribution v2.8.2+incompatible/go.mod h1:J2gT2udsDAN96Uj4KfcMRqY0/ypR+oyYUYmja8H+y+w= +github.com/distribution/reference v0.5.0 h1:/FUIFXtfc/x2gpa5/VGfiGLuOIdYa1t65IKK2OFGvA0= +github.com/distribution/reference v0.5.0/go.mod h1:BbU0aIcezP1/5jX/8MP0YiH4SdvB5Y4f/wlDRiLyi3E= +github.com/docker/distribution v2.8.3+incompatible h1:AtKxIZ36LoNK51+Z6RpzLpddBirtxJnzDrHLEKxTAYk= +github.com/docker/distribution v2.8.3+incompatible/go.mod h1:J2gT2udsDAN96Uj4KfcMRqY0/ypR+oyYUYmja8H+y+w= github.com/docker/docker v24.0.7+incompatible h1:Wo6l37AuwP3JaMnZa226lzVXGA3F9Ig1seQen0cKYlM= github.com/docker/docker v24.0.7+incompatible/go.mod h1:eEKB0N0r5NX/I1kEveEz05bcu8tLC/8azJZsviup8Sk= github.com/docker/go-connections v0.4.0 h1:El9xVISelRB7BuFusrZozjnkIM5YnzCViNKohAFqRJQ= @@ -459,12 +466,14 @@ github.com/envoyproxy/go-control-plane v0.9.9-0.20210512163311-63b5d3c536b0/go.m github.com/envoyproxy/go-control-plane v0.9.10-0.20210907150352-cf90f659a021/go.mod h1:AFq3mo9L8Lqqiid3OhADV3RfLJnjiw63cSpi+fDTRC0= github.com/envoyproxy/go-control-plane v0.10.2-0.20220325020618-49ff273808a1/go.mod h1:KJwIaB5Mv44NWtYuAOFCVOjcI94vtpEz2JU/D2v6IjE= github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= -github.com/ethereum/go-ethereum v1.12.1 h1:1kXDPxhLfyySuQYIfRxVBGYuaHdxNNxevA73vjIwsgk= -github.com/ethereum/go-ethereum v1.12.1/go.mod h1:zKetLweqBR8ZS+1O9iJWI8DvmmD2NzD19apjEWDCsnw= +github.com/envoyproxy/protoc-gen-validate v1.0.2 h1:QkIBuU5k+x7/QXPvPPnWXWlCdaBFApVqftFV6k087DA= +github.com/envoyproxy/protoc-gen-validate v1.0.2/go.mod h1:GpiZQP3dDbg4JouG/NNS7QWXpgx6x8QiMKdmN72jogE= +github.com/ethereum/go-ethereum v1.13.5 h1:U6TCRciCqZRe4FPXmy1sMGxTfuk8P7u2UoinF3VbaFk= +github.com/ethereum/go-ethereum v1.13.5/go.mod h1:yMTu38GSuyxaYzQMViqNmQ1s3cE84abZexQmTgenWk0= github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= github.com/fatih/color v1.13.0/go.mod h1:kLAiJbzzSOZDVNGyDpeOxJ47H46qBXwg5ILebYFFOfk= -github.com/fatih/color v1.15.0 h1:kOqh6YHBtK8aywxGerMG2Eq3H6Qgoqeo13Bk2Mv/nBs= -github.com/fatih/color v1.15.0/go.mod h1:0h5ZqXfHYED7Bhv2ZJamyIOUej9KtShiJESRwBDUSsw= +github.com/fatih/color v1.16.0 h1:zmkK9Ngbjj+K0yRhTVONQh1p/HknKYSlNT+vZCzyokM= +github.com/fatih/color v1.16.0/go.mod h1:fL2Sau1YI5c0pdGEVCbKQbLXB6edEj1ZgiY4NijnWvE= github.com/felixge/httpsnoop v1.0.4 h1:NFTV2Zj1bL4mc9sqWACXbQFVBBg2W3GPvqp8/ESS2Wg= github.com/felixge/httpsnoop v1.0.4/go.mod h1:m8KPJKqk1gH5J9DgRY2ASl2lWCfGKXixSwevea8zH2U= github.com/fortytw2/leaktest v1.3.0 h1:u8491cBMTQ8ft8aeV+adlcytMZylmA5nnwwkRZjI8vw= @@ -477,16 +486,11 @@ github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMo github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ= github.com/fsnotify/fsnotify v1.7.0 h1:8JEhPFa5W2WU7YfeZzPNqzMP6Lwt7L2715Ggo0nosvA= github.com/fsnotify/fsnotify v1.7.0/go.mod h1:40Bi/Hjc2AVfZrqy+aj+yEI+/bRxZnMJyTJwOpGvigM= -github.com/gabriel-vasile/mimetype v1.4.2 h1:w5qFW6JKBz9Y393Y4q372O9A7cUSequkh1Q7OhCmWKU= -github.com/gabriel-vasile/mimetype v1.4.2/go.mod h1:zApsH/mKG4w07erKIaJPFiX0Tsq9BFQgN3qGY5GnNgA= github.com/getsentry/sentry-go v0.25.0 h1:q6Eo+hS+yoJlTO3uu/azhQadsD8V+jQn2D8VvX1eOyI= github.com/getsentry/sentry-go v0.25.0/go.mod h1:lc76E2QywIyW8WuBnwl8Lc4bkmQH4+w1gwTf25trprY= github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= -github.com/gin-contrib/sse v0.1.0 h1:Y/yl/+YNO8GZSjAhjMsSuLt29uWRFHdHYUb5lYOV9qE= github.com/gin-contrib/sse v0.1.0/go.mod h1:RHrZQHXnP2xjPF+u1gW/2HnVO7nvIa9PG3Gm+fLHvGI= github.com/gin-gonic/gin v1.6.3/go.mod h1:75u5sXoLsGZoRN5Sgbi1eraJ4GU3++wFwWzhwvtwp4M= -github.com/gin-gonic/gin v1.8.1 h1:4+fr/el88TOO3ewCmQr8cx/CtZ/umlIRIs5M4NTNjf8= -github.com/gin-gonic/gin v1.8.1/go.mod h1:ji8BvRH1azfM+SYow9zQ6SZMvR8qOMZHmsCuWR9tTTk= github.com/go-errors/errors v1.4.2 h1:J6MZopCL4uSllY1OfXM374weqZFFItUbrImctkmUxIA= github.com/go-errors/errors v1.4.2/go.mod h1:sIVyrIiJhuEF+Pj9Ebtd6P/rEYROXFi3BopGUQ5a5Og= github.com/go-gl/glfw v0.0.0-20190409004039-e6da0acd62b1/go.mod h1:vR7hzQXu2zJy9AVAgeJqvqgH9Q5CA+iKCZ2gyEVpxRU= @@ -495,8 +499,8 @@ github.com/go-gl/glfw/v3.3/glfw v0.0.0-20200222043503-6f7a984d4dc4/go.mod h1:tQ2 github.com/go-kit/kit v0.8.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= github.com/go-kit/kit v0.9.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= github.com/go-kit/kit v0.10.0/go.mod h1:xUsJbQ/Fp4kEt7AFgCuvyX4a71u8h9jB8tj/ORgOZ7o= -github.com/go-kit/kit v0.12.0 h1:e4o3o3IsBfAKQh5Qbbiqyfu97Ku7jrO/JbohvztANh4= -github.com/go-kit/kit v0.12.0/go.mod h1:lHd+EkCZPIwYItmGDDRdhinkzX2A1sj+M9biaEaizzs= +github.com/go-kit/kit v0.13.0 h1:OoneCcHKHQ03LfBpoQCUfCluwd2Vt3ohz+kvbJneZAU= +github.com/go-kit/kit v0.13.0/go.mod h1:phqEHMMUbyrCFCTgH48JueqrM3md2HcAZ8N3XE4FKDg= github.com/go-kit/log v0.1.0/go.mod h1:zbhenjAZHb184qTLMA9ZjW7ThYL0H2mk7Q6pNt4vbaY= github.com/go-kit/log v0.2.1 h1:MRVx0/zhvdseW+Gza6N9rVzU/IVzaeE1SFI4raAhmBU= github.com/go-kit/log v0.2.1/go.mod h1:NwTd00d/i8cPZ3xOwwiv2PO5MOcx78fFErGNcVmBjv0= @@ -505,33 +509,24 @@ github.com/go-logfmt/logfmt v0.4.0/go.mod h1:3RMwSq7FuexP4Kalkev3ejPJsZTpXXBr9+V github.com/go-logfmt/logfmt v0.5.0/go.mod h1:wCYkCAKZfumFQihp8CzCvQ3paCTfi41vtzG1KdI/P7A= github.com/go-logfmt/logfmt v0.6.0 h1:wGYYu3uicYdqXVgoYbvnkrPVXkuLM1p1ifugDMEdRi4= github.com/go-logfmt/logfmt v0.6.0/go.mod h1:WYhtIu8zTZfxdn5+rREduYbwxfcBr/Vr6KEVveWlfTs= +github.com/go-logr/logr v1.2.2/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A= +github.com/go-logr/logr v1.3.0 h1:2y3SDp0ZXuc6/cjLSZ+Q3ir+QB9T/iG5yYRXqsagWSY= +github.com/go-logr/logr v1.3.0/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= +github.com/go-logr/stdr v1.2.2 h1:hSWxHoqTgW2S2qGc0LTAI563KZ5YKYRhT3MFKZMbjag= +github.com/go-logr/stdr v1.2.2/go.mod h1:mMo/vtBO5dYbehREoey6XUKy/eSumjCCveDpRre4VKE= github.com/go-ole/go-ole v1.2.6 h1:/Fpf6oFPoeFik9ty7siob0G6Ke8QvQEuVcuChpwXzpY= github.com/go-ole/go-ole v1.2.6/go.mod h1:pprOEPIfldk/42T2oK7lQ4v4JSDwmV0As9GaiUsvbm0= github.com/go-playground/assert/v2 v2.0.1/go.mod h1:VDjEfimB/XKnb+ZQfWdccd7VUvScMdVu0Titje2rxJ4= github.com/go-playground/locales v0.13.0/go.mod h1:taPMhCMXrRLJO55olJkUXHZBHCxTMfnGwq/HNwmWNS8= -github.com/go-playground/locales v0.14.1 h1:EWaQ/wswjilfKLTECiXz7Rh+3BjFhfDFKv/oXslEjJA= -github.com/go-playground/locales v0.14.1/go.mod h1:hxrqLVvrK65+Rwrd5Fc6F2O76J/NuW9t0sjnWqG1slY= github.com/go-playground/universal-translator v0.17.0/go.mod h1:UkSxE5sNxxRwHyU+Scu5vgOQjsIJAF8j9muTVoKLVtA= -github.com/go-playground/universal-translator v0.18.1 h1:Bcnm0ZwsGyWbCzImXv+pAJnYK9S473LQFuzCbDbfSFY= -github.com/go-playground/universal-translator v0.18.1/go.mod h1:xekY+UJKNuX9WP91TpwSH2VMlDf28Uj24BCp08ZFTUY= github.com/go-playground/validator/v10 v10.2.0/go.mod h1:uOYAAleCW8F/7oMFd6aG0GOhaH6EGOAJShg8Id5JGkI= -github.com/go-playground/validator/v10 v10.14.0 h1:vgvQWe3XCz3gIeFDm/HnTIbj6UGmg/+t63MyGU2n5js= -github.com/go-playground/validator/v10 v10.14.0/go.mod h1:9iXMNT7sEkjXb0I+enO7QXmzG6QCsPWY4zveKFVRSyU= github.com/go-sql-driver/mysql v1.4.0/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w= github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= github.com/go-stack/stack v1.8.1 h1:ntEHSVwIt7PNXNpgPmVfMrNhLtgjlmnZha2kOpuRiDw= github.com/go-stack/stack v1.8.1/go.mod h1:dcoOX6HbPZSZptuspn9bctJ+N/CnF5gGygcUP3XYfe4= github.com/gobwas/httphead v0.0.0-20180130184737-2c6c146eadee/go.mod h1:L0fX3K22YWvt/FAX9NnzrNzcI4wNYi9Yku4O0LKYflo= -github.com/gobwas/httphead v0.1.0 h1:exrUm0f4YX0L7EBwZHuCF4GDp8aJfVeBrlLQrs6NqWU= -github.com/gobwas/httphead v0.1.0/go.mod h1:O/RXo79gxV8G+RqlR/otEwx4Q36zl9rqC5u12GKvMCM= github.com/gobwas/pool v0.2.0/go.mod h1:q8bcK0KcYlCgd9e7WYLm9LpyS+YeLd8JVDW6WezmKEw= -github.com/gobwas/pool v0.2.1 h1:xfeeEhW7pwmX8nuLVlqbzVc7udMDrwetjEv+TZIz1og= -github.com/gobwas/pool v0.2.1/go.mod h1:q8bcK0KcYlCgd9e7WYLm9LpyS+YeLd8JVDW6WezmKEw= github.com/gobwas/ws v1.0.2/go.mod h1:szmBTxLgaFppYjEmNtny/v3w89xOydFnnZMcgRRu/EM= -github.com/gobwas/ws v1.2.1 h1:F2aeBZrm2NDsc7vbovKrWSogd4wvfAxg0FQ89/iqOTk= -github.com/gobwas/ws v1.2.1/go.mod h1:hRKAFb8wOxFROYNsT1bqfWnhX+b5MFeJM9r2ZSwg/KY= -github.com/goccy/go-json v0.10.2 h1:CrxCmQqYDkv1z7lO7Wbh2HN93uovUHgrECaO5ZrCXAU= -github.com/goccy/go-json v0.10.2/go.mod h1:6MelG93GURQebXPDq3khkgXZkazVtN9CRI+MGFi0w8I= github.com/godbus/dbus v0.0.0-20190726142602-4481cbc300e2 h1:ZpnhV/YsD2/4cESfV5+Hoeu/iUR3ruzNvZ+yQfO03a0= github.com/godbus/dbus v0.0.0-20190726142602-4481cbc300e2/go.mod h1:bBOAhwG1umN6/6ZUMtDFBMQR8jRg9O75tm9K00oMsK4= github.com/godbus/dbus/v5 v5.0.4/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA= @@ -631,16 +626,16 @@ github.com/google/pprof v0.0.0-20210226084205-cbba55b83ad5/go.mod h1:kpwsk12EmLe github.com/google/pprof v0.0.0-20210601050228-01bbb1931b22/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= github.com/google/pprof v0.0.0-20210609004039-a478d1d731e9/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= github.com/google/pprof v0.0.0-20210720184732-4bb14d4b1be1/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= -github.com/google/pprof v0.0.0-20230817174616-7a8ec2ada47b h1:h9U78+dx9a4BKdQkBBos92HalKpaGKHrp+3Uo6yTodo= -github.com/google/pprof v0.0.0-20230817174616-7a8ec2ada47b/go.mod h1:czg5+yv1E0ZGTi6S6vVK1mke0fV+FaUhNGcd6VRS9Ik= +github.com/google/pprof v0.0.0-20231023181126-ff6d637d2a7b h1:RMpPgZTSApbPf7xaVel+QkoGPRLFLrwFO89uDUHEGf0= +github.com/google/pprof v0.0.0-20231023181126-ff6d637d2a7b/go.mod h1:czg5+yv1E0ZGTi6S6vVK1mke0fV+FaUhNGcd6VRS9Ik= github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm40UhjYkI= github.com/google/s2a-go v0.1.7 h1:60BLSyTrOV4/haCDW4zb1guZItoSq8foHCXrAnjBo/o= github.com/google/s2a-go v0.1.7/go.mod h1:50CgR4k1jNlWBu4UfS4AcfhVe1r6pdZPygJ3R8F0Qdw= github.com/google/uuid v1.0.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.1.2/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.3.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= -github.com/google/uuid v1.4.0 h1:MtMxsa51/r9yyhkyLsVeVt0B+BGQZzpQiTQ4eHZ8bc4= -github.com/google/uuid v1.4.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/uuid v1.5.0 h1:1p67kYwdtXjb0gL0BPiP1Av9wiZPo5A8z2cWkTZ+eyU= +github.com/google/uuid v1.5.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/googleapis/enterprise-certificate-proxy v0.0.0-20220520183353-fd19c99a87aa/go.mod h1:17drOmN3MwGY7t0e+Ei9b45FFGA3fBs3x36SsCg1hq8= github.com/googleapis/enterprise-certificate-proxy v0.1.0/go.mod h1:17drOmN3MwGY7t0e+Ei9b45FFGA3fBs3x36SsCg1hq8= github.com/googleapis/enterprise-certificate-proxy v0.2.0/go.mod h1:8C0jb7/mgJe/9KK8Lm7X9ctZC2t60YyIpYEI16jx0Qg= @@ -668,8 +663,8 @@ github.com/gorilla/mux v1.8.1 h1:TuBL49tXwgrFYWhqrNgrUNEY92u81SPhu7sTdzQEiWY= github.com/gorilla/mux v1.8.1/go.mod h1:AKf9I4AEqPTmMytcMc0KkNouC66V3BtZ4qD5fmWSiMQ= github.com/gorilla/websocket v0.0.0-20170926233335-4201258b820c/go.mod h1:E7qHFY5m1UJ88s3WnNqhKjPHQ0heANvMoAMk2YaljkQ= github.com/gorilla/websocket v1.4.1/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= -github.com/gorilla/websocket v1.5.0 h1:PPwGk2jz7EePpoHN/+ClbZu8SPxiqlu12wZP/3sWmnc= -github.com/gorilla/websocket v1.5.0/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= +github.com/gorilla/websocket v1.5.1 h1:gmztn0JnHVt9JZquRuzLw3g4wouNVzKL15iLr/zn/QY= +github.com/gorilla/websocket v1.5.1/go.mod h1:x3kM2JMyaluk02fnUJpQuwD2dCS5NDG2ZHL0uE0tcaY= github.com/grpc-ecosystem/go-grpc-middleware v1.0.1-0.20190118093823-f849b5445de4/go.mod h1:FiyG127CGDf3tlThmgyCl78X/SZQqEOJBCDaAfeWzPs= github.com/grpc-ecosystem/go-grpc-middleware v1.2.2/go.mod h1:EaizFBKfUKtMIF5iaDEhniwNedqGo9FuLFzppDr3uwI= github.com/grpc-ecosystem/go-grpc-middleware v1.4.0 h1:UH//fgunKIs4JdUbpDl1VZCDaL56wXCB/5+wF6uHfaI= @@ -694,8 +689,8 @@ github.com/hashicorp/go-cleanhttp v0.5.2 h1:035FKYIWjmULyFRBKPs8TBQoi0x6d9G4xc9n github.com/hashicorp/go-cleanhttp v0.5.2/go.mod h1:kO/YDlP8L1346E6Sodw+PrpBSV4/SoxCXGY6BqNFT48= github.com/hashicorp/go-getter v1.7.3 h1:bN2+Fw9XPFvOCjB0UOevFIMICZ7G2XSQHzfvLUyOM5E= github.com/hashicorp/go-getter v1.7.3/go.mod h1:W7TalhMmbPmsSMdNjD0ZskARur/9GJ17cfHTRtXV744= -github.com/hashicorp/go-hclog v1.5.0 h1:bI2ocEMgcVlz55Oj1xZNBsVi900c7II+fWDyV9o+13c= -github.com/hashicorp/go-hclog v1.5.0/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M= +github.com/hashicorp/go-hclog v1.6.1 h1:pa92nu9bPoAqI7p+uPDCIWGAibUdlCi6TYWJEQQkLf8= +github.com/hashicorp/go-hclog v1.6.1/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M= github.com/hashicorp/go-immutable-radix v1.0.0/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60= github.com/hashicorp/go-immutable-radix v1.3.1 h1:DKHmCUm2hRBK510BaiZlwvpD40f8bJFeZnpfm2KLowc= github.com/hashicorp/go-immutable-radix v1.3.1/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60= @@ -703,8 +698,8 @@ github.com/hashicorp/go-metrics v0.5.3 h1:M5uADWMOGCTUNU1YuC4hfknOeHNaX54LDm4oYS github.com/hashicorp/go-metrics v0.5.3/go.mod h1:KEjodfebIOuBYSAe/bHTm+HChmKSxAOXPBieMLYozDE= github.com/hashicorp/go-msgpack v0.5.3/go.mod h1:ahLV/dePpqEmjfWmKiqvPkv/twdG7iPBM1vqhUKIvfM= github.com/hashicorp/go-multierror v1.0.0/go.mod h1:dHtQlpGsu+cZNNAkkCN/P3hoUDHhCYQXV3UM06sGGrk= -github.com/hashicorp/go-plugin v1.5.2 h1:aWv8eimFqWlsEiMrYZdPYl+FdHaBJSN4AWwGWfT1G2Y= -github.com/hashicorp/go-plugin v1.5.2/go.mod h1:w1sAEES3g3PuV/RzUrgow20W2uErMly84hhD3um1WL4= +github.com/hashicorp/go-plugin v1.6.0 h1:wgd4KxHJTVGGqWBq4QPB1i5BZNEx9BR8+OFmHDmTk8A= +github.com/hashicorp/go-plugin v1.6.0/go.mod h1:lBS5MtSSBZk0SHc66KACcjjlU6WzEVP/8pwz68aMkCI= github.com/hashicorp/go-retryablehttp v0.5.3/go.mod h1:9B5zBasrRhHXnJnui7y6sL7es7NDiJgTc6Er0maI1Xs= github.com/hashicorp/go-rootcerts v1.0.0/go.mod h1:K6zTfqpRlCUIjkwsN4Z+hiSfzSTQa6eBIzfwKfwNnHU= github.com/hashicorp/go-safetemp v1.0.0 h1:2HR189eFNrjHQyENnQMMpCiBAsRxzbTMIgBhEyExpmo= @@ -733,8 +728,8 @@ github.com/hashicorp/yamux v0.1.1 h1:yrQxtgseBDrq9Y652vSRDvsKCJKOUD+GzTS4Y0Y8pvE github.com/hashicorp/yamux v0.1.1/go.mod h1:CtWFDAQgb7dxtzFs4tWbplKIe2jSi3+5vKbgIO0SLnQ= github.com/hdevalence/ed25519consensus v0.1.0 h1:jtBwzzcHuTmFrQN6xQZn6CQEO/V9f7HsjsjeEZ6auqU= github.com/hdevalence/ed25519consensus v0.1.0/go.mod h1:w3BHWjwJbFU29IRHL1Iqkw3sus+7FctEyM4RqDxYNzo= -github.com/holiman/uint256 v1.2.3 h1:K8UWO1HUJpRMXBxbmaY1Y8IAMZC/RsKB+ArEnnK4l5o= -github.com/holiman/uint256 v1.2.3/go.mod h1:SC8Ryt4n+UBbPbIBKaG9zbbDlp4jOru9xFZmPzLUTxw= +github.com/holiman/uint256 v1.2.4 h1:jUc4Nk8fm9jZabQuqr2JzednajVmBpC+oiTiXZJEApU= +github.com/holiman/uint256 v1.2.4/go.mod h1:EOMSn4q6Nyt9P6efbI3bueV4e1b3dGlUCXeiRV4ng7E= github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU= github.com/huandu/go-assert v1.1.5 h1:fjemmA7sSfYHJD7CUqs9qTwwfdNAx7/j2/ZlHXzNB3c= github.com/huandu/go-assert v1.1.5/go.mod h1:yOLvuqZwmcHIC5rIzrBhT7D3Q9c3GFnd0JrPVhn/06U= @@ -745,8 +740,8 @@ github.com/iancoleman/strcase v0.3.0 h1:nTXanmYxhfFAMjZL34Ov6gkzEsSJZ5DbhxWjvSAS github.com/iancoleman/strcase v0.3.0/go.mod h1:iwCmte+B7n89clKwxIoIXy/HfoL7AsD47ZCWhYzw7ho= github.com/ianlancetaylor/demangle v0.0.0-20181102032728-5e5cf60278f6/go.mod h1:aSSvb/t6k1mPoxDqO4vJh6VOCGPwU4O0C2/Eqndh1Sc= github.com/ianlancetaylor/demangle v0.0.0-20200824232613-28f6c0f3b639/go.mod h1:aSSvb/t6k1mPoxDqO4vJh6VOCGPwU4O0C2/Eqndh1Sc= -github.com/icza/dyno v0.0.0-20220812133438-f0b6f8a18845 h1:H+uM0Bv88eur3ZSsd2NGKg3YIiuXxwxtlN7HjE66UTU= -github.com/icza/dyno v0.0.0-20220812133438-f0b6f8a18845/go.mod h1:c1tRKs5Tx7E2+uHGSyyncziFjvGpgv4H2HrqXeUQ/Uk= +github.com/icza/dyno v0.0.0-20230330125955-09f820a8d9c0 h1:nHoRIX8iXob3Y2kdt9KsjyIb7iApSvb3vgsd93xb5Ow= +github.com/icza/dyno v0.0.0-20230330125955-09f820a8d9c0/go.mod h1:c1tRKs5Tx7E2+uHGSyyncziFjvGpgv4H2HrqXeUQ/Uk= github.com/improbable-eng/grpc-web v0.15.0 h1:BN+7z6uNXZ1tQGcNAuaU1YjsLTApzkjt2tzCixLaUPQ= github.com/improbable-eng/grpc-web v0.15.0/go.mod h1:1sy9HKV4Jt9aEs9JSnkWlRJPuPtwNr0l57L4f878wP8= github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8= @@ -771,8 +766,6 @@ github.com/json-iterator/go v1.1.7/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/u github.com/json-iterator/go v1.1.8/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= github.com/json-iterator/go v1.1.9/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= github.com/json-iterator/go v1.1.10/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= -github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= -github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= github.com/jstemmer/go-junit-report v0.0.0-20190106144839-af01ea7f8024/go.mod h1:6v2b51hI/fHJwM22ozAgKL4VKDeJcHhJFhtBdhmNjmU= github.com/jstemmer/go-junit-report v0.9.1/go.mod h1:Brl9GWCQeLvo8nXZwPNNblvFj/XSXhF0NWZEnDohbsk= github.com/jtolds/gls v4.20.0+incompatible/go.mod h1:QJZ7F/aHp+rZTRtaJ1ow/lLfFfVYBRgL+9YlvaHOwJU= @@ -788,8 +781,8 @@ github.com/klauspost/compress v1.12.3/go.mod h1:8dP1Hq4DHOhN9w426knH3Rhby4rFm6D8 github.com/klauspost/compress v1.15.11/go.mod h1:QPwzmACJjUTFsnSHH934V6woptycfrDDJnH7hvFVbGM= github.com/klauspost/compress v1.17.4 h1:Ej5ixsIri7BrIjBkRZLTo6ghwrEtHFk7ijlczPW4fZ4= github.com/klauspost/compress v1.17.4/go.mod h1:/dCuZOvVtNoHsyb+cuJD3itjs3NbnF6KH9zAO4BDxPM= -github.com/klauspost/cpuid/v2 v2.2.5 h1:0E5MSMDEoAulmXNFquVs//DdoomxaoTY1kUhbc/qbZg= -github.com/klauspost/cpuid/v2 v2.2.5/go.mod h1:Lcz8mBdAVJIBVzewtcLocK12l3Y+JytZYpaMropDUws= +github.com/klauspost/cpuid/v2 v2.2.6 h1:ndNyv040zDGIDh8thGkXYjnFtiN02M1PVVF+JE/48xc= +github.com/klauspost/cpuid/v2 v2.2.6/go.mod h1:Lcz8mBdAVJIBVzewtcLocK12l3Y+JytZYpaMropDUws= github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= github.com/konsorten/go-windows-terminal-sequences v1.0.3/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= github.com/kr/logfmt v0.0.0-20140226030751-b84e30acd515/go.mod h1:+0opPa2QZZtGFBFZlji/RkVcI2GknAs/DXo4wKdlNEc= @@ -801,18 +794,16 @@ github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= github.com/leodido/go-urn v1.2.0/go.mod h1:+8+nEpDfqqsY+g338gtMEUOtuK+4dEMhiQEgxpxOKII= -github.com/leodido/go-urn v1.2.4 h1:XlAE/cm/ms7TE/VMVoduSpNBoyc2dOxHs5MZSwAN63Q= -github.com/leodido/go-urn v1.2.4/go.mod h1:7ZrI8mTSeBSHl/UaRyKQW1qZeMgak41ANeCNaVckg+4= -github.com/lib/pq v1.10.7 h1:p7ZhMD+KsSRozJr34udlUrhboJwWAgCg34+/ZZNvZZw= -github.com/lib/pq v1.10.7/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o= +github.com/lib/pq v1.10.9 h1:YXG7RB+JIjhP29X+OtkiDnYaXQwpS4JEWq7dtCCRUEw= +github.com/lib/pq v1.10.9/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o= github.com/libp2p/go-buffer-pool v0.1.0 h1:oK4mSFcQz7cTQIfqbe4MIj9gLW+mnanjyFtc6cdF0Y8= github.com/libp2p/go-buffer-pool v0.1.0/go.mod h1:N+vh8gMqimBzdKkSMVuydVDq+UV5QTWy5HSiZacSbPg= -github.com/libp2p/go-libp2p v0.31.0 h1:LFShhP8F6xthWiBBq3euxbKjZsoRajVEyBS9snfHxYg= -github.com/libp2p/go-libp2p v0.31.0/go.mod h1:W/FEK1c/t04PbRH3fA9i5oucu5YcgrG0JVoBWT1B7Eg= +github.com/libp2p/go-libp2p v0.32.1 h1:wy1J4kZIZxOaej6NveTWCZmHiJ/kY7GoAqXgqNCnPps= +github.com/libp2p/go-libp2p v0.32.1/go.mod h1:hXXC3kXPlBZ1eu8Q2hptGrMB4mZ3048JUoS4EKaHW5c= github.com/lightstep/lightstep-tracer-common/golang/gogo v0.0.0-20190605223551-bc2310a04743/go.mod h1:qklhhLq1aX+mtWk9cPHPzaBjWImj5ULL6C7HFJtXQMM= github.com/lightstep/lightstep-tracer-go v0.18.1/go.mod h1:jlF1pusYV4pidLvZ+XD0UBX0ZE6WURAspgAczcDHrL4= -github.com/linxGnu/grocksdb v1.8.6 h1:O7I6SIGPrypf3f/gmrrLUBQDKfO8uOoYdWf4gLS06tc= -github.com/linxGnu/grocksdb v1.8.6/go.mod h1:xZCIb5Muw+nhbDK4Y5UJuOrin5MceOuiXkVUR7vp4WY= +github.com/linxGnu/grocksdb v1.8.9 h1:/s352A7OI/+tOxeecK21qJyLJ0YHI7J8gN/cXOKzEis= +github.com/linxGnu/grocksdb v1.8.9/go.mod h1:xZCIb5Muw+nhbDK4Y5UJuOrin5MceOuiXkVUR7vp4WY= github.com/lyft/protoc-gen-validate v0.0.13/go.mod h1:XbGvPuh87YZc5TdIa2/I4pLk0QoUACkjt2znoq26NVQ= github.com/magiconair/properties v1.8.0/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ= github.com/magiconair/properties v1.8.7 h1:IeQXZAiQcpL9mgcAe1Nu6cX9LLw6ExEHKjN0VQdvPDY= @@ -865,12 +856,9 @@ github.com/mitchellh/mapstructure v1.5.0/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RR github.com/moby/term v0.0.0-20221205130635-1aeaba878587 h1:HfkjXDfhgVaN5rmueG8cL8KKeFNecRCXFhaJ2qZ5SKA= github.com/moby/term v0.0.0-20221205130635-1aeaba878587/go.mod h1:8FzsFHVUBGZdbDsJw/ot+X+d5HLUbvklYLJ9uGfcI3Y= github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= -github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w8PVh93nsPXa1VrQ6jlwL5oN8l14QlcNfg= github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= github.com/modern-go/reflect2 v0.0.0-20180701023420-4b7aa43c6742/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3RllmbCylyMrvgv0= github.com/modern-go/reflect2 v1.0.1/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3RllmbCylyMrvgv0= -github.com/modern-go/reflect2 v1.0.2 h1:xBagoLtFs94CBntxluKeaWgTMpvLxC4ur3nMaC9Gz0M= -github.com/modern-go/reflect2 v1.0.2/go.mod h1:yWuevngMOJpCy52FWWMvUC8ws7m/LJsjYzDa0/r8luk= github.com/morikuni/aec v1.0.0 h1:nP9CBfwrvYnBRgY6qfDQkygYDmYwOilePFkwzv4dU8A= github.com/morikuni/aec v1.0.0/go.mod h1:BbKIizmSmc5MMPqRYbxO4ZU0S0+P200+tUnFx7PXmsc= github.com/mr-tron/base58 v1.2.0 h1:T/HDJBh4ZCPbU39/+c3rRvE0uKBQlU27+QI8LJ4t64o= @@ -881,8 +869,8 @@ github.com/multiformats/go-base32 v0.1.0 h1:pVx9xoSPqEIQG8o+UbAe7DNi51oej1NtK+aG github.com/multiformats/go-base32 v0.1.0/go.mod h1:Kj3tFY6zNr+ABYMqeUNeGvkIC/UYgtWibDcT0rExnbI= github.com/multiformats/go-base36 v0.2.0 h1:lFsAbNOGeKtuKozrtBsAkSVhv1p9D0/qedU9rQyccr0= github.com/multiformats/go-base36 v0.2.0/go.mod h1:qvnKE++v+2MWCfePClUEjE78Z7P2a1UV0xHgWc0hkp4= -github.com/multiformats/go-multiaddr v0.11.0 h1:XqGyJ8ufbCE0HmTDwx2kPdsrQ36AGPZNZX6s6xfJH10= -github.com/multiformats/go-multiaddr v0.11.0/go.mod h1:gWUm0QLR4thQ6+ZF6SXUw8YjtwQSPapICM+NmCkxHSM= +github.com/multiformats/go-multiaddr v0.12.0 h1:1QlibTFkoXJuDjjYsMHhE73TnzJQl8FSWatk/0gxGzE= +github.com/multiformats/go-multiaddr v0.12.0/go.mod h1:WmZXgObOQOYp9r3cslLlppkrz1FYSHmE834dfz/lWu8= github.com/multiformats/go-multibase v0.2.0 h1:isdYCVLvksgWlMW9OZRYJEa9pZETFivncJHmHnnd87g= github.com/multiformats/go-multibase v0.2.0/go.mod h1:bFBZX4lKCA/2lyOFSAoKH5SS6oPyjtnzK/XTFDPkNuk= github.com/multiformats/go-multicodec v0.9.0 h1:pb/dlPnzee/Sxv/j4PmkDRxCOi3hXTz3IbPKOXWJkmg= @@ -917,8 +905,8 @@ github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+W github.com/onsi/ginkgo v1.7.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/ginkgo v1.12.1/go.mod h1:zj2OWP4+oCPe1qIXoGWkgMRwljMUYCdkwsT2108oapk= github.com/onsi/ginkgo v1.14.0/go.mod h1:iSB4RoI2tjJc9BBv4NKIKWKya62Rps+oPG/Lv9klQyY= -github.com/onsi/ginkgo v1.16.5 h1:8xi0RTUf59SOSfEtZMvwTvXYMzG4gV23XVHOZiXNtnE= -github.com/onsi/ginkgo v1.16.5/go.mod h1:+E8gABHa3K6zRBolWtd+ROzc/U5bkGt0FwiG042wbpU= +github.com/onsi/ginkgo v1.16.4 h1:29JGrr5oVBm5ulCWet69zQkzWipVXIol6ygQUe/EzNc= +github.com/onsi/ginkgo v1.16.4/go.mod h1:dX+/inL/fNMqNlz0e9LfyB9TswhZpCVdJM/Z6Vvnwo0= github.com/onsi/gomega v1.4.3/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY= github.com/onsi/gomega v1.7.1/go.mod h1:XdKZgCCFLUoM/7CFJVPcG8C1xQ1AJ0vpAezJrB7JYyY= github.com/onsi/gomega v1.10.1/go.mod h1:iN09h71vgCQne3DLsj+A5owkum+a2tYe+TOCB1ybHNo= @@ -927,8 +915,8 @@ github.com/onsi/gomega v1.27.8/go.mod h1:2J8vzI/s+2shY9XHRApDkdgPo1TKT7P2u6fXeJK github.com/op/go-logging v0.0.0-20160315200505-970db520ece7/go.mod h1:HzydrMdWErDVzsI23lYNej1Htcns9BCg93Dk0bBINWk= github.com/opencontainers/go-digest v1.0.0 h1:apOUWs51W5PlhuyGyz9FCeeBIOUDA/6nW8Oi/yOhh5U= github.com/opencontainers/go-digest v1.0.0/go.mod h1:0JzlMkj0TRzQZfJkVvzbP0HBR3IKzErnv2BNG4W4MAM= -github.com/opencontainers/image-spec v1.1.0-rc2 h1:2zx/Stx4Wc5pIPDvIxHXvXtQFW/7XWJGmnM7r3wg034= -github.com/opencontainers/image-spec v1.1.0-rc2/go.mod h1:3OVijpioIKYWTqjiG0zfF6wvoJ4fAXGbjdZuI2NgsRQ= +github.com/opencontainers/image-spec v1.1.0-rc5 h1:Ygwkfw9bpDvs+c9E34SdgGOj41dX/cbdlwvlWt0pnFI= +github.com/opencontainers/image-spec v1.1.0-rc5/go.mod h1:X4pATf0uXsnn3g5aiGIsVnJBR4mxhKzfwmvK/B2NTm8= github.com/opencontainers/runc v1.1.3 h1:vIXrkId+0/J2Ymu2m7VjGvbSlAId9XNRPhn2p4b+d8w= github.com/opencontainers/runc v1.1.3/go.mod h1:1J5XiS+vdZ3wCyZybsuxXZWGrgSr8fFJHLXuG2PsnNg= github.com/opentracing-contrib/go-observer v0.0.0-20170622124052-a52f23424492/go.mod h1:Ngi6UdF0k5OKD5t5wlmGhe/EDKPoUM3BXZSSfIuJbis= @@ -949,12 +937,12 @@ github.com/pborman/uuid v1.2.0/go.mod h1:X/NO0urCmaxf9VXbdlT7C2Yzkj2IKimNn4k+gtP github.com/pelletier/go-toml v1.2.0/go.mod h1:5z9KED0ma1S8pY6P1sdut58dfprrGBbd/94hg7ilaic= github.com/pelletier/go-toml v1.9.5 h1:4yBQzkHv+7BHq2PQUZF3Mx0IYxG7LsP222s7Agd3ve8= github.com/pelletier/go-toml v1.9.5/go.mod h1:u1nR/EPcESfeI/szUZKdtJ0xRNbUoANCkoOuaOx1Y+c= -github.com/pelletier/go-toml/v2 v2.1.0 h1:FnwAJ4oYMvbT/34k9zzHuZNrhlz48GB3/s6at6/MHO4= -github.com/pelletier/go-toml/v2 v2.1.0/go.mod h1:tJU2Z3ZkXwnxa4DPO899bsyIoywizdUvyaeZurnPPDc= +github.com/pelletier/go-toml/v2 v2.1.1 h1:LWAJwfNvjQZCFIDKWYQaM62NcYeYViCmWIwmOStowAI= +github.com/pelletier/go-toml/v2 v2.1.1/go.mod h1:tJU2Z3ZkXwnxa4DPO899bsyIoywizdUvyaeZurnPPDc= github.com/performancecopilot/speed v3.0.0+incompatible/go.mod h1:/CLtqpZ5gBg1M9iaPbIdPPGyKcA8hKdoy6hAWba7Yac= github.com/petermattis/goid v0.0.0-20180202154549-b0b1615b78e5/go.mod h1:jvVRKCrJTQWu0XVbaOlby/2lO20uSCHEMzzplHXte1o= -github.com/petermattis/goid v0.0.0-20230904192822-1876fd5063bc h1:8bQZVK1X6BJR/6nYUPxQEP+ReTsceJTKizeuwjWOPUA= -github.com/petermattis/goid v0.0.0-20230904192822-1876fd5063bc/go.mod h1:pxMtw7cyUw6B2bRH0ZBANSPg+AoSud1I1iyJHI69jH4= +github.com/petermattis/goid v0.0.0-20231207134359-e60b3f734c67 h1:jik8PHtAIsPlCRJjJzl4udgEf7hawInF9texMeO2jrU= +github.com/petermattis/goid v0.0.0-20231207134359-e60b3f734c67/go.mod h1:pxMtw7cyUw6B2bRH0ZBANSPg+AoSud1I1iyJHI69jH4= github.com/pierrec/lz4 v1.0.2-0.20190131084431-473cd7ce01a1/go.mod h1:3/3N9NVKO0jef7pBehbT1qWhCMrIgbYNnFAZCqQ5LRc= github.com/pierrec/lz4 v2.0.5+incompatible/go.mod h1:pdkljMzZIN41W+lC3N2tnIh5sFi+IEE17M5jbnwPHcY= github.com/pierrec/xxHash v0.1.5 h1:n/jBpwTHiER4xYvK3/CdPVnLDPchj8eTJFFLUb4QHBo= @@ -1017,8 +1005,8 @@ github.com/rogpeppe/go-internal v1.9.0/go.mod h1:WtVeX8xhTBvf0smdhujwtBcq4Qrzq/f github.com/rogpeppe/go-internal v1.11.0 h1:cWPaGQEPrBb5/AsnsZesgZZ9yb1OQ+GOISoDNXVBh4M= github.com/rogpeppe/go-internal v1.11.0/go.mod h1:ddIwULY96R17DhadqLgMfk9H9tvdUzkipdSkR5nkCZA= github.com/rs/cors v1.7.0/go.mod h1:gFx+x8UowdsKA9AchylcLynDq+nNFfI8FkUZdN/jGCU= -github.com/rs/cors v1.8.3 h1:O+qNyWn7Z+F9M0ILBHgMVPuB1xTOucVd5gtaYyXBpRo= -github.com/rs/cors v1.8.3/go.mod h1:XyqrcTp5zjWr1wsJ8PIRZssZ8b/WMcMf71DJnit4EMU= +github.com/rs/cors v1.10.1 h1:L0uuZVXIKlI1SShY2nhFfo44TYvDPQ1w4oFkUJNfhyo= +github.com/rs/cors v1.10.1/go.mod h1:XyqrcTp5zjWr1wsJ8PIRZssZ8b/WMcMf71DJnit4EMU= github.com/rs/xid v1.5.0/go.mod h1:trrq9SKmegXys3aeAKXMUTdJsYXVwGY3RLcfgqegfbg= github.com/rs/zerolog v1.31.0 h1:FcTR3NnLWW+NnTwwhFWiJSZr4ECLpqCm6QsEnyvbV4A= github.com/rs/zerolog v1.31.0/go.mod h1:/7mN4D5sKwJLZQ2b/znpjC3/GQWY/xaDXUM0kKWRHss= @@ -1070,8 +1058,8 @@ github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An github.com/spf13/viper v1.3.2/go.mod h1:ZiWeW+zYFKm7srdB9IoDzzZXaJaI5eL9QjNiN/DMA2s= github.com/spf13/viper v1.18.2 h1:LUXCnvUvSM6FXAsj6nnfc8Q2tp1dIgUfY9Kc8GsSOiQ= github.com/spf13/viper v1.18.2/go.mod h1:EKmWIqdnk5lOcmR72yw6hS+8OPYcwD0jteitLMVB+yk= -github.com/strangelove-ventures/interchaintest/v8 v8.0.0 h1:z6hz23NJEhRJxZUH1vuDNTVscRwnUii+K4En9lfyndc= -github.com/strangelove-ventures/interchaintest/v8 v8.0.0/go.mod h1:0LEZ1dXKlAYOm18X6s8AC4y5e6uAjJ0L69A6JpUkjDc= +github.com/strangelove-ventures/interchaintest/v8 v8.0.1-0.20231206154526-2f014d308bea h1:02x9Eh/BrvstT3LiobBVsHIi8NGN7owFq1WmVTerC1g= +github.com/strangelove-ventures/interchaintest/v8 v8.0.1-0.20231206154526-2f014d308bea/go.mod h1:jRhLAQ+HuxZf7yqp5C1ZksMsT0FOpmHtExdcbA6aOi8= github.com/streadway/amqp v0.0.0-20190404075320-75d898a42a94/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw= github.com/streadway/amqp v0.0.0-20190827072141-edfb9018d271/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw= github.com/streadway/handy v0.0.0-20190108123426-d5acb3125c2a/go.mod h1:qNTQ5P5JnDBl6z3cMAg/SywNDC5ABu5ApDIw6lUbRmI= @@ -1101,22 +1089,19 @@ github.com/tendermint/go-amino v0.16.0 h1:GyhmgQKvqF82e2oZeuMSp9JTN0N09emoSZlb2l github.com/tendermint/go-amino v0.16.0/go.mod h1:TQU0M1i/ImAo+tYpZi73AU3V/dKeCoMC9Sphe2ZwGME= github.com/tidwall/btree v1.7.0 h1:L1fkJH/AuEh5zBnnBbmTwQ5Lt+bRJ5A8EWecslvo9iI= github.com/tidwall/btree v1.7.0/go.mod h1:twD9XRA5jj9VUQGELzDO4HPQTNJsoWWfYEL+EUQ2cKY= -github.com/tklauser/go-sysconf v0.3.11 h1:89WgdJhk5SNwJfu+GKyYveZ4IaJ7xAkecBo+KdJV0CM= -github.com/tklauser/go-sysconf v0.3.11/go.mod h1:GqXfhXY3kiPa0nAXPDIQIWzJbMCB7AmcWpGR8lSZfqI= -github.com/tklauser/numcpus v0.4.0 h1:E53Dm1HjH1/R2/aoCtXtPgzmElmn51aOkhCFSuZq//o= -github.com/tklauser/numcpus v0.4.0/go.mod h1:1+UI3pD8NW14VMwdgJNJ1ESk2UnwhAnz5hMwiKKqXCQ= +github.com/tklauser/go-sysconf v0.3.12 h1:0QaGUFOdQaIVdPgfITYzaTegZvdCjmYO52cSFAEVmqU= +github.com/tklauser/go-sysconf v0.3.12/go.mod h1:Ho14jnntGE1fpdOqQEEaiKRpvIavV0hSfmBq8nJbHYI= +github.com/tklauser/numcpus v0.6.1 h1:ng9scYS7az0Bk4OZLvrNXNSAO2Pxr1XXRAPyjhIx+Fk= +github.com/tklauser/numcpus v0.6.1/go.mod h1:1XfjsgE2zo8GVw7POkMbHENHzVg3GzmoZ9fESEdAacY= github.com/tmc/grpc-websocket-proxy v0.0.0-20170815181823-89b8d40f7ca8/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U= github.com/tv42/httpunix v0.0.0-20150427012821-b75d8614f926/go.mod h1:9ESjWnEqriFuLhtthL60Sar/7RFoluCcXsuvEwTV5KM= github.com/tyler-smith/go-bip32 v1.0.0 h1:sDR9juArbUgX+bO/iblgZnMPeWY1KZMUC2AFUJdv5KE= github.com/tyler-smith/go-bip32 v1.0.0/go.mod h1:onot+eHknzV4BVPwrzqY5OoVpyCvnwD7lMawL5aQupE= github.com/tyler-smith/go-bip39 v1.1.0 h1:5eUemwrMargf3BSLRRCalXT93Ns6pQJIjYQN2nyfOP8= github.com/tyler-smith/go-bip39 v1.1.0/go.mod h1:gUYDtqQw1JS3ZJ8UWVcGTGqqr6YIN3CWg+kkNaLt55U= -github.com/ugorji/go v1.1.7 h1:/68gy2h+1mWMrwZFeD1kQialdSzAb432dtpeJ42ovdo= github.com/ugorji/go v1.1.7/go.mod h1:kZn38zHttfInRq0xu/PH0az30d+z6vm202qpg1oXVMw= github.com/ugorji/go/codec v0.0.0-20181204163529-d75b2dcb6bc8/go.mod h1:VFNgLljTbGfSG7qAOspJ7OScBnGdDN/yBr0sguwnwf0= github.com/ugorji/go/codec v1.1.7/go.mod h1:Ax+UKWsSmolVDwsd+7N3ZtXu+yMGCf907BLYF3GoBXY= -github.com/ugorji/go/codec v1.2.11 h1:BMaWp1Bb6fHwEtbplGBGJ498wD+LKlNSl25MjdZY4dU= -github.com/ugorji/go/codec v1.2.11/go.mod h1:UNopzCgEMSXjBc6AOMqYvWC1ktqTAfzJZUZgYf6w6lg= github.com/ulikunitz/xz v0.5.10/go.mod h1:nbz6k7qbPmH4IRqmfOplQw/tblSgqTqBwxkY0oWt/14= github.com/ulikunitz/xz v0.5.11 h1:kpFauv27b6ynzBNT/Xy+1k+fK4WswhN/6PN5WhFAGw8= github.com/ulikunitz/xz v0.5.11/go.mod h1:nbz6k7qbPmH4IRqmfOplQw/tblSgqTqBwxkY0oWt/14= @@ -1149,6 +1134,18 @@ go.opencensus.io v0.22.5/go.mod h1:5pWMHQbX5EPX2/62yrJeAkowc+lfs/XD7Uxpq3pI6kk= go.opencensus.io v0.23.0/go.mod h1:XItmlyltB5F7CS4xOC1DcqMoFqwtC6OG2xF7mCv7P7E= go.opencensus.io v0.24.0 h1:y73uSU6J157QMP2kn2r30vwW1A2W2WFwSCGnAVxeaD0= go.opencensus.io v0.24.0/go.mod h1:vNK8G9p7aAivkbmorf4v+7Hgx+Zs0yY+0fOtgBfjQKo= +go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.46.1 h1:SpGay3w+nEwMpfVnbqOLH5gY52/foP8RE8UzTZ1pdSE= +go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.46.1/go.mod h1:4UoMYEZOC0yN/sPGH76KPkkU7zgiEWYWL9vwmbnTJPE= +go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.46.1 h1:aFJWCqJMNjENlcleuuOkGAPH82y0yULBScfXcIEdS24= +go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.46.1/go.mod h1:sEGXWArGqc3tVa+ekntsN65DmVbVeW+7lTKTjZF3/Fo= +go.opentelemetry.io/otel v1.21.0 h1:hzLeKBZEL7Okw2mGzZ0cc4k/A7Fta0uoPgaJCr8fsFc= +go.opentelemetry.io/otel v1.21.0/go.mod h1:QZzNPQPm1zLX4gZK4cMi+71eaorMSGT3A4znnUvNNEo= +go.opentelemetry.io/otel/metric v1.21.0 h1:tlYWfeo+Bocx5kLEloTjbcDwBuELRrIFxwdQ36PlJu4= +go.opentelemetry.io/otel/metric v1.21.0/go.mod h1:o1p3CA8nNHW8j5yuQLdc1eeqEaPfzug24uvsyIEJRWM= +go.opentelemetry.io/otel/sdk v1.19.0 h1:6USY6zH+L8uMH8L3t1enZPR3WFEmSTADlqldyHtJi3o= +go.opentelemetry.io/otel/sdk v1.19.0/go.mod h1:NedEbbS4w3C6zElbLdPJKOpJQOrGUJ+GfzpjUvI0v1A= +go.opentelemetry.io/otel/trace v1.21.0 h1:WD9i5gzvoUPuXIXH24ZNBudiarZDKuekPqi/E8fpfLc= +go.opentelemetry.io/otel/trace v1.21.0/go.mod h1:LGbsEB0f9LGjN+OZaQQ26sohbOmiMR+BaslueVtS/qQ= go.opentelemetry.io/proto/otlp v0.7.0/go.mod h1:PqfVotwruBrMGOCsRd/89rSnXhoiJIqeYNgFYFoEGnI= go.uber.org/atomic v1.3.2/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= go.uber.org/atomic v1.4.0/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= @@ -1194,8 +1191,8 @@ golang.org/x/exp v0.0.0-20200119233911-0405dc783f0a/go.mod h1:2RIsYlXP63K8oxa1u0 golang.org/x/exp v0.0.0-20200207192155-f17229e696bd/go.mod h1:J/WKrq2StrnmMY6+EHIKF9dgMWnmCNThgcyBT1FY9mM= golang.org/x/exp v0.0.0-20200224162631-6cc2880d07d6/go.mod h1:3jZMyOhIsHpP37uCMkUooju7aAi5cS1Q23tOzKc+0MU= golang.org/x/exp v0.0.0-20200331195152-e8c3332aa8e5/go.mod h1:4M0jN8W1tt0AVLNr8HDosyJCDCDuyL9N9+3m7wDWgKw= -golang.org/x/exp v0.0.0-20231006140011-7918f672742d h1:jtJma62tbqLibJ5sFQz8bKtEM8rJBtfilJ2qTU199MI= -golang.org/x/exp v0.0.0-20231006140011-7918f672742d/go.mod h1:ldy0pHrwJyGW56pPQzzkH36rKxoZW1tw7ZJpeKx+hdo= +golang.org/x/exp v0.0.0-20231206192017-f3f8817b8deb h1:c0vyKkb6yr3KR7jEfJaOSv4lG7xPkbN6r52aJz1d8a8= +golang.org/x/exp v0.0.0-20231206192017-f3f8817b8deb/go.mod h1:iRJReGqOEeBhDZGkGbynYwcHlctCvnjTYIamk7uXpHI= golang.org/x/image v0.0.0-20190227222117-0694c2d4d067/go.mod h1:kZ7UVZpmo3dzQBMxlp+ypCbDeSB+sBbTgSJuh5dn5js= golang.org/x/image v0.0.0-20190802002840-cff245a6509b/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0= golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE= @@ -1397,7 +1394,6 @@ golang.org/x/sys v0.0.0-20210616094352-59db8d763f22/go.mod h1:oPkhp1MJrh7nUepCBc golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210806184541-e5e7981a1069/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210809222454-d867a43fc93e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20210819135213-f52c844e1c1c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210823070655-63515b42dcdf/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210908233432-aa78b53d3365/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= @@ -1512,8 +1508,8 @@ golang.org/x/tools v0.1.3/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk= golang.org/x/tools v0.1.4/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk= golang.org/x/tools v0.1.5/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk= golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc= -golang.org/x/tools v0.14.0 h1:jvNa2pY0M4r62jkRQ6RwEZZyPcymeL9XZMLBbV7U2nc= -golang.org/x/tools v0.14.0/go.mod h1:uYBEerGOWcJyEORxN+Ek8+TT266gXkNlHdJBwexUsBg= +golang.org/x/tools v0.16.0 h1:GO788SKMRunPIBCXiQyo2AaexLstOrVhuAL5YwsckQM= +golang.org/x/tools v0.16.0/go.mod h1:kYVVN6I1mBNoB1OX+noeBjbRk4IUEPa7JJ+TJMEooJ0= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= @@ -1521,8 +1517,9 @@ golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8T golang.org/x/xerrors v0.0.0-20220411194840-2f41105eb62f/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20220517211312-f3a8303e98df/go.mod h1:K8+ghG5WaK9qNqU5K3HdILfMLy1f3aNYFI/wnl100a8= golang.org/x/xerrors v0.0.0-20220609144429-65e65417b02f/go.mod h1:K8+ghG5WaK9qNqU5K3HdILfMLy1f3aNYFI/wnl100a8= -golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2 h1:H2TDz8ibqkAF6YGhCdN3jS9O0/s90v0rJh3X/OLHEUk= golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2/go.mod h1:K8+ghG5WaK9qNqU5K3HdILfMLy1f3aNYFI/wnl100a8= +golang.org/x/xerrors v0.0.0-20231012003039-104605ab7028 h1:+cNy6SZtPcJQH3LJVLOSmiC7MMxXNOb3PU/VUEz+EhU= +golang.org/x/xerrors v0.0.0-20231012003039-104605ab7028/go.mod h1:NDW/Ps6MPRej6fsCIbMTohpP40sJ/P/vI1MoTEGwX90= google.golang.org/api v0.3.1/go.mod h1:6wY9I6uQWHQ8EM57III9mq/AjF+i8G65rmVagqKMtkk= google.golang.org/api v0.4.0/go.mod h1:8k5glujaEP+g9n7WNsDg8QP6cUVNI86fCNMcbazEtwE= google.golang.org/api v0.7.0/go.mod h1:WtwebWUNSVBH/HAw79HIFXZNqEvBhG+Ra+ax0hx3E3M= @@ -1572,8 +1569,8 @@ google.golang.org/api v0.96.0/go.mod h1:w7wJQLTM+wvQpNf5JyEcBoxK0RH7EDrh/L4qfsuJ google.golang.org/api v0.97.0/go.mod h1:w7wJQLTM+wvQpNf5JyEcBoxK0RH7EDrh/L4qfsuJ13s= google.golang.org/api v0.98.0/go.mod h1:w7wJQLTM+wvQpNf5JyEcBoxK0RH7EDrh/L4qfsuJ13s= google.golang.org/api v0.100.0/go.mod h1:ZE3Z2+ZOr87Rx7dqFsdRQkRBk36kDtp/h+QpHbB7a70= -google.golang.org/api v0.153.0 h1:N1AwGhielyKFaUqH07/ZSIQR3uNPcV7NVw0vj+j4iR4= -google.golang.org/api v0.153.0/go.mod h1:3qNJX5eOmhiWYc67jRA/3GsDw97UFb5ivv7Y2PrriAY= +google.golang.org/api v0.154.0 h1:X7QkVKZBskztmpPKWQXgjJRPA2dJYrL6r+sYPRLj050= +google.golang.org/api v0.154.0/go.mod h1:qhSMkM85hgqiokIYsrRyKxrjfBeIhgl4Z2JmeRkYylc= google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= google.golang.org/appengine v1.2.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= @@ -1691,12 +1688,12 @@ google.golang.org/genproto v0.0.0-20221010155953-15ba04fc1c0e/go.mod h1:3526vdqw google.golang.org/genproto v0.0.0-20221014173430-6e2ab493f96b/go.mod h1:1vXfmgAz9N9Jx0QA82PqRVauvCz1SGSz739p0f183jM= google.golang.org/genproto v0.0.0-20221014213838-99cd37c6964a/go.mod h1:1vXfmgAz9N9Jx0QA82PqRVauvCz1SGSz739p0f183jM= google.golang.org/genproto v0.0.0-20221025140454-527a21cfbd71/go.mod h1:9qHF0xnpdSfF6knlcsnpzUu5y+rpwgbvsyGAZPBMg4s= -google.golang.org/genproto v0.0.0-20231120223509-83a465c0220f h1:Vn+VyHU5guc9KjB5KrjI2q0wCOWEOIh0OEsleqakHJg= -google.golang.org/genproto v0.0.0-20231120223509-83a465c0220f/go.mod h1:nWSwAFPb+qfNJXsoeO3Io7zf4tMSfN8EA8RlDA04GhY= -google.golang.org/genproto/googleapis/api v0.0.0-20231106174013-bbf56f31fb17 h1:JpwMPBpFN3uKhdaekDpiNlImDdkUAyiJ6ez/uxGaUSo= -google.golang.org/genproto/googleapis/api v0.0.0-20231106174013-bbf56f31fb17/go.mod h1:0xJLfVdJqpAPl8tDg1ujOCGzx6LFLttXT5NhllGOXY4= -google.golang.org/genproto/googleapis/rpc v0.0.0-20231211222908-989df2bf70f3 h1:kzJAXnzZoFbe5bhZd4zjUuHos/I31yH4thfMb/13oVY= -google.golang.org/genproto/googleapis/rpc v0.0.0-20231211222908-989df2bf70f3/go.mod h1:eJVxU6o+4G1PSczBr85xmyvSNYAKvAYgkub40YGomFM= +google.golang.org/genproto v0.0.0-20231212172506-995d672761c0 h1:YJ5pD9rF8o9Qtta0Cmy9rdBwkSjrTCT6XTiUQVOtIos= +google.golang.org/genproto v0.0.0-20231212172506-995d672761c0/go.mod h1:l/k7rMz0vFTBPy+tFSGvXEd3z+BcoG1k7EHbqm+YBsY= +google.golang.org/genproto/googleapis/api v0.0.0-20231212172506-995d672761c0 h1:s1w3X6gQxwrLEpxnLd/qXTVLgQE2yXwaOaoa6IlY/+o= +google.golang.org/genproto/googleapis/api v0.0.0-20231212172506-995d672761c0/go.mod h1:CAny0tYF+0/9rmDB9fahA9YLzX3+AEVl1qXbv5hhj6c= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231212172506-995d672761c0 h1:/jFB8jK5R3Sq3i/lmeZO0cATSzFfZaJq1J2Euan3XKU= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231212172506-995d672761c0/go.mod h1:FUoWkonphQm3RhTS+kOEhF8h0iDpm4tdXolVCeZ9KKA= google.golang.org/grpc v1.17.0/go.mod h1:6QZJwpn2B+Zp71q/5VxRsJ6NXXVCE5NRUHRo+f3cWCs= google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= google.golang.org/grpc v1.20.0/go.mod h1:chYK+tFQF0nDUGJgXMSgLCQk3phJEuONr2DCgLDdAQM= @@ -1806,18 +1803,18 @@ launchpad.net/gocheck v0.0.0-20140225173054-000000000087 h1:Izowp2XBH6Ya6rv+hqbc launchpad.net/gocheck v0.0.0-20140225173054-000000000087/go.mod h1:hj7XX3B/0A+80Vse0e+BUHsHMTEhd0O4cpUHr/e/BUM= lukechampine.com/blake3 v1.2.1 h1:YuqqRuaqsGV71BV/nm9xlI0MKUv4QC54jQnBChWbGnI= lukechampine.com/blake3 v1.2.1/go.mod h1:0OFRp7fBtAylGVCO40o87sbupkyIGgbpv1+M1k1LM6k= -lukechampine.com/uint128 v1.2.0 h1:mBi/5l91vocEN8otkC5bDLhi2KdCticRiwbdB0O+rjI= -lukechampine.com/uint128 v1.2.0/go.mod h1:c4eWIwlEGaxC/+H1VguhU4PHXNWDCDMUlWdIWl2j1gk= -modernc.org/cc/v3 v3.40.0 h1:P3g79IUS/93SYhtoeaHW+kRCIrYaxJ27MFPv+7kaTOw= -modernc.org/cc/v3 v3.40.0/go.mod h1:/bTg4dnWkSXowUO6ssQKnOV0yMVxDYNIsIrzqTFDGH0= -modernc.org/ccgo/v3 v3.16.13 h1:Mkgdzl46i5F/CNR/Kj80Ri59hC8TKAhZrYSaqvkwzUw= -modernc.org/ccgo/v3 v3.16.13/go.mod h1:2Quk+5YgpImhPjv2Qsob1DnZ/4som1lJTodubIcoUkY= +lukechampine.com/uint128 v1.3.0 h1:cDdUVfRwDUDovz610ABgFD17nXD4/uDgVHl2sC3+sbo= +lukechampine.com/uint128 v1.3.0/go.mod h1:c4eWIwlEGaxC/+H1VguhU4PHXNWDCDMUlWdIWl2j1gk= +modernc.org/cc/v3 v3.41.0 h1:QoR1Sn3YWlmA1T4vLaKZfawdVtSiGx8H+cEojbC7v1Q= +modernc.org/cc/v3 v3.41.0/go.mod h1:Ni4zjJYJ04CDOhG7dn640WGfwBzfE0ecX8TyMB0Fv0Y= +modernc.org/ccgo/v3 v3.16.15 h1:KbDR3ZAVU+wiLyMESPtbtE/Add4elztFyfsWoNTgxS0= +modernc.org/ccgo/v3 v3.16.15/go.mod h1:yT7B+/E2m43tmMOT51GMoM98/MtHIcQQSleGnddkUNI= modernc.org/ccorpus v1.11.6 h1:J16RXiiqiCgua6+ZvQot4yUuUy8zxgqbqEEUuGPlISk= modernc.org/ccorpus v1.11.6/go.mod h1:2gEUTrWqdpH2pXsmTM1ZkjeSrUWDpjMu2T6m29L/ErQ= modernc.org/httpfs v1.0.6 h1:AAgIpFZRXuYnkjftxTAZwMIiwEqAfk8aVB2/oA6nAeM= modernc.org/httpfs v1.0.6/go.mod h1:7dosgurJGp0sPaRanU53W4xZYKh14wfzX420oZADeHM= -modernc.org/libc v1.29.0 h1:tTFRFq69YKCF2QyGNuRUQxKBm1uZZLubf6Cjh/pVHXs= -modernc.org/libc v1.29.0/go.mod h1:DaG/4Q3LRRdqpiLyP0C2m1B8ZMGkQ+cCgOIjEtQlYhQ= +modernc.org/libc v1.37.1 h1:Wi3qhejztgB3hOYQGMc8NwePETHAWXmlU+GQnBNTrw8= +modernc.org/libc v1.37.1/go.mod h1:YAXkAZ8ktnkCKaN9sw/UDeUVkGYJ/YquGO4FTi5nmHE= modernc.org/mathutil v1.6.0 h1:fRe9+AmYlaej+64JsEEhoWuAYBkOtQiMEU7n/XgfYi4= modernc.org/mathutil v1.6.0/go.mod h1:Ui5Q9q1TR2gFm0AQRqQUaBWFLAhQpCwNcuhBOSedWPo= modernc.org/memory v1.7.2 h1:Klh90S215mmH8c9gO98QxQFsY+W451E8AnzjoE2ee1E= @@ -1826,17 +1823,17 @@ modernc.org/opt v0.1.3 h1:3XOZf2yznlhC+ibLltsDGzABUGVx8J6pnFMS3E4dcq4= modernc.org/opt v0.1.3/go.mod h1:WdSiB5evDcignE70guQKxYUl14mgWtbClRi5wmkkTX0= modernc.org/sqlite v1.27.0 h1:MpKAHoyYB7xqcwnUwkuD+npwEa0fojF0B5QRbN+auJ8= modernc.org/sqlite v1.27.0/go.mod h1:Qxpazz0zH8Z1xCFyi5GSL3FzbtZ3fvbjmywNogldEW0= -modernc.org/strutil v1.1.3 h1:fNMm+oJklMGYfU9Ylcywl0CO5O6nTfaowNsh2wpPjzY= -modernc.org/strutil v1.1.3/go.mod h1:MEHNA7PdEnEwLvspRMtWTNnp2nnyvMfkimT1NKNAGbw= +modernc.org/strutil v1.2.0 h1:agBi9dp1I+eOnxXeiZawM8F4LawKv4NzGWSaLfyeNZA= +modernc.org/strutil v1.2.0/go.mod h1:/mdcBmfOibveCTBxUl5B5l6W+TTH1FXPLHZE6bTosX0= modernc.org/tcl v1.15.2 h1:C4ybAYCGJw968e+Me18oW55kD/FexcHbqH2xak1ROSY= modernc.org/tcl v1.15.2/go.mod h1:3+k/ZaEbKrC8ePv8zJWPtBSW0V7Gg9g8rkmhI1Kfs3c= -modernc.org/token v1.0.1 h1:A3qvTqOwexpfZZeyI0FeGPDlSWX5pjZu9hF4lU+EKWg= -modernc.org/token v1.0.1/go.mod h1:UGzOrNV1mAFSEB63lOFHIpNRUVMvYTc6yu1SMY/XTDM= +modernc.org/token v1.1.0 h1:Xl7Ap9dKaEs5kLoOQeQmPWevfnk/DM5qcLcYlA8ys6Y= +modernc.org/token v1.1.0/go.mod h1:UGzOrNV1mAFSEB63lOFHIpNRUVMvYTc6yu1SMY/XTDM= modernc.org/z v1.7.3 h1:zDJf6iHjrnB+WRD88stbXokugjyc0/pB91ri1gO6LZY= modernc.org/z v1.7.3/go.mod h1:Ipv4tsdxZRbQyLq9Q1M6gdbkxYzdlrciF2Hi/lS7nWE= nhooyr.io/websocket v1.8.6/go.mod h1:B70DZP8IakI65RVQ51MsWP/8jndNma26DVA/nFSCgW0= -nhooyr.io/websocket v1.8.7 h1:usjR2uOr/zjjkVMy0lW+PPohFok7PCow5sDjLgX4P4g= -nhooyr.io/websocket v1.8.7/go.mod h1:B70DZP8IakI65RVQ51MsWP/8jndNma26DVA/nFSCgW0= +nhooyr.io/websocket v1.8.10 h1:mv4p+MnGrLDcPlBoWsvPP7XCzTYMXP9F9eIGoKbgx7Q= +nhooyr.io/websocket v1.8.10/go.mod h1:rN9OFWIUwuxg4fR5tELlYC04bXYowCP9GX47ivo2l+c= pgregory.net/rapid v1.1.0 h1:CMa0sjHSru3puNx+J0MIAuiiEV4N0qj8/cMWGBBCsjw= pgregory.net/rapid v1.1.0/go.mod h1:PY5XlDGj0+V1FCq0o192FdRhpKHGTRIWBgqjDBTrq04= rsc.io/binaryregexp v0.2.0/go.mod h1:qTv7/COck+e2FymRvadv62gMdZztPaShugOCi3I+8D8= diff --git a/e2e/sample.config.yaml b/e2e/sample.config.yaml index 5550e02a87b..4c9a750013c 100644 --- a/e2e/sample.config.yaml +++ b/e2e/sample.config.yaml @@ -30,7 +30,7 @@ relayers: tag: "latest" - id: hyperspace image: ghcr.io/misko9/hyperspace - tag: "timeout" + tag: "20231122v39" cometbft: logLevel: info diff --git a/e2e/tests/core/04-channel/upgrades_test.go b/e2e/tests/core/04-channel/upgrades_test.go new file mode 100644 index 00000000000..cb44b549a50 --- /dev/null +++ b/e2e/tests/core/04-channel/upgrades_test.go @@ -0,0 +1,141 @@ +//go:build !test_e2e + +package channel + +import ( + "context" + "testing" + + "github.com/strangelove-ventures/interchaintest/v8/ibc" + test "github.com/strangelove-ventures/interchaintest/v8/testutil" + testifysuite "github.com/stretchr/testify/suite" + + govtypes "github.com/cosmos/cosmos-sdk/x/gov/types" + + "github.com/cosmos/ibc-go/e2e/testsuite" + "github.com/cosmos/ibc-go/e2e/testvalues" + feetypes "github.com/cosmos/ibc-go/v8/modules/apps/29-fee/types" + transfertypes "github.com/cosmos/ibc-go/v8/modules/apps/transfer/types" + channeltypes "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" +) + +func TestChannelTestSuite(t *testing.T) { + testifysuite.Run(t, new(ChannelTestSuite)) +} + +type ChannelTestSuite struct { + testsuite.E2ETestSuite +} + +// TestChannelUpgrade_WithFeeMiddleware_Succeeds tests upgrading a transfer channel to wire up fee middleware +func (s *ChannelTestSuite) TestChannelUpgrade_WithFeeMiddleware_Succeeds() { + t := s.T() + ctx := context.TODO() + + relayer, channelA := s.SetupChainsRelayerAndChannel(ctx, s.TransferChannelOptions()) + channelB := channelA.Counterparty + chainA, chainB := s.GetChains() + + chainADenom := chainA.Config().Denom + chainBDenom := chainB.Config().Denom + chainAIBCToken := testsuite.GetIBCToken(chainBDenom, channelA.PortID, channelA.ChannelID) + chainBIBCToken := testsuite.GetIBCToken(chainADenom, channelB.PortID, channelB.ChannelID) + + chainAWallet := s.CreateUserOnChainA(ctx, testvalues.StartingTokenAmount) + chainAAddress := chainAWallet.FormattedAddress() + + chainBWallet := s.CreateUserOnChainB(ctx, testvalues.StartingTokenAmount) + chainBAddress := chainBWallet.FormattedAddress() + + s.Require().NoError(test.WaitForBlocks(ctx, 1, chainA, chainB), "failed to wait for blocks") + + // trying to create some inflight packets, although they might get relayed before the upgrade starts + t.Run("create inflight transfer packets between chain A and chain B", func(t *testing.T) { + transferTxResp := s.Transfer(ctx, chainA, chainAWallet, channelA.PortID, channelA.ChannelID, testvalues.DefaultTransferAmount(chainADenom), chainAAddress, chainBAddress, s.GetTimeoutHeight(ctx, chainB), 0, "") + s.AssertTxSuccess(transferTxResp) + + transferTxResp = s.Transfer(ctx, chainB, chainBWallet, channelB.PortID, channelB.ChannelID, testvalues.DefaultTransferAmount(chainBDenom), chainBAddress, chainAAddress, s.GetTimeoutHeight(ctx, chainA), 0, "") + s.AssertTxSuccess(transferTxResp) + }) + + t.Run("execute gov proposal to initiate channel upgrade", func(t *testing.T) { + chA, err := s.QueryChannel(ctx, chainA, channelA.PortID, channelA.ChannelID) + s.Require().NoError(err) + + s.initiateChannelUpgrade(ctx, chainA, chainAWallet, channelA.PortID, channelA.ChannelID, s.createUpgradeFields(chA)) + }) + + t.Run("start relayer", func(t *testing.T) { + s.StartRelayer(relayer) + }) + + s.Require().NoError(test.WaitForBlocks(ctx, 10, chainA, chainB), "failed to wait for blocks") + + t.Run("packets are relayed between chain A and chain B", func(t *testing.T) { + // packet from chain A to chain B + s.AssertPacketRelayed(ctx, chainA, channelA.PortID, channelA.ChannelID, 1) + actualBalance, err := s.QueryBalance(ctx, chainB, chainBAddress, chainBIBCToken.IBCDenom()) + s.Require().NoError(err) + expected := testvalues.IBCTransferAmount + s.Require().Equal(expected, actualBalance.Int64()) + + // packet from chain B to chain A + s.AssertPacketRelayed(ctx, chainB, channelB.PortID, channelB.ChannelID, 1) + actualBalance, err = s.QueryBalance(ctx, chainA, chainAAddress, chainAIBCToken.IBCDenom()) + s.Require().NoError(err) + expected = testvalues.IBCTransferAmount + s.Require().Equal(expected, actualBalance.Int64()) + }) + + t.Run("verify channel A upgraded and is fee enabled", func(t *testing.T) { + channel, err := s.QueryChannel(ctx, chainA, channelA.PortID, channelA.ChannelID) + s.Require().NoError(err) + + // check the channel version include the fee version + version, err := feetypes.MetadataFromVersion(channel.Version) + s.Require().NoError(err) + s.Require().Equal(feetypes.Version, version.FeeVersion, "the channel version did not include ics29") + + // extra check + feeEnabled, err := s.QueryFeeEnabledChannel(ctx, chainA, channelA.PortID, channelA.ChannelID) + s.Require().NoError(err) + s.Require().Equal(true, feeEnabled) + }) + + t.Run("verify channel B upgraded and has version with ics29", func(t *testing.T) { + channel, err := s.QueryChannel(ctx, chainB, channelB.PortID, channelB.ChannelID) + s.Require().NoError(err) + + // check the channel version include the fee version + version, err := feetypes.MetadataFromVersion(channel.Version) + s.Require().NoError(err) + s.Require().Equal(feetypes.Version, version.FeeVersion, "the channel version did not include ics29") + + // extra check + feeEnabled, err := s.QueryFeeEnabledChannel(ctx, chainB, channelB.PortID, channelB.ChannelID) + s.Require().NoError(err) + s.Require().Equal(true, feeEnabled) + }) +} + +// createUpgradeFields created the upgrade fields for channel +func (s *ChannelTestSuite) createUpgradeFields(channel channeltypes.Channel) channeltypes.UpgradeFields { + versionMetadata := feetypes.Metadata{ + FeeVersion: feetypes.Version, + AppVersion: transfertypes.Version, + } + versionBytes, err := feetypes.ModuleCdc.MarshalJSON(&versionMetadata) + s.Require().NoError(err) + + return channeltypes.NewUpgradeFields(channel.Ordering, channel.ConnectionHops, string(versionBytes)) +} + +// initiateChannelUpgrade creates and submits a governance proposal to execute the message to initiate a channel upgrade +func (s *ChannelTestSuite) initiateChannelUpgrade(ctx context.Context, chain ibc.Chain, wallet ibc.Wallet, portID, channelID string, upgradeFields channeltypes.UpgradeFields) { + govModuleAddress, err := s.QueryModuleAccountAddress(ctx, govtypes.ModuleName, chain) + s.Require().NoError(err) + s.Require().NotNil(govModuleAddress) + + msg := channeltypes.NewMsgChannelUpgradeInit(portID, channelID, upgradeFields, govModuleAddress.String()) + s.ExecuteAndPassGovV1Proposal(ctx, msg, chain, wallet) +} diff --git a/e2e/tests/interchain_accounts/localhost_test.go b/e2e/tests/interchain_accounts/localhost_test.go index 9f1f2272a03..99dbc591eb1 100644 --- a/e2e/tests/interchain_accounts/localhost_test.go +++ b/e2e/tests/interchain_accounts/localhost_test.go @@ -327,7 +327,8 @@ func (s *LocalhostInterchainAccountsTestSuite) TestInterchainAccounts_ReopenChan }) t.Run("close interchain accounts host channel end", func(t *testing.T) { - msgCloseConfirm := channeltypes.NewMsgChannelCloseConfirm(icatypes.HostPortID, msgChanOpenTryRes.ChannelId, localhost.SentinelProof, clienttypes.ZeroHeight(), rlyWallet.FormattedAddress()) + // Pass in zero for counterpartyUpgradeSequence given that channel has not undergone any upgrades. + msgCloseConfirm := channeltypes.NewMsgChannelCloseConfirm(icatypes.HostPortID, msgChanOpenTryRes.ChannelId, localhost.SentinelProof, clienttypes.ZeroHeight(), rlyWallet.FormattedAddress(), 0) txResp := s.BroadcastMessages(ctx, chainA, rlyWallet, msgCloseConfirm) s.AssertTxSuccess(txResp) diff --git a/e2e/tests/wasm/grandpa_test.go b/e2e/tests/wasm/grandpa_test.go index cf924e996f4..1db15f28d20 100644 --- a/e2e/tests/wasm/grandpa_test.go +++ b/e2e/tests/wasm/grandpa_test.go @@ -19,7 +19,7 @@ import ( "github.com/strangelove-ventures/interchaintest/v8/testutil" testifysuite "github.com/stretchr/testify/suite" - "cosmossdk.io/math" + sdkmath "cosmossdk.io/math" authtypes "github.com/cosmos/cosmos-sdk/x/auth/types" govtypes "github.com/cosmos/cosmos-sdk/x/gov/types" @@ -120,7 +120,7 @@ func (s *GrandpaTestSuite) TestMsgTransfer_Succeeds_GrandpaContract() { transfer := ibc.WalletAmount{ Address: polkadotUser.FormattedAddress(), Denom: cosmosChain.Config().Denom, - Amount: math.NewInt(amountToSend), + Amount: sdkmath.NewInt(amountToSend), } pathName := s.GetPathName(0) @@ -162,7 +162,7 @@ func (s *GrandpaTestSuite) TestMsgTransfer_Succeeds_GrandpaContract() { // verify token balance for cosmos user has decreased balance, err := cosmosChain.GetBalance(ctx, cosmosUser.FormattedAddress(), cosmosChain.Config().Denom) s.Require().NoError(err) - s.Require().Equal(balance, math.NewInt(fundAmount-amountToSend), "unexpected cosmos user balance after first tx") + s.Require().Equal(balance, sdkmath.NewInt(fundAmount-amountToSend), "unexpected cosmos user balance after first tx") err = testutil.WaitForBlocks(ctx, 15, cosmosChain, polkadotChain) s.Require().NoError(err) @@ -178,13 +178,13 @@ func (s *GrandpaTestSuite) TestMsgTransfer_Succeeds_GrandpaContract() { reflectTransfer := ibc.WalletAmount{ Address: cosmosUser.FormattedAddress(), Denom: "2", // stake - Amount: math.NewInt(amountToReflect), + Amount: sdkmath.NewInt(amountToReflect), } _, err := polkadotChain.SendIBCTransfer(ctx, "channel-0", polkadotUser.KeyName(), reflectTransfer, ibc.TransferOptions{}) s.Require().NoError(err) // Send 1.88 "UNIT" from Alice to cosmosUser - amountUnits := math.NewInt(1_880_000_000_000) + amountUnits := sdkmath.NewInt(1_880_000_000_000) unitTransfer := ibc.WalletAmount{ Address: cosmosUser.FormattedAddress(), Denom: "1", // UNIT @@ -194,7 +194,7 @@ func (s *GrandpaTestSuite) TestMsgTransfer_Succeeds_GrandpaContract() { s.Require().NoError(err) // Wait for MsgRecvPacket on cosmos chain - finalStakeBal := math.NewInt(fundAmount - amountToSend + amountToReflect) + finalStakeBal := sdkmath.NewInt(fundAmount - amountToSend + amountToReflect) err = cosmos.PollForBalance(ctx, cosmosChain, 20, ibc.WalletAmount{ Address: cosmosUser.FormattedAddress(), Denom: cosmosChain.Config().Denom, @@ -220,12 +220,12 @@ func (s *GrandpaTestSuite) TestMsgTransfer_Succeeds_GrandpaContract() { // Verify parachain user's final "unit" balance (will be less than expected due gas costs for stake tx) parachainUserUnits, err := polkadotChain.GetIbcBalance(ctx, string(polkadotUser.Address()), 1) s.Require().NoError(err) - s.Require().True(parachainUserUnits.Amount.LTE(math.NewInt(fundAmount)), "parachain user's final unit amount not expected") + s.Require().True(parachainUserUnits.Amount.LTE(sdkmath.NewInt(fundAmount)), "parachain user's final unit amount not expected") // Verify parachain user's final "stake" balance parachainUserStake, err := polkadotChain.GetIbcBalance(ctx, string(polkadotUser.Address()), 2) s.Require().NoError(err) - s.Require().True(parachainUserStake.Amount.Equal(math.NewInt(amountToSend-amountToReflect)), "parachain user's final stake amount not expected") + s.Require().True(parachainUserStake.Amount.Equal(sdkmath.NewInt(amountToSend-amountToReflect)), "parachain user's final stake amount not expected") }) } @@ -277,7 +277,7 @@ func (s *GrandpaTestSuite) TestMsgTransfer_TimesOut_GrandpaContract() { transfer := ibc.WalletAmount{ Address: polkadotUser.FormattedAddress(), Denom: cosmosChain.Config().Denom, - Amount: math.NewInt(amountToSend), + Amount: sdkmath.NewInt(amountToSend), } pathName := s.GetPathName(0) @@ -695,13 +695,13 @@ func (s *GrandpaTestSuite) clientStatus(ctx context.Context, chain ibc.Chain, cl } func (s *GrandpaTestSuite) fundUsers(ctx context.Context, fundAmount int64, polkadotChain ibc.Chain, cosmosChain ibc.Chain) (ibc.Wallet, ibc.Wallet) { - users := interchaintest.GetAndFundTestUsers(s.T(), ctx, "user", fundAmount, polkadotChain, cosmosChain) + users := interchaintest.GetAndFundTestUsers(s.T(), ctx, "user", sdkmath.NewInt(fundAmount), polkadotChain, cosmosChain) polkadotUser, cosmosUser := users[0], users[1] err := testutil.WaitForBlocks(ctx, 2, polkadotChain, cosmosChain) // Only waiting 1 block is flaky for parachain s.Require().NoError(err, "cosmos or polkadot chain failed to make blocks") // Check balances are correct - amount := math.NewInt(fundAmount) + amount := sdkmath.NewInt(fundAmount) polkadotUserAmount, err := polkadotChain.GetBalance(ctx, polkadotUser.FormattedAddress(), polkadotChain.Config().Denom) s.Require().NoError(err) s.Require().True(polkadotUserAmount.Equal(amount), "Initial polkadot user amount not expected") @@ -754,12 +754,12 @@ func (s *GrandpaTestSuite) GetGrandpaTestChains() (ibc.Chain, ibc.Chain) { // TODO: https://github.com/cosmos/ibc-go/issues/4965 { Repository: "ghcr.io/misko9/polkadot-node", - Version: "local", + Version: "v39", UidGid: "1000:1000", }, { Repository: "ghcr.io/misko9/parachain-node", - Version: "latest", + Version: "20231122v39", UidGid: "1000:1000", }, } diff --git a/e2e/testsuite/grpc_query.go b/e2e/testsuite/grpc_query.go index ee72396a56f..23e9a5fa5f8 100644 --- a/e2e/testsuite/grpc_query.go +++ b/e2e/testsuite/grpc_query.go @@ -258,6 +258,19 @@ func (s *E2ETestSuite) QueryIncentivizedPacketsForChannel( return res.IncentivizedPackets, err } +// QueryFeeEnabledChannel queries the fee-enabled status of a channel. +func (s *E2ETestSuite) QueryFeeEnabledChannel(ctx context.Context, chain ibc.Chain, portID, channelID string) (bool, error) { + queryClient := s.GetChainGRCPClients(chain).FeeQueryClient + res, err := queryClient.FeeEnabledChannel(ctx, &feetypes.QueryFeeEnabledChannelRequest{ + PortId: portID, + ChannelId: channelID, + }) + if err != nil { + return false, err + } + return res.FeeEnabled, nil +} + // QueryCounterPartyPayee queries the counterparty payee of the given chain and relayer address on the specified channel. func (s *E2ETestSuite) QueryCounterPartyPayee(ctx context.Context, chain ibc.Chain, relayerAddress, channelID string) (string, error) { queryClient := s.GetChainGRCPClients(chain).FeeQueryClient diff --git a/e2e/testsuite/testconfig.go b/e2e/testsuite/testconfig.go index 75050a29ee5..c88646fc6d9 100644 --- a/e2e/testsuite/testconfig.go +++ b/e2e/testsuite/testconfig.go @@ -56,9 +56,9 @@ const ( defaultRlyTag = "latest" // TODO: https://github.com/cosmos/ibc-go/issues/4965 - defaultHyperspaceTag = "timeout" + defaultHyperspaceTag = "20231122v39" // defaultHermesTag is the tag that will be used if no relayer tag is specified for hermes. - defaultHermesTag = "v1.7.0" + defaultHermesTag = "luca_joss-channel-upgrade-authority" // defaultChainTag is the tag that will be used for the chains if none is specified. defaultChainTag = "main" // defaultConfigFileName is the default filename for the config file that can be used to configure diff --git a/e2e/testsuite/testsuite.go b/e2e/testsuite/testsuite.go index e65a1246d80..46e8b73710d 100644 --- a/e2e/testsuite/testsuite.go +++ b/e2e/testsuite/testsuite.go @@ -15,6 +15,8 @@ import ( testifysuite "github.com/stretchr/testify/suite" "go.uber.org/zap" + sdkmath "cosmossdk.io/math" + "github.com/cosmos/ibc-go/e2e/relayer" "github.com/cosmos/ibc-go/e2e/testsuite/diagnostics" transfertypes "github.com/cosmos/ibc-go/v8/modules/apps/transfer/types" @@ -295,13 +297,13 @@ func (s *E2ETestSuite) RestartRelayer(ctx context.Context, ibcrelayer ibc.Relaye // CreateUserOnChainA creates a user with the given amount of funds on chain A. func (s *E2ETestSuite) CreateUserOnChainA(ctx context.Context, amount int64) ibc.Wallet { chainA, _ := s.GetChains() - return interchaintest.GetAndFundTestUsers(s.T(), ctx, strings.ReplaceAll(s.T().Name(), " ", "-"), amount, chainA)[0] + return interchaintest.GetAndFundTestUsers(s.T(), ctx, strings.ReplaceAll(s.T().Name(), " ", "-"), sdkmath.NewInt(amount), chainA)[0] } // CreateUserOnChainB creates a user with the given amount of funds on chain B. func (s *E2ETestSuite) CreateUserOnChainB(ctx context.Context, amount int64) ibc.Wallet { _, chainB := s.GetChains() - return interchaintest.GetAndFundTestUsers(s.T(), ctx, strings.ReplaceAll(s.T().Name(), " ", "-"), amount, chainB)[0] + return interchaintest.GetAndFundTestUsers(s.T(), ctx, strings.ReplaceAll(s.T().Name(), " ", "-"), sdkmath.NewInt(amount), chainB)[0] } // GetChainANativeBalance gets the balance of a given user on chain A. diff --git a/modules/apps/27-interchain-accounts/controller/ibc_middleware.go b/modules/apps/27-interchain-accounts/controller/ibc_middleware.go index b51592a12d8..199c4f2d9da 100644 --- a/modules/apps/27-interchain-accounts/controller/ibc_middleware.go +++ b/modules/apps/27-interchain-accounts/controller/ibc_middleware.go @@ -22,6 +22,7 @@ import ( var ( _ porttypes.Middleware = (*IBCMiddleware)(nil) _ porttypes.PacketDataUnmarshaler = (*IBCMiddleware)(nil) + _ porttypes.UpgradableModule = (*IBCMiddleware)(nil) ) // IBCMiddleware implements the ICS26 callbacks for the fee middleware given the @@ -231,6 +232,100 @@ func (im IBCMiddleware) OnTimeoutPacket( return nil } +// OnChanUpgradeInit implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeInit(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) (string, error) { + if !im.keeper.GetParams(ctx).ControllerEnabled { + return "", types.ErrControllerSubModuleDisabled + } + + version, err := im.keeper.OnChanUpgradeInit(ctx, portID, channelID, order, connectionHops, version) + if err != nil { + return "", err + } + + connectionID, err := im.keeper.GetConnectionID(ctx, portID, channelID) + if err != nil { + return "", err + } + + if im.app != nil && im.keeper.IsMiddlewareEnabled(ctx, portID, connectionID) { + // Only cast to UpgradableModule if the application is set. + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + return "", errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack") + } + return cbs.OnChanUpgradeInit(ctx, portID, channelID, order, connectionHops, version) + } + + return version, nil +} + +// OnChanUpgradeTry implements the IBCModule interface +func (IBCMiddleware) OnChanUpgradeTry(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, counterpartyVersion string) (string, error) { + return "", errorsmod.Wrap(icatypes.ErrInvalidChannelFlow, "channel upgrade handshake must be initiated by controller chain") +} + +// OnChanUpgradeAck implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeAck(ctx sdk.Context, portID, channelID, counterpartyVersion string) error { + if !im.keeper.GetParams(ctx).ControllerEnabled { + return types.ErrControllerSubModuleDisabled + } + + if err := im.keeper.OnChanUpgradeAck(ctx, portID, channelID, counterpartyVersion); err != nil { + return err + } + + connectionID, err := im.keeper.GetConnectionID(ctx, portID, channelID) + if err != nil { + return err + } + + if im.app != nil && im.keeper.IsMiddlewareEnabled(ctx, portID, connectionID) { + // Only cast to UpgradableModule if the application is set. + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + return errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack") + } + return cbs.OnChanUpgradeAck(ctx, portID, channelID, counterpartyVersion) + } + + return nil +} + +// OnChanUpgradeOpen implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeOpen(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) { + connectionID, err := im.keeper.GetConnectionID(ctx, portID, channelID) + if err != nil { + panic(err) + } + + if im.app != nil && im.keeper.IsMiddlewareEnabled(ctx, portID, connectionID) { + // Only cast to UpgradableModule if the application is set. + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + panic(errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack")) + } + cbs.OnChanUpgradeOpen(ctx, portID, channelID, order, connectionHops, version) + } +} + +// OnChanUpgradeRestore implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeRestore(ctx sdk.Context, portID, channelID string) { + connectionID, err := im.keeper.GetConnectionID(ctx, portID, channelID) + if err != nil { + panic(err) + } + + if im.app != nil && im.keeper.IsMiddlewareEnabled(ctx, portID, connectionID) { + // Only cast to UpgradableModule if the application is set. + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + panic(errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack")) + } + cbs.OnChanUpgradeRestore(ctx, portID, channelID) + } +} + // SendPacket implements the ICS4 Wrapper interface func (IBCMiddleware) SendPacket( ctx sdk.Context, diff --git a/modules/apps/27-interchain-accounts/controller/ibc_middleware_test.go b/modules/apps/27-interchain-accounts/controller/ibc_middleware_test.go index 3394c1af332..568edb2b031 100644 --- a/modules/apps/27-interchain-accounts/controller/ibc_middleware_test.go +++ b/modules/apps/27-interchain-accounts/controller/ibc_middleware_test.go @@ -18,8 +18,11 @@ import ( porttypes "github.com/cosmos/ibc-go/v8/modules/core/05-port/types" host "github.com/cosmos/ibc-go/v8/modules/core/24-host" ibctesting "github.com/cosmos/ibc-go/v8/testing" + ibcmock "github.com/cosmos/ibc-go/v8/testing/mock" ) +const invalidVersion = "invalid|version" + var ( // TestOwnerAddress defines a reusable bech32 address for testing purposes TestOwnerAddress = "cosmos17dtl0mjt3t77kpuhg2edqzjpszulwhgzuj9ljs" @@ -327,7 +330,7 @@ func (suite *InterchainAccountsTestSuite) TestOnChanOpenAck() { }, { "ICA OnChanOpenACK fails - invalid version", func() { - path.EndpointB.ChannelConfig.Version = "invalid|version" + path.EndpointB.ChannelConfig.Version = invalidVersion }, false, }, { @@ -762,6 +765,331 @@ func (suite *InterchainAccountsTestSuite) TestOnTimeoutPacket() { } } +func (suite *InterchainAccountsTestSuite) TestOnChanUpgradeInit() { + var ( + path *ibctesting.Path + isNilApp bool + version string + ) + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", func() {}, nil, + }, + { + "success: nil underlying app", + func() { + isNilApp = true + }, + nil, + }, + { + "controller submodule disabled", func() { + suite.chainA.GetSimApp().ICAControllerKeeper.SetParams(suite.chainA.GetContext(), types.NewParams(false)) + }, types.ErrControllerSubModuleDisabled, + }, + { + "ICA OnChanUpgradeInit fails - invalid version", func() { + version = invalidVersion + }, icatypes.ErrUnknownDataType, + }, + { + "ICA auth module callback fails", func() { + suite.chainA.GetSimApp().ICAAuthModule.IBCApp.OnChanUpgradeInit = func(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) (string, error) { + return "", ibcmock.MockApplicationCallbackError + } + }, ibcmock.MockApplicationCallbackError, + }, + { + "middleware disabled", func() { + suite.chainA.GetSimApp().ICAControllerKeeper.DeleteMiddlewareEnabled(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ConnectionID) + suite.chainA.GetSimApp().ICAAuthModule.IBCApp.OnChanUpgradeInit = func(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) (string, error) { + return "", ibcmock.MockApplicationCallbackError + } + }, nil, + }, + } + + for _, tc := range testCases { + tc := tc + + suite.Run(tc.name, func() { + suite.SetupTest() // reset + isNilApp = false + + path = NewICAPath(suite.chainA, suite.chainB) + suite.coordinator.SetupConnections(path) + + err := RegisterInterchainAccount(path.EndpointA, TestOwnerAddress) + suite.Require().NoError(err) + + metadata := icatypes.NewDefaultMetadata(path.EndpointA.ConnectionID, path.EndpointB.ConnectionID) + version = string(icatypes.ModuleCdc.MustMarshalJSON(&metadata)) + + tc.malleate() // malleate mutates test data + + module, _, err := suite.chainA.App.GetIBCKeeper().PortKeeper.LookupModuleByPort(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID) + suite.Require().NoError(err) + + app, ok := suite.chainA.App.GetIBCKeeper().Router.GetRoute(module) + suite.Require().True(ok) + cbs, ok := app.(porttypes.UpgradableModule) + suite.Require().True(ok) + + if isNilApp { + cbs = controller.NewIBCMiddleware(nil, suite.chainA.GetSimApp().ICAControllerKeeper) + } + + version, err = cbs.OnChanUpgradeInit( + suite.chainA.GetContext(), + path.EndpointA.ChannelConfig.PortID, + path.EndpointA.ChannelID, + channeltypes.ORDERED, + []string{path.EndpointA.ConnectionID}, + version, + ) + + if tc.expError == nil { + suite.Require().NoError(err) + } else { + suite.Require().ErrorIs(err, tc.expError) + suite.Require().Empty(version) + } + }) + } +} + +func (suite *InterchainAccountsTestSuite) TestOnChanUpgradeAck() { + var ( + path *ibctesting.Path + isNilApp bool + counterpartyVersion string + ) + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", func() {}, nil, + }, + { + "success: nil underlying app", + func() { + isNilApp = true + }, + nil, + }, + { + "controller submodule disabled", func() { + suite.chainA.GetSimApp().ICAControllerKeeper.SetParams(suite.chainA.GetContext(), types.NewParams(false)) + }, types.ErrControllerSubModuleDisabled, + }, + { + "ICA OnChanUpgradeAck fails - invalid version", func() { + counterpartyVersion = invalidVersion + }, icatypes.ErrUnknownDataType, + }, + { + "ICA auth module callback fails", func() { + suite.chainA.GetSimApp().ICAAuthModule.IBCApp.OnChanUpgradeAck = func(ctx sdk.Context, portID, channelID string, counterpartyVersion string) error { + return ibcmock.MockApplicationCallbackError + } + }, ibcmock.MockApplicationCallbackError, + }, + { + "middleware disabled", func() { + suite.chainA.GetSimApp().ICAControllerKeeper.DeleteMiddlewareEnabled(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ConnectionID) + suite.chainA.GetSimApp().ICAAuthModule.IBCApp.OnChanUpgradeAck = func(ctx sdk.Context, portID, channelID string, counterpartyVersion string) error { + return ibcmock.MockApplicationCallbackError + } + }, nil, + }, + } + + for _, tc := range testCases { + tc := tc + + suite.Run(tc.name, func() { + suite.SetupTest() // reset + isNilApp = false + + path = NewICAPath(suite.chainA, suite.chainB) + suite.coordinator.SetupConnections(path) + + err := SetupICAPath(path, TestOwnerAddress) + suite.Require().NoError(err) + + counterpartyVersion = path.EndpointB.GetChannel().Version + + tc.malleate() // malleate mutates test data + + module, _, err := suite.chainA.App.GetIBCKeeper().PortKeeper.LookupModuleByPort(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID) + suite.Require().NoError(err) + + app, ok := suite.chainA.App.GetIBCKeeper().Router.GetRoute(module) + suite.Require().True(ok) + cbs, ok := app.(porttypes.UpgradableModule) + suite.Require().True(ok) + + if isNilApp { + cbs = controller.NewIBCMiddleware(nil, suite.chainA.GetSimApp().ICAControllerKeeper) + } + + err = cbs.OnChanUpgradeAck( + suite.chainA.GetContext(), + path.EndpointA.ChannelConfig.PortID, + path.EndpointA.ChannelID, + counterpartyVersion, + ) + + if tc.expError == nil { + suite.Require().NoError(err) + } else { + suite.Require().ErrorIs(err, tc.expError) + } + }) + } +} + +func (suite *InterchainAccountsTestSuite) TestOnChanUpgradeOpen() { + var ( + path *ibctesting.Path + isNilApp bool + counterpartyVersion string + ) + + testCases := []struct { + name string + malleate func() + }{ + { + "success", + func() {}, + }, + { + "success: nil app", + func() { + isNilApp = true + }, + }, + { + "middleware disabled", func() { + suite.chainA.GetSimApp().ICAControllerKeeper.DeleteMiddlewareEnabled(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ConnectionID) + suite.chainA.GetSimApp().ICAAuthModule.IBCApp.OnChanUpgradeAck = func(ctx sdk.Context, portID, channelID string, counterpartyVersion string) error { + return ibcmock.MockApplicationCallbackError + } + }, + }, + } + + for _, tc := range testCases { + tc := tc + + suite.Run(tc.name, func() { + suite.SetupTest() // reset + isNilApp = false + + path = NewICAPath(suite.chainA, suite.chainB) + suite.coordinator.SetupConnections(path) + + err := SetupICAPath(path, TestOwnerAddress) + suite.Require().NoError(err) + + counterpartyVersion = path.EndpointB.GetChannel().Version + + tc.malleate() // malleate mutates test data + + module, _, err := suite.chainA.App.GetIBCKeeper().PortKeeper.LookupModuleByPort(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID) + suite.Require().NoError(err) + + app, ok := suite.chainA.App.GetIBCKeeper().Router.GetRoute(module) + suite.Require().True(ok) + cbs, ok := app.(porttypes.UpgradableModule) + suite.Require().True(ok) + + if isNilApp { + cbs = controller.NewIBCMiddleware(nil, suite.chainA.GetSimApp().ICAControllerKeeper) + } + + cbs.OnChanUpgradeOpen( + suite.chainA.GetContext(), + path.EndpointA.ChannelConfig.PortID, + path.EndpointA.ChannelID, + channeltypes.ORDERED, + []string{path.EndpointA.ConnectionID}, + counterpartyVersion, + ) + }) + } +} + +func (suite *InterchainAccountsTestSuite) TestOnChanUpgradeRestore() { + var ( + path *ibctesting.Path + isNilApp bool + ) + + testCases := []struct { + name string + malleate func() + }{ + { + "success", func() {}, + }, + { + "success: nil app", + func() { + isNilApp = true + }, + }, + { + "middleware disabled", func() { + suite.chainA.GetSimApp().ICAControllerKeeper.DeleteMiddlewareEnabled(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ConnectionID) + suite.chainA.GetSimApp().ICAAuthModule.IBCApp.OnChanUpgradeAck = func(ctx sdk.Context, portID, channelID string, counterpartyVersion string) error { + return ibcmock.MockApplicationCallbackError + } + }, + }, + } + + for _, tc := range testCases { + tc := tc + + suite.Run(tc.name, func() { + suite.SetupTest() // reset + isNilApp = false + + path = NewICAPath(suite.chainA, suite.chainB) + suite.coordinator.SetupConnections(path) + + err := SetupICAPath(path, TestOwnerAddress) + suite.Require().NoError(err) + + tc.malleate() // malleate mutates test data + + module, _, err := suite.chainA.App.GetIBCKeeper().PortKeeper.LookupModuleByPort(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID) + suite.Require().NoError(err) + + app, ok := suite.chainA.App.GetIBCKeeper().Router.GetRoute(module) + suite.Require().True(ok) + cbs, ok := app.(porttypes.UpgradableModule) + suite.Require().True(ok) + + if isNilApp { + cbs = controller.NewIBCMiddleware(nil, suite.chainA.GetSimApp().ICAControllerKeeper) + } + + cbs.OnChanUpgradeRestore(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + }) + } +} + func (suite *InterchainAccountsTestSuite) TestSingleHostMultipleControllers() { var ( pathAToB *ibctesting.Path diff --git a/modules/apps/27-interchain-accounts/controller/keeper/export_test.go b/modules/apps/27-interchain-accounts/controller/keeper/export_test.go index 382dde7a805..2cd4338dde2 100644 --- a/modules/apps/27-interchain-accounts/controller/keeper/export_test.go +++ b/modules/apps/27-interchain-accounts/controller/keeper/export_test.go @@ -4,9 +4,19 @@ package keeper This file is to allow for unexported functions and fields to be accessible to the testing package. */ -import porttypes "github.com/cosmos/ibc-go/v8/modules/core/05-port/types" +import ( + sdk "github.com/cosmos/cosmos-sdk/types" + + icatypes "github.com/cosmos/ibc-go/v8/modules/apps/27-interchain-accounts/types" + porttypes "github.com/cosmos/ibc-go/v8/modules/core/05-port/types" +) // GetICS4Wrapper is a getter for the keeper's ICS4Wrapper. func (k *Keeper) GetICS4Wrapper() porttypes.ICS4Wrapper { return k.ics4Wrapper } + +// GetAppMetadata is a wrapper around getAppMetadata to allow the function to be directly called in tests. +func (k Keeper) GetAppMetadata(ctx sdk.Context, portID, channelID string) (icatypes.Metadata, error) { + return k.getAppMetadata(ctx, portID, channelID) +} diff --git a/modules/apps/27-interchain-accounts/controller/keeper/handshake.go b/modules/apps/27-interchain-accounts/controller/keeper/handshake.go index 80ff3603734..4888ebc3f87 100644 --- a/modules/apps/27-interchain-accounts/controller/keeper/handshake.go +++ b/modules/apps/27-interchain-accounts/controller/keeper/handshake.go @@ -10,6 +10,7 @@ import ( capabilitytypes "github.com/cosmos/ibc-go/modules/capability/types" icatypes "github.com/cosmos/ibc-go/v8/modules/apps/27-interchain-accounts/types" + connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" channeltypes "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" ) @@ -42,7 +43,10 @@ func (k Keeper) OnChanOpenInit( return "", errorsmod.Wrapf(icatypes.ErrInvalidHostPort, "expected %s, got %s", icatypes.HostPortID, counterparty.PortId) } - var metadata icatypes.Metadata + var ( + err error + metadata icatypes.Metadata + ) if strings.TrimSpace(version) == "" { connection, err := k.channelKeeper.GetConnection(ctx, connectionHops[0]) if err != nil { @@ -51,8 +55,9 @@ func (k Keeper) OnChanOpenInit( metadata = icatypes.NewDefaultMetadata(connectionHops[0], connection.GetCounterparty().GetConnectionID()) } else { - if err := icatypes.ModuleCdc.UnmarshalJSON([]byte(version), &metadata); err != nil { - return "", errorsmod.Wrapf(icatypes.ErrUnknownDataType, "cannot unmarshal ICS-27 interchain accounts metadata") + metadata, err = icatypes.MetadataFromVersion(version) + if err != nil { + return "", err } } @@ -100,11 +105,10 @@ func (k Keeper) OnChanOpenAck( return errorsmod.Wrapf(icatypes.ErrInvalidControllerPort, "expected %s{owner-account-address}, got %s", icatypes.ControllerPortPrefix, portID) } - var metadata icatypes.Metadata - if err := icatypes.ModuleCdc.UnmarshalJSON([]byte(counterpartyVersion), &metadata); err != nil { - return errorsmod.Wrapf(icatypes.ErrUnknownDataType, "cannot unmarshal ICS-27 interchain accounts metadata") + metadata, err := icatypes.MetadataFromVersion(counterpartyVersion) + if err != nil { + return err } - if activeChannelID, found := k.GetOpenActiveChannel(ctx, metadata.ControllerConnectionId, portID); found { return errorsmod.Wrapf(icatypes.ErrActiveChannelAlreadySet, "existing active channel %s for portID %s", activeChannelID, portID) } @@ -136,3 +140,83 @@ func (Keeper) OnChanCloseConfirm( ) error { return nil } + +// OnChanUpgradeInit performs the upgrade init step of the channel upgrade handshake. +func (k Keeper) OnChanUpgradeInit(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) (string, error) { + if strings.TrimSpace(version) == "" { + return "", errorsmod.Wrap(icatypes.ErrInvalidVersion, "version cannot be empty") + } + + // support for unordered ICA channels is not implemented yet + if order != channeltypes.ORDERED { + return "", errorsmod.Wrapf(channeltypes.ErrInvalidChannelOrdering, "expected %s channel, got %s", channeltypes.ORDERED, order) + } + + metadata, err := icatypes.MetadataFromVersion(version) + if err != nil { + return "", err + } + + currentMetadata, err := k.getAppMetadata(ctx, portID, channelID) + if err != nil { + return "", err + } + + if err := icatypes.ValidateControllerMetadata(ctx, k.channelKeeper, connectionHops, metadata); err != nil { + return "", errorsmod.Wrap(err, "invalid metadata") + } + + // the interchain account address on the host chain + // must remain the same after the upgrade. + if currentMetadata.Address != metadata.Address { + return "", errorsmod.Wrap(icatypes.ErrInvalidAccountAddress, "interchain account address cannot be changed") + } + + if currentMetadata.ControllerConnectionId != connectionHops[0] { + return "", errorsmod.Wrap(connectiontypes.ErrInvalidConnectionIdentifier, "proposed connection hop must not change") + } + + return version, nil +} + +// OnChanUpgradeAck implements the ack setup of the channel upgrade handshake. +func (k Keeper) OnChanUpgradeAck(ctx sdk.Context, portID, channelID, counterpartyVersion string) error { + if strings.TrimSpace(counterpartyVersion) == "" { + return errorsmod.Wrap(channeltypes.ErrInvalidChannelVersion, "counterparty version cannot be empty") + } + + metadata, err := icatypes.MetadataFromVersion(counterpartyVersion) + if err != nil { + return err + } + + currentMetadata, err := k.getAppMetadata(ctx, portID, channelID) + if err != nil { + return err + } + + // the interchain account address on the host chain + // must remain the same after the upgrade. + if currentMetadata.Address != metadata.Address { + return errorsmod.Wrap(icatypes.ErrInvalidAccountAddress, "address cannot be changed") + } + + if currentMetadata.ControllerConnectionId != metadata.ControllerConnectionId { + return errorsmod.Wrap(connectiontypes.ErrInvalidConnectionIdentifier, "proposed controller connection ID must not change") + } + + if currentMetadata.HostConnectionId != metadata.HostConnectionId { + return errorsmod.Wrap(connectiontypes.ErrInvalidConnectionIdentifier, "proposed host connection ID must not change") + } + + channel, found := k.channelKeeper.GetChannel(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(channeltypes.ErrChannelNotFound, "failed to retrieve channel %s on port %s", channelID, portID) + } + + if err := icatypes.ValidateControllerMetadata(ctx, k.channelKeeper, channel.ConnectionHops, metadata); err != nil { + return err + } + + return nil +} diff --git a/modules/apps/27-interchain-accounts/controller/keeper/handshake_test.go b/modules/apps/27-interchain-accounts/controller/keeper/handshake_test.go index 29ebf75dec1..e34d91481a2 100644 --- a/modules/apps/27-interchain-accounts/controller/keeper/handshake_test.go +++ b/modules/apps/27-interchain-accounts/controller/keeper/handshake_test.go @@ -3,11 +3,16 @@ package keeper_test import ( capabilitytypes "github.com/cosmos/ibc-go/modules/capability/types" icatypes "github.com/cosmos/ibc-go/v8/modules/apps/27-interchain-accounts/types" + connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" channeltypes "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" host "github.com/cosmos/ibc-go/v8/modules/core/24-host" ibctesting "github.com/cosmos/ibc-go/v8/testing" ) +const ( + differentConnectionID = "connection-100" +) + func (suite *KeeperTestSuite) TestOnChanOpenInit() { var ( channel *channeltypes.Channel @@ -471,3 +476,258 @@ func (suite *KeeperTestSuite) TestOnChanCloseConfirm() { }) } } + +func (suite *KeeperTestSuite) TestOnChanUpgradeInit() { + var ( + path *ibctesting.Path + metadata icatypes.Metadata + order channeltypes.Order + ) + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + name: "failure: change ICA address", + malleate: func() { + metadata.Address = TestOwnerAddress + }, + expError: icatypes.ErrInvalidAccountAddress, + }, + { + name: "failure: change controller connection id", + malleate: func() { + metadata.ControllerConnectionId = differentConnectionID + }, + expError: connectiontypes.ErrInvalidConnection, + }, + { + name: "failure: change host connection id", + malleate: func() { + metadata.HostConnectionId = differentConnectionID + }, + expError: connectiontypes.ErrInvalidConnection, + }, + { + name: "failure: cannot decode version string", + malleate: func() { + channel := path.EndpointA.GetChannel() + channel.Version = "invalid-metadata-string" + path.EndpointA.SetChannel(channel) + }, + expError: icatypes.ErrUnknownDataType, + }, + { + name: "failure: invalid connection hops", + malleate: func() { + path.EndpointA.ConnectionID = differentConnectionID + }, + expError: connectiontypes.ErrConnectionNotFound, + }, + { + name: "failure: invalid order", + malleate: func() { + order = channeltypes.UNORDERED + }, + expError: channeltypes.ErrInvalidChannelOrdering, + }, + } + + for _, tc := range testCases { + tc := tc + + suite.Run(tc.name, func() { + suite.SetupTest() // reset + + path = NewICAPath(suite.chainA, suite.chainB) + suite.coordinator.SetupConnections(path) + + err := SetupICAPath(path, TestOwnerAddress) + suite.Require().NoError(err) + + currentMetadata, err := suite.chainA.GetSimApp().ICAControllerKeeper.GetAppMetadata(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().NoError(err) + + order = channeltypes.ORDERED + metadata = icatypes.NewDefaultMetadata(path.EndpointA.ConnectionID, path.EndpointB.ConnectionID) + // use the same address as the previous metadata. + metadata.Address = currentMetadata.Address + + // this is the actual change to the version. + metadata.Encoding = icatypes.EncodingProto3JSON + + tc.malleate() // malleate mutates test data + + version := string(icatypes.ModuleCdc.MustMarshalJSON(&metadata)) + + upgradeVersion, err := path.EndpointA.Chain.GetSimApp().ICAControllerKeeper.OnChanUpgradeInit( + path.EndpointA.Chain.GetContext(), + path.EndpointA.ChannelConfig.PortID, + path.EndpointA.ChannelID, + order, + []string{path.EndpointA.ConnectionID}, + version, + ) + + expPass := tc.expError == nil + + if expPass { + suite.Require().NoError(err) + suite.Require().Equal(upgradeVersion, version) + } else { + suite.Require().ErrorIs(err, tc.expError) + } + }) + } +} + +func (suite *KeeperTestSuite) TestOnChanUpgradeAck() { + const ( + invalidVersion = "invalid-version" + ) + + var ( + path *ibctesting.Path + metadata icatypes.Metadata + counterpartyVersion string + ) + + // updateMetadata is a helper function which modifies the metadata stored in the channel version + // and marshals it into a string to pass to OnChanUpgradeAck as the counterpartyVersion string. + updateMetadata := func(modificationFn func(*icatypes.Metadata)) { + metadata, err := icatypes.MetadataFromVersion(path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version) + suite.Require().NoError(err) + modificationFn(&metadata) + counterpartyVersion = string(icatypes.ModuleCdc.MustMarshalJSON(&metadata)) + } + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + name: "failure: empty counterparty version", + malleate: func() { + counterpartyVersion = "" + }, + expError: channeltypes.ErrInvalidChannelVersion, + }, + { + name: "failure: invalid counterparty version", + malleate: func() { + counterpartyVersion = invalidVersion + }, + expError: icatypes.ErrUnknownDataType, + }, + { + name: "failure: cannot decode self version string", + malleate: func() { + channel := path.EndpointA.GetChannel() + channel.Version = invalidVersion + path.EndpointA.SetChannel(channel) + }, + expError: icatypes.ErrUnknownDataType, + }, + { + name: "failure: invalid tx type", + malleate: func() { + updateMetadata(func(metadata *icatypes.Metadata) { + metadata.TxType = "invalid-tx-type" + }) + }, + expError: icatypes.ErrUnknownDataType, + }, + { + name: "failure: interchain account address has changed", + malleate: func() { + updateMetadata(func(metadata *icatypes.Metadata) { + metadata.Address = "different-address" + }) + }, + expError: icatypes.ErrInvalidAccountAddress, + }, + { + name: "failure: controller connection ID has changed", + malleate: func() { + updateMetadata(func(metadata *icatypes.Metadata) { + metadata.ControllerConnectionId = "different-connection-id" + }) + }, + expError: connectiontypes.ErrInvalidConnectionIdentifier, + }, + { + name: "failure: host connection ID has changed", + malleate: func() { + updateMetadata(func(metadata *icatypes.Metadata) { + metadata.HostConnectionId = "different-host-id" + }) + }, + expError: connectiontypes.ErrInvalidConnectionIdentifier, + }, + } + + for _, tc := range testCases { + tc := tc + + suite.Run(tc.name, func() { + suite.SetupTest() // reset + + path = NewICAPath(suite.chainA, suite.chainB) + suite.coordinator.SetupConnections(path) + + err := SetupICAPath(path, TestOwnerAddress) + suite.Require().NoError(err) + + currentMetadata, err := suite.chainA.GetSimApp().ICAControllerKeeper.GetAppMetadata(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().NoError(err) + + metadata = icatypes.NewDefaultMetadata(path.EndpointA.ConnectionID, path.EndpointB.ConnectionID) + // use the same address as the previous metadata. + metadata.Address = currentMetadata.Address + + // this is the actual change to the version. + metadata.Encoding = icatypes.EncodingProto3JSON + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = string(icatypes.ModuleCdc.MustMarshalJSON(&metadata)) + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = string(icatypes.ModuleCdc.MustMarshalJSON(&metadata)) + + err = path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + counterpartyVersion = path.EndpointB.GetChannel().Version + + tc.malleate() // malleate mutates test data + + err = suite.chainA.GetSimApp().ICAControllerKeeper.OnChanUpgradeAck( + suite.chainA.GetContext(), + path.EndpointA.ChannelConfig.PortID, + path.EndpointA.ChannelID, + counterpartyVersion, + ) + + expPass := tc.expError == nil + if expPass { + suite.Require().NoError(err) + suite.Require().Equal(path.EndpointA.GetChannel().Version, counterpartyVersion) + } else { + suite.Require().ErrorIs(err, tc.expError) + } + }) + } +} diff --git a/modules/apps/27-interchain-accounts/controller/keeper/keeper.go b/modules/apps/27-interchain-accounts/controller/keeper/keeper.go index 63e606c395e..4e11ea993e7 100644 --- a/modules/apps/27-interchain-accounts/controller/keeper/keeper.go +++ b/modules/apps/27-interchain-accounts/controller/keeper/keeper.go @@ -20,6 +20,7 @@ import ( channeltypes "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" porttypes "github.com/cosmos/ibc-go/v8/modules/core/05-port/types" host "github.com/cosmos/ibc-go/v8/modules/core/24-host" + ibcerrors "github.com/cosmos/ibc-go/v8/modules/core/errors" "github.com/cosmos/ibc-go/v8/modules/core/exported" ) @@ -280,6 +281,16 @@ func (k Keeper) GetAuthority() string { return k.authority } +// getAppMetadata retrieves the interchain accounts channel metadata from the store associated with the provided portID and channelID +func (k Keeper) getAppMetadata(ctx sdk.Context, portID, channelID string) (icatypes.Metadata, error) { + appVersion, found := k.GetAppVersion(ctx, portID, channelID) + if !found { + return icatypes.Metadata{}, errorsmod.Wrapf(ibcerrors.ErrNotFound, "app version not found for port %s and channel %s", portID, channelID) + } + + return icatypes.MetadataFromVersion(appVersion) +} + // GetParams returns the current ica/controller submodule parameters. func (k Keeper) GetParams(ctx sdk.Context) types.Params { store := ctx.KVStore(k.storeKey) diff --git a/modules/apps/27-interchain-accounts/host/ibc_module.go b/modules/apps/27-interchain-accounts/host/ibc_module.go index 50efd5c9dd2..bbc68506fc4 100644 --- a/modules/apps/27-interchain-accounts/host/ibc_module.go +++ b/modules/apps/27-interchain-accounts/host/ibc_module.go @@ -20,6 +20,7 @@ import ( var ( _ porttypes.IBCModule = (*IBCModule)(nil) _ porttypes.PacketDataUnmarshaler = (*IBCModule)(nil) + _ porttypes.UpgradableModule = (*IBCModule)(nil) ) // IBCModule implements the ICS26 interface for interchain accounts host chains @@ -156,6 +157,32 @@ func (IBCModule) OnTimeoutPacket( return errorsmod.Wrap(icatypes.ErrInvalidChannelFlow, "cannot cause a packet timeout on a host channel end, a host chain does not send a packet over the channel") } +// OnChanUpgradeInit implements the IBCModule interface +func (IBCModule) OnChanUpgradeInit(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) (string, error) { + return "", errorsmod.Wrap(icatypes.ErrInvalidChannelFlow, "channel upgrade handshake must be initiated by controller chain") +} + +// OnChanUpgradeTry implements the IBCModule interface +func (im IBCModule) OnChanUpgradeTry(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, counterpartyVersion string) (string, error) { + if !im.keeper.GetParams(ctx).HostEnabled { + return "", types.ErrHostSubModuleDisabled + } + + return im.keeper.OnChanUpgradeTry(ctx, portID, channelID, order, connectionHops, counterpartyVersion) +} + +// OnChanUpgradeAck implements the IBCModule interface +func (IBCModule) OnChanUpgradeAck(ctx sdk.Context, portID, channelID, counterpartyVersion string) error { + return errorsmod.Wrap(icatypes.ErrInvalidChannelFlow, "channel upgrade handshake must be initiated by controller chain") +} + +// OnChanUpgradeOpen implements the IBCModule interface +func (IBCModule) OnChanUpgradeOpen(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) { +} + +// OnChanUpgradeRestore implements the IBCModule interface +func (IBCModule) OnChanUpgradeRestore(ctx sdk.Context, portID, channelID string) {} + // UnmarshalPacketData attempts to unmarshal the provided packet data bytes // into an InterchainAccountPacketData. This function implements the optional // PacketDataUnmarshaler interface required for ADR 008 support. diff --git a/modules/apps/27-interchain-accounts/host/ibc_module_test.go b/modules/apps/27-interchain-accounts/host/ibc_module_test.go index a5bb9381e66..f5fdde6c5c1 100644 --- a/modules/apps/27-interchain-accounts/host/ibc_module_test.go +++ b/modules/apps/27-interchain-accounts/host/ibc_module_test.go @@ -20,6 +20,7 @@ import ( feetypes "github.com/cosmos/ibc-go/v8/modules/apps/29-fee/types" clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" channeltypes "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" + porttypes "github.com/cosmos/ibc-go/v8/modules/core/05-port/types" host "github.com/cosmos/ibc-go/v8/modules/core/24-host" "github.com/cosmos/ibc-go/v8/modules/core/exported" ibctesting "github.com/cosmos/ibc-go/v8/testing" @@ -603,6 +604,74 @@ func (suite *InterchainAccountsTestSuite) TestOnTimeoutPacket() { } } +func (suite *InterchainAccountsTestSuite) TestOnChanUpgradeTry() { + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", func() {}, nil, + }, + { + "host submodule disabled", func() { + suite.chainB.GetSimApp().ICAHostKeeper.SetParams(suite.chainB.GetContext(), types.NewParams(false, []string{})) + }, types.ErrHostSubModuleDisabled, + }, + } + + for _, tc := range testCases { + tc := tc + + suite.Run(tc.name, func() { + suite.SetupTest() // reset + + path := NewICAPath(suite.chainA, suite.chainB) + suite.coordinator.SetupConnections(path) + + err := SetupICAPath(path, TestOwnerAddress) + suite.Require().NoError(err) + + interchainAccountAddr, found := suite.chainB.GetSimApp().ICAHostKeeper.GetInterchainAccountAddress(suite.chainB.GetContext(), path.EndpointB.ConnectionID, path.EndpointA.ChannelConfig.PortID) + suite.Require().True(found) + + metadata := icatypes.NewDefaultMetadata(path.EndpointA.ConnectionID, path.EndpointB.ConnectionID) + metadata.Address = interchainAccountAddr + metadata.Encoding = icatypes.EncodingProto3JSON // this is the actual change to the version + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = string(icatypes.ModuleCdc.MustMarshalJSON(&metadata)) + + err = path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + tc.malleate() // malleate mutates test data + + module, _, err := suite.chainB.App.GetIBCKeeper().PortKeeper.LookupModuleByPort(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID) + suite.Require().NoError(err) + + app, ok := suite.chainB.App.GetIBCKeeper().Router.GetRoute(module) + suite.Require().True(ok) + cbs, ok := app.(porttypes.UpgradableModule) + suite.Require().True(ok) + + version, err := cbs.OnChanUpgradeTry( + suite.chainB.GetContext(), + path.EndpointB.ChannelConfig.PortID, + path.EndpointB.ChannelID, + channeltypes.ORDERED, + []string{path.EndpointB.ConnectionID}, + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version, + ) + + if tc.expError == nil { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + suite.Require().Empty(version) + } + }) + } +} + func (suite *InterchainAccountsTestSuite) fundICAWallet(ctx sdk.Context, portID string, amount sdk.Coins) { interchainAccountAddr, found := suite.chainB.GetSimApp().ICAHostKeeper.GetInterchainAccountAddress(ctx, ibctesting.FirstConnectionID, portID) suite.Require().True(found) diff --git a/modules/apps/27-interchain-accounts/host/keeper/handshake.go b/modules/apps/27-interchain-accounts/host/keeper/handshake.go index f3a202a3bae..819abd89426 100644 --- a/modules/apps/27-interchain-accounts/host/keeper/handshake.go +++ b/modules/apps/27-interchain-accounts/host/keeper/handshake.go @@ -2,6 +2,7 @@ package keeper import ( "fmt" + "strings" errorsmod "cosmossdk.io/errors" @@ -9,7 +10,9 @@ import ( capabilitytypes "github.com/cosmos/ibc-go/modules/capability/types" icatypes "github.com/cosmos/ibc-go/v8/modules/apps/27-interchain-accounts/types" + connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" channeltypes "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" + porttypes "github.com/cosmos/ibc-go/v8/modules/core/05-port/types" host "github.com/cosmos/ibc-go/v8/modules/core/24-host" ) @@ -35,12 +38,12 @@ func (k Keeper) OnChanOpenTry( return "", errorsmod.Wrapf(icatypes.ErrInvalidHostPort, "expected %s, got %s", icatypes.HostPortID, portID) } - var metadata icatypes.Metadata - if err := icatypes.ModuleCdc.UnmarshalJSON([]byte(counterpartyVersion), &metadata); err != nil { - return "", errorsmod.Wrapf(icatypes.ErrUnknownDataType, "cannot unmarshal ICS-27 interchain accounts metadata") + metadata, err := icatypes.MetadataFromVersion(counterpartyVersion) + if err != nil { + return "", err } - if err := icatypes.ValidateHostMetadata(ctx, k.channelKeeper, connectionHops, metadata); err != nil { + if err = icatypes.ValidateHostMetadata(ctx, k.channelKeeper, connectionHops, metadata); err != nil { return "", err } @@ -67,14 +70,11 @@ func (k Keeper) OnChanOpenTry( // On the host chain the capability may only be claimed during the OnChanOpenTry // The capability being claimed in OpenInit is for a controller chain (the port is different) - if err := k.ClaimCapability(ctx, chanCap, host.ChannelCapabilityPath(portID, channelID)); err != nil { + if err = k.ClaimCapability(ctx, chanCap, host.ChannelCapabilityPath(portID, channelID)); err != nil { return "", errorsmod.Wrapf(err, "failed to claim capability for channel %s on port %s", channelID, portID) } - var ( - accAddress sdk.AccAddress - err error - ) + var accAddress sdk.AccAddress interchainAccAddr, found := k.GetInterchainAccountAddress(ctx, metadata.HostConnectionId, counterparty.PortId) if found { @@ -130,3 +130,45 @@ func (Keeper) OnChanCloseConfirm( ) error { return nil } + +// OnChanUpgradeTry performs the upgrade try step of the channel upgrade handshake. +func (k Keeper) OnChanUpgradeTry(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, counterpartyVersion string) (string, error) { + if portID != icatypes.HostPortID { + return "", errorsmod.Wrapf(porttypes.ErrInvalidPort, "expected %s, got %s", icatypes.HostPortID, portID) + } + + if strings.TrimSpace(counterpartyVersion) == "" { + return "", errorsmod.Wrap(channeltypes.ErrInvalidChannelVersion, "counterparty version cannot be empty") + } + + // support for unordered ICA channels is not implemented yet + if order != channeltypes.ORDERED { + return "", errorsmod.Wrapf(channeltypes.ErrInvalidChannelOrdering, "expected %s channel, got %s", channeltypes.ORDERED, order) + } + + metadata, err := icatypes.MetadataFromVersion(counterpartyVersion) + if err != nil { + return "", err + } + + currentMetadata, err := k.getAppMetadata(ctx, portID, channelID) + if err != nil { + return "", err + } + + if err := icatypes.ValidateHostMetadata(ctx, k.channelKeeper, connectionHops, metadata); err != nil { + return "", errorsmod.Wrap(err, "invalid metadata") + } + + // the interchain account address on the host chain + // must remain the same after the upgrade. + if currentMetadata.Address != metadata.Address { + return "", errorsmod.Wrap(icatypes.ErrInvalidAccountAddress, "interchain account address cannot be changed") + } + + if currentMetadata.HostConnectionId != connectionHops[0] { + return "", errorsmod.Wrap(connectiontypes.ErrInvalidConnectionIdentifier, "proposed connection hop must not change") + } + + return counterpartyVersion, nil +} diff --git a/modules/apps/27-interchain-accounts/host/keeper/handshake_test.go b/modules/apps/27-interchain-accounts/host/keeper/handshake_test.go index 3074faf9b8e..c14ac85a576 100644 --- a/modules/apps/27-interchain-accounts/host/keeper/handshake_test.go +++ b/modules/apps/27-interchain-accounts/host/keeper/handshake_test.go @@ -8,7 +8,9 @@ import ( capabilitytypes "github.com/cosmos/ibc-go/modules/capability/types" hosttypes "github.com/cosmos/ibc-go/v8/modules/apps/27-interchain-accounts/host/types" icatypes "github.com/cosmos/ibc-go/v8/modules/apps/27-interchain-accounts/types" + connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" channeltypes "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" + porttypes "github.com/cosmos/ibc-go/v8/modules/core/05-port/types" host "github.com/cosmos/ibc-go/v8/modules/core/24-host" ibctesting "github.com/cosmos/ibc-go/v8/testing" ) @@ -422,3 +424,141 @@ func (suite *KeeperTestSuite) TestOnChanCloseConfirm() { }) } } + +func (suite *KeeperTestSuite) TestOnChanUpgradeTry() { + var ( + path *ibctesting.Path + metadata icatypes.Metadata + order channeltypes.Order + counterpartyVersion string + ) + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + name: "failure: invalid port ID", + malleate: func() { + path.EndpointB.ChannelConfig.PortID = "invalid-port-id" + }, + expError: porttypes.ErrInvalidPort, + }, + { + name: "failure: empty counterparty version", + malleate: func() { + counterpartyVersion = "" + }, + expError: channeltypes.ErrInvalidChannelVersion, + }, + { + name: "failure: cannot parse metadata from counterparty version string", + malleate: func() { + counterpartyVersion = "invalid-version" + }, + expError: icatypes.ErrUnknownDataType, + }, + { + name: "failure: cannot decode version string from channel", + malleate: func() { + channel := path.EndpointB.GetChannel() + channel.Version = "invalid-metadata-string" + path.EndpointB.SetChannel(channel) + }, + expError: icatypes.ErrUnknownDataType, + }, + { + name: "failure: metadata encoding not supported", + malleate: func() { + metadata.Encoding = "invalid-encoding-format" + counterpartyVersion = string(icatypes.ModuleCdc.MustMarshalJSON(&metadata)) + }, + expError: icatypes.ErrInvalidCodec, + }, + { + name: "failure: interchain account address has changed", + malleate: func() { + channel := path.EndpointB.GetChannel() + metadata.Address = "invalid address" + channel.Version = string(icatypes.ModuleCdc.MustMarshalJSON(&metadata)) + path.EndpointB.SetChannel(channel) + }, + expError: icatypes.ErrInvalidAccountAddress, + }, + { + name: "failure: invalid connection identifier", + malleate: func() { + channel := path.EndpointB.GetChannel() + metadata.HostConnectionId = "invalid-connection-id" + channel.Version = string(icatypes.ModuleCdc.MustMarshalJSON(&metadata)) + path.EndpointB.SetChannel(channel) + }, + expError: connectiontypes.ErrInvalidConnectionIdentifier, + }, + { + name: "failure: invalid order", + malleate: func() { + order = channeltypes.UNORDERED + }, + expError: channeltypes.ErrInvalidChannelOrdering, + }, + } + + for _, tc := range testCases { + tc := tc + + suite.Run(tc.name, func() { + suite.SetupTest() // reset + + path = NewICAPath(suite.chainA, suite.chainB, icatypes.EncodingProtobuf) + suite.coordinator.SetupConnections(path) + + err := SetupICAPath(path, TestOwnerAddress) + suite.Require().NoError(err) + + currentMetadata, err := suite.chainB.GetSimApp().ICAHostKeeper.GetAppMetadata(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().NoError(err) + + order = channeltypes.ORDERED + metadata = icatypes.NewDefaultMetadata(path.EndpointA.ConnectionID, path.EndpointB.ConnectionID) + // use the same address as the previous metadata. + metadata.Address = currentMetadata.Address + + // this is the actual change to the version. + metadata.Encoding = icatypes.EncodingProto3JSON + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = string(icatypes.ModuleCdc.MustMarshalJSON(&metadata)) + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = string(icatypes.ModuleCdc.MustMarshalJSON(&metadata)) + + err = path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + counterpartyVersion = path.EndpointA.GetChannel().Version + + tc.malleate() // malleate mutates test data + + version, err := suite.chainB.GetSimApp().ICAHostKeeper.OnChanUpgradeTry( + suite.chainB.GetContext(), + path.EndpointB.ChannelConfig.PortID, + path.EndpointB.ChannelID, + order, + []string{path.EndpointB.ConnectionID}, + counterpartyVersion, + ) + + expPass := tc.expError == nil + if expPass { + suite.Require().NoError(err) + suite.Require().Equal(path.EndpointB.GetChannel().Version, version) + } else { + suite.Require().ErrorIs(err, tc.expError) + } + }) + } +} diff --git a/modules/apps/27-interchain-accounts/host/keeper/keeper.go b/modules/apps/27-interchain-accounts/host/keeper/keeper.go index c426c4cc0cb..be0cfc8a0b5 100644 --- a/modules/apps/27-interchain-accounts/host/keeper/keeper.go +++ b/modules/apps/27-interchain-accounts/host/keeper/keeper.go @@ -111,20 +111,14 @@ func (k Keeper) GetAppVersion(ctx sdk.Context, portID, channelID string) (string return k.ics4Wrapper.GetAppVersion(ctx, portID, channelID) } -// GetAppMetadata retrieves the interchain accounts channel metadata from the store associated with the provided portID and channelID +// getAppMetadata retrieves the interchain accounts channel metadata from the store associated with the provided portID and channelID func (k Keeper) getAppMetadata(ctx sdk.Context, portID, channelID string) (icatypes.Metadata, error) { appVersion, found := k.GetAppVersion(ctx, portID, channelID) if !found { return icatypes.Metadata{}, errorsmod.Wrapf(ibcerrors.ErrNotFound, "app version not found for port %s and channel %s", portID, channelID) } - var metadata icatypes.Metadata - if err := icatypes.ModuleCdc.UnmarshalJSON([]byte(appVersion), &metadata); err != nil { - // UnmarshalJSON errors are indeterminate and therefore are not wrapped and included in failed acks - return icatypes.Metadata{}, errorsmod.Wrapf(icatypes.ErrUnknownDataType, "cannot unmarshal ICS-27 interchain accounts metadata") - } - - return metadata, nil + return icatypes.MetadataFromVersion(appVersion) } // GetActiveChannelID retrieves the active channelID from the store keyed by the provided connectionID and portID diff --git a/modules/apps/27-interchain-accounts/types/metadata.go b/modules/apps/27-interchain-accounts/types/metadata.go index 29d1da45d42..61c077a46f0 100644 --- a/modules/apps/27-interchain-accounts/types/metadata.go +++ b/modules/apps/27-interchain-accounts/types/metadata.go @@ -54,11 +54,20 @@ func NewDefaultMetadataString(controllerConnectionID, hostConnectionID string) s return string(ModuleCdc.MustMarshalJSON(&metadata)) } +// MetadataFromVersion parses Metadata from a json encoded version string. +func MetadataFromVersion(versionString string) (Metadata, error) { + var metadata Metadata + if err := ModuleCdc.UnmarshalJSON([]byte(versionString), &metadata); err != nil { + return Metadata{}, errorsmod.Wrapf(ErrUnknownDataType, "cannot unmarshal ICS-27 interchain accounts metadata") + } + return metadata, nil +} + // IsPreviousMetadataEqual compares a metadata to a previous version string set in a channel struct. // It ensures all fields are equal except the Address string func IsPreviousMetadataEqual(previousVersion string, metadata Metadata) bool { - var previousMetadata Metadata - if err := ModuleCdc.UnmarshalJSON([]byte(previousVersion), &previousMetadata); err != nil { + previousMetadata, err := MetadataFromVersion(previousVersion) + if err != nil { return false } diff --git a/modules/apps/29-fee/ibc_middleware.go b/modules/apps/29-fee/ibc_middleware.go index 385a29ef6f2..3f993d3f334 100644 --- a/modules/apps/29-fee/ibc_middleware.go +++ b/modules/apps/29-fee/ibc_middleware.go @@ -19,6 +19,7 @@ import ( var ( _ porttypes.Middleware = (*IBCMiddleware)(nil) _ porttypes.PacketDataUnmarshaler = (*IBCMiddleware)(nil) + _ porttypes.UpgradableModule = (*IBCMiddleware)(nil) ) // IBCMiddleware implements the ICS26 callbacks for the fee middleware given the @@ -326,6 +327,129 @@ func (im IBCMiddleware) OnTimeoutPacket( return im.app.OnTimeoutPacket(ctx, packet, relayer) } +// OnChanUpgradeInit implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeInit( + ctx sdk.Context, + portID string, + channelID string, + order channeltypes.Order, + connectionHops []string, + upgradeVersion string, +) (string, error) { + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + return "", errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack") + } + + versionMetadata, err := types.MetadataFromVersion(upgradeVersion) + if err != nil { + // since it is valid for fee version to not be specified, the upgrade version may be for a middleware + // or application further down in the stack. Thus, passthrough to next middleware or application in callstack. + return cbs.OnChanUpgradeInit(ctx, portID, channelID, order, connectionHops, upgradeVersion) + } + + if versionMetadata.FeeVersion != types.Version { + return "", errorsmod.Wrapf(types.ErrInvalidVersion, "expected %s, got %s", types.Version, versionMetadata.FeeVersion) + } + + appVersion, err := cbs.OnChanUpgradeInit(ctx, portID, channelID, order, connectionHops, versionMetadata.AppVersion) + if err != nil { + return "", err + } + + versionMetadata.AppVersion = appVersion + versionBz, err := types.ModuleCdc.MarshalJSON(&versionMetadata) + if err != nil { + return "", err + } + + return string(versionBz), nil +} + +// OnChanUpgradeTry implement s the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeTry(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, counterpartyVersion string) (string, error) { + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + return "", errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack") + } + + versionMetadata, err := types.MetadataFromVersion(counterpartyVersion) + if err != nil { + // since it is valid for fee version to not be specified, the counterparty upgrade version may be for a middleware + // or application further down in the stack. Thus, passthrough to next middleware or application in callstack. + return cbs.OnChanUpgradeTry(ctx, portID, channelID, order, connectionHops, counterpartyVersion) + } + + if versionMetadata.FeeVersion != types.Version { + return "", errorsmod.Wrapf(types.ErrInvalidVersion, "expected %s, got %s", types.Version, versionMetadata.FeeVersion) + } + + appVersion, err := cbs.OnChanUpgradeTry(ctx, portID, channelID, order, connectionHops, versionMetadata.AppVersion) + if err != nil { + return "", err + } + + versionMetadata.AppVersion = appVersion + versionBz, err := types.ModuleCdc.MarshalJSON(&versionMetadata) + if err != nil { + return "", err + } + + return string(versionBz), nil +} + +// OnChanUpgradeAck implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeAck(ctx sdk.Context, portID, channelID, counterpartyVersion string) error { + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + return errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack") + } + + versionMetadata, err := types.MetadataFromVersion(counterpartyVersion) + if err != nil { + // since it is valid for fee version to not be specified, the counterparty upgrade version may be for a middleware + // or application further down in the stack. Thus, passthrough to next middleware or application in callstack. + return cbs.OnChanUpgradeAck(ctx, portID, channelID, counterpartyVersion) + } + + if versionMetadata.FeeVersion != types.Version { + return errorsmod.Wrapf(types.ErrInvalidVersion, "expected counterparty fee version: %s, got: %s", types.Version, versionMetadata.FeeVersion) + } + + // call underlying app's OnChanUpgradeAck callback with the counterparty app version. + return cbs.OnChanUpgradeAck(ctx, portID, channelID, versionMetadata.AppVersion) +} + +// OnChanUpgradeOpen implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeOpen(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) { + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + panic(errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack")) + } + + versionMetadata, err := types.MetadataFromVersion(version) + if err != nil { + // set fee disabled and passthrough to the next middleware or application in callstack. + im.keeper.DeleteFeeEnabled(ctx, portID, channelID) + cbs.OnChanUpgradeOpen(ctx, portID, channelID, order, connectionHops, version) + return + } + + // set fee enabled and passthrough to the next middleware of application in callstack. + im.keeper.SetFeeEnabled(ctx, portID, channelID) + cbs.OnChanUpgradeOpen(ctx, portID, channelID, order, connectionHops, versionMetadata.AppVersion) +} + +// OnChanUpgradeRestore implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeRestore(ctx sdk.Context, portID, channelID string) { + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + panic(errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack")) + } + + cbs.OnChanUpgradeRestore(ctx, portID, channelID) +} + // SendPacket implements the ICS4 Wrapper interface func (im IBCMiddleware) SendPacket( ctx sdk.Context, diff --git a/modules/apps/29-fee/ibc_middleware_test.go b/modules/apps/29-fee/ibc_middleware_test.go index 941bce02dd4..d1a857a0ca7 100644 --- a/modules/apps/29-fee/ibc_middleware_test.go +++ b/modules/apps/29-fee/ibc_middleware_test.go @@ -256,7 +256,7 @@ func (suite *FeeTestSuite) TestOnChanOpenAck() { }, { "invalid version fails to unmarshal metadata", - "invalid-version", + ibctesting.InvalidID, func(suite *FeeTestSuite) {}, false, }, @@ -1009,6 +1009,441 @@ func (suite *FeeTestSuite) TestOnTimeoutPacket() { } } +func (suite *FeeTestSuite) TestOnChanUpgradeInit() { + var path *ibctesting.Path + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + "success with downgraded version", + func() { + // create a new path using a fee enabled channel and downgrade it to disable fees + path = ibctesting.NewPath(suite.chainA, suite.chainB) + + mockFeeVersion := string(types.ModuleCdc.MustMarshalJSON(&types.Metadata{FeeVersion: types.Version, AppVersion: ibcmock.Version})) + path.EndpointA.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointB.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointA.ChannelConfig.Version = mockFeeVersion + path.EndpointB.ChannelConfig.Version = mockFeeVersion + + upgradeVersion := ibcmock.Version + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + + suite.coordinator.Setup(path) + }, + nil, + }, + { + "invalid upgrade version", + func() { + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = ibctesting.InvalidID + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = ibctesting.InvalidID + + suite.chainA.GetSimApp().FeeMockModule.IBCApp.OnChanUpgradeInit = func(_ sdk.Context, _, _ string, _ channeltypes.Order, _ []string, _ string) (string, error) { + // intentionally force the error here so we can assert that a passthrough occurs when fees should not be enabled for this channel + return "", ibcmock.MockApplicationCallbackError + } + }, + ibcmock.MockApplicationCallbackError, + }, + { + "invalid fee version", + func() { + upgradeVersion := string(types.ModuleCdc.MustMarshalJSON(&types.Metadata{FeeVersion: ibctesting.InvalidID, AppVersion: ibcmock.Version})) + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + }, + types.ErrInvalidVersion, + }, + { + "underlying app callback returns error", + func() { + suite.chainA.GetSimApp().FeeMockModule.IBCApp.OnChanUpgradeInit = func(_ sdk.Context, _, _ string, _ channeltypes.Order, _ []string, _ string) (string, error) { + return "", ibcmock.MockApplicationCallbackError + } + }, + ibcmock.MockApplicationCallbackError, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + + // configure the initial path to create an unincentivized mock channel + path.EndpointA.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointB.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointA.ChannelConfig.Version = ibcmock.Version + path.EndpointB.ChannelConfig.Version = ibcmock.Version + + suite.coordinator.Setup(path) + + // configure the channel upgrade version to enabled ics29 fee middleware + upgradeVersion := string(types.ModuleCdc.MustMarshalJSON(&types.Metadata{FeeVersion: types.Version, AppVersion: ibcmock.Version})) + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + + tc.malleate() + + err := path.EndpointA.ChanUpgradeInit() + + expPass := tc.expError == nil + if expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + suite.Require().Contains(err.Error(), tc.expError.Error()) + } + }) + } +} + +func (suite *FeeTestSuite) TestOnChanUpgradeTry() { + var path *ibctesting.Path + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + "success disable fees", + func() { + // create a new path using a fee enabled channel and downgrade it to disable fees + path = ibctesting.NewPath(suite.chainA, suite.chainB) + + mockFeeVersion := string(types.ModuleCdc.MustMarshalJSON(&types.Metadata{FeeVersion: types.Version, AppVersion: ibcmock.Version})) + path.EndpointA.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointB.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointA.ChannelConfig.Version = mockFeeVersion + path.EndpointB.ChannelConfig.Version = mockFeeVersion + + upgradeVersion := ibcmock.Version + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + + suite.coordinator.Setup(path) + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + }, + nil, + }, + { + "invalid upgrade version", + func() { + counterpartyUpgrade := path.EndpointA.GetChannelUpgrade() + counterpartyUpgrade.Fields.Version = ibctesting.InvalidID + path.EndpointA.SetChannelUpgrade(counterpartyUpgrade) + + suite.coordinator.CommitBlock(suite.chainA) + + // intentionally force the error here so we can assert that a passthrough occurs when fees should not be enabled for this channel + suite.chainB.GetSimApp().FeeMockModule.IBCApp.OnChanUpgradeTry = func(_ sdk.Context, _, _ string, _ channeltypes.Order, _ []string, _ string) (string, error) { + return "", ibcmock.MockApplicationCallbackError + } + }, + ibcmock.MockApplicationCallbackError, + }, + { + "invalid fee version", + func() { + upgradeVersion := string(types.ModuleCdc.MustMarshalJSON(&types.Metadata{FeeVersion: ibctesting.InvalidID, AppVersion: ibcmock.Version})) + + counterpartyUpgrade := path.EndpointA.GetChannelUpgrade() + counterpartyUpgrade.Fields.Version = upgradeVersion + path.EndpointA.SetChannelUpgrade(counterpartyUpgrade) + + suite.coordinator.CommitBlock(suite.chainA) + }, + types.ErrInvalidVersion, + }, + { + "underlying app callback returns error", + func() { + suite.chainB.GetSimApp().FeeMockModule.IBCApp.OnChanUpgradeTry = func(_ sdk.Context, _, _ string, _ channeltypes.Order, _ []string, _ string) (string, error) { + return "", ibcmock.MockApplicationCallbackError + } + }, + ibcmock.MockApplicationCallbackError, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + + // configure the initial path to create an unincentivized mock channel + path.EndpointA.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointB.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointA.ChannelConfig.Version = ibcmock.Version + path.EndpointB.ChannelConfig.Version = ibcmock.Version + + suite.coordinator.Setup(path) + + // configure the channel upgrade version to enabled ics29 fee middleware + upgradeVersion := string(types.ModuleCdc.MustMarshalJSON(&types.Metadata{FeeVersion: types.Version, AppVersion: ibcmock.Version})) + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + tc.malleate() + + err = path.EndpointB.ChanUpgradeTry() + + expPass := tc.expError == nil + if expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + suite.Require().Contains(err.Error(), tc.expError.Error()) + } + }) + } +} + +func (suite *FeeTestSuite) TestOnChanUpgradeAck() { + var path *ibctesting.Path + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + "success with fee middleware disabled", + func() { + suite.chainA.GetSimApp().IBCFeeKeeper.DeleteFeeEnabled(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + }, + nil, + }, + { + "invalid upgrade version", + func() { + counterpartyUpgrade := path.EndpointB.GetChannelUpgrade() + counterpartyUpgrade.Fields.Version = ibctesting.InvalidID + path.EndpointB.SetChannelUpgrade(counterpartyUpgrade) + + suite.coordinator.CommitBlock(suite.chainB) + + suite.chainA.GetSimApp().FeeMockModule.IBCApp.OnChanUpgradeAck = func(_ sdk.Context, _, _, _ string) error { + return types.ErrInvalidVersion + } + }, + types.ErrInvalidVersion, + }, + { + "invalid fee version", + func() { + upgradeVersion := string(types.ModuleCdc.MustMarshalJSON(&types.Metadata{FeeVersion: ibctesting.InvalidID, AppVersion: ibcmock.Version})) + + counterpartyUpgrade := path.EndpointB.GetChannelUpgrade() + counterpartyUpgrade.Fields.Version = upgradeVersion + path.EndpointB.SetChannelUpgrade(counterpartyUpgrade) + + suite.coordinator.CommitBlock(suite.chainB) + }, + types.ErrInvalidVersion, + }, + { + "underlying app callback returns error", + func() { + suite.chainA.GetSimApp().FeeMockModule.IBCApp.OnChanUpgradeAck = func(_ sdk.Context, _, _, _ string) error { + return ibcmock.MockApplicationCallbackError + } + }, + ibcmock.MockApplicationCallbackError, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + + // configure the initial path to create an unincentivized mock channel + path.EndpointA.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointB.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointA.ChannelConfig.Version = ibcmock.Version + path.EndpointB.ChannelConfig.Version = ibcmock.Version + + suite.coordinator.Setup(path) + + // configure the channel upgrade version to enabled ics29 fee middleware + upgradeVersion := string(types.ModuleCdc.MustMarshalJSON(&types.Metadata{FeeVersion: types.Version, AppVersion: ibcmock.Version})) + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + tc.malleate() + + counterpartyUpgrade := path.EndpointB.GetChannelUpgrade() + + module, _, err := suite.chainA.App.GetIBCKeeper().PortKeeper.LookupModuleByPort(suite.chainA.GetContext(), ibctesting.MockFeePort) + suite.Require().NoError(err) + + app, ok := suite.chainA.App.GetIBCKeeper().Router.GetRoute(module) + suite.Require().True(ok) + + cbs, ok := app.(porttypes.UpgradableModule) + suite.Require().True(ok) + + err = cbs.OnChanUpgradeAck(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, counterpartyUpgrade.Fields.Version) + + expPass := tc.expError == nil + if expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + suite.Require().ErrorIs(err, tc.expError) + } + }) + } +} + +func (suite *FeeTestSuite) TestOnChanUpgradeOpen() { + var path *ibctesting.Path + + testCases := []struct { + name string + malleate func() + expFeeEnabled bool + }{ + { + "success: enable fees", + func() { + // Assert in callback that correct upgrade information is passed + suite.chainA.GetSimApp().FeeMockModule.IBCApp.OnChanUpgradeOpen = func(_ sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) { + suite.Require().Equal(path.EndpointA.ChannelConfig.PortID, portID) + suite.Require().Equal(path.EndpointA.ChannelID, channelID) + suite.Require().Equal(channeltypes.UNORDERED, order) + suite.Require().Equal([]string{path.EndpointA.ConnectionID}, connectionHops) + suite.Require().Equal(ibcmock.Version, version) + } + }, + true, + }, + { + "success: disable fees", + func() { + // create a new path using a fee enabled channel and downgrade it to disable fees + path = ibctesting.NewPath(suite.chainA, suite.chainB) + + mockFeeVersion := &types.Metadata{FeeVersion: types.Version, AppVersion: ibcmock.Version} + mockFeeVersionBz := string(types.ModuleCdc.MustMarshalJSON(mockFeeVersion)) + path.EndpointA.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointB.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointA.ChannelConfig.Version = mockFeeVersionBz + path.EndpointB.ChannelConfig.Version = mockFeeVersionBz + + upgradeVersion := ibcmock.Version + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + + suite.coordinator.Setup(path) + + // Assert in callback that correct version is passed + suite.chainA.GetSimApp().FeeMockModule.IBCApp.OnChanUpgradeOpen = func(_ sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) { + suite.Require().Equal(path.EndpointA.ChannelConfig.PortID, portID) + suite.Require().Equal(path.EndpointA.ChannelID, channelID) + suite.Require().Equal(channeltypes.UNORDERED, order) + suite.Require().Equal([]string{path.EndpointA.ConnectionID}, connectionHops) + suite.Require().Equal(mockFeeVersion.AppVersion, version) + } + }, + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + + // configure the initial path to create an unincentivized mock channel + path.EndpointA.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointB.ChannelConfig.PortID = ibctesting.MockFeePort + path.EndpointA.ChannelConfig.Version = ibcmock.Version + path.EndpointB.ChannelConfig.Version = ibcmock.Version + + suite.coordinator.Setup(path) + + // configure the channel upgrade version to enabled ics29 fee middleware + upgradeVersion := string(types.ModuleCdc.MustMarshalJSON(&types.Metadata{FeeVersion: types.Version, AppVersion: ibcmock.Version})) + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + + tc.malleate() + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeConfirm() + suite.Require().NoError(err) + + module, _, err := suite.chainA.App.GetIBCKeeper().PortKeeper.LookupModuleByPort(suite.chainA.GetContext(), ibctesting.MockFeePort) + suite.Require().NoError(err) + + app, ok := suite.chainA.App.GetIBCKeeper().Router.GetRoute(module) + suite.Require().True(ok) + + cbs, ok := app.(porttypes.UpgradableModule) + suite.Require().True(ok) + + upgrade := path.EndpointA.GetChannelUpgrade() + cbs.OnChanUpgradeOpen(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, upgrade.Fields.Ordering, upgrade.Fields.ConnectionHops, upgrade.Fields.Version) + + isFeeEnabled := suite.chainA.GetSimApp().IBCFeeKeeper.IsFeeEnabled(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + if tc.expFeeEnabled { + suite.Require().True(isFeeEnabled) + } else { + suite.Require().False(isFeeEnabled) + } + }) + } +} + func (suite *FeeTestSuite) TestGetAppVersion() { var ( portID string diff --git a/modules/apps/29-fee/transfer_test.go b/modules/apps/29-fee/transfer_test.go index 287a5cad1b8..d283cdc1713 100644 --- a/modules/apps/29-fee/transfer_test.go +++ b/modules/apps/29-fee/transfer_test.go @@ -68,3 +68,98 @@ func (suite *FeeTestSuite) TestFeeTransfer() { fee.AckFee.Add(fee.TimeoutFee...), // ack fee paid, timeout fee refunded sdk.NewCoins(suite.chainA.GetSimApp().BankKeeper.GetBalance(suite.chainA.GetContext(), suite.chainA.SenderAccount.GetAddress(), ibctesting.TestCoin.Denom)).Sub(originalChainASenderAccountBalance[0])) } + +func (suite *FeeTestSuite) TestTransferFeeUpgrade() { + var path *ibctesting.Path + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + + // configure the initial path to create a regular transfer channel + path.EndpointA.ChannelConfig.PortID = transfertypes.PortID + path.EndpointB.ChannelConfig.PortID = transfertypes.PortID + path.EndpointA.ChannelConfig.Version = transfertypes.Version + path.EndpointB.ChannelConfig.Version = transfertypes.Version + + suite.coordinator.Setup(path) + + // configure the channel upgrade to upgrade to an incentivized fee enabled transfer channel + upgradeVersion := string(types.ModuleCdc.MustMarshalJSON(&types.Metadata{FeeVersion: types.Version, AppVersion: transfertypes.Version})) + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = upgradeVersion + + tc.malleate() + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeConfirm() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeOpen() + suite.Require().NoError(err) + + expPass := tc.expError == nil + if expPass { + channelA := path.EndpointA.GetChannel() + suite.Require().Equal(upgradeVersion, channelA.Version) + + channelB := path.EndpointB.GetChannel() + suite.Require().Equal(upgradeVersion, channelB.Version) + + isFeeEnabled := suite.chainA.GetSimApp().IBCFeeKeeper.IsFeeEnabled(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(isFeeEnabled) + + isFeeEnabled = suite.chainB.GetSimApp().IBCFeeKeeper.IsFeeEnabled(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(isFeeEnabled) + + fee := types.NewFee(defaultRecvFee, defaultAckFee, defaultTimeoutFee) + msgs := []sdk.Msg{ + types.NewMsgPayPacketFee(fee, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, suite.chainA.SenderAccount.GetAddress().String(), nil), + transfertypes.NewMsgTransfer(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, ibctesting.TestCoin, suite.chainA.SenderAccount.GetAddress().String(), suite.chainB.SenderAccount.GetAddress().String(), clienttypes.NewHeight(1, 100), 0, ""), + } + + res, err := suite.chainA.SendMsgs(msgs...) + suite.Require().NoError(err) // message committed + + feeEscrowAddr := suite.chainA.GetSimApp().AccountKeeper.GetModuleAddress(types.ModuleName) + escrowBalance := suite.chainA.GetSimApp().BankKeeper.GetBalance(suite.chainA.GetContext(), feeEscrowAddr, sdk.DefaultBondDenom) + suite.Require().Equal(escrowBalance.Amount, fee.Total().AmountOf(sdk.DefaultBondDenom)) + + packet, err := ibctesting.ParsePacketFromEvents(res.Events) + suite.Require().NoError(err) + + err = path.RelayPacket(packet) + suite.Require().NoError(err) // relay committed + + escrowBalance = suite.chainA.GetSimApp().BankKeeper.GetBalance(suite.chainA.GetContext(), feeEscrowAddr, sdk.DefaultBondDenom) + suite.Require().True(escrowBalance.IsZero()) + } else { + suite.Require().Error(err) + suite.Require().ErrorIs(err, tc.expError) + } + }) + } +} diff --git a/modules/apps/callbacks/ibc_middleware.go b/modules/apps/callbacks/ibc_middleware.go index c7438df23be..5c1b2875656 100644 --- a/modules/apps/callbacks/ibc_middleware.go +++ b/modules/apps/callbacks/ibc_middleware.go @@ -20,6 +20,7 @@ import ( var ( _ porttypes.Middleware = (*IBCMiddleware)(nil) _ porttypes.PacketDataUnmarshaler = (*IBCMiddleware)(nil) + _ porttypes.UpgradableModule = (*IBCMiddleware)(nil) ) // IBCMiddleware implements the ICS26 callbacks for the ibc-callbacks middleware given @@ -363,6 +364,56 @@ func (im IBCMiddleware) OnChanCloseConfirm(ctx sdk.Context, portID, channelID st return im.app.OnChanCloseConfirm(ctx, portID, channelID) } +// OnChanUpgradeInit implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeInit(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) (string, error) { + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + return "", errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack") + } + + return cbs.OnChanUpgradeInit(ctx, portID, channelID, order, connectionHops, version) +} + +// OnChanUpgradeTry implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeTry(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, counterpartyVersion string) (string, error) { + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + return "", errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack") + } + + return cbs.OnChanUpgradeTry(ctx, portID, channelID, order, connectionHops, counterpartyVersion) +} + +// OnChanUpgradeAck implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeAck(ctx sdk.Context, portID, channelID, counterpartyVersion string) error { + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + return errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack") + } + + return cbs.OnChanUpgradeAck(ctx, portID, channelID, counterpartyVersion) +} + +// OnChanUpgradeOpen implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeOpen(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) { + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + panic(errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack")) + } + + cbs.OnChanUpgradeOpen(ctx, portID, channelID, order, connectionHops, version) +} + +// OnChanUpgradeRestore implements the IBCModule interface +func (im IBCMiddleware) OnChanUpgradeRestore(ctx sdk.Context, portID, channelID string) { + cbs, ok := im.app.(porttypes.UpgradableModule) + if !ok { + panic(errorsmod.Wrap(porttypes.ErrInvalidRoute, "upgrade route not found to module in application callstack")) + } + + cbs.OnChanUpgradeRestore(ctx, portID, channelID) +} + // GetAppVersion implements the ICS4Wrapper interface. Callbacks has no version, // so the call is deferred to the underlying application. func (im IBCMiddleware) GetAppVersion(ctx sdk.Context, portID, channelID string) (string, bool) { diff --git a/modules/apps/transfer/ibc_module.go b/modules/apps/transfer/ibc_module.go index db1fc0d5b0a..02ed5fc9d61 100644 --- a/modules/apps/transfer/ibc_module.go +++ b/modules/apps/transfer/ibc_module.go @@ -22,6 +22,7 @@ import ( var ( _ porttypes.IBCModule = (*IBCModule)(nil) _ porttypes.PacketDataUnmarshaler = (*IBCModule)(nil) + _ porttypes.UpgradableModule = (*IBCModule)(nil) ) // IBCModule implements the ICS26 interface for transfer given the transfer keeper. @@ -307,6 +308,48 @@ func (im IBCModule) OnTimeoutPacket( return nil } +// OnChanUpgradeInit implements the IBCModule interface +func (im IBCModule) OnChanUpgradeInit(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, upgradeVersion string) (string, error) { + if err := ValidateTransferChannelParams(ctx, im.keeper, order, portID, channelID); err != nil { + return "", err + } + + if upgradeVersion != types.Version { + return "", errorsmod.Wrapf(types.ErrInvalidVersion, "expected %s, got %s", types.Version, upgradeVersion) + } + + return upgradeVersion, nil +} + +// OnChanUpgradeTry implements the IBCModule interface +func (im IBCModule) OnChanUpgradeTry(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, counterpartyVersion string) (string, error) { + if err := ValidateTransferChannelParams(ctx, im.keeper, order, portID, channelID); err != nil { + return "", err + } + + if counterpartyVersion != types.Version { + return "", errorsmod.Wrapf(types.ErrInvalidVersion, "expected %s, got %s", types.Version, counterpartyVersion) + } + + return counterpartyVersion, nil +} + +// OnChanUpgradeAck implements the IBCModule interface +func (IBCModule) OnChanUpgradeAck(ctx sdk.Context, portID, channelID, counterpartyVersion string) error { + if counterpartyVersion != types.Version { + return errorsmod.Wrapf(types.ErrInvalidVersion, "expected %s, got %s", types.Version, counterpartyVersion) + } + + return nil +} + +// OnChanUpgradeOpen implements the IBCModule interface +func (IBCModule) OnChanUpgradeOpen(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) { +} + +// OnChanUpgradeRestore implements the IBCModule interface +func (IBCModule) OnChanUpgradeRestore(ctx sdk.Context, portID, channelID string) {} + // UnmarshalPacketData attempts to unmarshal the provided packet data bytes // into a FungibleTokenPacketData. This function implements the optional // PacketDataUnmarshaler interface required for ADR 008 support. diff --git a/modules/apps/transfer/ibc_module_test.go b/modules/apps/transfer/ibc_module_test.go index 81255a32670..6d7df22781a 100644 --- a/modules/apps/transfer/ibc_module_test.go +++ b/modules/apps/transfer/ibc_module_test.go @@ -9,7 +9,9 @@ import ( capabilitytypes "github.com/cosmos/ibc-go/modules/capability/types" "github.com/cosmos/ibc-go/v8/modules/apps/transfer" "github.com/cosmos/ibc-go/v8/modules/apps/transfer/types" + connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" channeltypes "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" + porttypes "github.com/cosmos/ibc-go/v8/modules/core/05-port/types" host "github.com/cosmos/ibc-go/v8/modules/core/24-host" ibctesting "github.com/cosmos/ibc-go/v8/testing" ) @@ -242,6 +244,224 @@ func (suite *TransferTestSuite) TestOnChanOpenAck() { } } +func (suite *TransferTestSuite) TestOnChanUpgradeInit() { + var path *ibctesting.Path + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, // successful happy path for a standalone transfer app is swapping out the underlying connection + nil, + }, + { + "invalid upgrade connection", + func() { + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.ConnectionHops = []string{"connection-100"} + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.ConnectionHops = []string{"connection-100"} + }, + connectiontypes.ErrConnectionNotFound, + }, + { + "invalid upgrade ordering", + func() { + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Ordering = channeltypes.ORDERED + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Ordering = channeltypes.ORDERED + }, + channeltypes.ErrInvalidChannelOrdering, + }, + { + "invalid upgrade version", + func() { + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = ibctesting.InvalidID + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = ibctesting.InvalidID + }, + types.ErrInvalidVersion, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = NewTransferPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + // configure the channel upgrade to modify the underlying connection + upgradePath := ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.SetupConnections(upgradePath) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.ConnectionHops = []string{upgradePath.EndpointA.ConnectionID} + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.ConnectionHops = []string{upgradePath.EndpointB.ConnectionID} + + tc.malleate() + + err := path.EndpointA.ChanUpgradeInit() + + expPass := tc.expError == nil + if expPass { + suite.Require().NoError(err) + upgrade := path.EndpointA.GetChannelUpgrade() + suite.Require().Equal(upgradePath.EndpointA.ConnectionID, upgrade.Fields.ConnectionHops[0]) + } else { + suite.Require().Error(err) + suite.Require().Contains(err.Error(), tc.expError.Error()) + } + }) + } +} + +func (suite *TransferTestSuite) TestOnChanUpgradeTry() { + var ( + counterpartyUpgrade channeltypes.Upgrade + path *ibctesting.Path + ) + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, // successful happy path for a standalone transfer app is swapping out the underlying connection + nil, + }, + { + "invalid upgrade ordering", + func() { + counterpartyUpgrade.Fields.Ordering = channeltypes.ORDERED + }, + channeltypes.ErrInvalidChannelOrdering, + }, + { + "invalid upgrade version", + func() { + counterpartyUpgrade.Fields.Version = ibctesting.InvalidID + }, + types.ErrInvalidVersion, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = NewTransferPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + // configure the channel upgrade to modify the underlying connection + upgradePath := ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.SetupConnections(upgradePath) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.ConnectionHops = []string{upgradePath.EndpointA.ConnectionID} + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.ConnectionHops = []string{upgradePath.EndpointB.ConnectionID} + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + counterpartyUpgrade = path.EndpointA.GetChannelUpgrade() + + tc.malleate() + + module, _, err := suite.chainB.App.GetIBCKeeper().PortKeeper.LookupModuleByPort(suite.chainB.GetContext(), types.PortID) + suite.Require().NoError(err) + + app, ok := suite.chainB.App.GetIBCKeeper().Router.GetRoute(module) + suite.Require().True(ok) + + cbs, ok := app.(porttypes.UpgradableModule) + suite.Require().True(ok) + + version, err := cbs.OnChanUpgradeTry( + suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, + counterpartyUpgrade.Fields.Ordering, counterpartyUpgrade.Fields.ConnectionHops, counterpartyUpgrade.Fields.Version, + ) + + expPass := tc.expError == nil + if expPass { + suite.Require().NoError(err) + suite.Require().Equal(types.Version, version) + } else { + suite.Require().Error(err) + suite.Require().Contains(err.Error(), tc.expError.Error()) + } + }) + } +} + +func (suite *TransferTestSuite) TestOnChanUpgradeAck() { + var path *ibctesting.Path + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, // successful happy path for a standalone transfer app is swapping out the underlying connection + nil, + }, + { + "invalid upgrade version", + func() { + path.EndpointB.ChannelConfig.Version = ibctesting.InvalidID + }, + types.ErrInvalidVersion, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = NewTransferPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + // configure the channel upgrade to modify the underlying connection + upgradePath := ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.SetupConnections(upgradePath) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.ConnectionHops = []string{upgradePath.EndpointA.ConnectionID} + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.ConnectionHops = []string{upgradePath.EndpointB.ConnectionID} + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + tc.malleate() + + module, _, err := suite.chainA.App.GetIBCKeeper().PortKeeper.LookupModuleByPort(suite.chainA.GetContext(), types.PortID) + suite.Require().NoError(err) + + app, ok := suite.chainA.App.GetIBCKeeper().Router.GetRoute(module) + suite.Require().True(ok) + + cbs, ok := app.(porttypes.UpgradableModule) + suite.Require().True(ok) + + err = cbs.OnChanUpgradeAck(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.Version) + + expPass := tc.expError == nil + if expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + suite.Require().Contains(err.Error(), tc.expError.Error()) + } + }) + } +} + func (suite *TransferTestSuite) TestPacketDataUnmarshalerInterface() { var ( sender = sdk.AccAddress(secp256k1.GenPrivKey().PubKey().Address()).String() diff --git a/modules/apps/transfer/transfer_test.go b/modules/apps/transfer/transfer_test.go index 647a1b83665..08f5bc80026 100644 --- a/modules/apps/transfer/transfer_test.go +++ b/modules/apps/transfer/transfer_test.go @@ -32,6 +32,16 @@ func (suite *TransferTestSuite) SetupTest() { suite.chainC = suite.coordinator.GetChain(ibctesting.GetChainID(3)) } +func NewTransferPath(chainA, chainB *ibctesting.TestChain) *ibctesting.Path { + path := ibctesting.NewPath(chainA, chainB) + path.EndpointA.ChannelConfig.PortID = ibctesting.TransferPort + path.EndpointB.ChannelConfig.PortID = ibctesting.TransferPort + path.EndpointA.ChannelConfig.Version = types.Version + path.EndpointB.ChannelConfig.Version = types.Version + + return path +} + // Constructs the following sends based on the established channels/connections // 1 - from chainA to chainB // 2 - from chainB to chainC diff --git a/modules/apps/transfer/types/authz.pb.go b/modules/apps/transfer/types/authz.pb.go index 22298d64b63..4d015c3c58a 100644 --- a/modules/apps/transfer/types/authz.pb.go +++ b/modules/apps/transfer/types/authz.pb.go @@ -36,8 +36,8 @@ type Allocation struct { SpendLimit github_com_cosmos_cosmos_sdk_types.Coins `protobuf:"bytes,3,rep,name=spend_limit,json=spendLimit,proto3,castrepeated=github.com/cosmos/cosmos-sdk/types.Coins" json:"spend_limit"` // allow list of receivers, an empty allow list permits any receiver address AllowList []string `protobuf:"bytes,4,rep,name=allow_list,json=allowList,proto3" json:"allow_list,omitempty"` - // allow list of packet data keys, an empty list. - // an empty list prohibits all packet data keys; a list only with "*" permits any packet data key + // allow list of packet data keys, an empty list prohibits all packet data keys; + // a list only with "*" permits any packet data key AllowedPacketData []string `protobuf:"bytes,5,rep,name=allowed_packet_data,json=allowedPacketData,proto3" json:"allowed_packet_data,omitempty"` } diff --git a/modules/core/02-client/keeper/grpc_query_test.go b/modules/core/02-client/keeper/grpc_query_test.go index 231d000a257..40c6dcf3178 100644 --- a/modules/core/02-client/keeper/grpc_query_test.go +++ b/modules/core/02-client/keeper/grpc_query_test.go @@ -164,7 +164,6 @@ func (suite *KeeperTestSuite) TestQueryClientStates() { suite.Run(fmt.Sprintf("Case %s", tc.msg), func() { suite.SetupTest() // reset - tc.malleate() ctx := suite.chainA.GetContext() diff --git a/modules/core/03-connection/keeper/verify.go b/modules/core/03-connection/keeper/verify.go index 1c4d160d368..a4d4ea33683 100644 --- a/modules/core/03-connection/keeper/verify.go +++ b/modules/core/03-connection/keeper/verify.go @@ -366,6 +366,127 @@ func (k Keeper) VerifyNextSequenceRecv( return nil } +// VerifyChannelUpgradeError verifies a proof of the provided upgrade error receipt. +func (k Keeper) VerifyChannelUpgradeError( + ctx sdk.Context, + connection exported.ConnectionI, + proofHeight exported.Height, + proofErrorReceipt []byte, + portID, + channelID string, + errorReceipt channeltypes.ErrorReceipt, +) error { + clientID := connection.GetClientID() + clientState, clientStore, err := k.getClientStateAndVerificationStore(ctx, clientID) + if err != nil { + return err + } + + if status := k.clientKeeper.GetClientStatus(ctx, clientState, clientID); status != exported.Active { + return errorsmod.Wrapf(clienttypes.ErrClientNotActive, "client (%s) status is %s", clientID, status) + } + + merklePath := commitmenttypes.NewMerklePath(host.ChannelUpgradeErrorPath(portID, channelID)) + merklePath, err = commitmenttypes.ApplyPrefix(connection.GetCounterparty().GetPrefix(), merklePath) + if err != nil { + return err + } + + bz, err := k.cdc.Marshal(&errorReceipt) + if err != nil { + return err + } + + if err := clientState.VerifyMembership( + ctx, clientStore, k.cdc, proofHeight, + 0, 0, // skip delay period checks for non-packet processing verification + proofErrorReceipt, merklePath, bz, + ); err != nil { + return errorsmod.Wrapf(err, "failed upgrade error receipt verification for client (%s)", clientID) + } + + return nil +} + +// VerifyChannelUpgradeErrorAbsence verifies a proof of the absence of a +// channel upgrade error. +func (k Keeper) VerifyChannelUpgradeErrorAbsence( + ctx sdk.Context, + connection exported.ConnectionI, + proofHeight exported.Height, + proofErrorReceiptAbsence []byte, + portID, + channelID string, +) error { + clientID := connection.GetClientID() + clientState, clientStore, err := k.getClientStateAndVerificationStore(ctx, clientID) + if err != nil { + return err + } + + if status := k.clientKeeper.GetClientStatus(ctx, clientState, clientID); status != exported.Active { + return errorsmod.Wrapf(clienttypes.ErrClientNotActive, "client (%s) status is %s", clientID, status) + } + + merklePath := commitmenttypes.NewMerklePath(host.ChannelUpgradeErrorPath(portID, channelID)) + merklePath, err = commitmenttypes.ApplyPrefix(connection.GetCounterparty().GetPrefix(), merklePath) + if err != nil { + return err + } + + if err := clientState.VerifyNonMembership( + ctx, clientStore, k.cdc, proofHeight, + 0, 0, + proofErrorReceiptAbsence, merklePath, + ); err != nil { + return errorsmod.Wrapf(err, "failed upgrade error receipt absence verification for client (%s)", clientID) + } + + return nil +} + +// VerifyChannelUpgrade verifies the proof that a particular proposed upgrade has been stored in the upgrade path. +func (k Keeper) VerifyChannelUpgrade( + ctx sdk.Context, + connection exported.ConnectionI, + proofHeight exported.Height, + proofUpgrade []byte, + portID, + channelID string, + upgrade channeltypes.Upgrade, +) error { + clientID := connection.GetClientID() + clientState, clientStore, err := k.getClientStateAndVerificationStore(ctx, clientID) + if err != nil { + return err + } + + if status := k.clientKeeper.GetClientStatus(ctx, clientState, clientID); status != exported.Active { + return errorsmod.Wrapf(clienttypes.ErrClientNotActive, "client (%s) status is %s", clientID, status) + } + + merklePath := commitmenttypes.NewMerklePath(host.ChannelUpgradePath(portID, channelID)) + merklePath, err = commitmenttypes.ApplyPrefix(connection.GetCounterparty().GetPrefix(), merklePath) + if err != nil { + return err + } + + bz, err := k.cdc.Marshal(&upgrade) + if err != nil { + return err + } + + if err := clientState.VerifyMembership( + ctx, clientStore, k.cdc, proofHeight, + 0, 0, // skip delay period checks for non-packet processing verification + proofUpgrade, merklePath, bz, + ); err != nil { + return errorsmod.Wrapf(err, "failed upgrade verification for client (%s) on channel (%s)", clientID, channelID) + } + + return nil +} + // getBlockDelay calculates the block delay period from the time delay of the connection // and the maximum expected time per block. func (k Keeper) getBlockDelay(ctx sdk.Context, connection exported.ConnectionI) uint64 { diff --git a/modules/core/03-connection/keeper/verify_test.go b/modules/core/03-connection/keeper/verify_test.go index c42fb0e044b..f97bd12690c 100644 --- a/modules/core/03-connection/keeper/verify_test.go +++ b/modules/core/03-connection/keeper/verify_test.go @@ -681,6 +681,239 @@ func (suite *KeeperTestSuite) TestVerifyNextSequenceRecv() { } } +func (suite *KeeperTestSuite) TestVerifyUpgradeErrorReceipt() { + var ( + path *ibctesting.Path + upgradeError *channeltypes.UpgradeError + ) + + cases := []struct { + name string + malleate func() + expPass bool + }{ + { + name: "success", + malleate: func() {}, + expPass: true, + }, + { + name: "fails when client state is frozen", + malleate: func() { + clientState := path.EndpointB.GetClientState().(*ibctm.ClientState) + clientState.FrozenHeight = clienttypes.NewHeight(0, 1) + path.EndpointB.SetClientState(clientState) + }, + expPass: false, + }, + { + name: "fails with bad client id", + malleate: func() { + connection := path.EndpointB.GetConnection() + connection.ClientId = ibctesting.InvalidID + path.EndpointB.SetConnection(connection) + }, + expPass: false, + }, + { + name: "verification fails when the key does not exist", + malleate: func() { + suite.chainA.DeleteKey(host.ChannelUpgradeErrorKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + suite.coordinator.CommitBlock(suite.chainA) + }, + expPass: false, + }, + { + name: "verification fails when message differs", + malleate: func() { + originalSequence := upgradeError.GetErrorReceipt().Sequence + upgradeError = channeltypes.NewUpgradeError(originalSequence, fmt.Errorf("new error")) + }, + expPass: false, + }, + } + + for _, tc := range cases { + tc := tc + + suite.Run(tc.name, func() { + suite.SetupTest() // reset + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + upgradeError = channeltypes.NewUpgradeError(1, channeltypes.ErrInvalidChannel) + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.SetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, upgradeError.GetErrorReceipt()) + + suite.chainA.Coordinator.CommitBlock(suite.chainA) + suite.Require().NoError(path.EndpointB.UpdateClient()) + + tc.malleate() + + upgradeErrorReceiptKey := host.ChannelUpgradeErrorKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proof, proofHeight := suite.chainA.QueryProof(upgradeErrorReceiptKey) + + err := suite.chainB.GetSimApp().IBCKeeper.ConnectionKeeper.VerifyChannelUpgradeError(suite.chainB.GetContext(), path.EndpointB.GetConnection(), proofHeight, proof, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, upgradeError.GetErrorReceipt()) + + if tc.expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *KeeperTestSuite) TestVerifyUpgradeErrorReceiptAbsence() { + var path *ibctesting.Path + + cases := []struct { + name string + malleate func() + expPass bool + }{ + { + name: "success", + malleate: func() {}, + expPass: true, + }, + { + name: "fails when client state is frozen", + malleate: func() { + clientState := path.EndpointB.GetClientState().(*ibctm.ClientState) + clientState.FrozenHeight = clienttypes.NewHeight(0, 1) + path.EndpointB.SetClientState(clientState) + }, + expPass: false, + }, + { + name: "fails with bad client id", + malleate: func() { + connection := path.EndpointB.GetConnection() + connection.ClientId = ibctesting.InvalidID + path.EndpointB.SetConnection(connection) + }, + expPass: false, + }, + { + name: "verification fails when the key exists", + malleate: func() { + errorReceipt := channeltypes.NewUpgradeError(1, channeltypes.ErrInvalidChannel).GetErrorReceipt() + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.SetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, errorReceipt) + suite.chainA.Coordinator.CommitBlock(suite.chainA) + suite.Require().NoError(path.EndpointB.UpdateClient()) + }, + expPass: false, + }, + } + + for _, tc := range cases { + tc := tc + + suite.Run(tc.name, func() { + suite.SetupTest() // reset + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + suite.chainA.Coordinator.CommitBlock(suite.chainA) + suite.Require().NoError(path.EndpointB.UpdateClient()) + + tc.malleate() + + upgradeErrorReceiptKey := host.ChannelUpgradeErrorKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proof, proofHeight := suite.chainA.QueryProof(upgradeErrorReceiptKey) + + err := suite.chainB.GetSimApp().IBCKeeper.ConnectionKeeper.VerifyChannelUpgradeErrorAbsence(suite.chainB.GetContext(), path.EndpointB.GetConnection(), proofHeight, proof, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + + if tc.expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *KeeperTestSuite) TestVerifyUpgrade() { + var ( + path *ibctesting.Path + upgrade channeltypes.Upgrade + ) + + cases := []struct { + name string + malleate func() + expPass bool + }{ + { + name: "success", + malleate: func() {}, + expPass: true, + }, + { + name: "fails when client state is frozen", + malleate: func() { + clientState := path.EndpointB.GetClientState().(*ibctm.ClientState) + clientState.FrozenHeight = clienttypes.NewHeight(0, 1) + path.EndpointB.SetClientState(clientState) + }, + expPass: false, + }, + { + name: "fails with bad client id", + malleate: func() { + connection := path.EndpointB.GetConnection() + connection.ClientId = ibctesting.InvalidID + path.EndpointB.SetConnection(connection) + }, + expPass: false, + }, + { + name: "fails when the upgrade field is different", + malleate: func() { + upgrade.Fields.Ordering = channeltypes.ORDERED + }, + expPass: false, + }, + } + + for _, tc := range cases { + tc := tc + + suite.Run(tc.name, func() { + suite.SetupTest() // reset + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + upgrade = channeltypes.NewUpgrade( + channeltypes.NewUpgradeFields(channeltypes.UNORDERED, []string{path.EndpointA.ConnectionID}, "v1.0.0"), + channeltypes.NewTimeout(clienttypes.ZeroHeight(), 100000), + 0, + ) + + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.SetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, upgrade) + + suite.chainA.Coordinator.CommitBlock(suite.chainA) + suite.Require().NoError(path.EndpointB.UpdateClient()) + + tc.malleate() + + channelUpgradeKey := host.ChannelUpgradeKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proof, proofHeight := suite.chainA.QueryProof(channelUpgradeKey) + + err := suite.chainB.GetSimApp().IBCKeeper.ConnectionKeeper.VerifyChannelUpgrade(suite.chainB.GetContext(), path.EndpointB.GetConnection(), proofHeight, proof, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, upgrade) + + if tc.expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + } + }) + } +} + func malleateHeight(height exported.Height, diff uint64) exported.Height { return clienttypes.NewHeight(height.GetRevisionNumber(), height.GetRevisionHeight()+diff) } diff --git a/modules/core/04-channel/client/cli/cli.go b/modules/core/04-channel/client/cli/cli.go index 0a2ed6313a7..450688502e1 100644 --- a/modules/core/04-channel/client/cli/cli.go +++ b/modules/core/04-channel/client/cli/cli.go @@ -31,6 +31,9 @@ func GetQueryCmd() *cobra.Command { GetCmdQueryUnreceivedAcks(), GetCmdQueryNextSequenceReceive(), GetCmdQueryNextSequenceSend(), + GetCmdQueryUpgradeError(), + GetCmdQueryUpgrade(), + GetCmdChannelParams(), ) return queryCmd diff --git a/modules/core/04-channel/client/cli/query.go b/modules/core/04-channel/client/cli/query.go index 21866263a15..c97ee430a14 100644 --- a/modules/core/04-channel/client/cli/query.go +++ b/modules/core/04-channel/client/cli/query.go @@ -491,3 +491,96 @@ func GetCmdQueryNextSequenceSend() *cobra.Command { return cmd } + +// GetCmdQueryUpgradeError defines the command to query for the error receipt associated with an upgrade +func GetCmdQueryUpgradeError() *cobra.Command { + cmd := &cobra.Command{ + Use: "upgrade-error [port-id] [channel-id]", + Short: "Query the upgrade error", + Long: "Query the upgrade error for a given channel", + Example: fmt.Sprintf( + "%s query %s %s upgrade-error [port-id] [channel-id]", version.AppName, ibcexported.ModuleName, types.SubModuleName, + ), + Args: cobra.ExactArgs(2), + RunE: func(cmd *cobra.Command, args []string) error { + clientCtx, err := client.GetClientQueryContext(cmd) + if err != nil { + return err + } + portID := args[0] + channelID := args[1] + prove, _ := cmd.Flags().GetBool(flags.FlagProve) + + errRes, err := utils.QueryUpgradeError(clientCtx, portID, channelID, prove) + if err != nil { + return err + } + + clientCtx = clientCtx.WithHeight(int64(errRes.ProofHeight.RevisionHeight)) + return clientCtx.PrintProto(errRes) + }, + } + cmd.Flags().Bool(flags.FlagProve, true, "show proofs for the query results") + flags.AddQueryFlagsToCmd(cmd) + + return cmd +} + +// GetCmdQueryUpgrade defines the command to query for the upgrade associated with a port and channel id +func GetCmdQueryUpgrade() *cobra.Command { + cmd := &cobra.Command{ + Use: "upgrade [port-id] [channel-id]", + Short: "Query the upgrade", + Long: "Query the upgrade for a given channel", + Example: fmt.Sprintf( + "%s query %s %s upgrade [port-id] [channel-id]", version.AppName, ibcexported.ModuleName, types.SubModuleName, + ), + Args: cobra.ExactArgs(2), + RunE: func(cmd *cobra.Command, args []string) error { + clientCtx, err := client.GetClientQueryContext(cmd) + if err != nil { + return err + } + portID := args[0] + channelID := args[1] + prove, _ := cmd.Flags().GetBool(flags.FlagProve) + + upgrade, err := utils.QueryUpgrade(clientCtx, portID, channelID, prove) + if err != nil { + return err + } + + clientCtx = clientCtx.WithHeight(int64(upgrade.ProofHeight.RevisionHeight)) + return clientCtx.PrintProto(upgrade) + }, + } + cmd.Flags().Bool(flags.FlagProve, false, "show proofs for the query results") + flags.AddQueryFlagsToCmd(cmd) + + return cmd +} + +// GetCmdChannelParams returns the command handler for ibc channel parameter querying. +func GetCmdChannelParams() *cobra.Command { + cmd := &cobra.Command{ + Use: "params", + Short: "Query the current ibc channel parameters", + Long: "Query the current ibc channel parameters", + Args: cobra.NoArgs, + Example: fmt.Sprintf("%s query %s %s params", version.AppName, ibcexported.ModuleName, types.SubModuleName), + RunE: func(cmd *cobra.Command, _ []string) error { + clientCtx, err := client.GetClientQueryContext(cmd) + if err != nil { + return err + } + queryClient := types.NewQueryClient(clientCtx) + + res, _ := queryClient.ChannelParams(cmd.Context(), &types.QueryChannelParamsRequest{}) + return clientCtx.PrintProto(res.Params) + }, + } + + flags.AddQueryFlagsToCmd(cmd) + + return cmd +} diff --git a/modules/core/04-channel/client/utils/utils.go b/modules/core/04-channel/client/utils/utils.go index 6fd5a1b1cfc..c5118aa0011 100644 --- a/modules/core/04-channel/client/utils/utils.go +++ b/modules/core/04-channel/client/utils/utils.go @@ -231,6 +231,92 @@ func queryNextSequenceSendABCI(clientCtx client.Context, portID, channelID strin return types.NewQueryNextSequenceSendResponse(sequence, proofBz, proofHeight), nil } +// QueryUpgradeError returns the upgrade error. +// If prove is true, it performs an ABCI store query in order to retrieve the merkle proof. Otherwise, +// it uses the gRPC query client. +func QueryUpgradeError( + clientCtx client.Context, portID, channelID string, prove bool, +) (*types.QueryUpgradeErrorResponse, error) { + if prove { + return queryUpgradeErrorABCI(clientCtx, portID, channelID) + } + + queryClient := types.NewQueryClient(clientCtx) + req := &types.QueryUpgradeErrorRequest{ + PortId: portID, + ChannelId: channelID, + } + + return queryClient.UpgradeError(context.Background(), req) +} + +// QueryUpgrade returns the upgrade. +// If prove is true, it performs an ABCI store query in order to retrieve the merkle proof. Otherwise, +// it uses the gRPC query client. +func QueryUpgrade( + clientCtx client.Context, portID, channelID string, prove bool, +) (*types.QueryUpgradeResponse, error) { + if prove { + return queryUpgradeABCI(clientCtx, portID, channelID) + } + + queryClient := types.NewQueryClient(clientCtx) + req := &types.QueryUpgradeRequest{ + PortId: portID, + ChannelId: channelID, + } + + return queryClient.Upgrade(context.Background(), req) +} + +// queryUpgradeErrorABCI queries the upgrade error from the store. +func queryUpgradeErrorABCI(clientCtx client.Context, portID, channelID string) (*types.QueryUpgradeErrorResponse, error) { + key := host.ChannelUpgradeErrorKey(portID, channelID) + + value, proofBz, proofHeight, err := ibcclient.QueryTendermintProof(clientCtx, key) + if err != nil { + return nil, err + } + + // check if upgrade error exists + if len(value) == 0 { + return nil, errorsmod.Wrapf(types.ErrUpgradeErrorNotFound, "portID (%s), channelID (%s)", portID, channelID) + } + + cdc := codec.NewProtoCodec(clientCtx.InterfaceRegistry) + + var receipt types.ErrorReceipt + if err := cdc.Unmarshal(value, &receipt); err != nil { + return nil, err + } + + return types.NewQueryUpgradeErrorResponse(receipt, proofBz, proofHeight), nil +} + +// queryUpgradeABCI queries the upgrade from the store. +func queryUpgradeABCI(clientCtx client.Context, portID, channelID string) (*types.QueryUpgradeResponse, error) { + key := host.ChannelUpgradeKey(portID, channelID) + + value, proofBz, proofHeight, err := ibcclient.QueryTendermintProof(clientCtx, key) + if err != nil { + return nil, err + } + + // check if upgrade exists + if len(value) == 0 { + return nil, errorsmod.Wrapf(types.ErrUpgradeErrorNotFound, "portID (%s), channelID (%s)", portID, channelID) + } + + cdc := codec.NewProtoCodec(clientCtx.InterfaceRegistry) + + var upgrade types.Upgrade + if err := cdc.Unmarshal(value, &upgrade); err != nil { + return nil, err + } + + return types.NewQueryUpgradeResponse(upgrade, proofBz, proofHeight), nil +} + // QueryPacketCommitment returns a packet commitment. // If prove is true, it performs an ABCI store query in order to retrieve the merkle proof. Otherwise, // it uses the gRPC query client. diff --git a/modules/core/04-channel/genesis.go b/modules/core/04-channel/genesis.go index 48680d962cd..42481e558c1 100644 --- a/modules/core/04-channel/genesis.go +++ b/modules/core/04-channel/genesis.go @@ -1,6 +1,8 @@ package channel import ( + "fmt" + sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/ibc-go/v8/modules/core/04-channel/keeper" @@ -10,6 +12,10 @@ import ( // InitGenesis initializes the ibc channel submodule's state from a provided genesis // state. func InitGenesis(ctx sdk.Context, k keeper.Keeper, gs types.GenesisState) { + if err := gs.Params.Validate(); err != nil { + panic(fmt.Sprintf("invalid ibc channel genesis state parameters: %v", err)) + } + k.SetParams(ctx, gs.Params) for _, channel := range gs.Channels { ch := types.NewChannel(channel.State, channel.Ordering, channel.Counterparty, channel.ConnectionHops, channel.Version) k.SetChannel(ctx, channel.PortId, channel.ChannelId, ch) @@ -46,5 +52,6 @@ func ExportGenesis(ctx sdk.Context, k keeper.Keeper) types.GenesisState { RecvSequences: k.GetAllPacketRecvSeqs(ctx), AckSequences: k.GetAllPacketAckSeqs(ctx), NextChannelSequence: k.GetNextChannelSequence(ctx), + Params: k.GetParams(ctx), } } diff --git a/modules/core/04-channel/keeper/events.go b/modules/core/04-channel/keeper/events.go index 3d86db32d9f..ff277a463bd 100644 --- a/modules/core/04-channel/keeper/events.go +++ b/modules/core/04-channel/keeper/events.go @@ -270,3 +270,187 @@ func emitChannelClosedEvent(ctx sdk.Context, packet exported.PacketI, channel ty ), }) } + +// EmitChannelUpgradeInitEvent emits a channel upgrade init event +func EmitChannelUpgradeInitEvent(ctx sdk.Context, portID string, channelID string, currentChannel types.Channel, upgrade types.Upgrade) { + ctx.EventManager().EmitEvents(sdk.Events{ + sdk.NewEvent( + types.EventTypeChannelUpgradeInit, + sdk.NewAttribute(types.AttributeKeyPortID, portID), + sdk.NewAttribute(types.AttributeKeyChannelID, channelID), + sdk.NewAttribute(types.AttributeCounterpartyPortID, currentChannel.Counterparty.PortId), + sdk.NewAttribute(types.AttributeCounterpartyChannelID, currentChannel.Counterparty.ChannelId), + sdk.NewAttribute(types.AttributeKeyUpgradeConnectionHops, upgrade.Fields.ConnectionHops[0]), + sdk.NewAttribute(types.AttributeKeyUpgradeVersion, upgrade.Fields.Version), + sdk.NewAttribute(types.AttributeKeyUpgradeOrdering, upgrade.Fields.Ordering.String()), + sdk.NewAttribute(types.AttributeKeyUpgradeSequence, fmt.Sprintf("%d", currentChannel.UpgradeSequence)), + ), + sdk.NewEvent( + sdk.EventTypeMessage, + sdk.NewAttribute(sdk.AttributeKeyModule, types.AttributeValueCategory), + ), + }) +} + +// EmitChannelUpgradeTryEvent emits a channel upgrade try event +func EmitChannelUpgradeTryEvent(ctx sdk.Context, portID string, channelID string, currentChannel types.Channel, upgrade types.Upgrade) { + ctx.EventManager().EmitEvents(sdk.Events{ + sdk.NewEvent( + types.EventTypeChannelUpgradeTry, + sdk.NewAttribute(types.AttributeKeyPortID, portID), + sdk.NewAttribute(types.AttributeKeyChannelID, channelID), + sdk.NewAttribute(types.AttributeCounterpartyPortID, currentChannel.Counterparty.PortId), + sdk.NewAttribute(types.AttributeCounterpartyChannelID, currentChannel.Counterparty.ChannelId), + sdk.NewAttribute(types.AttributeKeyUpgradeConnectionHops, upgrade.Fields.ConnectionHops[0]), + sdk.NewAttribute(types.AttributeKeyUpgradeVersion, upgrade.Fields.Version), + sdk.NewAttribute(types.AttributeKeyUpgradeOrdering, upgrade.Fields.Ordering.String()), + sdk.NewAttribute(types.AttributeKeyUpgradeSequence, fmt.Sprintf("%d", currentChannel.UpgradeSequence)), + ), + sdk.NewEvent( + sdk.EventTypeMessage, + sdk.NewAttribute(sdk.AttributeKeyModule, types.AttributeValueCategory), + ), + }) +} + +// EmitChannelUpgradeAckEvent emits a channel upgrade ack event +func EmitChannelUpgradeAckEvent(ctx sdk.Context, portID string, channelID string, currentChannel types.Channel, upgrade types.Upgrade) { + ctx.EventManager().EmitEvents(sdk.Events{ + sdk.NewEvent( + types.EventTypeChannelUpgradeAck, + sdk.NewAttribute(types.AttributeKeyPortID, portID), + sdk.NewAttribute(types.AttributeKeyChannelID, channelID), + sdk.NewAttribute(types.AttributeCounterpartyPortID, currentChannel.Counterparty.PortId), + sdk.NewAttribute(types.AttributeCounterpartyChannelID, currentChannel.Counterparty.ChannelId), + sdk.NewAttribute(types.AttributeKeyUpgradeConnectionHops, upgrade.Fields.ConnectionHops[0]), + sdk.NewAttribute(types.AttributeKeyUpgradeVersion, upgrade.Fields.Version), + sdk.NewAttribute(types.AttributeKeyUpgradeOrdering, upgrade.Fields.Ordering.String()), + sdk.NewAttribute(types.AttributeKeyUpgradeSequence, fmt.Sprintf("%d", currentChannel.UpgradeSequence)), + ), + sdk.NewEvent( + sdk.EventTypeMessage, + sdk.NewAttribute(sdk.AttributeKeyModule, types.AttributeValueCategory), + ), + }) +} + +// EmitChannelUpgradeConfirmEvent emits a channel upgrade confirm event +func EmitChannelUpgradeConfirmEvent(ctx sdk.Context, portID, channelID string, currentChannel types.Channel) { + ctx.EventManager().EmitEvents(sdk.Events{ + sdk.NewEvent( + types.EventTypeChannelUpgradeConfirm, + sdk.NewAttribute(types.AttributeKeyPortID, portID), + sdk.NewAttribute(types.AttributeKeyChannelID, channelID), + sdk.NewAttribute(types.AttributeKeyChannelState, currentChannel.State.String()), + sdk.NewAttribute(types.AttributeCounterpartyPortID, currentChannel.Counterparty.PortId), + sdk.NewAttribute(types.AttributeCounterpartyChannelID, currentChannel.Counterparty.ChannelId), + sdk.NewAttribute(types.AttributeKeyUpgradeSequence, fmt.Sprintf("%d", currentChannel.UpgradeSequence)), + ), + sdk.NewEvent( + sdk.EventTypeMessage, + sdk.NewAttribute(sdk.AttributeKeyModule, types.AttributeValueCategory), + ), + }) +} + +// EmitChannelUpgradeOpenEvent emits a channel upgrade open event +func EmitChannelUpgradeOpenEvent(ctx sdk.Context, portID string, channelID string, currentChannel types.Channel) { + ctx.EventManager().EmitEvents(sdk.Events{ + sdk.NewEvent( + types.EventTypeChannelUpgradeOpen, + sdk.NewAttribute(types.AttributeKeyPortID, portID), + sdk.NewAttribute(types.AttributeKeyChannelID, channelID), + sdk.NewAttribute(types.AttributeKeyChannelState, currentChannel.State.String()), + sdk.NewAttribute(types.AttributeCounterpartyPortID, currentChannel.Counterparty.PortId), + sdk.NewAttribute(types.AttributeCounterpartyChannelID, currentChannel.Counterparty.ChannelId), + sdk.NewAttribute(types.AttributeKeyUpgradeConnectionHops, currentChannel.ConnectionHops[0]), + sdk.NewAttribute(types.AttributeKeyUpgradeVersion, currentChannel.Version), + sdk.NewAttribute(types.AttributeKeyUpgradeOrdering, currentChannel.Ordering.String()), + sdk.NewAttribute(types.AttributeKeyUpgradeSequence, fmt.Sprintf("%d", currentChannel.UpgradeSequence)), + ), + sdk.NewEvent( + sdk.EventTypeMessage, + sdk.NewAttribute(sdk.AttributeKeyModule, types.AttributeValueCategory), + ), + }) +} + +// EmitChannelUpgradeTimeoutEvent emits an upgrade timeout event. +func EmitChannelUpgradeTimeoutEvent(ctx sdk.Context, portID string, channelID string, currentChannel types.Channel, upgrade types.Upgrade) { + ctx.EventManager().EmitEvents(sdk.Events{ + sdk.NewEvent( + types.EventTypeChannelUpgradeTimeout, + sdk.NewAttribute(types.AttributeKeyPortID, portID), + sdk.NewAttribute(types.AttributeKeyChannelID, channelID), + sdk.NewAttribute(types.AttributeCounterpartyPortID, currentChannel.Counterparty.PortId), + sdk.NewAttribute(types.AttributeCounterpartyChannelID, currentChannel.Counterparty.ChannelId), + sdk.NewAttribute(types.AttributeKeyUpgradeConnectionHops, upgrade.Fields.ConnectionHops[0]), + sdk.NewAttribute(types.AttributeKeyUpgradeVersion, upgrade.Fields.Version), + sdk.NewAttribute(types.AttributeKeyUpgradeOrdering, upgrade.Fields.Ordering.String()), + sdk.NewAttribute(types.AttributeKeyUpgradeTimeout, upgrade.Timeout.String()), + sdk.NewAttribute(types.AttributeKeyUpgradeSequence, fmt.Sprintf("%d", currentChannel.UpgradeSequence)), + ), + sdk.NewEvent( + sdk.EventTypeMessage, + sdk.NewAttribute(sdk.AttributeKeyModule, types.AttributeValueCategory), + ), + }) +} + +// EmitErrorReceiptEvent emits an error receipt event +func EmitErrorReceiptEvent(ctx sdk.Context, portID string, channelID string, currentChannel types.Channel, err error) { + ctx.EventManager().EmitEvents(sdk.Events{ + sdk.NewEvent( + types.EventTypeChannelUpgradeError, + sdk.NewAttribute(types.AttributeKeyPortID, portID), + sdk.NewAttribute(types.AttributeKeyChannelID, channelID), + sdk.NewAttribute(types.AttributeCounterpartyPortID, currentChannel.Counterparty.PortId), + sdk.NewAttribute(types.AttributeCounterpartyChannelID, currentChannel.Counterparty.ChannelId), + sdk.NewAttribute(types.AttributeKeyUpgradeSequence, fmt.Sprintf("%d", currentChannel.UpgradeSequence)), + sdk.NewAttribute(types.AttributeKeyUpgradeErrorReceipt, err.Error()), + ), + sdk.NewEvent( + sdk.EventTypeMessage, + sdk.NewAttribute(sdk.AttributeKeyModule, types.AttributeValueCategory), + ), + }) +} + +// EmitChannelUpgradeCancelEvent emits an upgraded cancelled event. +func EmitChannelUpgradeCancelEvent(ctx sdk.Context, portID string, channelID string, currentChannel types.Channel, upgrade types.Upgrade) { + ctx.EventManager().EmitEvents(sdk.Events{ + sdk.NewEvent( + types.EventTypeChannelUpgradeCancel, + sdk.NewAttribute(types.AttributeKeyPortID, portID), + sdk.NewAttribute(types.AttributeKeyChannelID, channelID), + sdk.NewAttribute(types.AttributeCounterpartyPortID, currentChannel.Counterparty.PortId), + sdk.NewAttribute(types.AttributeCounterpartyChannelID, currentChannel.Counterparty.ChannelId), + sdk.NewAttribute(types.AttributeKeyUpgradeConnectionHops, upgrade.Fields.ConnectionHops[0]), + sdk.NewAttribute(types.AttributeKeyUpgradeVersion, upgrade.Fields.Version), + sdk.NewAttribute(types.AttributeKeyUpgradeOrdering, upgrade.Fields.Ordering.String()), + sdk.NewAttribute(types.AttributeKeyUpgradeSequence, fmt.Sprintf("%d", currentChannel.UpgradeSequence)), + ), + sdk.NewEvent( + sdk.EventTypeMessage, + sdk.NewAttribute(sdk.AttributeKeyModule, types.AttributeValueCategory), + ), + }) +} + +// emitChannelFlushCompleteEvents emits an flushing event. +func emitChannelFlushCompleteEvent(ctx sdk.Context, portID string, channelID string, currentChannel types.Channel) { + ctx.EventManager().EmitEvents(sdk.Events{ + sdk.NewEvent( + types.EventTypeChannelFlushComplete, + sdk.NewAttribute(types.AttributeKeyPortID, portID), + sdk.NewAttribute(types.AttributeKeyChannelID, channelID), + sdk.NewAttribute(types.AttributeCounterpartyPortID, currentChannel.Counterparty.PortId), + sdk.NewAttribute(types.AttributeCounterpartyChannelID, currentChannel.Counterparty.ChannelId), + sdk.NewAttribute(types.AttributeKeyChannelState, currentChannel.State.String()), + ), + sdk.NewEvent( + sdk.EventTypeMessage, + sdk.NewAttribute(sdk.AttributeKeyModule, types.AttributeValueCategory), + ), + }) +} diff --git a/modules/core/04-channel/keeper/export_test.go b/modules/core/04-channel/keeper/export_test.go new file mode 100644 index 00000000000..21fad92d9dd --- /dev/null +++ b/modules/core/04-channel/keeper/export_test.go @@ -0,0 +1,36 @@ +package keeper + +/* + This file is to allow for unexported functions to be accessible to the testing package. +*/ + +import ( + sdk "github.com/cosmos/cosmos-sdk/types" + + "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" +) + +// StartFlushing is a wrapper around startFlushing to allow the function to be directly called in tests. +func (k Keeper) StartFlushing(ctx sdk.Context, portID, channelID string, upgrade *types.Upgrade) error { + return k.startFlushing(ctx, portID, channelID, upgrade) +} + +// ValidateSelfUpgradeFields is a wrapper around validateSelfUpgradeFields to allow the function to be directly called in tests. +func (k Keeper) ValidateSelfUpgradeFields(ctx sdk.Context, proposedUpgrade types.UpgradeFields, currentChannel types.Channel) error { + return k.validateSelfUpgradeFields(ctx, proposedUpgrade, currentChannel) +} + +// CheckForUpgradeCompatibility is a wrapper around checkForUpgradeCompatibility to allow the function to be directly called in tests. +func (k Keeper) CheckForUpgradeCompatibility(ctx sdk.Context, upgradeFields, counterpartyUpgradeFields types.UpgradeFields) error { + return k.checkForUpgradeCompatibility(ctx, upgradeFields, counterpartyUpgradeFields) +} + +// SyncUpgradeSequence is a wrapper around syncUpgradeSequence to allow the function to be directly called in tests. +func (k Keeper) SyncUpgradeSequence(ctx sdk.Context, portID, channelID string, channel types.Channel, counterpartyUpgradeSequence uint64) error { + return k.syncUpgradeSequence(ctx, portID, channelID, channel, counterpartyUpgradeSequence) +} + +// WriteErrorReceipt is a wrapper around writeErrorReceipt to allow the function to be directly called in tests. +func (k Keeper) WriteErrorReceipt(ctx sdk.Context, portID, channelID string, upgradeError *types.UpgradeError) { + k.writeErrorReceipt(ctx, portID, channelID, upgradeError) +} diff --git a/modules/core/04-channel/keeper/grpc_query.go b/modules/core/04-channel/keeper/grpc_query.go index 1802b2f4a1e..130edbc9614 100644 --- a/modules/core/04-channel/keeper/grpc_query.go +++ b/modules/core/04-channel/keeper/grpc_query.go @@ -566,6 +566,78 @@ func (k Keeper) NextSequenceSend(c context.Context, req *types.QueryNextSequence return types.NewQueryNextSequenceSendResponse(sequence, nil, selfHeight), nil } +// UpgradeErrorReceipt implements the Query/UpgradeErrorReceipt gRPC method +func (k Keeper) UpgradeErrorReceipt(c context.Context, req *types.QueryUpgradeErrorRequest) (*types.QueryUpgradeErrorResponse, error) { + if req == nil { + return nil, status.Error(codes.InvalidArgument, "empty request") + } + + if err := validategRPCRequest(req.PortId, req.ChannelId); err != nil { + return nil, err + } + + ctx := sdk.UnwrapSDKContext(c) + found := k.HasChannel(ctx, req.PortId, req.ChannelId) + if !found { + return nil, status.Error( + codes.NotFound, + errorsmod.Wrapf(types.ErrChannelNotFound, "port-id: %s, channel-id %s", req.PortId, req.ChannelId).Error(), + ) + } + + receipt, found := k.GetUpgradeErrorReceipt(ctx, req.PortId, req.ChannelId) + if !found { + return nil, status.Error( + codes.NotFound, + errorsmod.Wrapf(types.ErrUpgradeErrorNotFound, "port-id %s, channel-id %s", req.PortId, req.ChannelId).Error(), + ) + } + + selfHeight := clienttypes.GetSelfHeight(ctx) + return types.NewQueryUpgradeErrorResponse(receipt, nil, selfHeight), nil +} + +// Upgrade implements the Query/UpgradeSequence gRPC method +func (k Keeper) Upgrade(c context.Context, req *types.QueryUpgradeRequest) (*types.QueryUpgradeResponse, error) { + if req == nil { + return nil, status.Error(codes.InvalidArgument, "empty request") + } + + if err := validategRPCRequest(req.PortId, req.ChannelId); err != nil { + return nil, err + } + + ctx := sdk.UnwrapSDKContext(c) + found := k.HasChannel(ctx, req.PortId, req.ChannelId) + if !found { + return nil, status.Error( + codes.NotFound, + errorsmod.Wrapf(types.ErrChannelNotFound, "port-id: %s, channel-id %s", req.PortId, req.ChannelId).Error(), + ) + } + + upgrade, found := k.GetUpgrade(ctx, req.PortId, req.ChannelId) + if !found { + return nil, status.Error( + codes.NotFound, + errorsmod.Wrapf(types.ErrUpgradeNotFound, "port-id: %s, channel-id %s", req.PortId, req.ChannelId).Error(), + ) + } + + selfHeight := clienttypes.GetSelfHeight(ctx) + return types.NewQueryUpgradeResponse(upgrade, nil, selfHeight), nil +} + +// ChannelParams implements the Query/ChannelParams gRPC method. +func (k Keeper) ChannelParams(c context.Context, req *types.QueryChannelParamsRequest) (*types.QueryChannelParamsResponse, error) { + ctx := sdk.UnwrapSDKContext(c) + params := k.GetParams(ctx) + + return &types.QueryChannelParamsResponse{ + Params: ¶ms, + }, nil +} + func validategRPCRequest(portID, channelID string) error { if err := host.PortIdentifierValidator(portID); err != nil { return status.Error(codes.InvalidArgument, err.Error()) diff --git a/modules/core/04-channel/keeper/grpc_query_test.go b/modules/core/04-channel/keeper/grpc_query_test.go index 6603c972dc2..12ff1fbabbd 100644 --- a/modules/core/04-channel/keeper/grpc_query_test.go +++ b/modules/core/04-channel/keeper/grpc_query_test.go @@ -8,8 +8,10 @@ import ( clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" + host "github.com/cosmos/ibc-go/v8/modules/core/24-host" "github.com/cosmos/ibc-go/v8/modules/core/exported" ibctesting "github.com/cosmos/ibc-go/v8/testing" + "github.com/cosmos/ibc-go/v8/testing/mock" ) const doesnotexist = "doesnotexist" @@ -1701,3 +1703,195 @@ func (suite *KeeperTestSuite) TestQueryNextSequenceSend() { }) } } + +func (suite *KeeperTestSuite) TestQueryUpgradeError() { + var ( + req *types.QueryUpgradeErrorRequest + upgradeErr *types.UpgradeError + ) + + testCases := []struct { + msg string + malleate func() + expPass bool + }{ + { + "empty request", + func() { + req = nil + }, + false, + }, + { + "invalid port ID", + func() { + req = &types.QueryUpgradeErrorRequest{ + PortId: "", + ChannelId: "test-channel-id", + } + }, + false, + }, + { + "invalid channel ID", + func() { + req = &types.QueryUpgradeErrorRequest{ + PortId: "test-port-id", + ChannelId: "", + } + }, + false, + }, + { + "channel not found", + func() { + req = &types.QueryUpgradeErrorRequest{ + PortId: "test-port-id", + ChannelId: "test-channel-id", + } + }, + false, + }, + { + "success", + func() { + path := ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + upgradeErr = types.NewUpgradeError(uint64(1), fmt.Errorf("test error")) + suite.chainA.App.GetIBCKeeper().ChannelKeeper.SetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, upgradeErr.GetErrorReceipt()) + + req = &types.QueryUpgradeErrorRequest{ + PortId: path.EndpointA.ChannelConfig.PortID, + ChannelId: path.EndpointA.ChannelID, + } + }, + true, + }, + } + + for _, tc := range testCases { + suite.Run(fmt.Sprintf("Case %s", tc.msg), func() { + suite.SetupTest() // reset + + tc.malleate() + + ctx := suite.chainA.GetContext() + res, err := suite.chainA.QueryServer.UpgradeError(ctx, req) + + if tc.expPass { + suite.Require().NoError(err) + suite.Require().NotNil(res) + suite.Require().Equal(upgradeErr.GetErrorReceipt(), res.ErrorReceipt) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *KeeperTestSuite) TestQueryUpgrade() { + var ( + req *types.QueryUpgradeRequest + expectedUpgrade types.Upgrade + ) + + testCases := []struct { + msg string + malleate func() + expPass bool + }{ + { + "empty request", + func() { + req = nil + }, + false, + }, + { + "invalid port ID", + func() { + req = &types.QueryUpgradeRequest{ + PortId: "", + ChannelId: "test-channel-id", + } + }, + false, + }, + { + "invalid channel ID", + func() { + req = &types.QueryUpgradeRequest{ + PortId: "test-port-id", + ChannelId: "", + } + }, + false, + }, + { + "channel not found", + func() { + req = &types.QueryUpgradeRequest{ + PortId: "test-port-id", + ChannelId: "test-channel-id", + } + }, + false, + }, + { + "upgrade not found", + func() { + storeKey := suite.chainA.GetSimApp().GetKey(exported.StoreKey) + kvStore := suite.chainA.GetContext().KVStore(storeKey) + kvStore.Delete(host.ChannelUpgradeKey(req.PortId, req.ChannelId)) + }, + false, + }, + { + "success", + func() { + }, + true, + }, + } + + for _, tc := range testCases { + suite.Run(fmt.Sprintf("Case %s", tc.msg), func() { + suite.SetupTest() // reset + path := ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + expectedUpgrade = types.NewUpgrade( + types.NewUpgradeFields(types.UNORDERED, []string{ibctesting.FirstConnectionID}, mock.Version), + types.NewTimeout(clienttypes.ZeroHeight(), 1000000), + 0, + ) + + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.SetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, expectedUpgrade) + + req = &types.QueryUpgradeRequest{ + PortId: path.EndpointA.ChannelConfig.PortID, + ChannelId: path.EndpointA.ChannelID, + } + + tc.malleate() + + ctx := suite.chainA.GetContext() + res, err := suite.chainA.QueryServer.Upgrade(ctx, req) + + if tc.expPass { + suite.Require().NoError(err) + suite.Require().NotNil(res) + suite.Require().Equal(expectedUpgrade, res.Upgrade) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *KeeperTestSuite) TestQueryChannelParams() { + ctx := suite.chainA.GetContext() + expParams := types.DefaultParams() + res, _ := suite.chainA.QueryServer.ChannelParams(ctx, &types.QueryChannelParamsRequest{}) + suite.Require().Equal(&expParams, res.Params) +} diff --git a/modules/core/04-channel/keeper/handshake.go b/modules/core/04-channel/keeper/handshake.go index 30420a67270..ccb1633f98d 100644 --- a/modules/core/04-channel/keeper/handshake.go +++ b/modules/core/04-channel/keeper/handshake.go @@ -431,6 +431,7 @@ func (k Keeper) ChanCloseConfirm( chanCap *capabilitytypes.Capability, proofInit []byte, proofHeight exported.Height, + counterpartyUpgradeSequence uint64, ) error { if !k.scopedKeeper.AuthenticateCapability(ctx, chanCap, host.ChannelCapabilityPath(portID, channelID)) { return errorsmod.Wrap(types.ErrChannelCapabilityNotFound, "caller does not own capability for channel, port ID (%s) channel ID (%s)") @@ -460,10 +461,14 @@ func (k Keeper) ChanCloseConfirm( counterpartyHops := []string{connectionEnd.GetCounterparty().GetConnectionID()} counterparty := types.NewCounterparty(portID, channelID) - expectedChannel := types.NewChannel( - types.CLOSED, channel.Ordering, counterparty, - counterpartyHops, channel.Version, - ) + expectedChannel := types.Channel{ + State: types.CLOSED, + Ordering: channel.Ordering, + Counterparty: counterparty, + ConnectionHops: counterpartyHops, + Version: channel.Version, + UpgradeSequence: counterpartyUpgradeSequence, + } if err := k.connectionKeeper.VerifyChannelState( ctx, connectionEnd, proofHeight, proofInit, diff --git a/modules/core/04-channel/keeper/handshake_test.go b/modules/core/04-channel/keeper/handshake_test.go index 988de93045d..7051e11abb9 100644 --- a/modules/core/04-channel/keeper/handshake_test.go +++ b/modules/core/04-channel/keeper/handshake_test.go @@ -10,6 +10,7 @@ import ( host "github.com/cosmos/ibc-go/v8/modules/core/24-host" "github.com/cosmos/ibc-go/v8/modules/core/exported" ibctesting "github.com/cosmos/ibc-go/v8/testing" + "github.com/cosmos/ibc-go/v8/testing/mock" ) type testCase = struct { @@ -718,9 +719,10 @@ func (suite *KeeperTestSuite) TestChanCloseInit() { // bypassed on chainA by setting the channel state in the ChannelKeeper. func (suite *KeeperTestSuite) TestChanCloseConfirm() { var ( - path *ibctesting.Path - channelCap *capabilitytypes.Capability - heightDiff uint64 + path *ibctesting.Path + channelCap *capabilitytypes.Capability + heightDiff uint64 + counterpartyUpgradeSequence uint64 ) testCases := []testCase{ @@ -794,13 +796,32 @@ func (suite *KeeperTestSuite) TestChanCloseConfirm() { channelCap = capabilitytypes.NewCapability(3) }, false}, + { + "failure: invalid counterparty upgrade sequence", + func() { + suite.coordinator.Setup(path) + channelCap = suite.chainB.GetChannelCapability(path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + + // trigger upgradeInit on B which will bump the counterparty upgrade sequence. + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + err := path.EndpointB.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointA.SetChannelState(types.CLOSED) + suite.Require().NoError(err) + + channelCap = capabilitytypes.NewCapability(3) + }, + false, + }, } for _, tc := range testCases { tc := tc suite.Run(fmt.Sprintf("Case %s", tc.msg), func() { - suite.SetupTest() // reset - heightDiff = 0 // must explicitly be changed + suite.SetupTest() // reset + heightDiff = 0 // must explicitly be changed + counterpartyUpgradeSequence = 0 // must explicitly be changed path = ibctesting.NewPath(suite.chainA, suite.chainB) tc.malleate() @@ -810,7 +831,7 @@ func (suite *KeeperTestSuite) TestChanCloseConfirm() { err := suite.chainB.App.GetIBCKeeper().ChannelKeeper.ChanCloseConfirm( suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, ibctesting.FirstChannelID, channelCap, - proof, malleateHeight(proofHeight, heightDiff), + proof, malleateHeight(proofHeight, heightDiff), counterpartyUpgradeSequence, ) if tc.expPass { diff --git a/modules/core/04-channel/keeper/keeper.go b/modules/core/04-channel/keeper/keeper.go index f666b09d27b..9c30c8f252c 100644 --- a/modules/core/04-channel/keeper/keeper.go +++ b/modules/core/04-channel/keeper/keeper.go @@ -194,6 +194,12 @@ func (k Keeper) SetPacketReceipt(ctx sdk.Context, portID, channelID string, sequ store.Set(host.PacketReceiptKey(portID, channelID, sequence), []byte{byte(1)}) } +// deletePacketReceipt deletes a packet receipt from the store +func (k Keeper) deletePacketReceipt(ctx sdk.Context, portID, channelID string, sequence uint64) { + store := ctx.KVStore(k.storeKey) + store.Delete(host.PacketReceiptKey(portID, channelID, sequence)) +} + // GetPacketCommitment gets the packet commitment hash from the store func (k Keeper) GetPacketCommitment(ctx sdk.Context, portID, channelID string, sequence uint64) []byte { store := ctx.KVStore(k.storeKey) @@ -240,6 +246,12 @@ func (k Keeper) HasPacketAcknowledgement(ctx sdk.Context, portID, channelID stri return store.Has(host.PacketAcknowledgementKey(portID, channelID, sequence)) } +// deletePacketAcknowledgement deletes the packet ack hash from the store +func (k Keeper) deletePacketAcknowledgement(ctx sdk.Context, portID, channelID string, sequence uint64) { + store := ctx.KVStore(k.storeKey) + store.Delete(host.PacketAcknowledgementKey(portID, channelID, sequence)) +} + // IteratePacketSequence provides an iterator over all send, receive or ack sequences. // For each sequence, cb will be called. If the cb returns true, the iterator // will close and stop. @@ -481,6 +493,107 @@ func (k Keeper) LookupModuleByChannel(ctx sdk.Context, portID, channelID string) return porttypes.GetModuleOwner(modules), capability, nil } +// GetUpgradeErrorReceipt returns the upgrade error receipt for the provided port and channel identifiers. +func (k Keeper) GetUpgradeErrorReceipt(ctx sdk.Context, portID, channelID string) (types.ErrorReceipt, bool) { + store := ctx.KVStore(k.storeKey) + bz := store.Get(host.ChannelUpgradeErrorKey(portID, channelID)) + if bz == nil { + return types.ErrorReceipt{}, false + } + + var errorReceipt types.ErrorReceipt + k.cdc.MustUnmarshal(bz, &errorReceipt) + + return errorReceipt, true +} + +// SetUpgradeErrorReceipt sets the provided error receipt in store using the port and channel identifiers. +func (k Keeper) SetUpgradeErrorReceipt(ctx sdk.Context, portID, channelID string, errorReceipt types.ErrorReceipt) { + store := ctx.KVStore(k.storeKey) + bz := k.cdc.MustMarshal(&errorReceipt) + store.Set(host.ChannelUpgradeErrorKey(portID, channelID), bz) +} + +// GetUpgrade returns the proposed upgrade for the provided port and channel identifiers. +func (k Keeper) GetUpgrade(ctx sdk.Context, portID, channelID string) (types.Upgrade, bool) { + store := ctx.KVStore(k.storeKey) + bz := store.Get(host.ChannelUpgradeKey(portID, channelID)) + if bz == nil { + return types.Upgrade{}, false + } + + var upgrade types.Upgrade + k.cdc.MustUnmarshal(bz, &upgrade) + + return upgrade, true +} + +// SetUpgrade sets the proposed upgrade using the provided port and channel identifiers. +func (k Keeper) SetUpgrade(ctx sdk.Context, portID, channelID string, upgrade types.Upgrade) { + store := ctx.KVStore(k.storeKey) + bz := k.cdc.MustMarshal(&upgrade) + store.Set(host.ChannelUpgradeKey(portID, channelID), bz) +} + +// deleteUpgrade deletes the upgrade for the provided port and channel identifiers. +func (k Keeper) deleteUpgrade(ctx sdk.Context, portID, channelID string) { + store := ctx.KVStore(k.storeKey) + store.Delete(host.ChannelUpgradeKey(portID, channelID)) +} + +// GetCounterpartyUpgrade gets the counterparty upgrade from the store. +func (k Keeper) GetCounterpartyUpgrade(ctx sdk.Context, portID, channelID string) (types.Upgrade, bool) { + store := ctx.KVStore(k.storeKey) + bz := store.Get(host.ChannelCounterpartyUpgradeKey(portID, channelID)) + if bz == nil { + return types.Upgrade{}, false + } + + var upgrade types.Upgrade + k.cdc.MustUnmarshal(bz, &upgrade) + + return upgrade, true +} + +// SetCounterpartyUpgrade sets the counterparty upgrade in the store. +func (k Keeper) SetCounterpartyUpgrade(ctx sdk.Context, portID, channelID string, upgrade types.Upgrade) { + store := ctx.KVStore(k.storeKey) + bz := k.cdc.MustMarshal(&upgrade) + store.Set(host.ChannelCounterpartyUpgradeKey(portID, channelID), bz) +} + +// deleteCounterpartyUpgrade deletes the counterparty upgrade in the store. +func (k Keeper) deleteCounterpartyUpgrade(ctx sdk.Context, portID, channelID string) { + store := ctx.KVStore(k.storeKey) + store.Delete(host.ChannelCounterpartyUpgradeKey(portID, channelID)) +} + +// deleteUpgradeInfo deletes all auxiliary upgrade information. +func (k Keeper) deleteUpgradeInfo(ctx sdk.Context, portID, channelID string) { + k.deleteUpgrade(ctx, portID, channelID) + k.deleteCounterpartyUpgrade(ctx, portID, channelID) +} + +// SetParams sets the channel parameters. +func (k Keeper) SetParams(ctx sdk.Context, params types.Params) { + store := ctx.KVStore(k.storeKey) + bz := k.cdc.MustMarshal(¶ms) + store.Set([]byte(types.ParamsKey), bz) +} + +// GetParams returns the total set of the channel parameters. +func (k Keeper) GetParams(ctx sdk.Context) types.Params { + store := ctx.KVStore(k.storeKey) + bz := store.Get([]byte(types.ParamsKey)) + if bz == nil { // only panic on unset params and not on empty params + panic(errors.New("channel params are not set in store")) + } + + var params types.Params + k.cdc.MustUnmarshal(bz, ¶ms) + return params +} + // common functionality for IteratePacketCommitment and IteratePacketAcknowledgement func (Keeper) iterateHashes(ctx sdk.Context, iterator db.Iterator, cb func(portID, channelID string, sequence uint64, hash []byte) bool) { defer sdk.LogDeferred(ctx.Logger(), func() error { return iterator.Close() }) @@ -500,3 +613,94 @@ func (Keeper) iterateHashes(ctx sdk.Context, iterator db.Iterator, cb func(portI } } } + +// HasInflightPackets returns true if there are packet commitments stored at the specified +// port and channel, and false otherwise. +func (k Keeper) HasInflightPackets(ctx sdk.Context, portID, channelID string) bool { + iterator := storetypes.KVStorePrefixIterator(ctx.KVStore(k.storeKey), []byte(host.PacketCommitmentPrefixPath(portID, channelID))) + defer sdk.LogDeferred(ctx.Logger(), func() error { return iterator.Close() }) + + return iterator.Valid() +} + +// SetPruningSequenceEnd sets the channel's pruning sequence end to the store. +func (k Keeper) SetPruningSequenceEnd(ctx sdk.Context, portID, channelID string, sequence uint64) { + store := ctx.KVStore(k.storeKey) + bz := sdk.Uint64ToBigEndian(sequence) + store.Set(host.PruningSequenceEndKey(portID, channelID), bz) +} + +// GetPruningSequenceEnd gets a channel's pruning sequence end from the store. +func (k Keeper) GetPruningSequenceEnd(ctx sdk.Context, portID, channelID string) (uint64, bool) { + store := ctx.KVStore(k.storeKey) + bz := store.Get(host.PruningSequenceEndKey(portID, channelID)) + if len(bz) == 0 { + return 0, false + } + + return sdk.BigEndianToUint64(bz), true +} + +// SetPruningSequenceStart sets a channel's pruning sequence start to the store. +func (k Keeper) SetPruningSequenceStart(ctx sdk.Context, portID, channelID string, sequence uint64) { + store := ctx.KVStore(k.storeKey) + bz := sdk.Uint64ToBigEndian(sequence) + store.Set(host.PruningSequenceStartKey(portID, channelID), bz) +} + +// GetPruningSequenceStart gets a channel's pruning sequence start from the store. +func (k Keeper) GetPruningSequenceStart(ctx sdk.Context, portID, channelID string) uint64 { + store := ctx.KVStore(k.storeKey) + bz := store.Get(host.PruningSequenceStartKey(portID, channelID)) + if len(bz) == 0 { + return 0 + } + + return sdk.BigEndianToUint64(bz) +} + +// HasPruningSequenceStart returns true if the pruning sequence start is set for the specified channel. +func (k Keeper) HasPruningSequenceStart(ctx sdk.Context, portID, channelID string) bool { + store := ctx.KVStore(k.storeKey) + return store.Has(host.PruningSequenceStartKey(portID, channelID)) +} + +// PruneAcknowledgements prunes packet acknowledgements and receipts that have a sequence number less than pruning sequence end. +// The number of packet acks/receipts pruned is bounded by the limit. Pruning can only occur after a channel has been upgraded. +// +// Pruning sequence start keeps track of the packet ack/receipt that can be pruned next. When it reaches pruningSequenceEnd, +// pruning is complete. +func (k Keeper) PruneAcknowledgements(ctx sdk.Context, portID, channelID string, limit uint64) (uint64, uint64, error) { + if !k.HasPruningSequenceStart(ctx, portID, channelID) { + return 0, 0, errorsmod.Wrapf(types.ErrPruningSequenceStartNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + pruningSequenceStart := k.GetPruningSequenceStart(ctx, portID, channelID) + pruningSequenceEnd, found := k.GetPruningSequenceEnd(ctx, portID, channelID) + if !found { + return 0, 0, errorsmod.Wrapf(types.ErrPruningSequenceEndNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + start := pruningSequenceStart + end := pruningSequenceStart + limit + for ; start < end; start++ { + // stop pruning if pruningSequenceStart has reached pruningSequenceEnd, pruningSequenceEnd is + // set to be equal to the _next_ sequence to be sent by the counterparty. + if start >= pruningSequenceEnd { + break + } + + k.deletePacketAcknowledgement(ctx, portID, channelID, start) + + // NOTE: packet receipts are only relevant for unordered channels. + k.deletePacketReceipt(ctx, portID, channelID, start) + } + + // set pruning sequence start to the updated value + k.SetPruningSequenceStart(ctx, portID, channelID, start) + + totalPruned := start - pruningSequenceStart + totalRemaining := pruningSequenceEnd - start + + return totalPruned, totalRemaining, nil +} diff --git a/modules/core/04-channel/keeper/keeper_test.go b/modules/core/04-channel/keeper/keeper_test.go index 94917b92d00..93711a93065 100644 --- a/modules/core/04-channel/keeper/keeper_test.go +++ b/modules/core/04-channel/keeper/keeper_test.go @@ -1,13 +1,17 @@ package keeper_test import ( + "fmt" "reflect" "testing" testifysuite "github.com/stretchr/testify/suite" transfertypes "github.com/cosmos/ibc-go/v8/modules/apps/transfer/types" + clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" + host "github.com/cosmos/ibc-go/v8/modules/core/24-host" + "github.com/cosmos/ibc-go/v8/modules/core/exported" ibctesting "github.com/cosmos/ibc-go/v8/testing" ibcmock "github.com/cosmos/ibc-go/v8/testing/mock" ) @@ -465,3 +469,394 @@ func (suite *KeeperTestSuite) TestSetPacketAcknowledgement() { suite.Require().Equal(ackHash, storedAckHash) suite.Require().True(suite.chainA.App.GetIBCKeeper().ChannelKeeper.HasPacketAcknowledgement(ctxA, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, seq)) } + +func (suite *KeeperTestSuite) TestSetUpgradeErrorReceipt() { + path := ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.SetupConnections(path) + suite.coordinator.CreateChannels(path) + + errorReceipt, found := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().False(found) + suite.Require().Empty(errorReceipt) + + expErrorReceipt := types.NewUpgradeError(1, fmt.Errorf("testing")).GetErrorReceipt() + suite.chainA.App.GetIBCKeeper().ChannelKeeper.SetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, expErrorReceipt) + + errorReceipt, found = suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(expErrorReceipt, errorReceipt) +} + +// TestDefaultSetParams tests the default params set are what is expected +func (suite *KeeperTestSuite) TestDefaultSetParams() { + expParams := types.DefaultParams() + + channelKeeper := suite.chainA.App.GetIBCKeeper().ChannelKeeper + params := channelKeeper.GetParams(suite.chainA.GetContext()) + + suite.Require().Equal(expParams, params) + suite.Require().Equal(expParams.UpgradeTimeout, channelKeeper.GetParams(suite.chainA.GetContext()).UpgradeTimeout) +} + +// TestParams tests that Param setting and retrieval works properly +func (suite *KeeperTestSuite) TestParams() { + testCases := []struct { + name string + input types.Params + expPass bool + }{ + {"success: set default params", types.DefaultParams(), true}, + {"success: zero timeout height", types.NewParams(types.NewTimeout(clienttypes.ZeroHeight(), 10000)), true}, + {"fail: zero timeout timestamp", types.NewParams(types.NewTimeout(clienttypes.NewHeight(1, 1000), 0)), false}, + {"fail: zero timeout", types.NewParams(types.NewTimeout(clienttypes.ZeroHeight(), 0)), false}, + } + + for _, tc := range testCases { + tc := tc + + suite.Run(tc.name, func() { + suite.SetupTest() // reset + ctx := suite.chainA.GetContext() + err := tc.input.Validate() + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.SetParams(ctx, tc.input) + if tc.expPass { + suite.Require().NoError(err) + expected := tc.input + p := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetParams(ctx) + suite.Require().Equal(expected, p) + } else { + suite.Require().Error(err) + } + }) + } +} + +// TestUnsetParams tests that trying to get params that are not set panics. +func (suite *KeeperTestSuite) TestUnsetParams() { + suite.SetupTest() + ctx := suite.chainA.GetContext() + store := ctx.KVStore(suite.chainA.GetSimApp().GetKey(exported.StoreKey)) + store.Delete([]byte(types.ParamsKey)) + + suite.Require().Panics(func() { + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetParams(ctx) + }) +} + +func (suite *KeeperTestSuite) TestPruneAcknowledgements() { + var ( + path *ibctesting.Path + limit uint64 + upgradeFields types.UpgradeFields + + // postPruneExpState is a helper function to verify the expected state after pruning. Argument expLeft + // denotes the expected amount of packet acks and receipts left after pruning. Argument expSequenceStart + // denotes the expected value of PruneSequenceStart. + postPruneExpState = func(expAcksLen, expReceiptsLen, expPruningSequenceStart uint64) { + acks := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetAllPacketAcks(suite.chainA.GetContext()) + suite.Require().Len(acks, int(expAcksLen)) + + receipts := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetAllPacketReceipts(suite.chainA.GetContext()) + suite.Require().Len(receipts, int(expReceiptsLen)) + + start := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetPruningSequenceStart(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().Equal(start, expPruningSequenceStart) + } + ) + + testCases := []struct { + name string + pre func() + malleate func() + post func(pruned, left uint64) + expError error + }{ + { + "success: no packets sent, no stale packet state pruned", + func() {}, + func() {}, + func(pruned, left uint64) { + // Assert that PruneSequenceStart and PruneSequenceEnd are both set to 1. + start := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetPruningSequenceStart(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + end, found := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetPruningSequenceEnd(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + + suite.Require().Equal(uint64(1), start) + suite.Require().Equal(uint64(1), end) + + // We expect 0 to be pruned and 0 left. + suite.Require().Equal(uint64(0), pruned) + suite.Require().Equal(uint64(0), left) + }, + nil, + }, + { + "success: stale packet state pruned up to limit", + func() { + // Send 10 packets from B -> A, creating 10 packet receipts and 10 packet acks on A. + suite.sendMockPackets(path, 10) + }, + func() {}, + func(pruned, left uint64) { + sequenceEnd, found := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetPruningSequenceEnd(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + + // We expect nothing to be left and sequenceStart == sequenceEnd. + postPruneExpState(0, 0, sequenceEnd) + + // We expect 10 to be pruned and 0 left. + suite.Require().Equal(uint64(10), pruned) + suite.Require().Equal(uint64(0), left) + }, + nil, + }, + { + "success: stale packet state partially pruned", + func() { + // Send 10 packets from B -> A, creating 10 packet receipts and 10 packet acks on A. + suite.sendMockPackets(path, 10) + }, + func() { + // Prune only 6 packet acks. + limit = 6 + }, + func(pruned, left uint64) { + // We expect 4 to be left and sequenceStart == 7. + postPruneExpState(4, 4, 7) + + // We expect 6 to be pruned and 4 left. + suite.Require().Equal(uint64(6), pruned) + suite.Require().Equal(uint64(4), left) + }, + nil, + }, + { + "success: stale packet state pruned, two upgrades", + func() { + // Send 10 packets from B -> A, creating 10 packet receipts and 10 packet acks on A. + // This is _before_ the first upgrade. + suite.sendMockPackets(path, 10) + }, + func() { + // Previous upgrade is complete, send additional packets and do yet another upgrade. + // This is _after_ the first upgrade. + suite.sendMockPackets(path, 5) + + // Do another upgrade. + upgradeFields = types.UpgradeFields{Version: fmt.Sprintf("%s-v3", ibcmock.Version)} + suite.UpgradeChannel(path, upgradeFields) + + // set limit to 15, get them all in one go. + limit = 15 + }, + func(pruned, left uint64) { + sequenceEnd, found := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetPruningSequenceEnd(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + + // We expect nothing to be left and sequenceStart == sequenceEnd. + postPruneExpState(0, 0, sequenceEnd) + + // We expect 15 to be pruned and 0 left. + suite.Require().Equal(uint64(15), pruned) + suite.Require().Equal(uint64(0), left) + }, + nil, + }, + { + "success: stale packet state partially pruned, upgrade, prune again", + func() { + // Send 10 packets from B -> A, creating 10 packet receipts and 10 packet acks on A. + // This is _before_ the first upgrade. + suite.sendMockPackets(path, 10) + }, + func() { + // Prune 5 on A. + pruned, left, err := suite.chainA.App.GetIBCKeeper().ChannelKeeper.PruneAcknowledgements( + suite.chainA.GetContext(), + path.EndpointA.ChannelConfig.PortID, + path.EndpointA.ChannelID, + 4, // limit == 4 + ) + suite.Require().NoError(err) + + // We expect 4 to be pruned and 6 left. + suite.Require().Equal(uint64(4), pruned) + suite.Require().Equal(uint64(6), left) + + // Check state post-prune + postPruneExpState(6, 6, 5) + + // Previous upgrade is complete, send additional packets and do yet another upgrade. + // This is _after_ the first upgrade. + suite.sendMockPackets(path, 10) + + // Do another upgrade. + upgradeFields = types.UpgradeFields{Version: fmt.Sprintf("%s-v3", ibcmock.Version)} + suite.UpgradeChannel(path, upgradeFields) + + // A total of 16 stale acks/receipts exist on A. Prune 10 of them (default in test). + }, + func(pruned, left uint64) { + // Expected state should be 6 acks/receipts left, sequenceStart == 15. + postPruneExpState(6, 6, 15) + + // We expect 10 to be pruned and 6 left. + suite.Require().Equal(uint64(10), pruned) + suite.Require().Equal(uint64(6), left) + }, + nil, + }, + { + "success: unordered -> ordered -> unordered, acksLen != receiptsLen after packet sends", + func() { + // Send 5 packets from B -> A, creating 5 packet receipts and 5 packet acks on A. + // This is _before_ the first upgrade. + suite.sendMockPackets(path, 5) + + // Set Order for upgrade to Ordered. + upgradeFields = types.UpgradeFields{Version: fmt.Sprintf("%s-v2", ibcmock.Version), Ordering: types.ORDERED} + }, + func() { + // Previous upgrade is complete, send additional packets now on ordered channel (only acks!) + suite.sendMockPackets(path, 10) + + // Do another upgrade (go back to Unordered) + upgradeFields = types.UpgradeFields{Version: fmt.Sprintf("%s-v3", ibcmock.Version), Ordering: types.UNORDERED} + suite.UpgradeChannel(path, upgradeFields) + }, + func(pruned, left uint64) { + // After pruning 10 sequences we should be left with 5 acks and zero receipts. + postPruneExpState(5, 0, 11) + + // We expect 10 to be pruned and 5 left. + suite.Require().Equal(uint64(10), pruned) + suite.Require().Equal(uint64(5), left) + }, + nil, + }, + { + "success: packets sent before upgrade are pruned, after upgrade are not", + func() { + // Send 5 packets from B -> A, creating 5 packet receipts and 5 packet acks on A. + suite.sendMockPackets(path, 5) + }, + func() {}, + func(pruned, left uint64) { + // We expect 5 to be pruned and 0 left. + suite.Require().Equal(uint64(5), pruned) + suite.Require().Equal(uint64(0), left) + + // channel upgraded, send additional packets and try and prune. + suite.sendMockPackets(path, 12) + + // attempt to prune 5. + pruned, left, err := suite.chainA.App.GetIBCKeeper().ChannelKeeper.PruneAcknowledgements( + suite.chainA.GetContext(), + path.EndpointA.ChannelConfig.PortID, + path.EndpointA.ChannelID, + 5, + ) + suite.Require().NoError(err) + // We expect 0 to be pruned and 0 left. + suite.Require().Equal(uint64(0), pruned) + suite.Require().Equal(uint64(0), left) + + // we _do not_ expect error, simply a fast return + postPruneExpState(12, 12, 6) + }, + nil, + }, + { + "failure: packet sequence start not set", + func() {}, + func() { + path.EndpointA.ChannelConfig.PortID = "portidone" + }, + func(_, _ uint64) {}, + types.ErrPruningSequenceStartNotFound, + }, + { + "failure: packet sequence end not set", + func() {}, + func() { + store := suite.chainA.GetContext().KVStore(suite.chainA.GetSimApp().GetKey(exported.StoreKey)) + store.Delete(host.PruningSequenceEndKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + }, + func(_, _ uint64) {}, + types.ErrPruningSequenceEndNotFound, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() // reset + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + // Defaults will be filled in for rest. + upgradeFields = types.UpgradeFields{Version: ibcmock.UpgradeVersion} + limit = 10 + + // perform pre upgrade ops. + tc.pre() + + suite.UpgradeChannel(path, upgradeFields) + + tc.malleate() + + pruned, left, err := suite.chainA.App.GetIBCKeeper().ChannelKeeper.PruneAcknowledgements( + suite.chainA.GetContext(), + path.EndpointA.ChannelConfig.PortID, + path.EndpointA.ChannelID, + limit, + ) + + suite.Require().ErrorIs(err, tc.expError) + + // check on post state. + tc.post(pruned, left) + }) + } +} + +// UpgradeChannel performs a channel upgrade given a specific set of upgrade fields. +// Question(jim): setup.coordinator.UpgradeChannel() wen? +func (suite *KeeperTestSuite) UpgradeChannel(path *ibctesting.Path, upgradeFields types.UpgradeFields) { + // configure the channel upgrade version on testing endpoints + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields = upgradeFields + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields = upgradeFields + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeConfirm() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeOpen() + suite.Require().NoError(err) + + err = path.EndpointA.UpdateClient() + suite.Require().NoError(err) +} + +// sendMockPacket sends a packet from source to dest and acknowledges it on the source (completing the packet lifecycle). +// Question(jim): find a nicer home for this? +func (suite *KeeperTestSuite) sendMockPackets(path *ibctesting.Path, numPackets int) { + for i := 0; i < numPackets; i++ { + + sequence, err := path.EndpointB.SendPacket(clienttypes.NewHeight(1, 1000), disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + + packet := types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, clienttypes.NewHeight(1, 1000), disabledTimeoutTimestamp) + err = path.RelayPacket(packet) + suite.Require().NoError(err) + } +} diff --git a/modules/core/04-channel/keeper/packet.go b/modules/core/04-channel/keeper/packet.go index 28fdbe7a13e..78b7c464b3a 100644 --- a/modules/core/04-channel/keeper/packet.go +++ b/modules/core/04-channel/keeper/packet.go @@ -2,6 +2,7 @@ package keeper import ( "bytes" + "slices" "strconv" "time" @@ -34,11 +35,8 @@ func (k Keeper) SendPacket( return 0, errorsmod.Wrap(types.ErrChannelNotFound, sourceChannel) } - if !channel.IsOpen() { - return 0, errorsmod.Wrapf( - types.ErrInvalidChannelState, - "channel state is not OPEN (got %s)", channel.State.String(), - ) + if channel.State != types.OPEN { + return 0, errorsmod.Wrapf(types.ErrInvalidChannelState, "channel is not OPEN (got %s)", channel.State) } if !k.scopedKeeper.AuthenticateCapability(ctx, channelCap, host.ChannelCapabilityPath(sourcePort, sourceChannel)) { @@ -130,11 +128,26 @@ func (k Keeper) RecvPacket( return errorsmod.Wrap(types.ErrChannelNotFound, packet.GetDestChannel()) } - if !channel.IsOpen() { - return errorsmod.Wrapf( - types.ErrInvalidChannelState, - "channel state is not OPEN (got %s)", channel.State.String(), - ) + if !slices.Contains([]types.State{types.OPEN, types.FLUSHING}, channel.State) { + return errorsmod.Wrapf(types.ErrInvalidChannelState, "expected channel state to be one of [%s, %s], but got %s", types.OPEN, types.FLUSHING, channel.State) + } + + // If counterpartyUpgrade is stored we need to ensure that the + // packet sequence is < counterparty next sequence send. This is a defensive + // check and if the counterparty is implemented correctly, this should never abort. + counterpartyUpgrade, found := k.GetCounterpartyUpgrade(ctx, packet.GetDestPort(), packet.GetDestChannel()) + if found { + // only error if the counterparty next sequence send is set (> 0) + // this error should never be reached, as under normal circumstances the counterparty + // should not send any packets after the upgrade has been started. + counterpartyNextSequenceSend := counterpartyUpgrade.NextSequenceSend + if packet.GetSequence() >= counterpartyNextSequenceSend { + return errorsmod.Wrapf( + types.ErrInvalidPacket, + "failed to receive packet, cannot flush packet at sequence greater than or equal to counterparty next sequence send (%d) ≥ (%d). UNEXPECTED BEHAVIOUR ON COUNTERPARTY, PLEASE REPORT ISSUE TO RELEVANT CHAIN DEVELOPERS", + packet.GetSequence(), counterpartyNextSequenceSend, + ) + } } // Authenticate capability to ensure caller has authority to receive packet on this channel @@ -255,7 +268,6 @@ func (k Keeper) RecvPacket( // incrementing nextSequenceRecv and storing under this chain's channelEnd identifiers // Since this is the receiving chain, our channelEnd is packet's destination port and channel k.SetNextSequenceRecv(ctx, packet.GetDestPort(), packet.GetDestChannel(), nextSequenceRecv) - } // log that a packet has been received & executed @@ -371,11 +383,8 @@ func (k Keeper) AcknowledgePacket( ) } - if !channel.IsOpen() { - return errorsmod.Wrapf( - types.ErrInvalidChannelState, - "channel state is not OPEN (got %s)", channel.State.String(), - ) + if !slices.Contains([]types.State{types.OPEN, types.FLUSHING}, channel.State) { + return errorsmod.Wrapf(types.ErrInvalidChannelState, "packets cannot be acknowledged on channel with state (%s)", channel.State) } // Authenticate capability to ensure caller has authority to receive packet on this channel @@ -481,5 +490,29 @@ func (k Keeper) AcknowledgePacket( // emit an event marking that we have processed the acknowledgement emitAcknowledgePacketEvent(ctx, packet, channel) + // if an upgrade is in progress, handling packet flushing and update channel state appropriately + if channel.State == types.FLUSHING { + // counterparty upgrade is written in the OnChanUpgradeAck step. + counterpartyUpgrade, found := k.GetCounterpartyUpgrade(ctx, packet.GetSourcePort(), packet.GetSourceChannel()) + if found { + timeout := counterpartyUpgrade.Timeout + selfHeight, selfTimestamp := clienttypes.GetSelfHeight(ctx), uint64(ctx.BlockTime().UnixNano()) + + if timeout.Elapsed(selfHeight, selfTimestamp) { + // packet flushing timeout has expired, abort the upgrade and return nil, + // committing an error receipt to state, restoring the channel and successfully acknowledging the packet. + k.MustAbortUpgrade(ctx, packet.GetSourcePort(), packet.GetSourceChannel(), timeout.ErrTimeoutElapsed(selfHeight, selfTimestamp)) + return nil + } + + // set the channel state to flush complete if all packets have been acknowledged/flushed. + if !k.HasInflightPackets(ctx, packet.GetSourcePort(), packet.GetSourceChannel()) { + channel.State = types.FLUSHCOMPLETE + k.SetChannel(ctx, packet.GetSourcePort(), packet.GetSourceChannel(), channel) + emitChannelFlushCompleteEvent(ctx, packet.GetSourcePort(), packet.GetSourceChannel(), channel) + } + } + } + return nil } diff --git a/modules/core/04-channel/keeper/packet_test.go b/modules/core/04-channel/keeper/packet_test.go index 721a41d46de..8a33cb563e7 100644 --- a/modules/core/04-channel/keeper/packet_test.go +++ b/modules/core/04-channel/keeper/packet_test.go @@ -5,6 +5,8 @@ import ( "cosmossdk.io/errors" + sdk "github.com/cosmos/cosmos-sdk/types" + capabilitytypes "github.com/cosmos/ibc-go/modules/capability/types" clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" @@ -217,6 +219,34 @@ func (suite *KeeperTestSuite) TestSendPacket() { channelCap = capabilitytypes.NewCapability(5) }, false}, + { + "channel is in FLUSH_COMPLETE state", + func() { + suite.coordinator.Setup(path) + sourceChannel = path.EndpointA.ChannelID + + channel := path.EndpointA.GetChannel() + channel.State = types.FLUSHCOMPLETE + path.EndpointA.SetChannel(channel) + }, + false, + }, + { + "channel is in FLUSHING state", + func() { + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + + err := path.EndpointB.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeTry() + suite.Require().NoError(err) + }, + false, + }, } for i, tc := range testCases { @@ -309,6 +339,77 @@ func (suite *KeeperTestSuite) TestRecvPacket() { }, nil, }, + { + "success with counterpartyNextSequenceSend higher than packet sequence", + func() { + suite.coordinator.Setup(path) + sequence, err := path.EndpointA.SendPacket(defaultTimeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + channelCap = suite.chainB.GetChannelCapability(path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + + channel := path.EndpointB.GetChannel() + channel.State = types.FLUSHING + path.EndpointB.SetChannel(channel) + + // set upgrade next sequence send to sequence + 1 + counterpartyUpgrade := types.Upgrade{NextSequenceSend: sequence + 1} + path.EndpointB.SetChannelCounterpartyUpgrade(counterpartyUpgrade) + }, + nil, + }, + { + "success with counterparty upgrade not found", + func() { + suite.coordinator.Setup(path) + sequence, err := path.EndpointA.SendPacket(defaultTimeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + channelCap = suite.chainB.GetChannelCapability(path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + + channel := path.EndpointB.GetChannel() + channel.State = types.FLUSHING + path.EndpointB.SetChannel(channel) + }, + nil, + }, + { + "failure while upgrading channel, packet sequence ≥ counterparty next send sequence", + func() { + suite.coordinator.Setup(path) + // send 2 packets so that when NextSequenceSend is set to sequence - 1, it is not 0. + _, err := path.EndpointA.SendPacket(defaultTimeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + sequence, err := path.EndpointA.SendPacket(defaultTimeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + channelCap = suite.chainB.GetChannelCapability(path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + + channel := path.EndpointB.GetChannel() + channel.State = types.FLUSHING + path.EndpointB.SetChannel(channel) + + // set upgrade next sequence send to sequence - 1 + counterpartyUpgrade := types.Upgrade{NextSequenceSend: sequence - 1} + path.EndpointB.SetChannelCounterpartyUpgrade(counterpartyUpgrade) + }, + types.ErrInvalidPacket, + }, + { + "failure while upgrading channel, channel in flush complete state", + func() { + suite.coordinator.Setup(path) + sequence, err := path.EndpointA.SendPacket(defaultTimeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + channelCap = suite.chainB.GetChannelCapability(path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + + channel := path.EndpointB.GetChannel() + channel.State = types.FLUSHCOMPLETE + path.EndpointB.SetChannel(channel) + }, + types.ErrInvalidChannelState, + }, { "packet already relayed ORDERED channel (no-op)", func() { @@ -703,6 +804,7 @@ func (suite *KeeperTestSuite) TestAcknowledgePacket() { name string malleate func() expResult func(commitment []byte, err error) + expEvents func(path *ibctesting.Path) map[string]map[string]string }{ { name: "success on ordered channel", @@ -742,6 +844,144 @@ func (suite *KeeperTestSuite) TestAcknowledgePacket() { }, expResult: assertSuccess(func() uint64 { return uint64(1) }, "sequence incremented for UNORDERED channel"), }, + { + name: "success on channel in flushing state", + malleate: func() { + // setup uses an UNORDERED channel + suite.coordinator.Setup(path) + + // create packet commitment + sequence, err := path.EndpointA.SendPacket(defaultTimeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + + // create packet receipt and acknowledgement + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + err = path.EndpointB.RecvPacket(packet) + suite.Require().NoError(err) + + channelCap = suite.chainA.GetChannelCapability(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + + channel := path.EndpointA.GetChannel() + channel.State = types.FLUSHING + path.EndpointA.SetChannel(channel) + }, + expResult: func(commitment []byte, err error) { + suite.Require().NoError(err) + suite.Require().Nil(commitment) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.FLUSHING, channel.State) + + nextSequenceAck, found := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetNextSequenceAck(suite.chainA.GetContext(), packet.GetSourcePort(), packet.GetSourceChannel()) + suite.Require().True(found) + suite.Require().Equal(uint64(1), nextSequenceAck, "sequence incremented for UNORDERED channel") + }, + }, + { + name: "success on channel in flushing state with valid timeout", + malleate: func() { + // setup uses an UNORDERED channel + suite.coordinator.Setup(path) + + // create packet commitment + sequence, err := path.EndpointA.SendPacket(defaultTimeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + + // create packet receipt and acknowledgement + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + err = path.EndpointB.RecvPacket(packet) + suite.Require().NoError(err) + + channelCap = suite.chainA.GetChannelCapability(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + + channel := path.EndpointA.GetChannel() + channel.State = types.FLUSHING + + path.EndpointA.SetChannel(channel) + + counterpartyUpgrade := types.Upgrade{ + Timeout: types.NewTimeout(suite.chainB.GetTimeoutHeight(), 0), + } + + path.EndpointA.SetChannelCounterpartyUpgrade(counterpartyUpgrade) + }, + expResult: func(commitment []byte, err error) { + suite.Require().NoError(err) + suite.Require().Nil(commitment) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.FLUSHCOMPLETE, channel.State) + + nextSequenceAck, found := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetNextSequenceAck(suite.chainA.GetContext(), packet.GetSourcePort(), packet.GetSourceChannel()) + suite.Require().True(found) + suite.Require().Equal(uint64(1), nextSequenceAck, "sequence incremented for UNORDERED channel") + }, + expEvents: func(path *ibctesting.Path) map[string]map[string]string { + return ibctesting.EventsMap{ + types.EventTypeChannelFlushComplete: { + types.AttributeKeyPortID: path.EndpointA.ChannelConfig.PortID, + types.AttributeKeyChannelID: path.EndpointA.ChannelID, + types.AttributeCounterpartyPortID: path.EndpointB.ChannelConfig.PortID, + types.AttributeCounterpartyChannelID: path.EndpointB.ChannelID, + types.AttributeKeyChannelState: path.EndpointA.GetChannel().State.String(), + }, + sdk.EventTypeMessage: { + sdk.AttributeKeyModule: types.AttributeValueCategory, + }, + } + }, + }, + { + name: "success on channel in flushing state with timeout passed", + malleate: func() { + // setup uses an UNORDERED channel + suite.coordinator.Setup(path) + + // create packet commitment + sequence, err := path.EndpointA.SendPacket(defaultTimeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + + // create packet receipt and acknowledgement + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + err = path.EndpointB.RecvPacket(packet) + suite.Require().NoError(err) + + channelCap = suite.chainA.GetChannelCapability(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + + channel := path.EndpointA.GetChannel() + channel.State = types.FLUSHING + + path.EndpointA.SetChannel(channel) + + upgrade := types.Upgrade{ + Fields: types.NewUpgradeFields(types.UNORDERED, []string{ibctesting.FirstConnectionID}, ibcmock.UpgradeVersion), + Timeout: types.NewTimeout(clienttypes.ZeroHeight(), 1), + } + + counterpartyUpgrade := types.Upgrade{ + Fields: types.NewUpgradeFields(types.UNORDERED, []string{ibctesting.FirstConnectionID}, ibcmock.UpgradeVersion), + Timeout: types.NewTimeout(clienttypes.ZeroHeight(), 1), + } + + path.EndpointA.SetChannelUpgrade(upgrade) + path.EndpointA.SetChannelCounterpartyUpgrade(counterpartyUpgrade) + }, + expResult: func(commitment []byte, err error) { + suite.Require().NoError(err) + suite.Require().Nil(commitment) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.OPEN, channel.State) + + nextSequenceAck, found := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetNextSequenceAck(suite.chainA.GetContext(), packet.GetSourcePort(), packet.GetSourceChannel()) + suite.Require().True(found) + suite.Require().Equal(uint64(1), nextSequenceAck, "sequence incremented for UNORDERED channel") + + errorReceipt, found := path.EndpointA.Chain.App.GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().NotEmpty(errorReceipt) + }, + }, { name: "packet already acknowledged ordered channel (no-op)", malleate: func() { @@ -817,6 +1057,24 @@ func (suite *KeeperTestSuite) TestAcknowledgePacket() { }, expResult: assertErr(types.ErrInvalidChannelState), }, + { + name: "channel in flush complete state", + malleate: func() { + suite.coordinator.Setup(path) + packet = types.NewPacket(ibctesting.MockPacketData, 1, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + channelCap = suite.chainA.GetChannelCapability(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + + channel := path.EndpointA.GetChannel() + channel.State = types.FLUSHCOMPLETE + + path.EndpointA.SetChannel(channel) + }, + expResult: func(commitment []byte, err error) { + suite.Require().Error(err) + suite.Require().ErrorIs(err, types.ErrInvalidChannelState) + suite.Require().Nil(commitment) + }, + }, { name: "capability authentication failed ORDERED", malleate: func() { @@ -1015,16 +1273,24 @@ func (suite *KeeperTestSuite) TestAcknowledgePacket() { suite.SetupTest() // reset path = ibctesting.NewPath(suite.chainA, suite.chainB) + ctx := suite.chainA.GetContext() tc.malleate() packetKey := host.PacketAcknowledgementKey(packet.GetDestPort(), packet.GetDestChannel(), packet.GetSequence()) proof, proofHeight := path.EndpointB.QueryProof(packetKey) - err := suite.chainA.App.GetIBCKeeper().ChannelKeeper.AcknowledgePacket(suite.chainA.GetContext(), channelCap, packet, ack.Acknowledgement(), proof, proofHeight) + err := suite.chainA.App.GetIBCKeeper().ChannelKeeper.AcknowledgePacket(ctx, channelCap, packet, ack.Acknowledgement(), proof, proofHeight) - commitment := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetPacketCommitment(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, packet.GetSequence()) + commitment := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetPacketCommitment(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, packet.GetSequence()) tc.expResult(commitment, err) + if tc.expEvents != nil { + events := ctx.EventManager().ABCIEvents() + + expEvents := tc.expEvents(path) + + ibctesting.AssertEventsLegacy(&suite.Suite, expEvents, events) + } }) } } diff --git a/modules/core/04-channel/keeper/timeout.go b/modules/core/04-channel/keeper/timeout.go index a3334d2fcdd..a0f7f189fa6 100644 --- a/modules/core/04-channel/keeper/timeout.go +++ b/modules/core/04-channel/keeper/timeout.go @@ -9,6 +9,7 @@ import ( sdk "github.com/cosmos/cosmos-sdk/types" capabilitytypes "github.com/cosmos/ibc-go/modules/capability/types" + clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" host "github.com/cosmos/ibc-go/v8/modules/core/24-host" @@ -84,13 +85,6 @@ func (k Keeper) TimeoutPacket( return types.ErrNoOpMsg } - if !channel.IsOpen() { - return errorsmod.Wrapf( - types.ErrInvalidChannelState, - "channel state is not OPEN (got %s)", channel.State.String(), - ) - } - packetCommitment := types.CommitPacket(k.cdc, packet) // verify we sent the packet and haven't cleared it out yet @@ -132,6 +126,9 @@ func (k Keeper) TimeoutPacket( // TimeoutExecuted deletes the commitment send from this chain after it verifies timeout. // If the timed-out packet came from an ORDERED channel then this channel will be closed. +// If the channel is in the FLUSHING state and there is a counterparty upgrade, then the +// upgrade will be aborted if the upgrade has timed out. Otherwise, if there are no more inflight packets, +// then the channel will be set to the FLUSHCOMPLETE state. // // CONTRACT: this function must be called in the IBC handler func (k Keeper) TimeoutExecuted( @@ -154,9 +151,39 @@ func (k Keeper) TimeoutExecuted( k.deletePacketCommitment(ctx, packet.GetSourcePort(), packet.GetSourceChannel(), packet.GetSequence()) + // if an upgrade is in progress, handling packet flushing and update channel state appropriately + if channel.State == types.FLUSHING && channel.Ordering == types.UNORDERED { + counterpartyUpgrade, found := k.GetCounterpartyUpgrade(ctx, packet.GetSourcePort(), packet.GetSourceChannel()) + // once we have received the counterparty timeout in the channel UpgradeAck or UpgradeConfirm handshake steps + // then we can move to flushing complete if the timeout has not passed and there are no in-flight packets + if found { + timeout := counterpartyUpgrade.Timeout + selfHeight, selfTimestamp := clienttypes.GetSelfHeight(ctx), uint64(ctx.BlockTime().UnixNano()) + + if timeout.Elapsed(selfHeight, selfTimestamp) { + // packet flushing timeout has expired, abort the upgrade and return nil, + // committing an error receipt to state, restoring the channel and successfully timing out the packet. + k.MustAbortUpgrade(ctx, packet.GetSourcePort(), packet.GetSourceChannel(), timeout.ErrTimeoutElapsed(selfHeight, selfTimestamp)) + } else if !k.HasInflightPackets(ctx, packet.GetSourcePort(), packet.GetSourceChannel()) { + // set the channel state to flush complete if all packets have been flushed. + channel.State = types.FLUSHCOMPLETE + k.SetChannel(ctx, packet.GetSourcePort(), packet.GetSourceChannel(), channel) + emitChannelFlushCompleteEvent(ctx, packet.GetSourcePort(), packet.GetSourceChannel(), channel) + } + } + } + if channel.Ordering == types.ORDERED { + // NOTE: if the channel is ORDERED and a packet is timed out in FLUSHING state then + // the upgrade is aborted and the channel is set to CLOSED. + if channel.State == types.FLUSHING { + // an error receipt is written to state and the channel is restored to OPEN + k.MustAbortUpgrade(ctx, packet.GetSourcePort(), packet.GetSourceChannel(), types.ErrPacketTimeout) + } + channel.State = types.CLOSED k.SetChannel(ctx, packet.GetSourcePort(), packet.GetSourceChannel(), channel) + emitChannelClosedEvent(ctx, packet, channel) } k.Logger(ctx).Info( @@ -171,10 +198,6 @@ func (k Keeper) TimeoutExecuted( // emit an event marking that we have processed the timeout emitTimeoutPacketEvent(ctx, packet, channel) - if channel.Ordering == types.ORDERED && channel.IsClosed() { - emitChannelClosedEvent(ctx, packet, channel) - } - return nil } @@ -189,6 +212,7 @@ func (k Keeper) TimeoutOnClose( proofClosed []byte, proofHeight exported.Height, nextSequenceRecv uint64, + counterpartyUpgradeSequence uint64, ) error { channel, found := k.GetChannel(ctx, packet.GetSourcePort(), packet.GetSourceChannel()) if !found { @@ -243,9 +267,14 @@ func (k Keeper) TimeoutOnClose( counterpartyHops := []string{connectionEnd.GetCounterparty().GetConnectionID()} counterparty := types.NewCounterparty(packet.GetSourcePort(), packet.GetSourceChannel()) - expectedChannel := types.NewChannel( - types.CLOSED, channel.Ordering, counterparty, counterpartyHops, channel.Version, - ) + expectedChannel := types.Channel{ + State: types.CLOSED, + Ordering: channel.Ordering, + Counterparty: counterparty, + ConnectionHops: counterpartyHops, + Version: channel.Version, + UpgradeSequence: counterpartyUpgradeSequence, + } // check that the opposing channel end has closed if err := k.connectionKeeper.VerifyChannelState( diff --git a/modules/core/04-channel/keeper/timeout_test.go b/modules/core/04-channel/keeper/timeout_test.go index adaf237cf42..27f6def9f85 100644 --- a/modules/core/04-channel/keeper/timeout_test.go +++ b/modules/core/04-channel/keeper/timeout_test.go @@ -6,6 +6,8 @@ import ( errorsmod "cosmossdk.io/errors" + sdk "github.com/cosmos/cosmos-sdk/types" + capabilitytypes "github.com/cosmos/ibc-go/modules/capability/types" clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" @@ -13,6 +15,7 @@ import ( host "github.com/cosmos/ibc-go/v8/modules/core/24-host" "github.com/cosmos/ibc-go/v8/modules/core/exported" ibctesting "github.com/cosmos/ibc-go/v8/testing" + "github.com/cosmos/ibc-go/v8/testing/mock" ) // TestTimeoutPacket test the TimeoutPacket call on chainA by ensuring the timeout has passed @@ -98,22 +101,6 @@ func (suite *KeeperTestSuite) TestTimeoutPacket() { suite.coordinator.Setup(path) packet = types.NewPacket(ibctesting.MockPacketData, 1, ibctesting.InvalidID, ibctesting.InvalidID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) }, false}, - {"channel not open", func() { - expError = types.ErrInvalidChannelState - suite.coordinator.Setup(path) - - timeoutHeight := path.EndpointA.GetClientState().GetLatestHeight().Increment().(clienttypes.Height) - - sequence, err := path.EndpointA.SendPacket(timeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) - suite.Require().NoError(err) - packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, timeoutHeight, disabledTimeoutTimestamp) - // need to update chainA's client representing chainB to prove missing ack - err = path.EndpointA.UpdateClient() - suite.Require().NoError(err) - - err = path.EndpointA.SetChannelState(types.CLOSED) - suite.Require().NoError(err) - }, false}, {"packet destination port ≠ channel counterparty port", func() { expError = types.ErrInvalidPacket suite.coordinator.Setup(path) @@ -246,8 +233,9 @@ func (suite *KeeperTestSuite) TestTimeoutPacket() { } } -// TestTimeoutExectued verifies that packet commitments are deleted on chainA after the -// channel capabilities are verified. +// TestTimeoutExecuted verifies that packet commitments are deleted on chainA after the +// channel capabilities are verified. In addition, the test verifies that the channel state +// after a timeout is updated accordingly. func (suite *KeeperTestSuite) TestTimeoutExecuted() { var ( path *ibctesting.Path @@ -255,38 +243,276 @@ func (suite *KeeperTestSuite) TestTimeoutExecuted() { chanCap *capabilitytypes.Capability ) - testCases := []testCase{ - {"success ORDERED", func() { - path.SetChannelOrdered() - suite.coordinator.Setup(path) + testCases := []struct { + msg string + malleate func() + expResult func(packetCommitment []byte, err error) + expEvents func(path *ibctesting.Path) map[string]map[string]string + }{ + { + "success ORDERED", + func() { + path.SetChannelOrdered() + suite.coordinator.Setup(path) + + timeoutHeight := clienttypes.GetSelfHeight(suite.chainB.GetContext()) + timeoutTimestamp := uint64(suite.chainB.GetContext().BlockTime().UnixNano()) + + sequence, err := path.EndpointA.SendPacket(timeoutHeight, timeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) - timeoutHeight := clienttypes.GetSelfHeight(suite.chainB.GetContext()) - timeoutTimestamp := uint64(suite.chainB.GetContext().BlockTime().UnixNano()) + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, timeoutHeight, timeoutTimestamp) + chanCap = suite.chainA.GetChannelCapability(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + }, + func(packetCommitment []byte, err error) { + suite.Require().NoError(err) + suite.Require().Nil(packetCommitment) + + // Check channel has been closed + channel := path.EndpointA.GetChannel() + suite.Require().Equal(channel.State, types.CLOSED) + }, + nil, + }, + { + "channel not found", + func() { + // use wrong channel naming + suite.coordinator.Setup(path) + packet = types.NewPacket(ibctesting.MockPacketData, 1, ibctesting.InvalidID, ibctesting.InvalidID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + }, + func(packetCommitment []byte, err error) { + suite.Require().Error(err) + suite.Require().ErrorIs(err, types.ErrChannelNotFound) + + // packet never sent. + suite.Require().Nil(packetCommitment) + }, + nil, + }, + { + "incorrect capability ORDERED", + func() { + path.SetChannelOrdered() + suite.coordinator.Setup(path) + + timeoutHeight := clienttypes.GetSelfHeight(suite.chainB.GetContext()) + timeoutTimestamp := uint64(suite.chainB.GetContext().BlockTime().UnixNano()) + + sequence, err := path.EndpointA.SendPacket(timeoutHeight, timeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) - sequence, err := path.EndpointA.SendPacket(timeoutHeight, timeoutTimestamp, ibctesting.MockPacketData) - suite.Require().NoError(err) + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, timeoutHeight, timeoutTimestamp) + chanCap = capabilitytypes.NewCapability(100) + }, + func(packetCommitment []byte, err error) { + suite.Require().Error(err) + suite.Require().ErrorIs(err, types.ErrChannelCapabilityNotFound) + + // packet sent, never deleted. + suite.Require().NotNil(packetCommitment) + }, + nil, + }, + { + "set to flush complete with no inflight packets", + func() { + suite.coordinator.Setup(path) + + chanCap = suite.chainA.GetChannelCapability(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + + channel := path.EndpointA.GetChannel() + channel.State = types.FLUSHING + path.EndpointA.SetChannel(channel) + path.EndpointA.SetChannelCounterpartyUpgrade(types.Upgrade{ + Timeout: types.NewTimeout(clienttypes.ZeroHeight(), uint64(suite.chainA.GetContext().BlockTime().UnixNano())+types.DefaultTimeout.Timestamp), + }) + }, + func(packetCommitment []byte, err error) { + suite.Require().NoError(err) - packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, timeoutHeight, timeoutTimestamp) - chanCap = suite.chainA.GetChannelCapability(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) - }, true}, - {"channel not found", func() { - // use wrong channel naming - suite.coordinator.Setup(path) - packet = types.NewPacket(ibctesting.MockPacketData, 1, ibctesting.InvalidID, ibctesting.InvalidID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) - }, false}, - {"incorrect capability ORDERED", func() { - path.SetChannelOrdered() - suite.coordinator.Setup(path) + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.FLUSHCOMPLETE, channel.State, "channel state should still be set to FLUSHCOMPLETE") + }, + func(path *ibctesting.Path) map[string]map[string]string { + return ibctesting.EventsMap{ + types.EventTypeChannelFlushComplete: { + types.AttributeKeyPortID: path.EndpointA.ChannelConfig.PortID, + types.AttributeKeyChannelID: path.EndpointA.ChannelID, + types.AttributeCounterpartyPortID: path.EndpointB.ChannelConfig.PortID, + types.AttributeCounterpartyChannelID: path.EndpointB.ChannelID, + types.AttributeKeyChannelState: path.EndpointA.GetChannel().State.String(), + }, + sdk.EventTypeMessage: { + sdk.AttributeKeyModule: types.AttributeValueCategory, + }, + } + }, + }, + { + "conterparty upgrade timeout is invalid", + func() { + suite.coordinator.Setup(path) - timeoutHeight := clienttypes.GetSelfHeight(suite.chainB.GetContext()) - timeoutTimestamp := uint64(suite.chainB.GetContext().BlockTime().UnixNano()) + timeoutHeight := clienttypes.GetSelfHeight(suite.chainB.GetContext()) + timeoutTimestamp := uint64(suite.chainB.GetContext().BlockTime().UnixNano()) - sequence, err := path.EndpointA.SendPacket(timeoutHeight, timeoutTimestamp, ibctesting.MockPacketData) - suite.Require().NoError(err) + sequence, err := path.EndpointA.SendPacket(timeoutHeight, timeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) - packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, timeoutHeight, timeoutTimestamp) - chanCap = capabilitytypes.NewCapability(100) - }, false}, + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, timeoutHeight, timeoutTimestamp) + chanCap = suite.chainA.GetChannelCapability(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + + channel := path.EndpointA.GetChannel() + channel.State = types.FLUSHING + path.EndpointA.SetChannel(channel) + }, + func(packetCommitment []byte, err error) { + suite.Require().NoError(err) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.FLUSHING, channel.State, "channel state should still be FLUSHING") + }, + nil, + }, + { + "conterparty upgrade timed out (abort)", + func() { + suite.coordinator.Setup(path) + + timeoutHeight := clienttypes.GetSelfHeight(suite.chainB.GetContext()) + timeoutTimestamp := uint64(suite.chainB.GetContext().BlockTime().UnixNano()) + + sequence, err := path.EndpointA.SendPacket(timeoutHeight, timeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, timeoutHeight, timeoutTimestamp) + chanCap = suite.chainA.GetChannelCapability(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + + channel := path.EndpointA.GetChannel() + channel.State = types.FLUSHING + path.EndpointA.SetChannel(channel) + path.EndpointA.SetChannelUpgrade(types.Upgrade{ + Fields: path.EndpointA.GetProposedUpgrade().Fields, + Timeout: types.NewTimeout(clienttypes.ZeroHeight(), 1), + }) + path.EndpointA.SetChannelCounterpartyUpgrade(types.Upgrade{ + Timeout: types.NewTimeout(clienttypes.ZeroHeight(), 1), + }) + }, + func(packetCommitment []byte, err error) { + suite.Require().NoError(err) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.OPEN, channel.State, "channel state should still be OPEN") + + upgrade, found := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().False(found, "upgrade should not be present") + suite.Require().Equal(types.Upgrade{}, upgrade, "upgrade should be zero value") + + upgrade, found = suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetCounterpartyUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().False(found, "counterparty upgrade should not be present") + suite.Require().Equal(types.Upgrade{}, upgrade, "counterparty upgrade should be zero value") + + errorReceipt, found := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found, "error receipt should be present") + suite.Require().Equal(channel.UpgradeSequence, errorReceipt.Sequence, "error receipt sequence should be equal to channel upgrade sequence") + }, + nil, + }, + { + "conterparty upgrade has not timed out with in-flight packets", + func() { + suite.coordinator.Setup(path) + + timeoutHeight := clienttypes.GetSelfHeight(suite.chainB.GetContext()) + timeoutTimestamp := uint64(suite.chainB.GetContext().BlockTime().UnixNano()) + + // we are sending two packets here as one will be removed in TimeoutExecuted. This is to ensure that + // there is still an in-flight packet so that the channel remains in the flushing state. + _, err := path.EndpointA.SendPacket(timeoutHeight, timeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + + sequence, err := path.EndpointA.SendPacket(timeoutHeight, timeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, timeoutHeight, timeoutTimestamp) + chanCap = suite.chainA.GetChannelCapability(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + + channel := path.EndpointA.GetChannel() + channel.State = types.FLUSHING + path.EndpointA.SetChannel(channel) + path.EndpointA.SetChannelUpgrade(types.Upgrade{ + Fields: path.EndpointA.GetProposedUpgrade().Fields, + Timeout: types.NewTimeout(clienttypes.ZeroHeight(), uint64(suite.chainA.GetContext().BlockTime().UnixNano())+types.DefaultTimeout.Timestamp), + }) + path.EndpointA.SetChannelCounterpartyUpgrade(types.Upgrade{ + Timeout: types.NewTimeout(clienttypes.ZeroHeight(), uint64(suite.chainB.GetContext().BlockTime().UnixNano())+types.DefaultTimeout.Timestamp), + }) + }, + func(packetCommitment []byte, err error) { + suite.Require().NoError(err) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.FLUSHING, channel.State, "channel state should still be FLUSHING") + + _, found := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found, "upgrade should not be deleted") + + _, found = suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetCounterpartyUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found, "counterparty upgrade should not be deleted") + + _, found = suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().False(found, "error receipt should not be written") + }, + nil, + }, + { + "ordered channel is closed and upgrade is aborted when timeout is executed", + func() { + path.SetChannelOrdered() + suite.coordinator.Setup(path) + + timeoutHeight := clienttypes.GetSelfHeight(suite.chainB.GetContext()) + timeoutTimestamp := uint64(suite.chainB.GetContext().BlockTime().UnixNano()) + + sequence, err := path.EndpointA.SendPacket(timeoutHeight, timeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, timeoutHeight, timeoutTimestamp) + chanCap = suite.chainA.GetChannelCapability(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + + channel := path.EndpointA.GetChannel() + channel.State = types.FLUSHING + path.EndpointA.SetChannel(channel) + path.EndpointA.SetChannelUpgrade(types.Upgrade{ + Fields: path.EndpointA.GetProposedUpgrade().Fields, + Timeout: types.NewTimeout(clienttypes.ZeroHeight(), 1), + }) + path.EndpointA.SetChannelCounterpartyUpgrade(types.Upgrade{ + Timeout: types.NewTimeout(clienttypes.ZeroHeight(), 1), + }) + }, + func(packetCommitment []byte, err error) { + suite.Require().NoError(err) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.CLOSED, channel.State, "channel state should be CLOSED") + + upgrade, found := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().False(found, "upgrade should not be present") + suite.Require().Equal(types.Upgrade{}, upgrade, "upgrade should be zero value") + + upgrade, found = suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetCounterpartyUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().False(found, "counterparty upgrade should not be present") + suite.Require().Equal(types.Upgrade{}, upgrade, "counterparty upgrade should be zero value") + + errorReceipt, found := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found, "error receipt should be present") + suite.Require().Equal(channel.UpgradeSequence, errorReceipt.Sequence, "error receipt sequence should be equal to channel upgrade sequence") + }, + nil, + }, } for i, tc := range testCases { @@ -294,17 +520,20 @@ func (suite *KeeperTestSuite) TestTimeoutExecuted() { suite.Run(fmt.Sprintf("Case %s, %d/%d tests", tc.msg, i, len(testCases)), func() { suite.SetupTest() // reset path = ibctesting.NewPath(suite.chainA, suite.chainB) + ctx := suite.chainA.GetContext() tc.malleate() - err := suite.chainA.App.GetIBCKeeper().ChannelKeeper.TimeoutExecuted(suite.chainA.GetContext(), chanCap, packet) - pc := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetPacketCommitment(suite.chainA.GetContext(), packet.GetSourcePort(), packet.GetSourceChannel(), packet.GetSequence()) + err := suite.chainA.App.GetIBCKeeper().ChannelKeeper.TimeoutExecuted(ctx, chanCap, packet) + pc := suite.chainA.App.GetIBCKeeper().ChannelKeeper.GetPacketCommitment(ctx, packet.GetSourcePort(), packet.GetSourceChannel(), packet.GetSequence()) - if tc.expPass { - suite.NoError(err) - suite.Nil(pc) - } else { - suite.Error(err) + tc.expResult(pc, err) + if tc.expEvents != nil { + events := ctx.EventManager().ABCIEvents() + + expEvents := tc.expEvents(path) + + ibctesting.AssertEventsLegacy(&suite.Suite, expEvents, events) } }) } @@ -314,11 +543,12 @@ func (suite *KeeperTestSuite) TestTimeoutExecuted() { // channel on chainB after the packet commitment has been created. func (suite *KeeperTestSuite) TestTimeoutOnClose() { var ( - path *ibctesting.Path - packet types.Packet - chanCap *capabilitytypes.Capability - nextSeqRecv uint64 - ordered bool + path *ibctesting.Path + packet types.Packet + chanCap *capabilitytypes.Capability + nextSeqRecv uint64 + counterpartyUpgradeSequence uint64 + ordered bool ) testCases := []testCase{ @@ -483,6 +713,34 @@ func (suite *KeeperTestSuite) TestTimeoutOnClose() { packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, clienttypes.GetSelfHeight(suite.chainB.GetContext()), uint64(suite.chainB.GetContext().BlockTime().UnixNano())) chanCap = capabilitytypes.NewCapability(100) }, false}, + { + "failure: invalid counterparty upgrade sequence", + func() { + ordered = false + suite.coordinator.Setup(path) + + timeoutHeight := clienttypes.GetSelfHeight(suite.chainB.GetContext()) + + sequence, err := path.EndpointA.SendPacket(timeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + + // trigger upgradeInit on B which will bump the counterparty upgrade sequence. + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + err = path.EndpointB.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.SetChannelState(types.CLOSED) + suite.Require().NoError(err) + + // need to update chainA's client representing chainB to prove missing ack + err = path.EndpointA.UpdateClient() + suite.Require().NoError(err) + + packet = types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, timeoutHeight, disabledTimeoutTimestamp) + chanCap = suite.chainA.GetChannelCapability(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + }, + false, + }, } for i, tc := range testCases { @@ -490,8 +748,9 @@ func (suite *KeeperTestSuite) TestTimeoutOnClose() { suite.Run(fmt.Sprintf("Case %s, %d/%d tests", tc.msg, i, len(testCases)), func() { var proof []byte - suite.SetupTest() // reset - nextSeqRecv = 1 // must be explicitly changed + suite.SetupTest() // reset + nextSeqRecv = 1 // must be explicitly changed + counterpartyUpgradeSequence = 0 // must be explicitly changed path = ibctesting.NewPath(suite.chainA, suite.chainB) tc.malleate() @@ -508,7 +767,16 @@ func (suite *KeeperTestSuite) TestTimeoutOnClose() { proof, _ = suite.chainB.QueryProof(unorderedPacketKey) } - err := suite.chainA.App.GetIBCKeeper().ChannelKeeper.TimeoutOnClose(suite.chainA.GetContext(), chanCap, packet, proof, proofClosed, proofHeight, nextSeqRecv) + err := suite.chainA.App.GetIBCKeeper().ChannelKeeper.TimeoutOnClose( + suite.chainA.GetContext(), + chanCap, + packet, + proof, + proofClosed, + proofHeight, + nextSeqRecv, + counterpartyUpgradeSequence, + ) if tc.expPass { suite.Require().NoError(err) diff --git a/modules/core/04-channel/keeper/upgrade.go b/modules/core/04-channel/keeper/upgrade.go new file mode 100644 index 00000000000..5f451955606 --- /dev/null +++ b/modules/core/04-channel/keeper/upgrade.go @@ -0,0 +1,1015 @@ +package keeper + +import ( + "fmt" + "reflect" + "slices" + + errorsmod "cosmossdk.io/errors" + sdkmath "cosmossdk.io/math" + + "github.com/cosmos/cosmos-sdk/telemetry" + sdk "github.com/cosmos/cosmos-sdk/types" + + clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" + connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" + "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" + commitmenttypes "github.com/cosmos/ibc-go/v8/modules/core/23-commitment/types" + "github.com/cosmos/ibc-go/v8/modules/core/exported" +) + +// ChanUpgradeInit is called by a module to initiate a channel upgrade handshake with +// a module on another chain. +func (k Keeper) ChanUpgradeInit( + ctx sdk.Context, + portID string, + channelID string, + upgradeFields types.UpgradeFields, +) (types.Upgrade, error) { + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + return types.Upgrade{}, errorsmod.Wrapf(types.ErrChannelNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + if channel.State != types.OPEN { + return types.Upgrade{}, errorsmod.Wrapf(types.ErrInvalidChannelState, "expected %s, got %s", types.OPEN, channel.State) + } + + if err := k.validateSelfUpgradeFields(ctx, upgradeFields, channel); err != nil { + return types.Upgrade{}, err + } + + // NOTE: the Upgrade returned here is intentionally not fully populated. The Timeout remains unset + // until the counterparty calls ChanUpgradeTry. + return types.Upgrade{Fields: upgradeFields}, nil +} + +// WriteUpgradeInitChannel writes a channel which has successfully passed the UpgradeInit handshake step. +// An event is emitted for the handshake step. +func (k Keeper) WriteUpgradeInitChannel(ctx sdk.Context, portID, channelID string, upgrade types.Upgrade, upgradeVersion string) (types.Channel, types.Upgrade) { + defer telemetry.IncrCounter(1, "ibc", "channel", "upgrade-init") + + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + panic(fmt.Errorf("could not find existing channel when updating channel state in successful ChanUpgradeInit step, channelID: %s, portID: %s", channelID, portID)) + } + + channel.UpgradeSequence++ + + upgrade.Fields.Version = upgradeVersion + + k.SetChannel(ctx, portID, channelID, channel) + k.SetUpgrade(ctx, portID, channelID, upgrade) + + k.Logger(ctx).Info("channel state updated", "port-id", portID, "channel-id", channelID, "state", channel.State, "upgrade-sequence", fmt.Sprintf("%d", channel.UpgradeSequence)) + + return channel, upgrade +} + +// ChanUpgradeTry is called by a module to accept the first step of a channel upgrade handshake initiated by +// a module on another chain. If this function is successful, the proposed upgrade will be returned. If the upgrade fails, the upgrade sequence will still be incremented but an error will be returned. +func (k Keeper) ChanUpgradeTry( + ctx sdk.Context, + portID, + channelID string, + proposedConnectionHops []string, + counterpartyUpgradeFields types.UpgradeFields, + counterpartyUpgradeSequence uint64, + proofCounterpartyChannel, + proofCounterpartyUpgrade []byte, + proofHeight clienttypes.Height, +) (types.Channel, types.Upgrade, error) { + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + return types.Channel{}, types.Upgrade{}, errorsmod.Wrapf(types.ErrChannelNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + if !channel.IsOpen() { + return types.Channel{}, types.Upgrade{}, errorsmod.Wrapf(types.ErrInvalidChannelState, "expected %s, got %s", types.OPEN, channel.State) + } + + connection, found := k.connectionKeeper.GetConnection(ctx, channel.ConnectionHops[0]) + if !found { + return types.Channel{}, types.Upgrade{}, errorsmod.Wrap(connectiontypes.ErrConnectionNotFound, channel.ConnectionHops[0]) + } + + if connection.GetState() != int32(connectiontypes.OPEN) { + return types.Channel{}, types.Upgrade{}, errorsmod.Wrapf( + connectiontypes.ErrInvalidConnectionState, "connection state is not OPEN (got %s)", connectiontypes.State(connection.GetState()).String(), + ) + } + + // construct expected counterparty channel from information in state + // only the counterpartyUpgradeSequence is provided by the relayer + counterpartyConnectionHops := []string{connection.GetCounterparty().GetConnectionID()} + counterpartyChannel := types.Channel{ + State: types.OPEN, + Ordering: channel.Ordering, + Counterparty: types.NewCounterparty(portID, channelID), + ConnectionHops: counterpartyConnectionHops, + Version: channel.Version, + UpgradeSequence: counterpartyUpgradeSequence, // provided by the relayer + } + + // verify the counterparty channel state containing the upgrade sequence + if err := k.connectionKeeper.VerifyChannelState( + ctx, + connection, + proofHeight, proofCounterpartyChannel, + channel.Counterparty.PortId, + channel.Counterparty.ChannelId, + counterpartyChannel, + ); err != nil { + return types.Channel{}, types.Upgrade{}, errorsmod.Wrap(err, "failed to verify counterparty channel state") + } + + var ( + err error + upgrade types.Upgrade + isCrossingHello bool + ) + + upgrade, isCrossingHello = k.GetUpgrade(ctx, portID, channelID) + if counterpartyUpgradeSequence < channel.UpgradeSequence { + // In this case, the counterparty upgrade is outdated. We want to force the counterparty + // to abort their upgrade and come back to sync with our own upgrade sequence. + var upgradeSequence uint64 + if isCrossingHello { + // In the crossing hello case, we already have an upgrade but it is at a higher sequence than the counterparty. + // Thus, our upgrade should take priority. We force the counterparty to abort their upgrade by invalidating all counterparty + // upgrade attempts below our own sequence by setting errorReceipt to upgradeSequence - 1. + // The upgrade handshake may then proceed on the counterparty with our sequence + upgradeSequence = channel.UpgradeSequence - 1 + } else { + // In the case, that we are in a non-crossing hello (i.e. upgrade does not exist on our side), + // the sequence on both sides should move to a fresh sequence on the next upgrade attempt. + // Thus, we write an error receipt with our own upgrade sequence which will cause the counterparty + // to cancel their upgrade and move to the same sequence. When a new upgrade attempt is started from either + // side, it will be a fresh sequence for both sides (i.e. channel.upgradeSequence + 1) + upgradeSequence = channel.UpgradeSequence + } + + // NOTE: Two possible outcomes may occur in this scenario. + // The ChanUpgradeCancel datagram may reach the counterparty first, which will cause the counterparty to cancel. The counterparty + // may then receive a TRY with our channel upgrade sequence and correctly increment their sequence to become synced with our upgrade attempt. + // The ChanUpgradeTry message may arrive first, in this case, **IF** the upgrade fields are mutually compatible; the counterparty will simply + // fast forward their sequence to our own and continue the upgrade. The following ChanUpgradeCancel message will be rejected as it is below the current sequence. + + return channel, upgrade, types.NewUpgradeError(upgradeSequence, errorsmod.Wrapf( + types.ErrInvalidUpgradeSequence, "counterparty upgrade sequence < current upgrade sequence (%d < %d)", counterpartyUpgradeSequence, channel.UpgradeSequence, + )) + } + + // verifies the proof that a particular proposed upgrade has been stored in the upgrade path of the counterparty + if err := k.connectionKeeper.VerifyChannelUpgrade( + ctx, + connection, + proofHeight, proofCounterpartyUpgrade, + channel.Counterparty.PortId, + channel.Counterparty.ChannelId, + types.NewUpgrade(counterpartyUpgradeFields, types.Timeout{}, 0), + ); err != nil { + return types.Channel{}, types.Upgrade{}, errorsmod.Wrap(err, "failed to verify counterparty upgrade") + } + + // construct counterpartyChannel from existing information and provided counterpartyUpgradeSequence + // create upgrade fields from counterparty proposed upgrade and own verified connection hops + proposedUpgradeFields := types.UpgradeFields{ + Ordering: counterpartyUpgradeFields.Ordering, + ConnectionHops: proposedConnectionHops, + Version: counterpartyUpgradeFields.Version, + } + + // NOTE: if an upgrade exists (crossing hellos) then use existing upgrade fields + // otherwise, run the upgrade init sub-protocol + if isCrossingHello { + proposedUpgradeFields = upgrade.Fields + } else { + // NOTE: OnChanUpgradeInit will not be executed by the application + upgrade, err = k.ChanUpgradeInit(ctx, portID, channelID, proposedUpgradeFields) + if err != nil { + return types.Channel{}, types.Upgrade{}, errorsmod.Wrap(err, "failed to initialize upgrade") + } + + channel, upgrade = k.WriteUpgradeInitChannel(ctx, portID, channelID, upgrade, upgrade.Fields.Version) + } + + if err := k.checkForUpgradeCompatibility(ctx, proposedUpgradeFields, counterpartyUpgradeFields); err != nil { + return types.Channel{}, types.Upgrade{}, errorsmod.Wrap(err, "failed upgrade compatibility check") + } + + // if the counterparty sequence is greater than the current sequence, we fast-forward to the counterparty sequence. + if counterpartyUpgradeSequence > channel.UpgradeSequence { + channel.UpgradeSequence = counterpartyUpgradeSequence + k.SetChannel(ctx, portID, channelID, channel) + } + + if err := k.startFlushing(ctx, portID, channelID, &upgrade); err != nil { + return types.Channel{}, types.Upgrade{}, err + } + + return channel, upgrade, nil +} + +// WriteUpgradeTryChannel writes the channel end and upgrade to state after successfully passing the UpgradeTry handshake step. +// An event is emitted for the handshake step. +func (k Keeper) WriteUpgradeTryChannel(ctx sdk.Context, portID, channelID string, upgrade types.Upgrade, upgradeVersion string) (types.Channel, types.Upgrade) { + defer telemetry.IncrCounter(1, "ibc", "channel", "upgrade-try") + + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + panic(fmt.Errorf("could not find existing channel when updating channel state in successful ChanUpgradeTry step, channelID: %s, portID: %s", channelID, portID)) + } + + upgrade.Fields.Version = upgradeVersion + k.SetUpgrade(ctx, portID, channelID, upgrade) + + k.Logger(ctx).Info("channel state updated", "port-id", portID, "channel-id", channelID, "previous-state", types.OPEN, "new-state", channel.State) + + return channel, upgrade +} + +// ChanUpgradeAck is called by a module to accept the ACKUPGRADE handshake step of the channel upgrade protocol. +// This method should only be called by the IBC core msg server. +// This method will verify that the counterparty has called the ChanUpgradeTry handler. +// and that its own upgrade is compatible with the selected counterparty version. +// NOTE: the channel may be in either the OPEN or FLUSHING state. +// The channel may be in OPEN if we are in the happy path. +// +// A -> Init (OPEN), B -> Try (FLUSHING), A -> Ack (begins in OPEN) +// +// The channel may be in FLUSHING if we are in a crossing hellos situation. +// +// A -> Init (OPEN), B -> Init (OPEN) -> A -> Try (FLUSHING), B -> Try (FLUSHING), A -> Ack (begins in FLUSHING) +func (k Keeper) ChanUpgradeAck( + ctx sdk.Context, + portID, + channelID string, + counterpartyUpgrade types.Upgrade, + proofChannel, + proofUpgrade []byte, + proofHeight clienttypes.Height, +) error { + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(types.ErrChannelNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + if !slices.Contains([]types.State{types.OPEN, types.FLUSHING}, channel.State) { + return errorsmod.Wrapf(types.ErrInvalidChannelState, "expected one of [%s, %s], got %s", types.OPEN, types.FLUSHING, channel.State) + } + + connection, found := k.connectionKeeper.GetConnection(ctx, channel.ConnectionHops[0]) + if !found { + return errorsmod.Wrap(connectiontypes.ErrConnectionNotFound, channel.ConnectionHops[0]) + } + + if connection.GetState() != int32(connectiontypes.OPEN) { + return errorsmod.Wrapf(connectiontypes.ErrInvalidConnectionState, "connection state is not OPEN (got %s)", connectiontypes.State(connection.GetState()).String()) + } + + counterpartyHops := []string{connection.GetCounterparty().GetConnectionID()} + counterpartyChannel := types.Channel{ + State: types.FLUSHING, + Ordering: channel.Ordering, + ConnectionHops: counterpartyHops, + Counterparty: types.NewCounterparty(portID, channelID), + Version: channel.Version, + UpgradeSequence: channel.UpgradeSequence, + } + + // verify the counterparty channel state containing the upgrade sequence + if err := k.connectionKeeper.VerifyChannelState( + ctx, + connection, + proofHeight, proofChannel, + channel.Counterparty.PortId, + channel.Counterparty.ChannelId, + counterpartyChannel, + ); err != nil { + return errorsmod.Wrap(err, "failed to verify counterparty channel state") + } + + // verifies the proof that a particular proposed upgrade has been stored in the upgrade path of the counterparty + if err := k.connectionKeeper.VerifyChannelUpgrade( + ctx, + connection, + proofHeight, proofUpgrade, + channel.Counterparty.PortId, + channel.Counterparty.ChannelId, + counterpartyUpgrade, + ); err != nil { + return errorsmod.Wrap(err, "failed to verify counterparty upgrade") + } + + upgrade, found := k.GetUpgrade(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(types.ErrUpgradeNotFound, "failed to retrieve channel upgrade: port ID (%s) channel ID (%s)", portID, channelID) + } + + // optimistically accept version that TRY chain proposes and pass this to callback for confirmation + // in the crossing hello case, we do not modify version that our TRY call returned and instead enforce + // that both TRY calls returned the same version. It is possible that this will fail in the OnChanUpgradeAck + // callback if the version is invalid. + if channel.IsOpen() { + upgrade.Fields.Version = counterpartyUpgrade.Fields.Version + } + + // if upgrades are not compatible by ACK step, then we restore the channel + if err := k.checkForUpgradeCompatibility(ctx, upgrade.Fields, counterpartyUpgrade.Fields); err != nil { + return types.NewUpgradeError(channel.UpgradeSequence, err) + } + + if channel.IsOpen() { + if err := k.startFlushing(ctx, portID, channelID, &upgrade); err != nil { + return err + } + } + + timeout := counterpartyUpgrade.Timeout + selfHeight, selfTimestamp := clienttypes.GetSelfHeight(ctx), uint64(ctx.BlockTime().UnixNano()) + + if timeout.Elapsed(selfHeight, selfTimestamp) { + return types.NewUpgradeError(channel.UpgradeSequence, errorsmod.Wrap(timeout.ErrTimeoutElapsed(selfHeight, selfTimestamp), "counterparty upgrade timeout elapsed")) + } + + return nil +} + +// WriteUpgradeAckChannel writes a channel which has successfully passed the UpgradeAck handshake step as well as +// setting the upgrade for that channel. +// An event is emitted for the handshake step. +func (k Keeper) WriteUpgradeAckChannel(ctx sdk.Context, portID, channelID string, counterpartyUpgrade types.Upgrade) (types.Channel, types.Upgrade) { + defer telemetry.IncrCounter(1, "ibc", "channel", "upgrade-ack") + + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + panic(fmt.Errorf("could not find existing channel when updating channel state in successful ChanUpgradeAck step, channelID: %s, portID: %s", channelID, portID)) + } + + if !k.HasInflightPackets(ctx, portID, channelID) { + channel.State = types.FLUSHCOMPLETE + k.SetChannel(ctx, portID, channelID, channel) + } + + upgrade, found := k.GetUpgrade(ctx, portID, channelID) + if !found { + panic(fmt.Errorf("could not find existing upgrade when updating channel state in successful ChanUpgradeAck step, channelID: %s, portID: %s", channelID, portID)) + } + + upgrade.Fields.Version = counterpartyUpgrade.Fields.Version + + k.SetUpgrade(ctx, portID, channelID, upgrade) + k.SetCounterpartyUpgrade(ctx, portID, channelID, counterpartyUpgrade) + + k.Logger(ctx).Info("channel state updated", "port-id", portID, "channel-id", channelID, "state", channel.State.String()) + return channel, upgrade +} + +// ChanUpgradeConfirm is called on the chain which is on FLUSHING after chanUpgradeAck is called on the counterparty. +// This will inform the TRY chain of the timeout set on ACK by the counterparty. If the timeout has already exceeded, we will write an error receipt and restore. +func (k Keeper) ChanUpgradeConfirm( + ctx sdk.Context, + portID, + channelID string, + counterpartyChannelState types.State, + counterpartyUpgrade types.Upgrade, + proofChannel, + proofUpgrade []byte, + proofHeight clienttypes.Height, +) error { + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(types.ErrChannelNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + if channel.State != types.FLUSHING { + return errorsmod.Wrapf(types.ErrInvalidChannelState, "expected %s, got %s", types.FLUSHING, channel.State) + } + + if !slices.Contains([]types.State{types.FLUSHING, types.FLUSHCOMPLETE}, counterpartyChannelState) { + return errorsmod.Wrapf(types.ErrInvalidCounterparty, "expected one of [%s, %s], got %s", types.FLUSHING, types.FLUSHCOMPLETE, counterpartyChannelState) + } + + connection, found := k.connectionKeeper.GetConnection(ctx, channel.ConnectionHops[0]) + if !found { + return errorsmod.Wrap(connectiontypes.ErrConnectionNotFound, channel.ConnectionHops[0]) + } + + if connection.GetState() != int32(connectiontypes.OPEN) { + return errorsmod.Wrapf(connectiontypes.ErrInvalidConnectionState, "connection state is not OPEN (got %s)", connectiontypes.State(connection.GetState()).String()) + } + + counterpartyHops := []string{connection.GetCounterparty().GetConnectionID()} + counterpartyChannel := types.Channel{ + State: counterpartyChannelState, + Ordering: channel.Ordering, + ConnectionHops: counterpartyHops, + Counterparty: types.NewCounterparty(portID, channelID), + Version: channel.Version, + UpgradeSequence: channel.UpgradeSequence, + } + + if err := k.connectionKeeper.VerifyChannelState( + ctx, + connection, + proofHeight, proofChannel, + channel.Counterparty.PortId, + channel.Counterparty.ChannelId, + counterpartyChannel, + ); err != nil { + return errorsmod.Wrap(err, "failed to verify counterparty channel state") + } + + if err := k.connectionKeeper.VerifyChannelUpgrade( + ctx, + connection, + proofHeight, proofUpgrade, + channel.Counterparty.PortId, + channel.Counterparty.ChannelId, + counterpartyUpgrade, + ); err != nil { + return errorsmod.Wrap(err, "failed to verify counterparty upgrade") + } + + timeout := counterpartyUpgrade.Timeout + selfHeight, selfTimestamp := clienttypes.GetSelfHeight(ctx), uint64(ctx.BlockTime().UnixNano()) + + if timeout.Elapsed(selfHeight, selfTimestamp) { + return types.NewUpgradeError(channel.UpgradeSequence, errorsmod.Wrap(timeout.ErrTimeoutElapsed(selfHeight, selfTimestamp), "counterparty upgrade timeout elapsed")) + } + + return nil +} + +// WriteUpgradeConfirmChannel writes a channel which has successfully passed the ChanUpgradeConfirm handshake step. +// If the channel has no in-flight packets, its state is updated to indicate that flushing has completed. Otherwise, the counterparty upgrade is set +// and the channel state is left unchanged. +// An event is emitted for the handshake step. +func (k Keeper) WriteUpgradeConfirmChannel(ctx sdk.Context, portID, channelID string, counterpartyUpgrade types.Upgrade) types.Channel { + defer telemetry.IncrCounter(1, "ibc", "channel", "upgrade-confirm") + + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + panic(fmt.Errorf("could not find existing channel when updating channel state in successful ChanUpgradeConfirm step, channelID: %s, portID: %s", channelID, portID)) + } + + if !k.HasInflightPackets(ctx, portID, channelID) { + previousState := channel.State + channel.State = types.FLUSHCOMPLETE + k.SetChannel(ctx, portID, channelID, channel) + k.Logger(ctx).Info("channel state updated", "port-id", portID, "channel-id", channelID, "previous-state", previousState, "new-state", channel.State) + } + + k.SetCounterpartyUpgrade(ctx, portID, channelID, counterpartyUpgrade) + return channel +} + +// ChanUpgradeOpen is called by a module to complete the channel upgrade handshake and move the channel back to an OPEN state. +// This method should only be called after both channels have flushed any in-flight packets. +// This method should only be called directly by the core IBC message server. +func (k Keeper) ChanUpgradeOpen( + ctx sdk.Context, + portID, + channelID string, + counterpartyChannelState types.State, + proofCounterpartyChannel []byte, + proofHeight clienttypes.Height, +) error { + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(types.ErrChannelNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + if channel.State != types.FLUSHCOMPLETE { + return errorsmod.Wrapf(types.ErrInvalidChannelState, "expected %s, got %s", types.FLUSHCOMPLETE, channel.State) + } + + connection, found := k.connectionKeeper.GetConnection(ctx, channel.ConnectionHops[0]) + if !found { + return errorsmod.Wrap(connectiontypes.ErrConnectionNotFound, channel.ConnectionHops[0]) + } + + if connection.GetState() != int32(connectiontypes.OPEN) { + return errorsmod.Wrapf(connectiontypes.ErrInvalidConnectionState, "connection state is not OPEN (got %s)", connectiontypes.State(connection.GetState()).String()) + } + + var counterpartyChannel types.Channel + switch counterpartyChannelState { + case types.OPEN: + upgrade, found := k.GetUpgrade(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(types.ErrUpgradeNotFound, "failed to retrieve channel upgrade: port ID (%s) channel ID (%s)", portID, channelID) + } + // If counterparty has reached OPEN, we must use the upgraded connection to verify the counterparty channel + upgradeConnection, found := k.connectionKeeper.GetConnection(ctx, upgrade.Fields.ConnectionHops[0]) + if !found { + return errorsmod.Wrap(connectiontypes.ErrConnectionNotFound, upgrade.Fields.ConnectionHops[0]) + } + + if upgradeConnection.GetState() != int32(connectiontypes.OPEN) { + return errorsmod.Wrapf(connectiontypes.ErrInvalidConnectionState, "connection state is not OPEN (got %s)", connectiontypes.State(upgradeConnection.GetState()).String()) + } + + counterpartyChannel = types.Channel{ + State: types.OPEN, + Ordering: upgrade.Fields.Ordering, + ConnectionHops: []string{upgradeConnection.GetCounterparty().GetConnectionID()}, + Counterparty: types.NewCounterparty(portID, channelID), + Version: upgrade.Fields.Version, + UpgradeSequence: channel.UpgradeSequence, + } + + case types.FLUSHCOMPLETE: + counterpartyChannel = types.Channel{ + State: types.FLUSHCOMPLETE, + Ordering: channel.Ordering, + ConnectionHops: []string{connection.GetCounterparty().GetConnectionID()}, + Counterparty: types.NewCounterparty(portID, channelID), + Version: channel.Version, + UpgradeSequence: channel.UpgradeSequence, + } + + default: + return errorsmod.Wrapf(types.ErrInvalidCounterparty, "counterparty channel state must be one of [%s, %s], got %s", types.OPEN, types.FLUSHCOMPLETE, counterpartyChannelState) + } + + if err := k.connectionKeeper.VerifyChannelState( + ctx, + connection, + proofHeight, proofCounterpartyChannel, + channel.Counterparty.PortId, + channel.Counterparty.ChannelId, + counterpartyChannel, + ); err != nil { + return errorsmod.Wrap(err, "failed to verify counterparty channel") + } + + return nil +} + +// WriteUpgradeOpenChannel writes the agreed upon upgrade fields to the channel, and sets the channel state back to OPEN. This can be called in one of two cases: +// - In the UpgradeConfirm step of the handshake if both sides have already flushed all in-flight packets. +// - In the UpgradeOpen step of the handshake. +func (k Keeper) WriteUpgradeOpenChannel(ctx sdk.Context, portID, channelID string) types.Channel { + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + panic(fmt.Errorf("could not find existing channel when updating channel state, channelID: %s, portID: %s", channelID, portID)) + } + + upgrade, found := k.GetUpgrade(ctx, portID, channelID) + if !found { + panic(fmt.Errorf("could not find upgrade when updating channel state, channelID: %s, portID: %s", channelID, portID)) + } + + counterpartyUpgrade, found := k.GetCounterpartyUpgrade(ctx, portID, channelID) + if !found { + panic(fmt.Errorf("could not find counterparty upgrade when updating channel state, channelID: %s, portID: %s", channelID, portID)) + } + + // next seq recv and ack is used for ordered channels to verify the packet has been received/acked in the correct order + // this is no longer necessary if the channel is UNORDERED and should be reset to 1 + if channel.Ordering == types.ORDERED && upgrade.Fields.Ordering == types.UNORDERED { + k.SetNextSequenceRecv(ctx, portID, channelID, 1) + k.SetNextSequenceAck(ctx, portID, channelID, 1) + } + + // next seq recv and ack should updated when moving from UNORDERED to ORDERED using the counterparty NextSequenceSend as set just after blocking new packet sends. + // we can be sure that the next packet we are set to receive will be the first packet the counterparty sends after reopening. + // we can be sure that our next acknowledgement will be our first packet sent after upgrade, as the counterparty processed all sent packets after flushing completes. + if channel.Ordering == types.UNORDERED && upgrade.Fields.Ordering == types.ORDERED { + k.SetNextSequenceRecv(ctx, portID, channelID, counterpartyUpgrade.NextSequenceSend) + k.SetNextSequenceAck(ctx, portID, channelID, upgrade.NextSequenceSend) + } + + // set the counterparty next sequence send as pruning sequence end in order to have upper bound to prune to + k.SetPruningSequenceEnd(ctx, portID, channelID, counterpartyUpgrade.NextSequenceSend) + + // First upgrade for this channel will set the pruning sequence to 1, the starting sequence for pruning. + // Subsequent upgrades will not modify the pruning sequence thereby allowing pruning to continue from the last + // pruned sequence. + if !k.HasPruningSequenceStart(ctx, portID, channelID) { + k.SetPruningSequenceStart(ctx, portID, channelID, 1) + } + + // Switch channel fields to upgrade fields and set channel state to OPEN + previousState := channel.State + channel.Ordering = upgrade.Fields.Ordering + channel.Version = upgrade.Fields.Version + channel.ConnectionHops = upgrade.Fields.ConnectionHops + channel.State = types.OPEN + + k.SetChannel(ctx, portID, channelID, channel) + + // delete state associated with upgrade which is no longer required. + k.deleteUpgradeInfo(ctx, portID, channelID) + + k.Logger(ctx).Info("channel state updated", "port-id", portID, "channel-id", channelID, "previous-state", previousState.String(), "new-state", types.OPEN.String()) + return channel +} + +// ChanUpgradeCancel is called by the msg server to prove that an error receipt was written on the counterparty +// which constitutes a valid situation where the upgrade should be cancelled. An error is returned if sufficient evidence +// for cancelling the upgrade has not been provided. +func (k Keeper) ChanUpgradeCancel(ctx sdk.Context, portID, channelID string, errorReceipt types.ErrorReceipt, errorReceiptProof []byte, proofHeight clienttypes.Height) error { + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(types.ErrChannelNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + _, found = k.GetUpgrade(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(types.ErrUpgradeNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + // an error receipt proof must be provided. + if len(errorReceiptProof) == 0 { + return errorsmod.Wrap(commitmenttypes.ErrInvalidProof, "cannot submit an empty error receipt proof unless the sender is authorized to cancel upgrades AND channel is not in FLUSHCOMPLETE") + } + + // the error receipt should also have a sequence greater than or equal to the current upgrade sequence. + if errorReceipt.Sequence < channel.UpgradeSequence { + return errorsmod.Wrapf(types.ErrInvalidUpgradeSequence, "error receipt sequence (%d) must be greater than or equal to current upgrade sequence (%d)", errorReceipt.Sequence, channel.UpgradeSequence) + } + + // get underlying connection for proof verification + connection, found := k.connectionKeeper.GetConnection(ctx, channel.ConnectionHops[0]) + if !found { + return errorsmod.Wrap(connectiontypes.ErrConnectionNotFound, channel.ConnectionHops[0]) + } + + if connection.GetState() != int32(connectiontypes.OPEN) { + return errorsmod.Wrapf( + connectiontypes.ErrInvalidConnectionState, + "connection state is not OPEN (got %s)", connectiontypes.State(connection.GetState()).String(), + ) + } + + if err := k.connectionKeeper.VerifyChannelUpgradeError( + ctx, + connection, + proofHeight, + errorReceiptProof, + channel.Counterparty.PortId, + channel.Counterparty.ChannelId, + errorReceipt, + ); err != nil { + return errorsmod.Wrap(err, "failed to verify counterparty error receipt") + } + + return nil +} + +// WriteUpgradeCancelChannel writes a channel which has canceled the upgrade process.Auxiliary upgrade state is +// also deleted. +func (k Keeper) WriteUpgradeCancelChannel(ctx sdk.Context, portID, channelID string, sequence uint64) { + defer telemetry.IncrCounter(1, "ibc", "channel", "upgrade-cancel") + + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + panic(fmt.Errorf("could not find existing channel when updating channel state, channelID: %s, portID: %s", channelID, portID)) + } + + upgrade, found := k.GetUpgrade(ctx, portID, channelID) + if !found { + panic(fmt.Errorf("could not find upgrade when updating channel state, channelID: %s, portID: %s", channelID, portID)) + } + + previousState := channel.State + + channel = k.restoreChannel(ctx, portID, channelID, sequence, channel, types.NewUpgradeError(sequence, types.ErrInvalidUpgrade)) + + k.Logger(ctx).Info("channel state updated", "port-id", portID, "channel-id", channelID, "previous-state", previousState, "new-state", types.OPEN.String()) + EmitChannelUpgradeCancelEvent(ctx, portID, channelID, channel, upgrade) +} + +// ChanUpgradeTimeout times out an outstanding upgrade. +// This should be used by the initialising chain when the counterparty chain has not responded to an upgrade proposal within the specified timeout period. +func (k Keeper) ChanUpgradeTimeout( + ctx sdk.Context, + portID, channelID string, + counterpartyChannel types.Channel, + proofCounterpartyChannel []byte, + proofHeight exported.Height, +) error { + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(types.ErrChannelNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + if !slices.Contains([]types.State{types.FLUSHING, types.FLUSHCOMPLETE}, channel.State) { + return errorsmod.Wrapf(types.ErrInvalidChannelState, "expected one of [%s, %s], got %s", types.FLUSHING, types.FLUSHCOMPLETE, channel.State) + } + + upgrade, found := k.GetUpgrade(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(types.ErrUpgradeNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + connection, found := k.connectionKeeper.GetConnection(ctx, channel.ConnectionHops[0]) + if !found { + return errorsmod.Wrap( + connectiontypes.ErrConnectionNotFound, + channel.ConnectionHops[0], + ) + } + + if connection.GetState() != int32(connectiontypes.OPEN) { + return errorsmod.Wrapf( + connectiontypes.ErrInvalidConnectionState, + "connection state is not OPEN (got %s)", connectiontypes.State(connection.GetState()).String(), + ) + } + + proofTimestamp, err := k.connectionKeeper.GetTimestampAtHeight(ctx, connection, proofHeight) + if err != nil { + return err + } + + // proof must be from a height after timeout has elapsed. Either timeoutHeight or timeoutTimestamp must be defined. + // if timeoutHeight is defined and proof is from before timeout height, abort transaction + timeoutHeight := upgrade.Timeout.Height + timeoutTimeStamp := upgrade.Timeout.Timestamp + if (timeoutHeight.IsZero() || proofHeight.LT(timeoutHeight)) && + (timeoutTimeStamp == 0 || proofTimestamp < timeoutTimeStamp) { + return errorsmod.Wrap(types.ErrInvalidUpgradeTimeout, "upgrade timeout has not been reached for height or timestamp") + } + + // counterparty channel must be proved to still be in OPEN state or FLUSHING state. + if !slices.Contains([]types.State{types.OPEN, types.FLUSHING}, counterpartyChannel.State) { + return errorsmod.Wrapf(types.ErrInvalidCounterparty, "expected one of [%s, %s], got %s", types.OPEN, types.FLUSHING, counterpartyChannel.State) + } + + if counterpartyChannel.State == types.OPEN { + upgradeConnection, found := k.connectionKeeper.GetConnection(ctx, upgrade.Fields.ConnectionHops[0]) + if !found { + return errorsmod.Wrap( + connectiontypes.ErrConnectionNotFound, + upgrade.Fields.ConnectionHops[0], + ) + } + counterpartyHops := []string{upgradeConnection.GetCounterparty().GetConnectionID()} + + upgradeAlreadyComplete := upgrade.Fields.Version == counterpartyChannel.Version && upgrade.Fields.Ordering == counterpartyChannel.Ordering && upgrade.Fields.ConnectionHops[0] == counterpartyHops[0] + if upgradeAlreadyComplete { + // counterparty has already successfully upgraded so we cannot timeout + return errorsmod.Wrap(types.ErrUpgradeTimeoutFailed, "counterparty channel is already upgraded") + } + } + + if counterpartyChannel.UpgradeSequence < channel.UpgradeSequence { + return errorsmod.Wrapf(types.ErrInvalidUpgradeSequence, "counterparty channel upgrade sequence (%d) must be greater than or equal to current upgrade sequence (%d)", counterpartyChannel.UpgradeSequence, channel.UpgradeSequence) + } + + // verify the counterparty channel state + if err := k.connectionKeeper.VerifyChannelState( + ctx, + connection, + proofHeight, proofCounterpartyChannel, + channel.Counterparty.PortId, + channel.Counterparty.ChannelId, + counterpartyChannel, + ); err != nil { + return errorsmod.Wrap(err, "failed to verify counterparty channel state") + } + + return nil +} + +// WriteUpgradeTimeoutChannel restores the channel state of an initialising chain in the event that the counterparty chain has passed the timeout set in ChanUpgradeInit to the state before the upgrade was proposed. +// Auxiliary upgrade state is also deleted. +// An event is emitted for the handshake step. +func (k Keeper) WriteUpgradeTimeoutChannel( + ctx sdk.Context, + portID, channelID string, +) (types.Channel, types.Upgrade) { + defer telemetry.IncrCounter(1, "ibc", "channel", "upgrade-timeout") + + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + panic(fmt.Errorf("could not find existing channel when updating channel state in successful ChanUpgradeTimeout step, channelID: %s, portID: %s", channelID, portID)) + } + + upgrade, found := k.GetUpgrade(ctx, portID, channelID) + if !found { + panic(fmt.Errorf("could not find existing upgrade when cancelling channel upgrade, channelID: %s, portID: %s", channelID, portID)) + } + + channel = k.restoreChannel(ctx, portID, channelID, channel.UpgradeSequence, channel, types.NewUpgradeError(channel.UpgradeSequence, types.ErrUpgradeTimeout)) + + k.Logger(ctx).Info("channel state restored", "port-id", portID, "channel-id", channelID) + + return channel, upgrade +} + +// startFlushing will set the upgrade last packet send and continue blocking the upgrade from continuing until all +// in-flight packets have been flushed. +func (k Keeper) startFlushing(ctx sdk.Context, portID, channelID string, upgrade *types.Upgrade) error { + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(types.ErrChannelNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + connection, found := k.connectionKeeper.GetConnection(ctx, channel.ConnectionHops[0]) + if !found { + return errorsmod.Wrap(connectiontypes.ErrConnectionNotFound, channel.ConnectionHops[0]) + } + + if connection.GetState() != int32(connectiontypes.OPEN) { + return errorsmod.Wrapf(connectiontypes.ErrInvalidConnectionState, "connection state is not OPEN (got %s)", connectiontypes.State(connection.GetState()).String()) + } + + channel.State = types.FLUSHING + k.SetChannel(ctx, portID, channelID, channel) + + nextSequenceSend, found := k.GetNextSequenceSend(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(types.ErrSequenceSendNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + upgrade.NextSequenceSend = nextSequenceSend + upgrade.Timeout = k.getAbsoluteUpgradeTimeout(ctx) + k.SetUpgrade(ctx, portID, channelID, *upgrade) + + return nil +} + +// getAbsoluteUpgradeTimeout returns the absolute timeout for the given upgrade. +func (k Keeper) getAbsoluteUpgradeTimeout(ctx sdk.Context) types.Timeout { + upgradeTimeout := k.GetParams(ctx).UpgradeTimeout + return types.NewTimeout(clienttypes.ZeroHeight(), uint64(ctx.BlockTime().UnixNano())+upgradeTimeout.Timestamp) +} + +// syncUpgradeSequence ensures current upgrade handshake only continues if both channels are using the same upgrade sequence, +// otherwise an upgrade error is returned so that an error receipt will be written so that the upgrade handshake may be attempted again with synchronized sequences. +func (k Keeper) syncUpgradeSequence(ctx sdk.Context, portID, channelID string, channel types.Channel, counterpartyUpgradeSequence uint64) error { + // save the previous upgrade sequence for the error message + prevUpgradeSequence := channel.UpgradeSequence + + if counterpartyUpgradeSequence != channel.UpgradeSequence { + // error on the higher sequence so that both chains synchronize on a fresh sequence + channel.UpgradeSequence = sdkmath.Max(counterpartyUpgradeSequence, channel.UpgradeSequence) + k.SetChannel(ctx, portID, channelID, channel) + + return types.NewUpgradeError(channel.UpgradeSequence, errorsmod.Wrapf( + types.ErrInvalidUpgradeSequence, "expected upgrade sequence (%d) to match counterparty upgrade sequence (%d)", prevUpgradeSequence, counterpartyUpgradeSequence), + ) + } + + return nil +} + +// checkForUpgradeCompatibility checks performs stateful validation of self upgrade fields relative to counterparty upgrade. +func (k Keeper) checkForUpgradeCompatibility(ctx sdk.Context, upgradeFields, counterpartyUpgradeFields types.UpgradeFields) error { + // assert that both sides propose the same channel ordering + if upgradeFields.Ordering != counterpartyUpgradeFields.Ordering { + return errorsmod.Wrapf(types.ErrIncompatibleCounterpartyUpgrade, "expected upgrade ordering (%s) to match counterparty upgrade ordering (%s)", upgradeFields.Ordering, counterpartyUpgradeFields.Ordering) + } + + if upgradeFields.Version != counterpartyUpgradeFields.Version { + return errorsmod.Wrapf(types.ErrIncompatibleCounterpartyUpgrade, "expected upgrade version (%s) to match counterparty upgrade version (%s)", upgradeFields.Version, counterpartyUpgradeFields.Version) + } + + connection, found := k.connectionKeeper.GetConnection(ctx, upgradeFields.ConnectionHops[0]) + if !found { + // NOTE: this error is expected to be unreachable as the proposed upgrade connectionID should have been + // validated in the upgrade INIT and TRY handlers + return errorsmod.Wrap(connectiontypes.ErrConnectionNotFound, upgradeFields.ConnectionHops[0]) + } + + if connection.GetState() != int32(connectiontypes.OPEN) { + // NOTE: this error is expected to be unreachable as the proposed upgrade connectionID should have been + // validated in the upgrade INIT and TRY handlers + return errorsmod.Wrapf(connectiontypes.ErrInvalidConnectionState, "expected proposed connection to be OPEN (got %s)", connectiontypes.State(connection.GetState()).String()) + } + + // connectionHops can change in a channelUpgrade, however both sides must still be each other's counterparty. + if counterpartyUpgradeFields.ConnectionHops[0] != connection.GetCounterparty().GetConnectionID() { + return errorsmod.Wrapf( + types.ErrIncompatibleCounterpartyUpgrade, "counterparty upgrade connection end is not a counterparty of self proposed connection end (%s != %s)", counterpartyUpgradeFields.ConnectionHops[0], connection.GetCounterparty().GetConnectionID()) + } + + return nil +} + +// validateSelfUpgradeFields validates the proposed upgrade fields against the existing channel. +// It returns an error if the following constraints are not met: +// - there exists at least one valid proposed change to the existing channel fields +// - the proposed connection hops do not exist +// - the proposed version is non-empty (checked in UpgradeFields.ValidateBasic()) +// - the proposed connection hops are not open +func (k Keeper) validateSelfUpgradeFields(ctx sdk.Context, proposedUpgrade types.UpgradeFields, currentChannel types.Channel) error { + currentFields := extractUpgradeFields(currentChannel) + + if reflect.DeepEqual(proposedUpgrade, currentFields) { + return errorsmod.Wrapf(types.ErrInvalidUpgrade, "existing channel end is identical to proposed upgrade channel end: got %s", proposedUpgrade) + } + + connectionID := proposedUpgrade.ConnectionHops[0] + connection, found := k.connectionKeeper.GetConnection(ctx, connectionID) + if !found { + return errorsmod.Wrapf(connectiontypes.ErrConnectionNotFound, "failed to retrieve connection: %s", connectionID) + } + + if connection.GetState() != int32(connectiontypes.OPEN) { + return errorsmod.Wrapf( + connectiontypes.ErrInvalidConnectionState, + "connection state is not OPEN (got %s)", connectiontypes.State(connection.GetState()).String(), + ) + } + + getVersions := connection.GetVersions() + if len(getVersions) != 1 { + return errorsmod.Wrapf( + connectiontypes.ErrInvalidVersion, + "single version must be negotiated on connection before opening channel, got: %v", + getVersions, + ) + } + + if !connectiontypes.VerifySupportedFeature(getVersions[0], proposedUpgrade.Ordering.String()) { + return errorsmod.Wrapf( + connectiontypes.ErrInvalidVersion, + "connection version %s does not support channel ordering: %s", + getVersions[0], proposedUpgrade.Ordering.String(), + ) + } + + return nil +} + +// extractUpgradeFields returns the upgrade fields from the provided channel. +func extractUpgradeFields(channel types.Channel) types.UpgradeFields { + return types.UpgradeFields{ + Ordering: channel.Ordering, + ConnectionHops: channel.ConnectionHops, + Version: channel.Version, + } +} + +// MustAbortUpgrade will restore the channel state to its pre-upgrade state so that upgrade is aborted. +// Any unnecessary state is deleted and an error receipt is written. +// This function is expected to always succeed, a panic will occur if an error occurs. +func (k Keeper) MustAbortUpgrade(ctx sdk.Context, portID, channelID string, err error) { + if err := k.abortUpgrade(ctx, portID, channelID, err); err != nil { + panic(err) + } +} + +// abortUpgrade will restore the channel state to its pre-upgrade state so that upgrade is aborted. +// Any unnecessary state is delete and an error receipt is written. +func (k Keeper) abortUpgrade(ctx sdk.Context, portID, channelID string, err error) error { + if err == nil { + return errorsmod.Wrap(types.ErrInvalidUpgradeError, "cannot abort upgrade handshake with nil error") + } + + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + return errorsmod.Wrapf(types.ErrChannelNotFound, "port ID (%s) channel ID (%s)", portID, channelID) + } + + // in the case of application callbacks, the error may not be an upgrade error. + // in this case we need to construct one in order to write the error receipt. + upgradeError, ok := err.(*types.UpgradeError) + if !ok { + upgradeError = types.NewUpgradeError(channel.UpgradeSequence, err) + } + + // the channel upgrade sequence has already been updated in ChannelUpgradeTry, so we can pass + // its updated value. + k.restoreChannel(ctx, portID, channelID, channel.UpgradeSequence, channel, upgradeError) + return nil +} + +// restoreChannel will restore the channel state to its pre-upgrade state so that upgrade is aborted. +func (k Keeper) restoreChannel(ctx sdk.Context, portID, channelID string, upgradeSequence uint64, channel types.Channel, err *types.UpgradeError) types.Channel { + channel.State = types.OPEN + channel.UpgradeSequence = upgradeSequence + + k.SetChannel(ctx, portID, channelID, channel) + + // delete state associated with upgrade which is no longer required. + k.deleteUpgradeInfo(ctx, portID, channelID) + + k.SetUpgradeErrorReceipt(ctx, portID, channelID, err.GetErrorReceipt()) + + return channel +} + +// writeErrorReceipt will write an error receipt from the provided UpgradeError. +func (k Keeper) writeErrorReceipt(ctx sdk.Context, portID, channelID string, upgradeError *types.UpgradeError) { + channel, found := k.GetChannel(ctx, portID, channelID) + if !found { + panic(errorsmod.Wrapf(types.ErrChannelNotFound, "port ID (%s) channel ID (%s)", portID, channelID)) + } + + errorReceiptToWrite := upgradeError.GetErrorReceipt() + + existingErrorReceipt, found := k.GetUpgradeErrorReceipt(ctx, portID, channelID) + if found && existingErrorReceipt.Sequence >= errorReceiptToWrite.Sequence { + panic(errorsmod.Wrapf(types.ErrInvalidUpgradeSequence, "error receipt sequence (%d) must be greater than existing error receipt sequence (%d)", errorReceiptToWrite.Sequence, existingErrorReceipt.Sequence)) + } + + k.SetUpgradeErrorReceipt(ctx, portID, channelID, errorReceiptToWrite) + EmitErrorReceiptEvent(ctx, portID, channelID, channel, upgradeError) +} diff --git a/modules/core/04-channel/keeper/upgrade_test.go b/modules/core/04-channel/keeper/upgrade_test.go new file mode 100644 index 00000000000..475fb3b438b --- /dev/null +++ b/modules/core/04-channel/keeper/upgrade_test.go @@ -0,0 +1,2892 @@ +package keeper_test + +import ( + "fmt" + "math" + "testing" + + errorsmod "cosmossdk.io/errors" + + clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" + connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" + "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" + commitmenttypes "github.com/cosmos/ibc-go/v8/modules/core/23-commitment/types" + host "github.com/cosmos/ibc-go/v8/modules/core/24-host" + "github.com/cosmos/ibc-go/v8/modules/core/exported" + ibctesting "github.com/cosmos/ibc-go/v8/testing" + "github.com/cosmos/ibc-go/v8/testing/mock" +) + +func (suite *KeeperTestSuite) TestChanUpgradeInit() { + var ( + path *ibctesting.Path + expSequence uint64 + upgradeFields types.UpgradeFields + ) + + testCases := []struct { + name string + malleate func() + expPass bool + }{ + { + "success", + func() {}, + true, + }, + { + "success with later upgrade sequence", + func() { + channel := path.EndpointA.GetChannel() + channel.UpgradeSequence = 4 + path.EndpointA.SetChannel(channel) + expSequence = 5 + }, + true, + }, + { + "upgrade fields are identical to channel end", + func() { + channel := path.EndpointA.GetChannel() + upgradeFields = types.NewUpgradeFields(channel.Ordering, channel.ConnectionHops, channel.Version) + }, + false, + }, + { + "channel not found", + func() { + path.EndpointA.ChannelID = "invalid-channel" + path.EndpointA.ChannelConfig.PortID = "invalid-port" + }, + false, + }, + { + "channel state is not in OPEN state", + func() { + suite.Require().NoError(path.EndpointA.SetChannelState(types.CLOSED)) + }, + false, + }, + { + "proposed channel connection not found", + func() { + upgradeFields.ConnectionHops = []string{"connection-100"} + }, + false, + }, + { + "invalid proposed channel connection state", + func() { + connectionEnd := path.EndpointA.GetConnection() + connectionEnd.State = connectiontypes.UNINITIALIZED + + suite.chainA.GetSimApp().GetIBCKeeper().ConnectionKeeper.SetConnection(suite.chainA.GetContext(), "connection-100", connectionEnd) + upgradeFields.ConnectionHops = []string{"connection-100"} + }, + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + expSequence = 1 + + upgradeFields = types.NewUpgradeFields(types.UNORDERED, []string{path.EndpointA.ConnectionID}, mock.UpgradeVersion) + + tc.malleate() + + upgrade, err := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.ChanUpgradeInit( + suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, upgradeFields, + ) + + if tc.expPass { + ctx := suite.chainA.GetContext() + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.WriteUpgradeInitChannel(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, upgrade, upgrade.Fields.Version) + channel := path.EndpointA.GetChannel() + + // events := ctx.EventManager().Events().ToABCIEvents() + // expEvents := ibctesting.EventsMap{ + // types.EventTypeChannelUpgradeInit: { + // types.AttributeKeyPortID: path.EndpointA.ChannelConfig.PortID, + // types.AttributeKeyChannelID: path.EndpointA.ChannelID, + // types.AttributeCounterpartyPortID: path.EndpointB.ChannelConfig.PortID, + // types.AttributeCounterpartyChannelID: path.EndpointB.ChannelID, + // types.AttributeKeyUpgradeConnectionHops: upgradeFields.ConnectionHops[0], + // types.AttributeKeyUpgradeVersion: upgradeFields.Version, + // types.AttributeKeyUpgradeOrdering: upgradeFields.Ordering.String(), + // types.AttributeKeyUpgradeSequence: fmt.Sprintf("%d", channel.UpgradeSequence), + // }, + // sdk.EventTypeMessage: { + // sdk.AttributeKeyModule: types.AttributeValueCategory, + // }, + // } + + suite.Require().NoError(err) + suite.Require().Equal(expSequence, channel.UpgradeSequence) + suite.Require().Equal(mock.Version, channel.Version) + suite.Require().Equal(types.OPEN, channel.State) + + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *KeeperTestSuite) TestChanUpgradeTry() { + var ( + path *ibctesting.Path + proposedUpgrade types.Upgrade + counterpartyUpgrade types.Upgrade + ) + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + "success: crossing hellos", + func() { + err := path.EndpointB.ChanUpgradeInit() + suite.Require().NoError(err) + }, + nil, + }, + { + "success: upgrade sequence is fast forwarded to counterparty upgrade sequence", + func() { + channel := path.EndpointA.GetChannel() + channel.UpgradeSequence = 5 + path.EndpointA.SetChannel(channel) + + suite.coordinator.CommitBlock(suite.chainA) + }, + nil, + }, + { + "channel not found", + func() { + path.EndpointB.ChannelID = ibctesting.InvalidID + }, + types.ErrChannelNotFound, + }, + { + "channel state is not in OPEN state", + func() { + suite.Require().NoError(path.EndpointB.SetChannelState(types.CLOSED)) + }, + types.ErrInvalidChannelState, + }, + { + "connection not found", + func() { + channel := path.EndpointB.GetChannel() + channel.ConnectionHops = []string{"connection-100"} + path.EndpointB.SetChannel(channel) + }, + connectiontypes.ErrConnectionNotFound, + }, + { + "invalid connection state", + func() { + connectionEnd := path.EndpointB.GetConnection() + connectionEnd.State = connectiontypes.UNINITIALIZED + suite.chainB.GetSimApp().GetIBCKeeper().ConnectionKeeper.SetConnection(suite.chainB.GetContext(), path.EndpointB.ConnectionID, connectionEnd) + }, + connectiontypes.ErrInvalidConnectionState, + }, + { + "initializing handshake fails, proposed connection hops do not exist", + func() { + proposedUpgrade.Fields.ConnectionHops = []string{ibctesting.InvalidID} + }, + connectiontypes.ErrConnectionNotFound, + }, + { + "fails due to proof verification failure, counterparty channel ordering does not match expected ordering", + func() { + channel := path.EndpointB.GetChannel() + channel.Ordering = types.ORDERED + path.EndpointB.SetChannel(channel) + }, + commitmenttypes.ErrInvalidProof, + }, + { + "fails due to proof verification failure, counterparty upgrade connection hops are tampered with", + func() { + counterpartyUpgrade.Fields.ConnectionHops = []string{ibctesting.InvalidID} + }, + commitmenttypes.ErrInvalidProof, + }, + { + "fails due to incompatible upgrades, chainB proposes a new connection hop that does not match counterparty", + func() { + // reuse existing connection to create a new connection in a non OPEN state + connection := path.EndpointB.GetConnection() + // ensure counterparty connectionID does not match connectionID set in counterparty proposed upgrade + connection.Counterparty.ConnectionId = "connection-50" + + // set proposed connection in state + proposedConnectionID := "connection-100" //nolint:goconst + suite.chainB.GetSimApp().GetIBCKeeper().ConnectionKeeper.SetConnection(suite.chainB.GetContext(), proposedConnectionID, connection) + proposedUpgrade.Fields.ConnectionHops[0] = proposedConnectionID + }, + types.ErrIncompatibleCounterpartyUpgrade, + }, + { + "fails due to mismatch in upgrade sequences", + func() { + channel := path.EndpointB.GetChannel() + channel.UpgradeSequence = 5 + path.EndpointB.SetChannel(channel) + }, + // channel sequence will be returned so that counterparty inits on completely fresh sequence for both sides + types.NewUpgradeError(5, types.ErrInvalidUpgradeSequence), + }, + { + // ChainA(Sequence: 0, mock-version-v2), ChainB(Sequence: 0, mock-version-v3) + // ChainA.INIT(Sequence: 1) + // ChainB.INIT(Sequence: 1) + // ChainA.TRY => error (incompatible versions) + // ChainB.TRY => error (incompatible versions) + "crossing hellos: fails due to incompatible version", + func() { + // use incompatible version + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = fmt.Sprintf("%s-v3", mock.Version) + proposedUpgrade = path.EndpointB.GetProposedUpgrade() + + err := path.EndpointB.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeTry() + suite.Require().Error(err) + suite.Require().ErrorContains(err, "incompatible counterparty upgrade") + suite.Require().Equal(uint64(1), path.EndpointA.GetChannel().UpgradeSequence) + }, + types.ErrIncompatibleCounterpartyUpgrade, + }, + { + // ChainA(Sequence: 0, mock-version-v2), ChainB(Sequence: 4, mock-version-v3) + // ChainA.INIT(Sequence: 1) + // ChainB.INIT(Sequence: 5) + // ChainA.TRY => error (incompatible versions) + // ChainB.TRY(ErrorReceipt: 4) + "crossing hellos: upgrade starts with mismatching upgrade sequences and try fails on counterparty due to incompatible version", + func() { + channel := path.EndpointB.GetChannel() + channel.UpgradeSequence = 4 + path.EndpointB.SetChannel(channel) + + // use incompatible version + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = fmt.Sprintf("%s-v3", mock.Version) + proposedUpgrade = path.EndpointB.GetProposedUpgrade() + + err := path.EndpointB.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeTry() + suite.Require().Error(err) + suite.Require().ErrorContains(err, "incompatible counterparty upgrade") + suite.Require().Equal(uint64(1), path.EndpointA.GetChannel().UpgradeSequence) + }, + types.NewUpgradeError(4, types.ErrInvalidUpgradeSequence), + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + expPass := tc.expError == nil + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + proposedUpgrade = path.EndpointB.GetProposedUpgrade() + + var found bool + counterpartyUpgrade, found = path.EndpointA.Chain.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgrade(path.EndpointA.Chain.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + + tc.malleate() + + // ensure clients are up to date to receive valid proofs + suite.Require().NoError(path.EndpointB.UpdateClient()) + + proofChannel, proofUpgrade, proofHeight := path.EndpointA.QueryChannelUpgradeProof() + + _, upgrade, err := suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.ChanUpgradeTry( + suite.chainB.GetContext(), + path.EndpointB.ChannelConfig.PortID, + path.EndpointB.ChannelID, + proposedUpgrade.Fields.ConnectionHops, + counterpartyUpgrade.Fields, + path.EndpointA.GetChannel().UpgradeSequence, + proofChannel, + proofUpgrade, + proofHeight, + ) + + if expPass { + suite.Require().NoError(err) + suite.Require().NotEmpty(upgrade) + suite.Require().Equal(proposedUpgrade.Fields, upgrade.Fields) + + nextSequenceSend, found := path.EndpointB.Chain.GetSimApp().IBCKeeper.ChannelKeeper.GetNextSequenceSend(path.EndpointB.Chain.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(found) + suite.Require().Equal(nextSequenceSend, upgrade.NextSequenceSend) + } else { + suite.assertUpgradeError(err, tc.expError) + } + }) + } +} + +// TestChanUpgrade_CrossingHellos_UpgradeSucceeds_AfterCancel verifies that under crossing hellos if upgrade +// sequences become out of sync, the upgrade can still be performed successfully after the upgrade is cancelled. +// ChainA(Sequence: 0), ChainB(Sequence 4) +// ChainA.INIT(Sequence: 1) +// ChainB.INIT(Sequence: 5) +// ChainB.TRY(ErrorReceipt: 4) +// ChainA.Cancel(Sequence: 4) +// ChainA.TRY(Sequence: 5) // fastforward +// ChainB.ACK => Success +// ChainA.Confirm => Success +// ChainB.Open => Success +func (suite *KeeperTestSuite) TestChanUpgrade_CrossingHellos_UpgradeSucceeds_AfterCancel() { + var path *ibctesting.Path + + suite.Run("setup path", func() { + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + }) + + suite.Run("chainA upgrade init", func() { + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + }) + + suite.Run("set chainB upgrade sequence ahead of counterparty", func() { + channel := path.EndpointB.GetChannel() + channel.UpgradeSequence = 4 + path.EndpointB.SetChannel(channel) + }) + + suite.Run("chainB upgrade init (crossing hello)", func() { + err := path.EndpointB.ChanUpgradeInit() + suite.Require().NoError(err) + }) + + suite.Run("chainB upgrade try fails with invalid sequence", func() { + err := path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + errorReceipt, found := path.EndpointB.Chain.GetSimApp().GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(4), errorReceipt.Sequence) + }) + + suite.Run("cancel upgrade on chainA and fast forward upgrade sequence", func() { + err := path.EndpointA.ChanUpgradeCancel() + suite.Require().NoError(err) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.OPEN, channel.State) + suite.Require().Equal(uint64(4), channel.UpgradeSequence) + }) + + suite.Run("try chainA upgrade now succeeds with synchronized upgrade sequences", func() { + err := path.EndpointA.ChanUpgradeTry() + suite.Require().NoError(err) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.FLUSHING, channel.State) + suite.Require().Equal(uint64(5), channel.UpgradeSequence) + }) + + suite.Run("upgrade handshake completes successfully", func() { + err := path.EndpointB.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeConfirm() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeOpen() + suite.Require().NoError(err) + }) + + suite.Run("assert successful upgrade expected channel state", func() { + channelA := path.EndpointA.GetChannel() + suite.Require().Equal(types.OPEN, channelA.State, "channel should be in OPEN state") + suite.Require().Equal(mock.UpgradeVersion, channelA.Version, "version should be correctly upgraded") + suite.Require().Equal(mock.UpgradeVersion, path.EndpointB.GetChannel().Version, "version should be correctly upgraded") + suite.Require().Equal(uint64(5), channelA.UpgradeSequence, "upgrade sequence should be incremented") + + channelB := path.EndpointB.GetChannel() + suite.Require().Equal(types.OPEN, channelB.State, "channel should be in OPEN state") + suite.Require().Equal(mock.UpgradeVersion, channelB.Version, "version should be correctly upgraded") + suite.Require().Equal(mock.UpgradeVersion, channelB.Version, "version should be correctly upgraded") + suite.Require().Equal(uint64(5), channelB.UpgradeSequence, "upgrade sequence should be incremented") + }) +} + +// TestChanUpgrade_CrossingHellos_UpgradeSucceeds_AfterCancelErrors verifies that under crossing hellos if upgrade +// sequences become out of sync, the upgrade can still be performed successfully after the cancel fails. +// ChainA(Sequence: 0), ChainB(Sequence 4) +// ChainA.INIT(Sequence: 1) +// ChainB.INIT(Sequence: 5) +// ChainA.TRY(Sequence: 5) // fastforward +// ChainB.TRY(ErrorReceipt: 4) +// ChainA.Cancel => Error (errorReceipt.Sequence < channel.UpgradeSequence) +// ChainB.ACK => Success +// ChainA.Confirm => Success +// ChainB.Open => Success +func (suite *KeeperTestSuite) TestChanUpgrade_CrossingHellos_UpgradeSucceeds_AfterCancelErrors() { + var ( + historicalChannelProof []byte + historicalUpgradeProof []byte + proofHeight clienttypes.Height + path *ibctesting.Path + ) + + suite.Run("setup path", func() { + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + }) + + suite.Run("chainA upgrade init", func() { + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(uint64(1), channel.UpgradeSequence) + }) + + suite.Run("set chainB upgrade sequence ahead of counterparty", func() { + channel := path.EndpointB.GetChannel() + channel.UpgradeSequence = 4 + path.EndpointB.SetChannel(channel) + }) + + suite.Run("chainB upgrade init (crossing hello)", func() { + err := path.EndpointB.ChanUpgradeInit() + suite.Require().NoError(err) + + channel := path.EndpointB.GetChannel() + suite.Require().Equal(uint64(5), channel.UpgradeSequence) + }) + + suite.Run("query proofs at chainA upgrade sequence 1", func() { + // commit block and update client on chainB + suite.coordinator.CommitBlock(suite.chainA, suite.chainB) + suite.Require().NoError(path.EndpointB.UpdateClient()) + // use proofs when chain A has not executed TRY yet and use them when executing TRY on chain B + historicalChannelProof, historicalUpgradeProof, proofHeight = path.EndpointA.QueryChannelUpgradeProof() + }) + + suite.Run("chainA upgrade try (fast-forwards sequence)", func() { + err := path.EndpointA.ChanUpgradeTry() + suite.Require().NoError(err) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(uint64(5), channel.UpgradeSequence) + }) + + suite.Run("chainB upgrade try fails with written error receipt (4)", func() { + // NOTE: ante handlers are bypassed here and the handler is invoked directly. + // Thus, we set the upgrade error receipt explicitly below + _, _, err := suite.chainB.GetSimApp().GetIBCKeeper().ChannelKeeper.ChanUpgradeTry( + suite.chainB.GetContext(), + path.EndpointB.ChannelConfig.PortID, + path.EndpointB.ChannelID, + path.EndpointB.GetChannelUpgrade().Fields.ConnectionHops, + path.EndpointA.GetChannelUpgrade().Fields, + 1, // proofs queried at chainA upgrade sequence 1 + historicalChannelProof, + historicalUpgradeProof, + proofHeight, + ) + suite.Require().Error(err) + suite.assertUpgradeError(err, types.NewUpgradeError(4, types.ErrInvalidUpgradeSequence)) + + errorReceipt := err.(*types.UpgradeError).GetErrorReceipt() + suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.SetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, errorReceipt) + suite.coordinator.CommitBlock(suite.chainB) + }) + + suite.Run("chainA upgrade cancellation fails for invalid sequence", func() { + err := path.EndpointA.ChanUpgradeCancel() + suite.Require().Error(err) + suite.Require().ErrorContains(err, "invalid upgrade sequence") + + // assert channel remains in flushing state at upgrade sequence 5 + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.FLUSHING, channel.State) + suite.Require().Equal(uint64(5), channel.UpgradeSequence) + }) + + suite.Run("upgrade handshake completes successfully", func() { + err := path.EndpointB.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeConfirm() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeOpen() + suite.Require().NoError(err) + }) + + suite.Run("assert successful upgrade expected channel state", func() { + channelA := path.EndpointA.GetChannel() + suite.Require().Equal(types.OPEN, channelA.State, "channel should be in OPEN state") + suite.Require().Equal(mock.UpgradeVersion, channelA.Version, "version should be correctly upgraded") + suite.Require().Equal(mock.UpgradeVersion, path.EndpointB.GetChannel().Version, "version should be correctly upgraded") + suite.Require().Equal(uint64(5), channelA.UpgradeSequence, "upgrade sequence should be incremented") + + channelB := path.EndpointB.GetChannel() + suite.Require().Equal(types.OPEN, channelB.State, "channel should be in OPEN state") + suite.Require().Equal(mock.UpgradeVersion, channelB.Version, "version should be correctly upgraded") + suite.Require().Equal(mock.UpgradeVersion, channelB.Version, "version should be correctly upgraded") + suite.Require().Equal(uint64(5), channelB.UpgradeSequence, "upgrade sequence should be incremented") + }) +} + +func (suite *KeeperTestSuite) TestWriteUpgradeTry() { + var ( + path *ibctesting.Path + proposedUpgrade types.Upgrade + ) + + testCases := []struct { + name string + malleate func() + }{ + { + "success with no packet commitments", + func() {}, + }, + { + "success with packet commitments", + func() { + // manually set packet commitment + sequence, err := path.EndpointB.SendPacket(suite.chainB.GetTimeoutHeight(), 0, ibctesting.MockPacketData) + suite.Require().NoError(err) + suite.Require().Equal(uint64(1), sequence) + }, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + proposedUpgrade = path.EndpointB.GetProposedUpgrade() + + tc.malleate() + + ctx := suite.chainB.GetContext() + upgradedChannelEnd, upgradeWithAppCallbackVersion := suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.WriteUpgradeTryChannel( + ctx, + path.EndpointB.ChannelConfig.PortID, + path.EndpointB.ChannelID, + proposedUpgrade, + proposedUpgrade.Fields.Version, + ) + + channel := path.EndpointB.GetChannel() + suite.Require().Equal(upgradedChannelEnd, channel) + + upgrade, found := suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgrade(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(found) + suite.Require().Equal(upgradeWithAppCallbackVersion, upgrade) + + // events := ctx.EventManager().Events().ToABCIEvents() + // expEvents := ibctesting.EventsMap{ + // types.EventTypeChannelUpgradeTry: { + // types.AttributeKeyPortID: path.EndpointB.ChannelConfig.PortID, + // types.AttributeKeyChannelID: path.EndpointB.ChannelID, + // types.AttributeCounterpartyPortID: path.EndpointA.ChannelConfig.PortID, + // types.AttributeCounterpartyChannelID: path.EndpointA.ChannelID, + // types.AttributeKeyUpgradeConnectionHops: upgrade.Fields.ConnectionHops[0], + // types.AttributeKeyUpgradeVersion: upgrade.Fields.Version, + // types.AttributeKeyUpgradeOrdering: upgrade.Fields.Ordering.String(), + // types.AttributeKeyUpgradeSequence: fmt.Sprintf("%d", channel.UpgradeSequence), + // }, + // sdk.EventTypeMessage: { + // sdk.AttributeKeyModule: types.AttributeValueCategory, + // }, + // } + }) + } +} + +func (suite *KeeperTestSuite) TestChanUpgradeAck() { + var ( + path *ibctesting.Path + counterpartyUpgrade types.Upgrade + ) + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + "success with later upgrade sequence", + func() { + channel := path.EndpointA.GetChannel() + channel.UpgradeSequence = 10 + path.EndpointA.SetChannel(channel) + + channel = path.EndpointB.GetChannel() + channel.UpgradeSequence = 10 + path.EndpointB.SetChannel(channel) + + suite.coordinator.CommitBlock(suite.chainA, suite.chainB) + + err := path.EndpointA.UpdateClient() + suite.Require().NoError(err) + }, + nil, + }, + { + "channel not found", + func() { + path.EndpointA.ChannelID = ibctesting.InvalidID + path.EndpointA.ChannelConfig.PortID = ibctesting.InvalidID + }, + types.ErrChannelNotFound, + }, + { + "channel state is not in FLUSHING state", + func() { + suite.Require().NoError(path.EndpointA.SetChannelState(types.CLOSED)) + }, + types.ErrInvalidChannelState, + }, + { + "connection not found", + func() { + channel := path.EndpointA.GetChannel() + channel.ConnectionHops = []string{"connection-100"} + path.EndpointA.SetChannel(channel) + }, + connectiontypes.ErrConnectionNotFound, + }, + { + "invalid connection state", + func() { + connectionEnd := path.EndpointA.GetConnection() + connectionEnd.State = connectiontypes.UNINITIALIZED + path.EndpointA.SetConnection(connectionEnd) + }, + connectiontypes.ErrInvalidConnectionState, + }, + { + "upgrade not found", + func() { + store := suite.chainA.GetContext().KVStore(suite.chainA.GetSimApp().GetKey(exported.ModuleName)) + store.Delete(host.ChannelUpgradeKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + }, + types.ErrUpgradeNotFound, + }, + { + "fails due to upgrade incompatibility", + func() { + // Need to set counterparty upgrade in state and update clients to ensure + // proofs submitted reflect the altered upgrade. + counterpartyUpgrade.Fields.ConnectionHops = []string{ibctesting.InvalidID} + path.EndpointB.SetChannelUpgrade(counterpartyUpgrade) + + suite.coordinator.CommitBlock(suite.chainB) + + err := path.EndpointA.UpdateClient() + suite.Require().NoError(err) + }, + types.NewUpgradeError(1, types.ErrIncompatibleCounterpartyUpgrade), + }, + { + "fails due to proof verification failure, counterparty channel ordering does not match expected ordering", + func() { + channel := path.EndpointA.GetChannel() + channel.Ordering = types.ORDERED + path.EndpointA.SetChannel(channel) + }, + commitmenttypes.ErrInvalidProof, + }, + { + "fails due to proof verification failure, counterparty update has unexpected sequence", + func() { + // Decrementing NextSequenceSend is sufficient to cause the proof to fail. + counterpartyUpgrade.NextSequenceSend-- + }, + commitmenttypes.ErrInvalidProof, + }, + { + "fails due to mismatch in upgrade ordering", + func() { + upgrade := path.EndpointA.GetChannelUpgrade() + upgrade.Fields.Ordering = types.NONE + + path.EndpointA.SetChannelUpgrade(upgrade) + }, + types.NewUpgradeError(1, types.ErrIncompatibleCounterpartyUpgrade), + }, + { + "counterparty timeout has elapsed", + func() { + // Need to set counterparty upgrade in state and update clients to ensure + // proofs submitted reflect the altered upgrade. + counterpartyUpgrade.Timeout = types.NewTimeout(clienttypes.NewHeight(0, 1), 0) + path.EndpointB.SetChannelUpgrade(counterpartyUpgrade) + + err := path.EndpointB.UpdateClient() + suite.Require().NoError(err) + err = path.EndpointA.UpdateClient() + suite.Require().NoError(err) + }, + types.NewUpgradeError(1, types.ErrTimeoutElapsed), + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + // manually set packet commitment so that the chainB channel state is FLUSHING + sequence, err := path.EndpointB.SendPacket(suite.chainB.GetTimeoutHeight(), 0, ibctesting.MockPacketData) + suite.Require().NoError(err) + suite.Require().Equal(uint64(1), sequence) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + // ensure client is up to date to receive valid proofs + err = path.EndpointA.UpdateClient() + suite.Require().NoError(err) + + counterpartyUpgrade = path.EndpointB.GetChannelUpgrade() + + tc.malleate() + + proofChannel, proofUpgrade, proofHeight := path.EndpointB.QueryChannelUpgradeProof() + + err = suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.ChanUpgradeAck( + suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, counterpartyUpgrade, + proofChannel, proofUpgrade, proofHeight, + ) + + expPass := tc.expError == nil + if expPass { + suite.Require().NoError(err) + + channel := path.EndpointA.GetChannel() + // ChanUpgradeAck will set the channel state to FLUSHING + // It will be set to FLUSHING_COMPLETE in the write function. + suite.Require().Equal(types.FLUSHING, channel.State) + } else { + suite.assertUpgradeError(err, tc.expError) + } + }) + } +} + +func (suite *KeeperTestSuite) TestWriteChannelUpgradeAck() { + var ( + path *ibctesting.Path + proposedUpgrade types.Upgrade + ) + + testCases := []struct { + name string + malleate func() + hasPacketCommitments bool + }{ + { + "success with no packet commitments", + func() {}, + false, + }, + { + "success with packet commitments", + func() { + // manually set packet commitment + sequence, err := path.EndpointA.SendPacket(suite.chainB.GetTimeoutHeight(), 0, ibctesting.MockPacketData) + suite.Require().NoError(err) + suite.Require().Equal(uint64(1), sequence) + }, + true, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + tc.malleate() + + // perform the upgrade handshake. + suite.Require().NoError(path.EndpointA.ChanUpgradeInit()) + + suite.Require().NoError(path.EndpointB.ChanUpgradeTry()) + + ctx := suite.chainA.GetContext() + proposedUpgrade = path.EndpointB.GetChannelUpgrade() + + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.WriteUpgradeAckChannel(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, proposedUpgrade) + + channel := path.EndpointA.GetChannel() + upgrade := path.EndpointA.GetChannelUpgrade() + suite.Require().Equal(mock.UpgradeVersion, upgrade.Fields.Version) + + // events := ctx.EventManager().Events().ToABCIEvents() + // expEvents := ibctesting.EventsMap{ + // types.EventTypeChannelUpgradeAck: { + // types.AttributeKeyPortID: path.EndpointA.ChannelConfig.PortID, + // types.AttributeKeyChannelID: path.EndpointA.ChannelID, + // types.AttributeCounterpartyPortID: path.EndpointB.ChannelConfig.PortID, + // types.AttributeCounterpartyChannelID: path.EndpointB.ChannelID, + // types.AttributeKeyUpgradeConnectionHops: upgrade.Fields.ConnectionHops[0], + // types.AttributeKeyUpgradeVersion: upgrade.Fields.Version, + // types.AttributeKeyUpgradeOrdering: upgrade.Fields.Ordering.String(), + // types.AttributeKeyUpgradeSequence: fmt.Sprintf("%d", channel.UpgradeSequence), + // }, + // sdk.EventTypeMessage: { + // sdk.AttributeKeyModule: types.AttributeValueCategory, + // }, + // } + + if !tc.hasPacketCommitments { + suite.Require().Equal(types.FLUSHCOMPLETE, channel.State) + } + counterpartyUpgrade, ok := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetCounterpartyUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(ok) + suite.Require().Equal(proposedUpgrade, counterpartyUpgrade) + }) + } +} + +func (suite *KeeperTestSuite) TestChanUpgradeConfirm() { + var ( + path *ibctesting.Path + counterpartyChannelState types.State + counterpartyUpgrade types.Upgrade + ) + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + "success with later upgrade sequence", + func() { + channel := path.EndpointA.GetChannel() + channel.UpgradeSequence = 10 + path.EndpointA.SetChannel(channel) + + channel = path.EndpointB.GetChannel() + channel.UpgradeSequence = 10 + path.EndpointB.SetChannel(channel) + + suite.coordinator.CommitBlock(suite.chainA, suite.chainB) + + err := path.EndpointB.UpdateClient() + suite.Require().NoError(err) + }, + nil, + }, + { + "success with in-flight packets on init chain", + func() { + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + seq, err := path.EndpointA.SendPacket(defaultTimeoutHeight, 0, ibctesting.MockPacketData) + suite.Require().Equal(uint64(1), seq) + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointB.UpdateClient() + suite.Require().NoError(err) + + counterpartyChannelState = path.EndpointA.GetChannel().State + counterpartyUpgrade = path.EndpointA.GetChannelUpgrade() + }, + nil, + }, + { + "success with in-flight packets on try chain", + func() { + portID, channelID := path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID + suite.chainB.GetSimApp().GetIBCKeeper().ChannelKeeper.SetPacketCommitment(suite.chainB.GetContext(), portID, channelID, 1, []byte("hash")) + }, + nil, + }, + { + "channel not found", + func() { + path.EndpointB.ChannelID = ibctesting.InvalidID + path.EndpointB.ChannelConfig.PortID = ibctesting.InvalidID + }, + types.ErrChannelNotFound, + }, + { + "channel is not in FLUSHING state", + func() { + err := path.EndpointB.SetChannelState(types.CLOSED) + suite.Require().NoError(err) + }, + types.ErrInvalidChannelState, + }, + { + "invalid counterparty channel state", + func() { + counterpartyChannelState = types.CLOSED + }, + types.ErrInvalidCounterparty, + }, + { + "connection not found", + func() { + channel := path.EndpointB.GetChannel() + channel.ConnectionHops = []string{"connection-100"} + path.EndpointB.SetChannel(channel) + }, + connectiontypes.ErrConnectionNotFound, + }, + { + "invalid connection state", + func() { + connectionEnd := path.EndpointB.GetConnection() + connectionEnd.State = connectiontypes.UNINITIALIZED + path.EndpointB.SetConnection(connectionEnd) + }, + connectiontypes.ErrInvalidConnectionState, + }, + { + "fails due to proof verification failure, counterparty channel ordering does not match expected ordering", + func() { + channel := path.EndpointA.GetChannel() + channel.Ordering = types.ORDERED + path.EndpointA.SetChannel(channel) + + suite.coordinator.CommitBlock(suite.chainA) + + err := path.EndpointB.UpdateClient() + suite.Require().NoError(err) + }, + commitmenttypes.ErrInvalidProof, + }, + { + "fails due to mismatch in upgrade ordering", + func() { + upgrade := path.EndpointA.GetChannelUpgrade() + upgrade.Fields.Ordering = types.NONE + + path.EndpointA.SetChannelUpgrade(upgrade) + + suite.coordinator.CommitBlock(suite.chainA) + + err := path.EndpointB.UpdateClient() + suite.Require().NoError(err) + }, + commitmenttypes.ErrInvalidProof, + }, + { + "counterparty timeout has elapsed", + func() { + // Need to set counterparty upgrade in state and update clients to ensure + // proofs submitted reflect the altered upgrade. + counterpartyUpgrade.Timeout = types.NewTimeout(clienttypes.NewHeight(0, 1), 0) + path.EndpointA.SetChannelUpgrade(counterpartyUpgrade) + + suite.coordinator.CommitBlock(suite.chainA) + + err := path.EndpointB.UpdateClient() + suite.Require().NoError(err) + }, + types.NewUpgradeError(1, types.ErrTimeoutElapsed), + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointB.UpdateClient() + suite.Require().NoError(err) + + counterpartyChannelState = path.EndpointA.GetChannel().State + counterpartyUpgrade = path.EndpointA.GetChannelUpgrade() + + tc.malleate() + + proofChannel, proofUpgrade, proofHeight := path.EndpointA.QueryChannelUpgradeProof() + + err = suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.ChanUpgradeConfirm( + suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, counterpartyChannelState, counterpartyUpgrade, + proofChannel, proofUpgrade, proofHeight, + ) + + expPass := tc.expError == nil + if expPass { + suite.Require().NoError(err) + } else { + suite.assertUpgradeError(err, tc.expError) + } + }) + } +} + +func (suite *KeeperTestSuite) TestWriteUpgradeConfirm() { + var ( + path *ibctesting.Path + proposedUpgrade types.Upgrade + ) + + testCases := []struct { + name string + malleate func() + hasPacketCommitments bool + }{ + { + "success with no packet commitments", + func() {}, + false, + }, + { + "success with packet commitments", + func() { + // manually set packet commitment + sequence, err := path.EndpointA.SendPacket(suite.chainB.GetTimeoutHeight(), 0, ibctesting.MockPacketData) + suite.Require().NoError(err) + suite.Require().Equal(uint64(1), sequence) + }, + true, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + tc.malleate() + + // perform the upgrade handshake. + suite.Require().NoError(path.EndpointB.ChanUpgradeInit()) + + suite.Require().NoError(path.EndpointA.ChanUpgradeTry()) + + suite.Require().NoError(path.EndpointB.ChanUpgradeAck()) + + ctx := suite.chainA.GetContext() + proposedUpgrade = path.EndpointB.GetChannelUpgrade() + + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.WriteUpgradeConfirmChannel(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, proposedUpgrade) + + channel := path.EndpointA.GetChannel() + upgrade := path.EndpointA.GetChannelUpgrade() + suite.Require().Equal(mock.UpgradeVersion, upgrade.Fields.Version) + + // events := ctx.EventManager().Events().ToABCIEvents() + // expEvents := ibctesting.EventsMap{ + // types.EventTypeChannelUpgradeConfirm: { + // types.AttributeKeyPortID: path.EndpointA.ChannelConfig.PortID, + // types.AttributeKeyChannelID: path.EndpointA.ChannelID, + // types.AttributeKeyChannelState: channel.State.String(), + // types.AttributeCounterpartyPortID: path.EndpointB.ChannelConfig.PortID, + // types.AttributeCounterpartyChannelID: path.EndpointB.ChannelID, + // types.AttributeKeyUpgradeSequence: fmt.Sprintf("%d", channel.UpgradeSequence), + // }, + // sdk.EventTypeMessage: { + // sdk.AttributeKeyModule: types.AttributeValueCategory, + // }, + // } + + if !tc.hasPacketCommitments { + suite.Require().Equal(types.FLUSHCOMPLETE, channel.State) + } else { + suite.Require().Equal(types.FLUSHING, channel.State) + } + counterpartyUpgrade, ok := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetCounterpartyUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(ok, "counterparty upgrade should be present") + suite.Require().Equal(proposedUpgrade, counterpartyUpgrade) + }) + } +} + +func (suite *KeeperTestSuite) TestChanUpgradeOpen() { + var path *ibctesting.Path + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + "success: counterparty in flushcomplete", + func() { + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + // Need to create a packet commitment on A so as to keep it from going to FLUSHCOMPLETE if no inflight packets exist. + sequence, err := path.EndpointA.SendPacket(defaultTimeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + packet := types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + err = path.EndpointB.RecvPacket(packet) + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeConfirm() + suite.Require().NoError(err) + + err = path.EndpointA.AcknowledgePacket(packet, ibctesting.MockAcknowledgement) + suite.Require().NoError(err) + + // cause the packet commitment on chain A to be deleted and the channel state to be updated to FLUSHCOMPLETE. + suite.coordinator.CommitBlock(suite.chainA, suite.chainB) + suite.Require().NoError(path.EndpointA.UpdateClient()) + }, + nil, + }, + { + "channel not found", + func() { + path.EndpointA.ChannelConfig.PortID = ibctesting.InvalidID + }, + types.ErrChannelNotFound, + }, + { + "channel state is not FLUSHCOMPLETE", + func() { + channel := path.EndpointA.GetChannel() + channel.State = types.FLUSHING + path.EndpointA.SetChannel(channel) + }, + types.ErrInvalidChannelState, + }, + { + "connection not found", + func() { + channel := path.EndpointA.GetChannel() + channel.ConnectionHops = []string{"connection-100"} + path.EndpointA.SetChannel(channel) + }, + connectiontypes.ErrConnectionNotFound, + }, + { + "invalid connection state", + func() { + connectionEnd := path.EndpointA.GetConnection() + connectionEnd.State = connectiontypes.UNINITIALIZED + path.EndpointA.SetConnection(connectionEnd) + }, + connectiontypes.ErrInvalidConnectionState, + }, + { + "invalid counterparty channel state", + func() { + channel := path.EndpointB.GetChannel() + channel.State = types.CLOSED + path.EndpointB.SetChannel(channel) + }, + types.ErrInvalidCounterparty, + }, + } + + // Create an initial path used only to invoke a ChanOpenInit handshake. + // This bumps the channel identifier generated for chain A on the + // next path used to run the upgrade handshake. + // See issue 4062. + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.SetupConnections(path) + suite.Require().NoError(path.EndpointA.ChanOpenInit()) + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeConfirm() + suite.Require().NoError(err) + + err = path.EndpointA.UpdateClient() + suite.Require().NoError(err) + + tc.malleate() + + channelKey := host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proofChannel, proofHeight := path.EndpointB.QueryProof(channelKey) + + err = suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.ChanUpgradeOpen( + suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, + path.EndpointB.GetChannel().State, proofChannel, proofHeight, + ) + + if tc.expError == nil { + suite.Require().NoError(err) + } else { + suite.Require().ErrorIs(err, tc.expError) + } + }) + } +} + +func (suite *KeeperTestSuite) TestWriteUpgradeOpenChannel() { + var path *ibctesting.Path + + testCases := []struct { + name string + malleate func() + expPanic bool + }{ + { + name: "success", + malleate: func() {}, + expPanic: false, + }, + { + name: "channel not found", + malleate: func() { + path.EndpointA.Chain.DeleteKey(host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + }, + expPanic: true, + }, + { + name: "upgrade not found", + malleate: func() { + path.EndpointA.Chain.DeleteKey(host.ChannelUpgradeKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + }, + expPanic: true, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + // Need to create a packet commitment on A so as to keep it from going to OPEN if no inflight packets exist. + sequence, err := path.EndpointA.SendPacket(defaultTimeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + packet := types.NewPacket(ibctesting.MockPacketData, sequence, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + err = path.EndpointB.RecvPacket(packet) + suite.Require().NoError(err) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + suite.Require().NoError(path.EndpointA.ChanUpgradeInit()) + suite.Require().NoError(path.EndpointB.ChanUpgradeTry()) + suite.Require().NoError(path.EndpointA.ChanUpgradeAck()) + suite.Require().NoError(path.EndpointB.ChanUpgradeConfirm()) + + // Ack packet to delete packet commitment before calling WriteUpgradeOpenChannel + err = path.EndpointA.AcknowledgePacket(packet, ibctesting.MockAcknowledgement) + suite.Require().NoError(err) + + ctx := suite.chainA.GetContext() + + tc.malleate() + + if tc.expPanic { + suite.Require().Panics(func() { + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.WriteUpgradeOpenChannel(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + }) + } else { + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.WriteUpgradeOpenChannel(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + channel := path.EndpointA.GetChannel() + + // Assert that channel state has been updated + suite.Require().Equal(types.OPEN, channel.State) + suite.Require().Equal(mock.UpgradeVersion, channel.Version) + + // Assert that state stored for upgrade has been deleted + upgrade, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().Equal(types.Upgrade{}, upgrade) + suite.Require().False(found) + + counterpartyUpgrade, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetCounterpartyUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().Equal(types.Upgrade{}, counterpartyUpgrade) + suite.Require().False(found) + + // events := ctx.EventManager().Events().ToABCIEvents() + // expEvents := ibctesting.EventsMap{ + // types.EventTypeChannelUpgradeOpen: { + // types.AttributeKeyPortID: path.EndpointA.ChannelConfig.PortID, + // types.AttributeKeyChannelID: path.EndpointA.ChannelID, + // types.AttributeCounterpartyPortID: path.EndpointB.ChannelConfig.PortID, + // types.AttributeCounterpartyChannelID: path.EndpointB.ChannelID, + // types.AttributeKeyChannelState: types.OPEN.String(), + // types.AttributeKeyUpgradeConnectionHops: channel.ConnectionHops[0], + // types.AttributeKeyUpgradeVersion: channel.Version, + // types.AttributeKeyUpgradeOrdering: channel.Ordering.String(), + // types.AttributeKeyUpgradeSequence: fmt.Sprintf("%d", channel.UpgradeSequence), + // }, + // sdk.EventTypeMessage: { + // sdk.AttributeKeyModule: types.AttributeValueCategory, + // }, + // } + // ibctesting.AssertEventsLegacy(&suite.Suite, expEvents, events) + } + }) + } +} + +func (suite *KeeperTestSuite) TestWriteUpgradeOpenChannel_Ordering() { + var path *ibctesting.Path + + testCases := []struct { + name string + malleate func() + preUpgrade func() + postUpgrade func() + }{ + { + name: "success: ORDERED -> UNORDERED", + malleate: func() { + path.EndpointA.ChannelConfig.Order = types.ORDERED + path.EndpointB.ChannelConfig.Order = types.ORDERED + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Ordering = types.UNORDERED + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Ordering = types.UNORDERED + }, + preUpgrade: func() { + ctx := suite.chainA.GetContext() + + // assert that NextSeqAck is incremented to 2 because channel is still ordered + seq, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetNextSequenceAck(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(2), seq) + + // assert that NextSeqRecv is incremented to 2 because channel is still ordered + seq, found = suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetNextSequenceRecv(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(2), seq) + + // Assert that pruning sequence start has not been initialized. + suite.Require().False(suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.HasPruningSequenceStart(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + + // Assert that pruning sequence end has not been set + counterpartyNextSequenceSend, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetPruningSequenceEnd(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().False(found) + suite.Require().Equal(uint64(0), counterpartyNextSequenceSend) + }, + postUpgrade: func() { + channel := path.EndpointA.GetChannel() + ctx := suite.chainA.GetContext() + + // Assert that channel state has been updated + suite.Require().Equal(types.OPEN, channel.State) + suite.Require().Equal(types.UNORDERED, channel.Ordering) + + // assert that NextSeqRecv is now 1, because channel is now UNORDERED + seq, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetNextSequenceRecv(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(1), seq) + + // assert that NextSeqAck is now 1, because channel is now UNORDERED + seq, found = suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetNextSequenceAck(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(1), seq) + + // Assert that pruning sequence start has been initialized (set to 1) + suite.Require().True(suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.HasPruningSequenceStart(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + pruningSeq := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetPruningSequenceStart(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().Equal(uint64(1), pruningSeq) + + // Assert that pruning sequence end has been set correctly + counterpartySequenceSend, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetPruningSequenceEnd(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(2), counterpartySequenceSend) + }, + }, + { + name: "success: UNORDERED -> ORDERED", + malleate: func() { + path.EndpointA.ChannelConfig.Order = types.UNORDERED + path.EndpointB.ChannelConfig.Order = types.UNORDERED + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Ordering = types.ORDERED + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Ordering = types.ORDERED + }, + preUpgrade: func() { + ctx := suite.chainA.GetContext() + + // assert that NextSeqRecv is 1 because channel is UNORDERED + seq, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetNextSequenceRecv(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(1), seq) + + // assert that NextSeqAck is 1 because channel is UNORDERED + seq, found = suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetNextSequenceAck(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(1), seq) + + // Assert that pruning sequence start has not been initialized. + suite.Require().False(suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.HasPruningSequenceStart(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + + // Assert that pruning sequence end has not been set + counterpartyNextSequenceSend, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetPruningSequenceEnd(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().False(found) + suite.Require().Equal(uint64(0), counterpartyNextSequenceSend) + }, + postUpgrade: func() { + channel := path.EndpointA.GetChannel() + ctx := suite.chainA.GetContext() + + // Assert that channel state has been updated + suite.Require().Equal(types.OPEN, channel.State) + suite.Require().Equal(types.ORDERED, channel.Ordering) + + // assert that NextSeqRecv is incremented to 2, because channel is now ORDERED + // NextSeqRecv updated in WriteUpgradeOpenChannel to latest sequence (one packet sent) + 1 + seq, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetNextSequenceRecv(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(2), seq) + + // assert that NextSeqAck is incremented to 2 because channel is now ORDERED + seq, found = suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetNextSequenceAck(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(2), seq) + + // Assert that pruning sequence start has been initialized (set to 1) + suite.Require().True(suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.HasPruningSequenceStart(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + pruningSeq := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetPruningSequenceStart(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().Equal(uint64(1), pruningSeq) + + // Assert that pruning sequence end has been set correctly + counterpartySequenceSend, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetPruningSequenceEnd(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(2), counterpartySequenceSend) + }, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + + tc.malleate() + + suite.coordinator.Setup(path) + + // Need to create a packet commitment on A so as to keep it from going to OPEN if no inflight packets exist. + sequenceA, err := path.EndpointA.SendPacket(defaultTimeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + packetA := types.NewPacket(ibctesting.MockPacketData, sequenceA, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + err = path.EndpointB.RecvPacket(packetA) + suite.Require().NoError(err) + + // send second packet from B to A + sequenceB, err := path.EndpointB.SendPacket(defaultTimeoutHeight, disabledTimeoutTimestamp, ibctesting.MockPacketData) + suite.Require().NoError(err) + packetB := types.NewPacket(ibctesting.MockPacketData, sequenceB, path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, defaultTimeoutHeight, disabledTimeoutTimestamp) + err = path.EndpointA.RecvPacket(packetB) + suite.Require().NoError(err) + + suite.Require().NoError(path.EndpointA.ChanUpgradeInit()) + suite.Require().NoError(path.EndpointB.ChanUpgradeTry()) + suite.Require().NoError(path.EndpointA.ChanUpgradeAck()) + suite.Require().NoError(path.EndpointB.ChanUpgradeConfirm()) + + // Ack packets to delete packet commitments before calling WriteUpgradeOpenChannel + err = path.EndpointA.AcknowledgePacket(packetA, ibctesting.MockAcknowledgement) + suite.Require().NoError(err) + + err = path.EndpointB.AcknowledgePacket(packetB, ibctesting.MockAcknowledgement) + suite.Require().NoError(err) + + // pre upgrade assertions + tc.preUpgrade() + + tc.malleate() + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.WriteUpgradeOpenChannel(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + + // post upgrade assertions + tc.postUpgrade() + + // Assert that state stored for upgrade has been deleted + upgrade, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().Equal(types.Upgrade{}, upgrade) + suite.Require().False(found) + + counterpartyUpgrade, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetCounterpartyUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().Equal(types.Upgrade{}, counterpartyUpgrade) + suite.Require().False(found) + + // events := ctx.EventManager().Events().ToABCIEvents() + // expEvents := ibctesting.EventsMap{ + // types.EventTypeChannelUpgradeOpen: { + // types.AttributeKeyPortID: path.EndpointA.ChannelConfig.PortID, + // types.AttributeKeyChannelID: path.EndpointA.ChannelID, + // types.AttributeCounterpartyPortID: path.EndpointB.ChannelConfig.PortID, + // types.AttributeCounterpartyChannelID: path.EndpointB.ChannelID, + // types.AttributeKeyChannelState: types.OPEN.String(), + // types.AttributeKeyUpgradeConnectionHops: channel.ConnectionHops[0], + // types.AttributeKeyUpgradeVersion: channel.Version, + // types.AttributeKeyUpgradeOrdering: channel.Ordering.String(), + // types.AttributeKeyUpgradeSequence: fmt.Sprintf("%d", channel.UpgradeSequence), + // }, + // sdk.EventTypeMessage: { + // sdk.AttributeKeyModule: types.AttributeValueCategory, + // }, + // } + // ibctesting.AssertEventsLegacy(&suite.Suite, expEvents, events) + }) + } +} + +func (suite *KeeperTestSuite) TestChanUpgradeCancel() { + var ( + path *ibctesting.Path + errorReceipt types.ErrorReceipt + errorReceiptProof []byte + proofHeight clienttypes.Height + ) + + tests := []struct { + name string + malleate func() + expError error + }{ + { + name: "success with flush complete state", + malleate: func() {}, + expError: nil, + }, + { + name: "success with flushing state", + malleate: func() { + channel := path.EndpointA.GetChannel() + channel.State = types.FLUSHING + path.EndpointA.SetChannel(channel) + }, + expError: nil, + }, + { + name: "upgrade cannot be cancelled in FLUSHCOMPLETE with invalid error receipt", + malleate: func() { + errorReceiptProof = nil + }, + expError: commitmenttypes.ErrInvalidProof, + }, + { + name: "upgrade cannot be cancelled in FLUSHCOMPLETE with error receipt sequence less than channel upgrade sequence", + malleate: func() { + var ok bool + errorReceipt, ok = suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(ok) + + errorReceipt.Sequence = path.EndpointA.GetChannel().UpgradeSequence - 1 + + suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.SetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, errorReceipt) + + suite.coordinator.CommitBlock(suite.chainB) + + suite.Require().NoError(path.EndpointA.UpdateClient()) + + upgradeErrorReceiptKey := host.ChannelUpgradeErrorKey(path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + errorReceiptProof, proofHeight = suite.chainB.QueryProof(upgradeErrorReceiptKey) + }, + expError: types.ErrInvalidUpgradeSequence, + }, + { + name: "channel not found", + malleate: func() { + path.EndpointA.Chain.DeleteKey(host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + }, + expError: types.ErrChannelNotFound, + }, + { + name: "upgrade not found", + malleate: func() { + path.EndpointA.Chain.DeleteKey(host.ChannelUpgradeKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + }, + expError: types.ErrUpgradeNotFound, + }, + { + name: "error receipt sequence less than channel upgrade sequence", + malleate: func() { + var ok bool + errorReceipt, ok = suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(ok) + + errorReceipt.Sequence = path.EndpointA.GetChannel().UpgradeSequence - 1 + + suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.SetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, errorReceipt) + + suite.coordinator.CommitBlock(suite.chainB) + + suite.Require().NoError(path.EndpointA.UpdateClient()) + + upgradeErrorReceiptKey := host.ChannelUpgradeErrorKey(path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + errorReceiptProof, proofHeight = suite.chainB.QueryProof(upgradeErrorReceiptKey) + }, + expError: types.ErrInvalidUpgradeSequence, + }, + { + name: "connection not found", + malleate: func() { + channel := path.EndpointA.GetChannel() + channel.ConnectionHops = []string{"connection-100"} + path.EndpointA.SetChannel(channel) + }, + expError: connectiontypes.ErrConnectionNotFound, + }, + { + name: "channel is in flush complete, error verification failed", + malleate: func() { + var ok bool + errorReceipt, ok = suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(ok) + + errorReceipt.Message = ibctesting.InvalidID + + suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.SetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, errorReceipt) + suite.coordinator.CommitBlock(suite.chainB) + }, + expError: commitmenttypes.ErrInvalidProof, + }, + { + name: "error verification failed", + malleate: func() { + var ok bool + errorReceipt, ok = suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(ok) + + errorReceipt.Message = ibctesting.InvalidID + suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.SetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, errorReceipt) + suite.coordinator.CommitBlock(suite.chainB) + }, + expError: commitmenttypes.ErrInvalidProof, + }, + { + name: "error verification failed with empty proof", + malleate: func() { + errorReceiptProof = nil + }, + expError: commitmenttypes.ErrInvalidProof, + }, + } + + for _, tc := range tests { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + suite.Require().NoError(path.EndpointA.ChanUpgradeInit()) + + // cause the upgrade to fail on chain b so an error receipt is written. + // if the counterparty (chain A) upgrade sequence is less than the current sequence, (chain B) + // an upgrade error will be returned by chain B during ChanUpgradeTry. + channel := path.EndpointA.GetChannel() + channel.UpgradeSequence = 1 + path.EndpointA.SetChannel(channel) + + channel = path.EndpointB.GetChannel() + channel.UpgradeSequence = 2 + path.EndpointB.SetChannel(channel) + + suite.Require().NoError(path.EndpointA.UpdateClient()) + suite.Require().NoError(path.EndpointB.UpdateClient()) + + // error receipt is written to chain B here. + suite.Require().NoError(path.EndpointB.ChanUpgradeTry()) + + suite.Require().NoError(path.EndpointA.UpdateClient()) + + upgradeErrorReceiptKey := host.ChannelUpgradeErrorKey(path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + errorReceiptProof, proofHeight = suite.chainB.QueryProof(upgradeErrorReceiptKey) + + var ok bool + errorReceipt, ok = suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(ok) + + channel = path.EndpointA.GetChannel() + channel.State = types.FLUSHCOMPLETE + path.EndpointA.SetChannel(channel) + + tc.malleate() + + err := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.ChanUpgradeCancel(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, errorReceipt, errorReceiptProof, proofHeight) + + expPass := tc.expError == nil + if expPass { + suite.Require().NoError(err) + } else { + suite.Require().ErrorIs(err, tc.expError) + } + }) + } +} + +// TestChanUpgrade_UpgradeSucceeds_AfterCancel verifies that if upgrade sequences +// become out of sync, the upgrade can still be performed successfully after the upgrade is cancelled. +func (suite *KeeperTestSuite) TestChanUpgrade_UpgradeSucceeds_AfterCancel() { + path := ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + suite.Require().NoError(path.EndpointA.ChanUpgradeInit()) + + // cause the upgrade to fail on chain b so an error receipt is written. + // if the counterparty (chain A) upgrade sequence is less than the current sequence, (chain B) + // an upgrade error will be returned by chain B during ChanUpgradeTry. + channel := path.EndpointA.GetChannel() + channel.UpgradeSequence = 1 + path.EndpointA.SetChannel(channel) + + channel = path.EndpointB.GetChannel() + channel.UpgradeSequence = 5 + path.EndpointB.SetChannel(channel) + + suite.Require().NoError(path.EndpointA.UpdateClient()) + suite.Require().NoError(path.EndpointB.UpdateClient()) + + // error receipt is written to chain B here. + suite.Require().NoError(path.EndpointB.ChanUpgradeTry()) + + suite.Require().NoError(path.EndpointA.UpdateClient()) + + var errorReceipt types.ErrorReceipt + suite.T().Run("error receipt written", func(t *testing.T) { + var ok bool + errorReceipt, ok = suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(ok) + }) + + suite.T().Run("upgrade cancelled successfully", func(t *testing.T) { + upgradeErrorReceiptKey := host.ChannelUpgradeErrorKey(path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + errorReceiptProof, proofHeight := suite.chainB.QueryProof(upgradeErrorReceiptKey) + + err := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.ChanUpgradeCancel(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, errorReceipt, errorReceiptProof, proofHeight) + suite.Require().NoError(err) + + // need to explicitly call WriteUpgradeOpenChannel as this usually would happen in the msg server layer. + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.WriteUpgradeCancelChannel(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, errorReceipt.Sequence) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.OPEN, channel.State) + + suite.T().Run("verify upgrade sequence fastforwards to channelB sequence", func(t *testing.T) { + suite.Require().Equal(uint64(5), channel.UpgradeSequence) + }) + }) + + suite.T().Run("successfully completes upgrade", func(t *testing.T) { + suite.Require().NoError(path.EndpointA.ChanUpgradeInit()) + suite.Require().NoError(path.EndpointB.ChanUpgradeTry()) + suite.Require().NoError(path.EndpointA.ChanUpgradeAck()) + suite.Require().NoError(path.EndpointB.ChanUpgradeConfirm()) + suite.Require().NoError(path.EndpointA.ChanUpgradeOpen()) + }) + + suite.T().Run("channel in expected state", func(t *testing.T) { + channel := path.EndpointA.GetChannel() + suite.Require().Equal(types.OPEN, channel.State, "channel should be in OPEN state") + suite.Require().Equal(mock.UpgradeVersion, channel.Version, "version should be correctly upgraded") + suite.Require().Equal(mock.UpgradeVersion, path.EndpointB.GetChannel().Version, "version should be correctly upgraded") + suite.Require().Equal(uint64(6), channel.UpgradeSequence, "upgrade sequence should be incremented") + suite.Require().Equal(uint64(6), path.EndpointB.GetChannel().UpgradeSequence, "upgrade sequence should be incremented on counterparty") + }) +} + +func (suite *KeeperTestSuite) TestWriteUpgradeCancelChannel() { + var path *ibctesting.Path + + testCases := []struct { + name string + malleate func() + expPanic bool + }{ + { + name: "success", + malleate: func() {}, + expPanic: false, + }, + { + name: "channel not found", + malleate: func() { + path.EndpointA.Chain.DeleteKey(host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + }, + expPanic: true, + }, + { + name: "upgrade not found", + malleate: func() { + path.EndpointA.Chain.DeleteKey(host.ChannelUpgradeKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + }, + expPanic: true, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + suite.Require().NoError(path.EndpointA.ChanUpgradeInit()) + + // cause the upgrade to fail on chain b so an error receipt is written. + // if the counterparty (chain A) upgrade sequence is less than the current sequence, (chain B) + // an upgrade error will be returned by chain B during ChanUpgradeTry. + channel := path.EndpointA.GetChannel() + channel.UpgradeSequence = 1 + path.EndpointA.SetChannel(channel) + + channel = path.EndpointB.GetChannel() + channel.UpgradeSequence = 2 + path.EndpointB.SetChannel(channel) + + err := path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + err = path.EndpointA.UpdateClient() + suite.Require().NoError(err) + + errorReceipt, ok := suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(ok) + + ctx := suite.chainA.GetContext() + tc.malleate() + + if tc.expPanic { + suite.Require().Panics(func() { + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.WriteUpgradeCancelChannel(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, errorReceipt.Sequence) + }) + } else { + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.WriteUpgradeCancelChannel(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, errorReceipt.Sequence) + + channel = path.EndpointA.GetChannel() + + // Verify that channel has been restored to previous state + suite.Require().Equal(types.OPEN, channel.State) + suite.Require().Equal(mock.Version, channel.Version) + suite.Require().Equal(errorReceipt.Sequence, channel.UpgradeSequence) + + // Assert that state stored for upgrade has been deleted + upgrade, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().Equal(types.Upgrade{}, upgrade) + suite.Require().False(found) + + counterpartyUpgrade, found := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.GetCounterpartyUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().Equal(types.Upgrade{}, counterpartyUpgrade) + suite.Require().False(found) + + // we need to find the event values from the proposed upgrade as the actual upgrade has been deleted. + // proposedUpgrade := path.EndpointA.GetProposedUpgrade() + // events := ctx.EventManager().Events().ToABCIEvents() + // expEvents := ibctesting.EventsMap{ + // types.EventTypeChannelUpgradeCancel: { + // types.AttributeKeyPortID: path.EndpointA.ChannelConfig.PortID, + // types.AttributeKeyChannelID: path.EndpointA.ChannelID, + // types.AttributeCounterpartyPortID: path.EndpointB.ChannelConfig.PortID, + // types.AttributeCounterpartyChannelID: path.EndpointB.ChannelID, + // types.AttributeKeyUpgradeConnectionHops: proposedUpgrade.Fields.ConnectionHops[0], + // types.AttributeKeyUpgradeVersion: proposedUpgrade.Fields.Version, + // types.AttributeKeyUpgradeOrdering: proposedUpgrade.Fields.Ordering.String(), + // types.AttributeKeyUpgradeSequence: fmt.Sprintf("%d", channel.UpgradeSequence), + // }, + // sdk.EventTypeMessage: { + // sdk.AttributeKeyModule: types.AttributeValueCategory, + // }, + // } + + } + }) + } +} + +func (suite *KeeperTestSuite) TestChanUpgradeTimeout() { + var ( + path *ibctesting.Path + proofChannel []byte + proofHeight exported.Height + ) + + timeoutUpgrade := func() { + upgrade := path.EndpointA.GetProposedUpgrade() + upgrade.Timeout = types.NewTimeout(clienttypes.ZeroHeight(), 1) + path.EndpointA.SetChannelUpgrade(upgrade) + suite.Require().NoError(path.EndpointB.UpdateClient()) + } + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success: proof timestamp has passed", + func() { + timeoutUpgrade() + + channelKey := host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proofChannel, proofHeight = path.EndpointB.QueryProof(channelKey) + }, + nil, + }, + { + "channel not found", + func() { + path.EndpointA.ChannelID = ibctesting.InvalidID + }, + types.ErrChannelNotFound, + }, + { + "channel state is not in FLUSHING or FLUSHINGCOMPLETE state", + func() { + suite.Require().NoError(path.EndpointA.SetChannelState(types.OPEN)) + }, + types.ErrInvalidChannelState, + }, + { + "current upgrade not found", + func() { + suite.chainA.DeleteKey(host.ChannelUpgradeKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + }, + types.ErrUpgradeNotFound, + }, + { + "connection not found", + func() { + channel := path.EndpointA.GetChannel() + channel.ConnectionHops[0] = ibctesting.InvalidID + path.EndpointA.SetChannel(channel) + }, + connectiontypes.ErrConnectionNotFound, + }, + { + "connection not open", + func() { + connectionEnd := path.EndpointA.GetConnection() + connectionEnd.State = connectiontypes.UNINITIALIZED + path.EndpointA.SetConnection(connectionEnd) + }, + connectiontypes.ErrInvalidConnectionState, + }, + { + "unable to retrieve timestamp at proof height", + func() { + // TODO: revert this when the upgrade timeout is not hard coded to 1000 + proofHeight = clienttypes.NewHeight(clienttypes.ParseChainID(suite.chainA.ChainID), uint64(suite.chainA.GetContext().BlockHeight())+1000) + }, + clienttypes.ErrConsensusStateNotFound, + }, + { + "invalid channel state proof", + func() { + channel := path.EndpointB.GetChannel() + channel.State = types.OPEN + path.EndpointB.SetChannel(channel) + + timeoutUpgrade() + + suite.Require().NoError(path.EndpointA.UpdateClient()) + + channelKey := host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proofChannel, proofHeight = path.EndpointB.QueryProof(channelKey) + + // modify state so the proof becomes invalid. + channel.State = types.FLUSHING + path.EndpointB.SetChannel(channel) + suite.coordinator.CommitNBlocks(suite.chainB, 1) + }, + commitmenttypes.ErrInvalidProof, + }, + { + "invalid counterparty upgrade sequence", + func() { + channel := path.EndpointB.GetChannel() + channel.UpgradeSequence = path.EndpointA.GetChannel().UpgradeSequence - 1 + path.EndpointB.SetChannel(channel) + + timeoutUpgrade() + + suite.Require().NoError(path.EndpointA.UpdateClient()) + + channelKey := host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proofChannel, proofHeight = path.EndpointB.QueryProof(channelKey) + }, + types.ErrInvalidUpgradeSequence, + }, + { + "timeout timestamp has not passed", + func() { + upgrade := path.EndpointA.GetProposedUpgrade() + upgrade.Timeout.Timestamp = math.MaxUint64 + path.EndpointA.SetChannelUpgrade(upgrade) + + suite.Require().NoError(path.EndpointB.UpdateClient()) + + channelKey := host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proofChannel, proofHeight = path.EndpointB.QueryProof(channelKey) + }, + types.ErrInvalidUpgradeTimeout, + }, + { + "counterparty channel state is not OPEN or FLUSHING (crossing hellos)", + func() { + channel := path.EndpointB.GetChannel() + channel.State = types.FLUSHCOMPLETE + path.EndpointB.SetChannel(channel) + + timeoutUpgrade() + + suite.Require().NoError(path.EndpointA.UpdateClient()) + + channelKey := host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proofChannel, proofHeight = path.EndpointB.QueryProof(channelKey) + }, + types.ErrInvalidCounterparty, + }, + { + "counterparty proposed connection invalid", + func() { + channel := path.EndpointB.GetChannel() + channel.State = types.OPEN + path.EndpointB.SetChannel(channel) + + timeoutUpgrade() + + upgrade := path.EndpointA.GetChannelUpgrade() + upgrade.Fields.ConnectionHops = []string{"connection-100"} + path.EndpointA.SetChannelUpgrade(upgrade) + + suite.Require().NoError(path.EndpointA.UpdateClient()) + suite.Require().NoError(path.EndpointB.UpdateClient()) + + channelKey := host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proofChannel, proofHeight = path.EndpointB.QueryProof(channelKey) + }, + connectiontypes.ErrConnectionNotFound, + }, + { + "counterparty channel already upgraded", + func() { + // put chainA channel into OPEN state since both sides are in FLUSHCOMPLETE + suite.Require().NoError(path.EndpointB.ChanUpgradeConfirm()) + + timeoutUpgrade() + + suite.Require().NoError(path.EndpointA.UpdateClient()) + + channelKey := host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proofChannel, proofHeight = path.EndpointB.QueryProof(channelKey) + }, + types.ErrUpgradeTimeoutFailed, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + expPass := tc.expError == nil + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + suite.Require().NoError(path.EndpointA.ChanUpgradeInit()) + suite.Require().NoError(path.EndpointB.ChanUpgradeTry()) + suite.Require().NoError(path.EndpointA.ChanUpgradeAck()) + + channelKey := host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proofChannel, proofHeight = path.EndpointB.QueryProof(channelKey) + + tc.malleate() + + err := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.ChanUpgradeTimeout( + suite.chainA.GetContext(), + path.EndpointA.ChannelConfig.PortID, + path.EndpointA.ChannelID, + path.EndpointB.GetChannel(), + proofChannel, + proofHeight, + ) + + if expPass { + suite.Require().NoError(err) + } else { + suite.assertUpgradeError(err, tc.expError) + } + }) + } +} + +func (suite *KeeperTestSuite) TestStartFlush() { + var path *ibctesting.Path + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + "channel not found", + func() { + path.EndpointB.ChannelID = "invalid-channel" + path.EndpointB.ChannelConfig.PortID = "invalid-port" + }, + types.ErrChannelNotFound, + }, + { + "connection not found", + func() { + channel := path.EndpointB.GetChannel() + channel.ConnectionHops[0] = ibctesting.InvalidID + path.EndpointB.SetChannel(channel) + }, + connectiontypes.ErrConnectionNotFound, + }, + { + "connection state is not in OPEN state", + func() { + conn := path.EndpointB.GetConnection() + conn.State = connectiontypes.INIT + path.EndpointB.SetConnection(conn) + }, + connectiontypes.ErrInvalidConnectionState, + }, + { + "next sequence send not found", + func() { + // Delete next sequence send key from store + store := suite.chainB.GetContext().KVStore(suite.chainB.GetSimApp().GetKey(exported.StoreKey)) + store.Delete(host.NextSequenceSendKey(path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID)) + }, + types.ErrSequenceSendNotFound, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + // crossing hellos so that the upgrade is created on chain B. + // the ChanUpgradeInit sub protocol is also called when it is not a crossing hello situation. + err = path.EndpointB.ChanUpgradeInit() + suite.Require().NoError(err) + + upgrade := path.EndpointB.GetChannelUpgrade() + + tc.malleate() + + err = suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.StartFlushing( + suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, &upgrade, + ) + + if tc.expError != nil { + suite.assertUpgradeError(err, tc.expError) + } else { + channel := path.EndpointB.GetChannel() + + nextSequenceSend, ok := suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.GetNextSequenceSend(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(ok) + + suite.Require().Equal(types.FLUSHING, channel.State) + suite.Require().Equal(nextSequenceSend, upgrade.NextSequenceSend) + + expectedTimeoutTimestamp := types.DefaultTimeout.Timestamp + uint64(suite.chainB.GetContext().BlockTime().UnixNano()) + suite.Require().Equal(expectedTimeoutTimestamp, upgrade.Timeout.Timestamp) + suite.Require().Equal(clienttypes.ZeroHeight(), upgrade.Timeout.Height, "only timestamp should be set") + suite.Require().NoError(err) + } + }) + } +} + +func (suite *KeeperTestSuite) TestValidateUpgradeFields() { + var ( + proposedUpgrade *types.UpgradeFields + path *ibctesting.Path + ) + tests := []struct { + name string + malleate func() + expPass bool + }{ + { + name: "change channel version", + malleate: func() { + proposedUpgrade.Version = mock.UpgradeVersion + }, + expPass: true, + }, + { + name: "change connection hops", + malleate: func() { + path := ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + proposedUpgrade.ConnectionHops = []string{path.EndpointA.ConnectionID} + }, + expPass: true, + }, + { + name: "fails with unmodified fields", + malleate: func() {}, + expPass: false, + }, + { + name: "fails when connection is not set", + malleate: func() { + storeKey := suite.chainA.GetSimApp().GetKey(exported.StoreKey) + kvStore := suite.chainA.GetContext().KVStore(storeKey) + kvStore.Delete(host.ConnectionKey(ibctesting.FirstConnectionID)) + }, + expPass: false, + }, + { + name: "fails when connection is not open", + malleate: func() { + connection := path.EndpointA.GetConnection() + connection.State = connectiontypes.UNINITIALIZED + path.EndpointA.SetConnection(connection) + }, + expPass: false, + }, + { + name: "fails when connection versions do not exist", + malleate: func() { + // update channel version first so that existing channel end is not identical to proposed upgrade + proposedUpgrade.Version = mock.UpgradeVersion + + connection := path.EndpointA.GetConnection() + connection.Versions = []*connectiontypes.Version{} + path.EndpointA.SetConnection(connection) + }, + expPass: false, + }, + { + name: "fails when connection version does not support the new ordering", + malleate: func() { + // update channel version first so that existing channel end is not identical to proposed upgrade + proposedUpgrade.Version = mock.UpgradeVersion + + connection := path.EndpointA.GetConnection() + connection.Versions = []*connectiontypes.Version{ + connectiontypes.NewVersion("1", []string{"ORDER_ORDERED"}), + } + path.EndpointA.SetConnection(connection) + }, + expPass: false, + }, + } + + for _, tc := range tests { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + existingChannel := path.EndpointA.GetChannel() + proposedUpgrade = &types.UpgradeFields{ + Ordering: existingChannel.Ordering, + ConnectionHops: existingChannel.ConnectionHops, + Version: existingChannel.Version, + } + + tc.malleate() + + err := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.ValidateSelfUpgradeFields(suite.chainA.GetContext(), *proposedUpgrade, existingChannel) + if tc.expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *KeeperTestSuite) assertUpgradeError(actualError, expError error) { + suite.Require().Error(actualError) + + if expUpgradeError, ok := expError.(*types.UpgradeError); ok { + upgradeError, ok := actualError.(*types.UpgradeError) + suite.Require().True(ok) + suite.Require().Equal(expUpgradeError.GetErrorReceipt(), upgradeError.GetErrorReceipt()) + } + + suite.Require().True(errorsmod.IsOf(actualError, expError), fmt.Sprintf("expected error: %s, actual error: %s", expError, actualError)) +} + +// TestAbortUpgrade tests that when the channel handshake is aborted, the channel state +// is restored the previous state and that an error receipt is written, and upgrade state which +// is no longer required is deleted. +func (suite *KeeperTestSuite) TestAbortUpgrade() { + var ( + path *ibctesting.Path + upgradeError error + ) + + tests := []struct { + name string + malleate func() + expPass bool + }{ + { + name: "success", + malleate: func() {}, + expPass: true, + }, + { + name: "regular error", + malleate: func() { + // in app callbacks error receipts should still be written if a regular error is returned. + // i.e. not an instance of `types.UpgradeError` + upgradeError = types.ErrInvalidUpgrade + }, + expPass: true, + }, + { + name: "channel does not exist", + malleate: func() { + suite.chainA.DeleteKey(host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + }, + expPass: false, + }, + { + name: "fails with nil upgrade error", + malleate: func() { + upgradeError = nil + }, + expPass: false, + }, + } + + for _, tc := range tests { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + channelKeeper := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper + + path.EndpointA.ChannelConfig.Version = mock.UpgradeVersion + suite.Require().NoError(path.EndpointA.ChanUpgradeInit()) + + // fetch the upgrade before abort for assertions later on. + actualUpgrade, ok := channelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(ok, "upgrade should be found") + + upgradeError = types.NewUpgradeError(1, types.ErrInvalidChannel) + + tc.malleate() + + if tc.expPass { + + ctx := suite.chainA.GetContext() + + suite.Require().NotPanics(func() { + channelKeeper.MustAbortUpgrade(ctx, path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, upgradeError) + }) + + // events := ctx.EventManager().Events().ToABCIEvents() + // expEvents := ibctesting.EventsMap{ + // "channel_upgrade_error": { + // "port_id": path.EndpointA.ChannelConfig.PortID, + // "channel_id": path.EndpointA.ChannelID, + // "counterparty_port_id": path.EndpointB.ChannelConfig.PortID, + // "counterparty_channel_id": path.EndpointB.ChannelID, + // "upgrade_sequence": fmt.Sprintf("%d", path.EndpointA.GetChannel().UpgradeSequence), + // "upgrade_error_receipt": upgradeError.Error(), + // }, + // } + + channel, found := channelKeeper.GetChannel(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found, "channel should be found") + + suite.Require().Equal(types.OPEN, channel.State, "channel state should be %s", types.OPEN.String()) + + _, found = channelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().False(found, "upgrade info should be deleted") + + errorReceipt, found := channelKeeper.GetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found, "error receipt should be found") + + if ue, ok := upgradeError.(*types.UpgradeError); ok { + suite.Require().Equal(ue.GetErrorReceipt(), errorReceipt, "error receipt does not match expected error receipt") + } + } else { + + suite.Require().Panics(func() { + channelKeeper.MustAbortUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, upgradeError) + }) + + channel, found := channelKeeper.GetChannel(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + if found { // test cases uses a channel that exists + suite.Require().Equal(types.OPEN, channel.State, "channel state should not be restored to %s", types.OPEN.String()) + } + + _, found = channelKeeper.GetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().False(found, "error receipt should not be found") + + upgrade, found := channelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + if found { // this should be all test cases except for when the upgrade is explicitly deleted. + suite.Require().Equal(actualUpgrade, upgrade, "upgrade info should not be deleted") + } + } + }) + } +} + +func (suite *KeeperTestSuite) TestCheckForUpgradeCompatibility() { + var ( + path *ibctesting.Path + upgradeFields types.UpgradeFields + counterpartyUpgradeFields types.UpgradeFields + ) + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + "upgrade ordering is not the same on both sides", + func() { + upgradeFields.Ordering = types.ORDERED + }, + types.ErrIncompatibleCounterpartyUpgrade, + }, + { + "proposed connection is not found", + func() { + upgradeFields.ConnectionHops[0] = ibctesting.InvalidID + }, + connectiontypes.ErrConnectionNotFound, + }, + { + "proposed connection is not in OPEN state", + func() { + // reuse existing connection to create a new connection in a non OPEN state + connectionEnd := path.EndpointB.GetConnection() + connectionEnd.State = connectiontypes.UNINITIALIZED + connectionEnd.Counterparty.ConnectionId = counterpartyUpgradeFields.ConnectionHops[0] // both sides must be each other's counterparty + + // set proposed connection in state + proposedConnectionID := "connection-100" + suite.chainB.GetSimApp().GetIBCKeeper().ConnectionKeeper.SetConnection(suite.chainB.GetContext(), proposedConnectionID, connectionEnd) + upgradeFields.ConnectionHops[0] = proposedConnectionID + }, + connectiontypes.ErrInvalidConnectionState, + }, + { + "proposed connection ends are not each other's counterparty", + func() { + // reuse existing connection to create a new connection in a non OPEN state + connectionEnd := path.EndpointB.GetConnection() + // ensure counterparty connectionID does not match connectionID set in counterparty proposed upgrade + connectionEnd.Counterparty.ConnectionId = "connection-50" + + // set proposed connection in state + proposedConnectionID := "connection-100" + suite.chainB.GetSimApp().GetIBCKeeper().ConnectionKeeper.SetConnection(suite.chainB.GetContext(), proposedConnectionID, connectionEnd) + upgradeFields.ConnectionHops[0] = proposedConnectionID + }, + types.ErrIncompatibleCounterpartyUpgrade, + }, + { + "proposed upgrade version is not the same on both sides", + func() { + upgradeFields.Version = mock.Version + }, + types.ErrIncompatibleCounterpartyUpgrade, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + upgradeFields = path.EndpointA.GetProposedUpgrade().Fields + counterpartyUpgradeFields = path.EndpointB.GetProposedUpgrade().Fields + + tc.malleate() + + err = suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.CheckForUpgradeCompatibility(suite.chainB.GetContext(), upgradeFields, counterpartyUpgradeFields) + if tc.expError != nil { + suite.Require().ErrorIs(err, tc.expError) + } else { + suite.Require().NoError(err) + } + }) + } +} + +func (suite *KeeperTestSuite) TestSyncUpgradeSequence() { + var ( + path *ibctesting.Path + counterpartyUpgradeSequence uint64 + ) + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + "upgrade sequence mismatch, endpointB channel upgrade sequence is ahead", + func() { + channel := path.EndpointB.GetChannel() + channel.UpgradeSequence = 10 + path.EndpointB.SetChannel(channel) + }, + types.NewUpgradeError(10, types.ErrInvalidUpgradeSequence), // max sequence will be returned + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeInit() + suite.Require().NoError(err) + + counterpartyUpgradeSequence = 1 + + tc.malleate() + + err = suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.SyncUpgradeSequence(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID, path.EndpointB.GetChannel(), counterpartyUpgradeSequence) + if tc.expError != nil { + suite.Require().ErrorIs(err, tc.expError) + } else { + suite.Require().NoError(err) + } + }) + } +} + +func (suite *KeeperTestSuite) TestChanUpgradeCrossingHelloWithHistoricalProofs() { + var path *ibctesting.Path + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + "counterparty (chain B) has already progressed to ACK step", + func() { + err := path.EndpointB.ChanUpgradeAck() + suite.Require().NoError(err) + }, + types.ErrInvalidChannelState, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = mock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeInit() + suite.Require().NoError(err) + + suite.coordinator.CommitBlock(suite.chainA, suite.chainB) + + err = path.EndpointB.UpdateClient() + suite.Require().NoError(err) + + historicalChannelProof, historicalUpgradeProof, proofHeight := path.EndpointA.QueryChannelUpgradeProof() + + err = path.EndpointA.ChanUpgradeTry() + suite.Require().NoError(err) + + tc.malleate() + + _, upgrade, err := suite.chainB.GetSimApp().GetIBCKeeper().ChannelKeeper.ChanUpgradeTry( + suite.chainB.GetContext(), + path.EndpointB.ChannelConfig.PortID, + path.EndpointB.ChannelID, + path.EndpointB.GetChannelUpgrade().Fields.ConnectionHops, + path.EndpointA.GetChannelUpgrade().Fields, + 1, + historicalChannelProof, + historicalUpgradeProof, + proofHeight, + ) + + expPass := tc.expError == nil + if expPass { + suite.Require().NoError(err) + suite.Require().NotEmpty(upgrade) + } else { + suite.Require().ErrorIs(err, tc.expError) + } + }) + } +} + +func (suite *KeeperTestSuite) TestWriteErrorReceipt() { + var path *ibctesting.Path + var upgradeError *types.UpgradeError + + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success", + func() {}, + nil, + }, + { + "success: existing error receipt found at a lower sequence", + func() { + // write an error sequence with a lower sequence number + previousUpgradeError := types.NewUpgradeError(upgradeError.GetErrorReceipt().Sequence-1, types.ErrInvalidUpgrade) + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.SetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, previousUpgradeError.GetErrorReceipt()) + }, + nil, + }, + { + "failure: existing error receipt found at a higher sequence", + func() { + // write an error sequence with a higher sequence number + previousUpgradeError := types.NewUpgradeError(upgradeError.GetErrorReceipt().Sequence+1, types.ErrInvalidUpgrade) + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.SetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, previousUpgradeError.GetErrorReceipt()) + }, + errorsmod.Wrap(types.ErrInvalidUpgradeSequence, "error receipt sequence (10) must be greater than existing error receipt sequence (11)"), + }, + { + "failure: channel not found", + func() { + suite.chainA.DeleteKey(host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID)) + }, + errorsmod.Wrap(types.ErrChannelNotFound, "port ID (mock) channel ID (channel-0)"), + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + channelKeeper := suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper + + upgradeError = types.NewUpgradeError(10, types.ErrInvalidUpgrade) + + tc.malleate() + + expPass := tc.expError == nil + if expPass { + suite.NotPanics(func() { + channelKeeper.WriteErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, upgradeError) + }) + } else { + suite.PanicsWithError(tc.expError.Error(), func() { + channelKeeper.WriteErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID, upgradeError) + }) + } + }) + } +} diff --git a/modules/core/04-channel/types/channel.go b/modules/core/04-channel/types/channel.go index d288a2a8842..21b7bf3b658 100644 --- a/modules/core/04-channel/types/channel.go +++ b/modules/core/04-channel/types/channel.go @@ -23,6 +23,8 @@ func NewChannel( Counterparty: counterparty, ConnectionHops: hops, Version: version, + // UpgradeSequence is intentionally left empty as a new channel has not performed an upgrade. + UpgradeSequence: 0, } } @@ -115,13 +117,14 @@ func (c Counterparty) ValidateBasic() error { // NewIdentifiedChannel creates a new IdentifiedChannel instance func NewIdentifiedChannel(portID, channelID string, ch Channel) IdentifiedChannel { return IdentifiedChannel{ - State: ch.State, - Ordering: ch.Ordering, - Counterparty: ch.Counterparty, - ConnectionHops: ch.ConnectionHops, - Version: ch.Version, - PortId: portID, - ChannelId: channelID, + State: ch.State, + Ordering: ch.Ordering, + Counterparty: ch.Counterparty, + ConnectionHops: ch.ConnectionHops, + Version: ch.Version, + UpgradeSequence: ch.UpgradeSequence, + PortId: portID, + ChannelId: channelID, } } diff --git a/modules/core/04-channel/types/channel.pb.go b/modules/core/04-channel/types/channel.pb.go index de28522e4df..4ec0fc395e5 100644 --- a/modules/core/04-channel/types/channel.pb.go +++ b/modules/core/04-channel/types/channel.pb.go @@ -25,7 +25,7 @@ var _ = math.Inf const _ = proto.GoGoProtoPackageIsVersion3 // please upgrade the proto package // State defines if a channel is in one of the following states: -// CLOSED, INIT, TRYOPEN, OPEN or UNINITIALIZED. +// CLOSED, INIT, TRYOPEN, OPEN, FLUSHING, FLUSHCOMPLETE or UNINITIALIZED. type State int32 const ( @@ -41,6 +41,10 @@ const ( // A channel has been closed and can no longer be used to send or receive // packets. CLOSED State = 4 + // A channel has just accepted the upgrade handshake attempt and is flushing in-flight packets. + FLUSHING State = 5 + // A channel has just completed flushing any in-flight packets. + FLUSHCOMPLETE State = 6 ) var State_name = map[int32]string{ @@ -49,6 +53,8 @@ var State_name = map[int32]string{ 2: "STATE_TRYOPEN", 3: "STATE_OPEN", 4: "STATE_CLOSED", + 5: "STATE_FLUSHING", + 6: "STATE_FLUSHCOMPLETE", } var State_value = map[string]int32{ @@ -57,6 +63,8 @@ var State_value = map[string]int32{ "STATE_TRYOPEN": 2, "STATE_OPEN": 3, "STATE_CLOSED": 4, + "STATE_FLUSHING": 5, + "STATE_FLUSHCOMPLETE": 6, } func (x State) String() string { @@ -115,6 +123,9 @@ type Channel struct { ConnectionHops []string `protobuf:"bytes,4,rep,name=connection_hops,json=connectionHops,proto3" json:"connection_hops,omitempty"` // opaque channel version, which is agreed upon during the handshake Version string `protobuf:"bytes,5,opt,name=version,proto3" json:"version,omitempty"` + // upgrade sequence indicates the latest upgrade attempt performed by this channel + // the value of 0 indicates the channel has never been upgraded + UpgradeSequence uint64 `protobuf:"varint,6,opt,name=upgrade_sequence,json=upgradeSequence,proto3" json:"upgrade_sequence,omitempty"` } func (m *Channel) Reset() { *m = Channel{} } @@ -168,6 +179,9 @@ type IdentifiedChannel struct { PortId string `protobuf:"bytes,6,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` // channel identifier ChannelId string `protobuf:"bytes,7,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` + // upgrade sequence indicates the latest upgrade attempt performed by this channel + // the value of 0 indicates the channel has never been upgraded + UpgradeSequence uint64 `protobuf:"varint,8,opt,name=upgrade_sequence,json=upgradeSequence,proto3" json:"upgrade_sequence,omitempty"` } func (m *IdentifiedChannel) Reset() { *m = IdentifiedChannel{} } @@ -543,6 +557,52 @@ func (m *Timeout) GetTimestamp() uint64 { return 0 } +// Params defines the set of IBC channel parameters. +type Params struct { + // the relative timeout after which channel upgrades will time out. + UpgradeTimeout Timeout `protobuf:"bytes,1,opt,name=upgrade_timeout,json=upgradeTimeout,proto3" json:"upgrade_timeout"` +} + +func (m *Params) Reset() { *m = Params{} } +func (m *Params) String() string { return proto.CompactTextString(m) } +func (*Params) ProtoMessage() {} +func (*Params) Descriptor() ([]byte, []int) { + return fileDescriptor_c3a07336710636a0, []int{8} +} +func (m *Params) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *Params) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_Params.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } +} +func (m *Params) XXX_Merge(src proto.Message) { + xxx_messageInfo_Params.Merge(m, src) +} +func (m *Params) XXX_Size() int { + return m.Size() +} +func (m *Params) XXX_DiscardUnknown() { + xxx_messageInfo_Params.DiscardUnknown(m) +} + +var xxx_messageInfo_Params proto.InternalMessageInfo + +func (m *Params) GetUpgradeTimeout() Timeout { + if m != nil { + return m.UpgradeTimeout + } + return Timeout{} +} + func init() { proto.RegisterEnum("ibc.core.channel.v1.State", State_name, State_value) proto.RegisterEnum("ibc.core.channel.v1.Order", Order_name, Order_value) @@ -554,65 +614,72 @@ func init() { proto.RegisterType((*PacketId)(nil), "ibc.core.channel.v1.PacketId") proto.RegisterType((*Acknowledgement)(nil), "ibc.core.channel.v1.Acknowledgement") proto.RegisterType((*Timeout)(nil), "ibc.core.channel.v1.Timeout") + proto.RegisterType((*Params)(nil), "ibc.core.channel.v1.Params") } func init() { proto.RegisterFile("ibc/core/channel/v1/channel.proto", fileDescriptor_c3a07336710636a0) } var fileDescriptor_c3a07336710636a0 = []byte{ - // 842 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xe4, 0x55, 0xcd, 0x8e, 0xdb, 0x54, - 0x14, 0xb6, 0x33, 0xce, 0xdf, 0xc9, 0x64, 0x26, 0x73, 0x0b, 0x83, 0x65, 0x15, 0xc7, 0x1d, 0x81, - 0x08, 0x45, 0x8d, 0x3b, 0x05, 0xa1, 0xc2, 0x6e, 0x26, 0x31, 0xc4, 0x62, 0x94, 0x44, 0x4e, 0x66, - 0x41, 0x37, 0x91, 0x63, 0x5f, 0x12, 0xab, 0x89, 0xaf, 0xb1, 0x6f, 0x52, 0x55, 0xbc, 0x40, 0xc9, - 0x8a, 0x17, 0x88, 0x84, 0xc4, 0x43, 0xf0, 0x0a, 0x95, 0xd8, 0x74, 0xd9, 0x15, 0x42, 0x33, 0x2f, - 0x82, 0x7c, 0xef, 0xf5, 0x24, 0xa9, 0x46, 0x23, 0x84, 0xc4, 0x8a, 0x55, 0xee, 0xf9, 0xce, 0x77, - 0xbe, 0x73, 0xfc, 0x1d, 0xc7, 0x17, 0x1e, 0x04, 0x63, 0xcf, 0xf4, 0x48, 0x8c, 0x4d, 0x6f, 0xea, - 0x86, 0x21, 0x9e, 0x99, 0xcb, 0xd3, 0xec, 0xd8, 0x8c, 0x62, 0x42, 0x09, 0xba, 0x17, 0x8c, 0xbd, - 0x66, 0x4a, 0x69, 0x66, 0xf8, 0xf2, 0x54, 0x7b, 0x6f, 0x42, 0x26, 0x84, 0xe5, 0xcd, 0xf4, 0xc4, - 0xa9, 0x5a, 0x7d, 0xa3, 0x36, 0x0b, 0x70, 0x48, 0x99, 0x18, 0x3b, 0x71, 0xc2, 0xc9, 0xcf, 0x39, - 0x28, 0xb6, 0xb8, 0x0a, 0x7a, 0x0c, 0xf9, 0x84, 0xba, 0x14, 0xab, 0xb2, 0x21, 0x37, 0x0e, 0x9e, - 0x68, 0xcd, 0x5b, 0xfa, 0x34, 0x07, 0x29, 0xc3, 0xe1, 0x44, 0xf4, 0x25, 0x94, 0x48, 0xec, 0xe3, - 0x38, 0x08, 0x27, 0x6a, 0xee, 0x8e, 0xa2, 0x5e, 0x4a, 0x72, 0x6e, 0xb8, 0xe8, 0x3b, 0xd8, 0xf7, - 0xc8, 0x22, 0xa4, 0x38, 0x8e, 0xdc, 0x98, 0xbe, 0x54, 0xf7, 0x0c, 0xb9, 0x51, 0x79, 0xf2, 0xe0, - 0xd6, 0xda, 0xd6, 0x16, 0xf1, 0x5c, 0x79, 0xfd, 0x67, 0x5d, 0x72, 0x76, 0x8a, 0xd1, 0x27, 0x70, - 0xe8, 0x91, 0x30, 0xc4, 0x1e, 0x0d, 0x48, 0x38, 0x9a, 0x92, 0x28, 0x51, 0x15, 0x63, 0xaf, 0x51, - 0x76, 0x0e, 0x36, 0x70, 0x87, 0x44, 0x09, 0x52, 0xa1, 0xb8, 0xc4, 0x71, 0x12, 0x90, 0x50, 0xcd, - 0x1b, 0x72, 0xa3, 0xec, 0x64, 0xe1, 0xd7, 0xca, 0xab, 0x5f, 0xeb, 0xd2, 0xc9, 0x1f, 0x39, 0x38, - 0xb2, 0x7d, 0x1c, 0xd2, 0xe0, 0x87, 0x00, 0xfb, 0xff, 0x7b, 0x57, 0xd0, 0x07, 0x50, 0x8c, 0x48, - 0x4c, 0x47, 0x81, 0xaf, 0x16, 0x58, 0xa6, 0x90, 0x86, 0xb6, 0x8f, 0x3e, 0x04, 0x10, 0xa3, 0xa4, - 0xb9, 0x22, 0xcb, 0x95, 0x05, 0x62, 0xfb, 0xc2, 0xcd, 0x0b, 0xd8, 0xdf, 0x1e, 0x72, 0x5b, 0x4d, - 0xbe, 0x43, 0x2d, 0x77, 0xbb, 0xda, 0xdb, 0x1c, 0x14, 0xfa, 0xae, 0xf7, 0x1c, 0x53, 0xa4, 0x41, - 0x29, 0xc1, 0x3f, 0x2e, 0x70, 0xe8, 0xf1, 0x9d, 0x28, 0xce, 0x4d, 0x8c, 0xea, 0x50, 0x49, 0xc8, - 0x22, 0xf6, 0xf0, 0x28, 0x15, 0x17, 0x62, 0xc0, 0xa1, 0x3e, 0x89, 0x29, 0xfa, 0x18, 0x0e, 0x04, - 0x41, 0x74, 0x60, 0x2e, 0x97, 0x9d, 0x2a, 0x47, 0xb3, 0xa5, 0x7f, 0x0a, 0x35, 0x1f, 0x27, 0x34, - 0x08, 0x5d, 0x66, 0x1f, 0x13, 0x53, 0x18, 0xf1, 0x70, 0x0b, 0x67, 0x8a, 0x26, 0xdc, 0xdb, 0xa6, - 0x66, 0xb2, 0xdc, 0x4b, 0xb4, 0x95, 0xca, 0xb4, 0x11, 0x28, 0xbe, 0x4b, 0x5d, 0xe6, 0xe9, 0xbe, - 0xc3, 0xce, 0xe8, 0x5b, 0x38, 0xa0, 0xc1, 0x1c, 0x93, 0x05, 0x1d, 0x4d, 0x71, 0x30, 0x99, 0x52, - 0xe6, 0x6a, 0x65, 0xe7, 0xc5, 0xe1, 0x7f, 0xdb, 0xe5, 0x69, 0xb3, 0xc3, 0x18, 0x62, 0xeb, 0x55, - 0x51, 0xc7, 0x41, 0xf4, 0x19, 0x1c, 0x65, 0x42, 0xe9, 0x6f, 0x42, 0xdd, 0x79, 0xa4, 0x96, 0x98, - 0x4b, 0x35, 0x91, 0x18, 0x66, 0xb8, 0xb0, 0xf6, 0x27, 0xa8, 0x70, 0x67, 0xd9, 0x4b, 0xfc, 0x6f, - 0xf7, 0xb4, 0xb3, 0x96, 0xbd, 0x77, 0xd6, 0x92, 0x3d, 0xb2, 0xb2, 0x79, 0x64, 0xd1, 0xdc, 0x87, - 0x12, 0x6f, 0x6e, 0xfb, 0xff, 0x45, 0x67, 0xd1, 0xa5, 0x07, 0x87, 0x67, 0xde, 0xf3, 0x90, 0xbc, - 0x98, 0x61, 0x7f, 0x82, 0xe7, 0x38, 0xa4, 0x48, 0x85, 0x42, 0x8c, 0x93, 0xc5, 0x8c, 0xaa, 0xef, - 0xa7, 0x43, 0x75, 0x24, 0x47, 0xc4, 0xe8, 0x18, 0xf2, 0x38, 0x8e, 0x49, 0xac, 0x1e, 0xa7, 0x8d, - 0x3a, 0x92, 0xc3, 0xc3, 0x73, 0x80, 0x52, 0x8c, 0x93, 0x88, 0x84, 0x09, 0x3e, 0x71, 0xa1, 0x38, - 0xe4, 0x6e, 0xa2, 0xa7, 0x50, 0x10, 0x2b, 0x93, 0xff, 0xe1, 0xca, 0x04, 0x1f, 0xdd, 0x87, 0xf2, - 0x66, 0x47, 0x39, 0x36, 0xf8, 0x06, 0x78, 0xf8, 0xbb, 0x0c, 0xf9, 0x81, 0xf8, 0x9e, 0xd4, 0x07, - 0xc3, 0xb3, 0xa1, 0x35, 0xba, 0xec, 0xda, 0x5d, 0x7b, 0x68, 0x9f, 0x5d, 0xd8, 0xcf, 0xac, 0xf6, - 0xe8, 0xb2, 0x3b, 0xe8, 0x5b, 0x2d, 0xfb, 0x1b, 0xdb, 0x6a, 0xd7, 0x24, 0xed, 0x68, 0xb5, 0x36, - 0xaa, 0x3b, 0x04, 0xa4, 0x02, 0xf0, 0xba, 0x14, 0xac, 0xc9, 0x5a, 0x69, 0xb5, 0x36, 0x94, 0xf4, - 0x8c, 0x74, 0xa8, 0xf2, 0xcc, 0xd0, 0xf9, 0xbe, 0xd7, 0xb7, 0xba, 0xb5, 0x9c, 0x56, 0x59, 0xad, - 0x8d, 0xa2, 0x08, 0x37, 0x95, 0x2c, 0xb9, 0xc7, 0x2b, 0x59, 0xe6, 0x3e, 0xec, 0xf3, 0x4c, 0xeb, - 0xa2, 0x37, 0xb0, 0xda, 0x35, 0x45, 0x83, 0xd5, 0xda, 0x28, 0xf0, 0x48, 0x53, 0x5e, 0xfd, 0xa6, - 0x4b, 0x0f, 0x5f, 0x40, 0x9e, 0x7d, 0xda, 0xd0, 0x47, 0x70, 0xdc, 0x73, 0xda, 0x96, 0x33, 0xea, - 0xf6, 0xba, 0xd6, 0x3b, 0xf3, 0x32, 0xc9, 0x14, 0x47, 0x27, 0x70, 0xc8, 0x59, 0x97, 0x5d, 0xf6, - 0x6b, 0xb5, 0x6b, 0xb2, 0x56, 0x5d, 0xad, 0x8d, 0xf2, 0x0d, 0x90, 0x0e, 0xcc, 0x39, 0x19, 0x43, - 0x0c, 0x2c, 0x42, 0xde, 0xf8, 0x7c, 0xf0, 0xfa, 0x4a, 0x97, 0xdf, 0x5c, 0xe9, 0xf2, 0x5f, 0x57, - 0xba, 0xfc, 0xcb, 0xb5, 0x2e, 0xbd, 0xb9, 0xd6, 0xa5, 0xb7, 0xd7, 0xba, 0xf4, 0xec, 0xab, 0x49, - 0x40, 0xa7, 0x8b, 0x71, 0xd3, 0x23, 0x73, 0xd3, 0x23, 0xc9, 0x9c, 0x24, 0x66, 0x30, 0xf6, 0x1e, - 0x4d, 0x88, 0xb9, 0x7c, 0x6a, 0xce, 0x89, 0xbf, 0x98, 0xe1, 0x84, 0xdf, 0x93, 0x8f, 0xbf, 0x78, - 0x94, 0x5d, 0xbc, 0xf4, 0x65, 0x84, 0x93, 0x71, 0x81, 0x5d, 0x94, 0x9f, 0xff, 0x1d, 0x00, 0x00, - 0xff, 0xff, 0x15, 0x20, 0x09, 0x7f, 0x99, 0x07, 0x00, 0x00, + // 937 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xec, 0x56, 0x4f, 0x6f, 0xe2, 0xc6, + 0x1b, 0xc6, 0xc4, 0xfc, 0x7b, 0x93, 0x80, 0x33, 0xf9, 0xfd, 0x52, 0xcb, 0x4a, 0xc1, 0x8b, 0x5a, + 0x95, 0x4d, 0xb5, 0xb0, 0xd9, 0x56, 0xd5, 0xb6, 0xb7, 0x04, 0xbc, 0x8b, 0xb5, 0x14, 0x90, 0x81, + 0x43, 0xf7, 0x82, 0x8c, 0x3d, 0x05, 0x6b, 0xc1, 0x43, 0xed, 0x81, 0xd5, 0xaa, 0xe7, 0x4a, 0x2b, + 0x4e, 0xfd, 0x02, 0x48, 0x95, 0xfa, 0x15, 0xfa, 0x21, 0xf6, 0xb8, 0xc7, 0x3d, 0x55, 0x55, 0xf2, + 0x1d, 0x7a, 0xae, 0x3c, 0x33, 0x0e, 0x10, 0x45, 0x51, 0x55, 0xa9, 0xb7, 0x9e, 0x98, 0xf7, 0x79, + 0x9f, 0xf7, 0x7d, 0xde, 0x3f, 0xc3, 0xc8, 0xf0, 0xc0, 0x1b, 0x39, 0x35, 0x87, 0x04, 0xb8, 0xe6, + 0x4c, 0x6c, 0xdf, 0xc7, 0xd3, 0xda, 0xf2, 0x3c, 0x3e, 0x56, 0xe7, 0x01, 0xa1, 0x04, 0x1d, 0x7b, + 0x23, 0xa7, 0x1a, 0x51, 0xaa, 0x31, 0xbe, 0x3c, 0xd7, 0xfe, 0x37, 0x26, 0x63, 0xc2, 0xfc, 0xb5, + 0xe8, 0xc4, 0xa9, 0x5a, 0x69, 0x93, 0x6d, 0xea, 0x61, 0x9f, 0xb2, 0x64, 0xec, 0xc4, 0x09, 0xe5, + 0xdf, 0x92, 0x90, 0xa9, 0xf3, 0x2c, 0xe8, 0x31, 0xa4, 0x42, 0x6a, 0x53, 0xac, 0x4a, 0xba, 0x54, + 0xc9, 0x3f, 0xd1, 0xaa, 0x77, 0xe8, 0x54, 0x7b, 0x11, 0xc3, 0xe2, 0x44, 0xf4, 0x15, 0x64, 0x49, + 0xe0, 0xe2, 0xc0, 0xf3, 0xc7, 0x6a, 0xf2, 0x9e, 0xa0, 0x4e, 0x44, 0xb2, 0x6e, 0xb8, 0xe8, 0x05, + 0x1c, 0x38, 0x64, 0xe1, 0x53, 0x1c, 0xcc, 0xed, 0x80, 0xbe, 0x51, 0xf7, 0x74, 0xa9, 0xb2, 0xff, + 0xe4, 0xc1, 0x9d, 0xb1, 0xf5, 0x2d, 0xe2, 0xa5, 0xfc, 0xee, 0xf7, 0x52, 0xc2, 0xda, 0x09, 0x46, + 0x9f, 0x41, 0xc1, 0x21, 0xbe, 0x8f, 0x1d, 0xea, 0x11, 0x7f, 0x38, 0x21, 0xf3, 0x50, 0x95, 0xf5, + 0xbd, 0x4a, 0xce, 0xca, 0x6f, 0xe0, 0x26, 0x99, 0x87, 0x48, 0x85, 0xcc, 0x12, 0x07, 0xa1, 0x47, + 0x7c, 0x35, 0xa5, 0x4b, 0x95, 0x9c, 0x15, 0x9b, 0xe8, 0x21, 0x28, 0x8b, 0xf9, 0x38, 0xb0, 0x5d, + 0x3c, 0x0c, 0xf1, 0x0f, 0x0b, 0xec, 0x3b, 0x58, 0x4d, 0xeb, 0x52, 0x45, 0xb6, 0x0a, 0x02, 0xef, + 0x09, 0xf8, 0x1b, 0xf9, 0xed, 0x2f, 0xa5, 0x44, 0xf9, 0xcf, 0x24, 0x1c, 0x99, 0x2e, 0xf6, 0xa9, + 0xf7, 0xbd, 0x87, 0xdd, 0xff, 0x06, 0xf8, 0x11, 0x64, 0xe6, 0x24, 0xa0, 0x43, 0xcf, 0x65, 0x73, + 0xcb, 0x59, 0xe9, 0xc8, 0x34, 0x5d, 0xf4, 0x31, 0x80, 0x28, 0x25, 0xf2, 0x65, 0x98, 0x2f, 0x27, + 0x10, 0xd3, 0xbd, 0x73, 0xf0, 0xd9, 0xfb, 0x06, 0xdf, 0x82, 0x83, 0xed, 0x7e, 0xb6, 0x85, 0xa5, + 0x7b, 0x84, 0x93, 0xb7, 0x84, 0x45, 0xb6, 0x0f, 0x49, 0x48, 0x77, 0x6d, 0xe7, 0x15, 0xa6, 0x48, + 0x83, 0xec, 0x4d, 0x05, 0x12, 0xab, 0xe0, 0xc6, 0x46, 0x25, 0xd8, 0x0f, 0xc9, 0x22, 0x70, 0xf0, + 0x30, 0x4a, 0x2e, 0x92, 0x01, 0x87, 0xba, 0x24, 0xa0, 0xe8, 0x53, 0xc8, 0x0b, 0x82, 0x50, 0x60, + 0x0b, 0xc9, 0x59, 0x87, 0x1c, 0x8d, 0xef, 0xc7, 0x43, 0x50, 0x5c, 0x1c, 0x52, 0xcf, 0xb7, 0xd9, + 0xa4, 0x59, 0x32, 0x99, 0x11, 0x0b, 0x5b, 0x38, 0xcb, 0x58, 0x83, 0xe3, 0x6d, 0x6a, 0x9c, 0x96, + 0x8f, 0x1d, 0x6d, 0xb9, 0xe2, 0xdc, 0x08, 0x64, 0xd7, 0xa6, 0x36, 0x1b, 0xff, 0x81, 0xc5, 0xce, + 0xe8, 0x39, 0xe4, 0xa9, 0x37, 0xc3, 0x64, 0x41, 0x87, 0x13, 0xec, 0x8d, 0x27, 0x94, 0x2d, 0x60, + 0x7f, 0xe7, 0x8e, 0xf1, 0xc7, 0x60, 0x79, 0x5e, 0x6d, 0x32, 0x86, 0xb8, 0x20, 0x87, 0x22, 0x8e, + 0x83, 0xe8, 0x73, 0x38, 0x8a, 0x13, 0x45, 0xbf, 0x21, 0xb5, 0x67, 0x73, 0xb1, 0x27, 0x45, 0x38, + 0xfa, 0x31, 0x2e, 0x46, 0xfb, 0x23, 0xec, 0xf3, 0xc9, 0xb2, 0xfb, 0xfe, 0x4f, 0xf7, 0xb4, 0xb3, + 0x96, 0xbd, 0x5b, 0x6b, 0x89, 0x5b, 0x96, 0x37, 0x2d, 0x0b, 0x71, 0x17, 0xb2, 0x5c, 0xdc, 0x74, + 0xff, 0x0d, 0x65, 0xa1, 0xd2, 0x81, 0xc2, 0x85, 0xf3, 0xca, 0x27, 0xaf, 0xa7, 0xd8, 0x1d, 0xe3, + 0x19, 0xf6, 0x29, 0x52, 0x21, 0x1d, 0xe0, 0x70, 0x31, 0xa5, 0xea, 0xff, 0xa3, 0xa2, 0x9a, 0x09, + 0x4b, 0xd8, 0xe8, 0x04, 0x52, 0x38, 0x08, 0x48, 0xa0, 0x9e, 0x44, 0x42, 0xcd, 0x84, 0xc5, 0xcd, + 0x4b, 0x80, 0x6c, 0x80, 0xc3, 0x39, 0xf1, 0x43, 0x5c, 0xb6, 0x21, 0xd3, 0xe7, 0xd3, 0x44, 0x4f, + 0x21, 0x2d, 0x56, 0x26, 0xfd, 0xcd, 0x95, 0x09, 0x3e, 0x3a, 0x85, 0xdc, 0x66, 0x47, 0x49, 0x56, + 0xf8, 0x06, 0x28, 0x0f, 0xa2, 0x0b, 0x1f, 0xd8, 0xb3, 0x10, 0xbd, 0x80, 0xf8, 0x2f, 0x36, 0x14, + 0x2b, 0x14, 0x52, 0xa7, 0x77, 0xbe, 0x22, 0xa2, 0x30, 0x21, 0x96, 0x17, 0xa1, 0x02, 0x3d, 0xfb, + 0x29, 0x09, 0xa9, 0x9e, 0x78, 0xd1, 0x4a, 0xbd, 0xfe, 0x45, 0xdf, 0x18, 0x0e, 0xda, 0x66, 0xdb, + 0xec, 0x9b, 0x17, 0x2d, 0xf3, 0xa5, 0xd1, 0x18, 0x0e, 0xda, 0xbd, 0xae, 0x51, 0x37, 0x9f, 0x99, + 0x46, 0x43, 0x49, 0x68, 0x47, 0xab, 0xb5, 0x7e, 0xb8, 0x43, 0x40, 0x2a, 0x00, 0x8f, 0x8b, 0x40, + 0x45, 0xd2, 0xb2, 0xab, 0xb5, 0x2e, 0x47, 0x67, 0x54, 0x84, 0x43, 0xee, 0xe9, 0x5b, 0xdf, 0x75, + 0xba, 0x46, 0x5b, 0x49, 0x6a, 0xfb, 0xab, 0xb5, 0x9e, 0x11, 0xe6, 0x26, 0x92, 0x39, 0xf7, 0x78, + 0x24, 0xf3, 0x9c, 0xc2, 0x01, 0xf7, 0xd4, 0x5b, 0x9d, 0x9e, 0xd1, 0x50, 0x64, 0x0d, 0x56, 0x6b, + 0x3d, 0xcd, 0x2d, 0xa4, 0x43, 0x9e, 0x7b, 0x9f, 0xb5, 0x06, 0xbd, 0xa6, 0xd9, 0x7e, 0xae, 0xa4, + 0xb4, 0x83, 0xd5, 0x5a, 0xcf, 0xc6, 0x36, 0x3a, 0x83, 0xe3, 0x2d, 0x46, 0xbd, 0xf3, 0x6d, 0xb7, + 0x65, 0xf4, 0x0d, 0x25, 0xcd, 0xeb, 0xdf, 0x01, 0x35, 0xf9, 0xed, 0xaf, 0xc5, 0xc4, 0xd9, 0x6b, + 0x48, 0xb1, 0xa7, 0x1a, 0x7d, 0x02, 0x27, 0x1d, 0xab, 0x61, 0x58, 0xc3, 0x76, 0xa7, 0x6d, 0xdc, + 0xea, 0x9e, 0x15, 0x18, 0xe1, 0xa8, 0x0c, 0x05, 0xce, 0x1a, 0xb4, 0xd9, 0xaf, 0xd1, 0x50, 0x24, + 0xed, 0x70, 0xb5, 0xd6, 0x73, 0x37, 0x40, 0xd4, 0x3e, 0xe7, 0xc4, 0x0c, 0xd1, 0xbe, 0x30, 0xb9, + 0xf0, 0x65, 0xef, 0xdd, 0x55, 0x51, 0x7a, 0x7f, 0x55, 0x94, 0xfe, 0xb8, 0x2a, 0x4a, 0x3f, 0x5f, + 0x17, 0x13, 0xef, 0xaf, 0x8b, 0x89, 0x0f, 0xd7, 0xc5, 0xc4, 0xcb, 0xaf, 0xc7, 0x1e, 0x9d, 0x2c, + 0x46, 0x55, 0x87, 0xcc, 0x6a, 0x0e, 0x09, 0x67, 0x24, 0xac, 0x79, 0x23, 0xe7, 0xd1, 0x98, 0xd4, + 0x96, 0x4f, 0x6b, 0x33, 0xe2, 0x2e, 0xa6, 0x38, 0xe4, 0x9f, 0x08, 0x8f, 0xbf, 0x7c, 0x14, 0x7f, + 0x73, 0xd0, 0x37, 0x73, 0x1c, 0x8e, 0xd2, 0xec, 0x1b, 0xe1, 0x8b, 0xbf, 0x02, 0x00, 0x00, 0xff, + 0xff, 0x90, 0xd1, 0xb4, 0xca, 0x94, 0x08, 0x00, 0x00, } func (m *Channel) Marshal() (dAtA []byte, err error) { @@ -635,6 +702,11 @@ func (m *Channel) MarshalToSizedBuffer(dAtA []byte) (int, error) { _ = i var l int _ = l + if m.UpgradeSequence != 0 { + i = encodeVarintChannel(dAtA, i, uint64(m.UpgradeSequence)) + i-- + dAtA[i] = 0x30 + } if len(m.Version) > 0 { i -= len(m.Version) copy(dAtA[i:], m.Version) @@ -694,6 +766,11 @@ func (m *IdentifiedChannel) MarshalToSizedBuffer(dAtA []byte) (int, error) { _ = i var l int _ = l + if m.UpgradeSequence != 0 { + i = encodeVarintChannel(dAtA, i, uint64(m.UpgradeSequence)) + i-- + dAtA[i] = 0x40 + } if len(m.ChannelId) > 0 { i -= len(m.ChannelId) copy(dAtA[i:], m.ChannelId) @@ -1057,6 +1134,39 @@ func (m *Timeout) MarshalToSizedBuffer(dAtA []byte) (int, error) { return len(dAtA) - i, nil } +func (m *Params) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *Params) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *Params) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + { + size, err := m.UpgradeTimeout.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintChannel(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil +} + func encodeVarintChannel(dAtA []byte, offset int, v uint64) int { offset -= sovChannel(v) base := offset @@ -1092,6 +1202,9 @@ func (m *Channel) Size() (n int) { if l > 0 { n += 1 + l + sovChannel(uint64(l)) } + if m.UpgradeSequence != 0 { + n += 1 + sovChannel(uint64(m.UpgradeSequence)) + } return n } @@ -1127,6 +1240,9 @@ func (m *IdentifiedChannel) Size() (n int) { if l > 0 { n += 1 + l + sovChannel(uint64(l)) } + if m.UpgradeSequence != 0 { + n += 1 + sovChannel(uint64(m.UpgradeSequence)) + } return n } @@ -1276,6 +1392,17 @@ func (m *Timeout) Size() (n int) { return n } +func (m *Params) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = m.UpgradeTimeout.Size() + n += 1 + l + sovChannel(uint64(l)) + return n +} + func sovChannel(x uint64) (n int) { return (math_bits.Len64(x|1) + 6) / 7 } @@ -1446,6 +1573,25 @@ func (m *Channel) Unmarshal(dAtA []byte) error { } m.Version = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex + case 6: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field UpgradeSequence", wireType) + } + m.UpgradeSequence = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowChannel + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.UpgradeSequence |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } default: iNdEx = preIndex skippy, err := skipChannel(dAtA[iNdEx:]) @@ -1695,6 +1841,25 @@ func (m *IdentifiedChannel) Unmarshal(dAtA []byte) error { } m.ChannelId = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex + case 8: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field UpgradeSequence", wireType) + } + m.UpgradeSequence = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowChannel + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.UpgradeSequence |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } default: iNdEx = preIndex skippy, err := skipChannel(dAtA[iNdEx:]) @@ -2630,6 +2795,89 @@ func (m *Timeout) Unmarshal(dAtA []byte) error { } return nil } +func (m *Params) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowChannel + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: Params: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: Params: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field UpgradeTimeout", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowChannel + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthChannel + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthChannel + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.UpgradeTimeout.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipChannel(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthChannel + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} func skipChannel(dAtA []byte) (n int, err error) { l := len(dAtA) iNdEx := 0 diff --git a/modules/core/04-channel/types/channel_test.go b/modules/core/04-channel/types/channel_test.go index d35ec13a519..211be035fe8 100644 --- a/modules/core/04-channel/types/channel_test.go +++ b/modules/core/04-channel/types/channel_test.go @@ -6,6 +6,7 @@ import ( "github.com/stretchr/testify/require" "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" + host "github.com/cosmos/ibc-go/v8/modules/core/24-host" ) func TestChannelValidateBasic(t *testing.T) { @@ -57,3 +58,37 @@ func TestCounterpartyValidateBasic(t *testing.T) { } } } + +// TestIdentifiedChannelValidateBasic tests ValidateBasic for IdentifiedChannel. +func TestIdentifiedChannelValidateBasic(t *testing.T) { + channel := types.NewChannel(types.TRYOPEN, types.ORDERED, types.Counterparty{"portidone", "channelidone"}, connHops, version) + + testCases := []struct { + name string + identifiedChannel types.IdentifiedChannel + expErr error + }{ + { + "valid identified channel", + types.NewIdentifiedChannel("portidone", "channelidone", channel), + nil, + }, + { + "invalid portID", + types.NewIdentifiedChannel("(InvalidPort)", "channelidone", channel), + host.ErrInvalidID, + }, + { + "invalid channelID", + types.NewIdentifiedChannel("portidone", "(InvalidChannel)", channel), + host.ErrInvalidID, + }, + } + + for _, tc := range testCases { + tc := tc + + err := tc.identifiedChannel.ValidateBasic() + require.ErrorIs(t, err, tc.expErr) + } +} diff --git a/modules/core/04-channel/types/codec.go b/modules/core/04-channel/types/codec.go index 86f2f495d19..153f36cbf49 100644 --- a/modules/core/04-channel/types/codec.go +++ b/modules/core/04-channel/types/codec.go @@ -39,6 +39,14 @@ func RegisterInterfaces(registry codectypes.InterfaceRegistry) { &MsgAcknowledgement{}, &MsgTimeout{}, &MsgTimeoutOnClose{}, + &MsgChannelUpgradeInit{}, + &MsgChannelUpgradeTry{}, + &MsgChannelUpgradeAck{}, + &MsgChannelUpgradeConfirm{}, + &MsgChannelUpgradeOpen{}, + &MsgChannelUpgradeTimeout{}, + &MsgChannelUpgradeCancel{}, + &MsgUpdateParams{}, ) msgservice.RegisterMsgServiceDesc(registry, &_Msg_serviceDesc) diff --git a/modules/core/04-channel/types/errors.go b/modules/core/04-channel/types/errors.go index dfbbf30a1cb..703832a9330 100644 --- a/modules/core/04-channel/types/errors.go +++ b/modules/core/04-channel/types/errors.go @@ -37,7 +37,23 @@ var ( // Perform a no-op on the current Msg ErrNoOpMsg = errorsmod.Register(SubModuleName, 23, "message is redundant, no-op will be performed") - ErrInvalidChannelVersion = errorsmod.Register(SubModuleName, 24, "invalid channel version") - ErrPacketNotSent = errorsmod.Register(SubModuleName, 25, "packet has not been sent") - ErrInvalidTimeout = errorsmod.Register(SubModuleName, 26, "invalid packet timeout") + ErrInvalidChannelVersion = errorsmod.Register(SubModuleName, 24, "invalid channel version") + ErrPacketNotSent = errorsmod.Register(SubModuleName, 25, "packet has not been sent") + ErrInvalidTimeout = errorsmod.Register(SubModuleName, 26, "invalid packet timeout") + ErrUpgradeErrorNotFound = errorsmod.Register(SubModuleName, 27, "upgrade error receipt not found") + ErrInvalidUpgrade = errorsmod.Register(SubModuleName, 28, "invalid upgrade") + ErrInvalidUpgradeSequence = errorsmod.Register(SubModuleName, 29, "invalid upgrade sequence") + ErrUpgradeNotFound = errorsmod.Register(SubModuleName, 30, "upgrade not found") + ErrIncompatibleCounterpartyUpgrade = errorsmod.Register(SubModuleName, 31, "incompatible counterparty upgrade") + ErrInvalidUpgradeError = errorsmod.Register(SubModuleName, 32, "invalid upgrade error") + ErrUpgradeRestoreFailed = errorsmod.Register(SubModuleName, 33, "restore failed") + ErrUpgradeTimeout = errorsmod.Register(SubModuleName, 34, "upgrade timed-out") + ErrInvalidUpgradeTimeout = errorsmod.Register(SubModuleName, 35, "upgrade timeout is invalid") + ErrPendingInflightPackets = errorsmod.Register(SubModuleName, 36, "pending inflight packets exist") + ErrUpgradeTimeoutFailed = errorsmod.Register(SubModuleName, 37, "upgrade timeout failed") + ErrInvalidPruningLimit = errorsmod.Register(SubModuleName, 38, "invalid pruning limit") + ErrTimeoutNotReached = errorsmod.Register(SubModuleName, 39, "timeout not reached") + ErrTimeoutElapsed = errorsmod.Register(SubModuleName, 40, "timeout elapsed") + ErrPruningSequenceStartNotFound = errorsmod.Register(SubModuleName, 41, "pruning sequence start not found") + ErrPruningSequenceEndNotFound = errorsmod.Register(SubModuleName, 42, "pruning sequence end not found") ) diff --git a/modules/core/04-channel/types/events.go b/modules/core/04-channel/types/events.go index 3d4738626e2..414a02208e5 100644 --- a/modules/core/04-channel/types/events.go +++ b/modules/core/04-channel/types/events.go @@ -11,6 +11,7 @@ const ( AttributeKeyConnectionID = "connection_id" AttributeKeyPortID = "port_id" AttributeKeyChannelID = "channel_id" + AttributeKeyChannelState = "channel_state" AttributeVersion = "version" AttributeCounterpartyPortID = "counterparty_port_id" AttributeCounterpartyChannelID = "counterparty_channel_id" @@ -37,17 +38,34 @@ const ( AttributeKeyDstChannel = "packet_dst_channel" AttributeKeyChannelOrdering = "packet_channel_ordering" AttributeKeyConnection = "packet_connection" + + // upgrade specific keys + AttributeKeyUpgradeSequence = "upgrade_sequence" + AttributeKeyUpgradeVersion = "upgrade_version" + AttributeKeyUpgradeConnectionHops = "upgrade_connection_hops" + AttributeKeyUpgradeOrdering = "upgrade_ordering" + AttributeKeyUpgradeErrorReceipt = "upgrade_error_receipt" + AttributeKeyUpgradeTimeout = "upgrade_timeout" ) // IBC channel events vars var ( - EventTypeChannelOpenInit = "channel_open_init" - EventTypeChannelOpenTry = "channel_open_try" - EventTypeChannelOpenAck = "channel_open_ack" - EventTypeChannelOpenConfirm = "channel_open_confirm" - EventTypeChannelCloseInit = "channel_close_init" - EventTypeChannelCloseConfirm = "channel_close_confirm" - EventTypeChannelClosed = "channel_close" + EventTypeChannelOpenInit = "channel_open_init" + EventTypeChannelOpenTry = "channel_open_try" + EventTypeChannelOpenAck = "channel_open_ack" + EventTypeChannelOpenConfirm = "channel_open_confirm" + EventTypeChannelCloseInit = "channel_close_init" + EventTypeChannelCloseConfirm = "channel_close_confirm" + EventTypeChannelClosed = "channel_close" + EventTypeChannelUpgradeInit = "channel_upgrade_init" + EventTypeChannelUpgradeTry = "channel_upgrade_try" + EventTypeChannelUpgradeAck = "channel_upgrade_ack" + EventTypeChannelUpgradeConfirm = "channel_upgrade_confirm" + EventTypeChannelUpgradeOpen = "channel_upgrade_open" + EventTypeChannelUpgradeTimeout = "channel_upgrade_timeout" + EventTypeChannelUpgradeCancel = "channel_upgrade_cancelled" + EventTypeChannelUpgradeError = "channel_upgrade_error" + EventTypeChannelFlushComplete = "channel_flush_complete" AttributeValueCategory = fmt.Sprintf("%s_%s", ibcexported.ModuleName, SubModuleName) ) diff --git a/modules/core/04-channel/types/expected_keepers.go b/modules/core/04-channel/types/expected_keepers.go index b1e3aae98d3..9b3b4b2e2de 100644 --- a/modules/core/04-channel/types/expected_keepers.go +++ b/modules/core/04-channel/types/expected_keepers.go @@ -73,6 +73,32 @@ type ConnectionKeeper interface { channelID string, nextSequenceRecv uint64, ) error + VerifyChannelUpgrade( + ctx sdk.Context, + connection exported.ConnectionI, + height exported.Height, + proof []byte, + portID, + channelID string, + upgrade Upgrade, + ) error + VerifyChannelUpgradeError( + ctx sdk.Context, + connection exported.ConnectionI, + proofHeight exported.Height, + proofErrorReceipt []byte, + portID, + channelID string, + errorReceipt ErrorReceipt, + ) error + VerifyChannelUpgradeErrorAbsence( + ctx sdk.Context, + connection exported.ConnectionI, + proofHeight exported.Height, + proofErrorReceiptAbsence []byte, + portID, + channelID string, + ) error } // PortKeeper expected account IBC port keeper diff --git a/modules/core/04-channel/types/genesis.go b/modules/core/04-channel/types/genesis.go index 6e9afa0cbae..65a35bc43ae 100644 --- a/modules/core/04-channel/types/genesis.go +++ b/modules/core/04-channel/types/genesis.go @@ -45,6 +45,7 @@ func (ps PacketSequence) Validate() error { func NewGenesisState( channels []IdentifiedChannel, acks, receipts, commitments []PacketState, sendSeqs, recvSeqs, ackSeqs []PacketSequence, nextChannelSequence uint64, + params Params, ) GenesisState { return GenesisState{ Channels: channels, @@ -54,6 +55,7 @@ func NewGenesisState( RecvSequences: recvSeqs, AckSequences: ackSeqs, NextChannelSequence: nextChannelSequence, + Params: params, } } @@ -68,6 +70,7 @@ func DefaultGenesisState() GenesisState { RecvSequences: []PacketSequence{}, AckSequences: []PacketSequence{}, NextChannelSequence: 0, + Params: DefaultParams(), } } diff --git a/modules/core/04-channel/types/genesis.pb.go b/modules/core/04-channel/types/genesis.pb.go index 0ed3da2e528..bd8723eb637 100644 --- a/modules/core/04-channel/types/genesis.pb.go +++ b/modules/core/04-channel/types/genesis.pb.go @@ -34,6 +34,7 @@ type GenesisState struct { AckSequences []PacketSequence `protobuf:"bytes,7,rep,name=ack_sequences,json=ackSequences,proto3" json:"ack_sequences"` // the sequence for the next generated channel identifier NextChannelSequence uint64 `protobuf:"varint,8,opt,name=next_channel_sequence,json=nextChannelSequence,proto3" json:"next_channel_sequence,omitempty"` + Params Params `protobuf:"bytes,9,opt,name=params,proto3" json:"params"` } func (m *GenesisState) Reset() { *m = GenesisState{} } @@ -125,6 +126,13 @@ func (m *GenesisState) GetNextChannelSequence() uint64 { return 0 } +func (m *GenesisState) GetParams() Params { + if m != nil { + return m.Params + } + return Params{} +} + // PacketSequence defines the genesis type necessary to retrieve and store // next send and receive sequences. type PacketSequence struct { @@ -195,35 +203,37 @@ func init() { func init() { proto.RegisterFile("ibc/core/channel/v1/genesis.proto", fileDescriptor_cb06ec201f452595) } var fileDescriptor_cb06ec201f452595 = []byte{ - // 446 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x94, 0xd3, 0x4d, 0x6f, 0xd3, 0x30, - 0x18, 0x07, 0xf0, 0x66, 0x2d, 0x5d, 0xe7, 0xbd, 0x08, 0x3c, 0x10, 0xa1, 0x12, 0x59, 0x19, 0x12, - 0xea, 0x65, 0x31, 0x1b, 0x1c, 0xe0, 0x1a, 0x0e, 0xd0, 0x0b, 0x9a, 0xb2, 0x1b, 0x12, 0xaa, 0x12, - 0xfb, 0x21, 0xb3, 0xd2, 0xd8, 0x21, 0x76, 0x03, 0x7c, 0x0b, 0x3e, 0xd6, 0x8e, 0x3b, 0x72, 0x9a, - 0x50, 0xfb, 0x21, 0x90, 0x38, 0xa1, 0x38, 0x2f, 0x2b, 0x6a, 0x35, 0x29, 0xb7, 0xda, 0xcf, 0xf3, - 0xff, 0xfd, 0x7b, 0x88, 0xd1, 0x33, 0x1e, 0x52, 0x42, 0x65, 0x06, 0x84, 0x5e, 0x06, 0x42, 0xc0, - 0x8c, 0xe4, 0xa7, 0x24, 0x02, 0x01, 0x8a, 0x2b, 0x37, 0xcd, 0xa4, 0x96, 0xf8, 0x90, 0x87, 0xd4, - 0x2d, 0x56, 0xdc, 0x6a, 0xc5, 0xcd, 0x4f, 0x87, 0x0f, 0x23, 0x19, 0x49, 0x33, 0x27, 0xc5, 0xaf, - 0x72, 0x75, 0xb8, 0x51, 0xab, 0x53, 0x66, 0xe5, 0xf8, 0x4f, 0x0f, 0xed, 0xbd, 0x2f, 0xfd, 0x0b, - 0x1d, 0x68, 0xc0, 0x9f, 0xd1, 0xa0, 0xda, 0x50, 0xb6, 0x35, 0xea, 0x8e, 0x77, 0xcf, 0x5e, 0xb8, - 0x1b, 0x1a, 0xdd, 0x09, 0x03, 0xa1, 0xf9, 0x17, 0x0e, 0xec, 0x5d, 0x79, 0xe9, 0x3d, 0xb9, 0xba, - 0x39, 0xea, 0xfc, 0xbd, 0x39, 0x7a, 0xb0, 0x36, 0xf2, 0x1b, 0x12, 0xfb, 0xe8, 0x7e, 0x40, 0x63, - 0x21, 0xbf, 0xcd, 0x80, 0x45, 0x90, 0x80, 0xd0, 0xca, 0xde, 0x32, 0x35, 0xa3, 0x8d, 0x35, 0xe7, - 0x01, 0x8d, 0x41, 0x9b, 0xbf, 0xe6, 0xf5, 0x8a, 0x02, 0x7f, 0x2d, 0x8f, 0x3f, 0xa0, 0x5d, 0x2a, - 0x93, 0x84, 0xeb, 0x92, 0xeb, 0xb6, 0xe2, 0x56, 0xa3, 0xd8, 0x43, 0x83, 0x0c, 0x28, 0xf0, 0x54, - 0x2b, 0xbb, 0xd7, 0x8a, 0x69, 0x72, 0xf8, 0x1c, 0x1d, 0x28, 0x10, 0x6c, 0xaa, 0xe0, 0xeb, 0x1c, - 0x04, 0x05, 0x65, 0xdf, 0x33, 0xd2, 0xf3, 0xbb, 0xa4, 0x6a, 0xb7, 0xc2, 0xf6, 0x0b, 0xa0, 0xbe, - 0x33, 0x62, 0x06, 0x34, 0x5f, 0x11, 0xfb, 0xad, 0xc5, 0x02, 0xb8, 0x15, 0x3f, 0xa2, 0xfd, 0x80, - 0xc6, 0x2b, 0xe0, 0x76, 0x5b, 0x70, 0x2f, 0xa0, 0xf1, 0xad, 0x77, 0x86, 0x1e, 0x09, 0xf8, 0xae, - 0xa7, 0x55, 0xaa, 0x81, 0xed, 0xc1, 0xc8, 0x1a, 0xf7, 0xfc, 0xc3, 0x62, 0x58, 0x7d, 0x0b, 0x75, - 0xe8, 0x98, 0xa1, 0x83, 0xff, 0x65, 0xfc, 0x18, 0x6d, 0xa7, 0x32, 0xd3, 0x53, 0xce, 0x6c, 0x6b, - 0x64, 0x8d, 0x77, 0xfc, 0x7e, 0x71, 0x9c, 0x30, 0xfc, 0x14, 0xa1, 0x5a, 0xe6, 0xcc, 0xde, 0x32, - 0xb3, 0x9d, 0xea, 0x66, 0xc2, 0xf0, 0x10, 0x0d, 0x9a, 0xc2, 0xae, 0x29, 0x6c, 0xce, 0xde, 0xc5, - 0xd5, 0xc2, 0xb1, 0xae, 0x17, 0x8e, 0xf5, 0x7b, 0xe1, 0x58, 0x3f, 0x97, 0x4e, 0xe7, 0x7a, 0xe9, - 0x74, 0x7e, 0x2d, 0x9d, 0xce, 0xa7, 0xb7, 0x11, 0xd7, 0x97, 0xf3, 0xd0, 0xa5, 0x32, 0x21, 0x54, - 0xaa, 0x44, 0x2a, 0xc2, 0x43, 0x7a, 0x12, 0x49, 0x92, 0xbf, 0x21, 0x89, 0x64, 0xf3, 0x19, 0xa8, - 0xf2, 0xf1, 0xbc, 0x7c, 0x7d, 0x52, 0xbf, 0x1f, 0xfd, 0x23, 0x05, 0x15, 0xf6, 0xcd, 0xdb, 0x79, - 0xf5, 0x2f, 0x00, 0x00, 0xff, 0xff, 0xce, 0x58, 0xd9, 0xe7, 0xae, 0x03, 0x00, 0x00, + // 471 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x94, 0x93, 0x41, 0x6f, 0xd3, 0x30, + 0x18, 0x86, 0x9b, 0xb5, 0xeb, 0x5a, 0x77, 0x9b, 0xc0, 0x03, 0x11, 0x8a, 0xc8, 0xca, 0x90, 0x50, + 0x2f, 0x8b, 0x59, 0xe1, 0xc0, 0xae, 0xe5, 0x00, 0xbd, 0xa0, 0x29, 0xbb, 0x21, 0xa1, 0x2a, 0xb1, + 0x3f, 0x32, 0xab, 0x8d, 0x1d, 0x62, 0xb7, 0xc0, 0xbf, 0xe0, 0xb7, 0xf0, 0x2b, 0x76, 0xdc, 0x91, + 0xd3, 0x84, 0xda, 0x7f, 0xc1, 0x09, 0xc5, 0x71, 0xb2, 0xa2, 0x95, 0x49, 0xbd, 0xc5, 0xdf, 0xf7, + 0xbe, 0xcf, 0xfb, 0x1e, 0xf2, 0xa1, 0x67, 0x3c, 0xa2, 0x84, 0xca, 0x0c, 0x08, 0xbd, 0x08, 0x85, + 0x80, 0x29, 0x99, 0x9f, 0x90, 0x18, 0x04, 0x28, 0xae, 0xfc, 0x34, 0x93, 0x5a, 0xe2, 0x03, 0x1e, + 0x51, 0x3f, 0x97, 0xf8, 0x56, 0xe2, 0xcf, 0x4f, 0xba, 0x0f, 0x62, 0x19, 0x4b, 0xb3, 0x27, 0xf9, + 0x57, 0x21, 0xed, 0xae, 0xa5, 0x95, 0x2e, 0x23, 0x39, 0xfa, 0xb9, 0x8d, 0x76, 0xdf, 0x15, 0xfc, + 0x73, 0x1d, 0x6a, 0xc0, 0x9f, 0x50, 0xcb, 0x2a, 0x94, 0xeb, 0xf4, 0xea, 0xfd, 0xce, 0xe0, 0x85, + 0xbf, 0x26, 0xd1, 0x1f, 0x31, 0x10, 0x9a, 0x7f, 0xe6, 0xc0, 0xde, 0x16, 0xc3, 0xe1, 0xe3, 0xcb, + 0xeb, 0xc3, 0xda, 0x9f, 0xeb, 0xc3, 0xfb, 0xb7, 0x56, 0x41, 0x85, 0xc4, 0x01, 0xba, 0x17, 0xd2, + 0x89, 0x90, 0x5f, 0xa7, 0xc0, 0x62, 0x48, 0x40, 0x68, 0xe5, 0x6e, 0x99, 0x98, 0xde, 0xda, 0x98, + 0xb3, 0x90, 0x4e, 0x40, 0x9b, 0x6a, 0xc3, 0x46, 0x1e, 0x10, 0xdc, 0xf2, 0xe3, 0xf7, 0xa8, 0x43, + 0x65, 0x92, 0x70, 0x5d, 0xe0, 0xea, 0x1b, 0xe1, 0x56, 0xad, 0x78, 0x88, 0x5a, 0x19, 0x50, 0xe0, + 0xa9, 0x56, 0x6e, 0x63, 0x23, 0x4c, 0xe5, 0xc3, 0x67, 0x68, 0x5f, 0x81, 0x60, 0x63, 0x05, 0x5f, + 0x66, 0x20, 0x28, 0x28, 0x77, 0xdb, 0x90, 0x9e, 0xdf, 0x45, 0xb2, 0x5a, 0x0b, 0xdb, 0xcb, 0x01, + 0xe5, 0xcc, 0x10, 0x33, 0xa0, 0xf3, 0x15, 0x62, 0x73, 0x63, 0x62, 0x0e, 0xb8, 0x21, 0x7e, 0x40, + 0x7b, 0x21, 0x9d, 0xac, 0x00, 0x77, 0x36, 0x05, 0xee, 0x86, 0x74, 0x72, 0xc3, 0x1b, 0xa0, 0x87, + 0x02, 0xbe, 0xe9, 0xb1, 0x75, 0x55, 0x60, 0xb7, 0xd5, 0x73, 0xfa, 0x8d, 0xe0, 0x20, 0x5f, 0xda, + 0x7f, 0xa1, 0x34, 0xe1, 0x53, 0xd4, 0x4c, 0xc3, 0x2c, 0x4c, 0x94, 0xdb, 0xee, 0x39, 0xfd, 0xce, + 0xe0, 0xc9, 0x7f, 0xc2, 0x73, 0x89, 0x0d, 0xb5, 0x86, 0x23, 0x86, 0xf6, 0xff, 0x2d, 0x85, 0x1f, + 0xa1, 0x9d, 0x54, 0x66, 0x7a, 0xcc, 0x99, 0xeb, 0xf4, 0x9c, 0x7e, 0x3b, 0x68, 0xe6, 0xcf, 0x11, + 0xc3, 0x4f, 0x11, 0x2a, 0x4b, 0x71, 0xe6, 0x6e, 0x99, 0x5d, 0xdb, 0x4e, 0x46, 0x0c, 0x77, 0x51, + 0xab, 0xea, 0x5a, 0x37, 0x5d, 0xab, 0xf7, 0xf0, 0xfc, 0x72, 0xe1, 0x39, 0x57, 0x0b, 0xcf, 0xf9, + 0xbd, 0xf0, 0x9c, 0x1f, 0x4b, 0xaf, 0x76, 0xb5, 0xf4, 0x6a, 0xbf, 0x96, 0x5e, 0xed, 0xe3, 0x69, + 0xcc, 0xf5, 0xc5, 0x2c, 0xf2, 0xa9, 0x4c, 0x08, 0x95, 0x2a, 0x91, 0x8a, 0xf0, 0x88, 0x1e, 0xc7, + 0x92, 0xcc, 0xdf, 0x90, 0x44, 0xb2, 0xd9, 0x14, 0x54, 0x71, 0x77, 0x2f, 0x5f, 0x1f, 0x97, 0xa7, + 0xa7, 0xbf, 0xa7, 0xa0, 0xa2, 0xa6, 0x39, 0xbb, 0x57, 0x7f, 0x03, 0x00, 0x00, 0xff, 0xff, 0xaf, + 0xa9, 0x60, 0xe8, 0xe9, 0x03, 0x00, 0x00, } func (m *GenesisState) Marshal() (dAtA []byte, err error) { @@ -246,6 +256,16 @@ func (m *GenesisState) MarshalToSizedBuffer(dAtA []byte) (int, error) { _ = i var l int _ = l + { + size, err := m.Params.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintGenesis(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x4a if m.NextChannelSequence != 0 { i = encodeVarintGenesis(dAtA, i, uint64(m.NextChannelSequence)) i-- @@ -456,6 +476,8 @@ func (m *GenesisState) Size() (n int) { if m.NextChannelSequence != 0 { n += 1 + sovGenesis(uint64(m.NextChannelSequence)) } + l = m.Params.Size() + n += 1 + l + sovGenesis(uint64(l)) return n } @@ -771,6 +793,39 @@ func (m *GenesisState) Unmarshal(dAtA []byte) error { break } } + case 9: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Params", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGenesis + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthGenesis + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthGenesis + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.Params.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex default: iNdEx = preIndex skippy, err := skipGenesis(dAtA[iNdEx:]) diff --git a/modules/core/04-channel/types/genesis_test.go b/modules/core/04-channel/types/genesis_test.go index 973f06b6b0c..957c79725a7 100644 --- a/modules/core/04-channel/types/genesis_test.go +++ b/modules/core/04-channel/types/genesis_test.go @@ -67,6 +67,7 @@ func TestValidateGenesis(t *testing.T) { types.NewPacketSequence(testPort2, testChannel2, 1), }, 2, + types.Params{UpgradeTimeout: types.DefaultTimeout}, ), expPass: true, }, @@ -171,6 +172,7 @@ func TestValidateGenesis(t *testing.T) { types.NewPacketSequence(testPort2, testChannel2, 1), }, 0, + types.Params{UpgradeTimeout: types.DefaultTimeout}, ), expPass: false, }, @@ -208,6 +210,7 @@ func TestValidateGenesis(t *testing.T) { types.NewPacketSequence(testPort2, testChannel2, 1), }, 0, + types.Params{UpgradeTimeout: types.DefaultTimeout}, ), expPass: false, }, diff --git a/modules/core/04-channel/types/keys.go b/modules/core/04-channel/types/keys.go index bc9e88afdea..a99e14d5b21 100644 --- a/modules/core/04-channel/types/keys.go +++ b/modules/core/04-channel/types/keys.go @@ -28,6 +28,9 @@ const ( // ChannelPrefix is the prefix used when creating a channel identifier ChannelPrefix = "channel-" + + // ParamsKey defines the key to store the params in the keeper. + ParamsKey = "channelParams" ) // FormatChannelIdentifier returns the channel identifier with the sequence appended. diff --git a/modules/core/04-channel/types/msgs.go b/modules/core/04-channel/types/msgs.go index 02f6c43777b..9be788895c9 100644 --- a/modules/core/04-channel/types/msgs.go +++ b/modules/core/04-channel/types/msgs.go @@ -2,6 +2,7 @@ package types import ( "encoding/base64" + "slices" errorsmod "cosmossdk.io/errors" @@ -35,6 +36,10 @@ var ( _ sdk.HasValidateBasic = (*MsgAcknowledgement)(nil) _ sdk.HasValidateBasic = (*MsgTimeout)(nil) _ sdk.HasValidateBasic = (*MsgTimeoutOnClose)(nil) + _ sdk.HasValidateBasic = (*MsgChannelUpgradeInit)(nil) + _ sdk.HasValidateBasic = (*MsgChannelUpgradeTry)(nil) + _ sdk.HasValidateBasic = (*MsgChannelUpgradeAck)(nil) + _ sdk.HasValidateBasic = (*MsgChannelUpgradeConfirm)(nil) ) // NewMsgChannelOpenInit creates a new MsgChannelOpenInit. It sets the counterparty channel @@ -220,14 +225,15 @@ func (msg MsgChannelCloseInit) ValidateBasic() error { // NewMsgChannelCloseConfirm creates a new MsgChannelCloseConfirm instance func NewMsgChannelCloseConfirm( portID, channelID string, proofInit []byte, proofHeight clienttypes.Height, - signer string, + signer string, counterpartyUpgradeSequence uint64, ) *MsgChannelCloseConfirm { return &MsgChannelCloseConfirm{ - PortId: portID, - ChannelId: channelID, - ProofInit: proofInit, - ProofHeight: proofHeight, - Signer: signer, + PortId: portID, + ChannelId: channelID, + ProofInit: proofInit, + ProofHeight: proofHeight, + Signer: signer, + CounterpartyUpgradeSequence: counterpartyUpgradeSequence, } } @@ -315,14 +321,16 @@ func NewMsgTimeoutOnClose( packet Packet, nextSequenceRecv uint64, proofUnreceived, proofClose []byte, proofHeight clienttypes.Height, signer string, + counterpartyUpgradeSequence uint64, ) *MsgTimeoutOnClose { return &MsgTimeoutOnClose{ - Packet: packet, - NextSequenceRecv: nextSequenceRecv, - ProofUnreceived: proofUnreceived, - ProofClose: proofClose, - ProofHeight: proofHeight, - Signer: signer, + Packet: packet, + NextSequenceRecv: nextSequenceRecv, + ProofUnreceived: proofUnreceived, + ProofClose: proofClose, + ProofHeight: proofHeight, + Signer: signer, + CounterpartyUpgradeSequence: counterpartyUpgradeSequence, } } @@ -374,3 +382,377 @@ func (msg MsgAcknowledgement) ValidateBasic() error { } return msg.Packet.ValidateBasic() } + +var _ sdk.Msg = &MsgChannelUpgradeInit{} + +// NewMsgChannelUpgradeInit constructs a new MsgChannelUpgradeInit +// nolint:interfacer +func NewMsgChannelUpgradeInit( + portID, channelID string, + upgradeFields UpgradeFields, + signer string, +) *MsgChannelUpgradeInit { + return &MsgChannelUpgradeInit{ + PortId: portID, + ChannelId: channelID, + Fields: upgradeFields, + Signer: signer, + } +} + +// ValidateBasic implements sdk.Msg +func (msg MsgChannelUpgradeInit) ValidateBasic() error { + if err := host.PortIdentifierValidator(msg.PortId); err != nil { + return errorsmod.Wrap(err, "invalid port ID") + } + if !IsValidChannelID(msg.ChannelId) { + return ErrInvalidChannelIdentifier + } + + _, err := sdk.AccAddressFromBech32(msg.Signer) + if err != nil { + return errorsmod.Wrapf(ibcerrors.ErrInvalidAddress, "string could not be parsed as address: %v", err) + } + + return msg.Fields.ValidateBasic() +} + +var _ sdk.Msg = &MsgChannelUpgradeTry{} + +// NewMsgChannelUpgradeTry constructs a new MsgChannelUpgradeTry +// nolint:interfacer +func NewMsgChannelUpgradeTry( + portID, + channelID string, + proposedConnectionHops []string, + counterpartyUpgradeFields UpgradeFields, + counterpartyUpgradeSequence uint64, + proofChannel []byte, + proofUpgrade []byte, + proofHeight clienttypes.Height, + signer string, +) *MsgChannelUpgradeTry { + return &MsgChannelUpgradeTry{ + PortId: portID, + ChannelId: channelID, + ProposedUpgradeConnectionHops: proposedConnectionHops, + CounterpartyUpgradeFields: counterpartyUpgradeFields, + CounterpartyUpgradeSequence: counterpartyUpgradeSequence, + ProofChannel: proofChannel, + ProofUpgrade: proofUpgrade, + ProofHeight: proofHeight, + Signer: signer, + } +} + +// ValidateBasic implements sdk.Msg +func (msg MsgChannelUpgradeTry) ValidateBasic() error { + if err := host.PortIdentifierValidator(msg.PortId); err != nil { + return errorsmod.Wrap(err, "invalid port ID") + } + + if !IsValidChannelID(msg.ChannelId) { + return ErrInvalidChannelIdentifier + } + + if len(msg.ProposedUpgradeConnectionHops) == 0 { + return errorsmod.Wrap(ErrInvalidUpgrade, "proposed connection hops cannot be empty") + } + + if err := msg.CounterpartyUpgradeFields.ValidateBasic(); err != nil { + return errorsmod.Wrap(err, "error validating counterparty upgrade fields") + } + + if msg.CounterpartyUpgradeSequence == 0 { + return errorsmod.Wrap(ErrInvalidUpgradeSequence, "counterparty sequence cannot be 0") + } + + if len(msg.ProofChannel) == 0 { + return errorsmod.Wrap(commitmenttypes.ErrInvalidProof, "cannot submit an empty channel proof") + } + + if len(msg.ProofUpgrade) == 0 { + return errorsmod.Wrap(commitmenttypes.ErrInvalidProof, "cannot submit an empty upgrade proof") + } + + _, err := sdk.AccAddressFromBech32(msg.Signer) + if err != nil { + return errorsmod.Wrapf(ibcerrors.ErrInvalidAddress, "string could not be parsed as address: %v", err) + } + + return nil +} + +var _ sdk.Msg = &MsgChannelUpgradeAck{} + +// NewMsgChannelUpgradeAck constructs a new MsgChannelUpgradeAck +// nolint:interfacer +func NewMsgChannelUpgradeAck(portID, channelID string, counterpartyUpgrade Upgrade, proofChannel, proofUpgrade []byte, proofHeight clienttypes.Height, signer string) *MsgChannelUpgradeAck { + return &MsgChannelUpgradeAck{ + PortId: portID, + ChannelId: channelID, + CounterpartyUpgrade: counterpartyUpgrade, + ProofChannel: proofChannel, + ProofUpgrade: proofUpgrade, + ProofHeight: proofHeight, + Signer: signer, + } +} + +// ValidateBasic implements sdk.Msg +func (msg MsgChannelUpgradeAck) ValidateBasic() error { + if err := host.PortIdentifierValidator(msg.PortId); err != nil { + return errorsmod.Wrap(err, "invalid port ID") + } + if !IsValidChannelID(msg.ChannelId) { + return ErrInvalidChannelIdentifier + } + if len(msg.ProofChannel) == 0 { + return errorsmod.Wrap(commitmenttypes.ErrInvalidProof, "cannot submit an empty channel proof") + } + if len(msg.ProofUpgrade) == 0 { + return errorsmod.Wrap(commitmenttypes.ErrInvalidProof, "cannot submit an empty upgrade sequence proof") + } + if _, err := sdk.AccAddressFromBech32(msg.Signer); err != nil { + return errorsmod.Wrapf(ibcerrors.ErrInvalidAddress, "string could not be parsed as address: %v", err) + } + + return msg.CounterpartyUpgrade.ValidateBasic() +} + +var _ sdk.Msg = &MsgChannelUpgradeConfirm{} + +// NewMsgChannelUpgradeConfirm constructs a new MsgChannelUpgradeConfirm +func NewMsgChannelUpgradeConfirm( + portID, + channelID string, + counterpartyChannelState State, + counterpartyUpgrade Upgrade, + proofChannel, + proofUpgrade []byte, + proofHeight clienttypes.Height, + signer string, +) *MsgChannelUpgradeConfirm { + return &MsgChannelUpgradeConfirm{ + PortId: portID, + ChannelId: channelID, + CounterpartyChannelState: counterpartyChannelState, + CounterpartyUpgrade: counterpartyUpgrade, + ProofChannel: proofChannel, + ProofUpgrade: proofUpgrade, + ProofHeight: proofHeight, + Signer: signer, + } +} + +// ValidateBasic implements sdk.Msg +func (msg MsgChannelUpgradeConfirm) ValidateBasic() error { + if err := host.PortIdentifierValidator(msg.PortId); err != nil { + return errorsmod.Wrap(err, "invalid port ID") + } + + if !IsValidChannelID(msg.ChannelId) { + return ErrInvalidChannelIdentifier + } + + if !slices.Contains([]State{FLUSHING, FLUSHCOMPLETE}, msg.CounterpartyChannelState) { + return errorsmod.Wrapf(ErrInvalidChannelState, "expected channel state to be one of: %s or %s, got: %s", FLUSHING, FLUSHCOMPLETE, msg.CounterpartyChannelState) + } + + if len(msg.ProofChannel) == 0 { + return errorsmod.Wrap(commitmenttypes.ErrInvalidProof, "cannot submit an empty channel proof") + } + + if len(msg.ProofUpgrade) == 0 { + return errorsmod.Wrap(commitmenttypes.ErrInvalidProof, "cannot submit an empty upgrade proof") + } + + _, err := sdk.AccAddressFromBech32(msg.Signer) + if err != nil { + return errorsmod.Wrapf(ibcerrors.ErrInvalidAddress, "string could not be parsed as address: %v", err) + } + + return msg.CounterpartyUpgrade.ValidateBasic() +} + +var _ sdk.Msg = &MsgChannelUpgradeOpen{} + +// NewMsgChannelUpgradeOpen constructs a new MsgChannelUpgradeOpen +// nolint:interfacer +func NewMsgChannelUpgradeOpen( + portID, + channelID string, + counterpartyChannelState State, + proofChannel []byte, + proofHeight clienttypes.Height, + signer string, +) *MsgChannelUpgradeOpen { + return &MsgChannelUpgradeOpen{ + PortId: portID, + ChannelId: channelID, + CounterpartyChannelState: counterpartyChannelState, + ProofChannel: proofChannel, + ProofHeight: proofHeight, + Signer: signer, + } +} + +// ValidateBasic implements sdk.Msg +func (msg MsgChannelUpgradeOpen) ValidateBasic() error { + if err := host.PortIdentifierValidator(msg.PortId); err != nil { + return errorsmod.Wrap(err, "invalid port ID") + } + + if !IsValidChannelID(msg.ChannelId) { + return ErrInvalidChannelIdentifier + } + + if len(msg.ProofChannel) == 0 { + return errorsmod.Wrap(commitmenttypes.ErrInvalidProof, "cannot submit an empty channel proof") + } + + if !slices.Contains([]State{FLUSHCOMPLETE, OPEN}, msg.CounterpartyChannelState) { + return errorsmod.Wrapf(ErrInvalidChannelState, "expected channel state to be one of: [%s, %s], got: %s", FLUSHCOMPLETE, OPEN, msg.CounterpartyChannelState) + } + + _, err := sdk.AccAddressFromBech32(msg.Signer) + if err != nil { + return errorsmod.Wrapf(ibcerrors.ErrInvalidAddress, "string could not be parsed as address: %v", err) + } + + return nil +} + +var _ sdk.Msg = &MsgChannelUpgradeTimeout{} + +// NewMsgChannelUpgradeTimeout constructs a new MsgChannelUpgradeTimeout +// nolint:interfacer +func NewMsgChannelUpgradeTimeout( + portID, channelID string, + counterpartyChannel Channel, + proofChannel []byte, + proofHeight clienttypes.Height, + signer string, +) *MsgChannelUpgradeTimeout { + return &MsgChannelUpgradeTimeout{ + PortId: portID, + ChannelId: channelID, + CounterpartyChannel: counterpartyChannel, + ProofChannel: proofChannel, + ProofHeight: proofHeight, + Signer: signer, + } +} + +// ValidateBasic implements sdk.Msg +func (msg MsgChannelUpgradeTimeout) ValidateBasic() error { + if err := host.PortIdentifierValidator(msg.PortId); err != nil { + return errorsmod.Wrap(err, "invalid port ID") + } + + if !IsValidChannelID(msg.ChannelId) { + return ErrInvalidChannelIdentifier + } + + if len(msg.ProofChannel) == 0 { + return errorsmod.Wrap(commitmenttypes.ErrInvalidProof, "cannot submit an empty proof") + } + + if !slices.Contains([]State{FLUSHING, OPEN}, msg.CounterpartyChannel.State) { + return errorsmod.Wrapf(ErrInvalidChannelState, "expected counterparty channel state to be one of: [%s, %s], got: %s", FLUSHING, OPEN, msg.CounterpartyChannel.State) + } + + _, err := sdk.AccAddressFromBech32(msg.Signer) + if err != nil { + return errorsmod.Wrapf(ibcerrors.ErrInvalidAddress, "string could not be parsed as address: %v", err) + } + + return nil +} + +var _ sdk.Msg = &MsgChannelUpgradeCancel{} + +// NewMsgChannelUpgradeCancel constructs a new MsgChannelUpgradeCancel +// nolint:interfacer +func NewMsgChannelUpgradeCancel( + portID, channelID string, + errorReceipt ErrorReceipt, + proofErrReceipt []byte, + proofHeight clienttypes.Height, + signer string, +) *MsgChannelUpgradeCancel { + return &MsgChannelUpgradeCancel{ + PortId: portID, + ChannelId: channelID, + ErrorReceipt: errorReceipt, + ProofErrorReceipt: proofErrReceipt, + ProofHeight: proofHeight, + Signer: signer, + } +} + +// ValidateBasic implements sdk.Msg +func (msg MsgChannelUpgradeCancel) ValidateBasic() error { + if err := host.PortIdentifierValidator(msg.PortId); err != nil { + return errorsmod.Wrap(err, "invalid port ID") + } + + if !IsValidChannelID(msg.ChannelId) { + return ErrInvalidChannelIdentifier + } + + _, err := sdk.AccAddressFromBech32(msg.Signer) + if err != nil { + return errorsmod.Wrapf(ibcerrors.ErrInvalidAddress, "string could not be parsed as address: %v", err) + } + + return nil +} + +// NewMsgUpdateChannelParams creates a new instance of MsgUpdateParams. +func NewMsgUpdateChannelParams(authority string, params Params) *MsgUpdateParams { + return &MsgUpdateParams{ + Authority: authority, + Params: params, + } +} + +// ValidateBasic performs basic checks on a MsgUpdateParams. +func (msg *MsgUpdateParams) ValidateBasic() error { + if _, err := sdk.AccAddressFromBech32(msg.Authority); err != nil { + return errorsmod.Wrapf(ibcerrors.ErrInvalidAddress, "string could not be parsed as address: %v", err) + } + return msg.Params.Validate() +} + +// NewMsgPruneAcknowledgements creates a new instance of MsgPruneAcknowledgements. +func NewMsgPruneAcknowledgements(portID, channelID string, limit uint64, signer string) *MsgPruneAcknowledgements { + return &MsgPruneAcknowledgements{ + PortId: portID, + ChannelId: channelID, + Limit: limit, + Signer: signer, + } +} + +// ValidateBasic performs basic checks on a MsgPruneAcknowledgements. +func (msg *MsgPruneAcknowledgements) ValidateBasic() error { + if err := host.PortIdentifierValidator(msg.PortId); err != nil { + return errorsmod.Wrap(err, "invalid port ID") + } + + if !IsValidChannelID(msg.ChannelId) { + return ErrInvalidChannelIdentifier + } + + _, err := sdk.AccAddressFromBech32(msg.Signer) + if err != nil { + return errorsmod.Wrapf(ibcerrors.ErrInvalidAddress, "string could not be parsed as address: %v", err) + } + + if msg.Limit == 0 { + return errorsmod.Wrap(ErrInvalidPruningLimit, "number of acknowledgements to prune must be greater than 0") + } + + return nil +} diff --git a/modules/core/04-channel/types/msgs_test.go b/modules/core/04-channel/types/msgs_test.go index 8221ee95947..5a7bec0c889 100644 --- a/modules/core/04-channel/types/msgs_test.go +++ b/modules/core/04-channel/types/msgs_test.go @@ -20,16 +20,20 @@ import ( clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" commitmenttypes "github.com/cosmos/ibc-go/v8/modules/core/23-commitment/types" + host "github.com/cosmos/ibc-go/v8/modules/core/24-host" + ibcerrors "github.com/cosmos/ibc-go/v8/modules/core/errors" ibctesting "github.com/cosmos/ibc-go/v8/testing" + "github.com/cosmos/ibc-go/v8/testing/mock" "github.com/cosmos/ibc-go/v8/testing/simapp" ) const ( // valid constants used for testing - portid = "testportid" - chanid = "channel-0" - cpportid = "testcpport" - cpchanid = "testcpchannel" + portid = "testportid" + chanid = "channel-0" + cpportid = "testcpport" + cpchanid = "testcpchannel" + counterpartyUpgradeSequence = 0 version = "1.0" @@ -147,6 +151,18 @@ func (suite *TypesTestSuite) TestMsgChannelOpenInitValidateBasic() { } } +func (suite *TypesTestSuite) TestMsgChannelOpenInitGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + msg := types.NewMsgChannelOpenInit(portid, version, types.ORDERED, connHops, cpportid, addr) + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + func (suite *TypesTestSuite) TestMsgChannelOpenTryValidateBasic() { counterparty := types.NewCounterparty(cpportid, cpchanid) initChannel := types.NewChannel(types.INIT, types.ORDERED, counterparty, connHops, version) @@ -189,6 +205,18 @@ func (suite *TypesTestSuite) TestMsgChannelOpenTryValidateBasic() { } } +func (suite *TypesTestSuite) TestMsgChannelOpenTryGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + msg := types.NewMsgChannelOpenTry(portid, version, types.ORDERED, connHops, cpportid, cpchanid, version, suite.proof, height, addr) + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + func (suite *TypesTestSuite) TestMsgChannelOpenAckValidateBasic() { testCases := []struct { name string @@ -222,6 +250,18 @@ func (suite *TypesTestSuite) TestMsgChannelOpenAckValidateBasic() { } } +func (suite *TypesTestSuite) TestMsgChannelOpenAckGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + msg := types.NewMsgChannelOpenAck(portid, chanid, chanid, version, suite.proof, height, addr) + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + func (suite *TypesTestSuite) TestMsgChannelOpenConfirmValidateBasic() { testCases := []struct { name string @@ -253,6 +293,18 @@ func (suite *TypesTestSuite) TestMsgChannelOpenConfirmValidateBasic() { } } +func (suite *TypesTestSuite) TestMsgChannelOpenConfirmGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + msg := types.NewMsgChannelOpenConfirm(portid, chanid, suite.proof, height, addr) + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + func (suite *TypesTestSuite) TestMsgChannelCloseInitValidateBasic() { testCases := []struct { name string @@ -283,20 +335,33 @@ func (suite *TypesTestSuite) TestMsgChannelCloseInitValidateBasic() { } } +func (suite *TypesTestSuite) TestMsgChannelCloseInitGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + msg := types.NewMsgChannelCloseInit(portid, chanid, addr) + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + func (suite *TypesTestSuite) TestMsgChannelCloseConfirmValidateBasic() { testCases := []struct { name string msg *types.MsgChannelCloseConfirm expPass bool }{ - {"", types.NewMsgChannelCloseConfirm(portid, chanid, suite.proof, height, addr), true}, - {"too short port id", types.NewMsgChannelCloseConfirm(invalidShortPort, chanid, suite.proof, height, addr), false}, - {"too long port id", types.NewMsgChannelCloseConfirm(invalidLongPort, chanid, suite.proof, height, addr), false}, - {"port id contains non-alpha", types.NewMsgChannelCloseConfirm(invalidPort, chanid, suite.proof, height, addr), false}, - {"too short channel id", types.NewMsgChannelCloseConfirm(portid, invalidShortChannel, suite.proof, height, addr), false}, - {"too long channel id", types.NewMsgChannelCloseConfirm(portid, invalidLongChannel, suite.proof, height, addr), false}, - {"channel id contains non-alpha", types.NewMsgChannelCloseConfirm(portid, invalidChannel, suite.proof, height, addr), false}, - {"empty proof", types.NewMsgChannelCloseConfirm(portid, chanid, emptyProof, height, addr), false}, + {"success", types.NewMsgChannelCloseConfirm(portid, chanid, suite.proof, height, addr, 0), true}, + {"success, positive counterparty upgrade sequence", types.NewMsgChannelCloseConfirm(portid, chanid, suite.proof, height, addr, 1), true}, + {"too short port id", types.NewMsgChannelCloseConfirm(invalidShortPort, chanid, suite.proof, height, addr, 0), false}, + {"too long port id", types.NewMsgChannelCloseConfirm(invalidLongPort, chanid, suite.proof, height, addr, 0), false}, + {"port id contains non-alpha", types.NewMsgChannelCloseConfirm(invalidPort, chanid, suite.proof, height, addr, 0), false}, + {"too short channel id", types.NewMsgChannelCloseConfirm(portid, invalidShortChannel, suite.proof, height, addr, 0), false}, + {"too long channel id", types.NewMsgChannelCloseConfirm(portid, invalidLongChannel, suite.proof, height, addr, 0), false}, + {"channel id contains non-alpha", types.NewMsgChannelCloseConfirm(portid, invalidChannel, suite.proof, height, addr, 0), false}, + {"empty proof", types.NewMsgChannelCloseConfirm(portid, chanid, emptyProof, height, addr, 0), false}, } for _, tc := range testCases { @@ -314,6 +379,18 @@ func (suite *TypesTestSuite) TestMsgChannelCloseConfirmValidateBasic() { } } +func (suite *TypesTestSuite) TestMsgChannelCloseConfirmGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + msg := types.NewMsgChannelCloseConfirm(portid, chanid, suite.proof, height, addr, counterpartyUpgradeSequence) + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + func (suite *TypesTestSuite) TestMsgRecvPacketValidateBasic() { testCases := []struct { name string @@ -342,14 +419,15 @@ func (suite *TypesTestSuite) TestMsgRecvPacketValidateBasic() { } func (suite *TypesTestSuite) TestMsgRecvPacketGetSigners() { - signer := sdk.AccAddress(ibctesting.TestAccAddress) - msg := types.NewMsgRecvPacket(packet, suite.proof, height, signer.String()) + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + msg := types.NewMsgRecvPacket(packet, suite.proof, height, addr) encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) suite.Require().NoError(err) - suite.Require().Equal(signer.Bytes(), signers[0]) + suite.Require().Equal(expSigner.Bytes(), signers[0]) } func (suite *TypesTestSuite) TestMsgTimeoutValidateBasic() { @@ -380,18 +458,31 @@ func (suite *TypesTestSuite) TestMsgTimeoutValidateBasic() { } } +func (suite *TypesTestSuite) TestMsgTimeoutGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + msg := types.NewMsgTimeout(packet, 1, suite.proof, height, addr) + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + func (suite *TypesTestSuite) TestMsgTimeoutOnCloseValidateBasic() { testCases := []struct { name string msg *types.MsgTimeoutOnClose expPass bool }{ - {"success", types.NewMsgTimeoutOnClose(packet, 1, suite.proof, suite.proof, height, addr), true}, - {"seq 0", types.NewMsgTimeoutOnClose(packet, 0, suite.proof, suite.proof, height, addr), false}, - {"signer address is empty", types.NewMsgTimeoutOnClose(packet, 1, suite.proof, suite.proof, height, emptyAddr), false}, - {"empty proof", types.NewMsgTimeoutOnClose(packet, 1, emptyProof, suite.proof, height, addr), false}, - {"empty proof close", types.NewMsgTimeoutOnClose(packet, 1, suite.proof, emptyProof, height, addr), false}, - {"invalid packet", types.NewMsgTimeoutOnClose(invalidPacket, 1, suite.proof, suite.proof, height, addr), false}, + {"success", types.NewMsgTimeoutOnClose(packet, 1, suite.proof, suite.proof, height, addr, 0), true}, + {"success, positive counterparty upgrade sequence", types.NewMsgTimeoutOnClose(packet, 1, suite.proof, suite.proof, height, addr, 1), true}, + {"seq 0", types.NewMsgTimeoutOnClose(packet, 0, suite.proof, suite.proof, height, addr, 0), false}, + {"signer address is empty", types.NewMsgTimeoutOnClose(packet, 1, suite.proof, suite.proof, height, emptyAddr, 0), false}, + {"empty proof", types.NewMsgTimeoutOnClose(packet, 1, emptyProof, suite.proof, height, addr, 0), false}, + {"empty proof close", types.NewMsgTimeoutOnClose(packet, 1, suite.proof, emptyProof, height, addr, 0), false}, + {"invalid packet", types.NewMsgTimeoutOnClose(invalidPacket, 1, suite.proof, suite.proof, height, addr, 0), false}, } for _, tc := range testCases { @@ -409,6 +500,18 @@ func (suite *TypesTestSuite) TestMsgTimeoutOnCloseValidateBasic() { } } +func (suite *TypesTestSuite) TestMsgTimeoutOnCloseGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + msg := types.NewMsgTimeoutOnClose(packet, 1, suite.proof, suite.proof, height, addr, counterpartyUpgradeSequence) + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + func (suite *TypesTestSuite) TestMsgAcknowledgementValidateBasic() { testCases := []struct { name string @@ -436,3 +539,730 @@ func (suite *TypesTestSuite) TestMsgAcknowledgementValidateBasic() { }) } } + +func (suite *TypesTestSuite) TestMsgAcknowledgementGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + msg := types.NewMsgAcknowledgement(packet, packet.GetData(), suite.proof, height, addr) + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeInitValidateBasic() { + var msg *types.MsgChannelUpgradeInit + + testCases := []struct { + name string + malleate func() + expPass bool + }{ + { + "success", + func() {}, + true, + }, + { + "invalid port identifier", + func() { + msg.PortId = invalidPort + }, + false, + }, + { + "invalid channel identifier", + func() { + msg.ChannelId = invalidChannel + }, + false, + }, + { + "empty proposed upgrade channel version", + func() { + msg.Fields.Version = " " + }, + false, + }, + { + "missing signer address", + func() { + msg.Signer = emptyAddr + }, + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + msg = types.NewMsgChannelUpgradeInit( + ibctesting.MockPort, ibctesting.FirstChannelID, + types.NewUpgradeFields(types.UNORDERED, []string{ibctesting.FirstConnectionID}, mock.Version), + addr, + ) + + tc.malleate() + err := msg.ValidateBasic() + + if tc.expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeInitGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + msg := types.NewMsgChannelUpgradeInit( + ibctesting.MockPort, ibctesting.FirstChannelID, + types.NewUpgradeFields(types.UNORDERED, []string{ibctesting.FirstConnectionID}, mock.Version), + addr, + ) + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeTryValidateBasic() { + var msg *types.MsgChannelUpgradeTry + + testCases := []struct { + name string + malleate func() + expPass bool + }{ + { + "success", + func() {}, + true, + }, + { + "invalid port identifier", + func() { + msg.PortId = invalidPort + }, + false, + }, + { + "invalid channel identifier", + func() { + msg.ChannelId = invalidChannel + }, + false, + }, + { + "counterparty sequence cannot be zero", + func() { + msg.CounterpartyUpgradeSequence = 0 + }, + false, + }, + { + "invalid connection hops", + func() { + msg.ProposedUpgradeConnectionHops = []string{} + }, + false, + }, + { + "invalid counterparty upgrade fields ordering", + func() { + msg.CounterpartyUpgradeFields.Ordering = types.NONE + }, + false, + }, + { + "cannot submit an empty channel proof", + func() { + msg.ProofChannel = emptyProof + }, + false, + }, + { + "cannot submit an empty upgrade proof", + func() { + msg.ProofUpgrade = emptyProof + }, + false, + }, + { + "missing signer address", + func() { + msg.Signer = emptyAddr + }, + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + msg = types.NewMsgChannelUpgradeTry( + ibctesting.MockPort, + ibctesting.FirstChannelID, + []string{ibctesting.FirstConnectionID}, + types.NewUpgradeFields(types.UNORDERED, []string{ibctesting.FirstConnectionID}, mock.Version), + 1, + suite.proof, + suite.proof, + height, + addr, + ) + + tc.malleate() + err := msg.ValidateBasic() + + if tc.expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeTryGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + msg := types.NewMsgChannelUpgradeTry( + ibctesting.MockPort, + ibctesting.FirstChannelID, + []string{ibctesting.FirstConnectionID}, + types.NewUpgradeFields(types.UNORDERED, []string{ibctesting.FirstConnectionID}, mock.Version), + 1, + suite.proof, + suite.proof, + height, + addr, + ) + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeAckValidateBasic() { + var msg *types.MsgChannelUpgradeAck + + testCases := []struct { + name string + malleate func() + expPass bool + }{ + { + "success", + func() {}, + true, + }, + { + "invalid port identifier", + func() { + msg.PortId = invalidPort + }, + false, + }, + { + "invalid channel identifier", + func() { + msg.ChannelId = invalidChannel + }, + false, + }, + { + "cannot submit an empty channel proof", + func() { + msg.ProofChannel = emptyProof + }, + false, + }, + { + "cannot submit an empty upgrade proof", + func() { + msg.ProofUpgrade = emptyProof + }, + false, + }, + { + "missing signer address", + func() { + msg.Signer = emptyAddr + }, + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + upgrade := types.NewUpgrade( + types.NewUpgradeFields(types.ORDERED, []string{ibctesting.FirstConnectionID}, mock.Version), + types.NewTimeout(clienttypes.NewHeight(1, 100), 0), + 0, + ) + + msg = types.NewMsgChannelUpgradeAck( + ibctesting.MockPort, ibctesting.FirstChannelID, + upgrade, suite.proof, suite.proof, + height, addr, + ) + + tc.malleate() + err := msg.ValidateBasic() + + if tc.expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeAckGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + upgrade := types.NewUpgrade( + types.NewUpgradeFields(types.ORDERED, []string{ibctesting.FirstConnectionID}, mock.Version), + types.NewTimeout(clienttypes.NewHeight(1, 100), 0), + 0, + ) + + msg := types.NewMsgChannelUpgradeAck( + ibctesting.MockPort, ibctesting.FirstChannelID, + upgrade, suite.proof, suite.proof, + height, addr, + ) + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeConfirmValidateBasic() { + var msg *types.MsgChannelUpgradeConfirm + + testCases := []struct { + name string + malleate func() + expPass bool + }{ + { + "success", + func() {}, + true, + }, + { + "success: counterparty state set to FLUSHCOMPLETE", + func() { + msg.CounterpartyChannelState = types.FLUSHCOMPLETE + }, + true, + }, + { + "invalid port identifier", + func() { + msg.PortId = invalidPort + }, + false, + }, + { + "invalid channel identifier", + func() { + msg.ChannelId = invalidChannel + }, + false, + }, + { + "invalid counterparty channel state", + func() { + msg.CounterpartyChannelState = types.CLOSED + }, + false, + }, + { + "cannot submit an empty channel proof", + func() { + msg.ProofChannel = emptyProof + }, + false, + }, + { + "cannot submit an empty upgrade proof", + func() { + msg.ProofUpgrade = emptyProof + }, + false, + }, + { + "missing signer address", + func() { + msg.Signer = emptyAddr + }, + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + counterpartyUpgrade := types.NewUpgrade( + types.NewUpgradeFields(types.UNORDERED, []string{ibctesting.FirstConnectionID}, mock.Version), + types.NewTimeout(clienttypes.NewHeight(0, 10000), timeoutTimestamp), + 0, + ) + + msg = types.NewMsgChannelUpgradeConfirm( + ibctesting.MockPort, ibctesting.FirstChannelID, + types.FLUSHING, counterpartyUpgrade, suite.proof, suite.proof, + height, addr, + ) + + tc.malleate() + err := msg.ValidateBasic() + + if tc.expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeConfirmGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + + msg := &types.MsgChannelUpgradeConfirm{Signer: addr} + + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeOpenValidateBasic() { + var msg *types.MsgChannelUpgradeOpen + + testCases := []struct { + name string + malleate func() + expPass bool + }{ + { + "success: flushcomplete state", + func() {}, + true, + }, + { + "success: open state", + func() { + msg.CounterpartyChannelState = types.OPEN + }, + true, + }, + { + "invalid port identifier", + func() { + msg.PortId = invalidPort + }, + false, + }, + { + "invalid channel identifier", + func() { + msg.ChannelId = invalidChannel + }, + false, + }, + { + "invalid counterparty channel state", + func() { + msg.CounterpartyChannelState = types.CLOSED + }, + false, + }, + { + "cannot submit an empty channel proof", + func() { + msg.ProofChannel = emptyProof + }, + false, + }, + { + "missing signer address", + func() { + msg.Signer = emptyAddr + }, + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + msg = types.NewMsgChannelUpgradeOpen( + ibctesting.MockPort, ibctesting.FirstChannelID, + types.FLUSHCOMPLETE, suite.proof, + height, addr, + ) + + tc.malleate() + err := msg.ValidateBasic() + + if tc.expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeTimeoutValidateBasic() { + var msg *types.MsgChannelUpgradeTimeout + + testCases := []struct { + name string + malleate func() + expPass bool + }{ + { + "success", + func() {}, + true, + }, + { + "invalid port identifier", + func() { + msg.PortId = invalidPort + }, + false, + }, + { + "invalid channel identifier", + func() { + msg.ChannelId = invalidChannel + }, + false, + }, + { + "cannot submit an empty proof", + func() { + msg.ProofChannel = emptyProof + }, + false, + }, + { + "invalid counterparty channel state", + func() { + msg.CounterpartyChannel.State = types.CLOSED + }, + false, + }, + { + "missing signer address", + func() { + msg.Signer = emptyAddr + }, + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + msg = types.NewMsgChannelUpgradeTimeout( + ibctesting.MockPort, ibctesting.FirstChannelID, + types.Channel{State: types.OPEN}, + suite.proof, + height, addr, + ) + + tc.malleate() + err := msg.ValidateBasic() + + if tc.expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeTimeoutGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + + msg := types.NewMsgChannelUpgradeTimeout( + ibctesting.MockPort, ibctesting.FirstChannelID, + types.Channel{}, + suite.proof, + height, addr, + ) + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeCancelValidateBasic() { + var msg *types.MsgChannelUpgradeCancel + + testCases := []struct { + name string + malleate func() + expPass bool + }{ + { + "success", + func() {}, + true, + }, + { + "invalid port identifier", + func() { + msg.PortId = invalidPort + }, + false, + }, + { + "invalid channel identifier", + func() { + msg.ChannelId = invalidChannel + }, + false, + }, + { + "can submit an empty proof", + func() { + msg.ProofErrorReceipt = emptyProof + }, + true, + }, + { + "missing signer address", + func() { + msg.Signer = emptyAddr + }, + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + msg = types.NewMsgChannelUpgradeCancel(ibctesting.MockPort, ibctesting.FirstChannelID, types.ErrorReceipt{Sequence: 1}, suite.proof, height, addr) + + tc.malleate() + err := msg.ValidateBasic() + + if tc.expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *TypesTestSuite) TestMsgChannelUpgradeCancelGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + + msg := types.NewMsgChannelUpgradeCancel(ibctesting.MockPort, ibctesting.FirstChannelID, types.ErrorReceipt{Sequence: 1}, suite.proof, height, addr) + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} + +func (suite *TypesTestSuite) TestMsgPruneAcknowledgementsValidateBasic() { + var msg *types.MsgPruneAcknowledgements + + testCases := []struct { + name string + malleate func() + expErr error + }{ + { + "success", + func() {}, + nil, + }, + { + "failure: zero pruning limit", + func() { + msg.Limit = 0 + }, + types.ErrInvalidPruningLimit, + }, + { + "invalid port identifier", + func() { + msg.PortId = invalidPort + }, + host.ErrInvalidID, + }, + { + "invalid channel identifier", + func() { + msg.ChannelId = invalidChannel + }, + types.ErrInvalidChannelIdentifier, + }, + { + "empty signer address", + func() { + msg.Signer = emptyAddr + }, + ibcerrors.ErrInvalidAddress, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + msg = types.NewMsgPruneAcknowledgements(ibctesting.MockPort, ibctesting.FirstChannelID, 1, addr) + + tc.malleate() + err := msg.ValidateBasic() + + expPass := tc.expErr == nil + if expPass { + suite.Require().NoError(err) + } else { + suite.Require().ErrorIs(err, tc.expErr) + } + }) + } +} + +func (suite *TypesTestSuite) TestMsgPruneAcknowledgementsGetSigners() { + expSigner, err := sdk.AccAddressFromBech32(addr) + suite.Require().NoError(err) + + msg := types.NewMsgPruneAcknowledgements(ibctesting.MockPort, ibctesting.FirstChannelID, 0, addr) + encodingCfg := moduletestutil.MakeTestEncodingConfig(ibc.AppModuleBasic{}) + signers, _, err := encodingCfg.Codec.GetMsgV1Signers(msg) + + suite.Require().NoError(err) + suite.Require().Equal(expSigner.Bytes(), signers[0]) +} diff --git a/modules/core/04-channel/types/params.go b/modules/core/04-channel/types/params.go new file mode 100644 index 00000000000..cf44ae307c0 --- /dev/null +++ b/modules/core/04-channel/types/params.go @@ -0,0 +1,36 @@ +package types + +import ( + "fmt" + "time" + + clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" +) + +// DefaultTimeout defines a default parameter for the channel upgrade protocol. +// It allows relayers a window in which they can flush all in-flight packets on a channel before completing the upgrade handshake. +// This parameter can be overridden by a valid authority using the UpdateChannelParams rpc. +var DefaultTimeout = NewTimeout(clienttypes.ZeroHeight(), uint64(10*time.Minute.Nanoseconds())) + +// NewParams creates a new parameter configuration for the channel submodule +func NewParams(upgradeTimeout Timeout) Params { + return Params{ + UpgradeTimeout: upgradeTimeout, + } +} + +// DefaultParams is the default parameter configuration for the channel submodule +func DefaultParams() Params { + return NewParams(DefaultTimeout) +} + +// Validate the params. +func (p Params) Validate() error { + if !p.UpgradeTimeout.Height.IsZero() { + return fmt.Errorf("upgrade timeout height must be zero. got : %v", p.UpgradeTimeout.Height) + } + if p.UpgradeTimeout.Timestamp == 0 { + return fmt.Errorf("upgrade timeout timestamp invalid: %v", p.UpgradeTimeout.Timestamp) + } + return nil +} diff --git a/modules/core/04-channel/types/query.go b/modules/core/04-channel/types/query.go index 81b0cb58307..baa307d827f 100644 --- a/modules/core/04-channel/types/query.go +++ b/modules/core/04-channel/types/query.go @@ -104,3 +104,21 @@ func NewQueryNextSequenceSendResponse( ProofHeight: height, } } + +// NewQueryUpgradeErrorResponse creates a new QueryUpgradeErrorResponse instance +func NewQueryUpgradeErrorResponse(errorReceipt ErrorReceipt, proof []byte, height clienttypes.Height) *QueryUpgradeErrorResponse { + return &QueryUpgradeErrorResponse{ + ErrorReceipt: errorReceipt, + Proof: proof, + ProofHeight: height, + } +} + +// NewQueryUpgradeResponse creates a new QueryUpgradeResponse instance +func NewQueryUpgradeResponse(upgrade Upgrade, proof []byte, height clienttypes.Height) *QueryUpgradeResponse { + return &QueryUpgradeResponse{ + Upgrade: upgrade, + Proof: proof, + ProofHeight: height, + } +} diff --git a/modules/core/04-channel/types/query.pb.go b/modules/core/04-channel/types/query.pb.go index 8ca3338c254..9d3c481b71b 100644 --- a/modules/core/04-channel/types/query.pb.go +++ b/modules/core/04-channel/types/query.pb.go @@ -1611,7 +1611,7 @@ func (m *QueryNextSequenceReceiveRequest) GetChannelId() string { return "" } -// QuerySequenceResponse is the request type for the +// QuerySequenceResponse is the response type for the // Query/QueryNextSequenceReceiveResponse RPC method type QueryNextSequenceReceiveResponse struct { // next sequence receive number @@ -1797,6 +1797,321 @@ func (m *QueryNextSequenceSendResponse) GetProofHeight() types.Height { return types.Height{} } +// QueryUpgradeErrorRequest is the request type for the Query/QueryUpgradeError RPC method +type QueryUpgradeErrorRequest struct { + PortId string `protobuf:"bytes,1,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` + ChannelId string `protobuf:"bytes,2,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` +} + +func (m *QueryUpgradeErrorRequest) Reset() { *m = QueryUpgradeErrorRequest{} } +func (m *QueryUpgradeErrorRequest) String() string { return proto.CompactTextString(m) } +func (*QueryUpgradeErrorRequest) ProtoMessage() {} +func (*QueryUpgradeErrorRequest) Descriptor() ([]byte, []int) { + return fileDescriptor_1034a1e9abc4cca1, []int{28} +} +func (m *QueryUpgradeErrorRequest) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *QueryUpgradeErrorRequest) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_QueryUpgradeErrorRequest.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } +} +func (m *QueryUpgradeErrorRequest) XXX_Merge(src proto.Message) { + xxx_messageInfo_QueryUpgradeErrorRequest.Merge(m, src) +} +func (m *QueryUpgradeErrorRequest) XXX_Size() int { + return m.Size() +} +func (m *QueryUpgradeErrorRequest) XXX_DiscardUnknown() { + xxx_messageInfo_QueryUpgradeErrorRequest.DiscardUnknown(m) +} + +var xxx_messageInfo_QueryUpgradeErrorRequest proto.InternalMessageInfo + +func (m *QueryUpgradeErrorRequest) GetPortId() string { + if m != nil { + return m.PortId + } + return "" +} + +func (m *QueryUpgradeErrorRequest) GetChannelId() string { + if m != nil { + return m.ChannelId + } + return "" +} + +// QueryUpgradeErrorResponse is the response type for the Query/QueryUpgradeError RPC method +type QueryUpgradeErrorResponse struct { + ErrorReceipt ErrorReceipt `protobuf:"bytes,1,opt,name=error_receipt,json=errorReceipt,proto3" json:"error_receipt"` + // merkle proof of existence + Proof []byte `protobuf:"bytes,2,opt,name=proof,proto3" json:"proof,omitempty"` + // height at which the proof was retrieved + ProofHeight types.Height `protobuf:"bytes,3,opt,name=proof_height,json=proofHeight,proto3" json:"proof_height"` +} + +func (m *QueryUpgradeErrorResponse) Reset() { *m = QueryUpgradeErrorResponse{} } +func (m *QueryUpgradeErrorResponse) String() string { return proto.CompactTextString(m) } +func (*QueryUpgradeErrorResponse) ProtoMessage() {} +func (*QueryUpgradeErrorResponse) Descriptor() ([]byte, []int) { + return fileDescriptor_1034a1e9abc4cca1, []int{29} +} +func (m *QueryUpgradeErrorResponse) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *QueryUpgradeErrorResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_QueryUpgradeErrorResponse.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } +} +func (m *QueryUpgradeErrorResponse) XXX_Merge(src proto.Message) { + xxx_messageInfo_QueryUpgradeErrorResponse.Merge(m, src) +} +func (m *QueryUpgradeErrorResponse) XXX_Size() int { + return m.Size() +} +func (m *QueryUpgradeErrorResponse) XXX_DiscardUnknown() { + xxx_messageInfo_QueryUpgradeErrorResponse.DiscardUnknown(m) +} + +var xxx_messageInfo_QueryUpgradeErrorResponse proto.InternalMessageInfo + +func (m *QueryUpgradeErrorResponse) GetErrorReceipt() ErrorReceipt { + if m != nil { + return m.ErrorReceipt + } + return ErrorReceipt{} +} + +func (m *QueryUpgradeErrorResponse) GetProof() []byte { + if m != nil { + return m.Proof + } + return nil +} + +func (m *QueryUpgradeErrorResponse) GetProofHeight() types.Height { + if m != nil { + return m.ProofHeight + } + return types.Height{} +} + +// QueryUpgradeRequest is the request type for the QueryUpgradeRequest RPC method +type QueryUpgradeRequest struct { + PortId string `protobuf:"bytes,1,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` + ChannelId string `protobuf:"bytes,2,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` +} + +func (m *QueryUpgradeRequest) Reset() { *m = QueryUpgradeRequest{} } +func (m *QueryUpgradeRequest) String() string { return proto.CompactTextString(m) } +func (*QueryUpgradeRequest) ProtoMessage() {} +func (*QueryUpgradeRequest) Descriptor() ([]byte, []int) { + return fileDescriptor_1034a1e9abc4cca1, []int{30} +} +func (m *QueryUpgradeRequest) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *QueryUpgradeRequest) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_QueryUpgradeRequest.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } +} +func (m *QueryUpgradeRequest) XXX_Merge(src proto.Message) { + xxx_messageInfo_QueryUpgradeRequest.Merge(m, src) +} +func (m *QueryUpgradeRequest) XXX_Size() int { + return m.Size() +} +func (m *QueryUpgradeRequest) XXX_DiscardUnknown() { + xxx_messageInfo_QueryUpgradeRequest.DiscardUnknown(m) +} + +var xxx_messageInfo_QueryUpgradeRequest proto.InternalMessageInfo + +func (m *QueryUpgradeRequest) GetPortId() string { + if m != nil { + return m.PortId + } + return "" +} + +func (m *QueryUpgradeRequest) GetChannelId() string { + if m != nil { + return m.ChannelId + } + return "" +} + +// QueryUpgradeResponse is the response type for the QueryUpgradeResponse RPC method +type QueryUpgradeResponse struct { + Upgrade Upgrade `protobuf:"bytes,1,opt,name=upgrade,proto3" json:"upgrade"` + // merkle proof of existence + Proof []byte `protobuf:"bytes,2,opt,name=proof,proto3" json:"proof,omitempty"` + // height at which the proof was retrieved + ProofHeight types.Height `protobuf:"bytes,3,opt,name=proof_height,json=proofHeight,proto3" json:"proof_height"` +} + +func (m *QueryUpgradeResponse) Reset() { *m = QueryUpgradeResponse{} } +func (m *QueryUpgradeResponse) String() string { return proto.CompactTextString(m) } +func (*QueryUpgradeResponse) ProtoMessage() {} +func (*QueryUpgradeResponse) Descriptor() ([]byte, []int) { + return fileDescriptor_1034a1e9abc4cca1, []int{31} +} +func (m *QueryUpgradeResponse) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *QueryUpgradeResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_QueryUpgradeResponse.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } +} +func (m *QueryUpgradeResponse) XXX_Merge(src proto.Message) { + xxx_messageInfo_QueryUpgradeResponse.Merge(m, src) +} +func (m *QueryUpgradeResponse) XXX_Size() int { + return m.Size() +} +func (m *QueryUpgradeResponse) XXX_DiscardUnknown() { + xxx_messageInfo_QueryUpgradeResponse.DiscardUnknown(m) +} + +var xxx_messageInfo_QueryUpgradeResponse proto.InternalMessageInfo + +func (m *QueryUpgradeResponse) GetUpgrade() Upgrade { + if m != nil { + return m.Upgrade + } + return Upgrade{} +} + +func (m *QueryUpgradeResponse) GetProof() []byte { + if m != nil { + return m.Proof + } + return nil +} + +func (m *QueryUpgradeResponse) GetProofHeight() types.Height { + if m != nil { + return m.ProofHeight + } + return types.Height{} +} + +// QueryChannelParamsRequest is the request type for the Query/ChannelParams RPC method. +type QueryChannelParamsRequest struct { +} + +func (m *QueryChannelParamsRequest) Reset() { *m = QueryChannelParamsRequest{} } +func (m *QueryChannelParamsRequest) String() string { return proto.CompactTextString(m) } +func (*QueryChannelParamsRequest) ProtoMessage() {} +func (*QueryChannelParamsRequest) Descriptor() ([]byte, []int) { + return fileDescriptor_1034a1e9abc4cca1, []int{32} +} +func (m *QueryChannelParamsRequest) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *QueryChannelParamsRequest) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_QueryChannelParamsRequest.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } +} +func (m *QueryChannelParamsRequest) XXX_Merge(src proto.Message) { + xxx_messageInfo_QueryChannelParamsRequest.Merge(m, src) +} +func (m *QueryChannelParamsRequest) XXX_Size() int { + return m.Size() +} +func (m *QueryChannelParamsRequest) XXX_DiscardUnknown() { + xxx_messageInfo_QueryChannelParamsRequest.DiscardUnknown(m) +} + +var xxx_messageInfo_QueryChannelParamsRequest proto.InternalMessageInfo + +// QueryChannelParamsResponse is the response type for the Query/ChannelParams RPC method. +type QueryChannelParamsResponse struct { + // params defines the parameters of the module. + Params *Params `protobuf:"bytes,1,opt,name=params,proto3" json:"params,omitempty"` +} + +func (m *QueryChannelParamsResponse) Reset() { *m = QueryChannelParamsResponse{} } +func (m *QueryChannelParamsResponse) String() string { return proto.CompactTextString(m) } +func (*QueryChannelParamsResponse) ProtoMessage() {} +func (*QueryChannelParamsResponse) Descriptor() ([]byte, []int) { + return fileDescriptor_1034a1e9abc4cca1, []int{33} +} +func (m *QueryChannelParamsResponse) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *QueryChannelParamsResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_QueryChannelParamsResponse.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } +} +func (m *QueryChannelParamsResponse) XXX_Merge(src proto.Message) { + xxx_messageInfo_QueryChannelParamsResponse.Merge(m, src) +} +func (m *QueryChannelParamsResponse) XXX_Size() int { + return m.Size() +} +func (m *QueryChannelParamsResponse) XXX_DiscardUnknown() { + xxx_messageInfo_QueryChannelParamsResponse.DiscardUnknown(m) +} + +var xxx_messageInfo_QueryChannelParamsResponse proto.InternalMessageInfo + +func (m *QueryChannelParamsResponse) GetParams() *Params { + if m != nil { + return m.Params + } + return nil +} + func init() { proto.RegisterType((*QueryChannelRequest)(nil), "ibc.core.channel.v1.QueryChannelRequest") proto.RegisterType((*QueryChannelResponse)(nil), "ibc.core.channel.v1.QueryChannelResponse") @@ -1826,109 +2141,128 @@ func init() { proto.RegisterType((*QueryNextSequenceReceiveResponse)(nil), "ibc.core.channel.v1.QueryNextSequenceReceiveResponse") proto.RegisterType((*QueryNextSequenceSendRequest)(nil), "ibc.core.channel.v1.QueryNextSequenceSendRequest") proto.RegisterType((*QueryNextSequenceSendResponse)(nil), "ibc.core.channel.v1.QueryNextSequenceSendResponse") + proto.RegisterType((*QueryUpgradeErrorRequest)(nil), "ibc.core.channel.v1.QueryUpgradeErrorRequest") + proto.RegisterType((*QueryUpgradeErrorResponse)(nil), "ibc.core.channel.v1.QueryUpgradeErrorResponse") + proto.RegisterType((*QueryUpgradeRequest)(nil), "ibc.core.channel.v1.QueryUpgradeRequest") + proto.RegisterType((*QueryUpgradeResponse)(nil), "ibc.core.channel.v1.QueryUpgradeResponse") + proto.RegisterType((*QueryChannelParamsRequest)(nil), "ibc.core.channel.v1.QueryChannelParamsRequest") + proto.RegisterType((*QueryChannelParamsResponse)(nil), "ibc.core.channel.v1.QueryChannelParamsResponse") } func init() { proto.RegisterFile("ibc/core/channel/v1/query.proto", fileDescriptor_1034a1e9abc4cca1) } var fileDescriptor_1034a1e9abc4cca1 = []byte{ - // 1547 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xdc, 0x59, 0xcf, 0x6f, 0x13, 0x47, - 0x14, 0xce, 0x38, 0x06, 0x92, 0x07, 0x85, 0x30, 0x49, 0x4a, 0x58, 0x82, 0x13, 0x5c, 0xb5, 0x04, - 0x54, 0x76, 0x48, 0xa0, 0x34, 0xad, 0x5a, 0x24, 0x12, 0xa9, 0x90, 0xaa, 0xfc, 0xda, 0x94, 0x16, - 0x90, 0x5a, 0x77, 0xbd, 0x1e, 0x9c, 0x55, 0xe2, 0x5d, 0xe3, 0x5d, 0x1b, 0x50, 0xea, 0xaa, 0xea, - 0x81, 0x72, 0xac, 0xca, 0xa1, 0x52, 0x2f, 0x95, 0x7a, 0x2a, 0x87, 0x1e, 0xfa, 0x17, 0xf4, 0xca, - 0xad, 0x48, 0xf4, 0x50, 0x09, 0x89, 0x56, 0x04, 0x89, 0x5e, 0x7b, 0xe9, 0xb9, 0xda, 0xf9, 0xb1, - 0xde, 0xb5, 0x77, 0x37, 0x76, 0x1c, 0x4b, 0x51, 0x6f, 0xde, 0x99, 0x79, 0x6f, 0xbe, 0xef, 0x7b, - 0xf3, 0xde, 0xce, 0x5b, 0xc3, 0x84, 0x99, 0x37, 0x88, 0x61, 0x57, 0x28, 0x31, 0x96, 0x74, 0xcb, - 0xa2, 0x2b, 0xa4, 0x36, 0x4d, 0x6e, 0x56, 0x69, 0xe5, 0x8e, 0x5a, 0xae, 0xd8, 0xae, 0x8d, 0x87, - 0xcd, 0xbc, 0xa1, 0x7a, 0x0b, 0x54, 0xb1, 0x40, 0xad, 0x4d, 0x2b, 0x01, 0xab, 0x15, 0x93, 0x5a, - 0xae, 0x67, 0xc4, 0x7f, 0x71, 0x2b, 0xe5, 0xa8, 0x61, 0x3b, 0x25, 0xdb, 0x21, 0x79, 0xdd, 0xa1, - 0xdc, 0x1d, 0xa9, 0x4d, 0xe7, 0xa9, 0xab, 0x4f, 0x93, 0xb2, 0x5e, 0x34, 0x2d, 0xdd, 0x35, 0x6d, - 0x4b, 0xac, 0x3d, 0x14, 0x05, 0x41, 0x6e, 0xc6, 0x97, 0x8c, 0x17, 0x6d, 0xbb, 0xb8, 0x42, 0x89, - 0x5e, 0x36, 0x89, 0x6e, 0x59, 0xb6, 0xcb, 0xec, 0x1d, 0x31, 0xbb, 0x5f, 0xcc, 0xb2, 0xa7, 0x7c, - 0xf5, 0x06, 0xd1, 0x2d, 0x81, 0x5e, 0x19, 0x29, 0xda, 0x45, 0x9b, 0xfd, 0x24, 0xde, 0x2f, 0x3e, - 0x9a, 0x3d, 0x0f, 0xc3, 0x97, 0x3d, 0x4c, 0xf3, 0x7c, 0x13, 0x8d, 0xde, 0xac, 0x52, 0xc7, 0xc5, - 0xfb, 0x60, 0x47, 0xd9, 0xae, 0xb8, 0x39, 0xb3, 0x30, 0x86, 0x26, 0xd1, 0xd4, 0xa0, 0xb6, 0xdd, - 0x7b, 0x5c, 0x28, 0xe0, 0x83, 0x00, 0x02, 0x8f, 0x37, 0x97, 0x62, 0x73, 0x83, 0x62, 0x64, 0xa1, - 0x90, 0x7d, 0x80, 0x60, 0x24, 0xec, 0xcf, 0x29, 0xdb, 0x96, 0x43, 0xf1, 0x29, 0xd8, 0x21, 0x56, - 0x31, 0x87, 0x3b, 0x67, 0xc6, 0xd5, 0x08, 0x35, 0x55, 0x69, 0x26, 0x17, 0xe3, 0x11, 0xd8, 0x56, - 0xae, 0xd8, 0xf6, 0x0d, 0xb6, 0xd5, 0x2e, 0x8d, 0x3f, 0xe0, 0x79, 0xd8, 0xc5, 0x7e, 0xe4, 0x96, - 0xa8, 0x59, 0x5c, 0x72, 0xc7, 0xfa, 0x99, 0x4b, 0x25, 0xe0, 0x92, 0x47, 0xa0, 0x36, 0xad, 0x9e, - 0x63, 0x2b, 0xe6, 0xd2, 0x0f, 0x9f, 0x4e, 0xf4, 0x69, 0x3b, 0x99, 0x15, 0x1f, 0xca, 0x7e, 0x1a, - 0x86, 0xea, 0x48, 0xee, 0xef, 0x01, 0x34, 0x02, 0x23, 0xd0, 0xbe, 0xa6, 0xf2, 0x28, 0xaa, 0x5e, - 0x14, 0x55, 0x7e, 0x28, 0x44, 0x14, 0xd5, 0x4b, 0x7a, 0x91, 0x0a, 0x5b, 0x2d, 0x60, 0x99, 0x7d, - 0x8a, 0x60, 0xb4, 0x69, 0x03, 0x21, 0xc6, 0x1c, 0x0c, 0x08, 0x7e, 0xce, 0x18, 0x9a, 0xec, 0x67, - 0xfe, 0xa3, 0xd4, 0x58, 0x28, 0x50, 0xcb, 0x35, 0x6f, 0x98, 0xb4, 0x20, 0x75, 0xf1, 0xed, 0xf0, - 0xd9, 0x10, 0xca, 0x14, 0x43, 0x79, 0x78, 0x5d, 0x94, 0x1c, 0x40, 0x10, 0x26, 0x9e, 0x85, 0xed, - 0x1d, 0xaa, 0x28, 0xd6, 0x67, 0xef, 0x21, 0xc8, 0x70, 0x82, 0xb6, 0x65, 0x51, 0xc3, 0xf3, 0xd6, - 0xac, 0x65, 0x06, 0xc0, 0xf0, 0x27, 0xc5, 0x51, 0x0a, 0x8c, 0x34, 0x69, 0x9d, 0xda, 0xb0, 0xd6, - 0x7f, 0x23, 0x98, 0x88, 0x85, 0xf2, 0xff, 0x52, 0xfd, 0xaa, 0x14, 0x9d, 0x63, 0x9a, 0x67, 0xab, - 0x17, 0x5d, 0xdd, 0xa5, 0xdd, 0x26, 0xef, 0x9f, 0xbe, 0x88, 0x11, 0xae, 0x85, 0x88, 0x3a, 0xec, - 0x33, 0x7d, 0x7d, 0x72, 0x1c, 0x6a, 0xce, 0xf1, 0x96, 0x88, 0x4c, 0x39, 0x12, 0x45, 0x24, 0x20, - 0x69, 0xc0, 0xe7, 0xa8, 0x19, 0x35, 0xdc, 0xcb, 0x94, 0xff, 0x19, 0xc1, 0xa1, 0x10, 0x43, 0x8f, - 0x93, 0xe5, 0x54, 0x9d, 0xcd, 0xd0, 0x0f, 0x1f, 0x86, 0x3d, 0x15, 0x5a, 0x33, 0x1d, 0xd3, 0xb6, - 0x72, 0x56, 0xb5, 0x94, 0xa7, 0x15, 0x86, 0x32, 0xad, 0xed, 0x96, 0xc3, 0x17, 0xd8, 0x68, 0x68, - 0xa1, 0xa0, 0x93, 0x0e, 0x2f, 0x14, 0x78, 0x9f, 0x20, 0xc8, 0x26, 0xe1, 0x15, 0x41, 0x79, 0x17, - 0xf6, 0x18, 0x72, 0x26, 0x14, 0x8c, 0x11, 0x95, 0xbf, 0x0f, 0x54, 0xf9, 0x3e, 0x50, 0xcf, 0x58, - 0x77, 0xb4, 0xdd, 0x46, 0xc8, 0x0d, 0x3e, 0x00, 0x83, 0x22, 0x90, 0x3e, 0xab, 0x01, 0x3e, 0xb0, - 0x50, 0x68, 0x44, 0xa3, 0x3f, 0x29, 0x1a, 0xe9, 0x8d, 0x44, 0xa3, 0x02, 0xe3, 0x8c, 0xdc, 0x25, - 0xdd, 0x58, 0xa6, 0xee, 0xbc, 0x5d, 0x2a, 0x99, 0x6e, 0x89, 0x5a, 0x6e, 0xb7, 0x71, 0x50, 0x60, - 0xc0, 0xf1, 0x5c, 0x58, 0x06, 0x15, 0x01, 0xf0, 0x9f, 0xb3, 0xdf, 0x23, 0x38, 0x18, 0xb3, 0xa9, - 0x10, 0x93, 0x95, 0x2c, 0x39, 0xca, 0x36, 0xde, 0xa5, 0x05, 0x46, 0x7a, 0x79, 0x3c, 0x7f, 0x88, - 0x03, 0xe7, 0x74, 0x2b, 0x49, 0xb8, 0xce, 0xf6, 0x6f, 0xb8, 0xce, 0xbe, 0x90, 0x25, 0x3f, 0x02, - 0xa1, 0x5f, 0x66, 0x77, 0x36, 0xd4, 0x92, 0x95, 0x76, 0x32, 0xb2, 0xd2, 0x72, 0x27, 0xfc, 0x2c, - 0x07, 0x8d, 0xb6, 0x42, 0x99, 0xb5, 0x61, 0x7f, 0x80, 0xa8, 0x46, 0x0d, 0x6a, 0x96, 0x7b, 0x7a, - 0x32, 0xef, 0x23, 0x50, 0xa2, 0x76, 0x14, 0xb2, 0x2a, 0x30, 0x50, 0xf1, 0x86, 0x6a, 0x94, 0xfb, - 0x1d, 0xd0, 0xfc, 0xe7, 0x5e, 0xe6, 0xe8, 0x2d, 0x51, 0x30, 0x39, 0xa8, 0x33, 0xc6, 0xb2, 0x65, - 0xdf, 0x5a, 0xa1, 0x85, 0x22, 0xed, 0x75, 0xa2, 0x3e, 0x90, 0xa5, 0x2f, 0x66, 0x67, 0x21, 0xcb, - 0x14, 0xec, 0xd1, 0xc3, 0x53, 0x22, 0x65, 0x9b, 0x87, 0x7b, 0x99, 0xb7, 0xcf, 0x13, 0xb1, 0x6e, - 0x95, 0xe4, 0xc5, 0xa7, 0xe1, 0x40, 0x99, 0x01, 0xcc, 0x35, 0x72, 0x2d, 0x27, 0x05, 0x77, 0xc6, - 0xd2, 0x93, 0xfd, 0x53, 0x69, 0x6d, 0x7f, 0xb9, 0x29, 0xb3, 0x17, 0xe5, 0x82, 0xec, 0xbf, 0x08, - 0x5e, 0x49, 0xa4, 0x29, 0x62, 0xf2, 0x01, 0x0c, 0x35, 0x89, 0xdf, 0x7e, 0x19, 0x68, 0xb1, 0xdc, - 0x0a, 0xb5, 0xe0, 0x3b, 0x59, 0x97, 0xaf, 0x58, 0x32, 0xe7, 0x38, 0xe6, 0xae, 0x43, 0xbb, 0x4e, - 0x48, 0xfa, 0xd7, 0x0b, 0xc9, 0x6d, 0x51, 0x8e, 0x23, 0x80, 0x89, 0x60, 0x8c, 0xc3, 0x60, 0xc3, - 0x1f, 0x62, 0xfe, 0x1a, 0x03, 0x01, 0x4d, 0x52, 0x1d, 0x6a, 0x72, 0x57, 0x96, 0xab, 0xc6, 0xd6, - 0x67, 0x8c, 0xe5, 0xae, 0x05, 0x39, 0x0e, 0x23, 0x42, 0x10, 0xdd, 0x58, 0x6e, 0x51, 0x02, 0x97, - 0xe5, 0xc9, 0x6b, 0x48, 0x50, 0x85, 0x03, 0x91, 0x38, 0x7a, 0xcc, 0xff, 0x9a, 0xb8, 0x2b, 0x5f, - 0xa0, 0xb7, 0xfd, 0x78, 0x68, 0x1c, 0x40, 0xb7, 0xf7, 0xf0, 0x5f, 0x10, 0x4c, 0xc6, 0xfb, 0x16, - 0xbc, 0x66, 0x60, 0xd4, 0xa2, 0xb7, 0x1b, 0x87, 0x25, 0x27, 0xd8, 0xb3, 0xad, 0xd2, 0xda, 0xb0, - 0xd5, 0x6a, 0xdb, 0xcb, 0x12, 0xf8, 0x91, 0xb8, 0xcb, 0x05, 0x21, 0x2f, 0x52, 0xab, 0xd0, 0xad, - 0x16, 0x3f, 0xc9, 0xd4, 0x6b, 0x75, 0x2c, 0x84, 0x78, 0x1d, 0x70, 0x58, 0x08, 0x87, 0x5a, 0x05, - 0xa1, 0xc2, 0x90, 0xd5, 0x64, 0xd5, 0x43, 0x09, 0x66, 0x9e, 0xee, 0x83, 0x6d, 0x0c, 0x2a, 0xfe, - 0x11, 0xc1, 0x0e, 0x71, 0x63, 0xc7, 0x53, 0x91, 0x25, 0x2f, 0xe2, 0x9b, 0x8b, 0x72, 0xa4, 0x8d, - 0x95, 0x9c, 0x73, 0x76, 0xee, 0xab, 0xc7, 0xcf, 0xef, 0xa7, 0xde, 0xc1, 0x6f, 0x93, 0x84, 0x0f, - 0x46, 0x0e, 0x59, 0x6d, 0x28, 0x5b, 0x27, 0x9e, 0xde, 0x0e, 0x59, 0x15, 0x51, 0xa8, 0xe3, 0x7b, - 0x08, 0x06, 0x64, 0x8f, 0x8c, 0xd7, 0xdf, 0x5b, 0x66, 0xb6, 0x72, 0xb4, 0x9d, 0xa5, 0x02, 0xe7, - 0xab, 0x0c, 0xe7, 0x04, 0x3e, 0x98, 0x88, 0x13, 0xff, 0x8a, 0x00, 0xb7, 0x36, 0xee, 0xf8, 0x44, - 0xc2, 0x4e, 0x71, 0x5f, 0x1c, 0x94, 0x93, 0x9d, 0x19, 0x09, 0xa0, 0xa7, 0x19, 0xd0, 0x59, 0x7c, - 0x2a, 0x1a, 0xa8, 0x6f, 0xe8, 0x69, 0xea, 0x3f, 0xd4, 0x1b, 0x0c, 0x1e, 0x79, 0x0c, 0x5a, 0xba, - 0xe6, 0x44, 0x06, 0x71, 0xed, 0x7b, 0x22, 0x83, 0xd8, 0xc6, 0x3c, 0x7b, 0x91, 0x31, 0x58, 0xc0, - 0x67, 0x37, 0x7e, 0x24, 0x48, 0xb0, 0x9d, 0xc7, 0xdf, 0xa6, 0x60, 0x34, 0xb2, 0xed, 0xc4, 0xa7, - 0xd6, 0x07, 0x18, 0xd5, 0x57, 0x2b, 0x6f, 0x76, 0x6c, 0x27, 0xb8, 0x7d, 0x8d, 0x18, 0xb9, 0x2f, - 0x11, 0xfe, 0xa2, 0x1b, 0x76, 0xe1, 0x16, 0x99, 0xc8, 0x5e, 0x9b, 0xac, 0x36, 0x75, 0xed, 0x75, - 0xc2, 0xcb, 0x40, 0x60, 0x82, 0x0f, 0xd4, 0xf1, 0x13, 0x04, 0x43, 0xcd, 0xad, 0x0f, 0x9e, 0x8e, - 0xe7, 0x15, 0xd3, 0xda, 0x2a, 0x33, 0x9d, 0x98, 0x08, 0x15, 0x3e, 0x63, 0x22, 0x5c, 0xc7, 0x57, - 0xbb, 0xd0, 0xa0, 0xe5, 0xb2, 0xe1, 0x90, 0x55, 0x59, 0x38, 0xeb, 0xf8, 0x31, 0x82, 0xbd, 0x2d, - 0x8d, 0x1d, 0xee, 0x00, 0xab, 0x9f, 0x85, 0x27, 0x3a, 0xb2, 0x11, 0x04, 0xaf, 0x30, 0x82, 0x17, - 0xf1, 0xf9, 0x4d, 0x25, 0x88, 0x7f, 0x43, 0xf0, 0x52, 0xa8, 0xa7, 0xc2, 0xea, 0x7a, 0xe8, 0xc2, - 0xed, 0x9e, 0x42, 0xda, 0x5e, 0x2f, 0x98, 0x7c, 0xc2, 0x98, 0x7c, 0x8c, 0xaf, 0x74, 0xcf, 0xa4, - 0xc2, 0x5d, 0x87, 0xe2, 0xb4, 0x86, 0x60, 0x34, 0xf2, 0x0e, 0x9e, 0x94, 0x9a, 0x49, 0x1d, 0x5c, - 0x52, 0x6a, 0x26, 0xf6, 0x5f, 0xd9, 0x6b, 0x8c, 0xe9, 0x22, 0xbe, 0xdc, 0x3d, 0x53, 0xdd, 0x58, - 0x0e, 0xb1, 0x7c, 0x81, 0xe0, 0xe5, 0xe8, 0x4e, 0x03, 0x77, 0x0a, 0xd7, 0x3f, 0x97, 0xb3, 0x9d, - 0x1b, 0x0a, 0xa2, 0xd7, 0x19, 0xd1, 0x0f, 0xb1, 0xb6, 0x29, 0x44, 0xc3, 0x74, 0xee, 0xa6, 0x60, - 0x6f, 0xcb, 0x0d, 0x3e, 0x29, 0xef, 0xe2, 0xfa, 0x90, 0xa4, 0xbc, 0x8b, 0x6d, 0x11, 0x36, 0xa9, - 0xbc, 0x46, 0x95, 0x96, 0x84, 0xde, 0xa6, 0x4e, 0xaa, 0x3e, 0xa0, 0x5c, 0x59, 0x50, 0xfe, 0x07, - 0xc1, 0xee, 0xf0, 0x3d, 0x1e, 0x93, 0x76, 0x18, 0x05, 0x3a, 0x0f, 0xe5, 0x78, 0xfb, 0x06, 0x82, - 0xff, 0xe7, 0x8c, 0x7e, 0x0d, 0xbb, 0xbd, 0x61, 0x1f, 0x6a, 0x64, 0x42, 0xb4, 0xbd, 0x13, 0x8f, - 0x7f, 0x47, 0x30, 0x1c, 0x71, 0xd1, 0xc7, 0x09, 0xd7, 0x80, 0xf8, 0x9e, 0x43, 0x79, 0xa3, 0x43, - 0x2b, 0x21, 0xc1, 0x25, 0x26, 0xc1, 0xfb, 0xf8, 0x5c, 0x17, 0x12, 0x84, 0x6e, 0xe1, 0xde, 0x8d, - 0x68, 0xa8, 0xf9, 0xce, 0x9e, 0xf4, 0xa6, 0x8c, 0x69, 0x1c, 0x92, 0xde, 0x94, 0x71, 0x2d, 0xc1, - 0xa6, 0xbc, 0x48, 0x5a, 0x7b, 0x8a, 0xb9, 0xc5, 0x87, 0xcf, 0x32, 0xe8, 0xd1, 0xb3, 0x0c, 0xfa, - 0xeb, 0x59, 0x06, 0x7d, 0xb3, 0x96, 0xe9, 0x7b, 0xb4, 0x96, 0xe9, 0xfb, 0x63, 0x2d, 0xd3, 0x77, - 0xfd, 0xad, 0xa2, 0xe9, 0x2e, 0x55, 0xf3, 0xaa, 0x61, 0x97, 0x88, 0xf8, 0xbb, 0xd7, 0xcc, 0x1b, - 0xc7, 0x8a, 0x36, 0xa9, 0xcd, 0x92, 0x92, 0x5d, 0xa8, 0xae, 0x50, 0x87, 0xe3, 0x38, 0x7e, 0xf2, - 0x98, 0x84, 0xe2, 0xde, 0x29, 0x53, 0x27, 0xbf, 0x9d, 0x7d, 0x9a, 0x3f, 0xf1, 0x5f, 0x00, 0x00, - 0x00, 0xff, 0xff, 0xfa, 0x61, 0xcc, 0x20, 0x7e, 0x1e, 0x00, 0x00, + // 1757 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xdc, 0x5a, 0xcf, 0x6f, 0x14, 0x47, + 0x16, 0x76, 0xd9, 0xc6, 0x3f, 0x0a, 0x03, 0xa6, 0x6c, 0x2f, 0xa6, 0x6d, 0x8f, 0xcd, 0xa0, 0x5d, + 0x0c, 0x5a, 0xba, 0xb1, 0xcd, 0xb2, 0xde, 0x15, 0x8b, 0x84, 0xbd, 0xbb, 0x60, 0xb4, 0x80, 0x69, + 0x2f, 0x09, 0x20, 0x25, 0x93, 0x9e, 0x9e, 0x62, 0xdc, 0xb2, 0xa7, 0xbb, 0x99, 0xee, 0x19, 0x40, + 0x8e, 0xa3, 0x28, 0x07, 0xc2, 0x31, 0x0a, 0x8a, 0x22, 0xe5, 0x12, 0x29, 0xa7, 0x10, 0x29, 0x8a, + 0xf2, 0x17, 0xe4, 0x92, 0x03, 0xb7, 0x20, 0x91, 0x43, 0x24, 0x24, 0x12, 0x61, 0x22, 0x72, 0xcd, + 0x25, 0xe7, 0xa8, 0xab, 0x5e, 0xf5, 0x74, 0xcf, 0x74, 0xb7, 0x3d, 0x6e, 0x8f, 0x84, 0x72, 0x9b, + 0xae, 0xae, 0xf7, 0xea, 0xfb, 0xbe, 0x57, 0xf5, 0xba, 0xde, 0xb3, 0xf1, 0xb8, 0x91, 0xd7, 0x15, + 0xdd, 0x2a, 0x53, 0x45, 0x5f, 0xd6, 0x4c, 0x93, 0xae, 0x2a, 0xd5, 0x29, 0xe5, 0x56, 0x85, 0x96, + 0xef, 0xca, 0x76, 0xd9, 0x72, 0x2d, 0x32, 0x60, 0xe4, 0x75, 0xd9, 0x9b, 0x20, 0xc3, 0x04, 0xb9, + 0x3a, 0x25, 0x05, 0xac, 0x56, 0x0d, 0x6a, 0xba, 0x9e, 0x11, 0xff, 0xc5, 0xad, 0xa4, 0x63, 0xba, + 0xe5, 0x94, 0x2c, 0x47, 0xc9, 0x6b, 0x0e, 0xe5, 0xee, 0x94, 0xea, 0x54, 0x9e, 0xba, 0xda, 0x94, + 0x62, 0x6b, 0x45, 0xc3, 0xd4, 0x5c, 0xc3, 0x32, 0x61, 0xee, 0xa1, 0x28, 0x08, 0x62, 0x31, 0x3e, + 0x65, 0xb4, 0x68, 0x59, 0xc5, 0x55, 0xaa, 0x68, 0xb6, 0xa1, 0x68, 0xa6, 0x69, 0xb9, 0xcc, 0xde, + 0x81, 0xb7, 0x07, 0xe1, 0x2d, 0x7b, 0xca, 0x57, 0x6e, 0x2a, 0x9a, 0x09, 0xe8, 0xa5, 0xc1, 0xa2, + 0x55, 0xb4, 0xd8, 0x4f, 0xc5, 0xfb, 0x95, 0xb4, 0x62, 0xc5, 0x2e, 0x96, 0xb5, 0x02, 0xe5, 0x53, + 0xb2, 0x17, 0xf1, 0xc0, 0x15, 0x0f, 0xf6, 0x3c, 0x9f, 0xa0, 0xd2, 0x5b, 0x15, 0xea, 0xb8, 0xe4, + 0x00, 0xee, 0xb6, 0xad, 0xb2, 0x9b, 0x33, 0x0a, 0xc3, 0x68, 0x02, 0x4d, 0xf6, 0xaa, 0x5d, 0xde, + 0xe3, 0x42, 0x81, 0x8c, 0x61, 0x0c, 0xbe, 0xbc, 0x77, 0xed, 0xec, 0x5d, 0x2f, 0x8c, 0x2c, 0x14, + 0xb2, 0x0f, 0x11, 0x1e, 0x0c, 0xfb, 0x73, 0x6c, 0xcb, 0x74, 0x28, 0x39, 0x85, 0xbb, 0x61, 0x16, + 0x73, 0xb8, 0x7b, 0x7a, 0x54, 0x8e, 0x10, 0x5c, 0x16, 0x66, 0x62, 0x32, 0x19, 0xc4, 0xbb, 0xec, + 0xb2, 0x65, 0xdd, 0x64, 0x4b, 0xf5, 0xa9, 0xfc, 0x81, 0xcc, 0xe3, 0x3e, 0xf6, 0x23, 0xb7, 0x4c, + 0x8d, 0xe2, 0xb2, 0x3b, 0xdc, 0xc1, 0x5c, 0x4a, 0x01, 0x97, 0x3c, 0x48, 0xd5, 0x29, 0xf9, 0x3c, + 0x9b, 0x31, 0xd7, 0xf9, 0xe8, 0xd9, 0x78, 0x9b, 0xba, 0x9b, 0x59, 0xf1, 0xa1, 0xec, 0x9b, 0x61, + 0xa8, 0x8e, 0xe0, 0xfe, 0x5f, 0x8c, 0x6b, 0xb1, 0x03, 0xb4, 0x7f, 0x91, 0x79, 0xa0, 0x65, 0x2f, + 0xd0, 0x32, 0xdf, 0x37, 0x10, 0x68, 0x79, 0x51, 0x2b, 0x52, 0xb0, 0x55, 0x03, 0x96, 0xd9, 0x67, + 0x08, 0x0f, 0xd5, 0x2d, 0x00, 0x62, 0xcc, 0xe1, 0x1e, 0xe0, 0xe7, 0x0c, 0xa3, 0x89, 0x0e, 0xe6, + 0x3f, 0x4a, 0x8d, 0x85, 0x02, 0x35, 0x5d, 0xe3, 0xa6, 0x41, 0x0b, 0x42, 0x17, 0xdf, 0x8e, 0x9c, + 0x0b, 0xa1, 0x6c, 0x67, 0x28, 0x8f, 0x6c, 0x8a, 0x92, 0x03, 0x08, 0xc2, 0x24, 0xb3, 0xb8, 0xab, + 0x49, 0x15, 0x61, 0x7e, 0xf6, 0x3e, 0xc2, 0x19, 0x4e, 0xd0, 0x32, 0x4d, 0xaa, 0x7b, 0xde, 0xea, + 0xb5, 0xcc, 0x60, 0xac, 0xfb, 0x2f, 0x61, 0x2b, 0x05, 0x46, 0xea, 0xb4, 0x6e, 0xdf, 0xb6, 0xd6, + 0xbf, 0x20, 0x3c, 0x1e, 0x0b, 0xe5, 0x8f, 0xa5, 0xfa, 0x35, 0x21, 0x3a, 0xc7, 0x34, 0xcf, 0x66, + 0x2f, 0xb9, 0x9a, 0x4b, 0xd3, 0x1e, 0xde, 0x1f, 0x7d, 0x11, 0x23, 0x5c, 0x83, 0x88, 0x1a, 0x3e, + 0x60, 0xf8, 0xfa, 0xe4, 0x38, 0xd4, 0x9c, 0xe3, 0x4d, 0x81, 0x93, 0x72, 0x34, 0x8a, 0x48, 0x40, + 0xd2, 0x80, 0xcf, 0x21, 0x23, 0x6a, 0xb8, 0x95, 0x47, 0xfe, 0x4b, 0x84, 0x0f, 0x85, 0x18, 0x7a, + 0x9c, 0x4c, 0xa7, 0xe2, 0xec, 0x84, 0x7e, 0xe4, 0x08, 0xde, 0x57, 0xa6, 0x55, 0xc3, 0x31, 0x2c, + 0x33, 0x67, 0x56, 0x4a, 0x79, 0x5a, 0x66, 0x28, 0x3b, 0xd5, 0xbd, 0x62, 0xf8, 0x12, 0x1b, 0x0d, + 0x4d, 0x04, 0x3a, 0x9d, 0xe1, 0x89, 0x80, 0xf7, 0x29, 0xc2, 0xd9, 0x24, 0xbc, 0x10, 0x94, 0x7f, + 0xe1, 0x7d, 0xba, 0x78, 0x13, 0x0a, 0xc6, 0xa0, 0xcc, 0x3f, 0x19, 0xb2, 0xf8, 0x64, 0xc8, 0x67, + 0xcd, 0xbb, 0xea, 0x5e, 0x3d, 0xe4, 0x86, 0x8c, 0xe0, 0x5e, 0x08, 0xa4, 0xcf, 0xaa, 0x87, 0x0f, + 0x2c, 0x14, 0x6a, 0xd1, 0xe8, 0x48, 0x8a, 0x46, 0xe7, 0x76, 0xa2, 0x51, 0xc6, 0xa3, 0x8c, 0xdc, + 0xa2, 0xa6, 0xaf, 0x50, 0x77, 0xde, 0x2a, 0x95, 0x0c, 0xb7, 0x44, 0x4d, 0x37, 0x6d, 0x1c, 0x24, + 0xdc, 0xe3, 0x78, 0x2e, 0x4c, 0x9d, 0x42, 0x00, 0xfc, 0xe7, 0xec, 0x27, 0x08, 0x8f, 0xc5, 0x2c, + 0x0a, 0x62, 0xb2, 0x94, 0x25, 0x46, 0xd9, 0xc2, 0x7d, 0x6a, 0x60, 0xa4, 0x95, 0xdb, 0xf3, 0xd3, + 0x38, 0x70, 0x4e, 0x5a, 0x49, 0xc2, 0x79, 0xb6, 0x63, 0xdb, 0x79, 0xf6, 0xa5, 0x48, 0xf9, 0x11, + 0x08, 0xfd, 0x34, 0xbb, 0xbb, 0xa6, 0x96, 0xc8, 0xb4, 0x13, 0x91, 0x99, 0x96, 0x3b, 0xe1, 0x7b, + 0x39, 0x68, 0xf4, 0x2a, 0xa4, 0x59, 0x0b, 0x1f, 0x0c, 0x10, 0x55, 0xa9, 0x4e, 0x0d, 0xbb, 0xa5, + 0x3b, 0xf3, 0x01, 0xc2, 0x52, 0xd4, 0x8a, 0x20, 0xab, 0x84, 0x7b, 0xca, 0xde, 0x50, 0x95, 0x72, + 0xbf, 0x3d, 0xaa, 0xff, 0xdc, 0xca, 0x33, 0x7a, 0x1b, 0x12, 0x26, 0x07, 0x75, 0x56, 0x5f, 0x31, + 0xad, 0xdb, 0xab, 0xb4, 0x50, 0xa4, 0xad, 0x3e, 0xa8, 0x0f, 0x45, 0xea, 0x8b, 0x59, 0x19, 0x64, + 0x99, 0xc4, 0xfb, 0xb4, 0xf0, 0x2b, 0x38, 0xb2, 0xf5, 0xc3, 0xad, 0x3c, 0xb7, 0x2f, 0x12, 0xb1, + 0xbe, 0x2a, 0x87, 0x97, 0x9c, 0xc1, 0x23, 0x36, 0x03, 0x98, 0xab, 0x9d, 0xb5, 0x9c, 0x10, 0xdc, + 0x19, 0xee, 0x9c, 0xe8, 0x98, 0xec, 0x54, 0x0f, 0xda, 0x75, 0x27, 0x7b, 0x49, 0x4c, 0xc8, 0xfe, + 0x86, 0xf0, 0xe1, 0x44, 0x9a, 0x10, 0x93, 0xff, 0xe1, 0xfe, 0x3a, 0xf1, 0xb7, 0x9e, 0x06, 0x1a, + 0x2c, 0x5f, 0x85, 0x5c, 0xf0, 0xb1, 0xc8, 0xcb, 0x57, 0x4d, 0x71, 0xe6, 0x38, 0xe6, 0xd4, 0xa1, + 0xdd, 0x24, 0x24, 0x1d, 0x9b, 0x85, 0xe4, 0x0e, 0xa4, 0xe3, 0x08, 0x60, 0x10, 0x8c, 0x51, 0xdc, + 0x5b, 0xf3, 0x87, 0x98, 0xbf, 0xda, 0x40, 0x40, 0x93, 0xf6, 0x26, 0x35, 0xb9, 0x27, 0xd2, 0x55, + 0x6d, 0xe9, 0xb3, 0xfa, 0x4a, 0x6a, 0x41, 0x4e, 0xe0, 0x41, 0x10, 0x44, 0xd3, 0x57, 0x1a, 0x94, + 0x20, 0xb6, 0xd8, 0x79, 0x35, 0x09, 0x2a, 0x78, 0x24, 0x12, 0x47, 0x8b, 0xf9, 0x5f, 0x87, 0xbb, + 0xf2, 0x25, 0x7a, 0xc7, 0x8f, 0x87, 0xca, 0x01, 0xa4, 0xbd, 0x87, 0x7f, 0x8d, 0xf0, 0x44, 0xbc, + 0x6f, 0xe0, 0x35, 0x8d, 0x87, 0x4c, 0x7a, 0xa7, 0xb6, 0x59, 0x72, 0xc0, 0x9e, 0x2d, 0xd5, 0xa9, + 0x0e, 0x98, 0x8d, 0xb6, 0xad, 0x4c, 0x81, 0xaf, 0xc1, 0x5d, 0x2e, 0x08, 0x79, 0x89, 0x9a, 0x85, + 0xb4, 0x5a, 0x7c, 0x2e, 0x8e, 0x5e, 0xa3, 0x63, 0x10, 0xe2, 0xaf, 0x98, 0x84, 0x85, 0x70, 0xa8, + 0x59, 0x00, 0x15, 0xfa, 0xcd, 0x3a, 0xab, 0x56, 0x4a, 0xa0, 0xe2, 0x61, 0xbe, 0x11, 0x79, 0x83, + 0xe5, 0x3f, 0xe5, 0xb2, 0x55, 0x4e, 0x4b, 0xff, 0x5b, 0x04, 0xd7, 0x90, 0xb0, 0x53, 0x3f, 0xd1, + 0xee, 0xa1, 0xde, 0x00, 0x8f, 0xbd, 0xed, 0xc2, 0xad, 0xff, 0x50, 0x64, 0x96, 0x05, 0x53, 0x36, + 0x11, 0xe0, 0xf7, 0xd1, 0xc0, 0x58, 0x2b, 0xa5, 0x11, 0x5d, 0x26, 0x60, 0x91, 0x56, 0x95, 0xaf, + 0x44, 0x97, 0xc9, 0xf7, 0x07, 0x82, 0x9c, 0xc6, 0xdd, 0xd0, 0xde, 0x4a, 0xec, 0x32, 0x81, 0x19, + 0x20, 0x15, 0x26, 0xad, 0x14, 0x60, 0x04, 0xc2, 0x08, 0x75, 0xdc, 0xa2, 0x56, 0xd6, 0x4a, 0x22, + 0x57, 0x66, 0xaf, 0x40, 0x26, 0xad, 0x7b, 0x09, 0x9c, 0x66, 0x70, 0x97, 0xcd, 0x46, 0x80, 0xd2, + 0x48, 0xcc, 0x37, 0x94, 0x19, 0xc1, 0xd4, 0xe9, 0x9f, 0x47, 0xf0, 0x2e, 0xe6, 0x93, 0x7c, 0x86, + 0x70, 0x37, 0x38, 0x26, 0x93, 0x91, 0xa6, 0x11, 0xfd, 0x3f, 0xe9, 0xe8, 0x16, 0x66, 0x72, 0x7c, + 0xd9, 0xb9, 0xf7, 0x9e, 0xbc, 0x78, 0xd0, 0x7e, 0x9a, 0xfc, 0x53, 0x49, 0xe8, 0x6f, 0x3a, 0xca, + 0x5a, 0x2d, 0xa0, 0xeb, 0x8a, 0x17, 0x66, 0x47, 0x59, 0x83, 0xe0, 0xaf, 0x93, 0xfb, 0x08, 0xf7, + 0x88, 0x7e, 0x0d, 0xd9, 0x7c, 0x6d, 0xa1, 0x9c, 0x74, 0x6c, 0x2b, 0x53, 0x01, 0xe7, 0x9f, 0x19, + 0xce, 0x71, 0x32, 0x96, 0x88, 0x93, 0x7c, 0x83, 0x30, 0x69, 0x6c, 0x22, 0x91, 0x99, 0x84, 0x95, + 0xe2, 0xba, 0x5f, 0xd2, 0xc9, 0xe6, 0x8c, 0x00, 0xe8, 0x19, 0x06, 0x74, 0x96, 0x9c, 0x8a, 0x06, + 0xea, 0x1b, 0x7a, 0x9a, 0xfa, 0x0f, 0xeb, 0x35, 0x06, 0x8f, 0x3d, 0x06, 0x0d, 0x1d, 0x9c, 0x44, + 0x06, 0x71, 0xad, 0xa4, 0x44, 0x06, 0xb1, 0x4d, 0xa2, 0xec, 0x65, 0xc6, 0x60, 0x81, 0x9c, 0xdb, + 0xfe, 0x96, 0x50, 0x82, 0xad, 0x25, 0xf2, 0x61, 0x3b, 0x1e, 0x8a, 0x6c, 0x81, 0x90, 0x53, 0x9b, + 0x03, 0x8c, 0xea, 0xf1, 0x48, 0x7f, 0x6f, 0xda, 0x0e, 0xb8, 0xbd, 0x8f, 0x18, 0xb9, 0x77, 0x11, + 0x79, 0x27, 0x0d, 0xbb, 0x70, 0xbb, 0x46, 0x11, 0x7d, 0x1f, 0x65, 0xad, 0xae, 0x83, 0xb4, 0xae, + 0xf0, 0xb4, 0x13, 0x78, 0xc1, 0x07, 0xd6, 0xc9, 0x53, 0x84, 0xfb, 0xeb, 0xcb, 0x70, 0x32, 0x15, + 0xcf, 0x2b, 0xa6, 0xcd, 0x22, 0x4d, 0x37, 0x63, 0x02, 0x2a, 0xbc, 0xc5, 0x44, 0xb8, 0x41, 0xae, + 0xa5, 0xd0, 0xa0, 0xe1, 0xe2, 0xeb, 0x28, 0x6b, 0xe2, 0x23, 0xbe, 0x4e, 0x9e, 0x20, 0xbc, 0xbf, + 0xa1, 0xc9, 0x40, 0x9a, 0xc0, 0xea, 0x9f, 0xc2, 0x99, 0xa6, 0x6c, 0x80, 0xe0, 0x55, 0x46, 0xf0, + 0x32, 0xb9, 0xb8, 0xa3, 0x04, 0xc9, 0x77, 0x08, 0xef, 0x09, 0xd5, 0xf7, 0x44, 0xde, 0x0c, 0x5d, + 0xb8, 0xf5, 0x20, 0x29, 0x5b, 0x9e, 0x0f, 0x4c, 0xde, 0x60, 0x4c, 0x5e, 0x27, 0x57, 0xd3, 0x33, + 0x81, 0x6b, 0x46, 0x28, 0x4e, 0x1b, 0x08, 0x0f, 0x45, 0xd6, 0x83, 0x49, 0x47, 0x33, 0xa9, 0x9b, + 0x90, 0x74, 0x34, 0x13, 0x7b, 0x01, 0xd9, 0xeb, 0x8c, 0xe9, 0x12, 0xb9, 0x92, 0x9e, 0xa9, 0xa6, + 0xaf, 0x84, 0x58, 0xbe, 0x44, 0xf8, 0x4f, 0xd1, 0x55, 0x2f, 0x69, 0x16, 0xae, 0xbf, 0x2f, 0x67, + 0x9b, 0x37, 0x04, 0xa2, 0x37, 0x18, 0xd1, 0xff, 0x13, 0x75, 0x47, 0x88, 0x86, 0xe9, 0xdc, 0x6b, + 0xc7, 0xfb, 0x1b, 0xaa, 0xc9, 0xa4, 0x73, 0x17, 0x57, 0x13, 0x27, 0x9d, 0xbb, 0xd8, 0x72, 0x75, + 0x87, 0xd2, 0x6b, 0x54, 0x6a, 0x49, 0xa8, 0xb3, 0xd7, 0x95, 0x8a, 0x0f, 0x28, 0x67, 0x03, 0xe5, + 0x5f, 0x11, 0xde, 0x1b, 0xae, 0x29, 0x89, 0xb2, 0x15, 0x46, 0x81, 0x2a, 0x58, 0x3a, 0xb1, 0x75, + 0x03, 0xe0, 0xff, 0x36, 0xa3, 0x5f, 0x25, 0x6e, 0x6b, 0xd8, 0x87, 0x8a, 0xea, 0x10, 0x6d, 0x6f, + 0xc7, 0x93, 0xef, 0x11, 0x1e, 0x88, 0x28, 0x3a, 0x49, 0xc2, 0x35, 0x20, 0xbe, 0xfe, 0x95, 0xfe, + 0xd6, 0xa4, 0x15, 0x48, 0xb0, 0xc8, 0x24, 0xb8, 0x40, 0xce, 0xa7, 0x90, 0x20, 0x54, 0x11, 0x7a, + 0x37, 0xa2, 0xfe, 0xfa, 0xfa, 0x31, 0xe9, 0x4b, 0x19, 0x53, 0xc4, 0x26, 0x7d, 0x29, 0xe3, 0xca, + 0xd3, 0x1d, 0xf9, 0x90, 0x34, 0xd6, 0xb7, 0xde, 0x35, 0xb5, 0x2f, 0x58, 0x13, 0x92, 0xe3, 0x09, + 0x5b, 0xad, 0xb1, 0x20, 0x95, 0xe4, 0xad, 0x4e, 0xdf, 0xc1, 0xa0, 0x40, 0x9d, 0x95, 0x63, 0x55, + 0x27, 0xf9, 0x02, 0xe1, 0x6e, 0x58, 0x2a, 0xa9, 0x30, 0x09, 0x97, 0x8c, 0x49, 0x85, 0x49, 0x5d, + 0x31, 0x98, 0xbd, 0xc0, 0x20, 0xff, 0x9b, 0xcc, 0xa5, 0x87, 0x4c, 0x3e, 0x42, 0x78, 0x4f, 0xa8, + 0x3c, 0x4b, 0xfa, 0x6e, 0x47, 0x15, 0x79, 0x49, 0xdf, 0xed, 0xc8, 0xba, 0x2f, 0x7b, 0x98, 0xc1, + 0x1f, 0x23, 0x23, 0x91, 0xf0, 0x79, 0x9d, 0x37, 0xb7, 0xf4, 0xe8, 0x79, 0x06, 0x3d, 0x7e, 0x9e, + 0x41, 0x3f, 0x3d, 0xcf, 0xa0, 0x0f, 0x36, 0x32, 0x6d, 0x8f, 0x37, 0x32, 0x6d, 0x3f, 0x6c, 0x64, + 0xda, 0x6e, 0xfc, 0xa3, 0x68, 0xb8, 0xcb, 0x95, 0xbc, 0xac, 0x5b, 0x25, 0x05, 0xfe, 0x49, 0xc5, + 0xc8, 0xeb, 0xc7, 0x8b, 0x96, 0x52, 0x9d, 0x55, 0x4a, 0x56, 0xa1, 0xb2, 0x4a, 0x1d, 0xee, 0xf5, + 0xc4, 0xc9, 0xe3, 0xc2, 0xb1, 0x7b, 0xd7, 0xa6, 0x4e, 0xbe, 0x8b, 0xfd, 0xb5, 0x70, 0xe6, 0xf7, + 0x00, 0x00, 0x00, 0xff, 0xff, 0xe0, 0x50, 0xcd, 0xd6, 0x34, 0x23, 0x00, 0x00, } // Reference imports to suppress errors if they are not otherwise used. @@ -1979,6 +2313,12 @@ type QueryClient interface { NextSequenceReceive(ctx context.Context, in *QueryNextSequenceReceiveRequest, opts ...grpc.CallOption) (*QueryNextSequenceReceiveResponse, error) // NextSequenceSend returns the next send sequence for a given channel. NextSequenceSend(ctx context.Context, in *QueryNextSequenceSendRequest, opts ...grpc.CallOption) (*QueryNextSequenceSendResponse, error) + // UpgradeError returns the error receipt if the upgrade handshake failed. + UpgradeError(ctx context.Context, in *QueryUpgradeErrorRequest, opts ...grpc.CallOption) (*QueryUpgradeErrorResponse, error) + // Upgrade returns the upgrade for a given port and channel id. + Upgrade(ctx context.Context, in *QueryUpgradeRequest, opts ...grpc.CallOption) (*QueryUpgradeResponse, error) + // ChannelParams queries all parameters of the ibc channel submodule. + ChannelParams(ctx context.Context, in *QueryChannelParamsRequest, opts ...grpc.CallOption) (*QueryChannelParamsResponse, error) } type queryClient struct { @@ -2115,6 +2455,33 @@ func (c *queryClient) NextSequenceSend(ctx context.Context, in *QueryNextSequenc return out, nil } +func (c *queryClient) UpgradeError(ctx context.Context, in *QueryUpgradeErrorRequest, opts ...grpc.CallOption) (*QueryUpgradeErrorResponse, error) { + out := new(QueryUpgradeErrorResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Query/UpgradeError", in, out, opts...) + if err != nil { + return nil, err + } + return out, nil +} + +func (c *queryClient) Upgrade(ctx context.Context, in *QueryUpgradeRequest, opts ...grpc.CallOption) (*QueryUpgradeResponse, error) { + out := new(QueryUpgradeResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Query/Upgrade", in, out, opts...) + if err != nil { + return nil, err + } + return out, nil +} + +func (c *queryClient) ChannelParams(ctx context.Context, in *QueryChannelParamsRequest, opts ...grpc.CallOption) (*QueryChannelParamsResponse, error) { + out := new(QueryChannelParamsResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Query/ChannelParams", in, out, opts...) + if err != nil { + return nil, err + } + return out, nil +} + // QueryServer is the server API for Query service. type QueryServer interface { // Channel queries an IBC Channel. @@ -2153,6 +2520,12 @@ type QueryServer interface { NextSequenceReceive(context.Context, *QueryNextSequenceReceiveRequest) (*QueryNextSequenceReceiveResponse, error) // NextSequenceSend returns the next send sequence for a given channel. NextSequenceSend(context.Context, *QueryNextSequenceSendRequest) (*QueryNextSequenceSendResponse, error) + // UpgradeError returns the error receipt if the upgrade handshake failed. + UpgradeError(context.Context, *QueryUpgradeErrorRequest) (*QueryUpgradeErrorResponse, error) + // Upgrade returns the upgrade for a given port and channel id. + Upgrade(context.Context, *QueryUpgradeRequest) (*QueryUpgradeResponse, error) + // ChannelParams queries all parameters of the ibc channel submodule. + ChannelParams(context.Context, *QueryChannelParamsRequest) (*QueryChannelParamsResponse, error) } // UnimplementedQueryServer can be embedded to have forward compatible implementations. @@ -2201,6 +2574,15 @@ func (*UnimplementedQueryServer) NextSequenceReceive(ctx context.Context, req *Q func (*UnimplementedQueryServer) NextSequenceSend(ctx context.Context, req *QueryNextSequenceSendRequest) (*QueryNextSequenceSendResponse, error) { return nil, status.Errorf(codes.Unimplemented, "method NextSequenceSend not implemented") } +func (*UnimplementedQueryServer) UpgradeError(ctx context.Context, req *QueryUpgradeErrorRequest) (*QueryUpgradeErrorResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method UpgradeError not implemented") +} +func (*UnimplementedQueryServer) Upgrade(ctx context.Context, req *QueryUpgradeRequest) (*QueryUpgradeResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method Upgrade not implemented") +} +func (*UnimplementedQueryServer) ChannelParams(ctx context.Context, req *QueryChannelParamsRequest) (*QueryChannelParamsResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelParams not implemented") +} func RegisterQueryServer(s grpc1.Server, srv QueryServer) { s.RegisterService(&_Query_serviceDesc, srv) @@ -2458,44 +2840,98 @@ func _Query_NextSequenceSend_Handler(srv interface{}, ctx context.Context, dec f return interceptor(ctx, in, info, handler) } -var _Query_serviceDesc = grpc.ServiceDesc{ - ServiceName: "ibc.core.channel.v1.Query", - HandlerType: (*QueryServer)(nil), - Methods: []grpc.MethodDesc{ - { - MethodName: "Channel", - Handler: _Query_Channel_Handler, - }, - { - MethodName: "Channels", - Handler: _Query_Channels_Handler, - }, - { - MethodName: "ConnectionChannels", - Handler: _Query_ConnectionChannels_Handler, - }, - { - MethodName: "ChannelClientState", - Handler: _Query_ChannelClientState_Handler, - }, - { - MethodName: "ChannelConsensusState", - Handler: _Query_ChannelConsensusState_Handler, - }, - { - MethodName: "PacketCommitment", - Handler: _Query_PacketCommitment_Handler, - }, - { - MethodName: "PacketCommitments", - Handler: _Query_PacketCommitments_Handler, - }, - { - MethodName: "PacketReceipt", - Handler: _Query_PacketReceipt_Handler, - }, - { - MethodName: "PacketAcknowledgement", +func _Query_UpgradeError_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(QueryUpgradeErrorRequest) + if err := dec(in); err != nil { + return nil, err + } + if interceptor == nil { + return srv.(QueryServer).UpgradeError(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Query/UpgradeError", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(QueryServer).UpgradeError(ctx, req.(*QueryUpgradeErrorRequest)) + } + return interceptor(ctx, in, info, handler) +} + +func _Query_Upgrade_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(QueryUpgradeRequest) + if err := dec(in); err != nil { + return nil, err + } + if interceptor == nil { + return srv.(QueryServer).Upgrade(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Query/Upgrade", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(QueryServer).Upgrade(ctx, req.(*QueryUpgradeRequest)) + } + return interceptor(ctx, in, info, handler) +} + +func _Query_ChannelParams_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(QueryChannelParamsRequest) + if err := dec(in); err != nil { + return nil, err + } + if interceptor == nil { + return srv.(QueryServer).ChannelParams(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Query/ChannelParams", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(QueryServer).ChannelParams(ctx, req.(*QueryChannelParamsRequest)) + } + return interceptor(ctx, in, info, handler) +} + +var _Query_serviceDesc = grpc.ServiceDesc{ + ServiceName: "ibc.core.channel.v1.Query", + HandlerType: (*QueryServer)(nil), + Methods: []grpc.MethodDesc{ + { + MethodName: "Channel", + Handler: _Query_Channel_Handler, + }, + { + MethodName: "Channels", + Handler: _Query_Channels_Handler, + }, + { + MethodName: "ConnectionChannels", + Handler: _Query_ConnectionChannels_Handler, + }, + { + MethodName: "ChannelClientState", + Handler: _Query_ChannelClientState_Handler, + }, + { + MethodName: "ChannelConsensusState", + Handler: _Query_ChannelConsensusState_Handler, + }, + { + MethodName: "PacketCommitment", + Handler: _Query_PacketCommitment_Handler, + }, + { + MethodName: "PacketCommitments", + Handler: _Query_PacketCommitments_Handler, + }, + { + MethodName: "PacketReceipt", + Handler: _Query_PacketReceipt_Handler, + }, + { + MethodName: "PacketAcknowledgement", Handler: _Query_PacketAcknowledgement_Handler, }, { @@ -2518,6 +2954,18 @@ var _Query_serviceDesc = grpc.ServiceDesc{ MethodName: "NextSequenceSend", Handler: _Query_NextSequenceSend_Handler, }, + { + MethodName: "UpgradeError", + Handler: _Query_UpgradeError_Handler, + }, + { + MethodName: "Upgrade", + Handler: _Query_Upgrade_Handler, + }, + { + MethodName: "ChannelParams", + Handler: _Query_ChannelParams_Handler, + }, }, Streams: []grpc.StreamDesc{}, Metadata: "ibc/core/channel/v1/query.proto", @@ -3882,115 +4330,347 @@ func (m *QueryNextSequenceSendResponse) MarshalToSizedBuffer(dAtA []byte) (int, return len(dAtA) - i, nil } -func encodeVarintQuery(dAtA []byte, offset int, v uint64) int { - offset -= sovQuery(v) - base := offset - for v >= 1<<7 { - dAtA[offset] = uint8(v&0x7f | 0x80) - v >>= 7 - offset++ +func (m *QueryUpgradeErrorRequest) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err } - dAtA[offset] = uint8(v) - return base + return dAtA[:n], nil } -func (m *QueryChannelRequest) Size() (n int) { - if m == nil { - return 0 - } - var l int - _ = l - l = len(m.PortId) - if l > 0 { - n += 1 + l + sovQuery(uint64(l)) - } - l = len(m.ChannelId) - if l > 0 { - n += 1 + l + sovQuery(uint64(l)) - } - return n + +func (m *QueryUpgradeErrorRequest) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) } -func (m *QueryChannelResponse) Size() (n int) { - if m == nil { - return 0 - } +func (m *QueryUpgradeErrorRequest) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i var l int _ = l - if m.Channel != nil { - l = m.Channel.Size() - n += 1 + l + sovQuery(uint64(l)) + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintQuery(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 } - l = len(m.Proof) - if l > 0 { - n += 1 + l + sovQuery(uint64(l)) + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintQuery(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa } - l = m.ProofHeight.Size() - n += 1 + l + sovQuery(uint64(l)) - return n + return len(dAtA) - i, nil } -func (m *QueryChannelsRequest) Size() (n int) { - if m == nil { - return 0 - } - var l int - _ = l - if m.Pagination != nil { - l = m.Pagination.Size() - n += 1 + l + sovQuery(uint64(l)) +func (m *QueryUpgradeErrorResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err } - return n + return dAtA[:n], nil } -func (m *QueryChannelsResponse) Size() (n int) { - if m == nil { - return 0 - } +func (m *QueryUpgradeErrorResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *QueryUpgradeErrorResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i var l int _ = l - if len(m.Channels) > 0 { - for _, e := range m.Channels { - l = e.Size() - n += 1 + l + sovQuery(uint64(l)) + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err } + i -= size + i = encodeVarintQuery(dAtA, i, uint64(size)) } - if m.Pagination != nil { - l = m.Pagination.Size() - n += 1 + l + sovQuery(uint64(l)) + i-- + dAtA[i] = 0x1a + if len(m.Proof) > 0 { + i -= len(m.Proof) + copy(dAtA[i:], m.Proof) + i = encodeVarintQuery(dAtA, i, uint64(len(m.Proof))) + i-- + dAtA[i] = 0x12 } - l = m.Height.Size() - n += 1 + l + sovQuery(uint64(l)) - return n + { + size, err := m.ErrorReceipt.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintQuery(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil } -func (m *QueryConnectionChannelsRequest) Size() (n int) { - if m == nil { - return 0 +func (m *QueryUpgradeRequest) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err } + return dAtA[:n], nil +} + +func (m *QueryUpgradeRequest) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *QueryUpgradeRequest) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i var l int _ = l - l = len(m.Connection) - if l > 0 { - n += 1 + l + sovQuery(uint64(l)) + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintQuery(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 } - if m.Pagination != nil { - l = m.Pagination.Size() - n += 1 + l + sovQuery(uint64(l)) + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintQuery(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa } - return n + return len(dAtA) - i, nil } -func (m *QueryConnectionChannelsResponse) Size() (n int) { - if m == nil { - return 0 - } - var l int - _ = l - if len(m.Channels) > 0 { - for _, e := range m.Channels { - l = e.Size() - n += 1 + l + sovQuery(uint64(l)) - } +func (m *QueryUpgradeResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *QueryUpgradeResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *QueryUpgradeResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintQuery(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x1a + if len(m.Proof) > 0 { + i -= len(m.Proof) + copy(dAtA[i:], m.Proof) + i = encodeVarintQuery(dAtA, i, uint64(len(m.Proof))) + i-- + dAtA[i] = 0x12 + } + { + size, err := m.Upgrade.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintQuery(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil +} + +func (m *QueryChannelParamsRequest) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *QueryChannelParamsRequest) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *QueryChannelParamsRequest) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + return len(dAtA) - i, nil +} + +func (m *QueryChannelParamsResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *QueryChannelParamsResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *QueryChannelParamsResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.Params != nil { + { + size, err := m.Params.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintQuery(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func encodeVarintQuery(dAtA []byte, offset int, v uint64) int { + offset -= sovQuery(v) + base := offset + for v >= 1<<7 { + dAtA[offset] = uint8(v&0x7f | 0x80) + v >>= 7 + offset++ + } + dAtA[offset] = uint8(v) + return base +} +func (m *QueryChannelRequest) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovQuery(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovQuery(uint64(l)) + } + return n +} + +func (m *QueryChannelResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.Channel != nil { + l = m.Channel.Size() + n += 1 + l + sovQuery(uint64(l)) + } + l = len(m.Proof) + if l > 0 { + n += 1 + l + sovQuery(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovQuery(uint64(l)) + return n +} + +func (m *QueryChannelsRequest) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.Pagination != nil { + l = m.Pagination.Size() + n += 1 + l + sovQuery(uint64(l)) + } + return n +} + +func (m *QueryChannelsResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if len(m.Channels) > 0 { + for _, e := range m.Channels { + l = e.Size() + n += 1 + l + sovQuery(uint64(l)) + } + } + if m.Pagination != nil { + l = m.Pagination.Size() + n += 1 + l + sovQuery(uint64(l)) + } + l = m.Height.Size() + n += 1 + l + sovQuery(uint64(l)) + return n +} + +func (m *QueryConnectionChannelsRequest) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.Connection) + if l > 0 { + n += 1 + l + sovQuery(uint64(l)) + } + if m.Pagination != nil { + l = m.Pagination.Size() + n += 1 + l + sovQuery(uint64(l)) + } + return n +} + +func (m *QueryConnectionChannelsResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if len(m.Channels) > 0 { + for _, e := range m.Channels { + l = e.Size() + n += 1 + l + sovQuery(uint64(l)) + } } if m.Pagination != nil { l = m.Pagination.Size() @@ -4444,37 +5124,127 @@ func (m *QueryNextSequenceSendResponse) Size() (n int) { return n } -func sovQuery(x uint64) (n int) { - return (math_bits.Len64(x|1) + 6) / 7 +func (m *QueryUpgradeErrorRequest) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovQuery(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovQuery(uint64(l)) + } + return n } -func sozQuery(x uint64) (n int) { - return sovQuery(uint64((x << 1) ^ uint64((int64(x) >> 63)))) + +func (m *QueryUpgradeErrorResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = m.ErrorReceipt.Size() + n += 1 + l + sovQuery(uint64(l)) + l = len(m.Proof) + if l > 0 { + n += 1 + l + sovQuery(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovQuery(uint64(l)) + return n } -func (m *QueryChannelRequest) Unmarshal(dAtA []byte) error { - l := len(dAtA) - iNdEx := 0 - for iNdEx < l { - preIndex := iNdEx - var wire uint64 - for shift := uint(0); ; shift += 7 { - if shift >= 64 { - return ErrIntOverflowQuery - } - if iNdEx >= l { - return io.ErrUnexpectedEOF - } - b := dAtA[iNdEx] - iNdEx++ - wire |= uint64(b&0x7F) << shift - if b < 0x80 { - break - } - } - fieldNum := int32(wire >> 3) - wireType := int(wire & 0x7) - if wireType == 4 { - return fmt.Errorf("proto: QueryChannelRequest: wiretype end group for non-group") - } + +func (m *QueryUpgradeRequest) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovQuery(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovQuery(uint64(l)) + } + return n +} + +func (m *QueryUpgradeResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = m.Upgrade.Size() + n += 1 + l + sovQuery(uint64(l)) + l = len(m.Proof) + if l > 0 { + n += 1 + l + sovQuery(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovQuery(uint64(l)) + return n +} + +func (m *QueryChannelParamsRequest) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + return n +} + +func (m *QueryChannelParamsResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.Params != nil { + l = m.Params.Size() + n += 1 + l + sovQuery(uint64(l)) + } + return n +} + +func sovQuery(x uint64) (n int) { + return (math_bits.Len64(x|1) + 6) / 7 +} +func sozQuery(x uint64) (n int) { + return sovQuery(uint64((x << 1) ^ uint64((int64(x) >> 63)))) +} +func (m *QueryChannelRequest) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: QueryChannelRequest: wiretype end group for non-group") + } if fieldNum <= 0 { return fmt.Errorf("proto: QueryChannelRequest: illegal tag %d (wire type %d)", fieldNum, wire) } @@ -7960,44 +8730,544 @@ func (m *QueryUnreceivedAcksResponse) Unmarshal(dAtA []byte) error { if postIndex < 0 { return ErrInvalidLengthQuery } - if postIndex > l { + if postIndex > l { + return io.ErrUnexpectedEOF + } + var elementCount int + var count int + for _, integer := range dAtA[iNdEx:postIndex] { + if integer < 128 { + count++ + } + } + elementCount = count + if elementCount != 0 && len(m.Sequences) == 0 { + m.Sequences = make([]uint64, 0, elementCount) + } + for iNdEx < postIndex { + var v uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + v |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + m.Sequences = append(m.Sequences, v) + } + } else { + return fmt.Errorf("proto: wrong wireType = %d for field Sequences", wireType) + } + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Height", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthQuery + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthQuery + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.Height.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipQuery(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthQuery + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *QueryNextSequenceReceiveRequest) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: QueryNextSequenceReceiveRequest: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: QueryNextSequenceReceiveRequest: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthQuery + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthQuery + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.PortId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthQuery + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthQuery + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ChannelId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipQuery(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthQuery + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *QueryNextSequenceReceiveResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: QueryNextSequenceReceiveResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: QueryNextSequenceReceiveResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field NextSequenceReceive", wireType) + } + m.NextSequenceReceive = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.NextSequenceReceive |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Proof", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if byteLen < 0 { + return ErrInvalidLengthQuery + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthQuery + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Proof = append(m.Proof[:0], dAtA[iNdEx:postIndex]...) + if m.Proof == nil { + m.Proof = []byte{} + } + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthQuery + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthQuery + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipQuery(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthQuery + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *QueryNextSequenceSendRequest) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: QueryNextSequenceSendRequest: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: QueryNextSequenceSendRequest: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthQuery + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthQuery + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.PortId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthQuery + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthQuery + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ChannelId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipQuery(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthQuery + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *QueryNextSequenceSendResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: QueryNextSequenceSendResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: QueryNextSequenceSendResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field NextSequenceSend", wireType) + } + m.NextSequenceSend = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { return io.ErrUnexpectedEOF } - var elementCount int - var count int - for _, integer := range dAtA[iNdEx:postIndex] { - if integer < 128 { - count++ - } + b := dAtA[iNdEx] + iNdEx++ + m.NextSequenceSend |= uint64(b&0x7F) << shift + if b < 0x80 { + break } - elementCount = count - if elementCount != 0 && len(m.Sequences) == 0 { - m.Sequences = make([]uint64, 0, elementCount) + } + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Proof", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery } - for iNdEx < postIndex { - var v uint64 - for shift := uint(0); ; shift += 7 { - if shift >= 64 { - return ErrIntOverflowQuery - } - if iNdEx >= l { - return io.ErrUnexpectedEOF - } - b := dAtA[iNdEx] - iNdEx++ - v |= uint64(b&0x7F) << shift - if b < 0x80 { - break - } - } - m.Sequences = append(m.Sequences, v) + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break } - } else { - return fmt.Errorf("proto: wrong wireType = %d for field Sequences", wireType) } - case 2: + if byteLen < 0 { + return ErrInvalidLengthQuery + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthQuery + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Proof = append(m.Proof[:0], dAtA[iNdEx:postIndex]...) + if m.Proof == nil { + m.Proof = []byte{} + } + iNdEx = postIndex + case 3: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Height", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) } var msglen int for shift := uint(0); ; shift += 7 { @@ -8024,7 +9294,7 @@ func (m *QueryUnreceivedAcksResponse) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - if err := m.Height.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { return err } iNdEx = postIndex @@ -8049,7 +9319,7 @@ func (m *QueryUnreceivedAcksResponse) Unmarshal(dAtA []byte) error { } return nil } -func (m *QueryNextSequenceReceiveRequest) Unmarshal(dAtA []byte) error { +func (m *QueryUpgradeErrorRequest) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -8072,10 +9342,10 @@ func (m *QueryNextSequenceReceiveRequest) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: QueryNextSequenceReceiveRequest: wiretype end group for non-group") + return fmt.Errorf("proto: QueryUpgradeErrorRequest: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: QueryNextSequenceReceiveRequest: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: QueryUpgradeErrorRequest: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: @@ -8163,7 +9433,7 @@ func (m *QueryNextSequenceReceiveRequest) Unmarshal(dAtA []byte) error { } return nil } -func (m *QueryNextSequenceReceiveResponse) Unmarshal(dAtA []byte) error { +func (m *QueryUpgradeErrorResponse) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -8186,17 +9456,17 @@ func (m *QueryNextSequenceReceiveResponse) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: QueryNextSequenceReceiveResponse: wiretype end group for non-group") + return fmt.Errorf("proto: QueryUpgradeErrorResponse: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: QueryNextSequenceReceiveResponse: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: QueryUpgradeErrorResponse: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: - if wireType != 0 { - return fmt.Errorf("proto: wrong wireType = %d for field NextSequenceReceive", wireType) + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ErrorReceipt", wireType) } - m.NextSequenceReceive = 0 + var msglen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowQuery @@ -8206,11 +9476,25 @@ func (m *QueryNextSequenceReceiveResponse) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - m.NextSequenceReceive |= uint64(b&0x7F) << shift + msglen |= int(b&0x7F) << shift if b < 0x80 { break } } + if msglen < 0 { + return ErrInvalidLengthQuery + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthQuery + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.ErrorReceipt.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex case 2: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field Proof", wireType) @@ -8299,7 +9583,7 @@ func (m *QueryNextSequenceReceiveResponse) Unmarshal(dAtA []byte) error { } return nil } -func (m *QueryNextSequenceSendRequest) Unmarshal(dAtA []byte) error { +func (m *QueryUpgradeRequest) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -8322,10 +9606,10 @@ func (m *QueryNextSequenceSendRequest) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: QueryNextSequenceSendRequest: wiretype end group for non-group") + return fmt.Errorf("proto: QueryUpgradeRequest: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: QueryNextSequenceSendRequest: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: QueryUpgradeRequest: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: @@ -8413,7 +9697,7 @@ func (m *QueryNextSequenceSendRequest) Unmarshal(dAtA []byte) error { } return nil } -func (m *QueryNextSequenceSendResponse) Unmarshal(dAtA []byte) error { +func (m *QueryUpgradeResponse) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -8436,17 +9720,17 @@ func (m *QueryNextSequenceSendResponse) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: QueryNextSequenceSendResponse: wiretype end group for non-group") + return fmt.Errorf("proto: QueryUpgradeResponse: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: QueryNextSequenceSendResponse: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: QueryUpgradeResponse: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: - if wireType != 0 { - return fmt.Errorf("proto: wrong wireType = %d for field NextSequenceSend", wireType) + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Upgrade", wireType) } - m.NextSequenceSend = 0 + var msglen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowQuery @@ -8456,11 +9740,25 @@ func (m *QueryNextSequenceSendResponse) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - m.NextSequenceSend |= uint64(b&0x7F) << shift + msglen |= int(b&0x7F) << shift if b < 0x80 { break } } + if msglen < 0 { + return ErrInvalidLengthQuery + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthQuery + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.Upgrade.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex case 2: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field Proof", wireType) @@ -8549,6 +9847,142 @@ func (m *QueryNextSequenceSendResponse) Unmarshal(dAtA []byte) error { } return nil } +func (m *QueryChannelParamsRequest) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: QueryChannelParamsRequest: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: QueryChannelParamsRequest: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + default: + iNdEx = preIndex + skippy, err := skipQuery(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthQuery + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *QueryChannelParamsResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: QueryChannelParamsResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: QueryChannelParamsResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Params", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowQuery + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthQuery + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthQuery + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if m.Params == nil { + m.Params = &Params{} + } + if err := m.Params.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipQuery(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthQuery + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} func skipQuery(dAtA []byte) (n int, err error) { l := len(dAtA) iNdEx := 0 diff --git a/modules/core/04-channel/types/query.pb.gw.go b/modules/core/04-channel/types/query.pb.gw.go index 2f9c58f146d..bce31252f8b 100644 --- a/modules/core/04-channel/types/query.pb.gw.go +++ b/modules/core/04-channel/types/query.pb.gw.go @@ -1243,6 +1243,176 @@ func local_request_Query_NextSequenceSend_0(ctx context.Context, marshaler runti } +func request_Query_UpgradeError_0(ctx context.Context, marshaler runtime.Marshaler, client QueryClient, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) { + var protoReq QueryUpgradeErrorRequest + var metadata runtime.ServerMetadata + + var ( + val string + ok bool + err error + _ = err + ) + + val, ok = pathParams["channel_id"] + if !ok { + return nil, metadata, status.Errorf(codes.InvalidArgument, "missing parameter %s", "channel_id") + } + + protoReq.ChannelId, err = runtime.String(val) + + if err != nil { + return nil, metadata, status.Errorf(codes.InvalidArgument, "type mismatch, parameter: %s, error: %v", "channel_id", err) + } + + val, ok = pathParams["port_id"] + if !ok { + return nil, metadata, status.Errorf(codes.InvalidArgument, "missing parameter %s", "port_id") + } + + protoReq.PortId, err = runtime.String(val) + + if err != nil { + return nil, metadata, status.Errorf(codes.InvalidArgument, "type mismatch, parameter: %s, error: %v", "port_id", err) + } + + msg, err := client.UpgradeError(ctx, &protoReq, grpc.Header(&metadata.HeaderMD), grpc.Trailer(&metadata.TrailerMD)) + return msg, metadata, err + +} + +func local_request_Query_UpgradeError_0(ctx context.Context, marshaler runtime.Marshaler, server QueryServer, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) { + var protoReq QueryUpgradeErrorRequest + var metadata runtime.ServerMetadata + + var ( + val string + ok bool + err error + _ = err + ) + + val, ok = pathParams["channel_id"] + if !ok { + return nil, metadata, status.Errorf(codes.InvalidArgument, "missing parameter %s", "channel_id") + } + + protoReq.ChannelId, err = runtime.String(val) + + if err != nil { + return nil, metadata, status.Errorf(codes.InvalidArgument, "type mismatch, parameter: %s, error: %v", "channel_id", err) + } + + val, ok = pathParams["port_id"] + if !ok { + return nil, metadata, status.Errorf(codes.InvalidArgument, "missing parameter %s", "port_id") + } + + protoReq.PortId, err = runtime.String(val) + + if err != nil { + return nil, metadata, status.Errorf(codes.InvalidArgument, "type mismatch, parameter: %s, error: %v", "port_id", err) + } + + msg, err := server.UpgradeError(ctx, &protoReq) + return msg, metadata, err + +} + +func request_Query_Upgrade_0(ctx context.Context, marshaler runtime.Marshaler, client QueryClient, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) { + var protoReq QueryUpgradeRequest + var metadata runtime.ServerMetadata + + var ( + val string + ok bool + err error + _ = err + ) + + val, ok = pathParams["channel_id"] + if !ok { + return nil, metadata, status.Errorf(codes.InvalidArgument, "missing parameter %s", "channel_id") + } + + protoReq.ChannelId, err = runtime.String(val) + + if err != nil { + return nil, metadata, status.Errorf(codes.InvalidArgument, "type mismatch, parameter: %s, error: %v", "channel_id", err) + } + + val, ok = pathParams["port_id"] + if !ok { + return nil, metadata, status.Errorf(codes.InvalidArgument, "missing parameter %s", "port_id") + } + + protoReq.PortId, err = runtime.String(val) + + if err != nil { + return nil, metadata, status.Errorf(codes.InvalidArgument, "type mismatch, parameter: %s, error: %v", "port_id", err) + } + + msg, err := client.Upgrade(ctx, &protoReq, grpc.Header(&metadata.HeaderMD), grpc.Trailer(&metadata.TrailerMD)) + return msg, metadata, err + +} + +func local_request_Query_Upgrade_0(ctx context.Context, marshaler runtime.Marshaler, server QueryServer, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) { + var protoReq QueryUpgradeRequest + var metadata runtime.ServerMetadata + + var ( + val string + ok bool + err error + _ = err + ) + + val, ok = pathParams["channel_id"] + if !ok { + return nil, metadata, status.Errorf(codes.InvalidArgument, "missing parameter %s", "channel_id") + } + + protoReq.ChannelId, err = runtime.String(val) + + if err != nil { + return nil, metadata, status.Errorf(codes.InvalidArgument, "type mismatch, parameter: %s, error: %v", "channel_id", err) + } + + val, ok = pathParams["port_id"] + if !ok { + return nil, metadata, status.Errorf(codes.InvalidArgument, "missing parameter %s", "port_id") + } + + protoReq.PortId, err = runtime.String(val) + + if err != nil { + return nil, metadata, status.Errorf(codes.InvalidArgument, "type mismatch, parameter: %s, error: %v", "port_id", err) + } + + msg, err := server.Upgrade(ctx, &protoReq) + return msg, metadata, err + +} + +func request_Query_ChannelParams_0(ctx context.Context, marshaler runtime.Marshaler, client QueryClient, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) { + var protoReq QueryChannelParamsRequest + var metadata runtime.ServerMetadata + + msg, err := client.ChannelParams(ctx, &protoReq, grpc.Header(&metadata.HeaderMD), grpc.Trailer(&metadata.TrailerMD)) + return msg, metadata, err + +} + +func local_request_Query_ChannelParams_0(ctx context.Context, marshaler runtime.Marshaler, server QueryServer, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) { + var protoReq QueryChannelParamsRequest + var metadata runtime.ServerMetadata + + msg, err := server.ChannelParams(ctx, &protoReq) + return msg, metadata, err + +} + // RegisterQueryHandlerServer registers the http handlers for service Query to "mux". // UnaryRPC :call QueryServer directly. // StreamingRPC :currently unsupported pending https://github.com/grpc/grpc-go/issues/906. @@ -1571,6 +1741,75 @@ func RegisterQueryHandlerServer(ctx context.Context, mux *runtime.ServeMux, serv }) + mux.Handle("GET", pattern_Query_UpgradeError_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) { + ctx, cancel := context.WithCancel(req.Context()) + defer cancel() + var stream runtime.ServerTransportStream + ctx = grpc.NewContextWithServerTransportStream(ctx, &stream) + inboundMarshaler, outboundMarshaler := runtime.MarshalerForRequest(mux, req) + rctx, err := runtime.AnnotateIncomingContext(ctx, mux, req) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + resp, md, err := local_request_Query_UpgradeError_0(rctx, inboundMarshaler, server, req, pathParams) + md.HeaderMD, md.TrailerMD = metadata.Join(md.HeaderMD, stream.Header()), metadata.Join(md.TrailerMD, stream.Trailer()) + ctx = runtime.NewServerMetadataContext(ctx, md) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + + forward_Query_UpgradeError_0(ctx, mux, outboundMarshaler, w, req, resp, mux.GetForwardResponseOptions()...) + + }) + + mux.Handle("GET", pattern_Query_Upgrade_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) { + ctx, cancel := context.WithCancel(req.Context()) + defer cancel() + var stream runtime.ServerTransportStream + ctx = grpc.NewContextWithServerTransportStream(ctx, &stream) + inboundMarshaler, outboundMarshaler := runtime.MarshalerForRequest(mux, req) + rctx, err := runtime.AnnotateIncomingContext(ctx, mux, req) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + resp, md, err := local_request_Query_Upgrade_0(rctx, inboundMarshaler, server, req, pathParams) + md.HeaderMD, md.TrailerMD = metadata.Join(md.HeaderMD, stream.Header()), metadata.Join(md.TrailerMD, stream.Trailer()) + ctx = runtime.NewServerMetadataContext(ctx, md) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + + forward_Query_Upgrade_0(ctx, mux, outboundMarshaler, w, req, resp, mux.GetForwardResponseOptions()...) + + }) + + mux.Handle("GET", pattern_Query_ChannelParams_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) { + ctx, cancel := context.WithCancel(req.Context()) + defer cancel() + var stream runtime.ServerTransportStream + ctx = grpc.NewContextWithServerTransportStream(ctx, &stream) + inboundMarshaler, outboundMarshaler := runtime.MarshalerForRequest(mux, req) + rctx, err := runtime.AnnotateIncomingContext(ctx, mux, req) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + resp, md, err := local_request_Query_ChannelParams_0(rctx, inboundMarshaler, server, req, pathParams) + md.HeaderMD, md.TrailerMD = metadata.Join(md.HeaderMD, stream.Header()), metadata.Join(md.TrailerMD, stream.Trailer()) + ctx = runtime.NewServerMetadataContext(ctx, md) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + + forward_Query_ChannelParams_0(ctx, mux, outboundMarshaler, w, req, resp, mux.GetForwardResponseOptions()...) + + }) + return nil } @@ -1892,6 +2131,66 @@ func RegisterQueryHandlerClient(ctx context.Context, mux *runtime.ServeMux, clie }) + mux.Handle("GET", pattern_Query_UpgradeError_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) { + ctx, cancel := context.WithCancel(req.Context()) + defer cancel() + inboundMarshaler, outboundMarshaler := runtime.MarshalerForRequest(mux, req) + rctx, err := runtime.AnnotateContext(ctx, mux, req) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + resp, md, err := request_Query_UpgradeError_0(rctx, inboundMarshaler, client, req, pathParams) + ctx = runtime.NewServerMetadataContext(ctx, md) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + + forward_Query_UpgradeError_0(ctx, mux, outboundMarshaler, w, req, resp, mux.GetForwardResponseOptions()...) + + }) + + mux.Handle("GET", pattern_Query_Upgrade_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) { + ctx, cancel := context.WithCancel(req.Context()) + defer cancel() + inboundMarshaler, outboundMarshaler := runtime.MarshalerForRequest(mux, req) + rctx, err := runtime.AnnotateContext(ctx, mux, req) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + resp, md, err := request_Query_Upgrade_0(rctx, inboundMarshaler, client, req, pathParams) + ctx = runtime.NewServerMetadataContext(ctx, md) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + + forward_Query_Upgrade_0(ctx, mux, outboundMarshaler, w, req, resp, mux.GetForwardResponseOptions()...) + + }) + + mux.Handle("GET", pattern_Query_ChannelParams_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) { + ctx, cancel := context.WithCancel(req.Context()) + defer cancel() + inboundMarshaler, outboundMarshaler := runtime.MarshalerForRequest(mux, req) + rctx, err := runtime.AnnotateContext(ctx, mux, req) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + resp, md, err := request_Query_ChannelParams_0(rctx, inboundMarshaler, client, req, pathParams) + ctx = runtime.NewServerMetadataContext(ctx, md) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + + forward_Query_ChannelParams_0(ctx, mux, outboundMarshaler, w, req, resp, mux.GetForwardResponseOptions()...) + + }) + return nil } @@ -1923,6 +2222,12 @@ var ( pattern_Query_NextSequenceReceive_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3, 2, 4, 1, 0, 4, 1, 5, 5, 2, 6, 1, 0, 4, 1, 5, 7, 2, 8}, []string{"ibc", "core", "channel", "v1", "channels", "channel_id", "ports", "port_id", "next_sequence"}, "", runtime.AssumeColonVerbOpt(false))) pattern_Query_NextSequenceSend_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3, 2, 4, 1, 0, 4, 1, 5, 5, 2, 6, 1, 0, 4, 1, 5, 7, 2, 8}, []string{"ibc", "core", "channel", "v1", "channels", "channel_id", "ports", "port_id", "next_sequence_send"}, "", runtime.AssumeColonVerbOpt(false))) + + pattern_Query_UpgradeError_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3, 2, 4, 1, 0, 4, 1, 5, 5, 2, 6, 1, 0, 4, 1, 5, 7, 2, 8}, []string{"ibc", "core", "channel", "v1", "channels", "channel_id", "ports", "port_id", "upgrade_error"}, "", runtime.AssumeColonVerbOpt(false))) + + pattern_Query_Upgrade_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3, 2, 4, 1, 0, 4, 1, 5, 5, 2, 6, 1, 0, 4, 1, 5, 7, 2, 8}, []string{"ibc", "core", "channel", "v1", "channels", "channel_id", "ports", "port_id", "upgrade"}, "", runtime.AssumeColonVerbOpt(false))) + + pattern_Query_ChannelParams_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3, 2, 4}, []string{"ibc", "core", "channel", "v1", "params"}, "", runtime.AssumeColonVerbOpt(false))) ) var ( @@ -1953,4 +2258,10 @@ var ( forward_Query_NextSequenceReceive_0 = runtime.ForwardResponseMessage forward_Query_NextSequenceSend_0 = runtime.ForwardResponseMessage + + forward_Query_UpgradeError_0 = runtime.ForwardResponseMessage + + forward_Query_Upgrade_0 = runtime.ForwardResponseMessage + + forward_Query_ChannelParams_0 = runtime.ForwardResponseMessage ) diff --git a/modules/core/04-channel/types/timeout.go b/modules/core/04-channel/types/timeout.go new file mode 100644 index 00000000000..dc51c31a78a --- /dev/null +++ b/modules/core/04-channel/types/timeout.go @@ -0,0 +1,60 @@ +package types + +import ( + errorsmod "cosmossdk.io/errors" + + clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" +) + +// NewTimeout returns a new Timeout instance. +func NewTimeout(height clienttypes.Height, timestamp uint64) Timeout { + return Timeout{ + Height: height, + Timestamp: timestamp, + } +} + +// IsValid returns true if either the height or timestamp is non-zero. +func (t Timeout) IsValid() bool { + return !t.Height.IsZero() || t.Timestamp != 0 +} + +// Elapsed returns true if either the provided height or timestamp is past the +// respective absolute timeout values. +func (t Timeout) Elapsed(height clienttypes.Height, timestamp uint64) bool { + return t.heightElapsed(height) || t.timestampElapsed(timestamp) +} + +// ErrTimeoutElapsed returns a timeout elapsed error indicating which timeout value +// has elapsed. +func (t Timeout) ErrTimeoutElapsed(height clienttypes.Height, timestamp uint64) error { + if t.heightElapsed(height) { + return errorsmod.Wrapf(ErrTimeoutElapsed, "current height: %s, timeout height %s", height, t.Height) + } + + return errorsmod.Wrapf(ErrTimeoutElapsed, "current timestamp: %d, timeout timestamp %d", timestamp, t.Timestamp) +} + +// ErrTimeoutNotReached returns a timeout not reached error indicating which timeout value +// has not been reached. +func (t Timeout) ErrTimeoutNotReached(height clienttypes.Height, timestamp uint64) error { + // only return height information if the height is set + // t.heightElapsed() will return false when it is empty + if !t.Height.IsZero() && !t.heightElapsed(height) { + return errorsmod.Wrapf(ErrTimeoutNotReached, "current height: %s, timeout height %s", height, t.Height) + } + + return errorsmod.Wrapf(ErrTimeoutNotReached, "current timestamp: %d, timeout timestamp %d", timestamp, t.Timestamp) +} + +// heightElapsed returns true if the timeout height is non empty +// and the timeout height is greater than or equal to the relative height. +func (t Timeout) heightElapsed(height clienttypes.Height) bool { + return !t.Height.IsZero() && height.GTE(t.Height) +} + +// timestampElapsed returns true if the timeout timestamp is non empty +// and the timeout timestamp is greater than or equal to the relative timestamp. +func (t Timeout) timestampElapsed(timestamp uint64) bool { + return t.Timestamp != 0 && timestamp >= t.Timestamp +} diff --git a/modules/core/04-channel/types/timeout_test.go b/modules/core/04-channel/types/timeout_test.go new file mode 100644 index 00000000000..add2c3c876c --- /dev/null +++ b/modules/core/04-channel/types/timeout_test.go @@ -0,0 +1,238 @@ +package types_test + +import ( + errorsmod "cosmossdk.io/errors" + + clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" + "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" +) + +func (suite *TypesTestSuite) TestIsValid() { + var timeout types.Timeout + + testCases := []struct { + name string + malleate func() + expPass bool + }{ + { + "success: valid timeout with height and timestamp", + func() { + timeout = types.NewTimeout(clienttypes.NewHeight(1, 100), 100) + }, + true, + }, + { + "success: valid timeout with height and zero timestamp", + func() { + timeout = types.NewTimeout(clienttypes.NewHeight(1, 100), 0) + }, + true, + }, + { + "success: valid timeout with timestamp and zero height", + func() { + timeout = types.NewTimeout(clienttypes.ZeroHeight(), 100) + }, + true, + }, + { + "invalid timeout with zero height and zero timestamp", + func() { + timeout = types.NewTimeout(clienttypes.ZeroHeight(), 0) + }, + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + tc.malleate() + + isValid := timeout.IsValid() + if tc.expPass { + suite.Require().True(isValid) + } else { + suite.Require().False(isValid) + } + }) + } +} + +func (suite *TypesTestSuite) TestElapsed() { + // elapsed is expected to be true when either timeout height or timestamp + // is greater than or equal to 2 + var ( + height = clienttypes.NewHeight(0, 2) + timestamp = uint64(2) + ) + + testCases := []struct { + name string + timeout types.Timeout + expElapsed bool + }{ + { + "elapsed: both timeout with height and timestamp", + types.NewTimeout(height, timestamp), + true, + }, + { + "elapsed: timeout with height and zero timestamp", + types.NewTimeout(height, 0), + true, + }, + { + "elapsed: timeout with timestamp and zero height", + types.NewTimeout(clienttypes.ZeroHeight(), timestamp), + true, + }, + { + "elapsed: height elapsed, timestamp did not", + types.NewTimeout(height, timestamp+1), + true, + }, + { + "elapsed: timestamp elapsed, height did not", + types.NewTimeout(height.Increment().(clienttypes.Height), timestamp), + true, + }, + { + "elapsed: timestamp elapsed when less than current timestamp", + types.NewTimeout(clienttypes.ZeroHeight(), timestamp-1), + true, + }, + { + "elapsed: height elapsed when less than current height", + types.NewTimeout(clienttypes.NewHeight(0, 1), 0), + true, + }, + { + "not elapsed: invalid timeout", + types.NewTimeout(clienttypes.ZeroHeight(), 0), + false, + }, + { + "not elapsed: neither height nor timeout elapsed", + types.NewTimeout(height.Increment().(clienttypes.Height), timestamp+1), + false, + }, + { + "not elapsed: timeout not reached with height and zero timestamp", + types.NewTimeout(height.Increment().(clienttypes.Height), 0), + false, + }, + { + "elapsed: timeout not reached with timestamp and zero height", + types.NewTimeout(clienttypes.ZeroHeight(), timestamp+1), + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + elapsed := tc.timeout.Elapsed(height, timestamp) + suite.Require().Equal(tc.expElapsed, elapsed) + }) + } +} + +func (suite *TypesTestSuite) TestErrTimeoutElapsed() { + // elapsed is expected to be true when either timeout height or timestamp + // is greater than or equal to 2 + var ( + height = clienttypes.NewHeight(0, 2) + timestamp = uint64(2) + ) + + testCases := []struct { + name string + timeout types.Timeout + expError error + }{ + { + "both timeout with height and timestamp", + types.NewTimeout(height, timestamp), + errorsmod.Wrapf(types.ErrTimeoutElapsed, "current height: %s, timeout height %s", height, height), + }, + { + "timeout with height and zero timestamp", + types.NewTimeout(height, 0), + errorsmod.Wrapf(types.ErrTimeoutElapsed, "current height: %s, timeout height %s", height, height), + }, + { + "timeout with timestamp and zero height", + types.NewTimeout(clienttypes.ZeroHeight(), timestamp), + errorsmod.Wrapf(types.ErrTimeoutElapsed, "current timestamp: %d, timeout timestamp %d", timestamp, timestamp), + }, + { + "height elapsed, timestamp did not", + types.NewTimeout(height, timestamp+1), + errorsmod.Wrapf(types.ErrTimeoutElapsed, "current height: %s, timeout height %s", height, height), + }, + { + "timestamp elapsed, height did not", + types.NewTimeout(height.Increment().(clienttypes.Height), timestamp), + errorsmod.Wrapf(types.ErrTimeoutElapsed, "current timestamp: %d, timeout timestamp %d", timestamp, timestamp), + }, + { + "height elapsed when less than current height", + types.NewTimeout(clienttypes.NewHeight(0, 1), 0), + errorsmod.Wrapf(types.ErrTimeoutElapsed, "current height: %s, timeout height %s", height, clienttypes.NewHeight(0, 1)), + }, + { + "timestamp elapsed when less than current timestamp", + types.NewTimeout(clienttypes.ZeroHeight(), timestamp-1), + errorsmod.Wrapf(types.ErrTimeoutElapsed, "current timestamp: %d, timeout timestamp %d", timestamp, timestamp-1), + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + err := tc.timeout.ErrTimeoutElapsed(height, timestamp) + suite.Require().Equal(tc.expError.Error(), err.Error()) + }) + } +} + +func (suite *TypesTestSuite) TestErrTimeoutNotReached() { + // elapsed is expected to be true when either timeout height or timestamp + // is greater than or equal to 2 + var ( + height = clienttypes.NewHeight(0, 2) + timestamp = uint64(2) + ) + + testCases := []struct { + name string + timeout types.Timeout + expError error + }{ + { + "neither timeout reached with height and timestamp", + types.NewTimeout(height.Increment().(clienttypes.Height), timestamp+1), + errorsmod.Wrapf(types.ErrTimeoutNotReached, "current height: %s, timeout height %s", height, height.Increment().(clienttypes.Height)), + }, + { + "timeout not reached with height and zero timestamp", + types.NewTimeout(height.Increment().(clienttypes.Height), 0), + errorsmod.Wrapf(types.ErrTimeoutNotReached, "current height: %s, timeout height %s", height, height.Increment().(clienttypes.Height)), + }, + { + "timeout not reached with timestamp and zero height", + types.NewTimeout(clienttypes.ZeroHeight(), timestamp+1), + errorsmod.Wrapf(types.ErrTimeoutNotReached, "current timestamp: %d, timeout timestamp %d", timestamp, timestamp+1), + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + err := tc.timeout.ErrTimeoutNotReached(height, timestamp) + suite.Require().Equal(tc.expError.Error(), err.Error()) + }) + } +} diff --git a/modules/core/04-channel/types/tx.pb.go b/modules/core/04-channel/types/tx.pb.go index bd9cd757eb6..20560a7872f 100644 --- a/modules/core/04-channel/types/tx.pb.go +++ b/modules/core/04-channel/types/tx.pb.go @@ -40,18 +40,22 @@ const ( NOOP ResponseResultType = 1 // The message was executed successfully SUCCESS ResponseResultType = 2 + // The message was executed unsuccessfully + FAILURE ResponseResultType = 3 ) var ResponseResultType_name = map[int32]string{ 0: "RESPONSE_RESULT_TYPE_UNSPECIFIED", 1: "RESPONSE_RESULT_TYPE_NOOP", 2: "RESPONSE_RESULT_TYPE_SUCCESS", + 3: "RESPONSE_RESULT_TYPE_FAILURE", } var ResponseResultType_value = map[string]int32{ "RESPONSE_RESULT_TYPE_UNSPECIFIED": 0, "RESPONSE_RESULT_TYPE_NOOP": 1, "RESPONSE_RESULT_TYPE_SUCCESS": 2, + "RESPONSE_RESULT_TYPE_FAILURE": 3, } func (x ResponseResultType) String() string { @@ -473,11 +477,12 @@ var xxx_messageInfo_MsgChannelCloseInitResponse proto.InternalMessageInfo // MsgChannelCloseConfirm defines a msg sent by a Relayer to Chain B // to acknowledge the change of channel state to CLOSED on Chain A. type MsgChannelCloseConfirm struct { - PortId string `protobuf:"bytes,1,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` - ChannelId string `protobuf:"bytes,2,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` - ProofInit []byte `protobuf:"bytes,3,opt,name=proof_init,json=proofInit,proto3" json:"proof_init,omitempty"` - ProofHeight types.Height `protobuf:"bytes,4,opt,name=proof_height,json=proofHeight,proto3" json:"proof_height"` - Signer string `protobuf:"bytes,5,opt,name=signer,proto3" json:"signer,omitempty"` + PortId string `protobuf:"bytes,1,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` + ChannelId string `protobuf:"bytes,2,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` + ProofInit []byte `protobuf:"bytes,3,opt,name=proof_init,json=proofInit,proto3" json:"proof_init,omitempty"` + ProofHeight types.Height `protobuf:"bytes,4,opt,name=proof_height,json=proofHeight,proto3" json:"proof_height"` + Signer string `protobuf:"bytes,5,opt,name=signer,proto3" json:"signer,omitempty"` + CounterpartyUpgradeSequence uint64 `protobuf:"varint,6,opt,name=counterparty_upgrade_sequence,json=counterpartyUpgradeSequence,proto3" json:"counterparty_upgrade_sequence,omitempty"` } func (m *MsgChannelCloseConfirm) Reset() { *m = MsgChannelCloseConfirm{} } @@ -712,12 +717,13 @@ var xxx_messageInfo_MsgTimeoutResponse proto.InternalMessageInfo // MsgTimeoutOnClose timed-out packet upon counterparty channel closure. type MsgTimeoutOnClose struct { - Packet Packet `protobuf:"bytes,1,opt,name=packet,proto3" json:"packet"` - ProofUnreceived []byte `protobuf:"bytes,2,opt,name=proof_unreceived,json=proofUnreceived,proto3" json:"proof_unreceived,omitempty"` - ProofClose []byte `protobuf:"bytes,3,opt,name=proof_close,json=proofClose,proto3" json:"proof_close,omitempty"` - ProofHeight types.Height `protobuf:"bytes,4,opt,name=proof_height,json=proofHeight,proto3" json:"proof_height"` - NextSequenceRecv uint64 `protobuf:"varint,5,opt,name=next_sequence_recv,json=nextSequenceRecv,proto3" json:"next_sequence_recv,omitempty"` - Signer string `protobuf:"bytes,6,opt,name=signer,proto3" json:"signer,omitempty"` + Packet Packet `protobuf:"bytes,1,opt,name=packet,proto3" json:"packet"` + ProofUnreceived []byte `protobuf:"bytes,2,opt,name=proof_unreceived,json=proofUnreceived,proto3" json:"proof_unreceived,omitempty"` + ProofClose []byte `protobuf:"bytes,3,opt,name=proof_close,json=proofClose,proto3" json:"proof_close,omitempty"` + ProofHeight types.Height `protobuf:"bytes,4,opt,name=proof_height,json=proofHeight,proto3" json:"proof_height"` + NextSequenceRecv uint64 `protobuf:"varint,5,opt,name=next_sequence_recv,json=nextSequenceRecv,proto3" json:"next_sequence_recv,omitempty"` + Signer string `protobuf:"bytes,6,opt,name=signer,proto3" json:"signer,omitempty"` + CounterpartyUpgradeSequence uint64 `protobuf:"varint,7,opt,name=counterparty_upgrade_sequence,json=counterpartyUpgradeSequence,proto3" json:"counterparty_upgrade_sequence,omitempty"` } func (m *MsgTimeoutOnClose) Reset() { *m = MsgTimeoutOnClose{} } @@ -871,1829 +877,6798 @@ func (m *MsgAcknowledgementResponse) XXX_DiscardUnknown() { var xxx_messageInfo_MsgAcknowledgementResponse proto.InternalMessageInfo -func init() { - proto.RegisterEnum("ibc.core.channel.v1.ResponseResultType", ResponseResultType_name, ResponseResultType_value) - proto.RegisterType((*MsgChannelOpenInit)(nil), "ibc.core.channel.v1.MsgChannelOpenInit") - proto.RegisterType((*MsgChannelOpenInitResponse)(nil), "ibc.core.channel.v1.MsgChannelOpenInitResponse") - proto.RegisterType((*MsgChannelOpenTry)(nil), "ibc.core.channel.v1.MsgChannelOpenTry") - proto.RegisterType((*MsgChannelOpenTryResponse)(nil), "ibc.core.channel.v1.MsgChannelOpenTryResponse") - proto.RegisterType((*MsgChannelOpenAck)(nil), "ibc.core.channel.v1.MsgChannelOpenAck") - proto.RegisterType((*MsgChannelOpenAckResponse)(nil), "ibc.core.channel.v1.MsgChannelOpenAckResponse") - proto.RegisterType((*MsgChannelOpenConfirm)(nil), "ibc.core.channel.v1.MsgChannelOpenConfirm") - proto.RegisterType((*MsgChannelOpenConfirmResponse)(nil), "ibc.core.channel.v1.MsgChannelOpenConfirmResponse") - proto.RegisterType((*MsgChannelCloseInit)(nil), "ibc.core.channel.v1.MsgChannelCloseInit") - proto.RegisterType((*MsgChannelCloseInitResponse)(nil), "ibc.core.channel.v1.MsgChannelCloseInitResponse") - proto.RegisterType((*MsgChannelCloseConfirm)(nil), "ibc.core.channel.v1.MsgChannelCloseConfirm") - proto.RegisterType((*MsgChannelCloseConfirmResponse)(nil), "ibc.core.channel.v1.MsgChannelCloseConfirmResponse") - proto.RegisterType((*MsgRecvPacket)(nil), "ibc.core.channel.v1.MsgRecvPacket") - proto.RegisterType((*MsgRecvPacketResponse)(nil), "ibc.core.channel.v1.MsgRecvPacketResponse") - proto.RegisterType((*MsgTimeout)(nil), "ibc.core.channel.v1.MsgTimeout") - proto.RegisterType((*MsgTimeoutResponse)(nil), "ibc.core.channel.v1.MsgTimeoutResponse") - proto.RegisterType((*MsgTimeoutOnClose)(nil), "ibc.core.channel.v1.MsgTimeoutOnClose") - proto.RegisterType((*MsgTimeoutOnCloseResponse)(nil), "ibc.core.channel.v1.MsgTimeoutOnCloseResponse") - proto.RegisterType((*MsgAcknowledgement)(nil), "ibc.core.channel.v1.MsgAcknowledgement") - proto.RegisterType((*MsgAcknowledgementResponse)(nil), "ibc.core.channel.v1.MsgAcknowledgementResponse") +// MsgChannelUpgradeInit defines the request type for the ChannelUpgradeInit rpc +type MsgChannelUpgradeInit struct { + PortId string `protobuf:"bytes,1,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` + ChannelId string `protobuf:"bytes,2,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` + Fields UpgradeFields `protobuf:"bytes,3,opt,name=fields,proto3" json:"fields"` + Signer string `protobuf:"bytes,4,opt,name=signer,proto3" json:"signer,omitempty"` } -func init() { proto.RegisterFile("ibc/core/channel/v1/tx.proto", fileDescriptor_bc4637e0ac3fc7b7) } - -var fileDescriptor_bc4637e0ac3fc7b7 = []byte{ - // 1191 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x58, 0xbf, 0x6f, 0xdb, 0x46, - 0x14, 0x16, 0x65, 0x59, 0xb2, 0x9f, 0xdc, 0x48, 0xa1, 0x93, 0x58, 0xa1, 0x6d, 0x49, 0xf5, 0x10, - 0xbb, 0x6e, 0x2d, 0xc5, 0x4a, 0x5b, 0x34, 0x41, 0x81, 0xc2, 0x56, 0x55, 0xd4, 0x40, 0xfd, 0x03, - 0x94, 0x5c, 0xa0, 0x49, 0x51, 0xc1, 0xa2, 0x2e, 0x34, 0x21, 0x89, 0xa7, 0x92, 0x94, 0x12, 0x6d, - 0x45, 0x27, 0xc3, 0x43, 0xd1, 0xa1, 0xab, 0x81, 0x02, 0x9d, 0xba, 0x65, 0xca, 0xde, 0x2d, 0x63, - 0xc6, 0xa2, 0x40, 0x83, 0xc2, 0x1e, 0xf2, 0x6f, 0x14, 0xbc, 0x3b, 0x52, 0x14, 0x45, 0x4a, 0x4c, - 0xac, 0x78, 0x23, 0xdf, 0xfb, 0xee, 0xfd, 0xf8, 0xbe, 0xe3, 0xe3, 0x91, 0xb0, 0xa4, 0xd4, 0xa4, - 0xbc, 0x84, 0x35, 0x94, 0x97, 0x8e, 0x8f, 0x54, 0x15, 0x35, 0xf3, 0xdd, 0xcd, 0xbc, 0xf1, 0x34, - 0xd7, 0xd6, 0xb0, 0x81, 0xf9, 0x79, 0xa5, 0x26, 0xe5, 0x4c, 0x6f, 0x8e, 0x79, 0x73, 0xdd, 0x4d, - 0xe1, 0x86, 0x8c, 0x65, 0x4c, 0xfc, 0x79, 0xf3, 0x8a, 0x42, 0x85, 0x4c, 0x3f, 0x50, 0x53, 0x41, - 0xaa, 0x61, 0xc6, 0xa1, 0x57, 0x0c, 0xf0, 0xbe, 0x57, 0x26, 0x2b, 0x2c, 0x85, 0x2c, 0x48, 0x58, - 0x6f, 0x61, 0x3d, 0xdf, 0xd2, 0x65, 0xd3, 0xd9, 0xd2, 0x65, 0xea, 0x58, 0xf9, 0x8d, 0x03, 0x7e, - 0x57, 0x97, 0x8b, 0x14, 0xbd, 0xdf, 0x46, 0xea, 0x8e, 0xaa, 0x18, 0xfc, 0x02, 0xc4, 0xda, 0x58, - 0x33, 0xaa, 0x4a, 0x3d, 0xc5, 0x65, 0xb9, 0xb5, 0x59, 0x31, 0x6a, 0xde, 0xee, 0xd4, 0xf9, 0xcf, - 0x21, 0xc6, 0x22, 0xa7, 0xc2, 0x59, 0x6e, 0x2d, 0x5e, 0x58, 0xca, 0x79, 0x74, 0x92, 0x63, 0xf1, - 0xb6, 0x23, 0x2f, 0x5e, 0x65, 0x42, 0xa2, 0xb5, 0x84, 0xbf, 0x05, 0x51, 0x5d, 0x91, 0x55, 0xa4, - 0xa5, 0xa6, 0x68, 0x54, 0x7a, 0xf7, 0x20, 0x71, 0xf2, 0x7b, 0x26, 0xf4, 0xf3, 0xeb, 0x67, 0xeb, - 0xcc, 0xb0, 0xf2, 0x08, 0x84, 0xe1, 0xaa, 0x44, 0xa4, 0xb7, 0xb1, 0xaa, 0x23, 0x7e, 0x19, 0x80, - 0x45, 0xec, 0x17, 0x38, 0xcb, 0x2c, 0x3b, 0x75, 0x3e, 0x05, 0xb1, 0x2e, 0xd2, 0x74, 0x05, 0xab, - 0xa4, 0xc6, 0x59, 0xd1, 0xba, 0x7d, 0x10, 0x31, 0xf3, 0xac, 0xbc, 0x0a, 0xc3, 0xf5, 0xc1, 0xe8, - 0x15, 0xad, 0xe7, 0xdf, 0x72, 0x01, 0xe6, 0xdb, 0x1a, 0xea, 0x2a, 0xb8, 0xa3, 0x57, 0x1d, 0x69, - 0x49, 0xe8, 0xed, 0x70, 0x8a, 0x13, 0xaf, 0x5b, 0xee, 0xa2, 0x5d, 0x82, 0x83, 0xa6, 0xa9, 0x37, - 0xa7, 0x69, 0x13, 0x6e, 0x48, 0xb8, 0xa3, 0x1a, 0x48, 0x6b, 0x1f, 0x69, 0x46, 0xaf, 0x6a, 0x75, - 0x13, 0x21, 0x75, 0xcd, 0x3b, 0x7d, 0xdf, 0x52, 0x97, 0x49, 0x49, 0x5b, 0xc3, 0xf8, 0x71, 0x55, - 0x51, 0x15, 0x23, 0x35, 0x9d, 0xe5, 0xd6, 0xe6, 0xc4, 0x59, 0x62, 0x21, 0x7a, 0x16, 0x61, 0x8e, - 0xba, 0x8f, 0x91, 0x22, 0x1f, 0x1b, 0xa9, 0x28, 0x29, 0x4a, 0x70, 0x14, 0x45, 0x37, 0x54, 0x77, - 0x33, 0xf7, 0x35, 0x41, 0xb0, 0x92, 0xe2, 0x64, 0x15, 0x35, 0x39, 0xd4, 0x8b, 0x8d, 0x56, 0xef, - 0x21, 0xdc, 0x1e, 0xe2, 0xd7, 0x16, 0xcf, 0xa1, 0x0e, 0x37, 0xa0, 0x8e, 0x4b, 0xd6, 0xb0, 0x4b, - 0x56, 0x26, 0xde, 0x5f, 0x43, 0xe2, 0x6d, 0x49, 0x0d, 0x7f, 0xf1, 0x46, 0xc7, 0xe4, 0x3f, 0x85, - 0x85, 0x01, 0xa6, 0x1d, 0x58, 0xba, 0x43, 0x6f, 0x3a, 0xdd, 0x7d, 0x7d, 0xdf, 0x42, 0xa1, 0x45, - 0xa0, 0x7a, 0x54, 0x0d, 0xad, 0xc7, 0x04, 0x9a, 0x21, 0x06, 0x73, 0xf3, 0x5d, 0xad, 0x3e, 0x8b, - 0x6e, 0x7d, 0xb6, 0xa4, 0x86, 0xa5, 0xcf, 0xca, 0x3f, 0x1c, 0xdc, 0x1c, 0xf4, 0x16, 0xb1, 0xfa, - 0x58, 0xd1, 0x5a, 0x6f, 0x4d, 0xb2, 0xdd, 0xf9, 0x91, 0xd4, 0x20, 0xb4, 0x5a, 0x9d, 0x9b, 0xca, - 0xb9, 0x3b, 0x8f, 0x5c, 0xae, 0xf3, 0xe9, 0xd1, 0x9d, 0x67, 0x60, 0xd9, 0xb3, 0x37, 0xbb, 0xfb, - 0x2e, 0xcc, 0xf7, 0x01, 0xc5, 0x26, 0xd6, 0xd1, 0xe8, 0x79, 0x38, 0xa6, 0xf5, 0xc0, 0x03, 0x6f, - 0x19, 0x16, 0x3d, 0xf2, 0xda, 0x65, 0xfd, 0xcb, 0xc1, 0x2d, 0x97, 0xff, 0xb2, 0xaa, 0x0c, 0x4e, - 0x8c, 0xa9, 0x71, 0x13, 0xe3, 0xdd, 0xea, 0x92, 0x85, 0xb4, 0x77, 0x7b, 0x36, 0x03, 0x17, 0x1c, - 0xbc, 0xb7, 0xab, 0xcb, 0x22, 0x92, 0xba, 0x07, 0x47, 0x52, 0x03, 0x19, 0xfc, 0x7d, 0x88, 0xb6, - 0xc9, 0x15, 0xe9, 0x3b, 0x5e, 0x58, 0xf4, 0x1c, 0xb1, 0x14, 0xcc, 0x8a, 0x63, 0x0b, 0xf8, 0x0f, - 0x20, 0x49, 0x9b, 0x93, 0x70, 0xab, 0xa5, 0x18, 0x2d, 0xa4, 0x1a, 0x84, 0xa0, 0x39, 0x31, 0x41, - 0xec, 0x45, 0xdb, 0x3c, 0xc4, 0xc3, 0xd4, 0xe5, 0x78, 0x88, 0x8c, 0xe6, 0xe1, 0x07, 0xf2, 0xec, - 0xf5, 0x9b, 0xb4, 0xa7, 0xe6, 0x17, 0x10, 0xd5, 0x90, 0xde, 0x69, 0xd2, 0x66, 0xaf, 0x15, 0x56, - 0x3d, 0x9b, 0xb5, 0xe0, 0x22, 0x81, 0x56, 0x7a, 0x6d, 0x24, 0xb2, 0x65, 0x6c, 0x7a, 0xfe, 0x12, - 0x06, 0xd8, 0xd5, 0xe5, 0x8a, 0xd2, 0x42, 0xb8, 0x33, 0x19, 0x0a, 0x3b, 0xaa, 0x86, 0x24, 0xa4, - 0x74, 0x51, 0x7d, 0x80, 0xc2, 0x43, 0xdb, 0x3c, 0x19, 0x0a, 0x3f, 0x02, 0x5e, 0x45, 0x4f, 0x8d, - 0xaa, 0x8e, 0x7e, 0xec, 0x20, 0x55, 0x42, 0x55, 0x0d, 0x49, 0x5d, 0x42, 0x67, 0x44, 0x4c, 0x9a, - 0x9e, 0x32, 0x73, 0x98, 0xe4, 0x05, 0xdf, 0x78, 0x8f, 0xc8, 0xf1, 0x87, 0xf1, 0x31, 0x69, 0xb6, - 0x9f, 0xd3, 0x77, 0x15, 0x8b, 0xbe, 0xaf, 0x92, 0x8d, 0x7d, 0x45, 0xa4, 0x67, 0x20, 0xce, 0xb6, - 0xb8, 0x99, 0x94, 0x3d, 0xdf, 0xf4, 0x89, 0xa7, 0x65, 0x4c, 0xe4, 0x01, 0xf7, 0x56, 0x65, 0x7a, - 0xac, 0x2a, 0xd1, 0xd1, 0xaa, 0xd4, 0xc8, 0x0b, 0x6a, 0x90, 0xb7, 0x49, 0x8b, 0x73, 0x12, 0x26, - 0xd2, 0x6f, 0x49, 0x0d, 0x15, 0x3f, 0x69, 0xa2, 0xba, 0x8c, 0xc8, 0xf3, 0x7e, 0x09, 0x75, 0xd6, - 0x20, 0x71, 0x34, 0x18, 0xcd, 0x12, 0xc7, 0x65, 0xee, 0x8b, 0x63, 0x2e, 0xac, 0x0f, 0x88, 0xb3, - 0x65, 0x5a, 0xae, 0x78, 0xfa, 0x4a, 0xe4, 0xb4, 0xed, 0x62, 0x62, 0xc2, 0x7c, 0xaf, 0xff, 0xc9, - 0x01, 0x3f, 0x0c, 0xe2, 0x3f, 0x81, 0xac, 0x58, 0x2a, 0x1f, 0xec, 0xef, 0x95, 0x4b, 0x55, 0xb1, - 0x54, 0x3e, 0xfc, 0xa6, 0x52, 0xad, 0x7c, 0x77, 0x50, 0xaa, 0x1e, 0xee, 0x95, 0x0f, 0x4a, 0xc5, - 0x9d, 0xaf, 0x76, 0x4a, 0x5f, 0x26, 0x43, 0x42, 0xe2, 0xf4, 0x2c, 0x1b, 0x77, 0x98, 0xf8, 0x55, - 0xb8, 0xed, 0xb9, 0x6c, 0x6f, 0x7f, 0xff, 0x20, 0xc9, 0x09, 0x33, 0xa7, 0x67, 0xd9, 0x88, 0x79, - 0xcd, 0x6f, 0xc0, 0x92, 0x27, 0xb0, 0x7c, 0x58, 0x2c, 0x96, 0xca, 0xe5, 0x64, 0x58, 0x88, 0x9f, - 0x9e, 0x65, 0x63, 0xec, 0x56, 0x88, 0x9c, 0xfc, 0x91, 0x0e, 0x15, 0x9e, 0xcf, 0xc0, 0xd4, 0xae, - 0x2e, 0xf3, 0x0d, 0x48, 0xb8, 0xbf, 0x8c, 0xbc, 0xbb, 0x1f, 0xfe, 0x58, 0x11, 0xf2, 0x01, 0x81, - 0x36, 0xcf, 0xc7, 0x70, 0xcd, 0xf5, 0x49, 0x72, 0x27, 0x40, 0x88, 0x8a, 0xd6, 0x13, 0x72, 0xc1, - 0x70, 0x3e, 0x99, 0xcc, 0x53, 0x58, 0x90, 0x4c, 0x5b, 0x52, 0x23, 0x50, 0x26, 0xc7, 0x61, 0x92, - 0x37, 0x80, 0xf7, 0x38, 0x48, 0xae, 0x07, 0x88, 0xc2, 0xb0, 0x42, 0x21, 0x38, 0xd6, 0xce, 0xaa, - 0x42, 0x72, 0xe8, 0x04, 0xb7, 0x36, 0x26, 0x8e, 0x8d, 0x14, 0xee, 0x06, 0x45, 0xda, 0xf9, 0x9e, - 0xc0, 0xbc, 0xd7, 0xc9, 0xec, 0xc3, 0x20, 0x81, 0xac, 0x3e, 0xef, 0xbd, 0x01, 0xd8, 0x4e, 0xfc, - 0x3d, 0x80, 0xe3, 0x40, 0xb4, 0xe2, 0x17, 0xa2, 0x8f, 0x11, 0xd6, 0xc7, 0x63, 0xec, 0xe8, 0x65, - 0x88, 0x59, 0x07, 0x85, 0x8c, 0xdf, 0x32, 0x06, 0x10, 0x56, 0xc7, 0x00, 0x9c, 0x7b, 0xcf, 0xf5, - 0x3e, 0xbc, 0x33, 0x66, 0x29, 0xc3, 0xf9, 0xef, 0x3d, 0x9f, 0xf7, 0x44, 0x03, 0x12, 0xee, 0xe1, - 0xee, 0x5b, 0xa5, 0x0b, 0xe8, 0xff, 0xf0, 0xfa, 0x0c, 0x49, 0x61, 0xfa, 0xa7, 0xd7, 0xcf, 0xd6, - 0xb9, 0xed, 0xf2, 0x8b, 0xf3, 0x34, 0xf7, 0xf2, 0x3c, 0xcd, 0xfd, 0x77, 0x9e, 0xe6, 0x7e, 0xbd, - 0x48, 0x87, 0x5e, 0x5e, 0xa4, 0x43, 0x7f, 0x5f, 0xa4, 0x43, 0x0f, 0xef, 0xcb, 0x8a, 0x71, 0xdc, - 0xa9, 0xe5, 0x24, 0xdc, 0xca, 0xb3, 0x9f, 0x31, 0x4a, 0x4d, 0xda, 0x90, 0x71, 0xbe, 0xfb, 0x59, - 0xbe, 0x85, 0xeb, 0x9d, 0x26, 0xd2, 0xe9, 0x4f, 0x9c, 0xbb, 0x1f, 0x6f, 0x58, 0xff, 0x71, 0x8c, - 0x5e, 0x1b, 0xe9, 0xb5, 0x28, 0xf9, 0x55, 0x73, 0xef, 0xff, 0x00, 0x00, 0x00, 0xff, 0xff, 0x8d, - 0xa0, 0x17, 0x65, 0x52, 0x12, 0x00, 0x00, +func (m *MsgChannelUpgradeInit) Reset() { *m = MsgChannelUpgradeInit{} } +func (m *MsgChannelUpgradeInit) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeInit) ProtoMessage() {} +func (*MsgChannelUpgradeInit) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{20} +} +func (m *MsgChannelUpgradeInit) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgChannelUpgradeInit) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeInit.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } +} +func (m *MsgChannelUpgradeInit) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeInit.Merge(m, src) +} +func (m *MsgChannelUpgradeInit) XXX_Size() int { + return m.Size() +} +func (m *MsgChannelUpgradeInit) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeInit.DiscardUnknown(m) } -// Reference imports to suppress errors if they are not otherwise used. -var _ context.Context -var _ grpc.ClientConn - -// This is a compile-time assertion to ensure that this generated file -// is compatible with the grpc package it is being compiled against. -const _ = grpc.SupportPackageIsVersion4 +var xxx_messageInfo_MsgChannelUpgradeInit proto.InternalMessageInfo -// MsgClient is the client API for Msg service. -// -// For semantics around ctx use and closing/ending streaming RPCs, please refer to https://godoc.org/google.golang.org/grpc#ClientConn.NewStream. -type MsgClient interface { - // ChannelOpenInit defines a rpc handler method for MsgChannelOpenInit. - ChannelOpenInit(ctx context.Context, in *MsgChannelOpenInit, opts ...grpc.CallOption) (*MsgChannelOpenInitResponse, error) - // ChannelOpenTry defines a rpc handler method for MsgChannelOpenTry. - ChannelOpenTry(ctx context.Context, in *MsgChannelOpenTry, opts ...grpc.CallOption) (*MsgChannelOpenTryResponse, error) - // ChannelOpenAck defines a rpc handler method for MsgChannelOpenAck. - ChannelOpenAck(ctx context.Context, in *MsgChannelOpenAck, opts ...grpc.CallOption) (*MsgChannelOpenAckResponse, error) - // ChannelOpenConfirm defines a rpc handler method for MsgChannelOpenConfirm. - ChannelOpenConfirm(ctx context.Context, in *MsgChannelOpenConfirm, opts ...grpc.CallOption) (*MsgChannelOpenConfirmResponse, error) - // ChannelCloseInit defines a rpc handler method for MsgChannelCloseInit. - ChannelCloseInit(ctx context.Context, in *MsgChannelCloseInit, opts ...grpc.CallOption) (*MsgChannelCloseInitResponse, error) - // ChannelCloseConfirm defines a rpc handler method for - // MsgChannelCloseConfirm. - ChannelCloseConfirm(ctx context.Context, in *MsgChannelCloseConfirm, opts ...grpc.CallOption) (*MsgChannelCloseConfirmResponse, error) - // RecvPacket defines a rpc handler method for MsgRecvPacket. - RecvPacket(ctx context.Context, in *MsgRecvPacket, opts ...grpc.CallOption) (*MsgRecvPacketResponse, error) - // Timeout defines a rpc handler method for MsgTimeout. - Timeout(ctx context.Context, in *MsgTimeout, opts ...grpc.CallOption) (*MsgTimeoutResponse, error) - // TimeoutOnClose defines a rpc handler method for MsgTimeoutOnClose. - TimeoutOnClose(ctx context.Context, in *MsgTimeoutOnClose, opts ...grpc.CallOption) (*MsgTimeoutOnCloseResponse, error) - // Acknowledgement defines a rpc handler method for MsgAcknowledgement. - Acknowledgement(ctx context.Context, in *MsgAcknowledgement, opts ...grpc.CallOption) (*MsgAcknowledgementResponse, error) +// MsgChannelUpgradeInitResponse defines the MsgChannelUpgradeInit response type +type MsgChannelUpgradeInitResponse struct { + Upgrade Upgrade `protobuf:"bytes,1,opt,name=upgrade,proto3" json:"upgrade"` + UpgradeSequence uint64 `protobuf:"varint,2,opt,name=upgrade_sequence,json=upgradeSequence,proto3" json:"upgrade_sequence,omitempty"` } -type msgClient struct { - cc grpc1.ClientConn +func (m *MsgChannelUpgradeInitResponse) Reset() { *m = MsgChannelUpgradeInitResponse{} } +func (m *MsgChannelUpgradeInitResponse) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeInitResponse) ProtoMessage() {} +func (*MsgChannelUpgradeInitResponse) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{21} } - -func NewMsgClient(cc grpc1.ClientConn) MsgClient { - return &msgClient{cc} +func (m *MsgChannelUpgradeInitResponse) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) } - -func (c *msgClient) ChannelOpenInit(ctx context.Context, in *MsgChannelOpenInit, opts ...grpc.CallOption) (*MsgChannelOpenInitResponse, error) { - out := new(MsgChannelOpenInitResponse) - err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelOpenInit", in, out, opts...) - if err != nil { - return nil, err +func (m *MsgChannelUpgradeInitResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeInitResponse.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil } - return out, nil } - -func (c *msgClient) ChannelOpenTry(ctx context.Context, in *MsgChannelOpenTry, opts ...grpc.CallOption) (*MsgChannelOpenTryResponse, error) { - out := new(MsgChannelOpenTryResponse) - err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelOpenTry", in, out, opts...) - if err != nil { - return nil, err - } - return out, nil +func (m *MsgChannelUpgradeInitResponse) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeInitResponse.Merge(m, src) } - -func (c *msgClient) ChannelOpenAck(ctx context.Context, in *MsgChannelOpenAck, opts ...grpc.CallOption) (*MsgChannelOpenAckResponse, error) { - out := new(MsgChannelOpenAckResponse) - err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelOpenAck", in, out, opts...) - if err != nil { - return nil, err - } - return out, nil +func (m *MsgChannelUpgradeInitResponse) XXX_Size() int { + return m.Size() } - -func (c *msgClient) ChannelOpenConfirm(ctx context.Context, in *MsgChannelOpenConfirm, opts ...grpc.CallOption) (*MsgChannelOpenConfirmResponse, error) { - out := new(MsgChannelOpenConfirmResponse) - err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelOpenConfirm", in, out, opts...) - if err != nil { - return nil, err - } - return out, nil +func (m *MsgChannelUpgradeInitResponse) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeInitResponse.DiscardUnknown(m) } -func (c *msgClient) ChannelCloseInit(ctx context.Context, in *MsgChannelCloseInit, opts ...grpc.CallOption) (*MsgChannelCloseInitResponse, error) { - out := new(MsgChannelCloseInitResponse) - err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelCloseInit", in, out, opts...) - if err != nil { - return nil, err - } - return out, nil -} +var xxx_messageInfo_MsgChannelUpgradeInitResponse proto.InternalMessageInfo -func (c *msgClient) ChannelCloseConfirm(ctx context.Context, in *MsgChannelCloseConfirm, opts ...grpc.CallOption) (*MsgChannelCloseConfirmResponse, error) { - out := new(MsgChannelCloseConfirmResponse) - err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelCloseConfirm", in, out, opts...) - if err != nil { - return nil, err - } - return out, nil +// MsgChannelUpgradeTry defines the request type for the ChannelUpgradeTry rpc +type MsgChannelUpgradeTry struct { + PortId string `protobuf:"bytes,1,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` + ChannelId string `protobuf:"bytes,2,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` + ProposedUpgradeConnectionHops []string `protobuf:"bytes,3,rep,name=proposed_upgrade_connection_hops,json=proposedUpgradeConnectionHops,proto3" json:"proposed_upgrade_connection_hops,omitempty"` + CounterpartyUpgradeFields UpgradeFields `protobuf:"bytes,4,opt,name=counterparty_upgrade_fields,json=counterpartyUpgradeFields,proto3" json:"counterparty_upgrade_fields"` + CounterpartyUpgradeSequence uint64 `protobuf:"varint,5,opt,name=counterparty_upgrade_sequence,json=counterpartyUpgradeSequence,proto3" json:"counterparty_upgrade_sequence,omitempty"` + ProofChannel []byte `protobuf:"bytes,6,opt,name=proof_channel,json=proofChannel,proto3" json:"proof_channel,omitempty"` + ProofUpgrade []byte `protobuf:"bytes,7,opt,name=proof_upgrade,json=proofUpgrade,proto3" json:"proof_upgrade,omitempty"` + ProofHeight types.Height `protobuf:"bytes,8,opt,name=proof_height,json=proofHeight,proto3" json:"proof_height"` + Signer string `protobuf:"bytes,9,opt,name=signer,proto3" json:"signer,omitempty"` } -func (c *msgClient) RecvPacket(ctx context.Context, in *MsgRecvPacket, opts ...grpc.CallOption) (*MsgRecvPacketResponse, error) { - out := new(MsgRecvPacketResponse) - err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/RecvPacket", in, out, opts...) - if err != nil { - return nil, err - } - return out, nil +func (m *MsgChannelUpgradeTry) Reset() { *m = MsgChannelUpgradeTry{} } +func (m *MsgChannelUpgradeTry) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeTry) ProtoMessage() {} +func (*MsgChannelUpgradeTry) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{22} } - -func (c *msgClient) Timeout(ctx context.Context, in *MsgTimeout, opts ...grpc.CallOption) (*MsgTimeoutResponse, error) { - out := new(MsgTimeoutResponse) - err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/Timeout", in, out, opts...) - if err != nil { - return nil, err +func (m *MsgChannelUpgradeTry) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgChannelUpgradeTry) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeTry.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil } - return out, nil +} +func (m *MsgChannelUpgradeTry) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeTry.Merge(m, src) +} +func (m *MsgChannelUpgradeTry) XXX_Size() int { + return m.Size() +} +func (m *MsgChannelUpgradeTry) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeTry.DiscardUnknown(m) } -func (c *msgClient) TimeoutOnClose(ctx context.Context, in *MsgTimeoutOnClose, opts ...grpc.CallOption) (*MsgTimeoutOnCloseResponse, error) { - out := new(MsgTimeoutOnCloseResponse) - err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/TimeoutOnClose", in, out, opts...) - if err != nil { - return nil, err - } - return out, nil +var xxx_messageInfo_MsgChannelUpgradeTry proto.InternalMessageInfo + +// MsgChannelUpgradeTryResponse defines the MsgChannelUpgradeTry response type +type MsgChannelUpgradeTryResponse struct { + Upgrade Upgrade `protobuf:"bytes,1,opt,name=upgrade,proto3" json:"upgrade"` + UpgradeSequence uint64 `protobuf:"varint,2,opt,name=upgrade_sequence,json=upgradeSequence,proto3" json:"upgrade_sequence,omitempty"` + Result ResponseResultType `protobuf:"varint,3,opt,name=result,proto3,enum=ibc.core.channel.v1.ResponseResultType" json:"result,omitempty"` } -func (c *msgClient) Acknowledgement(ctx context.Context, in *MsgAcknowledgement, opts ...grpc.CallOption) (*MsgAcknowledgementResponse, error) { - out := new(MsgAcknowledgementResponse) - err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/Acknowledgement", in, out, opts...) - if err != nil { - return nil, err +func (m *MsgChannelUpgradeTryResponse) Reset() { *m = MsgChannelUpgradeTryResponse{} } +func (m *MsgChannelUpgradeTryResponse) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeTryResponse) ProtoMessage() {} +func (*MsgChannelUpgradeTryResponse) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{23} +} +func (m *MsgChannelUpgradeTryResponse) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgChannelUpgradeTryResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeTryResponse.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil } - return out, nil } - -// MsgServer is the server API for Msg service. -type MsgServer interface { - // ChannelOpenInit defines a rpc handler method for MsgChannelOpenInit. - ChannelOpenInit(context.Context, *MsgChannelOpenInit) (*MsgChannelOpenInitResponse, error) - // ChannelOpenTry defines a rpc handler method for MsgChannelOpenTry. - ChannelOpenTry(context.Context, *MsgChannelOpenTry) (*MsgChannelOpenTryResponse, error) - // ChannelOpenAck defines a rpc handler method for MsgChannelOpenAck. - ChannelOpenAck(context.Context, *MsgChannelOpenAck) (*MsgChannelOpenAckResponse, error) - // ChannelOpenConfirm defines a rpc handler method for MsgChannelOpenConfirm. - ChannelOpenConfirm(context.Context, *MsgChannelOpenConfirm) (*MsgChannelOpenConfirmResponse, error) - // ChannelCloseInit defines a rpc handler method for MsgChannelCloseInit. - ChannelCloseInit(context.Context, *MsgChannelCloseInit) (*MsgChannelCloseInitResponse, error) - // ChannelCloseConfirm defines a rpc handler method for - // MsgChannelCloseConfirm. - ChannelCloseConfirm(context.Context, *MsgChannelCloseConfirm) (*MsgChannelCloseConfirmResponse, error) - // RecvPacket defines a rpc handler method for MsgRecvPacket. - RecvPacket(context.Context, *MsgRecvPacket) (*MsgRecvPacketResponse, error) - // Timeout defines a rpc handler method for MsgTimeout. - Timeout(context.Context, *MsgTimeout) (*MsgTimeoutResponse, error) - // TimeoutOnClose defines a rpc handler method for MsgTimeoutOnClose. - TimeoutOnClose(context.Context, *MsgTimeoutOnClose) (*MsgTimeoutOnCloseResponse, error) - // Acknowledgement defines a rpc handler method for MsgAcknowledgement. - Acknowledgement(context.Context, *MsgAcknowledgement) (*MsgAcknowledgementResponse, error) +func (m *MsgChannelUpgradeTryResponse) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeTryResponse.Merge(m, src) +} +func (m *MsgChannelUpgradeTryResponse) XXX_Size() int { + return m.Size() +} +func (m *MsgChannelUpgradeTryResponse) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeTryResponse.DiscardUnknown(m) } -// UnimplementedMsgServer can be embedded to have forward compatible implementations. -type UnimplementedMsgServer struct { +var xxx_messageInfo_MsgChannelUpgradeTryResponse proto.InternalMessageInfo + +// MsgChannelUpgradeAck defines the request type for the ChannelUpgradeAck rpc +type MsgChannelUpgradeAck struct { + PortId string `protobuf:"bytes,1,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` + ChannelId string `protobuf:"bytes,2,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` + CounterpartyUpgrade Upgrade `protobuf:"bytes,3,opt,name=counterparty_upgrade,json=counterpartyUpgrade,proto3" json:"counterparty_upgrade"` + ProofChannel []byte `protobuf:"bytes,4,opt,name=proof_channel,json=proofChannel,proto3" json:"proof_channel,omitempty"` + ProofUpgrade []byte `protobuf:"bytes,5,opt,name=proof_upgrade,json=proofUpgrade,proto3" json:"proof_upgrade,omitempty"` + ProofHeight types.Height `protobuf:"bytes,6,opt,name=proof_height,json=proofHeight,proto3" json:"proof_height"` + Signer string `protobuf:"bytes,7,opt,name=signer,proto3" json:"signer,omitempty"` } -func (*UnimplementedMsgServer) ChannelOpenInit(ctx context.Context, req *MsgChannelOpenInit) (*MsgChannelOpenInitResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method ChannelOpenInit not implemented") +func (m *MsgChannelUpgradeAck) Reset() { *m = MsgChannelUpgradeAck{} } +func (m *MsgChannelUpgradeAck) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeAck) ProtoMessage() {} +func (*MsgChannelUpgradeAck) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{24} } -func (*UnimplementedMsgServer) ChannelOpenTry(ctx context.Context, req *MsgChannelOpenTry) (*MsgChannelOpenTryResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method ChannelOpenTry not implemented") +func (m *MsgChannelUpgradeAck) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) } -func (*UnimplementedMsgServer) ChannelOpenAck(ctx context.Context, req *MsgChannelOpenAck) (*MsgChannelOpenAckResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method ChannelOpenAck not implemented") +func (m *MsgChannelUpgradeAck) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeAck.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } } -func (*UnimplementedMsgServer) ChannelOpenConfirm(ctx context.Context, req *MsgChannelOpenConfirm) (*MsgChannelOpenConfirmResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method ChannelOpenConfirm not implemented") +func (m *MsgChannelUpgradeAck) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeAck.Merge(m, src) } -func (*UnimplementedMsgServer) ChannelCloseInit(ctx context.Context, req *MsgChannelCloseInit) (*MsgChannelCloseInitResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method ChannelCloseInit not implemented") +func (m *MsgChannelUpgradeAck) XXX_Size() int { + return m.Size() } -func (*UnimplementedMsgServer) ChannelCloseConfirm(ctx context.Context, req *MsgChannelCloseConfirm) (*MsgChannelCloseConfirmResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method ChannelCloseConfirm not implemented") +func (m *MsgChannelUpgradeAck) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeAck.DiscardUnknown(m) } -func (*UnimplementedMsgServer) RecvPacket(ctx context.Context, req *MsgRecvPacket) (*MsgRecvPacketResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method RecvPacket not implemented") + +var xxx_messageInfo_MsgChannelUpgradeAck proto.InternalMessageInfo + +// MsgChannelUpgradeAckResponse defines MsgChannelUpgradeAck response type +type MsgChannelUpgradeAckResponse struct { + Result ResponseResultType `protobuf:"varint,1,opt,name=result,proto3,enum=ibc.core.channel.v1.ResponseResultType" json:"result,omitempty"` } -func (*UnimplementedMsgServer) Timeout(ctx context.Context, req *MsgTimeout) (*MsgTimeoutResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method Timeout not implemented") + +func (m *MsgChannelUpgradeAckResponse) Reset() { *m = MsgChannelUpgradeAckResponse{} } +func (m *MsgChannelUpgradeAckResponse) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeAckResponse) ProtoMessage() {} +func (*MsgChannelUpgradeAckResponse) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{25} } -func (*UnimplementedMsgServer) TimeoutOnClose(ctx context.Context, req *MsgTimeoutOnClose) (*MsgTimeoutOnCloseResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method TimeoutOnClose not implemented") +func (m *MsgChannelUpgradeAckResponse) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) } -func (*UnimplementedMsgServer) Acknowledgement(ctx context.Context, req *MsgAcknowledgement) (*MsgAcknowledgementResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method Acknowledgement not implemented") +func (m *MsgChannelUpgradeAckResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeAckResponse.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } } - -func RegisterMsgServer(s grpc1.Server, srv MsgServer) { - s.RegisterService(&_Msg_serviceDesc, srv) +func (m *MsgChannelUpgradeAckResponse) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeAckResponse.Merge(m, src) +} +func (m *MsgChannelUpgradeAckResponse) XXX_Size() int { + return m.Size() +} +func (m *MsgChannelUpgradeAckResponse) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeAckResponse.DiscardUnknown(m) } -func _Msg_ChannelOpenInit_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(MsgChannelOpenInit) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(MsgServer).ChannelOpenInit(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: "/ibc.core.channel.v1.Msg/ChannelOpenInit", - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(MsgServer).ChannelOpenInit(ctx, req.(*MsgChannelOpenInit)) - } - return interceptor(ctx, in, info, handler) +var xxx_messageInfo_MsgChannelUpgradeAckResponse proto.InternalMessageInfo + +// MsgChannelUpgradeConfirm defines the request type for the ChannelUpgradeConfirm rpc +type MsgChannelUpgradeConfirm struct { + PortId string `protobuf:"bytes,1,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` + ChannelId string `protobuf:"bytes,2,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` + CounterpartyChannelState State `protobuf:"varint,3,opt,name=counterparty_channel_state,json=counterpartyChannelState,proto3,enum=ibc.core.channel.v1.State" json:"counterparty_channel_state,omitempty"` + CounterpartyUpgrade Upgrade `protobuf:"bytes,4,opt,name=counterparty_upgrade,json=counterpartyUpgrade,proto3" json:"counterparty_upgrade"` + ProofChannel []byte `protobuf:"bytes,5,opt,name=proof_channel,json=proofChannel,proto3" json:"proof_channel,omitempty"` + ProofUpgrade []byte `protobuf:"bytes,6,opt,name=proof_upgrade,json=proofUpgrade,proto3" json:"proof_upgrade,omitempty"` + ProofHeight types.Height `protobuf:"bytes,7,opt,name=proof_height,json=proofHeight,proto3" json:"proof_height"` + Signer string `protobuf:"bytes,8,opt,name=signer,proto3" json:"signer,omitempty"` } -func _Msg_ChannelOpenTry_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(MsgChannelOpenTry) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(MsgServer).ChannelOpenTry(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: "/ibc.core.channel.v1.Msg/ChannelOpenTry", - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(MsgServer).ChannelOpenTry(ctx, req.(*MsgChannelOpenTry)) +func (m *MsgChannelUpgradeConfirm) Reset() { *m = MsgChannelUpgradeConfirm{} } +func (m *MsgChannelUpgradeConfirm) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeConfirm) ProtoMessage() {} +func (*MsgChannelUpgradeConfirm) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{26} +} +func (m *MsgChannelUpgradeConfirm) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgChannelUpgradeConfirm) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeConfirm.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil } - return interceptor(ctx, in, info, handler) +} +func (m *MsgChannelUpgradeConfirm) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeConfirm.Merge(m, src) +} +func (m *MsgChannelUpgradeConfirm) XXX_Size() int { + return m.Size() +} +func (m *MsgChannelUpgradeConfirm) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeConfirm.DiscardUnknown(m) } -func _Msg_ChannelOpenAck_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(MsgChannelOpenAck) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(MsgServer).ChannelOpenAck(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: "/ibc.core.channel.v1.Msg/ChannelOpenAck", - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(MsgServer).ChannelOpenAck(ctx, req.(*MsgChannelOpenAck)) - } - return interceptor(ctx, in, info, handler) +var xxx_messageInfo_MsgChannelUpgradeConfirm proto.InternalMessageInfo + +// MsgChannelUpgradeConfirmResponse defines MsgChannelUpgradeConfirm response type +type MsgChannelUpgradeConfirmResponse struct { + Result ResponseResultType `protobuf:"varint,1,opt,name=result,proto3,enum=ibc.core.channel.v1.ResponseResultType" json:"result,omitempty"` } -func _Msg_ChannelOpenConfirm_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(MsgChannelOpenConfirm) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(MsgServer).ChannelOpenConfirm(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: "/ibc.core.channel.v1.Msg/ChannelOpenConfirm", - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(MsgServer).ChannelOpenConfirm(ctx, req.(*MsgChannelOpenConfirm)) +func (m *MsgChannelUpgradeConfirmResponse) Reset() { *m = MsgChannelUpgradeConfirmResponse{} } +func (m *MsgChannelUpgradeConfirmResponse) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeConfirmResponse) ProtoMessage() {} +func (*MsgChannelUpgradeConfirmResponse) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{27} +} +func (m *MsgChannelUpgradeConfirmResponse) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgChannelUpgradeConfirmResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeConfirmResponse.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil } - return interceptor(ctx, in, info, handler) +} +func (m *MsgChannelUpgradeConfirmResponse) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeConfirmResponse.Merge(m, src) +} +func (m *MsgChannelUpgradeConfirmResponse) XXX_Size() int { + return m.Size() +} +func (m *MsgChannelUpgradeConfirmResponse) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeConfirmResponse.DiscardUnknown(m) } -func _Msg_ChannelCloseInit_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(MsgChannelCloseInit) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(MsgServer).ChannelCloseInit(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: "/ibc.core.channel.v1.Msg/ChannelCloseInit", - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(MsgServer).ChannelCloseInit(ctx, req.(*MsgChannelCloseInit)) - } - return interceptor(ctx, in, info, handler) +var xxx_messageInfo_MsgChannelUpgradeConfirmResponse proto.InternalMessageInfo + +// MsgChannelUpgradeOpen defines the request type for the ChannelUpgradeOpen rpc +type MsgChannelUpgradeOpen struct { + PortId string `protobuf:"bytes,1,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` + ChannelId string `protobuf:"bytes,2,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` + CounterpartyChannelState State `protobuf:"varint,3,opt,name=counterparty_channel_state,json=counterpartyChannelState,proto3,enum=ibc.core.channel.v1.State" json:"counterparty_channel_state,omitempty"` + ProofChannel []byte `protobuf:"bytes,4,opt,name=proof_channel,json=proofChannel,proto3" json:"proof_channel,omitempty"` + ProofHeight types.Height `protobuf:"bytes,5,opt,name=proof_height,json=proofHeight,proto3" json:"proof_height"` + Signer string `protobuf:"bytes,6,opt,name=signer,proto3" json:"signer,omitempty"` } -func _Msg_ChannelCloseConfirm_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(MsgChannelCloseConfirm) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(MsgServer).ChannelCloseConfirm(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: "/ibc.core.channel.v1.Msg/ChannelCloseConfirm", - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(MsgServer).ChannelCloseConfirm(ctx, req.(*MsgChannelCloseConfirm)) +func (m *MsgChannelUpgradeOpen) Reset() { *m = MsgChannelUpgradeOpen{} } +func (m *MsgChannelUpgradeOpen) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeOpen) ProtoMessage() {} +func (*MsgChannelUpgradeOpen) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{28} +} +func (m *MsgChannelUpgradeOpen) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgChannelUpgradeOpen) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeOpen.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil } - return interceptor(ctx, in, info, handler) +} +func (m *MsgChannelUpgradeOpen) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeOpen.Merge(m, src) +} +func (m *MsgChannelUpgradeOpen) XXX_Size() int { + return m.Size() +} +func (m *MsgChannelUpgradeOpen) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeOpen.DiscardUnknown(m) } -func _Msg_RecvPacket_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(MsgRecvPacket) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(MsgServer).RecvPacket(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: "/ibc.core.channel.v1.Msg/RecvPacket", - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(MsgServer).RecvPacket(ctx, req.(*MsgRecvPacket)) - } - return interceptor(ctx, in, info, handler) +var xxx_messageInfo_MsgChannelUpgradeOpen proto.InternalMessageInfo + +// MsgChannelUpgradeOpenResponse defines the MsgChannelUpgradeOpen response type +type MsgChannelUpgradeOpenResponse struct { } -func _Msg_Timeout_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(MsgTimeout) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(MsgServer).Timeout(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: "/ibc.core.channel.v1.Msg/Timeout", - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(MsgServer).Timeout(ctx, req.(*MsgTimeout)) +func (m *MsgChannelUpgradeOpenResponse) Reset() { *m = MsgChannelUpgradeOpenResponse{} } +func (m *MsgChannelUpgradeOpenResponse) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeOpenResponse) ProtoMessage() {} +func (*MsgChannelUpgradeOpenResponse) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{29} +} +func (m *MsgChannelUpgradeOpenResponse) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgChannelUpgradeOpenResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeOpenResponse.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil } - return interceptor(ctx, in, info, handler) +} +func (m *MsgChannelUpgradeOpenResponse) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeOpenResponse.Merge(m, src) +} +func (m *MsgChannelUpgradeOpenResponse) XXX_Size() int { + return m.Size() +} +func (m *MsgChannelUpgradeOpenResponse) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeOpenResponse.DiscardUnknown(m) } -func _Msg_TimeoutOnClose_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(MsgTimeoutOnClose) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(MsgServer).TimeoutOnClose(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: "/ibc.core.channel.v1.Msg/TimeoutOnClose", - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(MsgServer).TimeoutOnClose(ctx, req.(*MsgTimeoutOnClose)) - } - return interceptor(ctx, in, info, handler) +var xxx_messageInfo_MsgChannelUpgradeOpenResponse proto.InternalMessageInfo + +// MsgChannelUpgradeTimeout defines the request type for the ChannelUpgradeTimeout rpc +type MsgChannelUpgradeTimeout struct { + PortId string `protobuf:"bytes,1,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` + ChannelId string `protobuf:"bytes,2,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` + CounterpartyChannel Channel `protobuf:"bytes,3,opt,name=counterparty_channel,json=counterpartyChannel,proto3" json:"counterparty_channel"` + ProofChannel []byte `protobuf:"bytes,4,opt,name=proof_channel,json=proofChannel,proto3" json:"proof_channel,omitempty"` + ProofHeight types.Height `protobuf:"bytes,5,opt,name=proof_height,json=proofHeight,proto3" json:"proof_height"` + Signer string `protobuf:"bytes,6,opt,name=signer,proto3" json:"signer,omitempty"` } -func _Msg_Acknowledgement_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(MsgAcknowledgement) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(MsgServer).Acknowledgement(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: "/ibc.core.channel.v1.Msg/Acknowledgement", - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(MsgServer).Acknowledgement(ctx, req.(*MsgAcknowledgement)) +func (m *MsgChannelUpgradeTimeout) Reset() { *m = MsgChannelUpgradeTimeout{} } +func (m *MsgChannelUpgradeTimeout) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeTimeout) ProtoMessage() {} +func (*MsgChannelUpgradeTimeout) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{30} +} +func (m *MsgChannelUpgradeTimeout) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgChannelUpgradeTimeout) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeTimeout.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil } - return interceptor(ctx, in, info, handler) +} +func (m *MsgChannelUpgradeTimeout) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeTimeout.Merge(m, src) +} +func (m *MsgChannelUpgradeTimeout) XXX_Size() int { + return m.Size() +} +func (m *MsgChannelUpgradeTimeout) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeTimeout.DiscardUnknown(m) } -var _Msg_serviceDesc = grpc.ServiceDesc{ - ServiceName: "ibc.core.channel.v1.Msg", - HandlerType: (*MsgServer)(nil), - Methods: []grpc.MethodDesc{ - { - MethodName: "ChannelOpenInit", - Handler: _Msg_ChannelOpenInit_Handler, - }, - { - MethodName: "ChannelOpenTry", - Handler: _Msg_ChannelOpenTry_Handler, - }, - { - MethodName: "ChannelOpenAck", - Handler: _Msg_ChannelOpenAck_Handler, - }, - { - MethodName: "ChannelOpenConfirm", - Handler: _Msg_ChannelOpenConfirm_Handler, - }, - { - MethodName: "ChannelCloseInit", - Handler: _Msg_ChannelCloseInit_Handler, - }, - { - MethodName: "ChannelCloseConfirm", - Handler: _Msg_ChannelCloseConfirm_Handler, - }, - { - MethodName: "RecvPacket", - Handler: _Msg_RecvPacket_Handler, - }, - { - MethodName: "Timeout", - Handler: _Msg_Timeout_Handler, - }, - { - MethodName: "TimeoutOnClose", - Handler: _Msg_TimeoutOnClose_Handler, - }, - { - MethodName: "Acknowledgement", - Handler: _Msg_Acknowledgement_Handler, - }, - }, - Streams: []grpc.StreamDesc{}, - Metadata: "ibc/core/channel/v1/tx.proto", -} +var xxx_messageInfo_MsgChannelUpgradeTimeout proto.InternalMessageInfo -func (m *MsgChannelOpenInit) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { - return nil, err - } - return dAtA[:n], nil +// MsgChannelUpgradeTimeoutRepsonse defines the MsgChannelUpgradeTimeout response type +type MsgChannelUpgradeTimeoutResponse struct { } -func (m *MsgChannelOpenInit) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func (m *MsgChannelUpgradeTimeoutResponse) Reset() { *m = MsgChannelUpgradeTimeoutResponse{} } +func (m *MsgChannelUpgradeTimeoutResponse) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeTimeoutResponse) ProtoMessage() {} +func (*MsgChannelUpgradeTimeoutResponse) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{31} } - -func (m *MsgChannelOpenInit) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if len(m.Signer) > 0 { - i -= len(m.Signer) - copy(dAtA[i:], m.Signer) - i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) - i-- - dAtA[i] = 0x1a - } - { - size, err := m.Channel.MarshalToSizedBuffer(dAtA[:i]) +func (m *MsgChannelUpgradeTimeoutResponse) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgChannelUpgradeTimeoutResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeTimeoutResponse.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) if err != nil { - return 0, err + return nil, err } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) - } - i-- - dAtA[i] = 0x12 - if len(m.PortId) > 0 { - i -= len(m.PortId) - copy(dAtA[i:], m.PortId) - i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) - i-- - dAtA[i] = 0xa + return b[:n], nil } - return len(dAtA) - i, nil } - -func (m *MsgChannelOpenInitResponse) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { - return nil, err - } - return dAtA[:n], nil +func (m *MsgChannelUpgradeTimeoutResponse) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeTimeoutResponse.Merge(m, src) } - -func (m *MsgChannelOpenInitResponse) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func (m *MsgChannelUpgradeTimeoutResponse) XXX_Size() int { + return m.Size() +} +func (m *MsgChannelUpgradeTimeoutResponse) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeTimeoutResponse.DiscardUnknown(m) } -func (m *MsgChannelOpenInitResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if len(m.Version) > 0 { - i -= len(m.Version) - copy(dAtA[i:], m.Version) - i = encodeVarintTx(dAtA, i, uint64(len(m.Version))) - i-- - dAtA[i] = 0x12 - } - if len(m.ChannelId) > 0 { - i -= len(m.ChannelId) - copy(dAtA[i:], m.ChannelId) - i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) - i-- - dAtA[i] = 0xa - } - return len(dAtA) - i, nil +var xxx_messageInfo_MsgChannelUpgradeTimeoutResponse proto.InternalMessageInfo + +// MsgChannelUpgradeCancel defines the request type for the ChannelUpgradeCancel rpc +type MsgChannelUpgradeCancel struct { + PortId string `protobuf:"bytes,1,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` + ChannelId string `protobuf:"bytes,2,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` + ErrorReceipt ErrorReceipt `protobuf:"bytes,3,opt,name=error_receipt,json=errorReceipt,proto3" json:"error_receipt"` + ProofErrorReceipt []byte `protobuf:"bytes,4,opt,name=proof_error_receipt,json=proofErrorReceipt,proto3" json:"proof_error_receipt,omitempty"` + ProofHeight types.Height `protobuf:"bytes,5,opt,name=proof_height,json=proofHeight,proto3" json:"proof_height"` + Signer string `protobuf:"bytes,6,opt,name=signer,proto3" json:"signer,omitempty"` } -func (m *MsgChannelOpenTry) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { - return nil, err +func (m *MsgChannelUpgradeCancel) Reset() { *m = MsgChannelUpgradeCancel{} } +func (m *MsgChannelUpgradeCancel) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeCancel) ProtoMessage() {} +func (*MsgChannelUpgradeCancel) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{32} +} +func (m *MsgChannelUpgradeCancel) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgChannelUpgradeCancel) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeCancel.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil } - return dAtA[:n], nil +} +func (m *MsgChannelUpgradeCancel) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeCancel.Merge(m, src) +} +func (m *MsgChannelUpgradeCancel) XXX_Size() int { + return m.Size() +} +func (m *MsgChannelUpgradeCancel) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeCancel.DiscardUnknown(m) } -func (m *MsgChannelOpenTry) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +var xxx_messageInfo_MsgChannelUpgradeCancel proto.InternalMessageInfo + +// MsgChannelUpgradeCancelResponse defines the MsgChannelUpgradeCancel response type +type MsgChannelUpgradeCancelResponse struct { } -func (m *MsgChannelOpenTry) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if len(m.Signer) > 0 { - i -= len(m.Signer) - copy(dAtA[i:], m.Signer) - i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) - i-- - dAtA[i] = 0x3a - } - { - size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) +func (m *MsgChannelUpgradeCancelResponse) Reset() { *m = MsgChannelUpgradeCancelResponse{} } +func (m *MsgChannelUpgradeCancelResponse) String() string { return proto.CompactTextString(m) } +func (*MsgChannelUpgradeCancelResponse) ProtoMessage() {} +func (*MsgChannelUpgradeCancelResponse) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{33} +} +func (m *MsgChannelUpgradeCancelResponse) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgChannelUpgradeCancelResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgChannelUpgradeCancelResponse.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) if err != nil { - return 0, err + return nil, err } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) - } - i-- - dAtA[i] = 0x32 - if len(m.ProofInit) > 0 { - i -= len(m.ProofInit) - copy(dAtA[i:], m.ProofInit) - i = encodeVarintTx(dAtA, i, uint64(len(m.ProofInit))) - i-- - dAtA[i] = 0x2a - } - if len(m.CounterpartyVersion) > 0 { - i -= len(m.CounterpartyVersion) - copy(dAtA[i:], m.CounterpartyVersion) - i = encodeVarintTx(dAtA, i, uint64(len(m.CounterpartyVersion))) - i-- - dAtA[i] = 0x22 + return b[:n], nil } - { - size, err := m.Channel.MarshalToSizedBuffer(dAtA[:i]) +} +func (m *MsgChannelUpgradeCancelResponse) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgChannelUpgradeCancelResponse.Merge(m, src) +} +func (m *MsgChannelUpgradeCancelResponse) XXX_Size() int { + return m.Size() +} +func (m *MsgChannelUpgradeCancelResponse) XXX_DiscardUnknown() { + xxx_messageInfo_MsgChannelUpgradeCancelResponse.DiscardUnknown(m) +} + +var xxx_messageInfo_MsgChannelUpgradeCancelResponse proto.InternalMessageInfo + +// MsgUpdateParams is the MsgUpdateParams request type. +type MsgUpdateParams struct { + // authority is the address that controls the module (defaults to x/gov unless overwritten). + Authority string `protobuf:"bytes,1,opt,name=authority,proto3" json:"authority,omitempty"` + // params defines the channel parameters to update. + // + // NOTE: All parameters must be supplied. + Params Params `protobuf:"bytes,2,opt,name=params,proto3" json:"params"` +} + +func (m *MsgUpdateParams) Reset() { *m = MsgUpdateParams{} } +func (m *MsgUpdateParams) String() string { return proto.CompactTextString(m) } +func (*MsgUpdateParams) ProtoMessage() {} +func (*MsgUpdateParams) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{34} +} +func (m *MsgUpdateParams) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgUpdateParams) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgUpdateParams.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) if err != nil { - return 0, err + return nil, err } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) - } - i-- - dAtA[i] = 0x1a - if len(m.PreviousChannelId) > 0 { - i -= len(m.PreviousChannelId) - copy(dAtA[i:], m.PreviousChannelId) - i = encodeVarintTx(dAtA, i, uint64(len(m.PreviousChannelId))) - i-- - dAtA[i] = 0x12 - } - if len(m.PortId) > 0 { - i -= len(m.PortId) - copy(dAtA[i:], m.PortId) - i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) - i-- - dAtA[i] = 0xa + return b[:n], nil } - return len(dAtA) - i, nil } - -func (m *MsgChannelOpenTryResponse) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { - return nil, err - } - return dAtA[:n], nil +func (m *MsgUpdateParams) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgUpdateParams.Merge(m, src) +} +func (m *MsgUpdateParams) XXX_Size() int { + return m.Size() +} +func (m *MsgUpdateParams) XXX_DiscardUnknown() { + xxx_messageInfo_MsgUpdateParams.DiscardUnknown(m) } -func (m *MsgChannelOpenTryResponse) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +var xxx_messageInfo_MsgUpdateParams proto.InternalMessageInfo + +// MsgUpdateParamsResponse defines the MsgUpdateParams response type. +type MsgUpdateParamsResponse struct { } -func (m *MsgChannelOpenTryResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if len(m.ChannelId) > 0 { - i -= len(m.ChannelId) - copy(dAtA[i:], m.ChannelId) - i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) - i-- - dAtA[i] = 0x12 - } - if len(m.Version) > 0 { - i -= len(m.Version) - copy(dAtA[i:], m.Version) - i = encodeVarintTx(dAtA, i, uint64(len(m.Version))) - i-- - dAtA[i] = 0xa - } - return len(dAtA) - i, nil +func (m *MsgUpdateParamsResponse) Reset() { *m = MsgUpdateParamsResponse{} } +func (m *MsgUpdateParamsResponse) String() string { return proto.CompactTextString(m) } +func (*MsgUpdateParamsResponse) ProtoMessage() {} +func (*MsgUpdateParamsResponse) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{35} } - -func (m *MsgChannelOpenAck) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { - return nil, err +func (m *MsgUpdateParamsResponse) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgUpdateParamsResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgUpdateParamsResponse.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil } - return dAtA[:n], nil +} +func (m *MsgUpdateParamsResponse) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgUpdateParamsResponse.Merge(m, src) +} +func (m *MsgUpdateParamsResponse) XXX_Size() int { + return m.Size() +} +func (m *MsgUpdateParamsResponse) XXX_DiscardUnknown() { + xxx_messageInfo_MsgUpdateParamsResponse.DiscardUnknown(m) } -func (m *MsgChannelOpenAck) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +var xxx_messageInfo_MsgUpdateParamsResponse proto.InternalMessageInfo + +// MsgPruneAcknowledgements defines the request type for the PruneAcknowledgements rpc. +type MsgPruneAcknowledgements struct { + PortId string `protobuf:"bytes,1,opt,name=port_id,json=portId,proto3" json:"port_id,omitempty"` + ChannelId string `protobuf:"bytes,2,opt,name=channel_id,json=channelId,proto3" json:"channel_id,omitempty"` + Limit uint64 `protobuf:"varint,3,opt,name=limit,proto3" json:"limit,omitempty"` + Signer string `protobuf:"bytes,4,opt,name=signer,proto3" json:"signer,omitempty"` } -func (m *MsgChannelOpenAck) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if len(m.Signer) > 0 { - i -= len(m.Signer) - copy(dAtA[i:], m.Signer) - i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) - i-- - dAtA[i] = 0x3a - } - { - size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) +func (m *MsgPruneAcknowledgements) Reset() { *m = MsgPruneAcknowledgements{} } +func (m *MsgPruneAcknowledgements) String() string { return proto.CompactTextString(m) } +func (*MsgPruneAcknowledgements) ProtoMessage() {} +func (*MsgPruneAcknowledgements) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{36} +} +func (m *MsgPruneAcknowledgements) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgPruneAcknowledgements) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgPruneAcknowledgements.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) if err != nil { - return 0, err + return nil, err } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) - } - i-- - dAtA[i] = 0x32 - if len(m.ProofTry) > 0 { - i -= len(m.ProofTry) - copy(dAtA[i:], m.ProofTry) - i = encodeVarintTx(dAtA, i, uint64(len(m.ProofTry))) - i-- - dAtA[i] = 0x2a - } - if len(m.CounterpartyVersion) > 0 { - i -= len(m.CounterpartyVersion) - copy(dAtA[i:], m.CounterpartyVersion) - i = encodeVarintTx(dAtA, i, uint64(len(m.CounterpartyVersion))) - i-- - dAtA[i] = 0x22 - } - if len(m.CounterpartyChannelId) > 0 { - i -= len(m.CounterpartyChannelId) - copy(dAtA[i:], m.CounterpartyChannelId) - i = encodeVarintTx(dAtA, i, uint64(len(m.CounterpartyChannelId))) - i-- - dAtA[i] = 0x1a - } - if len(m.ChannelId) > 0 { - i -= len(m.ChannelId) - copy(dAtA[i:], m.ChannelId) - i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) - i-- - dAtA[i] = 0x12 - } - if len(m.PortId) > 0 { - i -= len(m.PortId) - copy(dAtA[i:], m.PortId) - i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) - i-- - dAtA[i] = 0xa + return b[:n], nil } - return len(dAtA) - i, nil } - -func (m *MsgChannelOpenAckResponse) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { - return nil, err - } - return dAtA[:n], nil +func (m *MsgPruneAcknowledgements) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgPruneAcknowledgements.Merge(m, src) } - -func (m *MsgChannelOpenAckResponse) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func (m *MsgPruneAcknowledgements) XXX_Size() int { + return m.Size() } - -func (m *MsgChannelOpenAckResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - return len(dAtA) - i, nil +func (m *MsgPruneAcknowledgements) XXX_DiscardUnknown() { + xxx_messageInfo_MsgPruneAcknowledgements.DiscardUnknown(m) } -func (m *MsgChannelOpenConfirm) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { - return nil, err - } - return dAtA[:n], nil -} +var xxx_messageInfo_MsgPruneAcknowledgements proto.InternalMessageInfo -func (m *MsgChannelOpenConfirm) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +// MsgPruneAcknowledgementsResponse defines the response type for the PruneAcknowledgements rpc. +type MsgPruneAcknowledgementsResponse struct { + // Number of sequences pruned (includes both packet acknowledgements and packet receipts where appropriate). + TotalPrunedSequences uint64 `protobuf:"varint,1,opt,name=total_pruned_sequences,json=totalPrunedSequences,proto3" json:"total_pruned_sequences,omitempty"` + // Number of sequences left after pruning. + TotalRemainingSequences uint64 `protobuf:"varint,2,opt,name=total_remaining_sequences,json=totalRemainingSequences,proto3" json:"total_remaining_sequences,omitempty"` } -func (m *MsgChannelOpenConfirm) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if len(m.Signer) > 0 { - i -= len(m.Signer) - copy(dAtA[i:], m.Signer) - i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) - i-- - dAtA[i] = 0x2a - } - { - size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) +func (m *MsgPruneAcknowledgementsResponse) Reset() { *m = MsgPruneAcknowledgementsResponse{} } +func (m *MsgPruneAcknowledgementsResponse) String() string { return proto.CompactTextString(m) } +func (*MsgPruneAcknowledgementsResponse) ProtoMessage() {} +func (*MsgPruneAcknowledgementsResponse) Descriptor() ([]byte, []int) { + return fileDescriptor_bc4637e0ac3fc7b7, []int{37} +} +func (m *MsgPruneAcknowledgementsResponse) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *MsgPruneAcknowledgementsResponse) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_MsgPruneAcknowledgementsResponse.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) if err != nil { - return 0, err + return nil, err } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) - } - i-- - dAtA[i] = 0x22 - if len(m.ProofAck) > 0 { - i -= len(m.ProofAck) - copy(dAtA[i:], m.ProofAck) - i = encodeVarintTx(dAtA, i, uint64(len(m.ProofAck))) - i-- - dAtA[i] = 0x1a - } - if len(m.ChannelId) > 0 { - i -= len(m.ChannelId) - copy(dAtA[i:], m.ChannelId) - i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) - i-- - dAtA[i] = 0x12 - } - if len(m.PortId) > 0 { - i -= len(m.PortId) - copy(dAtA[i:], m.PortId) - i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) - i-- - dAtA[i] = 0xa + return b[:n], nil } - return len(dAtA) - i, nil +} +func (m *MsgPruneAcknowledgementsResponse) XXX_Merge(src proto.Message) { + xxx_messageInfo_MsgPruneAcknowledgementsResponse.Merge(m, src) +} +func (m *MsgPruneAcknowledgementsResponse) XXX_Size() int { + return m.Size() +} +func (m *MsgPruneAcknowledgementsResponse) XXX_DiscardUnknown() { + xxx_messageInfo_MsgPruneAcknowledgementsResponse.DiscardUnknown(m) } -func (m *MsgChannelOpenConfirmResponse) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { - return nil, err +var xxx_messageInfo_MsgPruneAcknowledgementsResponse proto.InternalMessageInfo + +func (m *MsgPruneAcknowledgementsResponse) GetTotalPrunedSequences() uint64 { + if m != nil { + return m.TotalPrunedSequences } - return dAtA[:n], nil + return 0 } -func (m *MsgChannelOpenConfirmResponse) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func (m *MsgPruneAcknowledgementsResponse) GetTotalRemainingSequences() uint64 { + if m != nil { + return m.TotalRemainingSequences + } + return 0 } -func (m *MsgChannelOpenConfirmResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - return len(dAtA) - i, nil +func init() { + proto.RegisterEnum("ibc.core.channel.v1.ResponseResultType", ResponseResultType_name, ResponseResultType_value) + proto.RegisterType((*MsgChannelOpenInit)(nil), "ibc.core.channel.v1.MsgChannelOpenInit") + proto.RegisterType((*MsgChannelOpenInitResponse)(nil), "ibc.core.channel.v1.MsgChannelOpenInitResponse") + proto.RegisterType((*MsgChannelOpenTry)(nil), "ibc.core.channel.v1.MsgChannelOpenTry") + proto.RegisterType((*MsgChannelOpenTryResponse)(nil), "ibc.core.channel.v1.MsgChannelOpenTryResponse") + proto.RegisterType((*MsgChannelOpenAck)(nil), "ibc.core.channel.v1.MsgChannelOpenAck") + proto.RegisterType((*MsgChannelOpenAckResponse)(nil), "ibc.core.channel.v1.MsgChannelOpenAckResponse") + proto.RegisterType((*MsgChannelOpenConfirm)(nil), "ibc.core.channel.v1.MsgChannelOpenConfirm") + proto.RegisterType((*MsgChannelOpenConfirmResponse)(nil), "ibc.core.channel.v1.MsgChannelOpenConfirmResponse") + proto.RegisterType((*MsgChannelCloseInit)(nil), "ibc.core.channel.v1.MsgChannelCloseInit") + proto.RegisterType((*MsgChannelCloseInitResponse)(nil), "ibc.core.channel.v1.MsgChannelCloseInitResponse") + proto.RegisterType((*MsgChannelCloseConfirm)(nil), "ibc.core.channel.v1.MsgChannelCloseConfirm") + proto.RegisterType((*MsgChannelCloseConfirmResponse)(nil), "ibc.core.channel.v1.MsgChannelCloseConfirmResponse") + proto.RegisterType((*MsgRecvPacket)(nil), "ibc.core.channel.v1.MsgRecvPacket") + proto.RegisterType((*MsgRecvPacketResponse)(nil), "ibc.core.channel.v1.MsgRecvPacketResponse") + proto.RegisterType((*MsgTimeout)(nil), "ibc.core.channel.v1.MsgTimeout") + proto.RegisterType((*MsgTimeoutResponse)(nil), "ibc.core.channel.v1.MsgTimeoutResponse") + proto.RegisterType((*MsgTimeoutOnClose)(nil), "ibc.core.channel.v1.MsgTimeoutOnClose") + proto.RegisterType((*MsgTimeoutOnCloseResponse)(nil), "ibc.core.channel.v1.MsgTimeoutOnCloseResponse") + proto.RegisterType((*MsgAcknowledgement)(nil), "ibc.core.channel.v1.MsgAcknowledgement") + proto.RegisterType((*MsgAcknowledgementResponse)(nil), "ibc.core.channel.v1.MsgAcknowledgementResponse") + proto.RegisterType((*MsgChannelUpgradeInit)(nil), "ibc.core.channel.v1.MsgChannelUpgradeInit") + proto.RegisterType((*MsgChannelUpgradeInitResponse)(nil), "ibc.core.channel.v1.MsgChannelUpgradeInitResponse") + proto.RegisterType((*MsgChannelUpgradeTry)(nil), "ibc.core.channel.v1.MsgChannelUpgradeTry") + proto.RegisterType((*MsgChannelUpgradeTryResponse)(nil), "ibc.core.channel.v1.MsgChannelUpgradeTryResponse") + proto.RegisterType((*MsgChannelUpgradeAck)(nil), "ibc.core.channel.v1.MsgChannelUpgradeAck") + proto.RegisterType((*MsgChannelUpgradeAckResponse)(nil), "ibc.core.channel.v1.MsgChannelUpgradeAckResponse") + proto.RegisterType((*MsgChannelUpgradeConfirm)(nil), "ibc.core.channel.v1.MsgChannelUpgradeConfirm") + proto.RegisterType((*MsgChannelUpgradeConfirmResponse)(nil), "ibc.core.channel.v1.MsgChannelUpgradeConfirmResponse") + proto.RegisterType((*MsgChannelUpgradeOpen)(nil), "ibc.core.channel.v1.MsgChannelUpgradeOpen") + proto.RegisterType((*MsgChannelUpgradeOpenResponse)(nil), "ibc.core.channel.v1.MsgChannelUpgradeOpenResponse") + proto.RegisterType((*MsgChannelUpgradeTimeout)(nil), "ibc.core.channel.v1.MsgChannelUpgradeTimeout") + proto.RegisterType((*MsgChannelUpgradeTimeoutResponse)(nil), "ibc.core.channel.v1.MsgChannelUpgradeTimeoutResponse") + proto.RegisterType((*MsgChannelUpgradeCancel)(nil), "ibc.core.channel.v1.MsgChannelUpgradeCancel") + proto.RegisterType((*MsgChannelUpgradeCancelResponse)(nil), "ibc.core.channel.v1.MsgChannelUpgradeCancelResponse") + proto.RegisterType((*MsgUpdateParams)(nil), "ibc.core.channel.v1.MsgUpdateParams") + proto.RegisterType((*MsgUpdateParamsResponse)(nil), "ibc.core.channel.v1.MsgUpdateParamsResponse") + proto.RegisterType((*MsgPruneAcknowledgements)(nil), "ibc.core.channel.v1.MsgPruneAcknowledgements") + proto.RegisterType((*MsgPruneAcknowledgementsResponse)(nil), "ibc.core.channel.v1.MsgPruneAcknowledgementsResponse") } -func (m *MsgChannelCloseInit) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { - return nil, err - } - return dAtA[:n], nil -} +func init() { proto.RegisterFile("ibc/core/channel/v1/tx.proto", fileDescriptor_bc4637e0ac3fc7b7) } -func (m *MsgChannelCloseInit) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +var fileDescriptor_bc4637e0ac3fc7b7 = []byte{ + // 1963 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xcc, 0x5a, 0xcf, 0x6f, 0xe3, 0xc6, + 0x15, 0x36, 0xf5, 0x73, 0xfd, 0xbc, 0x1b, 0x69, 0x29, 0xef, 0x5a, 0xa6, 0x6d, 0x59, 0xab, 0x16, + 0x59, 0xc7, 0xdd, 0x95, 0x62, 0x67, 0xb7, 0x68, 0x16, 0x01, 0x5a, 0xaf, 0xaa, 0x6d, 0x0c, 0xac, + 0xd7, 0x06, 0x65, 0x15, 0x6d, 0x52, 0x54, 0x90, 0xa9, 0x59, 0x8a, 0x90, 0x44, 0x32, 0x24, 0xa5, + 0xc4, 0x05, 0x5a, 0x14, 0x3d, 0x2d, 0xf6, 0x10, 0xb4, 0x40, 0xae, 0x0b, 0xb4, 0xe8, 0x3f, 0x90, + 0x73, 0x9b, 0x1e, 0x7a, 0xcb, 0xa9, 0xc8, 0x31, 0x28, 0xd0, 0xa0, 0xd8, 0x3d, 0xe4, 0xd2, 0xbf, + 0xa0, 0x40, 0x81, 0x82, 0x33, 0x43, 0x8a, 0x22, 0x87, 0x12, 0x65, 0x29, 0x46, 0x6e, 0xe2, 0xcc, + 0x37, 0xef, 0xbd, 0xf9, 0xbe, 0x37, 0x8f, 0x33, 0x43, 0xc1, 0xa6, 0x72, 0x26, 0x55, 0x24, 0xcd, + 0x40, 0x15, 0xa9, 0xd3, 0x52, 0x55, 0xd4, 0xab, 0x0c, 0xf7, 0x2a, 0xd6, 0x47, 0x65, 0xdd, 0xd0, + 0x2c, 0x8d, 0xcf, 0x29, 0x67, 0x52, 0xd9, 0xee, 0x2d, 0xd3, 0xde, 0xf2, 0x70, 0x4f, 0x58, 0x95, + 0x35, 0x59, 0xc3, 0xfd, 0x15, 0xfb, 0x17, 0x81, 0x0a, 0x6b, 0x92, 0x66, 0xf6, 0x35, 0xb3, 0xd2, + 0x37, 0x65, 0xdb, 0x44, 0xdf, 0x94, 0x69, 0xc7, 0xf6, 0xc8, 0x43, 0x4f, 0x41, 0xaa, 0x65, 0xf7, + 0x92, 0x5f, 0x14, 0x70, 0x8b, 0x15, 0x82, 0xe3, 0x6f, 0x02, 0x64, 0xa0, 0xcb, 0x46, 0xab, 0x8d, + 0x08, 0xa4, 0xf4, 0x09, 0x07, 0xfc, 0x91, 0x29, 0x57, 0x49, 0xff, 0xb1, 0x8e, 0xd4, 0x43, 0x55, + 0xb1, 0xf8, 0x35, 0x48, 0xeb, 0x9a, 0x61, 0x35, 0x95, 0x76, 0x9e, 0x2b, 0x72, 0x3b, 0xcb, 0x62, + 0xca, 0x7e, 0x3c, 0x6c, 0xf3, 0xef, 0x40, 0x9a, 0xda, 0xca, 0xc7, 0x8a, 0xdc, 0xce, 0xca, 0xfe, + 0x66, 0x99, 0x31, 0xd9, 0x32, 0xb5, 0xf7, 0x30, 0xf1, 0xf9, 0x57, 0xdb, 0x4b, 0xa2, 0x33, 0x84, + 0xbf, 0x09, 0x29, 0x53, 0x91, 0x55, 0x64, 0xe4, 0xe3, 0xc4, 0x2a, 0x79, 0x7a, 0x90, 0x79, 0xf6, + 0xc7, 0xed, 0xa5, 0xdf, 0x7d, 0xfd, 0xe9, 0x2e, 0x6d, 0x28, 0xbd, 0x0f, 0x42, 0x30, 0x2a, 0x11, + 0x99, 0xba, 0xa6, 0x9a, 0x88, 0xdf, 0x02, 0xa0, 0x16, 0x47, 0x01, 0x2e, 0xd3, 0x96, 0xc3, 0x36, + 0x9f, 0x87, 0xf4, 0x10, 0x19, 0xa6, 0xa2, 0xa9, 0x38, 0xc6, 0x65, 0xd1, 0x79, 0x7c, 0x90, 0xb0, + 0xfd, 0x94, 0xbe, 0x8a, 0xc1, 0xf5, 0x71, 0xeb, 0xa7, 0xc6, 0x79, 0xf8, 0x94, 0xf7, 0x21, 0xa7, + 0x1b, 0x68, 0xa8, 0x68, 0x03, 0xb3, 0xe9, 0x71, 0x8b, 0x4d, 0x3f, 0x8c, 0xe5, 0x39, 0xf1, 0xba, + 0xd3, 0x5d, 0x75, 0x43, 0xf0, 0xd0, 0x14, 0x9f, 0x9d, 0xa6, 0x3d, 0x58, 0x95, 0xb4, 0x81, 0x6a, + 0x21, 0x43, 0x6f, 0x19, 0xd6, 0x79, 0xd3, 0x99, 0x4d, 0x02, 0xc7, 0x95, 0xf3, 0xf6, 0xfd, 0x94, + 0x74, 0xd9, 0x94, 0xe8, 0x86, 0xa6, 0x3d, 0x6d, 0x2a, 0xaa, 0x62, 0xe5, 0x93, 0x45, 0x6e, 0xe7, + 0xaa, 0xb8, 0x8c, 0x5b, 0xb0, 0x9e, 0x55, 0xb8, 0x4a, 0xba, 0x3b, 0x48, 0x91, 0x3b, 0x56, 0x3e, + 0x85, 0x83, 0x12, 0x3c, 0x41, 0x91, 0xd4, 0x1a, 0xee, 0x95, 0xdf, 0xc5, 0x08, 0x1a, 0xd2, 0x0a, + 0x1e, 0x45, 0x9a, 0x3c, 0xea, 0xa5, 0x27, 0xab, 0xf7, 0x1e, 0xac, 0x07, 0xf8, 0x75, 0xc5, 0xf3, + 0xa8, 0xc3, 0x8d, 0xa9, 0xe3, 0x93, 0x35, 0xe6, 0x93, 0x95, 0x8a, 0xf7, 0xf7, 0x80, 0x78, 0x07, + 0x52, 0x37, 0x5c, 0xbc, 0xc9, 0x36, 0xf9, 0xef, 0xc3, 0xda, 0x18, 0xd3, 0x1e, 0x2c, 0xc9, 0xd0, + 0x1b, 0xde, 0xee, 0x91, 0xbe, 0x17, 0x50, 0x68, 0x03, 0x88, 0x1e, 0x4d, 0xcb, 0x38, 0xa7, 0x02, + 0x5d, 0xc1, 0x0d, 0x76, 0xf2, 0x5d, 0xae, 0x3e, 0x1b, 0x7e, 0x7d, 0x0e, 0xa4, 0xae, 0xa3, 0x4f, + 0xe9, 0x9f, 0x1c, 0xdc, 0x18, 0xef, 0xad, 0x6a, 0xea, 0x53, 0xc5, 0xe8, 0x5f, 0x98, 0x64, 0x77, + 0xe6, 0x2d, 0xa9, 0x8b, 0x69, 0x75, 0x66, 0x6e, 0x2b, 0xe7, 0x9f, 0x79, 0x62, 0xbe, 0x99, 0x27, + 0x27, 0xcf, 0x7c, 0x1b, 0xb6, 0x98, 0x73, 0x73, 0x67, 0x3f, 0x84, 0xdc, 0x08, 0x50, 0xed, 0x69, + 0x26, 0x9a, 0x5c, 0x0f, 0xa7, 0x4c, 0x3d, 0x72, 0xc1, 0xdb, 0x82, 0x0d, 0x86, 0x5f, 0x37, 0xac, + 0x3f, 0xc5, 0xe0, 0xa6, 0xaf, 0x7f, 0x5e, 0x55, 0xc6, 0x2b, 0x46, 0x7c, 0x5a, 0xc5, 0x58, 0xa4, + 0x2e, 0xfc, 0x43, 0xd8, 0x1a, 0x5b, 0x3e, 0xf4, 0x9d, 0xd4, 0x34, 0xd1, 0x07, 0x03, 0xa4, 0x4a, + 0x08, 0xe7, 0x7f, 0x42, 0xdc, 0xf0, 0x82, 0x1a, 0x04, 0x53, 0xa7, 0x90, 0x20, 0x85, 0x45, 0x28, + 0xb0, 0x29, 0x72, 0x59, 0x7c, 0xc5, 0xc1, 0xb5, 0x23, 0x53, 0x16, 0x91, 0x34, 0x3c, 0x69, 0x49, + 0x5d, 0x64, 0xf1, 0x6f, 0x43, 0x4a, 0xc7, 0xbf, 0x30, 0x77, 0x2b, 0xfb, 0x1b, 0xcc, 0x32, 0x4d, + 0xc0, 0x74, 0x82, 0x74, 0x00, 0xff, 0x06, 0x64, 0x09, 0x41, 0x92, 0xd6, 0xef, 0x2b, 0x56, 0x1f, + 0xa9, 0x16, 0x26, 0xf9, 0xaa, 0x98, 0xc1, 0xed, 0x55, 0xb7, 0x39, 0xc0, 0x65, 0x7c, 0x3e, 0x2e, + 0x13, 0x93, 0x53, 0xe9, 0x97, 0x78, 0xfd, 0x8e, 0x26, 0xe9, 0x56, 0xde, 0x1f, 0x42, 0xca, 0x40, + 0xe6, 0xa0, 0x47, 0x26, 0xfb, 0xda, 0xfe, 0x6d, 0xe6, 0x64, 0x1d, 0xb8, 0x88, 0xa1, 0xa7, 0xe7, + 0x3a, 0x12, 0xe9, 0x30, 0x5a, 0x81, 0x3f, 0x8e, 0x01, 0x1c, 0x99, 0xf2, 0xa9, 0xd2, 0x47, 0xda, + 0x60, 0x31, 0x14, 0x0e, 0x54, 0x03, 0x49, 0x48, 0x19, 0xa2, 0xf6, 0x18, 0x85, 0x0d, 0xb7, 0x79, + 0x31, 0x14, 0xde, 0x01, 0x5e, 0x45, 0x1f, 0x59, 0x6e, 0x9a, 0x35, 0x0d, 0x24, 0x0d, 0x31, 0x9d, + 0x09, 0x31, 0x6b, 0xf7, 0x38, 0xc9, 0x65, 0x93, 0x17, 0xbd, 0xa8, 0xbc, 0x8f, 0xb7, 0x50, 0x94, + 0x8f, 0x45, 0xb3, 0xfd, 0x5f, 0xf2, 0xbe, 0xa3, 0xd6, 0x8f, 0x55, 0x9c, 0xd8, 0x97, 0x44, 0xfa, + 0x36, 0xac, 0xd0, 0x14, 0xb7, 0x9d, 0xd2, 0x1a, 0x41, 0xaa, 0x06, 0x09, 0x63, 0x21, 0x45, 0x82, + 0xad, 0x4a, 0x72, 0xaa, 0x2a, 0xa9, 0xd9, 0x4a, 0x4a, 0xfa, 0x02, 0x25, 0xe5, 0x0c, 0xbf, 0x28, + 0xc7, 0xb9, 0x5f, 0xb4, 0xc0, 0xcf, 0x62, 0x38, 0x7d, 0x0e, 0xa4, 0xae, 0xaa, 0x7d, 0xd8, 0x43, + 0x6d, 0x19, 0xe1, 0x9a, 0x31, 0x87, 0xc2, 0x3b, 0x90, 0x69, 0x8d, 0x5b, 0x73, 0x04, 0xf6, 0x35, + 0x8f, 0x04, 0xb6, 0x07, 0xb6, 0xc7, 0x04, 0x3e, 0xb0, 0x5b, 0x2e, 0xf9, 0xed, 0x2c, 0xe1, 0x5d, + 0xbf, 0x8f, 0x89, 0x45, 0xf3, 0xfd, 0x97, 0xb1, 0xfd, 0x0d, 0x4d, 0x81, 0xb9, 0x5e, 0xf2, 0x3f, + 0x82, 0xd4, 0x53, 0x05, 0xf5, 0xda, 0x26, 0xad, 0x4a, 0x25, 0x66, 0x60, 0xd4, 0xd3, 0x23, 0x8c, + 0x74, 0x14, 0x23, 0xe3, 0xa2, 0xd7, 0xf6, 0x8f, 0x39, 0xef, 0x06, 0xc6, 0x13, 0xbc, 0xcb, 0xd2, + 0x3b, 0x90, 0xa6, 0xa9, 0x4f, 0x13, 0x67, 0x73, 0x52, 0x34, 0xce, 0xc9, 0x83, 0x0e, 0xb1, 0x8b, + 0x43, 0x60, 0xe1, 0xc4, 0xf0, 0xc2, 0xc9, 0x0c, 0x7c, 0x8b, 0x85, 0xb0, 0xf9, 0xbf, 0x38, 0xac, + 0x06, 0x02, 0x9a, 0x78, 0x9c, 0x9a, 0x42, 0xe6, 0x4f, 0xa0, 0xa8, 0x1b, 0x9a, 0xae, 0x99, 0xa8, + 0xed, 0xae, 0x61, 0x49, 0x53, 0x55, 0x24, 0x59, 0x8a, 0xa6, 0x36, 0x3b, 0x9a, 0x6e, 0xd3, 0x1c, + 0xdf, 0x59, 0x16, 0xb7, 0x1c, 0x1c, 0xf5, 0x5a, 0x75, 0x51, 0xef, 0x6a, 0xba, 0xc9, 0x77, 0x60, + 0x83, 0x59, 0x10, 0xa8, 0x54, 0x89, 0x19, 0xa5, 0x5a, 0x67, 0x14, 0x0e, 0x02, 0x98, 0x5e, 0x7a, + 0x92, 0x53, 0x4b, 0x0f, 0xff, 0x1d, 0xb8, 0x46, 0x4b, 0x2d, 0x3d, 0x36, 0xa6, 0xf0, 0x5a, 0x24, + 0xab, 0x8f, 0xb2, 0x3b, 0x02, 0x39, 0x0a, 0xa7, 0x3d, 0x20, 0x6a, 0x31, 0xb0, 0x64, 0xaf, 0xcc, + 0xb7, 0x64, 0x97, 0x27, 0x27, 0xe4, 0x3f, 0x38, 0xd8, 0x64, 0xe9, 0x7f, 0xe9, 0xf9, 0xe8, 0x29, + 0x0f, 0xf1, 0x79, 0xca, 0xc3, 0xbf, 0x62, 0x8c, 0x84, 0x9e, 0xe7, 0x88, 0xd9, 0xf0, 0x1d, 0x15, + 0x1d, 0x36, 0xe2, 0x91, 0xd9, 0xc8, 0x31, 0x12, 0x27, 0x98, 0x30, 0x89, 0x28, 0x09, 0x93, 0x8c, + 0x90, 0x30, 0xdf, 0xec, 0xd9, 0x13, 0x31, 0xf2, 0xc5, 0x73, 0xfc, 0x5c, 0x54, 0x95, 0xff, 0x6b, + 0x1c, 0xf2, 0x01, 0x3f, 0xf3, 0x1e, 0x99, 0x7e, 0x06, 0x02, 0xf3, 0xb6, 0xc0, 0xb4, 0x5a, 0x16, + 0xa2, 0x69, 0x27, 0x30, 0xe3, 0xad, 0xdb, 0x08, 0x31, 0xcf, 0xb8, 0x4c, 0xc0, 0x3d, 0xa1, 0x49, + 0x92, 0x58, 0x70, 0x92, 0x24, 0xa3, 0x24, 0x49, 0x2a, 0x42, 0x92, 0xa4, 0xe7, 0x4b, 0x92, 0x2b, + 0x93, 0x93, 0x44, 0x81, 0x62, 0x98, 0x78, 0x8b, 0x4e, 0x94, 0xcf, 0x62, 0x8c, 0xed, 0xc0, 0xb1, + 0x8e, 0xd4, 0x6f, 0x61, 0x96, 0x44, 0x5a, 0xf3, 0x7e, 0xa5, 0x92, 0xf3, 0x29, 0x95, 0x9a, 0xe1, + 0x42, 0xc5, 0xc3, 0x9e, 0x7b, 0xe6, 0xfe, 0x2c, 0xc6, 0x58, 0x88, 0xce, 0xd9, 0x71, 0x51, 0x35, + 0x75, 0xf6, 0xbb, 0xd6, 0x1c, 0x83, 0xe4, 0x6f, 0x23, 0xbf, 0x25, 0xc6, 0x4a, 0xf0, 0x9d, 0x34, + 0x4b, 0x7f, 0x8b, 0xc1, 0x5a, 0x70, 0xb9, 0xb4, 0x54, 0x09, 0xf5, 0x2e, 0xcc, 0xf0, 0x63, 0xb8, + 0x86, 0x0c, 0x43, 0x33, 0x9a, 0xf8, 0x30, 0xa8, 0x3b, 0x07, 0xee, 0x5b, 0x4c, 0x6a, 0x6b, 0x36, + 0x52, 0x24, 0x40, 0x3a, 0xdb, 0xab, 0xc8, 0xd3, 0xc6, 0x97, 0x21, 0x47, 0x38, 0x1b, 0xb7, 0x49, + 0xe8, 0xbd, 0x8e, 0xbb, 0xbc, 0x36, 0x2e, 0x99, 0xe3, 0x5b, 0xb0, 0x1d, 0x42, 0x9f, 0x4b, 0xf1, + 0x6f, 0x20, 0x73, 0x64, 0xca, 0x0d, 0xbd, 0xdd, 0xb2, 0xd0, 0x49, 0xcb, 0x68, 0xf5, 0x4d, 0x7e, + 0x13, 0x96, 0x5b, 0x03, 0xab, 0xa3, 0x19, 0x8a, 0x75, 0xee, 0x7c, 0x83, 0x70, 0x1b, 0xc8, 0xf1, + 0xcd, 0xc6, 0xd1, 0xcf, 0x24, 0x61, 0xc7, 0x37, 0x1b, 0x32, 0x3a, 0xbe, 0xd9, 0x4f, 0x0f, 0x78, + 0x27, 0xbe, 0x91, 0xb9, 0xd2, 0x3a, 0x56, 0xd8, 0xeb, 0xdf, 0x0d, 0xed, 0x0f, 0x1c, 0x5e, 0x60, + 0x27, 0xc6, 0x40, 0x45, 0xbe, 0xa3, 0x93, 0x79, 0x61, 0xf9, 0x57, 0x21, 0xd9, 0x53, 0xfa, 0xf4, + 0x5e, 0x30, 0x21, 0x92, 0x87, 0xe8, 0xc7, 0x94, 0x4f, 0x38, 0x9c, 0xb6, 0xcc, 0x98, 0xdc, 0x02, + 0x7e, 0x0f, 0x6e, 0x5a, 0x9a, 0xd5, 0xea, 0x35, 0x75, 0x1b, 0xd6, 0x76, 0x37, 0x78, 0x26, 0x0e, + 0x35, 0x21, 0xae, 0xe2, 0x5e, 0x6c, 0xa3, 0xed, 0xec, 0xf2, 0x4c, 0xfe, 0x01, 0xac, 0x93, 0x51, + 0x06, 0xea, 0xb7, 0x14, 0x55, 0x51, 0x65, 0xcf, 0x40, 0xb2, 0x35, 0x5c, 0xc3, 0x00, 0xd1, 0xe9, + 0x77, 0xc7, 0xee, 0x7e, 0xc9, 0x01, 0x1f, 0x7c, 0x21, 0xf0, 0xf7, 0xa1, 0x28, 0xd6, 0xea, 0x27, + 0xc7, 0x4f, 0xea, 0xb5, 0xa6, 0x58, 0xab, 0x37, 0x1e, 0x9f, 0x36, 0x4f, 0x7f, 0x7e, 0x52, 0x6b, + 0x36, 0x9e, 0xd4, 0x4f, 0x6a, 0xd5, 0xc3, 0x47, 0x87, 0xb5, 0x1f, 0x67, 0x97, 0x84, 0xcc, 0xf3, + 0x17, 0xc5, 0x15, 0x4f, 0x13, 0x7f, 0x1b, 0xd6, 0x99, 0xc3, 0x9e, 0x1c, 0x1f, 0x9f, 0x64, 0x39, + 0xe1, 0xca, 0xf3, 0x17, 0xc5, 0x84, 0xfd, 0x9b, 0xbf, 0x0b, 0x9b, 0x4c, 0x60, 0xbd, 0x51, 0xad, + 0xd6, 0xea, 0xf5, 0x6c, 0x4c, 0x58, 0x79, 0xfe, 0xa2, 0x98, 0xa6, 0x8f, 0xa1, 0xf0, 0x47, 0x07, + 0x87, 0x8f, 0x1b, 0x62, 0x2d, 0x1b, 0x27, 0x70, 0xfa, 0x28, 0x24, 0x9e, 0xfd, 0xb9, 0xb0, 0xb4, + 0xff, 0x9f, 0x2c, 0xc4, 0x8f, 0x4c, 0x99, 0xef, 0x42, 0xc6, 0xff, 0x2d, 0x8f, 0xfd, 0x62, 0x0c, + 0x7e, 0x5e, 0x13, 0x2a, 0x11, 0x81, 0xae, 0x82, 0x1d, 0x78, 0xcd, 0xf7, 0x11, 0xed, 0xf5, 0x08, + 0x26, 0x4e, 0x8d, 0x73, 0xa1, 0x1c, 0x0d, 0x17, 0xe2, 0xc9, 0xde, 0x8e, 0x47, 0xf1, 0x74, 0x20, + 0x75, 0x23, 0x79, 0xf2, 0xee, 0x3f, 0x2d, 0xe0, 0x19, 0x9f, 0x3e, 0x76, 0x23, 0x58, 0xa1, 0x58, + 0x61, 0x3f, 0x3a, 0xd6, 0xf5, 0xaa, 0x42, 0x36, 0xf0, 0xcd, 0x61, 0x67, 0x8a, 0x1d, 0x17, 0x29, + 0xbc, 0x19, 0x15, 0xe9, 0xfa, 0xfb, 0x10, 0x72, 0xac, 0x6f, 0x09, 0xdf, 0x8b, 0x62, 0xc8, 0x99, + 0xe7, 0x5b, 0x33, 0x80, 0x5d, 0xc7, 0xbf, 0x00, 0xf0, 0x5c, 0xbf, 0x97, 0xc2, 0x4c, 0x8c, 0x30, + 0xc2, 0xee, 0x74, 0x8c, 0x6b, 0xbd, 0x0e, 0x69, 0x67, 0x6b, 0xb1, 0x1d, 0x36, 0x8c, 0x02, 0x84, + 0xdb, 0x53, 0x00, 0xde, 0xdc, 0xf3, 0xdd, 0xbe, 0xbe, 0x3e, 0x65, 0x28, 0xc5, 0x85, 0xe7, 0x5e, + 0xc8, 0x8d, 0x62, 0x17, 0x32, 0xfe, 0x6b, 0xc0, 0xd0, 0x28, 0x7d, 0xc0, 0xf0, 0xc5, 0x1b, 0x76, + 0x9d, 0x36, 0x4a, 0x74, 0xef, 0x1d, 0xd8, 0xb4, 0x44, 0xf7, 0x60, 0xa7, 0x26, 0x3a, 0xeb, 0x7a, + 0xea, 0x03, 0xb8, 0x1e, 0xbc, 0x2b, 0x7a, 0x23, 0x9a, 0x21, 0xbb, 0x70, 0xec, 0x45, 0x86, 0x86, + 0xbb, 0xb4, 0xcb, 0x47, 0x44, 0x97, 0x76, 0x05, 0xd9, 0x8b, 0x0c, 0x75, 0x5d, 0xfe, 0x1a, 0x6e, + 0xb0, 0x4f, 0x9e, 0x77, 0xa3, 0xd9, 0x72, 0x96, 0xd8, 0xfd, 0x99, 0xe0, 0xe1, 0xd2, 0xe2, 0xf3, + 0x4c, 0x44, 0x69, 0x6d, 0x6c, 0x54, 0x69, 0xbd, 0x3b, 0xfd, 0xe0, 0xa4, 0x9d, 0xa5, 0x18, 0x71, + 0xd2, 0xce, 0xc2, 0xbc, 0x3f, 0x13, 0xdc, 0x75, 0xff, 0x2b, 0x58, 0x65, 0xee, 0x80, 0xef, 0x44, + 0xe4, 0x10, 0xa3, 0x85, 0x7b, 0xb3, 0xa0, 0x5d, 0xdf, 0x0a, 0xe4, 0xc8, 0xde, 0x8c, 0xa2, 0xe8, + 0x16, 0xf1, 0xbb, 0x61, 0xc6, 0xbc, 0x1b, 0x39, 0xe1, 0x4e, 0x14, 0x94, 0x97, 0x65, 0xf6, 0x56, + 0x2f, 0x94, 0x65, 0x26, 0x3c, 0x9c, 0xe5, 0x89, 0x9b, 0x36, 0x21, 0xf9, 0xdb, 0xaf, 0x3f, 0xdd, + 0xe5, 0x1e, 0xd6, 0x3f, 0x7f, 0x59, 0xe0, 0xbe, 0x78, 0x59, 0xe0, 0xfe, 0xfd, 0xb2, 0xc0, 0xfd, + 0xfe, 0x55, 0x61, 0xe9, 0x8b, 0x57, 0x85, 0xa5, 0x2f, 0x5f, 0x15, 0x96, 0xde, 0x7b, 0x5b, 0x56, + 0xac, 0xce, 0xe0, 0xac, 0x2c, 0x69, 0xfd, 0x0a, 0xfd, 0x6f, 0x93, 0x72, 0x26, 0xdd, 0x95, 0xb5, + 0xca, 0xf0, 0x07, 0x95, 0xbe, 0xd6, 0x1e, 0xf4, 0x90, 0x49, 0xfe, 0x93, 0xf4, 0xe6, 0xbd, 0xbb, + 0xce, 0xdf, 0x92, 0xac, 0x73, 0x1d, 0x99, 0x67, 0x29, 0xfc, 0x97, 0xa4, 0xb7, 0xfe, 0x1f, 0x00, + 0x00, 0xff, 0xff, 0xe5, 0xbe, 0x04, 0xd7, 0x5d, 0x25, 0x00, 0x00, } -func (m *MsgChannelCloseInit) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if len(m.Signer) > 0 { - i -= len(m.Signer) - copy(dAtA[i:], m.Signer) - i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) - i-- - dAtA[i] = 0x1a +// Reference imports to suppress errors if they are not otherwise used. +var _ context.Context +var _ grpc.ClientConn + +// This is a compile-time assertion to ensure that this generated file +// is compatible with the grpc package it is being compiled against. +const _ = grpc.SupportPackageIsVersion4 + +// MsgClient is the client API for Msg service. +// +// For semantics around ctx use and closing/ending streaming RPCs, please refer to https://godoc.org/google.golang.org/grpc#ClientConn.NewStream. +type MsgClient interface { + // ChannelOpenInit defines a rpc handler method for MsgChannelOpenInit. + ChannelOpenInit(ctx context.Context, in *MsgChannelOpenInit, opts ...grpc.CallOption) (*MsgChannelOpenInitResponse, error) + // ChannelOpenTry defines a rpc handler method for MsgChannelOpenTry. + ChannelOpenTry(ctx context.Context, in *MsgChannelOpenTry, opts ...grpc.CallOption) (*MsgChannelOpenTryResponse, error) + // ChannelOpenAck defines a rpc handler method for MsgChannelOpenAck. + ChannelOpenAck(ctx context.Context, in *MsgChannelOpenAck, opts ...grpc.CallOption) (*MsgChannelOpenAckResponse, error) + // ChannelOpenConfirm defines a rpc handler method for MsgChannelOpenConfirm. + ChannelOpenConfirm(ctx context.Context, in *MsgChannelOpenConfirm, opts ...grpc.CallOption) (*MsgChannelOpenConfirmResponse, error) + // ChannelCloseInit defines a rpc handler method for MsgChannelCloseInit. + ChannelCloseInit(ctx context.Context, in *MsgChannelCloseInit, opts ...grpc.CallOption) (*MsgChannelCloseInitResponse, error) + // ChannelCloseConfirm defines a rpc handler method for + // MsgChannelCloseConfirm. + ChannelCloseConfirm(ctx context.Context, in *MsgChannelCloseConfirm, opts ...grpc.CallOption) (*MsgChannelCloseConfirmResponse, error) + // RecvPacket defines a rpc handler method for MsgRecvPacket. + RecvPacket(ctx context.Context, in *MsgRecvPacket, opts ...grpc.CallOption) (*MsgRecvPacketResponse, error) + // Timeout defines a rpc handler method for MsgTimeout. + Timeout(ctx context.Context, in *MsgTimeout, opts ...grpc.CallOption) (*MsgTimeoutResponse, error) + // TimeoutOnClose defines a rpc handler method for MsgTimeoutOnClose. + TimeoutOnClose(ctx context.Context, in *MsgTimeoutOnClose, opts ...grpc.CallOption) (*MsgTimeoutOnCloseResponse, error) + // Acknowledgement defines a rpc handler method for MsgAcknowledgement. + Acknowledgement(ctx context.Context, in *MsgAcknowledgement, opts ...grpc.CallOption) (*MsgAcknowledgementResponse, error) + // ChannelUpgradeInit defines a rpc handler method for MsgChannelUpgradeInit. + ChannelUpgradeInit(ctx context.Context, in *MsgChannelUpgradeInit, opts ...grpc.CallOption) (*MsgChannelUpgradeInitResponse, error) + // ChannelUpgradeTry defines a rpc handler method for MsgChannelUpgradeTry. + ChannelUpgradeTry(ctx context.Context, in *MsgChannelUpgradeTry, opts ...grpc.CallOption) (*MsgChannelUpgradeTryResponse, error) + // ChannelUpgradeAck defines a rpc handler method for MsgChannelUpgradeAck. + ChannelUpgradeAck(ctx context.Context, in *MsgChannelUpgradeAck, opts ...grpc.CallOption) (*MsgChannelUpgradeAckResponse, error) + // ChannelUpgradeConfirm defines a rpc handler method for MsgChannelUpgradeConfirm. + ChannelUpgradeConfirm(ctx context.Context, in *MsgChannelUpgradeConfirm, opts ...grpc.CallOption) (*MsgChannelUpgradeConfirmResponse, error) + // ChannelUpgradeOpen defines a rpc handler method for MsgChannelUpgradeOpen. + ChannelUpgradeOpen(ctx context.Context, in *MsgChannelUpgradeOpen, opts ...grpc.CallOption) (*MsgChannelUpgradeOpenResponse, error) + // ChannelUpgradeTimeout defines a rpc handler method for MsgChannelUpgradeTimeout. + ChannelUpgradeTimeout(ctx context.Context, in *MsgChannelUpgradeTimeout, opts ...grpc.CallOption) (*MsgChannelUpgradeTimeoutResponse, error) + // ChannelUpgradeCancel defines a rpc handler method for MsgChannelUpgradeCancel. + ChannelUpgradeCancel(ctx context.Context, in *MsgChannelUpgradeCancel, opts ...grpc.CallOption) (*MsgChannelUpgradeCancelResponse, error) + // UpdateChannelParams defines a rpc handler method for MsgUpdateParams. + UpdateChannelParams(ctx context.Context, in *MsgUpdateParams, opts ...grpc.CallOption) (*MsgUpdateParamsResponse, error) + // PruneAcknowledgements defines a rpc handler method for MsgPruneAcknowledgements. + PruneAcknowledgements(ctx context.Context, in *MsgPruneAcknowledgements, opts ...grpc.CallOption) (*MsgPruneAcknowledgementsResponse, error) +} + +type msgClient struct { + cc grpc1.ClientConn +} + +func NewMsgClient(cc grpc1.ClientConn) MsgClient { + return &msgClient{cc} +} + +func (c *msgClient) ChannelOpenInit(ctx context.Context, in *MsgChannelOpenInit, opts ...grpc.CallOption) (*MsgChannelOpenInitResponse, error) { + out := new(MsgChannelOpenInitResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelOpenInit", in, out, opts...) + if err != nil { + return nil, err } - if len(m.ChannelId) > 0 { - i -= len(m.ChannelId) - copy(dAtA[i:], m.ChannelId) - i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) - i-- - dAtA[i] = 0x12 + return out, nil +} + +func (c *msgClient) ChannelOpenTry(ctx context.Context, in *MsgChannelOpenTry, opts ...grpc.CallOption) (*MsgChannelOpenTryResponse, error) { + out := new(MsgChannelOpenTryResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelOpenTry", in, out, opts...) + if err != nil { + return nil, err } - if len(m.PortId) > 0 { - i -= len(m.PortId) - copy(dAtA[i:], m.PortId) - i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) - i-- - dAtA[i] = 0xa + return out, nil +} + +func (c *msgClient) ChannelOpenAck(ctx context.Context, in *MsgChannelOpenAck, opts ...grpc.CallOption) (*MsgChannelOpenAckResponse, error) { + out := new(MsgChannelOpenAckResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelOpenAck", in, out, opts...) + if err != nil { + return nil, err } - return len(dAtA) - i, nil + return out, nil } -func (m *MsgChannelCloseInitResponse) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) +func (c *msgClient) ChannelOpenConfirm(ctx context.Context, in *MsgChannelOpenConfirm, opts ...grpc.CallOption) (*MsgChannelOpenConfirmResponse, error) { + out := new(MsgChannelOpenConfirmResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelOpenConfirm", in, out, opts...) if err != nil { return nil, err } - return dAtA[:n], nil + return out, nil } -func (m *MsgChannelCloseInitResponse) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func (c *msgClient) ChannelCloseInit(ctx context.Context, in *MsgChannelCloseInit, opts ...grpc.CallOption) (*MsgChannelCloseInitResponse, error) { + out := new(MsgChannelCloseInitResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelCloseInit", in, out, opts...) + if err != nil { + return nil, err + } + return out, nil } -func (m *MsgChannelCloseInitResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - return len(dAtA) - i, nil +func (c *msgClient) ChannelCloseConfirm(ctx context.Context, in *MsgChannelCloseConfirm, opts ...grpc.CallOption) (*MsgChannelCloseConfirmResponse, error) { + out := new(MsgChannelCloseConfirmResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelCloseConfirm", in, out, opts...) + if err != nil { + return nil, err + } + return out, nil } -func (m *MsgChannelCloseConfirm) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) +func (c *msgClient) RecvPacket(ctx context.Context, in *MsgRecvPacket, opts ...grpc.CallOption) (*MsgRecvPacketResponse, error) { + out := new(MsgRecvPacketResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/RecvPacket", in, out, opts...) if err != nil { return nil, err } - return dAtA[:n], nil + return out, nil } -func (m *MsgChannelCloseConfirm) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func (c *msgClient) Timeout(ctx context.Context, in *MsgTimeout, opts ...grpc.CallOption) (*MsgTimeoutResponse, error) { + out := new(MsgTimeoutResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/Timeout", in, out, opts...) + if err != nil { + return nil, err + } + return out, nil } -func (m *MsgChannelCloseConfirm) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if len(m.Signer) > 0 { - i -= len(m.Signer) - copy(dAtA[i:], m.Signer) - i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) - i-- - dAtA[i] = 0x2a +func (c *msgClient) TimeoutOnClose(ctx context.Context, in *MsgTimeoutOnClose, opts ...grpc.CallOption) (*MsgTimeoutOnCloseResponse, error) { + out := new(MsgTimeoutOnCloseResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/TimeoutOnClose", in, out, opts...) + if err != nil { + return nil, err } - { - size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) - if err != nil { - return 0, err - } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) + return out, nil +} + +func (c *msgClient) Acknowledgement(ctx context.Context, in *MsgAcknowledgement, opts ...grpc.CallOption) (*MsgAcknowledgementResponse, error) { + out := new(MsgAcknowledgementResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/Acknowledgement", in, out, opts...) + if err != nil { + return nil, err } - i-- - dAtA[i] = 0x22 - if len(m.ProofInit) > 0 { - i -= len(m.ProofInit) - copy(dAtA[i:], m.ProofInit) - i = encodeVarintTx(dAtA, i, uint64(len(m.ProofInit))) - i-- - dAtA[i] = 0x1a + return out, nil +} + +func (c *msgClient) ChannelUpgradeInit(ctx context.Context, in *MsgChannelUpgradeInit, opts ...grpc.CallOption) (*MsgChannelUpgradeInitResponse, error) { + out := new(MsgChannelUpgradeInitResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelUpgradeInit", in, out, opts...) + if err != nil { + return nil, err } - if len(m.ChannelId) > 0 { - i -= len(m.ChannelId) - copy(dAtA[i:], m.ChannelId) - i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) - i-- - dAtA[i] = 0x12 + return out, nil +} + +func (c *msgClient) ChannelUpgradeTry(ctx context.Context, in *MsgChannelUpgradeTry, opts ...grpc.CallOption) (*MsgChannelUpgradeTryResponse, error) { + out := new(MsgChannelUpgradeTryResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelUpgradeTry", in, out, opts...) + if err != nil { + return nil, err } - if len(m.PortId) > 0 { - i -= len(m.PortId) - copy(dAtA[i:], m.PortId) - i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) - i-- - dAtA[i] = 0xa + return out, nil +} + +func (c *msgClient) ChannelUpgradeAck(ctx context.Context, in *MsgChannelUpgradeAck, opts ...grpc.CallOption) (*MsgChannelUpgradeAckResponse, error) { + out := new(MsgChannelUpgradeAckResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelUpgradeAck", in, out, opts...) + if err != nil { + return nil, err } - return len(dAtA) - i, nil + return out, nil } -func (m *MsgChannelCloseConfirmResponse) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) +func (c *msgClient) ChannelUpgradeConfirm(ctx context.Context, in *MsgChannelUpgradeConfirm, opts ...grpc.CallOption) (*MsgChannelUpgradeConfirmResponse, error) { + out := new(MsgChannelUpgradeConfirmResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelUpgradeConfirm", in, out, opts...) if err != nil { return nil, err } - return dAtA[:n], nil + return out, nil } -func (m *MsgChannelCloseConfirmResponse) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func (c *msgClient) ChannelUpgradeOpen(ctx context.Context, in *MsgChannelUpgradeOpen, opts ...grpc.CallOption) (*MsgChannelUpgradeOpenResponse, error) { + out := new(MsgChannelUpgradeOpenResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelUpgradeOpen", in, out, opts...) + if err != nil { + return nil, err + } + return out, nil } -func (m *MsgChannelCloseConfirmResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - return len(dAtA) - i, nil +func (c *msgClient) ChannelUpgradeTimeout(ctx context.Context, in *MsgChannelUpgradeTimeout, opts ...grpc.CallOption) (*MsgChannelUpgradeTimeoutResponse, error) { + out := new(MsgChannelUpgradeTimeoutResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelUpgradeTimeout", in, out, opts...) + if err != nil { + return nil, err + } + return out, nil } -func (m *MsgRecvPacket) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) +func (c *msgClient) ChannelUpgradeCancel(ctx context.Context, in *MsgChannelUpgradeCancel, opts ...grpc.CallOption) (*MsgChannelUpgradeCancelResponse, error) { + out := new(MsgChannelUpgradeCancelResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/ChannelUpgradeCancel", in, out, opts...) if err != nil { return nil, err } - return dAtA[:n], nil + return out, nil } -func (m *MsgRecvPacket) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func (c *msgClient) UpdateChannelParams(ctx context.Context, in *MsgUpdateParams, opts ...grpc.CallOption) (*MsgUpdateParamsResponse, error) { + out := new(MsgUpdateParamsResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/UpdateChannelParams", in, out, opts...) + if err != nil { + return nil, err + } + return out, nil } -func (m *MsgRecvPacket) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if len(m.Signer) > 0 { - i -= len(m.Signer) - copy(dAtA[i:], m.Signer) - i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) - i-- - dAtA[i] = 0x22 +func (c *msgClient) PruneAcknowledgements(ctx context.Context, in *MsgPruneAcknowledgements, opts ...grpc.CallOption) (*MsgPruneAcknowledgementsResponse, error) { + out := new(MsgPruneAcknowledgementsResponse) + err := c.cc.Invoke(ctx, "/ibc.core.channel.v1.Msg/PruneAcknowledgements", in, out, opts...) + if err != nil { + return nil, err } - { - size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) - if err != nil { - return 0, err - } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) - } - i-- - dAtA[i] = 0x1a - if len(m.ProofCommitment) > 0 { - i -= len(m.ProofCommitment) - copy(dAtA[i:], m.ProofCommitment) - i = encodeVarintTx(dAtA, i, uint64(len(m.ProofCommitment))) - i-- - dAtA[i] = 0x12 - } - { - size, err := m.Packet.MarshalToSizedBuffer(dAtA[:i]) - if err != nil { - return 0, err - } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) - } - i-- - dAtA[i] = 0xa - return len(dAtA) - i, nil + return out, nil } -func (m *MsgRecvPacketResponse) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { - return nil, err - } - return dAtA[:n], nil +// MsgServer is the server API for Msg service. +type MsgServer interface { + // ChannelOpenInit defines a rpc handler method for MsgChannelOpenInit. + ChannelOpenInit(context.Context, *MsgChannelOpenInit) (*MsgChannelOpenInitResponse, error) + // ChannelOpenTry defines a rpc handler method for MsgChannelOpenTry. + ChannelOpenTry(context.Context, *MsgChannelOpenTry) (*MsgChannelOpenTryResponse, error) + // ChannelOpenAck defines a rpc handler method for MsgChannelOpenAck. + ChannelOpenAck(context.Context, *MsgChannelOpenAck) (*MsgChannelOpenAckResponse, error) + // ChannelOpenConfirm defines a rpc handler method for MsgChannelOpenConfirm. + ChannelOpenConfirm(context.Context, *MsgChannelOpenConfirm) (*MsgChannelOpenConfirmResponse, error) + // ChannelCloseInit defines a rpc handler method for MsgChannelCloseInit. + ChannelCloseInit(context.Context, *MsgChannelCloseInit) (*MsgChannelCloseInitResponse, error) + // ChannelCloseConfirm defines a rpc handler method for + // MsgChannelCloseConfirm. + ChannelCloseConfirm(context.Context, *MsgChannelCloseConfirm) (*MsgChannelCloseConfirmResponse, error) + // RecvPacket defines a rpc handler method for MsgRecvPacket. + RecvPacket(context.Context, *MsgRecvPacket) (*MsgRecvPacketResponse, error) + // Timeout defines a rpc handler method for MsgTimeout. + Timeout(context.Context, *MsgTimeout) (*MsgTimeoutResponse, error) + // TimeoutOnClose defines a rpc handler method for MsgTimeoutOnClose. + TimeoutOnClose(context.Context, *MsgTimeoutOnClose) (*MsgTimeoutOnCloseResponse, error) + // Acknowledgement defines a rpc handler method for MsgAcknowledgement. + Acknowledgement(context.Context, *MsgAcknowledgement) (*MsgAcknowledgementResponse, error) + // ChannelUpgradeInit defines a rpc handler method for MsgChannelUpgradeInit. + ChannelUpgradeInit(context.Context, *MsgChannelUpgradeInit) (*MsgChannelUpgradeInitResponse, error) + // ChannelUpgradeTry defines a rpc handler method for MsgChannelUpgradeTry. + ChannelUpgradeTry(context.Context, *MsgChannelUpgradeTry) (*MsgChannelUpgradeTryResponse, error) + // ChannelUpgradeAck defines a rpc handler method for MsgChannelUpgradeAck. + ChannelUpgradeAck(context.Context, *MsgChannelUpgradeAck) (*MsgChannelUpgradeAckResponse, error) + // ChannelUpgradeConfirm defines a rpc handler method for MsgChannelUpgradeConfirm. + ChannelUpgradeConfirm(context.Context, *MsgChannelUpgradeConfirm) (*MsgChannelUpgradeConfirmResponse, error) + // ChannelUpgradeOpen defines a rpc handler method for MsgChannelUpgradeOpen. + ChannelUpgradeOpen(context.Context, *MsgChannelUpgradeOpen) (*MsgChannelUpgradeOpenResponse, error) + // ChannelUpgradeTimeout defines a rpc handler method for MsgChannelUpgradeTimeout. + ChannelUpgradeTimeout(context.Context, *MsgChannelUpgradeTimeout) (*MsgChannelUpgradeTimeoutResponse, error) + // ChannelUpgradeCancel defines a rpc handler method for MsgChannelUpgradeCancel. + ChannelUpgradeCancel(context.Context, *MsgChannelUpgradeCancel) (*MsgChannelUpgradeCancelResponse, error) + // UpdateChannelParams defines a rpc handler method for MsgUpdateParams. + UpdateChannelParams(context.Context, *MsgUpdateParams) (*MsgUpdateParamsResponse, error) + // PruneAcknowledgements defines a rpc handler method for MsgPruneAcknowledgements. + PruneAcknowledgements(context.Context, *MsgPruneAcknowledgements) (*MsgPruneAcknowledgementsResponse, error) } -func (m *MsgRecvPacketResponse) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +// UnimplementedMsgServer can be embedded to have forward compatible implementations. +type UnimplementedMsgServer struct { } -func (m *MsgRecvPacketResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if m.Result != 0 { - i = encodeVarintTx(dAtA, i, uint64(m.Result)) - i-- - dAtA[i] = 0x8 - } - return len(dAtA) - i, nil +func (*UnimplementedMsgServer) ChannelOpenInit(ctx context.Context, req *MsgChannelOpenInit) (*MsgChannelOpenInitResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelOpenInit not implemented") } - -func (m *MsgTimeout) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { - return nil, err - } - return dAtA[:n], nil +func (*UnimplementedMsgServer) ChannelOpenTry(ctx context.Context, req *MsgChannelOpenTry) (*MsgChannelOpenTryResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelOpenTry not implemented") +} +func (*UnimplementedMsgServer) ChannelOpenAck(ctx context.Context, req *MsgChannelOpenAck) (*MsgChannelOpenAckResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelOpenAck not implemented") +} +func (*UnimplementedMsgServer) ChannelOpenConfirm(ctx context.Context, req *MsgChannelOpenConfirm) (*MsgChannelOpenConfirmResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelOpenConfirm not implemented") +} +func (*UnimplementedMsgServer) ChannelCloseInit(ctx context.Context, req *MsgChannelCloseInit) (*MsgChannelCloseInitResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelCloseInit not implemented") +} +func (*UnimplementedMsgServer) ChannelCloseConfirm(ctx context.Context, req *MsgChannelCloseConfirm) (*MsgChannelCloseConfirmResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelCloseConfirm not implemented") +} +func (*UnimplementedMsgServer) RecvPacket(ctx context.Context, req *MsgRecvPacket) (*MsgRecvPacketResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method RecvPacket not implemented") +} +func (*UnimplementedMsgServer) Timeout(ctx context.Context, req *MsgTimeout) (*MsgTimeoutResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method Timeout not implemented") +} +func (*UnimplementedMsgServer) TimeoutOnClose(ctx context.Context, req *MsgTimeoutOnClose) (*MsgTimeoutOnCloseResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method TimeoutOnClose not implemented") +} +func (*UnimplementedMsgServer) Acknowledgement(ctx context.Context, req *MsgAcknowledgement) (*MsgAcknowledgementResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method Acknowledgement not implemented") +} +func (*UnimplementedMsgServer) ChannelUpgradeInit(ctx context.Context, req *MsgChannelUpgradeInit) (*MsgChannelUpgradeInitResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelUpgradeInit not implemented") +} +func (*UnimplementedMsgServer) ChannelUpgradeTry(ctx context.Context, req *MsgChannelUpgradeTry) (*MsgChannelUpgradeTryResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelUpgradeTry not implemented") +} +func (*UnimplementedMsgServer) ChannelUpgradeAck(ctx context.Context, req *MsgChannelUpgradeAck) (*MsgChannelUpgradeAckResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelUpgradeAck not implemented") +} +func (*UnimplementedMsgServer) ChannelUpgradeConfirm(ctx context.Context, req *MsgChannelUpgradeConfirm) (*MsgChannelUpgradeConfirmResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelUpgradeConfirm not implemented") +} +func (*UnimplementedMsgServer) ChannelUpgradeOpen(ctx context.Context, req *MsgChannelUpgradeOpen) (*MsgChannelUpgradeOpenResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelUpgradeOpen not implemented") +} +func (*UnimplementedMsgServer) ChannelUpgradeTimeout(ctx context.Context, req *MsgChannelUpgradeTimeout) (*MsgChannelUpgradeTimeoutResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelUpgradeTimeout not implemented") +} +func (*UnimplementedMsgServer) ChannelUpgradeCancel(ctx context.Context, req *MsgChannelUpgradeCancel) (*MsgChannelUpgradeCancelResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method ChannelUpgradeCancel not implemented") +} +func (*UnimplementedMsgServer) UpdateChannelParams(ctx context.Context, req *MsgUpdateParams) (*MsgUpdateParamsResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method UpdateChannelParams not implemented") +} +func (*UnimplementedMsgServer) PruneAcknowledgements(ctx context.Context, req *MsgPruneAcknowledgements) (*MsgPruneAcknowledgementsResponse, error) { + return nil, status.Errorf(codes.Unimplemented, "method PruneAcknowledgements not implemented") } -func (m *MsgTimeout) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func RegisterMsgServer(s grpc1.Server, srv MsgServer) { + s.RegisterService(&_Msg_serviceDesc, srv) } -func (m *MsgTimeout) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if len(m.Signer) > 0 { - i -= len(m.Signer) - copy(dAtA[i:], m.Signer) - i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) - i-- - dAtA[i] = 0x2a - } - if m.NextSequenceRecv != 0 { - i = encodeVarintTx(dAtA, i, uint64(m.NextSequenceRecv)) - i-- - dAtA[i] = 0x20 +func _Msg_ChannelOpenInit_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelOpenInit) + if err := dec(in); err != nil { + return nil, err } - { - size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) - if err != nil { - return 0, err - } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) + if interceptor == nil { + return srv.(MsgServer).ChannelOpenInit(ctx, in) } - i-- - dAtA[i] = 0x1a - if len(m.ProofUnreceived) > 0 { - i -= len(m.ProofUnreceived) - copy(dAtA[i:], m.ProofUnreceived) - i = encodeVarintTx(dAtA, i, uint64(len(m.ProofUnreceived))) - i-- - dAtA[i] = 0x12 + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelOpenInit", } - { - size, err := m.Packet.MarshalToSizedBuffer(dAtA[:i]) - if err != nil { - return 0, err - } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelOpenInit(ctx, req.(*MsgChannelOpenInit)) } - i-- - dAtA[i] = 0xa - return len(dAtA) - i, nil + return interceptor(ctx, in, info, handler) } -func (m *MsgTimeoutResponse) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { +func _Msg_ChannelOpenTry_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelOpenTry) + if err := dec(in); err != nil { return nil, err } - return dAtA[:n], nil -} - -func (m *MsgTimeoutResponse) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) -} - -func (m *MsgTimeoutResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if m.Result != 0 { - i = encodeVarintTx(dAtA, i, uint64(m.Result)) - i-- - dAtA[i] = 0x8 + if interceptor == nil { + return srv.(MsgServer).ChannelOpenTry(ctx, in) } - return len(dAtA) - i, nil + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelOpenTry", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelOpenTry(ctx, req.(*MsgChannelOpenTry)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgTimeoutOnClose) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { +func _Msg_ChannelOpenAck_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelOpenAck) + if err := dec(in); err != nil { return nil, err } - return dAtA[:n], nil + if interceptor == nil { + return srv.(MsgServer).ChannelOpenAck(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelOpenAck", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelOpenAck(ctx, req.(*MsgChannelOpenAck)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgTimeoutOnClose) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func _Msg_ChannelOpenConfirm_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelOpenConfirm) + if err := dec(in); err != nil { + return nil, err + } + if interceptor == nil { + return srv.(MsgServer).ChannelOpenConfirm(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelOpenConfirm", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelOpenConfirm(ctx, req.(*MsgChannelOpenConfirm)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgTimeoutOnClose) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if len(m.Signer) > 0 { - i -= len(m.Signer) - copy(dAtA[i:], m.Signer) - i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) - i-- - dAtA[i] = 0x32 +func _Msg_ChannelCloseInit_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelCloseInit) + if err := dec(in); err != nil { + return nil, err } - if m.NextSequenceRecv != 0 { - i = encodeVarintTx(dAtA, i, uint64(m.NextSequenceRecv)) - i-- - dAtA[i] = 0x28 + if interceptor == nil { + return srv.(MsgServer).ChannelCloseInit(ctx, in) } - { - size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) - if err != nil { - return 0, err - } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelCloseInit", } - i-- - dAtA[i] = 0x22 - if len(m.ProofClose) > 0 { - i -= len(m.ProofClose) - copy(dAtA[i:], m.ProofClose) - i = encodeVarintTx(dAtA, i, uint64(len(m.ProofClose))) - i-- - dAtA[i] = 0x1a + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelCloseInit(ctx, req.(*MsgChannelCloseInit)) } - if len(m.ProofUnreceived) > 0 { - i -= len(m.ProofUnreceived) - copy(dAtA[i:], m.ProofUnreceived) - i = encodeVarintTx(dAtA, i, uint64(len(m.ProofUnreceived))) - i-- - dAtA[i] = 0x12 + return interceptor(ctx, in, info, handler) +} + +func _Msg_ChannelCloseConfirm_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelCloseConfirm) + if err := dec(in); err != nil { + return nil, err } - { - size, err := m.Packet.MarshalToSizedBuffer(dAtA[:i]) - if err != nil { - return 0, err - } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) + if interceptor == nil { + return srv.(MsgServer).ChannelCloseConfirm(ctx, in) } - i-- - dAtA[i] = 0xa - return len(dAtA) - i, nil + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelCloseConfirm", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelCloseConfirm(ctx, req.(*MsgChannelCloseConfirm)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgTimeoutOnCloseResponse) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { +func _Msg_RecvPacket_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgRecvPacket) + if err := dec(in); err != nil { return nil, err } - return dAtA[:n], nil + if interceptor == nil { + return srv.(MsgServer).RecvPacket(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/RecvPacket", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).RecvPacket(ctx, req.(*MsgRecvPacket)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgTimeoutOnCloseResponse) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func _Msg_Timeout_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgTimeout) + if err := dec(in); err != nil { + return nil, err + } + if interceptor == nil { + return srv.(MsgServer).Timeout(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/Timeout", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).Timeout(ctx, req.(*MsgTimeout)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgTimeoutOnCloseResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if m.Result != 0 { - i = encodeVarintTx(dAtA, i, uint64(m.Result)) - i-- - dAtA[i] = 0x8 +func _Msg_TimeoutOnClose_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgTimeoutOnClose) + if err := dec(in); err != nil { + return nil, err } - return len(dAtA) - i, nil + if interceptor == nil { + return srv.(MsgServer).TimeoutOnClose(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/TimeoutOnClose", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).TimeoutOnClose(ctx, req.(*MsgTimeoutOnClose)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgAcknowledgement) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { +func _Msg_Acknowledgement_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgAcknowledgement) + if err := dec(in); err != nil { return nil, err } - return dAtA[:n], nil + if interceptor == nil { + return srv.(MsgServer).Acknowledgement(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/Acknowledgement", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).Acknowledgement(ctx, req.(*MsgAcknowledgement)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgAcknowledgement) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func _Msg_ChannelUpgradeInit_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelUpgradeInit) + if err := dec(in); err != nil { + return nil, err + } + if interceptor == nil { + return srv.(MsgServer).ChannelUpgradeInit(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelUpgradeInit", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelUpgradeInit(ctx, req.(*MsgChannelUpgradeInit)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgAcknowledgement) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if len(m.Signer) > 0 { - i -= len(m.Signer) - copy(dAtA[i:], m.Signer) - i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) - i-- - dAtA[i] = 0x2a - } - { - size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) - if err != nil { - return 0, err - } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) +func _Msg_ChannelUpgradeTry_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelUpgradeTry) + if err := dec(in); err != nil { + return nil, err } - i-- - dAtA[i] = 0x22 - if len(m.ProofAcked) > 0 { - i -= len(m.ProofAcked) - copy(dAtA[i:], m.ProofAcked) - i = encodeVarintTx(dAtA, i, uint64(len(m.ProofAcked))) - i-- - dAtA[i] = 0x1a + if interceptor == nil { + return srv.(MsgServer).ChannelUpgradeTry(ctx, in) } - if len(m.Acknowledgement) > 0 { - i -= len(m.Acknowledgement) - copy(dAtA[i:], m.Acknowledgement) - i = encodeVarintTx(dAtA, i, uint64(len(m.Acknowledgement))) - i-- - dAtA[i] = 0x12 + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelUpgradeTry", } - { - size, err := m.Packet.MarshalToSizedBuffer(dAtA[:i]) - if err != nil { - return 0, err - } - i -= size - i = encodeVarintTx(dAtA, i, uint64(size)) + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelUpgradeTry(ctx, req.(*MsgChannelUpgradeTry)) } - i-- - dAtA[i] = 0xa - return len(dAtA) - i, nil + return interceptor(ctx, in, info, handler) } -func (m *MsgAcknowledgementResponse) Marshal() (dAtA []byte, err error) { - size := m.Size() - dAtA = make([]byte, size) - n, err := m.MarshalToSizedBuffer(dAtA[:size]) - if err != nil { +func _Msg_ChannelUpgradeAck_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelUpgradeAck) + if err := dec(in); err != nil { return nil, err } - return dAtA[:n], nil + if interceptor == nil { + return srv.(MsgServer).ChannelUpgradeAck(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelUpgradeAck", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelUpgradeAck(ctx, req.(*MsgChannelUpgradeAck)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgAcknowledgementResponse) MarshalTo(dAtA []byte) (int, error) { - size := m.Size() - return m.MarshalToSizedBuffer(dAtA[:size]) +func _Msg_ChannelUpgradeConfirm_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelUpgradeConfirm) + if err := dec(in); err != nil { + return nil, err + } + if interceptor == nil { + return srv.(MsgServer).ChannelUpgradeConfirm(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelUpgradeConfirm", + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelUpgradeConfirm(ctx, req.(*MsgChannelUpgradeConfirm)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgAcknowledgementResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { - i := len(dAtA) - _ = i - var l int - _ = l - if m.Result != 0 { - i = encodeVarintTx(dAtA, i, uint64(m.Result)) - i-- - dAtA[i] = 0x8 - } - return len(dAtA) - i, nil -} - -func encodeVarintTx(dAtA []byte, offset int, v uint64) int { - offset -= sovTx(v) - base := offset - for v >= 1<<7 { - dAtA[offset] = uint8(v&0x7f | 0x80) - v >>= 7 - offset++ +func _Msg_ChannelUpgradeOpen_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelUpgradeOpen) + if err := dec(in); err != nil { + return nil, err } - dAtA[offset] = uint8(v) - return base -} -func (m *MsgChannelOpenInit) Size() (n int) { - if m == nil { - return 0 + if interceptor == nil { + return srv.(MsgServer).ChannelUpgradeOpen(ctx, in) } - var l int - _ = l - l = len(m.PortId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelUpgradeOpen", } - l = m.Channel.Size() - n += 1 + l + sovTx(uint64(l)) - l = len(m.Signer) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelUpgradeOpen(ctx, req.(*MsgChannelUpgradeOpen)) } - return n + return interceptor(ctx, in, info, handler) } -func (m *MsgChannelOpenInitResponse) Size() (n int) { - if m == nil { - return 0 +func _Msg_ChannelUpgradeTimeout_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelUpgradeTimeout) + if err := dec(in); err != nil { + return nil, err } - var l int - _ = l - l = len(m.ChannelId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if interceptor == nil { + return srv.(MsgServer).ChannelUpgradeTimeout(ctx, in) } - l = len(m.Version) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelUpgradeTimeout", } - return n + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelUpgradeTimeout(ctx, req.(*MsgChannelUpgradeTimeout)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgChannelOpenTry) Size() (n int) { - if m == nil { - return 0 - } - var l int - _ = l - l = len(m.PortId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) - } - l = len(m.PreviousChannelId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) +func _Msg_ChannelUpgradeCancel_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgChannelUpgradeCancel) + if err := dec(in); err != nil { + return nil, err } - l = m.Channel.Size() - n += 1 + l + sovTx(uint64(l)) - l = len(m.CounterpartyVersion) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if interceptor == nil { + return srv.(MsgServer).ChannelUpgradeCancel(ctx, in) } - l = len(m.ProofInit) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/ChannelUpgradeCancel", } - l = m.ProofHeight.Size() - n += 1 + l + sovTx(uint64(l)) - l = len(m.Signer) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).ChannelUpgradeCancel(ctx, req.(*MsgChannelUpgradeCancel)) } - return n + return interceptor(ctx, in, info, handler) } -func (m *MsgChannelOpenTryResponse) Size() (n int) { - if m == nil { - return 0 +func _Msg_UpdateChannelParams_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgUpdateParams) + if err := dec(in); err != nil { + return nil, err } - var l int - _ = l - l = len(m.Version) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if interceptor == nil { + return srv.(MsgServer).UpdateChannelParams(ctx, in) } - l = len(m.ChannelId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/UpdateChannelParams", } - return n + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).UpdateChannelParams(ctx, req.(*MsgUpdateParams)) + } + return interceptor(ctx, in, info, handler) } -func (m *MsgChannelOpenAck) Size() (n int) { - if m == nil { - return 0 - } - var l int - _ = l - l = len(m.PortId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) - } - l = len(m.ChannelId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) - } - l = len(m.CounterpartyChannelId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) +func _Msg_PruneAcknowledgements_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(MsgPruneAcknowledgements) + if err := dec(in); err != nil { + return nil, err } - l = len(m.CounterpartyVersion) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if interceptor == nil { + return srv.(MsgServer).PruneAcknowledgements(ctx, in) } - l = len(m.ProofTry) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: "/ibc.core.channel.v1.Msg/PruneAcknowledgements", } - l = m.ProofHeight.Size() - n += 1 + l + sovTx(uint64(l)) - l = len(m.Signer) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(MsgServer).PruneAcknowledgements(ctx, req.(*MsgPruneAcknowledgements)) } - return n + return interceptor(ctx, in, info, handler) } -func (m *MsgChannelOpenAckResponse) Size() (n int) { - if m == nil { - return 0 - } - var l int - _ = l - return n +var _Msg_serviceDesc = grpc.ServiceDesc{ + ServiceName: "ibc.core.channel.v1.Msg", + HandlerType: (*MsgServer)(nil), + Methods: []grpc.MethodDesc{ + { + MethodName: "ChannelOpenInit", + Handler: _Msg_ChannelOpenInit_Handler, + }, + { + MethodName: "ChannelOpenTry", + Handler: _Msg_ChannelOpenTry_Handler, + }, + { + MethodName: "ChannelOpenAck", + Handler: _Msg_ChannelOpenAck_Handler, + }, + { + MethodName: "ChannelOpenConfirm", + Handler: _Msg_ChannelOpenConfirm_Handler, + }, + { + MethodName: "ChannelCloseInit", + Handler: _Msg_ChannelCloseInit_Handler, + }, + { + MethodName: "ChannelCloseConfirm", + Handler: _Msg_ChannelCloseConfirm_Handler, + }, + { + MethodName: "RecvPacket", + Handler: _Msg_RecvPacket_Handler, + }, + { + MethodName: "Timeout", + Handler: _Msg_Timeout_Handler, + }, + { + MethodName: "TimeoutOnClose", + Handler: _Msg_TimeoutOnClose_Handler, + }, + { + MethodName: "Acknowledgement", + Handler: _Msg_Acknowledgement_Handler, + }, + { + MethodName: "ChannelUpgradeInit", + Handler: _Msg_ChannelUpgradeInit_Handler, + }, + { + MethodName: "ChannelUpgradeTry", + Handler: _Msg_ChannelUpgradeTry_Handler, + }, + { + MethodName: "ChannelUpgradeAck", + Handler: _Msg_ChannelUpgradeAck_Handler, + }, + { + MethodName: "ChannelUpgradeConfirm", + Handler: _Msg_ChannelUpgradeConfirm_Handler, + }, + { + MethodName: "ChannelUpgradeOpen", + Handler: _Msg_ChannelUpgradeOpen_Handler, + }, + { + MethodName: "ChannelUpgradeTimeout", + Handler: _Msg_ChannelUpgradeTimeout_Handler, + }, + { + MethodName: "ChannelUpgradeCancel", + Handler: _Msg_ChannelUpgradeCancel_Handler, + }, + { + MethodName: "UpdateChannelParams", + Handler: _Msg_UpdateChannelParams_Handler, + }, + { + MethodName: "PruneAcknowledgements", + Handler: _Msg_PruneAcknowledgements_Handler, + }, + }, + Streams: []grpc.StreamDesc{}, + Metadata: "ibc/core/channel/v1/tx.proto", } -func (m *MsgChannelOpenConfirm) Size() (n int) { - if m == nil { - return 0 +func (m *MsgChannelOpenInit) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err } + return dAtA[:n], nil +} + +func (m *MsgChannelOpenInit) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelOpenInit) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i var l int _ = l - l = len(m.PortId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x1a } - l = len(m.ChannelId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + { + size, err := m.Channel.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) } - l = len(m.ProofAck) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) - } - l = m.ProofHeight.Size() - n += 1 + l + sovTx(uint64(l)) - l = len(m.Signer) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + i-- + dAtA[i] = 0x12 + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa } - return n + return len(dAtA) - i, nil } -func (m *MsgChannelOpenConfirmResponse) Size() (n int) { - if m == nil { - return 0 +func (m *MsgChannelOpenInitResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err } - var l int - _ = l - return n + return dAtA[:n], nil } -func (m *MsgChannelCloseInit) Size() (n int) { - if m == nil { - return 0 - } +func (m *MsgChannelOpenInitResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelOpenInitResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i var l int _ = l - l = len(m.PortId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) - } - l = len(m.ChannelId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if len(m.Version) > 0 { + i -= len(m.Version) + copy(dAtA[i:], m.Version) + i = encodeVarintTx(dAtA, i, uint64(len(m.Version))) + i-- + dAtA[i] = 0x12 } - l = len(m.Signer) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0xa } - return n + return len(dAtA) - i, nil } -func (m *MsgChannelCloseInitResponse) Size() (n int) { - if m == nil { - return 0 +func (m *MsgChannelOpenTry) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err } - var l int - _ = l - return n + return dAtA[:n], nil } -func (m *MsgChannelCloseConfirm) Size() (n int) { - if m == nil { - return 0 - } +func (m *MsgChannelOpenTry) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelOpenTry) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i var l int _ = l - l = len(m.PortId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) - } - l = len(m.ChannelId) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x3a } - l = len(m.ProofInit) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) } - l = m.ProofHeight.Size() - n += 1 + l + sovTx(uint64(l)) - l = len(m.Signer) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + i-- + dAtA[i] = 0x32 + if len(m.ProofInit) > 0 { + i -= len(m.ProofInit) + copy(dAtA[i:], m.ProofInit) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofInit))) + i-- + dAtA[i] = 0x2a } - return n -} - -func (m *MsgChannelCloseConfirmResponse) Size() (n int) { - if m == nil { - return 0 + if len(m.CounterpartyVersion) > 0 { + i -= len(m.CounterpartyVersion) + copy(dAtA[i:], m.CounterpartyVersion) + i = encodeVarintTx(dAtA, i, uint64(len(m.CounterpartyVersion))) + i-- + dAtA[i] = 0x22 } - var l int - _ = l - return n -} - -func (m *MsgRecvPacket) Size() (n int) { - if m == nil { - return 0 + { + size, err := m.Channel.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) } - var l int - _ = l - l = m.Packet.Size() - n += 1 + l + sovTx(uint64(l)) - l = len(m.ProofCommitment) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + i-- + dAtA[i] = 0x1a + if len(m.PreviousChannelId) > 0 { + i -= len(m.PreviousChannelId) + copy(dAtA[i:], m.PreviousChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PreviousChannelId))) + i-- + dAtA[i] = 0x12 } - l = m.ProofHeight.Size() - n += 1 + l + sovTx(uint64(l)) - l = len(m.Signer) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa } - return n + return len(dAtA) - i, nil } -func (m *MsgRecvPacketResponse) Size() (n int) { - if m == nil { - return 0 - } - var l int - _ = l - if m.Result != 0 { - n += 1 + sovTx(uint64(m.Result)) +func (m *MsgChannelOpenTryResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err } - return n + return dAtA[:n], nil } -func (m *MsgTimeout) Size() (n int) { - if m == nil { - return 0 - } +func (m *MsgChannelOpenTryResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelOpenTryResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i var l int _ = l - l = m.Packet.Size() - n += 1 + l + sovTx(uint64(l)) - l = len(m.ProofUnreceived) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) - } - l = m.ProofHeight.Size() - n += 1 + l + sovTx(uint64(l)) - if m.NextSequenceRecv != 0 { - n += 1 + sovTx(uint64(m.NextSequenceRecv)) + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 } - l = len(m.Signer) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if len(m.Version) > 0 { + i -= len(m.Version) + copy(dAtA[i:], m.Version) + i = encodeVarintTx(dAtA, i, uint64(len(m.Version))) + i-- + dAtA[i] = 0xa } - return n + return len(dAtA) - i, nil } -func (m *MsgTimeoutResponse) Size() (n int) { - if m == nil { - return 0 - } - var l int - _ = l - if m.Result != 0 { - n += 1 + sovTx(uint64(m.Result)) +func (m *MsgChannelOpenAck) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err } - return n + return dAtA[:n], nil } -func (m *MsgTimeoutOnClose) Size() (n int) { - if m == nil { - return 0 - } +func (m *MsgChannelOpenAck) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelOpenAck) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i var l int _ = l - l = m.Packet.Size() - n += 1 + l + sovTx(uint64(l)) - l = len(m.ProofUnreceived) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x3a } - l = len(m.ProofClose) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) } - l = m.ProofHeight.Size() - n += 1 + l + sovTx(uint64(l)) - if m.NextSequenceRecv != 0 { - n += 1 + sovTx(uint64(m.NextSequenceRecv)) + i-- + dAtA[i] = 0x32 + if len(m.ProofTry) > 0 { + i -= len(m.ProofTry) + copy(dAtA[i:], m.ProofTry) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofTry))) + i-- + dAtA[i] = 0x2a } - l = len(m.Signer) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if len(m.CounterpartyVersion) > 0 { + i -= len(m.CounterpartyVersion) + copy(dAtA[i:], m.CounterpartyVersion) + i = encodeVarintTx(dAtA, i, uint64(len(m.CounterpartyVersion))) + i-- + dAtA[i] = 0x22 } - return n + if len(m.CounterpartyChannelId) > 0 { + i -= len(m.CounterpartyChannelId) + copy(dAtA[i:], m.CounterpartyChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.CounterpartyChannelId))) + i-- + dAtA[i] = 0x1a + } + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 + } + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil } -func (m *MsgTimeoutOnCloseResponse) Size() (n int) { - if m == nil { - return 0 +func (m *MsgChannelOpenAckResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err } + return dAtA[:n], nil +} + +func (m *MsgChannelOpenAckResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelOpenAckResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i var l int _ = l - if m.Result != 0 { - n += 1 + sovTx(uint64(m.Result)) - } - return n + return len(dAtA) - i, nil } -func (m *MsgAcknowledgement) Size() (n int) { - if m == nil { - return 0 +func (m *MsgChannelOpenConfirm) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err } + return dAtA[:n], nil +} + +func (m *MsgChannelOpenConfirm) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelOpenConfirm) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i var l int _ = l - l = m.Packet.Size() - n += 1 + l + sovTx(uint64(l)) - l = len(m.Acknowledgement) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x2a } - l = len(m.ProofAcked) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) } - l = m.ProofHeight.Size() - n += 1 + l + sovTx(uint64(l)) - l = len(m.Signer) - if l > 0 { - n += 1 + l + sovTx(uint64(l)) + i-- + dAtA[i] = 0x22 + if len(m.ProofAck) > 0 { + i -= len(m.ProofAck) + copy(dAtA[i:], m.ProofAck) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofAck))) + i-- + dAtA[i] = 0x1a } - return n + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 + } + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil } -func (m *MsgAcknowledgementResponse) Size() (n int) { - if m == nil { - return 0 +func (m *MsgChannelOpenConfirmResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err } + return dAtA[:n], nil +} + +func (m *MsgChannelOpenConfirmResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelOpenConfirmResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i var l int _ = l - if m.Result != 0 { - n += 1 + sovTx(uint64(m.Result)) + return len(dAtA) - i, nil +} + +func (m *MsgChannelCloseInit) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err } - return n + return dAtA[:n], nil } -func sovTx(x uint64) (n int) { - return (math_bits.Len64(x|1) + 6) / 7 +func (m *MsgChannelCloseInit) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) } -func sozTx(x uint64) (n int) { - return sovTx(uint64((x << 1) ^ uint64((int64(x) >> 63)))) + +func (m *MsgChannelCloseInit) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x1a + } + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 + } + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func (m *MsgChannelCloseInitResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelCloseInitResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelCloseInitResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + return len(dAtA) - i, nil +} + +func (m *MsgChannelCloseConfirm) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelCloseConfirm) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelCloseConfirm) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.CounterpartyUpgradeSequence != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.CounterpartyUpgradeSequence)) + i-- + dAtA[i] = 0x30 + } + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x2a + } + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x22 + if len(m.ProofInit) > 0 { + i -= len(m.ProofInit) + copy(dAtA[i:], m.ProofInit) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofInit))) + i-- + dAtA[i] = 0x1a + } + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 + } + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func (m *MsgChannelCloseConfirmResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelCloseConfirmResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelCloseConfirmResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + return len(dAtA) - i, nil +} + +func (m *MsgRecvPacket) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgRecvPacket) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgRecvPacket) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x22 + } + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x1a + if len(m.ProofCommitment) > 0 { + i -= len(m.ProofCommitment) + copy(dAtA[i:], m.ProofCommitment) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofCommitment))) + i-- + dAtA[i] = 0x12 + } + { + size, err := m.Packet.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil +} + +func (m *MsgRecvPacketResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgRecvPacketResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgRecvPacketResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.Result != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.Result)) + i-- + dAtA[i] = 0x8 + } + return len(dAtA) - i, nil +} + +func (m *MsgTimeout) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgTimeout) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgTimeout) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x2a + } + if m.NextSequenceRecv != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.NextSequenceRecv)) + i-- + dAtA[i] = 0x20 + } + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x1a + if len(m.ProofUnreceived) > 0 { + i -= len(m.ProofUnreceived) + copy(dAtA[i:], m.ProofUnreceived) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofUnreceived))) + i-- + dAtA[i] = 0x12 + } + { + size, err := m.Packet.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil +} + +func (m *MsgTimeoutResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgTimeoutResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgTimeoutResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.Result != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.Result)) + i-- + dAtA[i] = 0x8 + } + return len(dAtA) - i, nil +} + +func (m *MsgTimeoutOnClose) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgTimeoutOnClose) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgTimeoutOnClose) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.CounterpartyUpgradeSequence != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.CounterpartyUpgradeSequence)) + i-- + dAtA[i] = 0x38 + } + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x32 + } + if m.NextSequenceRecv != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.NextSequenceRecv)) + i-- + dAtA[i] = 0x28 + } + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x22 + if len(m.ProofClose) > 0 { + i -= len(m.ProofClose) + copy(dAtA[i:], m.ProofClose) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofClose))) + i-- + dAtA[i] = 0x1a + } + if len(m.ProofUnreceived) > 0 { + i -= len(m.ProofUnreceived) + copy(dAtA[i:], m.ProofUnreceived) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofUnreceived))) + i-- + dAtA[i] = 0x12 + } + { + size, err := m.Packet.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil +} + +func (m *MsgTimeoutOnCloseResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgTimeoutOnCloseResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgTimeoutOnCloseResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.Result != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.Result)) + i-- + dAtA[i] = 0x8 + } + return len(dAtA) - i, nil +} + +func (m *MsgAcknowledgement) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgAcknowledgement) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgAcknowledgement) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x2a + } + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x22 + if len(m.ProofAcked) > 0 { + i -= len(m.ProofAcked) + copy(dAtA[i:], m.ProofAcked) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofAcked))) + i-- + dAtA[i] = 0x1a + } + if len(m.Acknowledgement) > 0 { + i -= len(m.Acknowledgement) + copy(dAtA[i:], m.Acknowledgement) + i = encodeVarintTx(dAtA, i, uint64(len(m.Acknowledgement))) + i-- + dAtA[i] = 0x12 + } + { + size, err := m.Packet.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil +} + +func (m *MsgAcknowledgementResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgAcknowledgementResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgAcknowledgementResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.Result != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.Result)) + i-- + dAtA[i] = 0x8 + } + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeInit) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeInit) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeInit) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x22 + } + { + size, err := m.Fields.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x1a + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 + } + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeInitResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeInitResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeInitResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.UpgradeSequence != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.UpgradeSequence)) + i-- + dAtA[i] = 0x10 + } + { + size, err := m.Upgrade.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeTry) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeTry) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeTry) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x4a + } + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x42 + if len(m.ProofUpgrade) > 0 { + i -= len(m.ProofUpgrade) + copy(dAtA[i:], m.ProofUpgrade) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofUpgrade))) + i-- + dAtA[i] = 0x3a + } + if len(m.ProofChannel) > 0 { + i -= len(m.ProofChannel) + copy(dAtA[i:], m.ProofChannel) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofChannel))) + i-- + dAtA[i] = 0x32 + } + if m.CounterpartyUpgradeSequence != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.CounterpartyUpgradeSequence)) + i-- + dAtA[i] = 0x28 + } + { + size, err := m.CounterpartyUpgradeFields.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x22 + if len(m.ProposedUpgradeConnectionHops) > 0 { + for iNdEx := len(m.ProposedUpgradeConnectionHops) - 1; iNdEx >= 0; iNdEx-- { + i -= len(m.ProposedUpgradeConnectionHops[iNdEx]) + copy(dAtA[i:], m.ProposedUpgradeConnectionHops[iNdEx]) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProposedUpgradeConnectionHops[iNdEx]))) + i-- + dAtA[i] = 0x1a + } + } + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 + } + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeTryResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeTryResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeTryResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.Result != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.Result)) + i-- + dAtA[i] = 0x18 + } + if m.UpgradeSequence != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.UpgradeSequence)) + i-- + dAtA[i] = 0x10 + } + { + size, err := m.Upgrade.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeAck) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeAck) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeAck) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x3a + } + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x32 + if len(m.ProofUpgrade) > 0 { + i -= len(m.ProofUpgrade) + copy(dAtA[i:], m.ProofUpgrade) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofUpgrade))) + i-- + dAtA[i] = 0x2a + } + if len(m.ProofChannel) > 0 { + i -= len(m.ProofChannel) + copy(dAtA[i:], m.ProofChannel) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofChannel))) + i-- + dAtA[i] = 0x22 + } + { + size, err := m.CounterpartyUpgrade.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x1a + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 + } + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeAckResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeAckResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeAckResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.Result != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.Result)) + i-- + dAtA[i] = 0x8 + } + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeConfirm) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeConfirm) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeConfirm) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x42 + } + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x3a + if len(m.ProofUpgrade) > 0 { + i -= len(m.ProofUpgrade) + copy(dAtA[i:], m.ProofUpgrade) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofUpgrade))) + i-- + dAtA[i] = 0x32 + } + if len(m.ProofChannel) > 0 { + i -= len(m.ProofChannel) + copy(dAtA[i:], m.ProofChannel) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofChannel))) + i-- + dAtA[i] = 0x2a + } + { + size, err := m.CounterpartyUpgrade.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x22 + if m.CounterpartyChannelState != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.CounterpartyChannelState)) + i-- + dAtA[i] = 0x18 + } + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 + } + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeConfirmResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeConfirmResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeConfirmResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.Result != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.Result)) + i-- + dAtA[i] = 0x8 + } + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeOpen) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeOpen) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeOpen) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x32 + } + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x2a + if len(m.ProofChannel) > 0 { + i -= len(m.ProofChannel) + copy(dAtA[i:], m.ProofChannel) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofChannel))) + i-- + dAtA[i] = 0x22 + } + if m.CounterpartyChannelState != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.CounterpartyChannelState)) + i-- + dAtA[i] = 0x18 + } + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 + } + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeOpenResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeOpenResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeOpenResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeTimeout) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeTimeout) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeTimeout) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x32 + } + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x2a + if len(m.ProofChannel) > 0 { + i -= len(m.ProofChannel) + copy(dAtA[i:], m.ProofChannel) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofChannel))) + i-- + dAtA[i] = 0x22 + } + { + size, err := m.CounterpartyChannel.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x1a + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 + } + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeTimeoutResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeTimeoutResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeTimeoutResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeCancel) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeCancel) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeCancel) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x32 + } + { + size, err := m.ProofHeight.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x2a + if len(m.ProofErrorReceipt) > 0 { + i -= len(m.ProofErrorReceipt) + copy(dAtA[i:], m.ProofErrorReceipt) + i = encodeVarintTx(dAtA, i, uint64(len(m.ProofErrorReceipt))) + i-- + dAtA[i] = 0x22 + } + { + size, err := m.ErrorReceipt.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x1a + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 + } + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func (m *MsgChannelUpgradeCancelResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgChannelUpgradeCancelResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgChannelUpgradeCancelResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + return len(dAtA) - i, nil +} + +func (m *MsgUpdateParams) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgUpdateParams) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgUpdateParams) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + { + size, err := m.Params.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintTx(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x12 + if len(m.Authority) > 0 { + i -= len(m.Authority) + copy(dAtA[i:], m.Authority) + i = encodeVarintTx(dAtA, i, uint64(len(m.Authority))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func (m *MsgUpdateParamsResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgUpdateParamsResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgUpdateParamsResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + return len(dAtA) - i, nil +} + +func (m *MsgPruneAcknowledgements) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgPruneAcknowledgements) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgPruneAcknowledgements) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Signer) > 0 { + i -= len(m.Signer) + copy(dAtA[i:], m.Signer) + i = encodeVarintTx(dAtA, i, uint64(len(m.Signer))) + i-- + dAtA[i] = 0x22 + } + if m.Limit != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.Limit)) + i-- + dAtA[i] = 0x18 + } + if len(m.ChannelId) > 0 { + i -= len(m.ChannelId) + copy(dAtA[i:], m.ChannelId) + i = encodeVarintTx(dAtA, i, uint64(len(m.ChannelId))) + i-- + dAtA[i] = 0x12 + } + if len(m.PortId) > 0 { + i -= len(m.PortId) + copy(dAtA[i:], m.PortId) + i = encodeVarintTx(dAtA, i, uint64(len(m.PortId))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func (m *MsgPruneAcknowledgementsResponse) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *MsgPruneAcknowledgementsResponse) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *MsgPruneAcknowledgementsResponse) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.TotalRemainingSequences != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.TotalRemainingSequences)) + i-- + dAtA[i] = 0x10 + } + if m.TotalPrunedSequences != 0 { + i = encodeVarintTx(dAtA, i, uint64(m.TotalPrunedSequences)) + i-- + dAtA[i] = 0x8 + } + return len(dAtA) - i, nil +} + +func encodeVarintTx(dAtA []byte, offset int, v uint64) int { + offset -= sovTx(v) + base := offset + for v >= 1<<7 { + dAtA[offset] = uint8(v&0x7f | 0x80) + v >>= 7 + offset++ + } + dAtA[offset] = uint8(v) + return base +} +func (m *MsgChannelOpenInit) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.Channel.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelOpenInitResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.Version) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelOpenTry) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.PreviousChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.Channel.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.CounterpartyVersion) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ProofInit) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelOpenTryResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.Version) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelOpenAck) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.CounterpartyChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.CounterpartyVersion) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ProofTry) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelOpenAckResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + return n +} + +func (m *MsgChannelOpenConfirm) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ProofAck) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelOpenConfirmResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + return n +} + +func (m *MsgChannelCloseInit) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelCloseInitResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + return n +} + +func (m *MsgChannelCloseConfirm) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ProofInit) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + if m.CounterpartyUpgradeSequence != 0 { + n += 1 + sovTx(uint64(m.CounterpartyUpgradeSequence)) + } + return n +} + +func (m *MsgChannelCloseConfirmResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + return n +} + +func (m *MsgRecvPacket) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = m.Packet.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.ProofCommitment) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgRecvPacketResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.Result != 0 { + n += 1 + sovTx(uint64(m.Result)) + } + return n +} + +func (m *MsgTimeout) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = m.Packet.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.ProofUnreceived) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + if m.NextSequenceRecv != 0 { + n += 1 + sovTx(uint64(m.NextSequenceRecv)) + } + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgTimeoutResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.Result != 0 { + n += 1 + sovTx(uint64(m.Result)) + } + return n +} + +func (m *MsgTimeoutOnClose) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = m.Packet.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.ProofUnreceived) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ProofClose) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + if m.NextSequenceRecv != 0 { + n += 1 + sovTx(uint64(m.NextSequenceRecv)) + } + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + if m.CounterpartyUpgradeSequence != 0 { + n += 1 + sovTx(uint64(m.CounterpartyUpgradeSequence)) + } + return n +} + +func (m *MsgTimeoutOnCloseResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.Result != 0 { + n += 1 + sovTx(uint64(m.Result)) + } + return n +} + +func (m *MsgAcknowledgement) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = m.Packet.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Acknowledgement) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ProofAcked) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgAcknowledgementResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.Result != 0 { + n += 1 + sovTx(uint64(m.Result)) + } + return n +} + +func (m *MsgChannelUpgradeInit) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.Fields.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelUpgradeInitResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = m.Upgrade.Size() + n += 1 + l + sovTx(uint64(l)) + if m.UpgradeSequence != 0 { + n += 1 + sovTx(uint64(m.UpgradeSequence)) + } + return n +} + +func (m *MsgChannelUpgradeTry) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + if len(m.ProposedUpgradeConnectionHops) > 0 { + for _, s := range m.ProposedUpgradeConnectionHops { + l = len(s) + n += 1 + l + sovTx(uint64(l)) + } + } + l = m.CounterpartyUpgradeFields.Size() + n += 1 + l + sovTx(uint64(l)) + if m.CounterpartyUpgradeSequence != 0 { + n += 1 + sovTx(uint64(m.CounterpartyUpgradeSequence)) + } + l = len(m.ProofChannel) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ProofUpgrade) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelUpgradeTryResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = m.Upgrade.Size() + n += 1 + l + sovTx(uint64(l)) + if m.UpgradeSequence != 0 { + n += 1 + sovTx(uint64(m.UpgradeSequence)) + } + if m.Result != 0 { + n += 1 + sovTx(uint64(m.Result)) + } + return n +} + +func (m *MsgChannelUpgradeAck) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.CounterpartyUpgrade.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.ProofChannel) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ProofUpgrade) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelUpgradeAckResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.Result != 0 { + n += 1 + sovTx(uint64(m.Result)) + } + return n +} + +func (m *MsgChannelUpgradeConfirm) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + if m.CounterpartyChannelState != 0 { + n += 1 + sovTx(uint64(m.CounterpartyChannelState)) + } + l = m.CounterpartyUpgrade.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.ProofChannel) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ProofUpgrade) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelUpgradeConfirmResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.Result != 0 { + n += 1 + sovTx(uint64(m.Result)) + } + return n +} + +func (m *MsgChannelUpgradeOpen) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + if m.CounterpartyChannelState != 0 { + n += 1 + sovTx(uint64(m.CounterpartyChannelState)) + } + l = len(m.ProofChannel) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelUpgradeOpenResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + return n +} + +func (m *MsgChannelUpgradeTimeout) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.CounterpartyChannel.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.ProofChannel) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelUpgradeTimeoutResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + return n +} + +func (m *MsgChannelUpgradeCancel) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ErrorReceipt.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.ProofErrorReceipt) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.ProofHeight.Size() + n += 1 + l + sovTx(uint64(l)) + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgChannelUpgradeCancelResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + return n +} + +func (m *MsgUpdateParams) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.Authority) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = m.Params.Size() + n += 1 + l + sovTx(uint64(l)) + return n +} + +func (m *MsgUpdateParamsResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + return n +} + +func (m *MsgPruneAcknowledgements) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.PortId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + l = len(m.ChannelId) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + if m.Limit != 0 { + n += 1 + sovTx(uint64(m.Limit)) + } + l = len(m.Signer) + if l > 0 { + n += 1 + l + sovTx(uint64(l)) + } + return n +} + +func (m *MsgPruneAcknowledgementsResponse) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.TotalPrunedSequences != 0 { + n += 1 + sovTx(uint64(m.TotalPrunedSequences)) + } + if m.TotalRemainingSequences != 0 { + n += 1 + sovTx(uint64(m.TotalRemainingSequences)) + } + return n +} + +func sovTx(x uint64) (n int) { + return (math_bits.Len64(x|1) + 6) / 7 +} +func sozTx(x uint64) (n int) { + return sovTx(uint64((x << 1) ^ uint64((int64(x) >> 63)))) +} +func (m *MsgChannelOpenInit) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelOpenInit: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelOpenInit: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.PortId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Channel", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.Channel.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Signer = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgChannelOpenInitResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelOpenInitResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelOpenInitResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ChannelId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Version", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Version = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgChannelOpenTry) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelOpenTry: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelOpenTry: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.PortId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field PreviousChannelId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.PreviousChannelId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Channel", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.Channel.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 4: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyVersion", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.CounterpartyVersion = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 5: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofInit", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if byteLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ProofInit = append(m.ProofInit[:0], dAtA[iNdEx:postIndex]...) + if m.ProofInit == nil { + m.ProofInit = []byte{} + } + iNdEx = postIndex + case 6: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 7: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Signer = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgChannelOpenTryResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelOpenTryResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelOpenTryResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Version", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Version = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ChannelId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgChannelOpenAck) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelOpenAck: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelOpenAck: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.PortId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ChannelId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyChannelId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.CounterpartyChannelId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 4: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyVersion", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.CounterpartyVersion = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 5: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofTry", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if byteLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ProofTry = append(m.ProofTry[:0], dAtA[iNdEx:postIndex]...) + if m.ProofTry == nil { + m.ProofTry = []byte{} + } + iNdEx = postIndex + case 6: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 7: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Signer = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgChannelOpenAckResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelOpenAckResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelOpenAckResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgChannelOpenConfirm) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelOpenConfirm: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelOpenConfirm: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.PortId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ChannelId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofAck", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if byteLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ProofAck = append(m.ProofAck[:0], dAtA[iNdEx:postIndex]...) + if m.ProofAck == nil { + m.ProofAck = []byte{} + } + iNdEx = postIndex + case 4: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 5: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Signer = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgChannelOpenConfirmResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelOpenConfirmResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelOpenConfirmResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgChannelCloseInit) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelCloseInit: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelCloseInit: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.PortId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ChannelId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Signer = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgChannelCloseInitResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelCloseInitResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelCloseInitResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgChannelCloseConfirm) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelCloseConfirm: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelCloseConfirm: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.PortId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ChannelId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofInit", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if byteLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ProofInit = append(m.ProofInit[:0], dAtA[iNdEx:postIndex]...) + if m.ProofInit == nil { + m.ProofInit = []byte{} + } + iNdEx = postIndex + case 4: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 5: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Signer = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 6: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyUpgradeSequence", wireType) + } + m.CounterpartyUpgradeSequence = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.CounterpartyUpgradeSequence |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgChannelCloseConfirmResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelCloseConfirmResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelCloseConfirmResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgRecvPacket) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgRecvPacket: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgRecvPacket: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Packet", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.Packet.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofCommitment", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if byteLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ProofCommitment = append(m.ProofCommitment[:0], dAtA[iNdEx:postIndex]...) + if m.ProofCommitment == nil { + m.ProofCommitment = []byte{} + } + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 4: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Signer = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgRecvPacketResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgRecvPacketResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgRecvPacketResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field Result", wireType) + } + m.Result = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.Result |= ResponseResultType(b&0x7F) << shift + if b < 0x80 { + break + } + } + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgTimeout) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgTimeout: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgTimeout: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Packet", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.Packet.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofUnreceived", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if byteLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ProofUnreceived = append(m.ProofUnreceived[:0], dAtA[iNdEx:postIndex]...) + if m.ProofUnreceived == nil { + m.ProofUnreceived = []byte{} + } + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 4: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field NextSequenceRecv", wireType) + } + m.NextSequenceRecv = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.NextSequenceRecv |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + case 5: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Signer = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgTimeoutResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgTimeoutResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgTimeoutResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field Result", wireType) + } + m.Result = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.Result |= ResponseResultType(b&0x7F) << shift + if b < 0x80 { + break + } + } + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgTimeoutOnClose) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgTimeoutOnClose: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgTimeoutOnClose: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Packet", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.Packet.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofUnreceived", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if byteLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ProofUnreceived = append(m.ProofUnreceived[:0], dAtA[iNdEx:postIndex]...) + if m.ProofUnreceived == nil { + m.ProofUnreceived = []byte{} + } + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofClose", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if byteLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ProofClose = append(m.ProofClose[:0], dAtA[iNdEx:postIndex]...) + if m.ProofClose == nil { + m.ProofClose = []byte{} + } + iNdEx = postIndex + case 4: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 5: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field NextSequenceRecv", wireType) + } + m.NextSequenceRecv = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.NextSequenceRecv |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + case 6: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Signer = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 7: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyUpgradeSequence", wireType) + } + m.CounterpartyUpgradeSequence = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.CounterpartyUpgradeSequence |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgTimeoutOnCloseResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgTimeoutOnCloseResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgTimeoutOnCloseResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field Result", wireType) + } + m.Result = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.Result |= ResponseResultType(b&0x7F) << shift + if b < 0x80 { + break + } + } + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil } -func (m *MsgChannelOpenInit) Unmarshal(dAtA []byte) error { +func (m *MsgAcknowledgement) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -2716,17 +7691,17 @@ func (m *MsgChannelOpenInit) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgChannelOpenInit: wiretype end group for non-group") + return fmt.Errorf("proto: MsgAcknowledgement: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgChannelOpenInit: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgAcknowledgement: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field Packet", wireType) } - var stringLen uint64 + var msglen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -2736,29 +7711,30 @@ func (m *MsgChannelOpenInit) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - stringLen |= uint64(b&0x7F) << shift + msglen |= int(b&0x7F) << shift if b < 0x80 { break } } - intStringLen := int(stringLen) - if intStringLen < 0 { + if msglen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + intStringLen + postIndex := iNdEx + msglen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.PortId = string(dAtA[iNdEx:postIndex]) + if err := m.Packet.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } iNdEx = postIndex case 2: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Channel", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field Acknowledgement", wireType) } - var msglen int + var byteLen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -2768,30 +7744,31 @@ func (m *MsgChannelOpenInit) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - msglen |= int(b&0x7F) << shift + byteLen |= int(b&0x7F) << shift if b < 0x80 { break } } - if msglen < 0 { + if byteLen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + msglen + postIndex := iNdEx + byteLen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - if err := m.Channel.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { - return err + m.Acknowledgement = append(m.Acknowledgement[:0], dAtA[iNdEx:postIndex]...) + if m.Acknowledgement == nil { + m.Acknowledgement = []byte{} } iNdEx = postIndex case 3: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ProofAcked", wireType) } - var stringLen uint64 + var byteLen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -2801,79 +7778,31 @@ func (m *MsgChannelOpenInit) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - stringLen |= uint64(b&0x7F) << shift + byteLen |= int(b&0x7F) << shift if b < 0x80 { break } } - intStringLen := int(stringLen) - if intStringLen < 0 { + if byteLen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + intStringLen + postIndex := iNdEx + byteLen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.Signer = string(dAtA[iNdEx:postIndex]) - iNdEx = postIndex - default: - iNdEx = preIndex - skippy, err := skipTx(dAtA[iNdEx:]) - if err != nil { - return err - } - if (skippy < 0) || (iNdEx+skippy) < 0 { - return ErrInvalidLengthTx - } - if (iNdEx + skippy) > l { - return io.ErrUnexpectedEOF - } - iNdEx += skippy - } - } - - if iNdEx > l { - return io.ErrUnexpectedEOF - } - return nil -} -func (m *MsgChannelOpenInitResponse) Unmarshal(dAtA []byte) error { - l := len(dAtA) - iNdEx := 0 - for iNdEx < l { - preIndex := iNdEx - var wire uint64 - for shift := uint(0); ; shift += 7 { - if shift >= 64 { - return ErrIntOverflowTx - } - if iNdEx >= l { - return io.ErrUnexpectedEOF - } - b := dAtA[iNdEx] - iNdEx++ - wire |= uint64(b&0x7F) << shift - if b < 0x80 { - break + m.ProofAcked = append(m.ProofAcked[:0], dAtA[iNdEx:postIndex]...) + if m.ProofAcked == nil { + m.ProofAcked = []byte{} } - } - fieldNum := int32(wire >> 3) - wireType := int(wire & 0x7) - if wireType == 4 { - return fmt.Errorf("proto: MsgChannelOpenInitResponse: wiretype end group for non-group") - } - if fieldNum <= 0 { - return fmt.Errorf("proto: MsgChannelOpenInitResponse: illegal tag %d (wire type %d)", fieldNum, wire) - } - switch fieldNum { - case 1: + iNdEx = postIndex + case 4: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) } - var stringLen uint64 + var msglen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -2883,27 +7812,28 @@ func (m *MsgChannelOpenInitResponse) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - stringLen |= uint64(b&0x7F) << shift + msglen |= int(b&0x7F) << shift if b < 0x80 { break } } - intStringLen := int(stringLen) - if intStringLen < 0 { + if msglen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + intStringLen + postIndex := iNdEx + msglen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.ChannelId = string(dAtA[iNdEx:postIndex]) + if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } iNdEx = postIndex - case 2: + case 5: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Version", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) } var stringLen uint64 for shift := uint(0); ; shift += 7 { @@ -2931,7 +7861,7 @@ func (m *MsgChannelOpenInitResponse) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - m.Version = string(dAtA[iNdEx:postIndex]) + m.Signer = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex default: iNdEx = preIndex @@ -2954,7 +7884,7 @@ func (m *MsgChannelOpenInitResponse) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgChannelOpenTry) Unmarshal(dAtA []byte) error { +func (m *MsgAcknowledgementResponse) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -2977,49 +7907,17 @@ func (m *MsgChannelOpenTry) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgChannelOpenTry: wiretype end group for non-group") + return fmt.Errorf("proto: MsgAcknowledgementResponse: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgChannelOpenTry: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgAcknowledgementResponse: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: - if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) - } - var stringLen uint64 - for shift := uint(0); ; shift += 7 { - if shift >= 64 { - return ErrIntOverflowTx - } - if iNdEx >= l { - return io.ErrUnexpectedEOF - } - b := dAtA[iNdEx] - iNdEx++ - stringLen |= uint64(b&0x7F) << shift - if b < 0x80 { - break - } - } - intStringLen := int(stringLen) - if intStringLen < 0 { - return ErrInvalidLengthTx - } - postIndex := iNdEx + intStringLen - if postIndex < 0 { - return ErrInvalidLengthTx - } - if postIndex > l { - return io.ErrUnexpectedEOF - } - m.PortId = string(dAtA[iNdEx:postIndex]) - iNdEx = postIndex - case 2: - if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field PreviousChannelId", wireType) + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field Result", wireType) } - var stringLen uint64 + m.Result = 0 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -3029,60 +7927,64 @@ func (m *MsgChannelOpenTry) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - stringLen |= uint64(b&0x7F) << shift + m.Result |= ResponseResultType(b&0x7F) << shift if b < 0x80 { break } } - intStringLen := int(stringLen) - if intStringLen < 0 { - return ErrInvalidLengthTx + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err } - postIndex := iNdEx + intStringLen - if postIndex < 0 { + if (skippy < 0) || (iNdEx+skippy) < 0 { return ErrInvalidLengthTx } - if postIndex > l { + if (iNdEx + skippy) > l { return io.ErrUnexpectedEOF } - m.PreviousChannelId = string(dAtA[iNdEx:postIndex]) - iNdEx = postIndex - case 3: - if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Channel", wireType) - } - var msglen int - for shift := uint(0); ; shift += 7 { - if shift >= 64 { - return ErrIntOverflowTx - } - if iNdEx >= l { - return io.ErrUnexpectedEOF - } - b := dAtA[iNdEx] - iNdEx++ - msglen |= int(b&0x7F) << shift - if b < 0x80 { - break - } - } - if msglen < 0 { - return ErrInvalidLengthTx - } - postIndex := iNdEx + msglen - if postIndex < 0 { - return ErrInvalidLengthTx + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgChannelUpgradeInit) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx } - if postIndex > l { + if iNdEx >= l { return io.ErrUnexpectedEOF } - if err := m.Channel.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { - return err + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break } - iNdEx = postIndex - case 4: + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelUpgradeInit: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelUpgradeInit: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyVersion", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) } var stringLen uint64 for shift := uint(0); ; shift += 7 { @@ -3110,13 +8012,13 @@ func (m *MsgChannelOpenTry) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - m.CounterpartyVersion = string(dAtA[iNdEx:postIndex]) + m.PortId = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex - case 5: + case 2: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ProofInit", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) } - var byteLen int + var stringLen uint64 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -3126,29 +8028,27 @@ func (m *MsgChannelOpenTry) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - byteLen |= int(b&0x7F) << shift + stringLen |= uint64(b&0x7F) << shift if b < 0x80 { break } } - if byteLen < 0 { + intStringLen := int(stringLen) + if intStringLen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + byteLen + postIndex := iNdEx + intStringLen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.ProofInit = append(m.ProofInit[:0], dAtA[iNdEx:postIndex]...) - if m.ProofInit == nil { - m.ProofInit = []byte{} - } + m.ChannelId = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex - case 6: + case 3: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field Fields", wireType) } var msglen int for shift := uint(0); ; shift += 7 { @@ -3175,11 +8075,11 @@ func (m *MsgChannelOpenTry) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + if err := m.Fields.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { return err } iNdEx = postIndex - case 7: + case 4: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) } @@ -3232,7 +8132,7 @@ func (m *MsgChannelOpenTry) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgChannelOpenTryResponse) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeInitResponse) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -3255,17 +8155,17 @@ func (m *MsgChannelOpenTryResponse) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgChannelOpenTryResponse: wiretype end group for non-group") + return fmt.Errorf("proto: MsgChannelUpgradeInitResponse: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgChannelOpenTryResponse: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgChannelUpgradeInitResponse: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Version", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field Upgrade", wireType) } - var stringLen uint64 + var msglen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -3275,29 +8175,30 @@ func (m *MsgChannelOpenTryResponse) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - stringLen |= uint64(b&0x7F) << shift + msglen |= int(b&0x7F) << shift if b < 0x80 { break } } - intStringLen := int(stringLen) - if intStringLen < 0 { + if msglen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + intStringLen + postIndex := iNdEx + msglen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.Version = string(dAtA[iNdEx:postIndex]) + if err := m.Upgrade.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } iNdEx = postIndex case 2: - if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field UpgradeSequence", wireType) } - var stringLen uint64 + m.UpgradeSequence = 0 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -3307,24 +8208,11 @@ func (m *MsgChannelOpenTryResponse) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - stringLen |= uint64(b&0x7F) << shift + m.UpgradeSequence |= uint64(b&0x7F) << shift if b < 0x80 { break } } - intStringLen := int(stringLen) - if intStringLen < 0 { - return ErrInvalidLengthTx - } - postIndex := iNdEx + intStringLen - if postIndex < 0 { - return ErrInvalidLengthTx - } - if postIndex > l { - return io.ErrUnexpectedEOF - } - m.ChannelId = string(dAtA[iNdEx:postIndex]) - iNdEx = postIndex default: iNdEx = preIndex skippy, err := skipTx(dAtA[iNdEx:]) @@ -3346,7 +8234,7 @@ func (m *MsgChannelOpenTryResponse) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgChannelOpenAck) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeTry) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -3369,10 +8257,10 @@ func (m *MsgChannelOpenAck) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgChannelOpenAck: wiretype end group for non-group") + return fmt.Errorf("proto: MsgChannelUpgradeTry: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgChannelOpenAck: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgChannelUpgradeTry: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: @@ -3441,7 +8329,7 @@ func (m *MsgChannelOpenAck) Unmarshal(dAtA []byte) error { iNdEx = postIndex case 3: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyChannelId", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ProposedUpgradeConnectionHops", wireType) } var stringLen uint64 for shift := uint(0); ; shift += 7 { @@ -3469,13 +8357,13 @@ func (m *MsgChannelOpenAck) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - m.CounterpartyChannelId = string(dAtA[iNdEx:postIndex]) + m.ProposedUpgradeConnectionHops = append(m.ProposedUpgradeConnectionHops, string(dAtA[iNdEx:postIndex])) iNdEx = postIndex case 4: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyVersion", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyUpgradeFields", wireType) } - var stringLen uint64 + var msglen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -3485,27 +8373,47 @@ func (m *MsgChannelOpenAck) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - stringLen |= uint64(b&0x7F) << shift + msglen |= int(b&0x7F) << shift if b < 0x80 { break } } - intStringLen := int(stringLen) - if intStringLen < 0 { + if msglen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + intStringLen + postIndex := iNdEx + msglen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.CounterpartyVersion = string(dAtA[iNdEx:postIndex]) + if err := m.CounterpartyUpgradeFields.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } iNdEx = postIndex case 5: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyUpgradeSequence", wireType) + } + m.CounterpartyUpgradeSequence = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.CounterpartyUpgradeSequence |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + case 6: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ProofTry", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ProofChannel", wireType) } var byteLen int for shift := uint(0); ; shift += 7 { @@ -3532,12 +8440,46 @@ func (m *MsgChannelOpenAck) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - m.ProofTry = append(m.ProofTry[:0], dAtA[iNdEx:postIndex]...) - if m.ProofTry == nil { - m.ProofTry = []byte{} + m.ProofChannel = append(m.ProofChannel[:0], dAtA[iNdEx:postIndex]...) + if m.ProofChannel == nil { + m.ProofChannel = []byte{} } iNdEx = postIndex - case 6: + case 7: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofUpgrade", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if byteLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ProofUpgrade = append(m.ProofUpgrade[:0], dAtA[iNdEx:postIndex]...) + if m.ProofUpgrade == nil { + m.ProofUpgrade = []byte{} + } + iNdEx = postIndex + case 8: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) } @@ -3570,7 +8512,7 @@ func (m *MsgChannelOpenAck) Unmarshal(dAtA []byte) error { return err } iNdEx = postIndex - case 7: + case 9: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) } @@ -3623,7 +8565,7 @@ func (m *MsgChannelOpenAck) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgChannelOpenAckResponse) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeTryResponse) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -3646,12 +8588,83 @@ func (m *MsgChannelOpenAckResponse) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgChannelOpenAckResponse: wiretype end group for non-group") + return fmt.Errorf("proto: MsgChannelUpgradeTryResponse: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgChannelOpenAckResponse: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgChannelUpgradeTryResponse: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Upgrade", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.Upgrade.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 2: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field UpgradeSequence", wireType) + } + m.UpgradeSequence = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.UpgradeSequence |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + case 3: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field Result", wireType) + } + m.Result = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.Result |= ResponseResultType(b&0x7F) << shift + if b < 0x80 { + break + } + } default: iNdEx = preIndex skippy, err := skipTx(dAtA[iNdEx:]) @@ -3673,7 +8686,7 @@ func (m *MsgChannelOpenAckResponse) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgChannelOpenConfirm) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeAck) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -3696,10 +8709,10 @@ func (m *MsgChannelOpenConfirm) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgChannelOpenConfirm: wiretype end group for non-group") + return fmt.Errorf("proto: MsgChannelUpgradeAck: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgChannelOpenConfirm: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgChannelUpgradeAck: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: @@ -3757,18 +8770,85 @@ func (m *MsgChannelOpenConfirm) Unmarshal(dAtA []byte) error { if intStringLen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + intStringLen + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ChannelId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyUpgrade", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.CounterpartyUpgrade.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 4: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofChannel", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if byteLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + byteLen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.ChannelId = string(dAtA[iNdEx:postIndex]) + m.ProofChannel = append(m.ProofChannel[:0], dAtA[iNdEx:postIndex]...) + if m.ProofChannel == nil { + m.ProofChannel = []byte{} + } iNdEx = postIndex - case 3: + case 5: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ProofAck", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ProofUpgrade", wireType) } var byteLen int for shift := uint(0); ; shift += 7 { @@ -3795,12 +8875,12 @@ func (m *MsgChannelOpenConfirm) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - m.ProofAck = append(m.ProofAck[:0], dAtA[iNdEx:postIndex]...) - if m.ProofAck == nil { - m.ProofAck = []byte{} + m.ProofUpgrade = append(m.ProofUpgrade[:0], dAtA[iNdEx:postIndex]...) + if m.ProofUpgrade == nil { + m.ProofUpgrade = []byte{} } iNdEx = postIndex - case 4: + case 6: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) } @@ -3833,7 +8913,7 @@ func (m *MsgChannelOpenConfirm) Unmarshal(dAtA []byte) error { return err } iNdEx = postIndex - case 5: + case 7: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) } @@ -3886,7 +8966,7 @@ func (m *MsgChannelOpenConfirm) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgChannelOpenConfirmResponse) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeAckResponse) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -3909,12 +8989,31 @@ func (m *MsgChannelOpenConfirmResponse) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgChannelOpenConfirmResponse: wiretype end group for non-group") + return fmt.Errorf("proto: MsgChannelUpgradeAckResponse: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgChannelOpenConfirmResponse: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgChannelUpgradeAckResponse: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { + case 1: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field Result", wireType) + } + m.Result = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.Result |= ResponseResultType(b&0x7F) << shift + if b < 0x80 { + break + } + } default: iNdEx = preIndex skippy, err := skipTx(dAtA[iNdEx:]) @@ -3936,7 +9035,7 @@ func (m *MsgChannelOpenConfirmResponse) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgChannelCloseInit) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeConfirm) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -3959,10 +9058,10 @@ func (m *MsgChannelCloseInit) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgChannelCloseInit: wiretype end group for non-group") + return fmt.Errorf("proto: MsgChannelUpgradeConfirm: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgChannelCloseInit: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgChannelUpgradeConfirm: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: @@ -4030,10 +9129,10 @@ func (m *MsgChannelCloseInit) Unmarshal(dAtA []byte) error { m.ChannelId = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex case 3: - if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyChannelState", wireType) } - var stringLen uint64 + m.CounterpartyChannelState = 0 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -4043,129 +9142,16 @@ func (m *MsgChannelCloseInit) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - stringLen |= uint64(b&0x7F) << shift + m.CounterpartyChannelState |= State(b&0x7F) << shift if b < 0x80 { break } } - intStringLen := int(stringLen) - if intStringLen < 0 { - return ErrInvalidLengthTx - } - postIndex := iNdEx + intStringLen - if postIndex < 0 { - return ErrInvalidLengthTx - } - if postIndex > l { - return io.ErrUnexpectedEOF - } - m.Signer = string(dAtA[iNdEx:postIndex]) - iNdEx = postIndex - default: - iNdEx = preIndex - skippy, err := skipTx(dAtA[iNdEx:]) - if err != nil { - return err - } - if (skippy < 0) || (iNdEx+skippy) < 0 { - return ErrInvalidLengthTx - } - if (iNdEx + skippy) > l { - return io.ErrUnexpectedEOF - } - iNdEx += skippy - } - } - - if iNdEx > l { - return io.ErrUnexpectedEOF - } - return nil -} -func (m *MsgChannelCloseInitResponse) Unmarshal(dAtA []byte) error { - l := len(dAtA) - iNdEx := 0 - for iNdEx < l { - preIndex := iNdEx - var wire uint64 - for shift := uint(0); ; shift += 7 { - if shift >= 64 { - return ErrIntOverflowTx - } - if iNdEx >= l { - return io.ErrUnexpectedEOF - } - b := dAtA[iNdEx] - iNdEx++ - wire |= uint64(b&0x7F) << shift - if b < 0x80 { - break - } - } - fieldNum := int32(wire >> 3) - wireType := int(wire & 0x7) - if wireType == 4 { - return fmt.Errorf("proto: MsgChannelCloseInitResponse: wiretype end group for non-group") - } - if fieldNum <= 0 { - return fmt.Errorf("proto: MsgChannelCloseInitResponse: illegal tag %d (wire type %d)", fieldNum, wire) - } - switch fieldNum { - default: - iNdEx = preIndex - skippy, err := skipTx(dAtA[iNdEx:]) - if err != nil { - return err - } - if (skippy < 0) || (iNdEx+skippy) < 0 { - return ErrInvalidLengthTx - } - if (iNdEx + skippy) > l { - return io.ErrUnexpectedEOF - } - iNdEx += skippy - } - } - - if iNdEx > l { - return io.ErrUnexpectedEOF - } - return nil -} -func (m *MsgChannelCloseConfirm) Unmarshal(dAtA []byte) error { - l := len(dAtA) - iNdEx := 0 - for iNdEx < l { - preIndex := iNdEx - var wire uint64 - for shift := uint(0); ; shift += 7 { - if shift >= 64 { - return ErrIntOverflowTx - } - if iNdEx >= l { - return io.ErrUnexpectedEOF - } - b := dAtA[iNdEx] - iNdEx++ - wire |= uint64(b&0x7F) << shift - if b < 0x80 { - break - } - } - fieldNum := int32(wire >> 3) - wireType := int(wire & 0x7) - if wireType == 4 { - return fmt.Errorf("proto: MsgChannelCloseConfirm: wiretype end group for non-group") - } - if fieldNum <= 0 { - return fmt.Errorf("proto: MsgChannelCloseConfirm: illegal tag %d (wire type %d)", fieldNum, wire) - } - switch fieldNum { - case 1: + case 4: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyUpgrade", wireType) } - var stringLen uint64 + var msglen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -4175,29 +9161,30 @@ func (m *MsgChannelCloseConfirm) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - stringLen |= uint64(b&0x7F) << shift + msglen |= int(b&0x7F) << shift if b < 0x80 { break } } - intStringLen := int(stringLen) - if intStringLen < 0 { + if msglen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + intStringLen + postIndex := iNdEx + msglen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.PortId = string(dAtA[iNdEx:postIndex]) + if err := m.CounterpartyUpgrade.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } iNdEx = postIndex - case 2: + case 5: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ProofChannel", wireType) } - var stringLen uint64 + var byteLen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -4207,27 +9194,29 @@ func (m *MsgChannelCloseConfirm) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - stringLen |= uint64(b&0x7F) << shift + byteLen |= int(b&0x7F) << shift if b < 0x80 { break } } - intStringLen := int(stringLen) - if intStringLen < 0 { + if byteLen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + intStringLen + postIndex := iNdEx + byteLen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.ChannelId = string(dAtA[iNdEx:postIndex]) + m.ProofChannel = append(m.ProofChannel[:0], dAtA[iNdEx:postIndex]...) + if m.ProofChannel == nil { + m.ProofChannel = []byte{} + } iNdEx = postIndex - case 3: + case 6: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ProofInit", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ProofUpgrade", wireType) } var byteLen int for shift := uint(0); ; shift += 7 { @@ -4254,12 +9243,12 @@ func (m *MsgChannelCloseConfirm) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - m.ProofInit = append(m.ProofInit[:0], dAtA[iNdEx:postIndex]...) - if m.ProofInit == nil { - m.ProofInit = []byte{} + m.ProofUpgrade = append(m.ProofUpgrade[:0], dAtA[iNdEx:postIndex]...) + if m.ProofUpgrade == nil { + m.ProofUpgrade = []byte{} } iNdEx = postIndex - case 4: + case 7: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) } @@ -4292,7 +9281,7 @@ func (m *MsgChannelCloseConfirm) Unmarshal(dAtA []byte) error { return err } iNdEx = postIndex - case 5: + case 8: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) } @@ -4345,7 +9334,7 @@ func (m *MsgChannelCloseConfirm) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgChannelCloseConfirmResponse) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeConfirmResponse) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -4368,12 +9357,31 @@ func (m *MsgChannelCloseConfirmResponse) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgChannelCloseConfirmResponse: wiretype end group for non-group") + return fmt.Errorf("proto: MsgChannelUpgradeConfirmResponse: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgChannelCloseConfirmResponse: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgChannelUpgradeConfirmResponse: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { + case 1: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field Result", wireType) + } + m.Result = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.Result |= ResponseResultType(b&0x7F) << shift + if b < 0x80 { + break + } + } default: iNdEx = preIndex skippy, err := skipTx(dAtA[iNdEx:]) @@ -4395,7 +9403,7 @@ func (m *MsgChannelCloseConfirmResponse) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgRecvPacket) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeOpen) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -4405,30 +9413,62 @@ func (m *MsgRecvPacket) Unmarshal(dAtA []byte) error { if shift >= 64 { return ErrIntOverflowTx } - if iNdEx >= l { - return io.ErrUnexpectedEOF + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgChannelUpgradeOpen: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgChannelUpgradeOpen: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx } - b := dAtA[iNdEx] - iNdEx++ - wire |= uint64(b&0x7F) << shift - if b < 0x80 { - break + if postIndex > l { + return io.ErrUnexpectedEOF } - } - fieldNum := int32(wire >> 3) - wireType := int(wire & 0x7) - if wireType == 4 { - return fmt.Errorf("proto: MsgRecvPacket: wiretype end group for non-group") - } - if fieldNum <= 0 { - return fmt.Errorf("proto: MsgRecvPacket: illegal tag %d (wire type %d)", fieldNum, wire) - } - switch fieldNum { - case 1: + m.PortId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Packet", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) } - var msglen int + var stringLen uint64 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -4438,28 +9478,46 @@ func (m *MsgRecvPacket) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - msglen |= int(b&0x7F) << shift + stringLen |= uint64(b&0x7F) << shift if b < 0x80 { break } } - if msglen < 0 { + intStringLen := int(stringLen) + if intStringLen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + msglen + postIndex := iNdEx + intStringLen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - if err := m.Packet.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { - return err - } + m.ChannelId = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex - case 2: + case 3: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyChannelState", wireType) + } + m.CounterpartyChannelState = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.CounterpartyChannelState |= State(b&0x7F) << shift + if b < 0x80 { + break + } + } + case 4: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ProofCommitment", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ProofChannel", wireType) } var byteLen int for shift := uint(0); ; shift += 7 { @@ -4486,12 +9544,12 @@ func (m *MsgRecvPacket) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - m.ProofCommitment = append(m.ProofCommitment[:0], dAtA[iNdEx:postIndex]...) - if m.ProofCommitment == nil { - m.ProofCommitment = []byte{} + m.ProofChannel = append(m.ProofChannel[:0], dAtA[iNdEx:postIndex]...) + if m.ProofChannel == nil { + m.ProofChannel = []byte{} } iNdEx = postIndex - case 3: + case 5: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) } @@ -4524,7 +9582,7 @@ func (m *MsgRecvPacket) Unmarshal(dAtA []byte) error { return err } iNdEx = postIndex - case 4: + case 6: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) } @@ -4577,7 +9635,7 @@ func (m *MsgRecvPacket) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgRecvPacketResponse) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeOpenResponse) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -4600,31 +9658,12 @@ func (m *MsgRecvPacketResponse) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgRecvPacketResponse: wiretype end group for non-group") + return fmt.Errorf("proto: MsgChannelUpgradeOpenResponse: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgRecvPacketResponse: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgChannelUpgradeOpenResponse: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { - case 1: - if wireType != 0 { - return fmt.Errorf("proto: wrong wireType = %d for field Result", wireType) - } - m.Result = 0 - for shift := uint(0); ; shift += 7 { - if shift >= 64 { - return ErrIntOverflowTx - } - if iNdEx >= l { - return io.ErrUnexpectedEOF - } - b := dAtA[iNdEx] - iNdEx++ - m.Result |= ResponseResultType(b&0x7F) << shift - if b < 0x80 { - break - } - } default: iNdEx = preIndex skippy, err := skipTx(dAtA[iNdEx:]) @@ -4646,7 +9685,7 @@ func (m *MsgRecvPacketResponse) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgTimeout) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeTimeout) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -4669,17 +9708,17 @@ func (m *MsgTimeout) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgTimeout: wiretype end group for non-group") + return fmt.Errorf("proto: MsgChannelUpgradeTimeout: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgTimeout: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgChannelUpgradeTimeout: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Packet", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) } - var msglen int + var stringLen uint64 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -4689,30 +9728,29 @@ func (m *MsgTimeout) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - msglen |= int(b&0x7F) << shift + stringLen |= uint64(b&0x7F) << shift if b < 0x80 { break } } - if msglen < 0 { + intStringLen := int(stringLen) + if intStringLen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + msglen + postIndex := iNdEx + intStringLen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - if err := m.Packet.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { - return err - } + m.PortId = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex case 2: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ProofUnreceived", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) } - var byteLen int + var stringLen uint64 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -4722,29 +9760,27 @@ func (m *MsgTimeout) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - byteLen |= int(b&0x7F) << shift + stringLen |= uint64(b&0x7F) << shift if b < 0x80 { break } } - if byteLen < 0 { + intStringLen := int(stringLen) + if intStringLen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + byteLen + postIndex := iNdEx + intStringLen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.ProofUnreceived = append(m.ProofUnreceived[:0], dAtA[iNdEx:postIndex]...) - if m.ProofUnreceived == nil { - m.ProofUnreceived = []byte{} - } + m.ChannelId = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex case 3: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field CounterpartyChannel", wireType) } var msglen int for shift := uint(0); ; shift += 7 { @@ -4771,15 +9807,15 @@ func (m *MsgTimeout) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + if err := m.CounterpartyChannel.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { return err } iNdEx = postIndex case 4: - if wireType != 0 { - return fmt.Errorf("proto: wrong wireType = %d for field NextSequenceRecv", wireType) + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofChannel", wireType) } - m.NextSequenceRecv = 0 + var byteLen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -4789,12 +9825,60 @@ func (m *MsgTimeout) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - m.NextSequenceRecv |= uint64(b&0x7F) << shift + byteLen |= int(b&0x7F) << shift if b < 0x80 { break } } + if byteLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ProofChannel = append(m.ProofChannel[:0], dAtA[iNdEx:postIndex]...) + if m.ProofChannel == nil { + m.ProofChannel = []byte{} + } + iNdEx = postIndex case 5: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 6: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) } @@ -4847,7 +9931,7 @@ func (m *MsgTimeout) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgTimeoutResponse) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeTimeoutResponse) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -4870,31 +9954,12 @@ func (m *MsgTimeoutResponse) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgTimeoutResponse: wiretype end group for non-group") + return fmt.Errorf("proto: MsgChannelUpgradeTimeoutResponse: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgTimeoutResponse: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgChannelUpgradeTimeoutResponse: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { - case 1: - if wireType != 0 { - return fmt.Errorf("proto: wrong wireType = %d for field Result", wireType) - } - m.Result = 0 - for shift := uint(0); ; shift += 7 { - if shift >= 64 { - return ErrIntOverflowTx - } - if iNdEx >= l { - return io.ErrUnexpectedEOF - } - b := dAtA[iNdEx] - iNdEx++ - m.Result |= ResponseResultType(b&0x7F) << shift - if b < 0x80 { - break - } - } default: iNdEx = preIndex skippy, err := skipTx(dAtA[iNdEx:]) @@ -4916,7 +9981,7 @@ func (m *MsgTimeoutResponse) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgTimeoutOnClose) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeCancel) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -4939,17 +10004,17 @@ func (m *MsgTimeoutOnClose) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgTimeoutOnClose: wiretype end group for non-group") + return fmt.Errorf("proto: MsgChannelUpgradeCancel: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgTimeoutOnClose: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgChannelUpgradeCancel: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Packet", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) } - var msglen int + var stringLen uint64 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -4959,30 +10024,29 @@ func (m *MsgTimeoutOnClose) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - msglen |= int(b&0x7F) << shift + stringLen |= uint64(b&0x7F) << shift if b < 0x80 { break } } - if msglen < 0 { + intStringLen := int(stringLen) + if intStringLen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + msglen + postIndex := iNdEx + intStringLen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - if err := m.Packet.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { - return err - } + m.PortId = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex case 2: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ProofUnreceived", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) } - var byteLen int + var stringLen uint64 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -4992,29 +10056,60 @@ func (m *MsgTimeoutOnClose) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - byteLen |= int(b&0x7F) << shift + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthTx + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthTx + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ChannelId = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ErrorReceipt", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift if b < 0x80 { break } } - if byteLen < 0 { + if msglen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + byteLen + postIndex := iNdEx + msglen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.ProofUnreceived = append(m.ProofUnreceived[:0], dAtA[iNdEx:postIndex]...) - if m.ProofUnreceived == nil { - m.ProofUnreceived = []byte{} + if err := m.ErrorReceipt.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err } iNdEx = postIndex - case 3: + case 4: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ProofClose", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ProofErrorReceipt", wireType) } var byteLen int for shift := uint(0); ; shift += 7 { @@ -5041,12 +10136,12 @@ func (m *MsgTimeoutOnClose) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - m.ProofClose = append(m.ProofClose[:0], dAtA[iNdEx:postIndex]...) - if m.ProofClose == nil { - m.ProofClose = []byte{} + m.ProofErrorReceipt = append(m.ProofErrorReceipt[:0], dAtA[iNdEx:postIndex]...) + if m.ProofErrorReceipt == nil { + m.ProofErrorReceipt = []byte{} } iNdEx = postIndex - case 4: + case 5: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) } @@ -5079,25 +10174,6 @@ func (m *MsgTimeoutOnClose) Unmarshal(dAtA []byte) error { return err } iNdEx = postIndex - case 5: - if wireType != 0 { - return fmt.Errorf("proto: wrong wireType = %d for field NextSequenceRecv", wireType) - } - m.NextSequenceRecv = 0 - for shift := uint(0); ; shift += 7 { - if shift >= 64 { - return ErrIntOverflowTx - } - if iNdEx >= l { - return io.ErrUnexpectedEOF - } - b := dAtA[iNdEx] - iNdEx++ - m.NextSequenceRecv |= uint64(b&0x7F) << shift - if b < 0x80 { - break - } - } case 6: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) @@ -5151,7 +10227,7 @@ func (m *MsgTimeoutOnClose) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgTimeoutOnCloseResponse) Unmarshal(dAtA []byte) error { +func (m *MsgChannelUpgradeCancelResponse) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -5174,31 +10250,12 @@ func (m *MsgTimeoutOnCloseResponse) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgTimeoutOnCloseResponse: wiretype end group for non-group") + return fmt.Errorf("proto: MsgChannelUpgradeCancelResponse: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgTimeoutOnCloseResponse: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgChannelUpgradeCancelResponse: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { - case 1: - if wireType != 0 { - return fmt.Errorf("proto: wrong wireType = %d for field Result", wireType) - } - m.Result = 0 - for shift := uint(0); ; shift += 7 { - if shift >= 64 { - return ErrIntOverflowTx - } - if iNdEx >= l { - return io.ErrUnexpectedEOF - } - b := dAtA[iNdEx] - iNdEx++ - m.Result |= ResponseResultType(b&0x7F) << shift - if b < 0x80 { - break - } - } default: iNdEx = preIndex skippy, err := skipTx(dAtA[iNdEx:]) @@ -5220,7 +10277,7 @@ func (m *MsgTimeoutOnCloseResponse) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgAcknowledgement) Unmarshal(dAtA []byte) error { +func (m *MsgUpdateParams) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -5243,17 +10300,17 @@ func (m *MsgAcknowledgement) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgAcknowledgement: wiretype end group for non-group") + return fmt.Errorf("proto: MsgUpdateParams: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgAcknowledgement: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgUpdateParams: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Packet", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field Authority", wireType) } - var msglen int + var stringLen uint64 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -5263,30 +10320,29 @@ func (m *MsgAcknowledgement) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - msglen |= int(b&0x7F) << shift + stringLen |= uint64(b&0x7F) << shift if b < 0x80 { break } } - if msglen < 0 { + intStringLen := int(stringLen) + if intStringLen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + msglen + postIndex := iNdEx + intStringLen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - if err := m.Packet.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { - return err - } + m.Authority = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex case 2: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Acknowledgement", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field Params", wireType) } - var byteLen int + var msglen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -5296,31 +10352,130 @@ func (m *MsgAcknowledgement) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - byteLen |= int(b&0x7F) << shift + msglen |= int(b&0x7F) << shift if b < 0x80 { break } } - if byteLen < 0 { + if msglen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + byteLen + postIndex := iNdEx + msglen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.Acknowledgement = append(m.Acknowledgement[:0], dAtA[iNdEx:postIndex]...) - if m.Acknowledgement == nil { - m.Acknowledgement = []byte{} + if err := m.Params.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err } iNdEx = postIndex - case 3: + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgUpdateParamsResponse) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgUpdateParamsResponse: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgUpdateParamsResponse: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + default: + iNdEx = preIndex + skippy, err := skipTx(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthTx + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *MsgPruneAcknowledgements) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: MsgPruneAcknowledgements: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: MsgPruneAcknowledgements: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ProofAcked", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field PortId", wireType) } - var byteLen int + var stringLen uint64 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -5330,31 +10485,29 @@ func (m *MsgAcknowledgement) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - byteLen |= int(b&0x7F) << shift + stringLen |= uint64(b&0x7F) << shift if b < 0x80 { break } } - if byteLen < 0 { + intStringLen := int(stringLen) + if intStringLen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + byteLen + postIndex := iNdEx + intStringLen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - m.ProofAcked = append(m.ProofAcked[:0], dAtA[iNdEx:postIndex]...) - if m.ProofAcked == nil { - m.ProofAcked = []byte{} - } + m.PortId = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex - case 4: + case 2: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field ProofHeight", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field ChannelId", wireType) } - var msglen int + var stringLen uint64 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -5364,26 +10517,44 @@ func (m *MsgAcknowledgement) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - msglen |= int(b&0x7F) << shift + stringLen |= uint64(b&0x7F) << shift if b < 0x80 { break } } - if msglen < 0 { + intStringLen := int(stringLen) + if intStringLen < 0 { return ErrInvalidLengthTx } - postIndex := iNdEx + msglen + postIndex := iNdEx + intStringLen if postIndex < 0 { return ErrInvalidLengthTx } if postIndex > l { return io.ErrUnexpectedEOF } - if err := m.ProofHeight.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { - return err - } + m.ChannelId = string(dAtA[iNdEx:postIndex]) iNdEx = postIndex - case 5: + case 3: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field Limit", wireType) + } + m.Limit = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.Limit |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + case 4: if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field Signer", wireType) } @@ -5436,7 +10607,7 @@ func (m *MsgAcknowledgement) Unmarshal(dAtA []byte) error { } return nil } -func (m *MsgAcknowledgementResponse) Unmarshal(dAtA []byte) error { +func (m *MsgPruneAcknowledgementsResponse) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 for iNdEx < l { @@ -5459,17 +10630,17 @@ func (m *MsgAcknowledgementResponse) Unmarshal(dAtA []byte) error { fieldNum := int32(wire >> 3) wireType := int(wire & 0x7) if wireType == 4 { - return fmt.Errorf("proto: MsgAcknowledgementResponse: wiretype end group for non-group") + return fmt.Errorf("proto: MsgPruneAcknowledgementsResponse: wiretype end group for non-group") } if fieldNum <= 0 { - return fmt.Errorf("proto: MsgAcknowledgementResponse: illegal tag %d (wire type %d)", fieldNum, wire) + return fmt.Errorf("proto: MsgPruneAcknowledgementsResponse: illegal tag %d (wire type %d)", fieldNum, wire) } switch fieldNum { case 1: if wireType != 0 { - return fmt.Errorf("proto: wrong wireType = %d for field Result", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field TotalPrunedSequences", wireType) } - m.Result = 0 + m.TotalPrunedSequences = 0 for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowTx @@ -5479,7 +10650,26 @@ func (m *MsgAcknowledgementResponse) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - m.Result |= ResponseResultType(b&0x7F) << shift + m.TotalPrunedSequences |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + case 2: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field TotalRemainingSequences", wireType) + } + m.TotalRemainingSequences = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowTx + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.TotalRemainingSequences |= uint64(b&0x7F) << shift if b < 0x80 { break } diff --git a/modules/core/04-channel/types/upgrade.go b/modules/core/04-channel/types/upgrade.go new file mode 100644 index 00000000000..d96e41f5e3c --- /dev/null +++ b/modules/core/04-channel/types/upgrade.go @@ -0,0 +1,126 @@ +package types + +import ( + "errors" + "fmt" + "slices" + "strings" + + errorsmod "cosmossdk.io/errors" + + connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" +) + +// NewUpgrade creates a new Upgrade instance. +func NewUpgrade(upgradeFields UpgradeFields, timeout Timeout, nextSequenceSend uint64) Upgrade { + return Upgrade{ + Fields: upgradeFields, + Timeout: timeout, + NextSequenceSend: nextSequenceSend, + } +} + +// NewUpgradeFields returns a new ModifiableUpgradeFields instance. +func NewUpgradeFields(ordering Order, connectionHops []string, version string) UpgradeFields { + return UpgradeFields{ + Ordering: ordering, + ConnectionHops: connectionHops, + Version: version, + } +} + +// ValidateBasic performs a basic validation of the upgrade fields +func (u Upgrade) ValidateBasic() error { + if err := u.Fields.ValidateBasic(); err != nil { + return errorsmod.Wrap(err, "proposed upgrade fields are invalid") + } + + if !u.Timeout.IsValid() { + return errorsmod.Wrap(ErrInvalidUpgrade, "upgrade timeout height and upgrade timeout timestamp cannot both be 0") + } + + return nil +} + +// ValidateBasic performs a basic validation of the proposed upgrade fields +func (uf UpgradeFields) ValidateBasic() error { + if !slices.Contains(connectiontypes.SupportedOrderings, uf.Ordering.String()) { + return errorsmod.Wrap(ErrInvalidChannelOrdering, uf.Ordering.String()) + } + + if len(uf.ConnectionHops) != 1 { + return errorsmod.Wrap(ErrTooManyConnectionHops, "current IBC version only supports one connection hop") + } + + if strings.TrimSpace(uf.Version) == "" { + return errorsmod.Wrap(ErrInvalidChannelVersion, "version cannot be empty") + } + + return nil +} + +// UpgradeError defines an error that occurs during an upgrade. +type UpgradeError struct { + // err is the underlying error that caused the upgrade to fail. + // this error should not be written to state. + err error + // sequence is the upgrade sequence number of the upgrade that failed. + sequence uint64 +} + +var _ error = &UpgradeError{} + +// NewUpgradeError returns a new UpgradeError instance. +func NewUpgradeError(upgradeSequence uint64, err error) *UpgradeError { + return &UpgradeError{ + err: err, + sequence: upgradeSequence, + } +} + +// Error implements the error interface, returning the underlying error which caused the upgrade to fail. +func (u *UpgradeError) Error() string { + return u.err.Error() +} + +// Is returns true if the underlying error is of the given err type. +func (u *UpgradeError) Is(err error) bool { + return errors.Is(u.err, err) +} + +// Unwrap returns the base error that caused the upgrade to fail. +func (u *UpgradeError) Unwrap() error { + baseError := u.err + for { + if err := errors.Unwrap(baseError); err != nil { + baseError = err + } else { + return baseError + } + } +} + +// Cause implements the sdk error interface which uses this function to unwrap the error in various functions such as `wrappedError.Is()`. +// Cause returns the underlying error which caused the upgrade to fail. +func (u *UpgradeError) Cause() error { + return u.err +} + +// GetErrorReceipt returns an error receipt with the code from the underlying error type stripped. +func (u *UpgradeError) GetErrorReceipt() ErrorReceipt { + // restoreErrorString defines a string constant included in error receipts. + // NOTE: Changing this const is state machine breaking as it is written into state. + const restoreErrorString = "restored channel to pre-upgrade state" + + _, code, _ := errorsmod.ABCIInfo(u, false) // discard non-determinstic codespace and log values + return ErrorReceipt{ + Sequence: u.sequence, + Message: fmt.Sprintf("ABCI code: %d: %s", code, restoreErrorString), + } +} + +// IsUpgradeError returns true if err is of type UpgradeError, otherwise false. +func IsUpgradeError(err error) bool { + _, ok := err.(*UpgradeError) + return ok +} diff --git a/modules/core/04-channel/types/upgrade.pb.go b/modules/core/04-channel/types/upgrade.pb.go new file mode 100644 index 00000000000..e7931817125 --- /dev/null +++ b/modules/core/04-channel/types/upgrade.pb.go @@ -0,0 +1,842 @@ +// Code generated by protoc-gen-gogo. DO NOT EDIT. +// source: ibc/core/channel/v1/upgrade.proto + +package types + +import ( + fmt "fmt" + _ "github.com/cosmos/gogoproto/gogoproto" + proto "github.com/cosmos/gogoproto/proto" + io "io" + math "math" + math_bits "math/bits" +) + +// Reference imports to suppress errors if they are not otherwise used. +var _ = proto.Marshal +var _ = fmt.Errorf +var _ = math.Inf + +// This is a compile-time assertion to ensure that this generated file +// is compatible with the proto package it is being compiled against. +// A compilation error at this line likely means your copy of the +// proto package needs to be updated. +const _ = proto.GoGoProtoPackageIsVersion3 // please upgrade the proto package + +// Upgrade is a verifiable type which contains the relevant information +// for an attempted upgrade. It provides the proposed changes to the channel +// end, the timeout for this upgrade attempt and the next packet sequence +// which allows the counterparty to efficiently know the highest sequence it has received. +// The next sequence send is used for pruning and upgrading from unordered to ordered channels. +type Upgrade struct { + Fields UpgradeFields `protobuf:"bytes,1,opt,name=fields,proto3" json:"fields"` + Timeout Timeout `protobuf:"bytes,2,opt,name=timeout,proto3" json:"timeout"` + NextSequenceSend uint64 `protobuf:"varint,3,opt,name=next_sequence_send,json=nextSequenceSend,proto3" json:"next_sequence_send,omitempty"` +} + +func (m *Upgrade) Reset() { *m = Upgrade{} } +func (m *Upgrade) String() string { return proto.CompactTextString(m) } +func (*Upgrade) ProtoMessage() {} +func (*Upgrade) Descriptor() ([]byte, []int) { + return fileDescriptor_fb1cef68588848b2, []int{0} +} +func (m *Upgrade) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *Upgrade) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_Upgrade.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } +} +func (m *Upgrade) XXX_Merge(src proto.Message) { + xxx_messageInfo_Upgrade.Merge(m, src) +} +func (m *Upgrade) XXX_Size() int { + return m.Size() +} +func (m *Upgrade) XXX_DiscardUnknown() { + xxx_messageInfo_Upgrade.DiscardUnknown(m) +} + +var xxx_messageInfo_Upgrade proto.InternalMessageInfo + +// UpgradeFields are the fields in a channel end which may be changed +// during a channel upgrade. +type UpgradeFields struct { + Ordering Order `protobuf:"varint,1,opt,name=ordering,proto3,enum=ibc.core.channel.v1.Order" json:"ordering,omitempty"` + ConnectionHops []string `protobuf:"bytes,2,rep,name=connection_hops,json=connectionHops,proto3" json:"connection_hops,omitempty"` + Version string `protobuf:"bytes,3,opt,name=version,proto3" json:"version,omitempty"` +} + +func (m *UpgradeFields) Reset() { *m = UpgradeFields{} } +func (m *UpgradeFields) String() string { return proto.CompactTextString(m) } +func (*UpgradeFields) ProtoMessage() {} +func (*UpgradeFields) Descriptor() ([]byte, []int) { + return fileDescriptor_fb1cef68588848b2, []int{1} +} +func (m *UpgradeFields) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *UpgradeFields) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_UpgradeFields.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } +} +func (m *UpgradeFields) XXX_Merge(src proto.Message) { + xxx_messageInfo_UpgradeFields.Merge(m, src) +} +func (m *UpgradeFields) XXX_Size() int { + return m.Size() +} +func (m *UpgradeFields) XXX_DiscardUnknown() { + xxx_messageInfo_UpgradeFields.DiscardUnknown(m) +} + +var xxx_messageInfo_UpgradeFields proto.InternalMessageInfo + +// ErrorReceipt defines a type which encapsulates the upgrade sequence and error associated with the +// upgrade handshake failure. When a channel upgrade handshake is aborted both chains are expected to increment to the +// next sequence. +type ErrorReceipt struct { + // the channel upgrade sequence + Sequence uint64 `protobuf:"varint,1,opt,name=sequence,proto3" json:"sequence,omitempty"` + // the error message detailing the cause of failure + Message string `protobuf:"bytes,2,opt,name=message,proto3" json:"message,omitempty"` +} + +func (m *ErrorReceipt) Reset() { *m = ErrorReceipt{} } +func (m *ErrorReceipt) String() string { return proto.CompactTextString(m) } +func (*ErrorReceipt) ProtoMessage() {} +func (*ErrorReceipt) Descriptor() ([]byte, []int) { + return fileDescriptor_fb1cef68588848b2, []int{2} +} +func (m *ErrorReceipt) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *ErrorReceipt) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + if deterministic { + return xxx_messageInfo_ErrorReceipt.Marshal(b, m, deterministic) + } else { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil + } +} +func (m *ErrorReceipt) XXX_Merge(src proto.Message) { + xxx_messageInfo_ErrorReceipt.Merge(m, src) +} +func (m *ErrorReceipt) XXX_Size() int { + return m.Size() +} +func (m *ErrorReceipt) XXX_DiscardUnknown() { + xxx_messageInfo_ErrorReceipt.DiscardUnknown(m) +} + +var xxx_messageInfo_ErrorReceipt proto.InternalMessageInfo + +func init() { + proto.RegisterType((*Upgrade)(nil), "ibc.core.channel.v1.Upgrade") + proto.RegisterType((*UpgradeFields)(nil), "ibc.core.channel.v1.UpgradeFields") + proto.RegisterType((*ErrorReceipt)(nil), "ibc.core.channel.v1.ErrorReceipt") +} + +func init() { proto.RegisterFile("ibc/core/channel/v1/upgrade.proto", fileDescriptor_fb1cef68588848b2) } + +var fileDescriptor_fb1cef68588848b2 = []byte{ + // 406 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x6c, 0x91, 0x41, 0x6f, 0xd3, 0x30, + 0x14, 0xc7, 0xe3, 0xad, 0x5a, 0x57, 0x03, 0x03, 0x19, 0x0e, 0x51, 0x85, 0xb2, 0xd2, 0x0b, 0x3d, + 0xb0, 0x98, 0x0d, 0x84, 0x00, 0x71, 0x40, 0x93, 0x40, 0x88, 0x0b, 0x92, 0x0b, 0x17, 0x2e, 0x55, + 0xe3, 0x3c, 0x52, 0x4b, 0x8d, 0x5f, 0xb0, 0x9d, 0x08, 0xbe, 0x01, 0xc7, 0x7d, 0x04, 0xbe, 0x08, + 0xf7, 0x1d, 0x77, 0xe4, 0x84, 0x50, 0xfb, 0x45, 0x50, 0x9c, 0xa4, 0x68, 0x52, 0x6e, 0x7e, 0x7e, + 0xbf, 0xff, 0xdf, 0xff, 0xe7, 0x47, 0x1f, 0xa8, 0x44, 0x72, 0x89, 0x06, 0xb8, 0x5c, 0x2d, 0xb5, + 0x86, 0x35, 0xaf, 0x4e, 0x79, 0x59, 0x64, 0x66, 0x99, 0x42, 0x5c, 0x18, 0x74, 0xc8, 0xee, 0xaa, + 0x44, 0xc6, 0x35, 0x12, 0xb7, 0x48, 0x5c, 0x9d, 0x8e, 0xef, 0x65, 0x98, 0xa1, 0xef, 0xf3, 0xfa, + 0xd4, 0xa0, 0xe3, 0x5e, 0xb7, 0x4e, 0xe5, 0x91, 0xe9, 0x2f, 0x42, 0x87, 0x9f, 0x1a, 0x7f, 0xf6, + 0x9a, 0x1e, 0x7c, 0x51, 0xb0, 0x4e, 0x6d, 0x48, 0x26, 0x64, 0x76, 0xe3, 0x6c, 0x1a, 0xf7, 0x3c, + 0x15, 0xb7, 0xf4, 0x5b, 0x4f, 0x9e, 0x0f, 0x2e, 0xff, 0x1c, 0x07, 0xa2, 0xd5, 0xb1, 0x57, 0x74, + 0xe8, 0x54, 0x0e, 0x58, 0xba, 0x70, 0xcf, 0x5b, 0xdc, 0xef, 0xb5, 0xf8, 0xd8, 0x30, 0xad, 0xb8, + 0x93, 0xb0, 0x47, 0x94, 0x69, 0xf8, 0xe6, 0x16, 0x16, 0xbe, 0x96, 0xa0, 0x25, 0x2c, 0x2c, 0xe8, + 0x34, 0xdc, 0x9f, 0x90, 0xd9, 0x40, 0xdc, 0xa9, 0x3b, 0xf3, 0xb6, 0x31, 0x07, 0x9d, 0xbe, 0x1c, + 0xfc, 0xf8, 0x79, 0x1c, 0x4c, 0x2f, 0x08, 0xbd, 0x75, 0x2d, 0x11, 0x7b, 0x46, 0x0f, 0xd1, 0xa4, + 0x60, 0x94, 0xce, 0xfc, 0x1c, 0x47, 0x67, 0xe3, 0xde, 0x10, 0x1f, 0x6a, 0x48, 0xec, 0x58, 0xf6, + 0x90, 0xde, 0x96, 0xa8, 0x35, 0x48, 0xa7, 0x50, 0x2f, 0x56, 0x58, 0xd8, 0x70, 0x6f, 0xb2, 0x3f, + 0x1b, 0x89, 0xa3, 0xff, 0xd7, 0xef, 0xb0, 0xb0, 0x2c, 0xa4, 0xc3, 0x0a, 0x8c, 0x55, 0xa8, 0x7d, + 0xb6, 0x91, 0xe8, 0xca, 0x36, 0xd2, 0x7b, 0x7a, 0xf3, 0x8d, 0x31, 0x68, 0x04, 0x48, 0x50, 0x85, + 0x63, 0x63, 0x7a, 0xd8, 0x4d, 0xe4, 0x03, 0x0d, 0xc4, 0xae, 0xae, 0xbd, 0x72, 0xb0, 0x76, 0x99, + 0x81, 0xff, 0xb0, 0x91, 0xe8, 0xca, 0xc6, 0xeb, 0x7c, 0x7e, 0xb9, 0x89, 0xc8, 0xd5, 0x26, 0x22, + 0x7f, 0x37, 0x11, 0xb9, 0xd8, 0x46, 0xc1, 0xd5, 0x36, 0x0a, 0x7e, 0x6f, 0xa3, 0xe0, 0xf3, 0x8b, + 0x4c, 0xb9, 0x55, 0x99, 0xc4, 0x12, 0x73, 0x2e, 0xd1, 0xe6, 0x68, 0xb9, 0x4a, 0xe4, 0x49, 0x86, + 0xbc, 0x7a, 0xce, 0x73, 0x4c, 0xcb, 0x35, 0xd8, 0x66, 0xf7, 0x8f, 0x9f, 0x9e, 0x74, 0xeb, 0x77, + 0xdf, 0x0b, 0xb0, 0xc9, 0x81, 0x5f, 0xfd, 0x93, 0x7f, 0x01, 0x00, 0x00, 0xff, 0xff, 0xcc, 0x31, + 0xc0, 0xc6, 0x6d, 0x02, 0x00, 0x00, +} + +func (m *Upgrade) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *Upgrade) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *Upgrade) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if m.NextSequenceSend != 0 { + i = encodeVarintUpgrade(dAtA, i, uint64(m.NextSequenceSend)) + i-- + dAtA[i] = 0x18 + } + { + size, err := m.Timeout.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintUpgrade(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x12 + { + size, err := m.Fields.MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintUpgrade(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0xa + return len(dAtA) - i, nil +} + +func (m *UpgradeFields) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *UpgradeFields) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *UpgradeFields) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Version) > 0 { + i -= len(m.Version) + copy(dAtA[i:], m.Version) + i = encodeVarintUpgrade(dAtA, i, uint64(len(m.Version))) + i-- + dAtA[i] = 0x1a + } + if len(m.ConnectionHops) > 0 { + for iNdEx := len(m.ConnectionHops) - 1; iNdEx >= 0; iNdEx-- { + i -= len(m.ConnectionHops[iNdEx]) + copy(dAtA[i:], m.ConnectionHops[iNdEx]) + i = encodeVarintUpgrade(dAtA, i, uint64(len(m.ConnectionHops[iNdEx]))) + i-- + dAtA[i] = 0x12 + } + } + if m.Ordering != 0 { + i = encodeVarintUpgrade(dAtA, i, uint64(m.Ordering)) + i-- + dAtA[i] = 0x8 + } + return len(dAtA) - i, nil +} + +func (m *ErrorReceipt) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *ErrorReceipt) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *ErrorReceipt) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.Message) > 0 { + i -= len(m.Message) + copy(dAtA[i:], m.Message) + i = encodeVarintUpgrade(dAtA, i, uint64(len(m.Message))) + i-- + dAtA[i] = 0x12 + } + if m.Sequence != 0 { + i = encodeVarintUpgrade(dAtA, i, uint64(m.Sequence)) + i-- + dAtA[i] = 0x8 + } + return len(dAtA) - i, nil +} + +func encodeVarintUpgrade(dAtA []byte, offset int, v uint64) int { + offset -= sovUpgrade(v) + base := offset + for v >= 1<<7 { + dAtA[offset] = uint8(v&0x7f | 0x80) + v >>= 7 + offset++ + } + dAtA[offset] = uint8(v) + return base +} +func (m *Upgrade) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = m.Fields.Size() + n += 1 + l + sovUpgrade(uint64(l)) + l = m.Timeout.Size() + n += 1 + l + sovUpgrade(uint64(l)) + if m.NextSequenceSend != 0 { + n += 1 + sovUpgrade(uint64(m.NextSequenceSend)) + } + return n +} + +func (m *UpgradeFields) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.Ordering != 0 { + n += 1 + sovUpgrade(uint64(m.Ordering)) + } + if len(m.ConnectionHops) > 0 { + for _, s := range m.ConnectionHops { + l = len(s) + n += 1 + l + sovUpgrade(uint64(l)) + } + } + l = len(m.Version) + if l > 0 { + n += 1 + l + sovUpgrade(uint64(l)) + } + return n +} + +func (m *ErrorReceipt) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.Sequence != 0 { + n += 1 + sovUpgrade(uint64(m.Sequence)) + } + l = len(m.Message) + if l > 0 { + n += 1 + l + sovUpgrade(uint64(l)) + } + return n +} + +func sovUpgrade(x uint64) (n int) { + return (math_bits.Len64(x|1) + 6) / 7 +} +func sozUpgrade(x uint64) (n int) { + return sovUpgrade(uint64((x << 1) ^ uint64((int64(x) >> 63)))) +} +func (m *Upgrade) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowUpgrade + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: Upgrade: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: Upgrade: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Fields", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowUpgrade + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthUpgrade + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthUpgrade + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.Fields.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Timeout", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowUpgrade + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthUpgrade + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthUpgrade + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + if err := m.Timeout.Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + case 3: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field NextSequenceSend", wireType) + } + m.NextSequenceSend = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowUpgrade + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.NextSequenceSend |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + default: + iNdEx = preIndex + skippy, err := skipUpgrade(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthUpgrade + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *UpgradeFields) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowUpgrade + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: UpgradeFields: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: UpgradeFields: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field Ordering", wireType) + } + m.Ordering = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowUpgrade + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.Ordering |= Order(b&0x7F) << shift + if b < 0x80 { + break + } + } + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field ConnectionHops", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowUpgrade + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthUpgrade + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthUpgrade + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.ConnectionHops = append(m.ConnectionHops, string(dAtA[iNdEx:postIndex])) + iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Version", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowUpgrade + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthUpgrade + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthUpgrade + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Version = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipUpgrade(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthUpgrade + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *ErrorReceipt) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowUpgrade + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: ErrorReceipt: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: ErrorReceipt: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field Sequence", wireType) + } + m.Sequence = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowUpgrade + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.Sequence |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Message", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowUpgrade + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return ErrInvalidLengthUpgrade + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return ErrInvalidLengthUpgrade + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Message = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipUpgrade(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return ErrInvalidLengthUpgrade + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func skipUpgrade(dAtA []byte) (n int, err error) { + l := len(dAtA) + iNdEx := 0 + depth := 0 + for iNdEx < l { + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return 0, ErrIntOverflowUpgrade + } + if iNdEx >= l { + return 0, io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= (uint64(b) & 0x7F) << shift + if b < 0x80 { + break + } + } + wireType := int(wire & 0x7) + switch wireType { + case 0: + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return 0, ErrIntOverflowUpgrade + } + if iNdEx >= l { + return 0, io.ErrUnexpectedEOF + } + iNdEx++ + if dAtA[iNdEx-1] < 0x80 { + break + } + } + case 1: + iNdEx += 8 + case 2: + var length int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return 0, ErrIntOverflowUpgrade + } + if iNdEx >= l { + return 0, io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + length |= (int(b) & 0x7F) << shift + if b < 0x80 { + break + } + } + if length < 0 { + return 0, ErrInvalidLengthUpgrade + } + iNdEx += length + case 3: + depth++ + case 4: + if depth == 0 { + return 0, ErrUnexpectedEndOfGroupUpgrade + } + depth-- + case 5: + iNdEx += 4 + default: + return 0, fmt.Errorf("proto: illegal wireType %d", wireType) + } + if iNdEx < 0 { + return 0, ErrInvalidLengthUpgrade + } + if depth == 0 { + return iNdEx, nil + } + } + return 0, io.ErrUnexpectedEOF +} + +var ( + ErrInvalidLengthUpgrade = fmt.Errorf("proto: negative length found during unmarshaling") + ErrIntOverflowUpgrade = fmt.Errorf("proto: integer overflow") + ErrUnexpectedEndOfGroupUpgrade = fmt.Errorf("proto: unexpected end of group") +) diff --git a/modules/core/04-channel/types/upgrade_test.go b/modules/core/04-channel/types/upgrade_test.go new file mode 100644 index 00000000000..3bf7cf67d54 --- /dev/null +++ b/modules/core/04-channel/types/upgrade_test.go @@ -0,0 +1,215 @@ +package types_test + +import ( + "errors" + + errorsmod "cosmossdk.io/errors" + + clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" + "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" + ibctesting "github.com/cosmos/ibc-go/v8/testing" + "github.com/cosmos/ibc-go/v8/testing/mock" +) + +func (suite *TypesTestSuite) TestUpgradeValidateBasic() { + var upgrade types.Upgrade + + testCases := []struct { + name string + malleate func() + expPass bool + }{ + { + "success", + func() {}, + true, + }, + { + "invalid ordering", + func() { + upgrade.Fields.Ordering = types.NONE + }, + false, + }, + { + "connection hops length not equal to 1", + func() { + upgrade.Fields.ConnectionHops = []string{"connection-0", "connection-1"} + }, + false, + }, + { + "empty version", + func() { + upgrade.Fields.Version = " " + }, + false, + }, + { + "invalid timeout", + func() { + upgrade.Timeout.Height = clienttypes.ZeroHeight() + upgrade.Timeout.Timestamp = 0 + }, + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + upgrade = types.NewUpgrade( + types.NewUpgradeFields(types.ORDERED, []string{ibctesting.FirstConnectionID}, mock.Version), + types.NewTimeout(clienttypes.NewHeight(0, 100), 0), + 0, + ) + + tc.malleate() + + err := upgrade.ValidateBasic() + + if tc.expPass { + suite.Require().NoError(err) + } else { + suite.Require().Error(err) + } + }) + } +} + +func (suite *TypesTestSuite) TestUpgradeErrorIsOf() { + var ( + upgradeError *types.UpgradeError + inputErr error + ) + + testCases := []struct { + msg string + malleate func() + expPass bool + }{ + { + msg: "standard sdk error", + malleate: func() {}, + expPass: true, + }, + { + msg: "input is upgrade error", + malleate: func() { + inputErr = types.NewUpgradeError(1, types.ErrInvalidChannel) + }, + expPass: true, + }, + { + msg: "input has wrapped upgrade error", + malleate: func() { + wrappedErr := errorsmod.Wrap(types.ErrInvalidChannel, "wrapped upgrade error") + inputErr = types.NewUpgradeError(1, wrappedErr) + }, + expPass: true, + }, + { + msg: "not equal to nil error", + malleate: func() { + upgradeError = &types.UpgradeError{} + }, + expPass: false, + }, + { + msg: "wrapped upgrade error", + malleate: func() { + wrappedErr := errorsmod.Wrap(upgradeError, "wrapped upgrade error") + upgradeError = types.NewUpgradeError(1, wrappedErr) + }, + expPass: true, + }, + { + msg: "empty upgrade and non nil target", + malleate: func() { + upgradeError = &types.UpgradeError{} + }, + expPass: false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.msg, func() { + upgradeError = types.NewUpgradeError(1, types.ErrInvalidChannel) + inputErr = types.ErrInvalidChannel + + tc.malleate() + + res := errorsmod.IsOf(upgradeError, inputErr) + suite.Require().Equal(tc.expPass, res) + }) + } +} + +// TestGetErrorReceipt tests that the error receipt message is the same for both wrapped and unwrapped errors. +func (suite *TypesTestSuite) TestGetErrorReceipt() { + upgradeError := types.NewUpgradeError(1, types.ErrInvalidChannel) + + wrappedErr := errorsmod.Wrap(upgradeError, "wrapped upgrade error") + suite.Require().True(errorsmod.IsOf(wrappedErr, types.ErrInvalidChannel)) + + upgradeError2 := types.NewUpgradeError(1, wrappedErr) + + suite.Require().Equal(upgradeError2.GetErrorReceipt().Message, upgradeError.GetErrorReceipt().Message) +} + +// TestUpgradeErrorUnwrap tests that the underlying error is not modified when Unwrap is called. +func (suite *TypesTestSuite) TestUpgradeErrorUnwrap() { + baseUnderlyingError := errorsmod.Wrap(types.ErrInvalidChannel, "base error") + wrappedErr := errorsmod.Wrap(baseUnderlyingError, "wrapped error") + upgradeError := types.NewUpgradeError(1, wrappedErr) + + originalUpgradeError := upgradeError.Error() + unWrapped := errors.Unwrap(upgradeError) + postUnwrapUpgradeError := upgradeError.Error() + + suite.Require().Equal(types.ErrInvalidChannel, unWrapped, "unwrapped error was not equal to base underlying error") + suite.Require().Equal(originalUpgradeError, postUnwrapUpgradeError, "original error was modified when unwrapped") +} + +func (suite *TypesTestSuite) TestIsUpgradeError() { + var err error + + testCases := []struct { + msg string + malleate func() + expPass bool + }{ + { + "true", + func() {}, + true, + }, + { + "false with non upgrade error", + func() { + err = errors.New("error") + }, + false, + }, + { + "false with nil error", + func() { + err = nil + }, + false, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.msg, func() { + err = types.NewUpgradeError(1, types.ErrInvalidChannel) + + tc.malleate() + + res := types.IsUpgradeError(err) + suite.Require().Equal(tc.expPass, res) + }) + } +} diff --git a/modules/core/05-port/types/module.go b/modules/core/05-port/types/module.go index a72ff9658ec..a5c6386f926 100644 --- a/modules/core/05-port/types/module.go +++ b/modules/core/05-port/types/module.go @@ -106,6 +106,52 @@ type IBCModule interface { ) error } +// UpgradableModule defines the callbacks required to perform a channel upgrade. +type UpgradableModule interface { + // OnChanUpgradeInit initializes the channel upgrade handshake. + OnChanUpgradeInit( + ctx sdk.Context, + portID, channelID string, + order channeltypes.Order, + connectionHops []string, + version string, + ) (string, error) + + // OnChanUpgradeTry verifies the counterparty upgrade and sets the upgrade on TRY chain + OnChanUpgradeTry( + ctx sdk.Context, + portID, channelID string, + order channeltypes.Order, + connectionHops []string, + counterpartyVersion string, + ) (string, error) + + // OnChanUpgradeAck TODO + OnChanUpgradeAck( + ctx sdk.Context, + portID, + channelID, + counterpartyVersion string, + ) error + + // OnChanUpgradeOpen TODO + OnChanUpgradeOpen( + ctx sdk.Context, + portID, + channelID string, + order channeltypes.Order, + connectionHops []string, + version string, + ) + + // OnChanUpgradeRestore TODO + OnChanUpgradeRestore( + ctx sdk.Context, + portID, + channelID string, + ) +} + // ICS4Wrapper implements the ICS4 interfaces that IBC applications use to send packets and acknowledgements. type ICS4Wrapper interface { SendPacket( diff --git a/modules/core/24-host/channel_keys.go b/modules/core/24-host/channel_keys.go new file mode 100644 index 00000000000..b21666dd3b6 --- /dev/null +++ b/modules/core/24-host/channel_keys.go @@ -0,0 +1,66 @@ +package host + +import "fmt" + +const ( + KeyChannelEndPrefix = "channelEnds" + KeyChannelPrefix = "channels" + KeyChannelUpgradePrefix = "channelUpgrades" + KeyUpgradePrefix = "upgrades" + KeyUpgradeErrorPrefix = "upgradeError" + KeyCounterpartyUpgrade = "counterpartyUpgrade" + KeyChannelCapabilityPrefix = "capabilities" +) + +// ICS04 +// The following paths are the keys to the store as defined in https://github.com/cosmos/ibc/tree/master/spec/core/ics-004-channel-and-packet-semantics#store-paths + +// ChannelPath defines the path under which channels are stored +func ChannelPath(portID, channelID string) string { + return fmt.Sprintf("%s/%s", KeyChannelEndPrefix, channelPath(portID, channelID)) +} + +// ChannelKey returns the store key for a particular channel +func ChannelKey(portID, channelID string) []byte { + return []byte(ChannelPath(portID, channelID)) +} + +// ChannelCapabilityPath defines the path under which capability keys associated +// with a channel are stored +func ChannelCapabilityPath(portID, channelID string) string { + return fmt.Sprintf("%s/%s", KeyChannelCapabilityPrefix, channelPath(portID, channelID)) +} + +// ChannelUpgradeErrorPath defines the path under which the ErrorReceipt is stored in the case that a chain does not accept the proposed upgrade +func ChannelUpgradeErrorPath(portID, channelID string) string { + return fmt.Sprintf("%s/%s/%s", KeyChannelUpgradePrefix, KeyUpgradeErrorPrefix, channelPath(portID, channelID)) +} + +// ChannelUpgradeErrorKey returns the store key for a particular channelEnd used to stor the ErrorReceipt in the case that a chain does not accept the proposed upgrade +func ChannelUpgradeErrorKey(portID, channelID string) []byte { + return []byte(ChannelUpgradeErrorPath(portID, channelID)) +} + +// ChannelUpgradePath defines the path which stores the information related to an upgrade attempt +func ChannelUpgradePath(portID, channelID string) string { + return fmt.Sprintf("%s/%s/%s", KeyChannelUpgradePrefix, KeyUpgradePrefix, channelPath(portID, channelID)) +} + +// ChannelUpgradeKey returns the store key for a particular channel upgrade attempt +func ChannelUpgradeKey(portID, channelID string) []byte { + return []byte(ChannelUpgradePath(portID, channelID)) +} + +// ChannelCounterpartyUpgradeKey returns the store key for the upgrade used on the counterparty channel. +func ChannelCounterpartyUpgradeKey(portID, channelID string) []byte { + return []byte(ChannelCounterpartyUpgradePath(portID, channelID)) +} + +// ChannelCounterpartyUpgradePath defines the path under which the upgrade used on the counterparty channel is stored. +func ChannelCounterpartyUpgradePath(portID, channelID string) string { + return fmt.Sprintf("%s/%s/%s", KeyChannelUpgradePrefix, KeyCounterpartyUpgrade, channelPath(portID, channelID)) +} + +func channelPath(portID, channelID string) string { + return fmt.Sprintf("%s/%s/%s/%s", KeyPortPrefix, portID, KeyChannelPrefix, channelID) +} diff --git a/modules/core/24-host/client_keys.go b/modules/core/24-host/client_keys.go new file mode 100644 index 00000000000..4b12bc63e5a --- /dev/null +++ b/modules/core/24-host/client_keys.go @@ -0,0 +1,86 @@ +package host + +import ( + "fmt" + + "github.com/cosmos/ibc-go/v8/modules/core/exported" +) + +// KeyClientStorePrefix defines the KVStore key prefix for IBC clients +var KeyClientStorePrefix = []byte("clients") + +const ( + KeyClientState = "clientState" + KeyConsensusStatePrefix = "consensusStates" +) + +// FullClientPath returns the full path of a specific client path in the format: +// "clients/{clientID}/{path}" as a string. +func FullClientPath(clientID string, path string) string { + return fmt.Sprintf("%s/%s/%s", KeyClientStorePrefix, clientID, path) +} + +// FullClientKey returns the full path of specific client path in the format: +// "clients/{clientID}/{path}" as a byte array. +func FullClientKey(clientID string, path []byte) []byte { + return []byte(FullClientPath(clientID, string(path))) +} + +// PrefixedClientStorePath returns a key path which can be used for prefixed +// key store iteration. The prefix may be a clientType, clientID, or any +// valid key prefix which may be concatenated with the client store constant. +func PrefixedClientStorePath(prefix []byte) string { + return fmt.Sprintf("%s/%s", KeyClientStorePrefix, prefix) +} + +// PrefixedClientStoreKey returns a key which can be used for prefixed +// key store iteration. The prefix may be a clientType, clientID, or any +// valid key prefix which may be concatenated with the client store constant. +func PrefixedClientStoreKey(prefix []byte) []byte { + return []byte(PrefixedClientStorePath(prefix)) +} + +// ICS02 +// The following paths are the keys to the store as defined in https://github.com/cosmos/ibc/tree/master/spec/core/ics-002-client-semantics#path-space + +// FullClientStatePath takes a client identifier and returns a Path under which to store a +// particular client state +func FullClientStatePath(clientID string) string { + return FullClientPath(clientID, KeyClientState) +} + +// FullClientStateKey takes a client identifier and returns a Key under which to store a +// particular client state. +func FullClientStateKey(clientID string) []byte { + return FullClientKey(clientID, []byte(KeyClientState)) +} + +// ClientStateKey returns a store key under which a particular client state is stored +// in a client prefixed store +func ClientStateKey() []byte { + return []byte(KeyClientState) +} + +// FullConsensusStatePath takes a client identifier and returns a Path under which to +// store the consensus state of a client. +func FullConsensusStatePath(clientID string, height exported.Height) string { + return FullClientPath(clientID, ConsensusStatePath(height)) +} + +// FullConsensusStateKey returns the store key for the consensus state of a particular +// client. +func FullConsensusStateKey(clientID string, height exported.Height) []byte { + return []byte(FullConsensusStatePath(clientID, height)) +} + +// ConsensusStatePath returns the suffix store key for the consensus state at a +// particular height stored in a client prefixed store. +func ConsensusStatePath(height exported.Height) string { + return fmt.Sprintf("%s/%s", KeyConsensusStatePrefix, height) +} + +// ConsensusStateKey returns the store key for a the consensus state of a particular +// client stored in a client prefixed store. +func ConsensusStateKey(height exported.Height) []byte { + return []byte(ConsensusStatePath(height)) +} diff --git a/modules/core/24-host/connection_keys.go b/modules/core/24-host/connection_keys.go new file mode 100644 index 00000000000..fde9ee3b730 --- /dev/null +++ b/modules/core/24-host/connection_keys.go @@ -0,0 +1,28 @@ +package host + +import "fmt" + +const KeyConnectionPrefix = "connections" + +// ICS03 +// The following paths are the keys to the store as defined in https://github.com/cosmos/ibc/blob/master/spec/core/ics-003-connection-semantics#store-paths + +// ClientConnectionsPath defines a reverse mapping from clients to a set of connections +func ClientConnectionsPath(clientID string) string { + return FullClientPath(clientID, KeyConnectionPrefix) +} + +// ClientConnectionsKey returns the store key for the connections of a given client +func ClientConnectionsKey(clientID string) []byte { + return []byte(ClientConnectionsPath(clientID)) +} + +// ConnectionPath defines the path under which connection paths are stored +func ConnectionPath(connectionID string) string { + return fmt.Sprintf("%s/%s", KeyConnectionPrefix, connectionID) +} + +// ConnectionKey returns the store key for a particular connection +func ConnectionKey(connectionID string) []byte { + return []byte(ConnectionPath(connectionID)) +} diff --git a/modules/core/24-host/keys.go b/modules/core/24-host/keys.go deleted file mode 100644 index 9e018f8f0d8..00000000000 --- a/modules/core/24-host/keys.go +++ /dev/null @@ -1,235 +0,0 @@ -package host - -import ( - "fmt" - - "github.com/cosmos/ibc-go/v8/modules/core/exported" -) - -// KVStore key prefixes for IBC -var ( - KeyClientStorePrefix = []byte("clients") -) - -// KVStore key prefixes for IBC -const ( - KeyClientState = "clientState" - KeyConsensusStatePrefix = "consensusStates" - KeyConnectionPrefix = "connections" - KeyChannelEndPrefix = "channelEnds" - KeyChannelPrefix = "channels" - KeyPortPrefix = "ports" - KeySequencePrefix = "sequences" - KeyChannelCapabilityPrefix = "capabilities" - KeyNextSeqSendPrefix = "nextSequenceSend" - KeyNextSeqRecvPrefix = "nextSequenceRecv" - KeyNextSeqAckPrefix = "nextSequenceAck" - KeyPacketCommitmentPrefix = "commitments" - KeyPacketAckPrefix = "acks" - KeyPacketReceiptPrefix = "receipts" -) - -// FullClientPath returns the full path of a specific client path in the format: -// "clients/{clientID}/{path}" as a string. -func FullClientPath(clientID string, path string) string { - return fmt.Sprintf("%s/%s/%s", KeyClientStorePrefix, clientID, path) -} - -// FullClientKey returns the full path of specific client path in the format: -// "clients/{clientID}/{path}" as a byte array. -func FullClientKey(clientID string, path []byte) []byte { - return []byte(FullClientPath(clientID, string(path))) -} - -// PrefixedClientStorePath returns a key path which can be used for prefixed -// key store iteration. The prefix may be a clientType, clientID, or any -// valid key prefix which may be concatenated with the client store constant. -func PrefixedClientStorePath(prefix []byte) string { - return fmt.Sprintf("%s/%s", KeyClientStorePrefix, prefix) -} - -// PrefixedClientStoreKey returns a key which can be used for prefixed -// key store iteration. The prefix may be a clientType, clientID, or any -// valid key prefix which may be concatenated with the client store constant. -func PrefixedClientStoreKey(prefix []byte) []byte { - return []byte(PrefixedClientStorePath(prefix)) -} - -// ICS02 -// The following paths are the keys to the store as defined in https://github.com/cosmos/ibc/tree/master/spec/core/ics-002-client-semantics#path-space - -// FullClientStatePath takes a client identifier and returns a Path under which to store a -// particular client state -func FullClientStatePath(clientID string) string { - return FullClientPath(clientID, KeyClientState) -} - -// FullClientStateKey takes a client identifier and returns a Key under which to store a -// particular client state. -func FullClientStateKey(clientID string) []byte { - return FullClientKey(clientID, []byte(KeyClientState)) -} - -// ClientStateKey returns a store key under which a particular client state is stored -// in a client prefixed store -func ClientStateKey() []byte { - return []byte(KeyClientState) -} - -// FullConsensusStatePath takes a client identifier and returns a Path under which to -// store the consensus state of a client. -func FullConsensusStatePath(clientID string, height exported.Height) string { - return FullClientPath(clientID, ConsensusStatePath(height)) -} - -// FullConsensusStateKey returns the store key for the consensus state of a particular -// client. -func FullConsensusStateKey(clientID string, height exported.Height) []byte { - return []byte(FullConsensusStatePath(clientID, height)) -} - -// ConsensusStatePath returns the suffix store key for the consensus state at a -// particular height stored in a client prefixed store. -func ConsensusStatePath(height exported.Height) string { - return fmt.Sprintf("%s/%s", KeyConsensusStatePrefix, height) -} - -// ConsensusStateKey returns the store key for a the consensus state of a particular -// client stored in a client prefixed store. -func ConsensusStateKey(height exported.Height) []byte { - return []byte(ConsensusStatePath(height)) -} - -// ICS03 -// The following paths are the keys to the store as defined in https://github.com/cosmos/ibc/blob/master/spec/core/ics-003-connection-semantics#store-paths - -// ClientConnectionsPath defines a reverse mapping from clients to a set of connections -func ClientConnectionsPath(clientID string) string { - return FullClientPath(clientID, KeyConnectionPrefix) -} - -// ClientConnectionsKey returns the store key for the connections of a given client -func ClientConnectionsKey(clientID string) []byte { - return []byte(ClientConnectionsPath(clientID)) -} - -// ConnectionPath defines the path under which connection paths are stored -func ConnectionPath(connectionID string) string { - return fmt.Sprintf("%s/%s", KeyConnectionPrefix, connectionID) -} - -// ConnectionKey returns the store key for a particular connection -func ConnectionKey(connectionID string) []byte { - return []byte(ConnectionPath(connectionID)) -} - -// ICS04 -// The following paths are the keys to the store as defined in https://github.com/cosmos/ibc/tree/master/spec/core/ics-004-channel-and-packet-semantics#store-paths - -// ChannelPath defines the path under which channels are stored -func ChannelPath(portID, channelID string) string { - return fmt.Sprintf("%s/%s", KeyChannelEndPrefix, channelPath(portID, channelID)) -} - -// ChannelKey returns the store key for a particular channel -func ChannelKey(portID, channelID string) []byte { - return []byte(ChannelPath(portID, channelID)) -} - -// ChannelCapabilityPath defines the path under which capability keys associated -// with a channel are stored -func ChannelCapabilityPath(portID, channelID string) string { - return fmt.Sprintf("%s/%s", KeyChannelCapabilityPrefix, channelPath(portID, channelID)) -} - -// NextSequenceSendPath defines the next send sequence counter store path -func NextSequenceSendPath(portID, channelID string) string { - return fmt.Sprintf("%s/%s", KeyNextSeqSendPrefix, channelPath(portID, channelID)) -} - -// NextSequenceSendKey returns the store key for the send sequence of a particular -// channel binded to a specific port. -func NextSequenceSendKey(portID, channelID string) []byte { - return []byte(NextSequenceSendPath(portID, channelID)) -} - -// NextSequenceRecvPath defines the next receive sequence counter store path. -func NextSequenceRecvPath(portID, channelID string) string { - return fmt.Sprintf("%s/%s", KeyNextSeqRecvPrefix, channelPath(portID, channelID)) -} - -// NextSequenceRecvKey returns the store key for the receive sequence of a particular -// channel binded to a specific port -func NextSequenceRecvKey(portID, channelID string) []byte { - return []byte(NextSequenceRecvPath(portID, channelID)) -} - -// NextSequenceAckPath defines the next acknowledgement sequence counter store path -func NextSequenceAckPath(portID, channelID string) string { - return fmt.Sprintf("%s/%s", KeyNextSeqAckPrefix, channelPath(portID, channelID)) -} - -// NextSequenceAckKey returns the store key for the acknowledgement sequence of -// a particular channel binded to a specific port. -func NextSequenceAckKey(portID, channelID string) []byte { - return []byte(NextSequenceAckPath(portID, channelID)) -} - -// PacketCommitmentPath defines the commitments to packet data fields store path -func PacketCommitmentPath(portID, channelID string, sequence uint64) string { - return fmt.Sprintf("%s/%d", PacketCommitmentPrefixPath(portID, channelID), sequence) -} - -// PacketCommitmentKey returns the store key of under which a packet commitment -// is stored -func PacketCommitmentKey(portID, channelID string, sequence uint64) []byte { - return []byte(PacketCommitmentPath(portID, channelID, sequence)) -} - -// PacketCommitmentPrefixPath defines the prefix for commitments to packet data fields store path. -func PacketCommitmentPrefixPath(portID, channelID string) string { - return fmt.Sprintf("%s/%s/%s", KeyPacketCommitmentPrefix, channelPath(portID, channelID), KeySequencePrefix) -} - -// PacketAcknowledgementPath defines the packet acknowledgement store path -func PacketAcknowledgementPath(portID, channelID string, sequence uint64) string { - return fmt.Sprintf("%s/%d", PacketAcknowledgementPrefixPath(portID, channelID), sequence) -} - -// PacketAcknowledgementKey returns the store key of under which a packet -// acknowledgement is stored -func PacketAcknowledgementKey(portID, channelID string, sequence uint64) []byte { - return []byte(PacketAcknowledgementPath(portID, channelID, sequence)) -} - -// PacketAcknowledgementPrefixPath defines the prefix for commitments to packet data fields store path. -func PacketAcknowledgementPrefixPath(portID, channelID string) string { - return fmt.Sprintf("%s/%s/%s", KeyPacketAckPrefix, channelPath(portID, channelID), KeySequencePrefix) -} - -// PacketReceiptPath defines the packet receipt store path -func PacketReceiptPath(portID, channelID string, sequence uint64) string { - return fmt.Sprintf("%s/%s/%s", KeyPacketReceiptPrefix, channelPath(portID, channelID), sequencePath(sequence)) -} - -// PacketReceiptKey returns the store key of under which a packet -// receipt is stored -func PacketReceiptKey(portID, channelID string, sequence uint64) []byte { - return []byte(PacketReceiptPath(portID, channelID, sequence)) -} - -func channelPath(portID, channelID string) string { - return fmt.Sprintf("%s/%s/%s/%s", KeyPortPrefix, portID, KeyChannelPrefix, channelID) -} - -func sequencePath(sequence uint64) string { - return fmt.Sprintf("%s/%d", KeySequencePrefix, sequence) -} - -// ICS05 -// The following paths are the keys to the store as defined in https://github.com/cosmos/ibc/tree/master/spec/core/ics-005-port-allocation#store-paths - -// PortPath defines the path under which ports paths are stored on the capability module -func PortPath(portID string) string { - return fmt.Sprintf("%s/%s", KeyPortPrefix, portID) -} diff --git a/modules/core/24-host/packet_keys.go b/modules/core/24-host/packet_keys.go new file mode 100644 index 00000000000..75730e57d73 --- /dev/null +++ b/modules/core/24-host/packet_keys.go @@ -0,0 +1,118 @@ +package host + +import "fmt" + +const ( + KeySequencePrefix = "sequences" + KeyNextSeqSendPrefix = "nextSequenceSend" + KeyNextSeqRecvPrefix = "nextSequenceRecv" + KeyNextSeqAckPrefix = "nextSequenceAck" + KeyPacketCommitmentPrefix = "commitments" + KeyPacketAckPrefix = "acks" + KeyPacketReceiptPrefix = "receipts" + KeyPruningSequenceStart = "pruningSequenceStart" + KeyPruningSequenceEnd = "pruningSequenceEnd" +) + +// ICS04 +// The following paths are the keys to the store as defined in https://github.com/cosmos/ibc/tree/master/spec/core/ics-004-channel-and-packet-semantics#store-paths + +// NextSequenceSendPath defines the next send sequence counter store path +func NextSequenceSendPath(portID, channelID string) string { + return fmt.Sprintf("%s/%s", KeyNextSeqSendPrefix, channelPath(portID, channelID)) +} + +// NextSequenceSendKey returns the store key for the send sequence of a particular +// channel binded to a specific port. +func NextSequenceSendKey(portID, channelID string) []byte { + return []byte(NextSequenceSendPath(portID, channelID)) +} + +// NextSequenceRecvPath defines the next receive sequence counter store path. +func NextSequenceRecvPath(portID, channelID string) string { + return fmt.Sprintf("%s/%s", KeyNextSeqRecvPrefix, channelPath(portID, channelID)) +} + +// NextSequenceRecvKey returns the store key for the receive sequence of a particular +// channel binded to a specific port +func NextSequenceRecvKey(portID, channelID string) []byte { + return []byte(NextSequenceRecvPath(portID, channelID)) +} + +// NextSequenceAckPath defines the next acknowledgement sequence counter store path +func NextSequenceAckPath(portID, channelID string) string { + return fmt.Sprintf("%s/%s", KeyNextSeqAckPrefix, channelPath(portID, channelID)) +} + +// NextSequenceAckKey returns the store key for the acknowledgement sequence of +// a particular channel binded to a specific port. +func NextSequenceAckKey(portID, channelID string) []byte { + return []byte(NextSequenceAckPath(portID, channelID)) +} + +// PacketCommitmentPath defines the commitments to packet data fields store path +func PacketCommitmentPath(portID, channelID string, sequence uint64) string { + return fmt.Sprintf("%s/%d", PacketCommitmentPrefixPath(portID, channelID), sequence) +} + +// PacketCommitmentKey returns the store key of under which a packet commitment +// is stored +func PacketCommitmentKey(portID, channelID string, sequence uint64) []byte { + return []byte(PacketCommitmentPath(portID, channelID, sequence)) +} + +// PacketCommitmentPrefixPath defines the prefix for commitments to packet data fields store path. +func PacketCommitmentPrefixPath(portID, channelID string) string { + return fmt.Sprintf("%s/%s/%s", KeyPacketCommitmentPrefix, channelPath(portID, channelID), KeySequencePrefix) +} + +// PacketAcknowledgementPath defines the packet acknowledgement store path +func PacketAcknowledgementPath(portID, channelID string, sequence uint64) string { + return fmt.Sprintf("%s/%d", PacketAcknowledgementPrefixPath(portID, channelID), sequence) +} + +// PacketAcknowledgementKey returns the store key of under which a packet +// acknowledgement is stored +func PacketAcknowledgementKey(portID, channelID string, sequence uint64) []byte { + return []byte(PacketAcknowledgementPath(portID, channelID, sequence)) +} + +// PacketAcknowledgementPrefixPath defines the prefix for commitments to packet data fields store path. +func PacketAcknowledgementPrefixPath(portID, channelID string) string { + return fmt.Sprintf("%s/%s/%s", KeyPacketAckPrefix, channelPath(portID, channelID), KeySequencePrefix) +} + +// PacketReceiptPath defines the packet receipt store path +func PacketReceiptPath(portID, channelID string, sequence uint64) string { + return fmt.Sprintf("%s/%s/%s", KeyPacketReceiptPrefix, channelPath(portID, channelID), sequencePath(sequence)) +} + +// PacketReceiptKey returns the store key of under which a packet +// receipt is stored +func PacketReceiptKey(portID, channelID string, sequence uint64) []byte { + return []byte(PacketReceiptPath(portID, channelID, sequence)) +} + +// PruningSequenceStartPath defines the path under which the pruning sequence starting value is stored +func PruningSequenceStartPath(portID, channelID string) string { + return fmt.Sprintf("%s/%s", KeyPruningSequenceStart, channelPath(portID, channelID)) +} + +// PruningSequenceStartKey returns the store key for the pruning sequence start of a particular channel +func PruningSequenceStartKey(portID, channelID string) []byte { + return []byte(PruningSequenceStartPath(portID, channelID)) +} + +// PruningSequenceEndPath defines the path under which the pruning sequence end is stored +func PruningSequenceEndPath(portID, channelID string) string { + return fmt.Sprintf("%s/%s", KeyPruningSequenceEnd, channelPath(portID, channelID)) +} + +// PruningSequenceEndKey returns the store key for the pruning sequence end of a particular channel +func PruningSequenceEndKey(portID, channelID string) []byte { + return []byte(PruningSequenceEndPath(portID, channelID)) +} + +func sequencePath(sequence uint64) string { + return fmt.Sprintf("%s/%d", KeySequencePrefix, sequence) +} diff --git a/modules/core/24-host/port_keys.go b/modules/core/24-host/port_keys.go new file mode 100644 index 00000000000..9bd720065c2 --- /dev/null +++ b/modules/core/24-host/port_keys.go @@ -0,0 +1,15 @@ +package host + +import "fmt" + +const ( + KeyPortPrefix = "ports" +) + +// ICS05 +// The following paths are the keys to the store as defined in https://github.com/cosmos/ibc/tree/master/spec/core/ics-005-port-allocation#store-paths + +// PortPath defines the path under which ports paths are stored on the capability module +func PortPath(portID string) string { + return fmt.Sprintf("%s/%s", KeyPortPrefix, portID) +} diff --git a/modules/core/ante/ante_test.go b/modules/core/ante/ante_test.go index 1b9a8c15c64..734d71cc290 100644 --- a/modules/core/ante/ante_test.go +++ b/modules/core/ante/ante_test.go @@ -147,7 +147,7 @@ func (suite *AnteTestSuite) createTimeoutOnCloseMessage(isRedundant bool) sdk.Ms channelKey := host.ChannelKey(packet.GetDestPort(), packet.GetDestChannel()) proofClosed, _ := suite.chainA.QueryProof(channelKey) - return channeltypes.NewMsgTimeoutOnClose(packet, 1, proof, proofClosed, proofHeight, suite.path.EndpointA.Chain.SenderAccount.GetAddress().String()) + return channeltypes.NewMsgTimeoutOnClose(packet, 1, proof, proofClosed, proofHeight, suite.path.EndpointA.Chain.SenderAccount.GetAddress().String(), 0) } func (suite *AnteTestSuite) createUpdateClientMessage() sdk.Msg { diff --git a/modules/core/genesis_test.go b/modules/core/genesis_test.go index 3f6515573c7..be1eb909678 100644 --- a/modules/core/genesis_test.go +++ b/modules/core/genesis_test.go @@ -142,6 +142,7 @@ func (suite *IBCTestSuite) TestValidateGenesis() { channeltypes.NewPacketSequence(port2, channel2, 1), }, 0, + channeltypes.Params{UpgradeTimeout: channeltypes.DefaultTimeout}, ), }, expPass: true, @@ -300,6 +301,7 @@ func (suite *IBCTestSuite) TestInitGenesis() { channeltypes.NewPacketSequence(port2, channel2, 1), }, 0, + channeltypes.Params{UpgradeTimeout: channeltypes.DefaultTimeout}, ), }, }, diff --git a/modules/core/keeper/grpc_query.go b/modules/core/keeper/grpc_query.go index bfdce2c6015..59807638af0 100644 --- a/modules/core/keeper/grpc_query.go +++ b/modules/core/keeper/grpc_query.go @@ -152,3 +152,18 @@ func (k Keeper) NextSequenceReceive(c context.Context, req *channeltypes.QueryNe func (k Keeper) NextSequenceSend(c context.Context, req *channeltypes.QueryNextSequenceSendRequest) (*channeltypes.QueryNextSequenceSendResponse, error) { return k.ChannelKeeper.NextSequenceSend(c, req) } + +// UpgradeError implements the IBC QueryServer interface +func (k Keeper) UpgradeError(c context.Context, req *channeltypes.QueryUpgradeErrorRequest) (*channeltypes.QueryUpgradeErrorResponse, error) { + return k.ChannelKeeper.UpgradeErrorReceipt(c, req) +} + +// Upgrade implements the IBC QueryServer interface +func (k Keeper) Upgrade(c context.Context, req *channeltypes.QueryUpgradeRequest) (*channeltypes.QueryUpgradeResponse, error) { + return k.ChannelKeeper.Upgrade(c, req) +} + +// ChannelParams implements the IBC QueryServer interface +func (k Keeper) ChannelParams(c context.Context, req *channeltypes.QueryChannelParamsRequest) (*channeltypes.QueryChannelParamsResponse, error) { + return k.ChannelKeeper.ChannelParams(c, req) +} diff --git a/modules/core/keeper/msg_server.go b/modules/core/keeper/msg_server.go index 29aa15071e5..65ffc528f0b 100644 --- a/modules/core/keeper/msg_server.go +++ b/modules/core/keeper/msg_server.go @@ -12,6 +12,7 @@ import ( clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" + "github.com/cosmos/ibc-go/v8/modules/core/04-channel/keeper" channeltypes "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" porttypes "github.com/cosmos/ibc-go/v8/modules/core/05-port/types" ibcerrors "github.com/cosmos/ibc-go/v8/modules/core/errors" @@ -431,7 +432,7 @@ func (k Keeper) ChannelCloseConfirm(goCtx context.Context, msg *channeltypes.Msg return nil, errorsmod.Wrapf(err, "channel close confirm callback failed for port ID: %s, channel ID: %s", msg.PortId, msg.ChannelId) } - err = k.ChannelKeeper.ChanCloseConfirm(ctx, msg.PortId, msg.ChannelId, capability, msg.ProofInit, msg.ProofHeight) + err = k.ChannelKeeper.ChanCloseConfirm(ctx, msg.PortId, msg.ChannelId, capability, msg.ProofInit, msg.ProofHeight, msg.CounterpartyUpgradeSequence) if err != nil { ctx.Logger().Error("channel close confirm failed", "port-id", msg.PortId, "channel-id", msg.ChannelId, "error", err.Error()) return nil, errorsmod.Wrap(err, "channel handshake close confirm failed") @@ -621,7 +622,7 @@ func (k Keeper) TimeoutOnClose(goCtx context.Context, msg *channeltypes.MsgTimeo // If the timeout was already received, perform a no-op // Use a cached context to prevent accidental state changes cacheCtx, writeFn := ctx.CacheContext() - err = k.ChannelKeeper.TimeoutOnClose(cacheCtx, capability, msg.Packet, msg.ProofUnreceived, msg.ProofClose, msg.ProofHeight, msg.NextSequenceRecv) + err = k.ChannelKeeper.TimeoutOnClose(cacheCtx, capability, msg.Packet, msg.ProofUnreceived, msg.ProofClose, msg.ProofHeight, msg.NextSequenceRecv, msg.CounterpartyUpgradeSequence) switch err { case nil: @@ -733,6 +734,381 @@ func (k Keeper) Acknowledgement(goCtx context.Context, msg *channeltypes.MsgAckn return &channeltypes.MsgAcknowledgementResponse{Result: channeltypes.SUCCESS}, nil } +// ChannelUpgradeInit defines a rpc handler method for MsgChannelUpgradeInit. +func (k Keeper) ChannelUpgradeInit(goCtx context.Context, msg *channeltypes.MsgChannelUpgradeInit) (*channeltypes.MsgChannelUpgradeInitResponse, error) { + ctx := sdk.UnwrapSDKContext(goCtx) + + if k.GetAuthority() != msg.Signer { + return nil, errorsmod.Wrapf(ibcerrors.ErrUnauthorized, "expected %s, got %s", k.GetAuthority(), msg.Signer) + } + + module, _, err := k.ChannelKeeper.LookupModuleByChannel(ctx, msg.PortId, msg.ChannelId) + if err != nil { + ctx.Logger().Error("channel upgrade init failed", "port-id", msg.PortId, "error", errorsmod.Wrap(err, "could not retrieve module from port-id")) + return nil, errorsmod.Wrap(err, "could not retrieve module from port-id") + } + + app, ok := k.Router.GetRoute(module) + if !ok { + ctx.Logger().Error("channel upgrade init failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module) + } + + cbs, ok := app.(porttypes.UpgradableModule) + if !ok { + ctx.Logger().Error("channel upgrade init failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module) + } + + upgrade, err := k.ChannelKeeper.ChanUpgradeInit(ctx, msg.PortId, msg.ChannelId, msg.Fields) + if err != nil { + ctx.Logger().Error("channel upgrade init failed", "error", errorsmod.Wrap(err, "channel upgrade init failed")) + return nil, errorsmod.Wrap(err, "channel upgrade init failed") + } + + upgradeVersion, err := cbs.OnChanUpgradeInit( + ctx, + msg.PortId, + msg.ChannelId, + upgrade.Fields.Ordering, + upgrade.Fields.ConnectionHops, + upgrade.Fields.Version, + ) + if err != nil { + ctx.Logger().Error("channel upgrade init callback failed", "port-id", msg.PortId, "channel-id", msg.ChannelId, "error", err.Error()) + return nil, errorsmod.Wrapf(err, "channel upgrade init callback failed for port ID: %s, channel ID: %s", msg.PortId, msg.ChannelId) + } + + channel, upgrade := k.ChannelKeeper.WriteUpgradeInitChannel(ctx, msg.PortId, msg.ChannelId, upgrade, upgradeVersion) + + ctx.Logger().Info("channel upgrade init succeeded", "channel-id", msg.ChannelId, "version", upgradeVersion) + keeper.EmitChannelUpgradeInitEvent(ctx, msg.PortId, msg.ChannelId, channel, upgrade) + + return &channeltypes.MsgChannelUpgradeInitResponse{ + Upgrade: upgrade, + UpgradeSequence: channel.UpgradeSequence, + }, nil +} + +// ChannelUpgradeTry defines a rpc handler method for MsgChannelUpgradeTry. +func (k Keeper) ChannelUpgradeTry(goCtx context.Context, msg *channeltypes.MsgChannelUpgradeTry) (*channeltypes.MsgChannelUpgradeTryResponse, error) { + ctx := sdk.UnwrapSDKContext(goCtx) + + module, _, err := k.ChannelKeeper.LookupModuleByChannel(ctx, msg.PortId, msg.ChannelId) + if err != nil { + ctx.Logger().Error("channel upgrade try failed", "port-id", msg.PortId, "error", errorsmod.Wrap(err, "could not retrieve module from port-id")) + return nil, errorsmod.Wrap(err, "could not retrieve module from port-id") + } + + app, ok := k.Router.GetRoute(module) + if !ok { + ctx.Logger().Error("channel upgrade try failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module) + } + + cbs, ok := app.(porttypes.UpgradableModule) + if !ok { + ctx.Logger().Error("channel upgrade try failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module) + } + + channel, upgrade, err := k.ChannelKeeper.ChanUpgradeTry(ctx, msg.PortId, msg.ChannelId, msg.ProposedUpgradeConnectionHops, msg.CounterpartyUpgradeFields, msg.CounterpartyUpgradeSequence, msg.ProofChannel, msg.ProofUpgrade, msg.ProofHeight) + if err != nil { + ctx.Logger().Error("channel upgrade try failed", "error", errorsmod.Wrap(err, "channel upgrade try failed")) + if channeltypes.IsUpgradeError(err) { + k.ChannelKeeper.SetUpgradeErrorReceipt(ctx, msg.PortId, msg.ChannelId, err.(*channeltypes.UpgradeError).GetErrorReceipt()) + keeper.EmitErrorReceiptEvent(ctx, msg.PortId, msg.ChannelId, channel, err) + // NOTE: a FAILURE result is returned to the client and an error receipt is written to state. + // This signals to the relayer to begin the cancel upgrade handshake subprotocol. + return &channeltypes.MsgChannelUpgradeTryResponse{Result: channeltypes.FAILURE}, nil + } + + // NOTE: an error is returned to baseapp and transaction state is not committed. + return nil, errorsmod.Wrap(err, "channel upgrade try failed") + } + + upgradeVersion, err := cbs.OnChanUpgradeTry(ctx, msg.PortId, msg.ChannelId, upgrade.Fields.Ordering, upgrade.Fields.ConnectionHops, upgrade.Fields.Version) + if err != nil { + ctx.Logger().Error("channel upgrade try callback failed", "port-id", msg.PortId, "channel-id", msg.ChannelId, "error", err.Error()) + return nil, err + } + + channel, upgrade = k.ChannelKeeper.WriteUpgradeTryChannel(ctx, msg.PortId, msg.ChannelId, upgrade, upgradeVersion) + + ctx.Logger().Info("channel upgrade try succeeded", "port-id", msg.PortId, "channel-id", msg.ChannelId) + keeper.EmitChannelUpgradeTryEvent(ctx, msg.PortId, msg.ChannelId, channel, upgrade) + + return &channeltypes.MsgChannelUpgradeTryResponse{ + Result: channeltypes.SUCCESS, + Upgrade: upgrade, + UpgradeSequence: channel.UpgradeSequence, + }, nil +} + +// ChannelUpgradeAck defines a rpc handler method for MsgChannelUpgradeAck. +func (k Keeper) ChannelUpgradeAck(goCtx context.Context, msg *channeltypes.MsgChannelUpgradeAck) (*channeltypes.MsgChannelUpgradeAckResponse, error) { + ctx := sdk.UnwrapSDKContext(goCtx) + + module, _, err := k.ChannelKeeper.LookupModuleByChannel(ctx, msg.PortId, msg.ChannelId) + if err != nil { + ctx.Logger().Error("channel upgrade ack failed", "port-id", msg.PortId, "error", errorsmod.Wrap(err, "could not retrieve module from port-id")) + return nil, errorsmod.Wrap(err, "could not retrieve module from port-id") + } + + app, ok := k.Router.GetRoute(module) + if !ok { + ctx.Logger().Error("channel upgrade ack failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module) + } + + cbs, ok := app.(porttypes.UpgradableModule) + if !ok { + ctx.Logger().Error("channel upgrade ack failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module) + } + + err = k.ChannelKeeper.ChanUpgradeAck(ctx, msg.PortId, msg.ChannelId, msg.CounterpartyUpgrade, msg.ProofChannel, msg.ProofUpgrade, msg.ProofHeight) + if err != nil { + ctx.Logger().Error("channel upgrade ack failed", "error", errorsmod.Wrap(err, "channel upgrade ack failed")) + if channeltypes.IsUpgradeError(err) { + k.ChannelKeeper.MustAbortUpgrade(ctx, msg.PortId, msg.ChannelId, err) + cbs.OnChanUpgradeRestore(ctx, msg.PortId, msg.ChannelId) + + // NOTE: a FAILURE result is returned to the client and an error receipt is written to state. + // This signals to the relayer to begin the cancel upgrade handshake subprotocol. + return &channeltypes.MsgChannelUpgradeAckResponse{Result: channeltypes.FAILURE}, nil + } + + // NOTE: an error is returned to baseapp and transaction state is not committed. + return nil, errorsmod.Wrap(err, "channel upgrade ack failed") + } + + cacheCtx, writeFn := ctx.CacheContext() + err = cbs.OnChanUpgradeAck(cacheCtx, msg.PortId, msg.ChannelId, msg.CounterpartyUpgrade.Fields.Version) + if err != nil { + ctx.Logger().Error("channel upgrade ack callback failed", "port-id", msg.PortId, "channel-id", msg.ChannelId, "error", err.Error()) + k.ChannelKeeper.MustAbortUpgrade(ctx, msg.PortId, msg.ChannelId, err) + cbs.OnChanUpgradeRestore(ctx, msg.PortId, msg.ChannelId) + + return &channeltypes.MsgChannelUpgradeAckResponse{Result: channeltypes.FAILURE}, nil + } + + writeFn() + + channel, upgrade := k.ChannelKeeper.WriteUpgradeAckChannel(ctx, msg.PortId, msg.ChannelId, msg.CounterpartyUpgrade) + + ctx.Logger().Info("channel upgrade ack succeeded", "port-id", msg.PortId, "channel-id", msg.ChannelId) + keeper.EmitChannelUpgradeAckEvent(ctx, msg.PortId, msg.ChannelId, channel, upgrade) + + return &channeltypes.MsgChannelUpgradeAckResponse{Result: channeltypes.SUCCESS}, nil +} + +// ChannelUpgradeConfirm defines a rpc handler method for MsgChannelUpgradeConfirm. +func (k Keeper) ChannelUpgradeConfirm(goCtx context.Context, msg *channeltypes.MsgChannelUpgradeConfirm) (*channeltypes.MsgChannelUpgradeConfirmResponse, error) { + ctx := sdk.UnwrapSDKContext(goCtx) + + module, _, err := k.ChannelKeeper.LookupModuleByChannel(ctx, msg.PortId, msg.ChannelId) + if err != nil { + ctx.Logger().Error("channel upgrade confirm failed", "port-id", msg.PortId, "error", errorsmod.Wrap(err, "could not retrieve module from port-id")) + return nil, errorsmod.Wrap(err, "could not retrieve module from port-id") + } + + app, ok := k.Router.GetRoute(module) + if !ok { + ctx.Logger().Error("channel upgrade confirm failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module) + } + + cbs, ok := app.(porttypes.UpgradableModule) + if !ok { + ctx.Logger().Error("channel upgrade confirm failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module) + } + + err = k.ChannelKeeper.ChanUpgradeConfirm(ctx, msg.PortId, msg.ChannelId, msg.CounterpartyChannelState, msg.CounterpartyUpgrade, msg.ProofChannel, msg.ProofUpgrade, msg.ProofHeight) + if err != nil { + ctx.Logger().Error("channel upgrade confirm failed", "error", errorsmod.Wrap(err, "channel upgrade confirm failed")) + if channeltypes.IsUpgradeError(err) { + k.ChannelKeeper.MustAbortUpgrade(ctx, msg.PortId, msg.ChannelId, err) + cbs.OnChanUpgradeRestore(ctx, msg.PortId, msg.ChannelId) + + // NOTE: a FAILURE result is returned to the client and an error receipt is written to state. + // This signals to the relayer to begin the cancel upgrade handshake subprotocol. + return &channeltypes.MsgChannelUpgradeConfirmResponse{Result: channeltypes.FAILURE}, nil + } + + // NOTE: an error is returned to baseapp and transaction state is not committed. + return nil, errorsmod.Wrap(err, "channel upgrade confirm failed") + } + + channel := k.ChannelKeeper.WriteUpgradeConfirmChannel(ctx, msg.PortId, msg.ChannelId, msg.CounterpartyUpgrade) + ctx.Logger().Info("channel upgrade confirm succeeded", "port-id", msg.PortId, "channel-id", msg.ChannelId) + keeper.EmitChannelUpgradeConfirmEvent(ctx, msg.PortId, msg.ChannelId, channel) + + // Move channel to OPEN state if both chains have finished flushing in-flight packets. + // Counterparty channel state has been verified in ChanUpgradeConfirm. + if msg.CounterpartyChannelState == channeltypes.FLUSHCOMPLETE && !k.ChannelKeeper.HasInflightPackets(ctx, msg.PortId, msg.ChannelId) { + upgrade, found := k.ChannelKeeper.GetUpgrade(ctx, msg.PortId, msg.ChannelId) + if !found { + return nil, errorsmod.Wrapf(channeltypes.ErrUpgradeNotFound, "failed to retrieve channel upgrade: port ID (%s) channel ID (%s)", msg.PortId, msg.ChannelId) + } + + k.ChannelKeeper.WriteUpgradeOpenChannel(ctx, msg.PortId, msg.ChannelId) + cbs.OnChanUpgradeOpen(ctx, msg.PortId, msg.ChannelId, upgrade.Fields.Ordering, upgrade.Fields.ConnectionHops, upgrade.Fields.Version) + + ctx.Logger().Info("channel upgrade open succeeded", "port-id", msg.PortId, "channel-id", msg.ChannelId) + keeper.EmitChannelUpgradeOpenEvent(ctx, msg.PortId, msg.ChannelId, channel) + } + + return &channeltypes.MsgChannelUpgradeConfirmResponse{Result: channeltypes.SUCCESS}, nil +} + +// ChannelUpgradeOpen defines a rpc handler method for MsgChannelUpgradeOpen. +func (k Keeper) ChannelUpgradeOpen(goCtx context.Context, msg *channeltypes.MsgChannelUpgradeOpen) (*channeltypes.MsgChannelUpgradeOpenResponse, error) { + ctx := sdk.UnwrapSDKContext(goCtx) + + module, _, err := k.ChannelKeeper.LookupModuleByChannel(ctx, msg.PortId, msg.ChannelId) + if err != nil { + ctx.Logger().Error("channel upgrade open failed", "port-id", msg.PortId, "error", errorsmod.Wrap(err, "could not retrieve module from port-id")) + return nil, errorsmod.Wrap(err, "could not retrieve module from port-id") + } + + app, ok := k.Router.GetRoute(module) + if !ok { + ctx.Logger().Error("channel upgrade open failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module) + } + + cbs, ok := app.(porttypes.UpgradableModule) + if !ok { + ctx.Logger().Error("channel upgrade open failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module) + } + + if err = k.ChannelKeeper.ChanUpgradeOpen(ctx, msg.PortId, msg.ChannelId, msg.CounterpartyChannelState, msg.ProofChannel, msg.ProofHeight); err != nil { + ctx.Logger().Error("channel upgrade open failed", "error", errorsmod.Wrap(err, "channel upgrade open failed")) + return nil, errorsmod.Wrap(err, "channel upgrade open failed") + } + + upgrade, found := k.ChannelKeeper.GetUpgrade(ctx, msg.PortId, msg.ChannelId) + if !found { + return nil, errorsmod.Wrapf(channeltypes.ErrUpgradeNotFound, "failed to retrieve channel upgrade: port ID (%s) channel ID (%s)", msg.PortId, msg.ChannelId) + } + + cbs.OnChanUpgradeOpen(ctx, msg.PortId, msg.ChannelId, upgrade.Fields.Ordering, upgrade.Fields.ConnectionHops, upgrade.Fields.Version) + + channel := k.ChannelKeeper.WriteUpgradeOpenChannel(ctx, msg.PortId, msg.ChannelId) + + ctx.Logger().Info("channel upgrade open succeeded", "port-id", msg.PortId, "channel-id", msg.ChannelId) + keeper.EmitChannelUpgradeOpenEvent(ctx, msg.PortId, msg.ChannelId, channel) + + return &channeltypes.MsgChannelUpgradeOpenResponse{}, nil +} + +// ChannelUpgradeTimeout defines a rpc handler method for MsgChannelUpgradeTimeout. +func (k Keeper) ChannelUpgradeTimeout(goCtx context.Context, msg *channeltypes.MsgChannelUpgradeTimeout) (*channeltypes.MsgChannelUpgradeTimeoutResponse, error) { + ctx := sdk.UnwrapSDKContext(goCtx) + module, _, err := k.ChannelKeeper.LookupModuleByChannel(ctx, msg.PortId, msg.ChannelId) + if err != nil { + ctx.Logger().Error("channel upgrade timeout failed", "port-id", msg.PortId, "error", errorsmod.Wrap(err, "could not retrieve module from port-id")) + return nil, errorsmod.Wrap(err, "could not retrieve module from port-id") + } + + app, ok := k.Router.GetRoute(module) + if !ok { + ctx.Logger().Error("channel upgrade timeout failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module) + } + + cbs, ok := app.(porttypes.UpgradableModule) + if !ok { + ctx.Logger().Error("channel upgrade timeout failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module) + } + + err = k.ChannelKeeper.ChanUpgradeTimeout(ctx, msg.PortId, msg.ChannelId, msg.CounterpartyChannel, msg.ProofChannel, msg.ProofHeight) + if err != nil { + return nil, errorsmod.Wrapf(err, "could not timeout upgrade for channel: %s", msg.ChannelId) + } + + channel, upgrade := k.ChannelKeeper.WriteUpgradeTimeoutChannel(ctx, msg.PortId, msg.ChannelId) + + cbs.OnChanUpgradeRestore(ctx, msg.PortId, msg.ChannelId) + + ctx.Logger().Info("channel upgrade timeout callback succeeded: portID %s, channelID %s", msg.PortId, msg.ChannelId) + keeper.EmitChannelUpgradeTimeoutEvent(ctx, msg.PortId, msg.ChannelId, channel, upgrade) + + return &channeltypes.MsgChannelUpgradeTimeoutResponse{}, nil +} + +// ChannelUpgradeCancel defines a rpc handler method for MsgChannelUpgradeCancel. +func (k Keeper) ChannelUpgradeCancel(goCtx context.Context, msg *channeltypes.MsgChannelUpgradeCancel) (*channeltypes.MsgChannelUpgradeCancelResponse, error) { + ctx := sdk.UnwrapSDKContext(goCtx) + module, _, err := k.ChannelKeeper.LookupModuleByChannel(ctx, msg.PortId, msg.ChannelId) + if err != nil { + ctx.Logger().Error("channel upgrade cancel failed", "port-id", msg.PortId, "error", errorsmod.Wrap(err, "could not retrieve module from port-id")) + return nil, errorsmod.Wrap(err, "could not retrieve module from port-id") + } + + app, ok := k.Router.GetRoute(module) + if !ok { + ctx.Logger().Error("channel upgrade cancel failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "route not found to module: %s", module) + } + + cbs, ok := app.(porttypes.UpgradableModule) + if !ok { + ctx.Logger().Error("channel upgrade cancel failed", "port-id", msg.PortId, "error", errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module)) + return nil, errorsmod.Wrapf(porttypes.ErrInvalidRoute, "upgrade route not found to module: %s", module) + } + + channel, found := k.ChannelKeeper.GetChannel(ctx, msg.PortId, msg.ChannelId) + if !found { + return nil, errorsmod.Wrapf(channeltypes.ErrChannelNotFound, "port ID (%s) channel ID (%s)", msg.PortId, msg.ChannelId) + } + + // if the msgSender is authorized to make and cancel upgrades AND the current channel has not already reached FLUSHCOMPLETE + // then we can restore immediately without any additional checks + isAuthority := k.GetAuthority() == msg.Signer + if isAuthority && channel.State != channeltypes.FLUSHCOMPLETE { + k.ChannelKeeper.WriteUpgradeCancelChannel(ctx, msg.PortId, msg.ChannelId, channel.UpgradeSequence) + + cbs.OnChanUpgradeRestore(ctx, msg.PortId, msg.ChannelId) + + ctx.Logger().Info("channel upgrade cancel succeeded", "port-id", msg.PortId, "channel-id", msg.ChannelId) + + return &channeltypes.MsgChannelUpgradeCancelResponse{}, nil + } + + if err := k.ChannelKeeper.ChanUpgradeCancel(ctx, msg.PortId, msg.ChannelId, msg.ErrorReceipt, msg.ProofErrorReceipt, msg.ProofHeight); err != nil { + ctx.Logger().Error("channel upgrade cancel failed", "port-id", msg.PortId, "error", err.Error()) + return nil, errorsmod.Wrap(err, "channel upgrade cancel failed") + } + + k.ChannelKeeper.WriteUpgradeCancelChannel(ctx, msg.PortId, msg.ChannelId, msg.ErrorReceipt.Sequence) + + cbs.OnChanUpgradeRestore(ctx, msg.PortId, msg.ChannelId) + + ctx.Logger().Info("channel upgrade cancel succeeded", "port-id", msg.PortId, "channel-id", msg.ChannelId) + + return &channeltypes.MsgChannelUpgradeCancelResponse{}, nil +} + +// PruneAcknowledgements defines a rpc handler method for MsgPruneAcknowledgements. +func (k Keeper) PruneAcknowledgements(goCtx context.Context, msg *channeltypes.MsgPruneAcknowledgements) (*channeltypes.MsgPruneAcknowledgementsResponse, error) { + ctx := sdk.UnwrapSDKContext(goCtx) + + pruned, remaining, err := k.ChannelKeeper.PruneAcknowledgements(ctx, msg.PortId, msg.ChannelId, msg.Limit) + if err != nil { + return nil, err + } + + return &channeltypes.MsgPruneAcknowledgementsResponse{ + TotalPrunedSequences: pruned, + TotalRemainingSequences: remaining, + }, nil +} + // UpdateClientParams defines a rpc handler method for MsgUpdateParams. func (k Keeper) UpdateClientParams(goCtx context.Context, msg *clienttypes.MsgUpdateParams) (*clienttypes.MsgUpdateParamsResponse, error) { if k.GetAuthority() != msg.Signer { @@ -756,3 +1132,15 @@ func (k Keeper) UpdateConnectionParams(goCtx context.Context, msg *connectiontyp return &connectiontypes.MsgUpdateParamsResponse{}, nil } + +// UpdateChannelParams defines a rpc handler method for MsgUpdateParams. +func (k Keeper) UpdateChannelParams(goCtx context.Context, msg *channeltypes.MsgUpdateParams) (*channeltypes.MsgUpdateParamsResponse, error) { + if k.GetAuthority() != msg.Authority { + return nil, errorsmod.Wrapf(ibcerrors.ErrUnauthorized, "expected %s, got %s", k.GetAuthority(), msg.Authority) + } + + ctx := sdk.UnwrapSDKContext(goCtx) + k.ChannelKeeper.SetParams(ctx, msg.Params) + + return &channeltypes.MsgUpdateParamsResponse{}, nil +} diff --git a/modules/core/keeper/msg_server_test.go b/modules/core/keeper/msg_server_test.go index 84298ae0481..ee8444514e5 100644 --- a/modules/core/keeper/msg_server_test.go +++ b/modules/core/keeper/msg_server_test.go @@ -2,11 +2,14 @@ package keeper_test import ( "errors" + "fmt" upgradetypes "cosmossdk.io/x/upgrade/types" + sdk "github.com/cosmos/cosmos-sdk/types" sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" + capabilitytypes "github.com/cosmos/ibc-go/modules/capability/types" clienttypes "github.com/cosmos/ibc-go/v8/modules/core/02-client/types" connectiontypes "github.com/cosmos/ibc-go/v8/modules/core/03-connection/types" channeltypes "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types" @@ -202,6 +205,82 @@ func (suite *KeeperTestSuite) TestHandleRecvPacket() { } } +func (suite *KeeperTestSuite) TestRecoverClient() { + var msg *clienttypes.MsgRecoverClient + + testCases := []struct { + name string + malleate func() + expErr error + }{ + { + "success: recover client", + func() {}, + nil, + }, + { + "signer doesn't match authority", + func() { + msg.Signer = ibctesting.InvalidID + }, + ibcerrors.ErrUnauthorized, + }, + { + "invalid subject client", + func() { + msg.SubjectClientId = ibctesting.InvalidID + }, + clienttypes.ErrClientNotFound, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + subjectPath := ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.SetupClients(subjectPath) + subject := subjectPath.EndpointA.ClientID + subjectClientState := suite.chainA.GetClientState(subject) + + substitutePath := ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.SetupClients(substitutePath) + substitute := substitutePath.EndpointA.ClientID + + // update substitute twice + err := substitutePath.EndpointA.UpdateClient() + suite.Require().NoError(err) + err = substitutePath.EndpointA.UpdateClient() + suite.Require().NoError(err) + + tmClientState, ok := subjectClientState.(*ibctm.ClientState) + suite.Require().True(ok) + tmClientState.FrozenHeight = tmClientState.LatestHeight + suite.chainA.App.GetIBCKeeper().ClientKeeper.SetClientState(suite.chainA.GetContext(), subject, tmClientState) + + msg = clienttypes.NewMsgRecoverClient(suite.chainA.App.GetIBCKeeper().GetAuthority(), subject, substitute) + + tc.malleate() + + _, err = keeper.Keeper.RecoverClient(*suite.chainA.App.GetIBCKeeper(), suite.chainA.GetContext(), msg) + + expPass := tc.expErr == nil + if expPass { + suite.Require().NoError(err) + + // Assert that client status is now Active + clientStore := suite.chainA.App.GetIBCKeeper().ClientKeeper.ClientStore(suite.chainA.GetContext(), subjectPath.EndpointA.ClientID) + tmClientState := subjectPath.EndpointA.GetClientState().(*ibctm.ClientState) + suite.Require().Equal(tmClientState.Status(suite.chainA.GetContext(), clientStore, suite.chainA.App.AppCodec()), exported.Active) + } else { + suite.Require().Error(err) + suite.Require().ErrorIs(err, tc.expErr) + } + }) + } +} + // tests the IBC handler acknowledgement of a packet on ordered and unordered // channels. It verifies that the deletion of packet commitments from state // occurs. It test high level properties like ordering and basic sanity @@ -499,9 +578,10 @@ func (suite *KeeperTestSuite) TestHandleTimeoutPacket() { // 'TimeoutExecuted' can be found in the 04-channel/keeper/timeout_test.go. func (suite *KeeperTestSuite) TestHandleTimeoutOnClosePacket() { var ( - packet channeltypes.Packet - packetKey []byte - path *ibctesting.Path + packet channeltypes.Packet + packetKey []byte + path *ibctesting.Path + counterpartyUpgradeSequence uint64 ) testCases := []struct { @@ -638,7 +718,7 @@ func (suite *KeeperTestSuite) TestHandleTimeoutOnClosePacket() { channelKey := host.ChannelKey(path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) proofClosed, _ := suite.chainB.QueryProof(channelKey) - msg := channeltypes.NewMsgTimeoutOnClose(packet, 1, proof, proofClosed, proofHeight, suite.chainA.SenderAccount.GetAddress().String()) + msg := channeltypes.NewMsgTimeoutOnClose(packet, 1, proof, proofClosed, proofHeight, suite.chainA.SenderAccount.GetAddress().String(), counterpartyUpgradeSequence) _, err := keeper.Keeper.TimeoutOnClose(*suite.chainA.App.GetIBCKeeper(), suite.chainA.GetContext(), msg) @@ -780,187 +860,1083 @@ func (suite *KeeperTestSuite) TestUpgradeClient() { } } -func (suite *KeeperTestSuite) TestRecoverClient() { - var msg *clienttypes.MsgRecoverClient +func (suite *KeeperTestSuite) TestChannelUpgradeInit() { + var ( + path *ibctesting.Path + msg *channeltypes.MsgChannelUpgradeInit + ) - testCases := []struct { - name string - malleate func() - expErr error + cases := []struct { + name string + malleate func() + expResult func(res *channeltypes.MsgChannelUpgradeInitResponse, err error) }{ { - "success: recover client", - func() {}, - nil, - }, - { - "signer doesn't match authority", + "success", func() { - msg.Signer = ibctesting.InvalidID + msg = channeltypes.NewMsgChannelUpgradeInit( + path.EndpointA.ChannelConfig.PortID, + path.EndpointA.ChannelID, + path.EndpointA.GetProposedUpgrade().Fields, + path.EndpointA.Chain.GetSimApp().IBCKeeper.GetAuthority(), + ) + }, + func(res *channeltypes.MsgChannelUpgradeInitResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + suite.Require().Equal(uint64(1), res.UpgradeSequence) }, - ibcerrors.ErrUnauthorized, }, { - "invalid subject client", + "authority is not signer of the upgrade init msg", func() { - msg.SubjectClientId = ibctesting.InvalidID + msg = channeltypes.NewMsgChannelUpgradeInit( + path.EndpointA.ChannelConfig.PortID, + path.EndpointA.ChannelID, + path.EndpointA.GetProposedUpgrade().Fields, + path.EndpointA.Chain.SenderAccount.String(), + ) + }, + func(res *channeltypes.MsgChannelUpgradeInitResponse, err error) { + suite.Require().Error(err) + suite.Require().ErrorContains(err, ibcerrors.ErrUnauthorized.Error()) + suite.Require().Nil(res) }, - clienttypes.ErrClientNotFound, }, } - for _, tc := range testCases { + for _, tc := range cases { tc := tc suite.Run(tc.name, func() { suite.SetupTest() - subjectPath := ibctesting.NewPath(suite.chainA, suite.chainB) - suite.coordinator.SetupClients(subjectPath) - subject := subjectPath.EndpointA.ClientID - subjectClientState := suite.chainA.GetClientState(subject) - - substitutePath := ibctesting.NewPath(suite.chainA, suite.chainB) - suite.coordinator.SetupClients(substitutePath) - substitute := substitutePath.EndpointA.ClientID - - // update substitute twice - err := substitutePath.EndpointA.UpdateClient() - suite.Require().NoError(err) - err = substitutePath.EndpointA.UpdateClient() - suite.Require().NoError(err) - - tmClientState, ok := subjectClientState.(*ibctm.ClientState) - suite.Require().True(ok) - tmClientState.FrozenHeight = tmClientState.LatestHeight - suite.chainA.App.GetIBCKeeper().ClientKeeper.SetClientState(suite.chainA.GetContext(), subject, tmClientState) + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) - msg = clienttypes.NewMsgRecoverClient(suite.chainA.App.GetIBCKeeper().GetAuthority(), subject, substitute) + // configure the channel upgrade version on testing endpoints + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion tc.malleate() - _, err = keeper.Keeper.RecoverClient(*suite.chainA.App.GetIBCKeeper(), suite.chainA.GetContext(), msg) - - expPass := tc.expErr == nil - if expPass { - suite.Require().NoError(err) + res, err := keeper.Keeper.ChannelUpgradeInit(*suite.chainA.App.GetIBCKeeper(), suite.chainA.GetContext(), msg) - // Assert that client status is now Active - clientStore := suite.chainA.App.GetIBCKeeper().ClientKeeper.ClientStore(suite.chainA.GetContext(), subjectPath.EndpointA.ClientID) - tmClientState := subjectPath.EndpointA.GetClientState().(*ibctm.ClientState) - suite.Require().Equal(tmClientState.Status(suite.chainA.GetContext(), clientStore, suite.chainA.App.AppCodec()), exported.Active) - } else { - suite.Require().Error(err) - suite.Require().ErrorIs(err, tc.expErr) - } + tc.expResult(res, err) }) } } -// TestIBCSoftwareUpgrade tests the IBCSoftwareUpgrade rpc handler -func (suite *KeeperTestSuite) TestIBCSoftwareUpgrade() { - var msg *clienttypes.MsgIBCSoftwareUpgrade - testCases := []struct { - name string - malleate func() - expError error +func (suite *KeeperTestSuite) TestChannelUpgradeTry() { + var ( + path *ibctesting.Path + msg *channeltypes.MsgChannelUpgradeTry + ) + + cases := []struct { + name string + malleate func() + expResult func(res *channeltypes.MsgChannelUpgradeTryResponse, err error) }{ { - "success: valid authority and client upgrade", + "success", func() {}, - nil, - }, - { - "failure: invalid authority address", - func() { - msg.Signer = suite.chainA.SenderAccount.GetAddress().String() + func(res *channeltypes.MsgChannelUpgradeTryResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + suite.Require().Equal(channeltypes.SUCCESS, res.Result) + + channel := path.EndpointB.GetChannel() + suite.Require().Equal(channeltypes.FLUSHING, channel.State) + suite.Require().Equal(uint64(1), channel.UpgradeSequence) }, - ibcerrors.ErrUnauthorized, }, { - "failure: invalid clientState", + "module capability not found", func() { - msg.UpgradedClientState = nil + msg.PortId = "invalid-port" + msg.ChannelId = "invalid-channel" + }, + func(res *channeltypes.MsgChannelUpgradeTryResponse, err error) { + suite.Require().Error(err) + suite.Require().Nil(res) + + suite.Require().ErrorIs(err, capabilitytypes.ErrCapabilityNotFound) }, - clienttypes.ErrInvalidClientType, }, { - "failure: failed to schedule client upgrade", + "unsynchronized upgrade sequence writes upgrade error receipt", func() { - msg.Plan.Height = 0 + channel := path.EndpointB.GetChannel() + channel.UpgradeSequence = 99 + + path.EndpointB.SetChannel(channel) + }, + func(res *channeltypes.MsgChannelUpgradeTryResponse, err error) { + suite.Require().NoError(err) + + suite.Require().NotNil(res) + suite.Require().Equal(channeltypes.FAILURE, res.Result) + + errorReceipt, found := suite.chainB.GetSimApp().GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(99), errorReceipt.Sequence) }, - sdkerrors.ErrInvalidRequest, }, } - for _, tc := range testCases { + for _, tc := range cases { tc := tc suite.Run(tc.name, func() { - path := ibctesting.NewPath(suite.chainA, suite.chainB) - suite.coordinator.SetupClients(path) - validAuthority := suite.chainA.App.GetIBCKeeper().GetAuthority() - plan := upgradetypes.Plan{ - Name: "upgrade IBC clients", - Height: 1000, - } - // update trusting period - clientState := path.EndpointB.GetClientState() - clientState.(*ibctm.ClientState).TrustingPeriod += 100 + suite.SetupTest() - var err error - msg, err = clienttypes.NewMsgIBCSoftwareUpgrade( - validAuthority, - plan, - clientState, - ) + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + // configure the channel upgrade version on testing endpoints + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + err := path.EndpointA.ChanUpgradeInit() suite.Require().NoError(err) - tc.malleate() + err = path.EndpointB.UpdateClient() + suite.Require().NoError(err) - _, err = keeper.Keeper.IBCSoftwareUpgrade(*suite.chainA.App.GetIBCKeeper(), suite.chainA.GetContext(), msg) + counterpartySequence := path.EndpointA.GetChannel().UpgradeSequence + counterpartyUpgrade, found := suite.chainA.GetSimApp().GetIBCKeeper().ChannelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + + proofChannel, proofUpgrade, proofHeight := path.EndpointA.QueryChannelUpgradeProof() + + msg = &channeltypes.MsgChannelUpgradeTry{ + PortId: path.EndpointB.ChannelConfig.PortID, + ChannelId: path.EndpointB.ChannelID, + ProposedUpgradeConnectionHops: []string{ibctesting.FirstConnectionID}, + CounterpartyUpgradeSequence: counterpartySequence, + CounterpartyUpgradeFields: counterpartyUpgrade.Fields, + ProofChannel: proofChannel, + ProofUpgrade: proofUpgrade, + ProofHeight: proofHeight, + Signer: suite.chainB.SenderAccount.GetAddress().String(), + } - if tc.expError == nil { - suite.Require().NoError(err) - // upgrade plan is stored - storedPlan, err := suite.chainA.GetSimApp().UpgradeKeeper.GetUpgradePlan(suite.chainA.GetContext()) - suite.Require().NoError(err) - suite.Require().Equal(plan, storedPlan) + tc.malleate() - // upgraded client state is stored - bz, err := suite.chainA.GetSimApp().UpgradeKeeper.GetUpgradedClient(suite.chainA.GetContext(), plan.Height) - suite.Require().NoError(err) - upgradedClientState, err := clienttypes.UnmarshalClientState(suite.chainA.App.AppCodec(), bz) - suite.Require().NoError(err) - suite.Require().Equal(clientState.ZeroCustomFields(), upgradedClientState) - } else { - suite.Require().True(errors.Is(err, tc.expError)) - } + res, err := suite.chainB.GetSimApp().GetIBCKeeper().ChannelUpgradeTry(suite.chainB.GetContext(), msg) + + tc.expResult(res, err) }) } } -// TestUpdateClientParams tests the UpdateClientParams rpc handler -func (suite *KeeperTestSuite) TestUpdateClientParams() { - signer := suite.chainA.App.GetIBCKeeper().GetAuthority() - testCases := []struct { - name string - msg *clienttypes.MsgUpdateParams - expPass bool +func (suite *KeeperTestSuite) TestChannelUpgradeAck() { + var ( + path *ibctesting.Path + msg *channeltypes.MsgChannelUpgradeAck + ) + + cases := []struct { + name string + malleate func() + expResult func(res *channeltypes.MsgChannelUpgradeAckResponse, err error) }{ { - "success: valid signer and default params", - clienttypes.NewMsgUpdateParams(signer, clienttypes.DefaultParams()), - true, - }, - { - "failure: malformed signer address", - clienttypes.NewMsgUpdateParams(ibctesting.InvalidID, clienttypes.DefaultParams()), - false, + "success, no pending in-flight packets", + func() {}, + func(res *channeltypes.MsgChannelUpgradeAckResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + suite.Require().Equal(channeltypes.SUCCESS, res.Result) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(channeltypes.FLUSHCOMPLETE, channel.State) + suite.Require().Equal(uint64(1), channel.UpgradeSequence) + }, }, { - "failure: empty signer address", - clienttypes.NewMsgUpdateParams("", clienttypes.DefaultParams()), - false, + "success, pending in-flight packets", + func() { + portID := path.EndpointA.ChannelConfig.PortID + channelID := path.EndpointA.ChannelID + // Set a dummy packet commitment to simulate in-flight packets + suite.chainA.GetSimApp().IBCKeeper.ChannelKeeper.SetPacketCommitment(suite.chainA.GetContext(), portID, channelID, 1, []byte("hash")) + }, + func(res *channeltypes.MsgChannelUpgradeAckResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + suite.Require().Equal(channeltypes.SUCCESS, res.Result) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(channeltypes.FLUSHING, channel.State) + suite.Require().Equal(uint64(1), channel.UpgradeSequence) + }, + }, + { + "module capability not found", + func() { + msg.PortId = ibctesting.InvalidID + msg.ChannelId = ibctesting.InvalidID + }, + func(res *channeltypes.MsgChannelUpgradeAckResponse, err error) { + suite.Require().Error(err) + suite.Require().Nil(res) + + suite.Require().ErrorIs(err, capabilitytypes.ErrCapabilityNotFound) + }, + }, + { + "core handler returns error and no upgrade error receipt is written", + func() { + // force an error by overriding the channel state to an invalid value + channel := path.EndpointA.GetChannel() + channel.State = channeltypes.CLOSED + + path.EndpointA.SetChannel(channel) + }, + func(res *channeltypes.MsgChannelUpgradeAckResponse, err error) { + suite.Require().Error(err) + suite.Require().Nil(res) + suite.Require().ErrorIs(err, channeltypes.ErrInvalidChannelState) + + errorReceipt, found := suite.chainA.GetSimApp().GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().Empty(errorReceipt) + suite.Require().False(found) + }, + }, + { + "core handler returns error and writes upgrade error receipt", + func() { + // force an upgrade error by modifying the channel upgrade ordering to an incompatible value + upgrade := path.EndpointA.GetChannelUpgrade() + upgrade.Fields.Ordering = channeltypes.NONE + + path.EndpointA.SetChannelUpgrade(upgrade) + }, + func(res *channeltypes.MsgChannelUpgradeAckResponse, err error) { + suite.Require().NoError(err) + + suite.Require().NotNil(res) + suite.Require().Equal(channeltypes.FAILURE, res.Result) + + errorReceipt, found := suite.chainA.GetSimApp().GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(1), errorReceipt.Sequence) + }, + }, + { + "application callback returns error and error receipt is written", + func() { + suite.chainA.GetSimApp().IBCMockModule.IBCApp.OnChanUpgradeAck = func( + ctx sdk.Context, portID, channelID, counterpartyVersion string, + ) error { + // set arbitrary value in store to mock application state changes + store := ctx.KVStore(suite.chainA.GetSimApp().GetKey(exported.ModuleName)) + store.Set([]byte("foo"), []byte("bar")) + return fmt.Errorf("mock app callback failed") + } + }, + func(res *channeltypes.MsgChannelUpgradeAckResponse, err error) { + suite.Require().NoError(err) + + suite.Require().NotNil(res) + suite.Require().Equal(channeltypes.FAILURE, res.Result) + + errorReceipt, found := suite.chainA.GetSimApp().GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(1), errorReceipt.Sequence) + + // assert application state changes are not committed + store := suite.chainA.GetContext().KVStore(suite.chainA.GetSimApp().GetKey(exported.ModuleName)) + suite.Require().False(store.Has([]byte("foo"))) + }, + }, + } + + for _, tc := range cases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + // configure the channel upgrade version on testing endpoints + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + err = path.EndpointA.UpdateClient() + suite.Require().NoError(err) + + counterpartyUpgrade := path.EndpointB.GetChannelUpgrade() + + proofChannel, proofUpgrade, proofHeight := path.EndpointB.QueryChannelUpgradeProof() + + msg = &channeltypes.MsgChannelUpgradeAck{ + PortId: path.EndpointA.ChannelConfig.PortID, + ChannelId: path.EndpointA.ChannelID, + CounterpartyUpgrade: counterpartyUpgrade, + ProofChannel: proofChannel, + ProofUpgrade: proofUpgrade, + ProofHeight: proofHeight, + Signer: suite.chainA.SenderAccount.GetAddress().String(), + } + + tc.malleate() + + res, err := suite.chainA.GetSimApp().GetIBCKeeper().ChannelUpgradeAck(suite.chainA.GetContext(), msg) + + tc.expResult(res, err) + }) + } +} + +func (suite *KeeperTestSuite) TestChannelUpgradeConfirm() { + var ( + path *ibctesting.Path + msg *channeltypes.MsgChannelUpgradeConfirm + ) + + cases := []struct { + name string + malleate func() + expResult func(res *channeltypes.MsgChannelUpgradeConfirmResponse, err error) + }{ + { + "success, no pending in-flight packets", + func() {}, + func(res *channeltypes.MsgChannelUpgradeConfirmResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + suite.Require().Equal(channeltypes.SUCCESS, res.Result) + + channel := path.EndpointB.GetChannel() + suite.Require().Equal(channeltypes.OPEN, channel.State) + suite.Require().Equal(uint64(1), channel.UpgradeSequence) + }, + }, + { + "success, pending in-flight packets on init chain", + func() { + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + seq, err := path.EndpointA.SendPacket(path.EndpointB.Chain.GetTimeoutHeight(), 0, ibctesting.MockPacketData) + suite.Require().Equal(uint64(1), seq) + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointB.UpdateClient() + suite.Require().NoError(err) + + counterpartyChannelState := path.EndpointA.GetChannel().State + counterpartyUpgrade := path.EndpointA.GetChannelUpgrade() + + proofChannel, proofUpgrade, proofHeight := path.EndpointA.QueryChannelUpgradeProof() + + msg = &channeltypes.MsgChannelUpgradeConfirm{ + PortId: path.EndpointB.ChannelConfig.PortID, + ChannelId: path.EndpointB.ChannelID, + CounterpartyChannelState: counterpartyChannelState, + CounterpartyUpgrade: counterpartyUpgrade, + ProofChannel: proofChannel, + ProofUpgrade: proofUpgrade, + ProofHeight: proofHeight, + Signer: suite.chainA.SenderAccount.GetAddress().String(), + } + }, + func(res *channeltypes.MsgChannelUpgradeConfirmResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + suite.Require().Equal(channeltypes.SUCCESS, res.Result) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(channeltypes.FLUSHING, channel.State) + suite.Require().Equal(uint64(1), channel.UpgradeSequence) + + channel = path.EndpointB.GetChannel() + suite.Require().Equal(channeltypes.FLUSHCOMPLETE, channel.State) + suite.Require().Equal(uint64(1), channel.UpgradeSequence) + }, + }, + { + "success, pending in-flight packets on try chain", + func() { + portID, channelID := path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID + suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.SetPacketCommitment(suite.chainB.GetContext(), portID, channelID, 1, []byte("hash")) + }, + func(res *channeltypes.MsgChannelUpgradeConfirmResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + suite.Require().Equal(channeltypes.SUCCESS, res.Result) + + channel := path.EndpointB.GetChannel() + suite.Require().Equal(channeltypes.FLUSHING, channel.State) + suite.Require().Equal(uint64(1), channel.UpgradeSequence) + }, + }, + { + "module capability not found", + func() { + msg.PortId = ibctesting.InvalidID + msg.ChannelId = ibctesting.InvalidID + }, + func(res *channeltypes.MsgChannelUpgradeConfirmResponse, err error) { + suite.Require().Error(err) + suite.Require().Nil(res) + + suite.Require().ErrorIs(err, capabilitytypes.ErrCapabilityNotFound) + }, + }, + { + "core handler returns error and no upgrade error receipt is written", + func() { + // force an error by overriding the channel state to an invalid value + channel := path.EndpointB.GetChannel() + channel.State = channeltypes.CLOSED + + path.EndpointB.SetChannel(channel) + }, + func(res *channeltypes.MsgChannelUpgradeConfirmResponse, err error) { + suite.Require().Error(err) + suite.Require().Nil(res) + suite.Require().ErrorIs(err, channeltypes.ErrInvalidChannelState) + + errorReceipt, found := suite.chainB.GetSimApp().GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().Empty(errorReceipt) + suite.Require().False(found) + }, + }, + { + "core handler returns error and writes upgrade error receipt", + func() { + // force an upgrade error by modifying the counterparty channel upgrade timeout to be elapsed + upgrade := path.EndpointA.GetChannelUpgrade() + upgrade.Timeout = channeltypes.NewTimeout(clienttypes.ZeroHeight(), uint64(path.EndpointB.Chain.CurrentHeader.Time.UnixNano())) + + path.EndpointA.SetChannelUpgrade(upgrade) + + suite.coordinator.CommitBlock(suite.chainA) + + err := path.EndpointB.UpdateClient() + suite.Require().NoError(err) + + proofChannel, proofUpgrade, proofHeight := path.EndpointA.QueryChannelUpgradeProof() + + msg.CounterpartyUpgrade = upgrade + msg.ProofChannel = proofChannel + msg.ProofUpgrade = proofUpgrade + msg.ProofHeight = proofHeight + }, + func(res *channeltypes.MsgChannelUpgradeConfirmResponse, err error) { + suite.Require().NoError(err) + + suite.Require().NotNil(res) + suite.Require().Equal(channeltypes.FAILURE, res.Result) + + errorReceipt, found := suite.chainB.GetSimApp().GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(found) + suite.Require().Equal(uint64(1), errorReceipt.Sequence) + }, + }, + } + + for _, tc := range cases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + // configure the channel upgrade version on testing endpoints + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointB.UpdateClient() + suite.Require().NoError(err) + + counterpartyChannelState := path.EndpointA.GetChannel().State + counterpartyUpgrade := path.EndpointA.GetChannelUpgrade() + + proofChannel, proofUpgrade, proofHeight := path.EndpointA.QueryChannelUpgradeProof() + + msg = &channeltypes.MsgChannelUpgradeConfirm{ + PortId: path.EndpointB.ChannelConfig.PortID, + ChannelId: path.EndpointB.ChannelID, + CounterpartyChannelState: counterpartyChannelState, + CounterpartyUpgrade: counterpartyUpgrade, + ProofChannel: proofChannel, + ProofUpgrade: proofUpgrade, + ProofHeight: proofHeight, + Signer: suite.chainA.SenderAccount.GetAddress().String(), + } + + tc.malleate() + + res, err := suite.chainB.GetSimApp().GetIBCKeeper().ChannelUpgradeConfirm(suite.chainB.GetContext(), msg) + + tc.expResult(res, err) + }) + } +} + +func (suite *KeeperTestSuite) TestChannelUpgradeOpen() { + var ( + path *ibctesting.Path + msg *channeltypes.MsgChannelUpgradeOpen + ) + + cases := []struct { + name string + malleate func() + expResult func(res *channeltypes.MsgChannelUpgradeOpenResponse, err error) + }{ + { + "success", + func() {}, + func(res *channeltypes.MsgChannelUpgradeOpenResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + + channel := path.EndpointA.GetChannel() + suite.Require().Equal(channeltypes.OPEN, channel.State) + }, + }, + { + "module capability not found", + func() { + msg.PortId = ibctesting.InvalidID + msg.ChannelId = ibctesting.InvalidID + }, + func(res *channeltypes.MsgChannelUpgradeOpenResponse, err error) { + suite.Require().Error(err) + suite.Require().Nil(res) + + suite.Require().ErrorIs(err, capabilitytypes.ErrCapabilityNotFound) + }, + }, + { + "core handler fails", + func() { + channel := path.EndpointA.GetChannel() + channel.State = channeltypes.FLUSHING + path.EndpointA.SetChannel(channel) + }, + func(res *channeltypes.MsgChannelUpgradeOpenResponse, err error) { + suite.Require().Error(err) + suite.Require().Nil(res) + + suite.Require().ErrorIs(err, channeltypes.ErrInvalidChannelState) + }, + }, + } + + for _, tc := range cases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + // configure the channel upgrade version on testing endpoints + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeConfirm() + suite.Require().NoError(err) + + err = path.EndpointA.UpdateClient() + suite.Require().NoError(err) + + counterpartyChannel := path.EndpointB.GetChannel() + channelKey := host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + proofChannel, proofHeight := path.EndpointB.QueryProof(channelKey) + + msg = &channeltypes.MsgChannelUpgradeOpen{ + PortId: path.EndpointA.ChannelConfig.PortID, + ChannelId: path.EndpointA.ChannelID, + CounterpartyChannelState: counterpartyChannel.State, + ProofChannel: proofChannel, + ProofHeight: proofHeight, + Signer: suite.chainA.SenderAccount.GetAddress().String(), + } + + tc.malleate() + + res, err := suite.chainA.GetSimApp().GetIBCKeeper().ChannelUpgradeOpen(suite.chainA.GetContext(), msg) + + tc.expResult(res, err) + }) + } +} + +func (suite *KeeperTestSuite) TestChannelUpgradeCancel() { + var ( + path *ibctesting.Path + msg *channeltypes.MsgChannelUpgradeCancel + ) + + cases := []struct { + name string + malleate func() + expResult func(res *channeltypes.MsgChannelUpgradeCancelResponse, err error) + }{ + { + "success: keeper is not authority, valid error receipt so channnel changed to match error receipt seq", + func() {}, + func(res *channeltypes.MsgChannelUpgradeCancelResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + + channel := path.EndpointA.GetChannel() + // Channel state should be reverted back to open. + suite.Require().Equal(channeltypes.OPEN, channel.State) + // Upgrade sequence should be changed to match sequence on error receipt. + suite.Require().Equal(uint64(2), channel.UpgradeSequence) + }, + }, + { + "success: keeper is authority & channel state in FLUSHING, so error receipt is ignored and channel is restored to initial upgrade sequence", + func() { + msg.Signer = suite.chainA.App.GetIBCKeeper().GetAuthority() + + channel := path.EndpointA.GetChannel() + channel.State = channeltypes.FLUSHING + channel.UpgradeSequence = uint64(3) + path.EndpointA.SetChannel(channel) + }, + func(res *channeltypes.MsgChannelUpgradeCancelResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + + channel := path.EndpointA.GetChannel() + // Channel state should be reverted back to open. + suite.Require().Equal(channeltypes.OPEN, channel.State) + // Upgrade sequence should be changed to match initial upgrade sequence. + suite.Require().Equal(uint64(3), channel.UpgradeSequence) + }, + }, + { + "success: keeper is authority & channel state in FLUSHING, can be cancelled even with invalid error receipt", + func() { + msg.Signer = suite.chainA.App.GetIBCKeeper().GetAuthority() + msg.ProofErrorReceipt = []byte("invalid proof") + + channel := path.EndpointA.GetChannel() + channel.State = channeltypes.FLUSHING + channel.UpgradeSequence = uint64(1) + path.EndpointA.SetChannel(channel) + }, + func(res *channeltypes.MsgChannelUpgradeCancelResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + + channel := path.EndpointA.GetChannel() + // Channel state should be reverted back to open. + suite.Require().Equal(channeltypes.OPEN, channel.State) + // Upgrade sequence should be changed to match initial upgrade sequence. + suite.Require().Equal(uint64(1), channel.UpgradeSequence) + }, + }, + { + "success: keeper is authority & channel state in FLUSHING, can be cancelled even with empty error receipt", + func() { + msg.Signer = suite.chainA.App.GetIBCKeeper().GetAuthority() + msg.ProofErrorReceipt = nil + + channel := path.EndpointA.GetChannel() + channel.State = channeltypes.FLUSHING + channel.UpgradeSequence = uint64(1) + path.EndpointA.SetChannel(channel) + }, + func(res *channeltypes.MsgChannelUpgradeCancelResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + + channel := path.EndpointA.GetChannel() + // Channel state should be reverted back to open. + suite.Require().Equal(channeltypes.OPEN, channel.State) + // Upgrade sequence should be changed to match initial upgrade sequence. + suite.Require().Equal(uint64(1), channel.UpgradeSequence) + }, + }, + { + "success: keeper is authority but channel state in FLUSHCOMPLETE, requires valid error receipt", + func() { + msg.Signer = suite.chainA.App.GetIBCKeeper().GetAuthority() + + channel := path.EndpointA.GetChannel() + channel.State = channeltypes.FLUSHCOMPLETE + channel.UpgradeSequence = uint64(1) + path.EndpointA.SetChannel(channel) + }, + func(res *channeltypes.MsgChannelUpgradeCancelResponse, err error) { + suite.Require().NoError(err) + suite.Require().NotNil(res) + + channel := path.EndpointA.GetChannel() + // Channel state should be reverted back to open. + suite.Require().Equal(channeltypes.OPEN, channel.State) + // Upgrade sequence should be changed to match error receipt sequence. + suite.Require().Equal(uint64(2), channel.UpgradeSequence) + }, + }, + { + "capability not found", + func() { + msg.ChannelId = ibctesting.InvalidID + }, + func(res *channeltypes.MsgChannelUpgradeCancelResponse, err error) { + suite.Require().Error(err) + suite.Require().Nil(res) + + channel := path.EndpointA.GetChannel() + suite.Require().ErrorIs(err, capabilitytypes.ErrCapabilityNotFound) + suite.Require().Equal(channeltypes.OPEN, channel.State) + // Upgrade sequence should not be changed. + suite.Require().Equal(uint64(1), channel.UpgradeSequence) + }, + }, + { + "core handler fails: invalid proof", + func() { + msg.ProofErrorReceipt = []byte("invalid proof") + // Force set to STATE_FLUSHCOMPLETE to check that state is not changed. + suite.Require().NoError(path.EndpointA.SetChannelState(channeltypes.FLUSHCOMPLETE)) + }, + func(res *channeltypes.MsgChannelUpgradeCancelResponse, err error) { + suite.Require().Error(err) + suite.Require().Nil(res) + + channel := path.EndpointA.GetChannel() + suite.Require().ErrorIs(err, commitmenttypes.ErrInvalidProof) + // Channel state should not be changed. + suite.Require().Equal(channeltypes.FLUSHCOMPLETE, channel.State) + // Upgrade sequence should not be changed. + suite.Require().Equal(uint64(1), channel.UpgradeSequence) + }, + }, + } + for _, tc := range cases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + // configure the channel upgrade version on testing endpoints + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + // cause the upgrade to fail on chain b so an error receipt is written. + // if the counterparty (chain A) upgrade sequence is less than the current sequence, (chain B) + // an upgrade error will be returned by chain B during ChanUpgradeTry. + channel := path.EndpointA.GetChannel() + channel.UpgradeSequence = 1 + path.EndpointA.SetChannel(channel) + + channel = path.EndpointB.GetChannel() + channel.UpgradeSequence = 2 + path.EndpointB.SetChannel(channel) + + suite.Require().NoError(path.EndpointA.UpdateClient()) + suite.Require().NoError(path.EndpointB.UpdateClient()) + + suite.Require().NoError(path.EndpointB.ChanUpgradeTry()) + + suite.Require().NoError(path.EndpointA.UpdateClient()) + + upgradeErrorReceiptKey := host.ChannelUpgradeErrorKey(path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + errorReceiptProof, proofHeight := path.EndpointB.QueryProof(upgradeErrorReceiptKey) + + errorReceipt, ok := suite.chainB.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgradeErrorReceipt(suite.chainB.GetContext(), path.EndpointB.ChannelConfig.PortID, path.EndpointB.ChannelID) + suite.Require().True(ok) + + msg = &channeltypes.MsgChannelUpgradeCancel{ + PortId: path.EndpointA.ChannelConfig.PortID, + ChannelId: path.EndpointA.ChannelID, + ErrorReceipt: errorReceipt, + ProofErrorReceipt: errorReceiptProof, + ProofHeight: proofHeight, + Signer: suite.chainA.SenderAccount.GetAddress().String(), + } + + tc.malleate() + + res, err := suite.chainA.GetSimApp().GetIBCKeeper().ChannelUpgradeCancel(suite.chainA.GetContext(), msg) + tc.expResult(res, err) + }) + } +} + +func (suite *KeeperTestSuite) TestChannelUpgradeTimeout() { + var ( + path *ibctesting.Path + msg *channeltypes.MsgChannelUpgradeTimeout + ) + + timeoutUpgrade := func() { + upgrade := path.EndpointA.GetProposedUpgrade() + upgrade.Timeout = channeltypes.NewTimeout(clienttypes.ZeroHeight(), 1) + path.EndpointA.SetChannelUpgrade(upgrade) + suite.Require().NoError(path.EndpointB.UpdateClient()) + } + + cases := []struct { + name string + malleate func() + expResult func(res *channeltypes.MsgChannelUpgradeTimeoutResponse, err error) + }{ + { + "success", + func() { + timeoutUpgrade() + + suite.Require().NoError(path.EndpointA.UpdateClient()) + + channelKey := host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + channelProof, proofHeight := path.EndpointB.QueryProof(channelKey) + + msg.ProofChannel = channelProof + msg.ProofHeight = proofHeight + }, + func(res *channeltypes.MsgChannelUpgradeTimeoutResponse, err error) { + suite.Require().NoError(err) + channel := path.EndpointA.GetChannel() + + suite.Require().Equalf(channeltypes.OPEN, channel.State, "channel state should be %s", channeltypes.OPEN.String()) + + _, found := path.EndpointA.Chain.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().False(found, "channel upgrade should be nil") + + suite.Require().NotNil(res) + }, + }, + { + "capability not found", + func() { + msg.ChannelId = ibctesting.InvalidID + }, + func(res *channeltypes.MsgChannelUpgradeTimeoutResponse, err error) { + suite.Require().Error(err) + suite.Require().ErrorIs(err, capabilitytypes.ErrCapabilityNotFound) + + channel := path.EndpointA.GetChannel() + suite.Require().Equalf(channeltypes.FLUSHCOMPLETE, channel.State, "channel state should be %s", channeltypes.OPEN) + suite.Require().Equal(uint64(1), channel.UpgradeSequence, "channel upgrade sequence should not incremented") + + _, found := path.EndpointA.Chain.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found, "channel upgrade should not be nil") + }, + }, + { + "core handler fails: invalid proof", + func() { + timeoutUpgrade() + + suite.Require().NoError(path.EndpointA.UpdateClient()) + + _, _, proofHeight := path.EndpointB.QueryChannelUpgradeProof() + + msg.ProofHeight = proofHeight + msg.ProofChannel = []byte("invalid proof") + }, + func(res *channeltypes.MsgChannelUpgradeTimeoutResponse, err error) { + suite.Require().Error(err) + suite.Require().ErrorIs(err, commitmenttypes.ErrInvalidProof) + + channel := path.EndpointA.GetChannel() + suite.Require().Equalf(channeltypes.FLUSHCOMPLETE, channel.State, "channel state should be %s", channeltypes.OPEN) + suite.Require().Equal(uint64(1), channel.UpgradeSequence, "channel upgrade sequence should not incremented") + + _, found := path.EndpointA.Chain.GetSimApp().IBCKeeper.ChannelKeeper.GetUpgrade(suite.chainA.GetContext(), path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + suite.Require().True(found, "channel upgrade should not be nil") + }, + }, + } + + for _, tc := range cases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path = ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + + suite.Require().NoError(path.EndpointA.ChanUpgradeInit()) + suite.Require().NoError(path.EndpointB.ChanUpgradeTry()) + suite.Require().NoError(path.EndpointA.ChanUpgradeAck()) + + channelKey := host.ChannelKey(path.EndpointA.ChannelConfig.PortID, path.EndpointA.ChannelID) + channelProof, proofHeight := path.EndpointB.QueryProof(channelKey) + + msg = &channeltypes.MsgChannelUpgradeTimeout{ + PortId: path.EndpointA.ChannelConfig.PortID, + ChannelId: path.EndpointA.ChannelID, + CounterpartyChannel: path.EndpointB.GetChannel(), + ProofChannel: channelProof, + ProofHeight: proofHeight, + Signer: suite.chainA.SenderAccount.GetAddress().String(), + } + + tc.malleate() + + ctx := suite.chainA.GetContext() + res, err := suite.chainA.GetSimApp().GetIBCKeeper().ChannelUpgradeTimeout(ctx, msg) + + tc.expResult(res, err) + }) + } +} + +// TestIBCSoftwareUpgrade tests the IBCSoftwareUpgrade rpc handler +func (suite *KeeperTestSuite) TestIBCSoftwareUpgrade() { + var msg *clienttypes.MsgIBCSoftwareUpgrade + testCases := []struct { + name string + malleate func() + expError error + }{ + { + "success: valid authority and client upgrade", + func() {}, + nil, + }, + { + "failure: invalid authority address", + func() { + msg.Signer = suite.chainA.SenderAccount.GetAddress().String() + }, + ibcerrors.ErrUnauthorized, + }, + { + "failure: invalid clientState", + func() { + msg.UpgradedClientState = nil + }, + clienttypes.ErrInvalidClientType, + }, + { + "failure: failed to schedule client upgrade", + func() { + msg.Plan.Height = 0 + }, + sdkerrors.ErrInvalidRequest, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + path := ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.SetupClients(path) + validAuthority := suite.chainA.App.GetIBCKeeper().GetAuthority() + plan := upgradetypes.Plan{ + Name: "upgrade IBC clients", + Height: 1000, + } + // update trusting period + clientState := path.EndpointB.GetClientState() + clientState.(*ibctm.ClientState).TrustingPeriod += 100 + + var err error + msg, err = clienttypes.NewMsgIBCSoftwareUpgrade( + validAuthority, + plan, + clientState, + ) + + suite.Require().NoError(err) + + tc.malleate() + + _, err = keeper.Keeper.IBCSoftwareUpgrade(*suite.chainA.App.GetIBCKeeper(), suite.chainA.GetContext(), msg) + + if tc.expError == nil { + suite.Require().NoError(err) + // upgrade plan is stored + storedPlan, err := suite.chainA.GetSimApp().UpgradeKeeper.GetUpgradePlan(suite.chainA.GetContext()) + suite.Require().NoError(err) + suite.Require().Equal(plan, storedPlan) + + // upgraded client state is stored + bz, err := suite.chainA.GetSimApp().UpgradeKeeper.GetUpgradedClient(suite.chainA.GetContext(), plan.Height) + suite.Require().NoError(err) + upgradedClientState, err := clienttypes.UnmarshalClientState(suite.chainA.App.AppCodec(), bz) + suite.Require().NoError(err) + suite.Require().Equal(clientState.ZeroCustomFields(), upgradedClientState) + } else { + suite.Require().True(errors.Is(err, tc.expError)) + } + }) + } +} + +// TestUpdateClientParams tests the UpdateClientParams rpc handler +func (suite *KeeperTestSuite) TestUpdateClientParams() { + signer := suite.chainA.App.GetIBCKeeper().GetAuthority() + testCases := []struct { + name string + msg *clienttypes.MsgUpdateParams + expPass bool + }{ + { + "success: valid signer and default params", + clienttypes.NewMsgUpdateParams(signer, clienttypes.DefaultParams()), + true, + }, + { + "failure: malformed signer address", + clienttypes.NewMsgUpdateParams(ibctesting.InvalidID, clienttypes.DefaultParams()), + false, + }, + { + "failure: empty signer address", + clienttypes.NewMsgUpdateParams("", clienttypes.DefaultParams()), + false, }, { "failure: whitespace signer address", @@ -1040,3 +2016,77 @@ func (suite *KeeperTestSuite) TestUpdateConnectionParams() { }) } } + +func (suite *KeeperTestSuite) TestPruneAcknowledgements() { + var msg *channeltypes.MsgPruneAcknowledgements + + testCases := []struct { + name string + malleate func() + expErr error + }{ + { + "success", + func() {}, + nil, + }, + { + "failure: core keeper function fails, pruning sequence end not found", + func() { + msg.PortId = "portidone" + }, + channeltypes.ErrPruningSequenceEndNotFound, + }, + } + + for _, tc := range testCases { + tc := tc + suite.Run(tc.name, func() { + suite.SetupTest() + + path := ibctesting.NewPath(suite.chainA, suite.chainB) + suite.coordinator.Setup(path) + + // configure the channel upgrade version on testing endpoints + path.EndpointA.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + path.EndpointB.ChannelConfig.ProposedUpgrade.Fields.Version = ibcmock.UpgradeVersion + + err := path.EndpointA.ChanUpgradeInit() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeTry() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeAck() + suite.Require().NoError(err) + + err = path.EndpointB.ChanUpgradeConfirm() + suite.Require().NoError(err) + + err = path.EndpointA.ChanUpgradeOpen() + suite.Require().NoError(err) + + err = path.EndpointA.UpdateClient() + suite.Require().NoError(err) + + msg = channeltypes.NewMsgPruneAcknowledgements( + path.EndpointA.ChannelConfig.PortID, + path.EndpointA.ChannelID, + 10, + suite.chainA.SenderAccount.GetAddress().String(), + ) + + tc.malleate() + + resp, err := suite.chainA.App.GetIBCKeeper().PruneAcknowledgements(suite.chainA.GetContext(), msg) + + if tc.expErr == nil { + suite.Require().NoError(err) + suite.Require().NotNil(resp) + } else { + suite.Require().Error(err) + suite.Require().Nil(resp) + } + }) + } +} diff --git a/modules/light-clients/09-localhost/client_state_test.go b/modules/light-clients/09-localhost/client_state_test.go index d1059fac5e2..7764289768d 100644 --- a/modules/light-clients/09-localhost/client_state_test.go +++ b/modules/light-clients/09-localhost/client_state_test.go @@ -281,7 +281,8 @@ func (suite *LocalhostTestSuite) TestVerifyMembership() { path = merklePath - channel.State = channeltypes.CLOSED // modify the channel before marshalling to value bz + // modify the channel before marshalling to value bz + channel.State = channeltypes.CLOSED value = suite.chain.Codec.MustMarshal(&channel) }, false, diff --git a/proto/ibc/applications/transfer/v1/transfer.proto b/proto/ibc/applications/transfer/v1/transfer.proto index 12914b7a4b8..7f77237621f 100644 --- a/proto/ibc/applications/transfer/v1/transfer.proto +++ b/proto/ibc/applications/transfer/v1/transfer.proto @@ -25,4 +25,4 @@ message Params { // receive_enabled enables or disables all cross-chain token transfers to this // chain. bool receive_enabled = 2; -} \ No newline at end of file +} diff --git a/proto/ibc/core/channel/v1/channel.proto b/proto/ibc/core/channel/v1/channel.proto index 9879a19df37..242ff8fdbdd 100644 --- a/proto/ibc/core/channel/v1/channel.proto +++ b/proto/ibc/core/channel/v1/channel.proto @@ -24,6 +24,9 @@ message Channel { repeated string connection_hops = 4; // opaque channel version, which is agreed upon during the handshake string version = 5; + // upgrade sequence indicates the latest upgrade attempt performed by this channel + // the value of 0 indicates the channel has never been upgraded + uint64 upgrade_sequence = 6; } // IdentifiedChannel defines a channel with additional port and channel @@ -46,10 +49,13 @@ message IdentifiedChannel { string port_id = 6; // channel identifier string channel_id = 7; + // upgrade sequence indicates the latest upgrade attempt performed by this channel + // the value of 0 indicates the channel has never been upgraded + uint64 upgrade_sequence = 8; } // State defines if a channel is in one of the following states: -// CLOSED, INIT, TRYOPEN, OPEN or UNINITIALIZED. +// CLOSED, INIT, TRYOPEN, OPEN, FLUSHING, FLUSHCOMPLETE or UNINITIALIZED. enum State { option (gogoproto.goproto_enum_prefix) = false; @@ -65,6 +71,10 @@ enum State { // A channel has been closed and can no longer be used to send or receive // packets. STATE_CLOSED = 4 [(gogoproto.enumvalue_customname) = "CLOSED"]; + // A channel has just accepted the upgrade handshake attempt and is flushing in-flight packets. + STATE_FLUSHING = 5 [(gogoproto.enumvalue_customname) = "FLUSHING"]; + // A channel has just completed flushing any in-flight packets. + STATE_FLUSHCOMPLETE = 6 [(gogoproto.enumvalue_customname) = "FLUSHCOMPLETE"]; } // Order defines if a channel is ORDERED or UNORDERED @@ -169,3 +179,9 @@ message Timeout { // block timestamp (in nanoseconds) after which the packet or upgrade times out uint64 timestamp = 2; } + +// Params defines the set of IBC channel parameters. +message Params { + // the relative timeout after which channel upgrades will time out. + Timeout upgrade_timeout = 1 [(gogoproto.nullable) = false]; +} diff --git a/proto/ibc/core/channel/v1/genesis.proto b/proto/ibc/core/channel/v1/genesis.proto index 382a8048d45..665b2b1562f 100644 --- a/proto/ibc/core/channel/v1/genesis.proto +++ b/proto/ibc/core/channel/v1/genesis.proto @@ -18,6 +18,7 @@ message GenesisState { repeated PacketSequence ack_sequences = 7 [(gogoproto.nullable) = false]; // the sequence for the next generated channel identifier uint64 next_channel_sequence = 8; + Params params = 9 [(gogoproto.nullable) = false]; } // PacketSequence defines the genesis type necessary to retrieve and store diff --git a/proto/ibc/core/channel/v1/query.proto b/proto/ibc/core/channel/v1/query.proto index 42c4caea7d0..f89d212736a 100644 --- a/proto/ibc/core/channel/v1/query.proto +++ b/proto/ibc/core/channel/v1/query.proto @@ -10,6 +10,7 @@ import "ibc/core/channel/v1/channel.proto"; import "google/api/annotations.proto"; import "google/protobuf/any.proto"; import "gogoproto/gogo.proto"; +import "ibc/core/channel/v1/upgrade.proto"; // Query provides defines the gRPC querier service service Query { @@ -104,6 +105,23 @@ service Query { option (google.api.http).get = "/ibc/core/channel/v1/channels/{channel_id}/" "ports/{port_id}/next_sequence_send"; } + + // UpgradeError returns the error receipt if the upgrade handshake failed. + rpc UpgradeError(QueryUpgradeErrorRequest) returns (QueryUpgradeErrorResponse) { + option (google.api.http).get = "/ibc/core/channel/v1/channels/{channel_id}/" + "ports/{port_id}/upgrade_error"; + } + + // Upgrade returns the upgrade for a given port and channel id. + rpc Upgrade(QueryUpgradeRequest) returns (QueryUpgradeResponse) { + option (google.api.http).get = "/ibc/core/channel/v1/channels/{channel_id}/" + "ports/{port_id}/upgrade"; + } + + // ChannelParams queries all parameters of the ibc channel submodule. + rpc ChannelParams(QueryChannelParamsRequest) returns (QueryChannelParamsResponse) { + option (google.api.http).get = "/ibc/core/channel/v1/params"; + } } // QueryChannelRequest is the request type for the Query/Channel RPC method @@ -370,7 +388,7 @@ message QueryNextSequenceReceiveRequest { string channel_id = 2; } -// QuerySequenceResponse is the request type for the +// QuerySequenceResponse is the response type for the // Query/QueryNextSequenceReceiveResponse RPC method message QueryNextSequenceReceiveResponse { // next sequence receive number @@ -399,4 +417,43 @@ message QueryNextSequenceSendResponse { bytes proof = 2; // height at which the proof was retrieved ibc.core.client.v1.Height proof_height = 3 [(gogoproto.nullable) = false]; +} + +// QueryUpgradeErrorRequest is the request type for the Query/QueryUpgradeError RPC method +message QueryUpgradeErrorRequest { + string port_id = 1; + string channel_id = 2; +} + +// QueryUpgradeErrorResponse is the response type for the Query/QueryUpgradeError RPC method +message QueryUpgradeErrorResponse { + ErrorReceipt error_receipt = 1 [(gogoproto.nullable) = false]; + // merkle proof of existence + bytes proof = 2; + // height at which the proof was retrieved + ibc.core.client.v1.Height proof_height = 3 [(gogoproto.nullable) = false]; +} + +// QueryUpgradeRequest is the request type for the QueryUpgradeRequest RPC method +message QueryUpgradeRequest { + string port_id = 1; + string channel_id = 2; +} + +// QueryUpgradeResponse is the response type for the QueryUpgradeResponse RPC method +message QueryUpgradeResponse { + Upgrade upgrade = 1 [(gogoproto.nullable) = false]; + // merkle proof of existence + bytes proof = 2; + // height at which the proof was retrieved + ibc.core.client.v1.Height proof_height = 3 [(gogoproto.nullable) = false]; +} + +// QueryChannelParamsRequest is the request type for the Query/ChannelParams RPC method. +message QueryChannelParamsRequest {} + +// QueryChannelParamsResponse is the response type for the Query/ChannelParams RPC method. +message QueryChannelParamsResponse { + // params defines the parameters of the module. + Params params = 1; } \ No newline at end of file diff --git a/proto/ibc/core/channel/v1/tx.proto b/proto/ibc/core/channel/v1/tx.proto index 4b9ad3d75cd..c87510c3570 100644 --- a/proto/ibc/core/channel/v1/tx.proto +++ b/proto/ibc/core/channel/v1/tx.proto @@ -5,9 +5,10 @@ package ibc.core.channel.v1; option go_package = "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types"; import "gogoproto/gogo.proto"; +import "cosmos/msg/v1/msg.proto"; import "ibc/core/client/v1/client.proto"; import "ibc/core/channel/v1/channel.proto"; -import "cosmos/msg/v1/msg.proto"; +import "ibc/core/channel/v1/upgrade.proto"; // Msg defines the ibc/channel Msg service. service Msg { @@ -43,6 +44,33 @@ service Msg { // Acknowledgement defines a rpc handler method for MsgAcknowledgement. rpc Acknowledgement(MsgAcknowledgement) returns (MsgAcknowledgementResponse); + + // ChannelUpgradeInit defines a rpc handler method for MsgChannelUpgradeInit. + rpc ChannelUpgradeInit(MsgChannelUpgradeInit) returns (MsgChannelUpgradeInitResponse); + + // ChannelUpgradeTry defines a rpc handler method for MsgChannelUpgradeTry. + rpc ChannelUpgradeTry(MsgChannelUpgradeTry) returns (MsgChannelUpgradeTryResponse); + + // ChannelUpgradeAck defines a rpc handler method for MsgChannelUpgradeAck. + rpc ChannelUpgradeAck(MsgChannelUpgradeAck) returns (MsgChannelUpgradeAckResponse); + + // ChannelUpgradeConfirm defines a rpc handler method for MsgChannelUpgradeConfirm. + rpc ChannelUpgradeConfirm(MsgChannelUpgradeConfirm) returns (MsgChannelUpgradeConfirmResponse); + + // ChannelUpgradeOpen defines a rpc handler method for MsgChannelUpgradeOpen. + rpc ChannelUpgradeOpen(MsgChannelUpgradeOpen) returns (MsgChannelUpgradeOpenResponse); + + // ChannelUpgradeTimeout defines a rpc handler method for MsgChannelUpgradeTimeout. + rpc ChannelUpgradeTimeout(MsgChannelUpgradeTimeout) returns (MsgChannelUpgradeTimeoutResponse); + + // ChannelUpgradeCancel defines a rpc handler method for MsgChannelUpgradeCancel. + rpc ChannelUpgradeCancel(MsgChannelUpgradeCancel) returns (MsgChannelUpgradeCancelResponse); + + // UpdateChannelParams defines a rpc handler method for MsgUpdateParams. + rpc UpdateChannelParams(MsgUpdateParams) returns (MsgUpdateParamsResponse); + + // PruneAcknowledgements defines a rpc handler method for MsgPruneAcknowledgements. + rpc PruneAcknowledgements(MsgPruneAcknowledgements) returns (MsgPruneAcknowledgementsResponse); } // ResponseResultType defines the possible outcomes of the execution of a message @@ -55,6 +83,8 @@ enum ResponseResultType { RESPONSE_RESULT_TYPE_NOOP = 1 [(gogoproto.enumvalue_customname) = "NOOP"]; // The message was executed successfully RESPONSE_RESULT_TYPE_SUCCESS = 2 [(gogoproto.enumvalue_customname) = "SUCCESS"]; + // The message was executed unsuccessfully + RESPONSE_RESULT_TYPE_FAILURE = 3 [(gogoproto.enumvalue_customname) = "FAILURE"]; } // MsgChannelOpenInit defines an sdk.Msg to initialize a channel handshake. It @@ -163,11 +193,12 @@ message MsgChannelCloseConfirm { option (gogoproto.goproto_getters) = false; - string port_id = 1; - string channel_id = 2; - bytes proof_init = 3; - ibc.core.client.v1.Height proof_height = 4 [(gogoproto.nullable) = false]; - string signer = 5; + string port_id = 1; + string channel_id = 2; + bytes proof_init = 3; + ibc.core.client.v1.Height proof_height = 4 [(gogoproto.nullable) = false]; + string signer = 5; + uint64 counterparty_upgrade_sequence = 6; } // MsgChannelCloseConfirmResponse defines the Msg/ChannelCloseConfirm response @@ -219,12 +250,13 @@ message MsgTimeoutOnClose { option (gogoproto.goproto_getters) = false; - Packet packet = 1 [(gogoproto.nullable) = false]; - bytes proof_unreceived = 2; - bytes proof_close = 3; - ibc.core.client.v1.Height proof_height = 4 [(gogoproto.nullable) = false]; - uint64 next_sequence_recv = 5; - string signer = 6; + Packet packet = 1 [(gogoproto.nullable) = false]; + bytes proof_unreceived = 2; + bytes proof_close = 3; + ibc.core.client.v1.Height proof_height = 4 [(gogoproto.nullable) = false]; + uint64 next_sequence_recv = 5; + string signer = 6; + uint64 counterparty_upgrade_sequence = 7; } // MsgTimeoutOnCloseResponse defines the Msg/TimeoutOnClose response type. @@ -253,3 +285,179 @@ message MsgAcknowledgementResponse { ResponseResultType result = 1; } + +// MsgChannelUpgradeInit defines the request type for the ChannelUpgradeInit rpc +message MsgChannelUpgradeInit { + option (cosmos.msg.v1.signer) = "signer"; + + option (gogoproto.goproto_getters) = false; + + string port_id = 1; + string channel_id = 2; + UpgradeFields fields = 3 [(gogoproto.nullable) = false]; + string signer = 4; +} + +// MsgChannelUpgradeInitResponse defines the MsgChannelUpgradeInit response type +message MsgChannelUpgradeInitResponse { + option (gogoproto.goproto_getters) = false; + + Upgrade upgrade = 1 [(gogoproto.nullable) = false]; + uint64 upgrade_sequence = 2; +} + +// MsgChannelUpgradeTry defines the request type for the ChannelUpgradeTry rpc +message MsgChannelUpgradeTry { + option (cosmos.msg.v1.signer) = "signer"; + + option (gogoproto.goproto_getters) = false; + + string port_id = 1; + string channel_id = 2; + repeated string proposed_upgrade_connection_hops = 3; + UpgradeFields counterparty_upgrade_fields = 4 [(gogoproto.nullable) = false]; + uint64 counterparty_upgrade_sequence = 5; + bytes proof_channel = 6; + bytes proof_upgrade = 7; + ibc.core.client.v1.Height proof_height = 8 [(gogoproto.nullable) = false]; + string signer = 9; +} + +// MsgChannelUpgradeTryResponse defines the MsgChannelUpgradeTry response type +message MsgChannelUpgradeTryResponse { + option (gogoproto.goproto_getters) = false; + + Upgrade upgrade = 1 [(gogoproto.nullable) = false]; + uint64 upgrade_sequence = 2; + ResponseResultType result = 3; +} + +// MsgChannelUpgradeAck defines the request type for the ChannelUpgradeAck rpc +message MsgChannelUpgradeAck { + option (cosmos.msg.v1.signer) = "signer"; + + option (gogoproto.goproto_getters) = false; + string port_id = 1; + string channel_id = 2; + Upgrade counterparty_upgrade = 3 [(gogoproto.nullable) = false]; + bytes proof_channel = 4; + bytes proof_upgrade = 5; + ibc.core.client.v1.Height proof_height = 6 [(gogoproto.nullable) = false]; + string signer = 7; +} + +// MsgChannelUpgradeAckResponse defines MsgChannelUpgradeAck response type +message MsgChannelUpgradeAckResponse { + option (gogoproto.goproto_getters) = false; + + ResponseResultType result = 1; +} + +// MsgChannelUpgradeConfirm defines the request type for the ChannelUpgradeConfirm rpc +message MsgChannelUpgradeConfirm { + option (cosmos.msg.v1.signer) = "signer"; + + option (gogoproto.goproto_getters) = false; + string port_id = 1; + string channel_id = 2; + State counterparty_channel_state = 3; + Upgrade counterparty_upgrade = 4 [(gogoproto.nullable) = false]; + bytes proof_channel = 5; + bytes proof_upgrade = 6; + ibc.core.client.v1.Height proof_height = 7 [(gogoproto.nullable) = false]; + string signer = 8; +} + +// MsgChannelUpgradeConfirmResponse defines MsgChannelUpgradeConfirm response type +message MsgChannelUpgradeConfirmResponse { + option (gogoproto.goproto_getters) = false; + + ResponseResultType result = 1; +} + +// MsgChannelUpgradeOpen defines the request type for the ChannelUpgradeOpen rpc +message MsgChannelUpgradeOpen { + option (cosmos.msg.v1.signer) = "signer"; + + option (gogoproto.goproto_getters) = false; + string port_id = 1; + string channel_id = 2; + State counterparty_channel_state = 3; + bytes proof_channel = 4; + ibc.core.client.v1.Height proof_height = 5 [(gogoproto.nullable) = false]; + string signer = 6; +} + +// MsgChannelUpgradeOpenResponse defines the MsgChannelUpgradeOpen response type +message MsgChannelUpgradeOpenResponse {} + +// MsgChannelUpgradeTimeout defines the request type for the ChannelUpgradeTimeout rpc +message MsgChannelUpgradeTimeout { + option (cosmos.msg.v1.signer) = "signer"; + + option (gogoproto.goproto_getters) = false; + + string port_id = 1; + string channel_id = 2; + Channel counterparty_channel = 3 [(gogoproto.nullable) = false]; + bytes proof_channel = 4; + ibc.core.client.v1.Height proof_height = 5 [(gogoproto.nullable) = false]; + string signer = 6; +} + +// MsgChannelUpgradeTimeoutRepsonse defines the MsgChannelUpgradeTimeout response type +message MsgChannelUpgradeTimeoutResponse {} + +// MsgChannelUpgradeCancel defines the request type for the ChannelUpgradeCancel rpc +message MsgChannelUpgradeCancel { + option (cosmos.msg.v1.signer) = "signer"; + + option (gogoproto.goproto_getters) = false; + + string port_id = 1; + string channel_id = 2; + ErrorReceipt error_receipt = 3 [(gogoproto.nullable) = false]; + bytes proof_error_receipt = 4; + ibc.core.client.v1.Height proof_height = 5 [(gogoproto.nullable) = false]; + string signer = 6; +} + +// MsgChannelUpgradeCancelResponse defines the MsgChannelUpgradeCancel response type +message MsgChannelUpgradeCancelResponse {} + +// MsgUpdateParams is the MsgUpdateParams request type. +message MsgUpdateParams { + option (cosmos.msg.v1.signer) = "authority"; + + option (gogoproto.goproto_getters) = false; + + // authority is the address that controls the module (defaults to x/gov unless overwritten). + string authority = 1; + + // params defines the channel parameters to update. + // + // NOTE: All parameters must be supplied. + Params params = 2 [(gogoproto.nullable) = false]; +} + +// MsgUpdateParamsResponse defines the MsgUpdateParams response type. +message MsgUpdateParamsResponse {} + +// MsgPruneAcknowledgements defines the request type for the PruneAcknowledgements rpc. +message MsgPruneAcknowledgements { + option (cosmos.msg.v1.signer) = "signer"; + option (gogoproto.goproto_getters) = false; + + string port_id = 1; + string channel_id = 2; + uint64 limit = 3; + string signer = 4; +} + +// MsgPruneAcknowledgementsResponse defines the response type for the PruneAcknowledgements rpc. +message MsgPruneAcknowledgementsResponse { + // Number of sequences pruned (includes both packet acknowledgements and packet receipts where appropriate). + uint64 total_pruned_sequences = 1; + // Number of sequences left after pruning. + uint64 total_remaining_sequences = 2; +} \ No newline at end of file diff --git a/proto/ibc/core/channel/v1/upgrade.proto b/proto/ibc/core/channel/v1/upgrade.proto new file mode 100644 index 00000000000..81530ed2a28 --- /dev/null +++ b/proto/ibc/core/channel/v1/upgrade.proto @@ -0,0 +1,43 @@ +syntax = "proto3"; + +package ibc.core.channel.v1; + +option go_package = "github.com/cosmos/ibc-go/v8/modules/core/04-channel/types"; + +import "gogoproto/gogo.proto"; +import "ibc/core/channel/v1/channel.proto"; + +// Upgrade is a verifiable type which contains the relevant information +// for an attempted upgrade. It provides the proposed changes to the channel +// end, the timeout for this upgrade attempt and the next packet sequence +// which allows the counterparty to efficiently know the highest sequence it has received. +// The next sequence send is used for pruning and upgrading from unordered to ordered channels. +message Upgrade { + option (gogoproto.goproto_getters) = false; + + UpgradeFields fields = 1 [(gogoproto.nullable) = false]; + Timeout timeout = 2 [(gogoproto.nullable) = false]; + uint64 next_sequence_send = 3; +} + +// UpgradeFields are the fields in a channel end which may be changed +// during a channel upgrade. +message UpgradeFields { + option (gogoproto.goproto_getters) = false; + + Order ordering = 1; + repeated string connection_hops = 2; + string version = 3; +} + +// ErrorReceipt defines a type which encapsulates the upgrade sequence and error associated with the +// upgrade handshake failure. When a channel upgrade handshake is aborted both chains are expected to increment to the +// next sequence. +message ErrorReceipt { + option (gogoproto.goproto_getters) = false; + + // the channel upgrade sequence + uint64 sequence = 1; + // the error message detailing the cause of failure + string message = 2; +} diff --git a/testing/chain.go b/testing/chain.go index f7d672b7470..ccaebff7475 100644 --- a/testing/chain.go +++ b/testing/chain.go @@ -344,6 +344,14 @@ func (chain *TestChain) SendMsgs(msgs ...sdk.Msg) (*abci.ExecTxResult, error) { // ensure the chain has the latest time chain.Coordinator.UpdateTimeForChain(chain) + // increment acc sequence regardless of success or failure tx execution + defer func() { + err := chain.SenderAccount.SetSequence(chain.SenderAccount.GetSequence() + 1) + if err != nil { + panic(err) + } + }() + resp, err := simapp.SignAndDeliver( chain.TB, chain.TxConfig, @@ -370,12 +378,6 @@ func (chain *TestChain) SendMsgs(msgs ...sdk.Msg) (*abci.ExecTxResult, error) { return txResult, fmt.Errorf("%s/%d: %q", txResult.Codespace, txResult.Code, txResult.Log) } - // increment sequence for successful transaction execution - err = chain.SenderAccount.SetSequence(chain.SenderAccount.GetSequence() + 1) - if err != nil { - return nil, err - } - chain.Coordinator.IncrementTime() return txResult, nil @@ -641,3 +643,10 @@ func (chain *TestChain) GetChannelCapability(portID, channelID string) *capabili func (chain *TestChain) GetTimeoutHeight() clienttypes.Height { return clienttypes.NewHeight(clienttypes.ParseChainID(chain.ChainID), uint64(chain.GetContext().BlockHeight())+100) } + +// DeleteKey deletes the specified key from the ibc store. +func (chain *TestChain) DeleteKey(key []byte) { + storeKey := chain.GetSimApp().GetKey(exported.StoreKey) + kvStore := chain.GetContext().KVStore(storeKey) + kvStore.Delete(key) +} diff --git a/testing/config.go b/testing/config.go index 46dae7899d9..4c1cba8005b 100644 --- a/testing/config.go +++ b/testing/config.go @@ -47,9 +47,10 @@ func NewConnectionConfig() *ConnectionConfig { } type ChannelConfig struct { - PortID string - Version string - Order channeltypes.Order + PortID string + Version string + Order channeltypes.Order + ProposedUpgrade channeltypes.Upgrade } func NewChannelConfig() *ChannelConfig { diff --git a/testing/endpoint.go b/testing/endpoint.go index 76ba78fe77e..fcf5099562f 100644 --- a/testing/endpoint.go +++ b/testing/endpoint.go @@ -7,6 +7,8 @@ import ( "github.com/stretchr/testify/require" "github.com/cosmos/cosmos-sdk/baseapp" + sdk "github.com/cosmos/cosmos-sdk/types" + govtypesv1 "github.com/cosmos/cosmos-sdk/x/gov/types/v1" abci "github.com/cometbft/cometbft/abci/types" @@ -561,11 +563,202 @@ func (endpoint *Endpoint) TimeoutOnClose(packet channeltypes.Packet) error { timeoutOnCloseMsg := channeltypes.NewMsgTimeoutOnClose( packet, nextSeqRecv, proof, proofClosed, proofHeight, endpoint.Chain.SenderAccount.GetAddress().String(), + endpoint.Counterparty.GetChannel().UpgradeSequence, ) return endpoint.Chain.sendMsgs(timeoutOnCloseMsg) } +// QueryChannelUpgradeProof returns all the proofs necessary to execute UpgradeTry/UpgradeAck/UpgradeOpen. +// It returns the proof for the channel on the endpoint's chain, the proof for the upgrade attempt on the +// endpoint's chain, and the height at which the proof was queried. +func (endpoint *Endpoint) QueryChannelUpgradeProof() ([]byte, []byte, clienttypes.Height) { + channelKey := host.ChannelKey(endpoint.ChannelConfig.PortID, endpoint.ChannelID) + proofChannel, height := endpoint.QueryProof(channelKey) + + upgradeKey := host.ChannelUpgradeKey(endpoint.ChannelConfig.PortID, endpoint.ChannelID) + proofUpgrade, _ := endpoint.QueryProof(upgradeKey) + + return proofChannel, proofUpgrade, height +} + +// ChanUpgradeInit sends a MsgChannelUpgradeInit on the associated endpoint. +// A default upgrade proposal is used with overrides from the ProposedUpgrade +// in the channel config, and submitted via governance proposal +func (endpoint *Endpoint) ChanUpgradeInit() error { + upgrade := endpoint.GetProposedUpgrade() + + // create upgrade init message via gov proposal and submit the proposal + msg := channeltypes.NewMsgChannelUpgradeInit( + endpoint.ChannelConfig.PortID, + endpoint.ChannelID, + upgrade.Fields, + endpoint.Chain.GetSimApp().IBCKeeper.GetAuthority(), + ) + + proposal, err := govtypesv1.NewMsgSubmitProposal( + []sdk.Msg{msg}, + sdk.NewCoins(sdk.NewCoin(sdk.DefaultBondDenom, govtypesv1.DefaultMinDepositTokens)), + endpoint.Chain.SenderAccount.GetAddress().String(), + endpoint.ChannelID, + "upgrade-init", + fmt.Sprintf("gov proposal for initialising channel upgrade: %s", endpoint.ChannelID), + false, + ) + require.NoError(endpoint.Chain.TB, err) + + var proposalID uint64 + res, err := endpoint.Chain.SendMsgs(proposal) + if err != nil { + return err + } + + proposalID, err = ParseProposalIDFromEvents(res.Events) + require.NoError(endpoint.Chain.TB, err) + + return VoteAndCheckProposalStatus(endpoint, proposalID) +} + +// ChanUpgradeTry sends a MsgChannelUpgradeTry on the associated endpoint. +func (endpoint *Endpoint) ChanUpgradeTry() error { + err := endpoint.UpdateClient() + require.NoError(endpoint.Chain.TB, err) + + upgrade := endpoint.GetProposedUpgrade() + proofChannel, proofUpgrade, height := endpoint.Counterparty.QueryChannelUpgradeProof() + + counterpartyUpgrade, found := endpoint.Counterparty.Chain.App.GetIBCKeeper().ChannelKeeper.GetUpgrade(endpoint.Counterparty.Chain.GetContext(), endpoint.Counterparty.ChannelConfig.PortID, endpoint.Counterparty.ChannelID) + require.True(endpoint.Chain.TB, found) + + if !found { + return fmt.Errorf("could not find upgrade for channel %s", endpoint.ChannelID) + } + + msg := channeltypes.NewMsgChannelUpgradeTry( + endpoint.ChannelConfig.PortID, + endpoint.ChannelID, + upgrade.Fields.ConnectionHops, + counterpartyUpgrade.Fields, + endpoint.Counterparty.GetChannel().UpgradeSequence, + proofChannel, + proofUpgrade, + height, + endpoint.Chain.SenderAccount.GetAddress().String(), + ) + + return endpoint.Chain.sendMsgs(msg) +} + +// ChanUpgradeAck sends a MsgChannelUpgradeAck to the associated endpoint. +func (endpoint *Endpoint) ChanUpgradeAck() error { + err := endpoint.UpdateClient() + require.NoError(endpoint.Chain.TB, err) + + proofChannel, proofUpgrade, height := endpoint.Counterparty.QueryChannelUpgradeProof() + + counterpartyUpgrade, found := endpoint.Counterparty.Chain.App.GetIBCKeeper().ChannelKeeper.GetUpgrade(endpoint.Counterparty.Chain.GetContext(), endpoint.Counterparty.ChannelConfig.PortID, endpoint.Counterparty.ChannelID) + require.True(endpoint.Chain.TB, found) + + msg := channeltypes.NewMsgChannelUpgradeAck( + endpoint.ChannelConfig.PortID, + endpoint.ChannelID, + counterpartyUpgrade, + proofChannel, + proofUpgrade, + height, + endpoint.Chain.SenderAccount.GetAddress().String(), + ) + + return endpoint.Chain.sendMsgs(msg) +} + +// ChanUpgradeConfirm sends a MsgChannelUpgradeConfirm to the associated endpoint. +func (endpoint *Endpoint) ChanUpgradeConfirm() error { + err := endpoint.UpdateClient() + require.NoError(endpoint.Chain.TB, err) + + proofChannel, proofUpgrade, height := endpoint.Counterparty.QueryChannelUpgradeProof() + + counterpartyUpgrade, found := endpoint.Counterparty.Chain.App.GetIBCKeeper().ChannelKeeper.GetUpgrade(endpoint.Counterparty.Chain.GetContext(), endpoint.Counterparty.ChannelConfig.PortID, endpoint.Counterparty.ChannelID) + require.True(endpoint.Chain.TB, found) + + msg := channeltypes.NewMsgChannelUpgradeConfirm( + endpoint.ChannelConfig.PortID, + endpoint.ChannelID, + endpoint.Counterparty.GetChannel().State, + counterpartyUpgrade, + proofChannel, + proofUpgrade, + height, + endpoint.Chain.SenderAccount.GetAddress().String(), + ) + + return endpoint.Chain.sendMsgs(msg) +} + +// ChanUpgradeOpen sends a MsgChannelUpgradeOpen to the associated endpoint. +func (endpoint *Endpoint) ChanUpgradeOpen() error { + err := endpoint.UpdateClient() + require.NoError(endpoint.Chain.TB, err) + + channelKey := host.ChannelKey(endpoint.Counterparty.ChannelConfig.PortID, endpoint.Counterparty.ChannelID) + proofChannel, height := endpoint.Counterparty.QueryProof(channelKey) + + msg := channeltypes.NewMsgChannelUpgradeOpen( + endpoint.ChannelConfig.PortID, + endpoint.ChannelID, + endpoint.Counterparty.GetChannel().State, + proofChannel, + height, + endpoint.Chain.SenderAccount.GetAddress().String(), + ) + + return endpoint.Chain.sendMsgs(msg) +} + +// ChanUpgradeTimeout sends a MsgChannelUpgradeTimeout to the associated endpoint. +func (endpoint *Endpoint) ChanUpgradeTimeout() error { + err := endpoint.UpdateClient() + require.NoError(endpoint.Chain.TB, err) + + channelKey := host.ChannelKey(endpoint.Counterparty.ChannelConfig.PortID, endpoint.Counterparty.ChannelID) + proofChannel, height := endpoint.Counterparty.Chain.QueryProof(channelKey) + + msg := channeltypes.NewMsgChannelUpgradeTimeout( + endpoint.ChannelConfig.PortID, + endpoint.ChannelID, + endpoint.Counterparty.GetChannel(), + proofChannel, + height, + endpoint.Chain.SenderAccount.GetAddress().String(), + ) + + return endpoint.Chain.sendMsgs(msg) +} + +// ChanUpgradeCancel sends a MsgChannelUpgradeCancel to the associated endpoint. +func (endpoint *Endpoint) ChanUpgradeCancel() error { + err := endpoint.UpdateClient() + require.NoError(endpoint.Chain.TB, err) + + errorReceiptKey := host.ChannelUpgradeErrorKey(endpoint.Counterparty.ChannelConfig.PortID, endpoint.Counterparty.ChannelID) + proofErrorReceipt, height := endpoint.Counterparty.Chain.QueryProof(errorReceiptKey) + + errorReceipt, found := endpoint.Counterparty.Chain.App.GetIBCKeeper().ChannelKeeper.GetUpgradeErrorReceipt(endpoint.Counterparty.Chain.GetContext(), endpoint.Counterparty.ChannelConfig.PortID, endpoint.Counterparty.ChannelID) + require.True(endpoint.Chain.TB, found) + + msg := channeltypes.NewMsgChannelUpgradeCancel( + endpoint.ChannelConfig.PortID, + endpoint.ChannelID, + errorReceipt, + proofErrorReceipt, + height, + endpoint.Chain.SenderAccount.GetAddress().String(), + ) + + return endpoint.Chain.sendMsgs(msg) +} + // SetChannelState sets a channel state func (endpoint *Endpoint) SetChannelState(state channeltypes.State) error { channel := endpoint.GetChannel() @@ -631,6 +824,25 @@ func (endpoint *Endpoint) SetChannel(channel channeltypes.Channel) { endpoint.Chain.App.GetIBCKeeper().ChannelKeeper.SetChannel(endpoint.Chain.GetContext(), endpoint.ChannelConfig.PortID, endpoint.ChannelID, channel) } +// GetChannelUpgrade retrieves an IBC Channel Upgrade for the endpoint. The upgrade +// is expected to exist otherwise testing will fail. +func (endpoint *Endpoint) GetChannelUpgrade() channeltypes.Upgrade { + upgrade, found := endpoint.Chain.App.GetIBCKeeper().ChannelKeeper.GetUpgrade(endpoint.Chain.GetContext(), endpoint.ChannelConfig.PortID, endpoint.ChannelID) + require.True(endpoint.Chain.TB, found) + + return upgrade +} + +// SetChannelUpgrade sets the channel upgrade for this endpoint. +func (endpoint *Endpoint) SetChannelUpgrade(upgrade channeltypes.Upgrade) { + endpoint.Chain.App.GetIBCKeeper().ChannelKeeper.SetUpgrade(endpoint.Chain.GetContext(), endpoint.ChannelConfig.PortID, endpoint.ChannelID, upgrade) +} + +// SetChannelCounterpartyUpgrade sets the channel counterparty upgrade for this endpoint. +func (endpoint *Endpoint) SetChannelCounterpartyUpgrade(upgrade channeltypes.Upgrade) { + endpoint.Chain.App.GetIBCKeeper().ChannelKeeper.SetCounterpartyUpgrade(endpoint.Chain.GetContext(), endpoint.ChannelConfig.PortID, endpoint.ChannelID, upgrade) +} + // QueryClientStateProof performs and abci query for a client stat associated // with this endpoint and returns the ClientState along with the proof. func (endpoint *Endpoint) QueryClientStateProof() (exported.ClientState, []byte) { @@ -642,3 +854,40 @@ func (endpoint *Endpoint) QueryClientStateProof() (exported.ClientState, []byte) return clientState, proofClient } + +// GetProposedUpgrade returns a valid upgrade which can be used for UpgradeInit and UpgradeTry. +// By default, the endpoint's existing channel fields will be used for the upgrade fields and +// a sane default timeout will be used by querying the counterparty's latest height. +// If any non-empty values are specified in the ChannelConfig's ProposedUpgrade, +// those values will be used in the returned upgrade. +func (endpoint *Endpoint) GetProposedUpgrade() channeltypes.Upgrade { + // create a default upgrade + upgrade := channeltypes.Upgrade{ + Fields: channeltypes.UpgradeFields{ + Ordering: endpoint.ChannelConfig.Order, + ConnectionHops: []string{endpoint.ConnectionID}, + Version: endpoint.ChannelConfig.Version, + }, + Timeout: channeltypes.NewTimeout(endpoint.Counterparty.Chain.GetTimeoutHeight(), 0), + NextSequenceSend: 0, + } + + override := endpoint.ChannelConfig.ProposedUpgrade + if override.Timeout.IsValid() { + upgrade.Timeout = override.Timeout + } + + if override.Fields.Ordering != channeltypes.NONE { + upgrade.Fields.Ordering = override.Fields.Ordering + } + + if override.Fields.Version != "" { + upgrade.Fields.Version = override.Fields.Version + } + + if len(override.Fields.ConnectionHops) != 0 { + upgrade.Fields.ConnectionHops = override.Fields.ConnectionHops + } + + return upgrade +} diff --git a/testing/events.go b/testing/events.go index c0dcb7acc4c..9a9dac0dd9f 100644 --- a/testing/events.go +++ b/testing/events.go @@ -154,6 +154,19 @@ func ParseAckFromEvents(events []abci.Event) ([]byte, error) { return nil, fmt.Errorf("acknowledgement event attribute not found") } +// ParseProposalIDFromEvents parses events emitted from MsgSubmitProposal and returns proposalID +func ParseProposalIDFromEvents(events []abci.Event) (uint64, error) { + for _, event := range events { + for _, attribute := range event.Attributes { + if attribute.Key == "proposal_id" { + return strconv.ParseUint(attribute.Value, 10, 64) + } + } + } + + return 0, fmt.Errorf("proposalID event attribute not found") +} + // AssertEventsLegacy asserts that expected events are present in the actual events. // Expected map needs to be a subset of actual events to pass. func AssertEventsLegacy( diff --git a/testing/mock/ibc_app.go b/testing/mock/ibc_app.go index 72b6d4da100..a49a834ef96 100644 --- a/testing/mock/ibc_app.go +++ b/testing/mock/ibc_app.go @@ -85,6 +85,44 @@ type IBCApp struct { packet channeltypes.Packet, relayer sdk.AccAddress, ) error + + OnChanUpgradeInit func( + ctx sdk.Context, + portID, channelID string, + order channeltypes.Order, + connectionHops []string, + version string, + ) (string, error) + + OnChanUpgradeTry func( + ctx sdk.Context, + portID, channelID string, + order channeltypes.Order, + connectionHops []string, + counterpartyVersion string, + ) (string, error) + + OnChanUpgradeAck func( + ctx sdk.Context, + portID, + channelID, + counterpartyVersion string, + ) error + + OnChanUpgradeOpen func( + ctx sdk.Context, + portID, + channelID string, + order channeltypes.Order, + connectionHops []string, + version string, + ) + + OnChanUpgradeRestore func( + ctx sdk.Context, + portID, + channelID string, + ) } // NewIBCApp returns a IBCApp. An empty PortID indicates the mock app doesn't bind/claim ports. diff --git a/testing/mock/ibc_module.go b/testing/mock/ibc_module.go index 5a01fa2cb47..c0a153918bf 100644 --- a/testing/mock/ibc_module.go +++ b/testing/mock/ibc_module.go @@ -19,6 +19,7 @@ import ( var ( _ porttypes.IBCModule = (*IBCModule)(nil) _ porttypes.PacketDataUnmarshaler = (*IBCModule)(nil) + _ porttypes.UpgradableModule = (*IBCModule)(nil) ) // applicationCallbackError is a custom error type that will be unique for testing purposes. @@ -176,6 +177,47 @@ func (im IBCModule) OnTimeoutPacket(ctx sdk.Context, packet channeltypes.Packet, return nil } +// OnChanUpgradeInit implements the IBCModule interface +func (im IBCModule) OnChanUpgradeInit(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) (string, error) { + if im.IBCApp.OnChanUpgradeInit != nil { + return im.IBCApp.OnChanUpgradeInit(ctx, portID, channelID, order, connectionHops, version) + } + + return version, nil +} + +// OnChanUpgradeTry implements the IBCModule interface +func (im IBCModule) OnChanUpgradeTry(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, counterpartyVersion string) (string, error) { + if im.IBCApp.OnChanUpgradeTry != nil { + return im.IBCApp.OnChanUpgradeTry(ctx, portID, channelID, order, connectionHops, counterpartyVersion) + } + + return counterpartyVersion, nil +} + +// OnChanUpgradeAck implements the IBCModule interface +func (im IBCModule) OnChanUpgradeAck(ctx sdk.Context, portID, channelID, counterpartyVersion string) error { + if im.IBCApp.OnChanUpgradeAck != nil { + return im.IBCApp.OnChanUpgradeAck(ctx, portID, channelID, counterpartyVersion) + } + + return nil +} + +// OnChanUpgradeOpen implements the IBCModule interface +func (im IBCModule) OnChanUpgradeOpen(ctx sdk.Context, portID, channelID string, order channeltypes.Order, connectionHops []string, version string) { + if im.IBCApp.OnChanUpgradeOpen != nil { + im.IBCApp.OnChanUpgradeOpen(ctx, portID, channelID, order, connectionHops, version) + } +} + +// OnChanUpgradeRestore implements the IBCModule interface +func (im IBCModule) OnChanUpgradeRestore(ctx sdk.Context, portID, channelID string) { + if im.IBCApp.OnChanUpgradeRestore != nil { + im.IBCApp.OnChanUpgradeRestore(ctx, portID, channelID) + } +} + // UnmarshalPacketData returns the MockPacketData. This function implements the optional // PacketDataUnmarshaler interface required for ADR 008 support. func (IBCModule) UnmarshalPacketData(bz []byte) (interface{}, error) { diff --git a/testing/mock/mock.go b/testing/mock/mock.go index 96da67a25c7..86de269f48b 100644 --- a/testing/mock/mock.go +++ b/testing/mock/mock.go @@ -43,6 +43,7 @@ var ( MockRecvCanaryCapabilityName = "mock receive canary capability name" MockAckCanaryCapabilityName = "mock acknowledgement canary capability name" MockTimeoutCanaryCapabilityName = "mock timeout canary capability name" + UpgradeVersion = fmt.Sprintf("%s-v2", Version) // MockApplicationCallbackError should be returned when an application callback should fail. It is possible to // test that this error was returned using ErrorIs. MockApplicationCallbackError error = &applicationCallbackError{} diff --git a/testing/simapp/app.go b/testing/simapp/app.go index 754353c6ba2..7c63fc97340 100644 --- a/testing/simapp/app.go +++ b/testing/simapp/app.go @@ -214,6 +214,7 @@ type SimApp struct { // make IBC modules public for test purposes // these modules are never directly routed to by the IBC Router + IBCMockModule ibcmock.IBCModule ICAAuthModule ibcmock.IBCModule FeeMockModule ibcmock.IBCModule @@ -485,6 +486,7 @@ func NewSimApp( // The mock module is used for testing IBC mockIBCModule := ibcmock.NewIBCModule(&mockModule, ibcmock.NewIBCApp(ibcmock.ModuleName, scopedIBCMockKeeper)) + app.IBCMockModule = mockIBCModule ibcRouter.AddRoute(ibcmock.ModuleName, mockIBCModule) // Create Transfer Stack diff --git a/testing/solomachine.go b/testing/solomachine.go index 2293f285bec..81eb087f6bc 100644 --- a/testing/solomachine.go +++ b/testing/solomachine.go @@ -358,6 +358,7 @@ func (solo *Solomachine) ChanCloseConfirm(chain *TestChain, portID, channelID st proofInit, clienttypes.ZeroHeight(), chain.SenderAccount.GetAddress().String(), + 0, // use default value for channel that hasn't undergone an upgrade ) res, err := chain.SendMsgs(msgChanCloseConfirm) @@ -449,6 +450,7 @@ func (solo *Solomachine) TimeoutPacketOnClose(chain *TestChain, packet channelty proofClosed, clienttypes.ZeroHeight(), chain.SenderAccount.GetAddress().String(), + 0, // use default value for channel that hasn't undergone an upgrade ) res, err := chain.SendMsgs(msgTimeout) diff --git a/testing/utils.go b/testing/utils.go index bc023cec6fe..773c39b420d 100644 --- a/testing/utils.go +++ b/testing/utils.go @@ -9,6 +9,7 @@ import ( "github.com/cosmos/cosmos-sdk/codec" sdk "github.com/cosmos/cosmos-sdk/types" + govtypesv1 "github.com/cosmos/cosmos-sdk/x/gov/types/v1" abci "github.com/cometbft/cometbft/abci/types" cmttypes "github.com/cometbft/cometbft/types" @@ -29,6 +30,29 @@ func ApplyValSetChanges(tb testing.TB, valSet *cmttypes.ValidatorSet, valUpdates return newVals } +// VoteAndCheckProposalStatus votes on a gov proposal, checks if the proposal has passed, and returns an error if it has not with the failure reason. +func VoteAndCheckProposalStatus(endpoint *Endpoint, proposalID uint64) error { + // vote on proposal + ctx := endpoint.Chain.GetContext() + require.NoError(endpoint.Chain.TB, endpoint.Chain.GetSimApp().GovKeeper.AddVote(ctx, proposalID, endpoint.Chain.SenderAccount.GetAddress(), govtypesv1.NewNonSplitVoteOption(govtypesv1.OptionYes), "")) + + // fast forward the chain context to end the voting period + params, err := endpoint.Chain.GetSimApp().GovKeeper.Params.Get(ctx) + require.NoError(endpoint.Chain.TB, err) + + endpoint.Chain.Coordinator.IncrementTimeBy(*params.VotingPeriod + *params.MaxDepositPeriod) + endpoint.Chain.NextBlock() + + // check if proposal passed or failed on msg execution + // we need to grab the context again since the previous context is no longer valid as the chain header time has been incremented + p, err := endpoint.Chain.GetSimApp().GovKeeper.Proposals.Get(endpoint.Chain.GetContext(), proposalID) + require.NoError(endpoint.Chain.TB, err) + if p.Status != govtypesv1.StatusPassed { + return fmt.Errorf("proposal failed: %s", p.FailedReason) + } + return nil +} + // GenerateString generates a random string of the given length in bytes func GenerateString(length uint) string { bytes := make([]byte, length)