fix: check store keys length before accessing (#9639)

* check store keys length before accessing

* check store keys length in all modules

* add changelog

* refactoring

* address review comments

* remove commented lines

* small fixes

* address review comments

* fix failing tests

* add godocs
This commit is contained in:
likhita-809 2021-07-08 16:59:12 +05:30 committed by GitHub
parent c5ce800bc5
commit d13d488d9b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
13 changed files with 101 additions and 83 deletions

View File

@ -75,6 +75,7 @@ Ref: https://keepachangelog.com/en/1.0.0/
### Bug Fixes ### Bug Fixes
* [\#9639](https://github.com/cosmos/cosmos-sdk/pull/9639) Check store keys length before accessing them by making sure that `key` is of length `m+1` (for `key[n:m]`)
* (types) [\#9627](https://github.com/cosmos/cosmos-sdk/pull/9627) Fix nil pointer panic on `NewBigIntFromInt` * (types) [\#9627](https://github.com/cosmos/cosmos-sdk/pull/9627) Fix nil pointer panic on `NewBigIntFromInt`
* (x/genutil) [\#9574](https://github.com/cosmos/cosmos-sdk/pull/9575) Actually use the `gentx` client tx flags (like `--keyring-dir`) * (x/genutil) [\#9574](https://github.com/cosmos/cosmos-sdk/pull/9575) Actually use the `gentx` client tx flags (like `--keyring-dir`)
* (x/distribution) [\#9599](https://github.com/cosmos/cosmos-sdk/pull/9599) Withdraw rewards event now includes a value attribute even if there are 0 rewards (due to situations like 100% commission). * (x/distribution) [\#9599](https://github.com/cosmos/cosmos-sdk/pull/9599) Withdraw rewards event now includes a value attribute even if there are 0 rewards (due to situations like 100% commission).

17
types/kv/helpers.go Normal file
View File

@ -0,0 +1,17 @@
package kv
import "fmt"
// AssertKeyAtLeastLength panics when store key length is less than the given length.
func AssertKeyAtLeastLength(bz []byte, length int) {
if len(bz) < length {
panic(fmt.Sprintf("expected key of length at least %d, got %d", length, len(bz)))
}
}
// AssertKeyLength panics when store key length is not equal to the given length.
func AssertKeyLength(bz []byte, length int) {
if len(bz) != length {
panic(fmt.Sprintf("unexpected key length; got: %d, expected: %d", len(bz), length))
}
}

View File

@ -4,6 +4,7 @@ import (
"github.com/cosmos/cosmos-sdk/internal/conv" "github.com/cosmos/cosmos-sdk/internal/conv"
sdk "github.com/cosmos/cosmos-sdk/types" sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/types/address" "github.com/cosmos/cosmos-sdk/types/address"
"github.com/cosmos/cosmos-sdk/types/kv"
"github.com/cosmos/cosmos-sdk/x/authz" "github.com/cosmos/cosmos-sdk/x/authz"
) )
@ -38,9 +39,12 @@ func grantStoreKey(grantee sdk.AccAddress, granter sdk.AccAddress, msgType strin
func addressesFromGrantStoreKey(key []byte) (granterAddr, granteeAddr sdk.AccAddress) { func addressesFromGrantStoreKey(key []byte) (granterAddr, granteeAddr sdk.AccAddress) {
// key is of format: // key is of format:
// 0x01<granterAddressLen (1 Byte)><granterAddress_Bytes><granteeAddressLen (1 Byte)><granteeAddress_Bytes><msgType_Bytes> // 0x01<granterAddressLen (1 Byte)><granterAddress_Bytes><granteeAddressLen (1 Byte)><granteeAddress_Bytes><msgType_Bytes>
kv.AssertKeyAtLeastLength(key, 2)
granterAddrLen := key[1] // remove prefix key granterAddrLen := key[1] // remove prefix key
kv.AssertKeyAtLeastLength(key, int(3+granterAddrLen))
granterAddr = sdk.AccAddress(key[2 : 2+granterAddrLen]) granterAddr = sdk.AccAddress(key[2 : 2+granterAddrLen])
granteeAddrLen := int(key[2+granterAddrLen]) granteeAddrLen := int(key[2+granterAddrLen])
kv.AssertKeyAtLeastLength(key, 4+int(granterAddrLen+byte(granteeAddrLen)))
granteeAddr = sdk.AccAddress(key[3+granterAddrLen : 3+granterAddrLen+byte(granteeAddrLen)]) granteeAddr = sdk.AccAddress(key[3+granterAddrLen : 3+granterAddrLen+byte(granteeAddrLen)])
return granterAddr, granteeAddr return granterAddr, granteeAddr

View File

@ -3,9 +3,8 @@
package v040 package v040
import ( import (
"fmt"
sdk "github.com/cosmos/cosmos-sdk/types" sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/types/kv"
v040auth "github.com/cosmos/cosmos-sdk/x/auth/migrations/v040" v040auth "github.com/cosmos/cosmos-sdk/x/auth/migrations/v040"
) )
@ -40,10 +39,8 @@ func DenomMetadataKey(denom string) []byte {
// store. The key must not contain the perfix BalancesPrefix as the prefix store // store. The key must not contain the perfix BalancesPrefix as the prefix store
// iterator discards the actual prefix. // iterator discards the actual prefix.
func AddressFromBalancesStore(key []byte) sdk.AccAddress { func AddressFromBalancesStore(key []byte) sdk.AccAddress {
kv.AssertKeyAtLeastLength(key, 1+v040auth.AddrLen)
addr := key[:v040auth.AddrLen] addr := key[:v040auth.AddrLen]
if len(addr) != v040auth.AddrLen { kv.AssertKeyLength(addr, v040auth.AddrLen)
panic(fmt.Sprintf("unexpected account address key length; got: %d, expected: %d", len(addr), v040auth.AddrLen))
}
return sdk.AccAddress(addr) return sdk.AccAddress(addr)
} }

View File

@ -3,6 +3,7 @@ package types
import ( import (
sdk "github.com/cosmos/cosmos-sdk/types" sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/types/address" "github.com/cosmos/cosmos-sdk/types/address"
"github.com/cosmos/cosmos-sdk/types/kv"
) )
const ( const (
@ -43,6 +44,7 @@ func AddressFromBalancesStore(key []byte) (sdk.AccAddress, error) {
if len(key) == 0 { if len(key) == 0 {
return nil, ErrInvalidKey return nil, ErrInvalidKey
} }
kv.AssertKeyAtLeastLength(key, 1)
addrLen := key[0] addrLen := key[0]
bound := int(addrLen) bound := int(addrLen)
if len(key)-1 < bound { if len(key)-1 < bound {

View File

@ -6,6 +6,7 @@ import (
"encoding/binary" "encoding/binary"
sdk "github.com/cosmos/cosmos-sdk/types" sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/types/kv"
v040auth "github.com/cosmos/cosmos-sdk/x/auth/migrations/v040" v040auth "github.com/cosmos/cosmos-sdk/x/auth/migrations/v040"
) )
@ -58,78 +59,68 @@ var (
// gets an address from a validator's outstanding rewards key // gets an address from a validator's outstanding rewards key
func GetValidatorOutstandingRewardsAddress(key []byte) (valAddr sdk.ValAddress) { func GetValidatorOutstandingRewardsAddress(key []byte) (valAddr sdk.ValAddress) {
kv.AssertKeyAtLeastLength(key, 2)
addr := key[1:] addr := key[1:]
if len(addr) != v040auth.AddrLen { kv.AssertKeyLength(addr, v040auth.AddrLen)
panic("unexpected key length")
}
return sdk.ValAddress(addr) return sdk.ValAddress(addr)
} }
// gets an address from a delegator's withdraw info key // gets an address from a delegator's withdraw info key
func GetDelegatorWithdrawInfoAddress(key []byte) (delAddr sdk.AccAddress) { func GetDelegatorWithdrawInfoAddress(key []byte) (delAddr sdk.AccAddress) {
kv.AssertKeyAtLeastLength(key, 2)
addr := key[1:] addr := key[1:]
if len(addr) != v040auth.AddrLen { kv.AssertKeyLength(addr, v040auth.AddrLen)
panic("unexpected key length")
}
return sdk.AccAddress(addr) return sdk.AccAddress(addr)
} }
// gets the addresses from a delegator starting info key // gets the addresses from a delegator starting info key
func GetDelegatorStartingInfoAddresses(key []byte) (valAddr sdk.ValAddress, delAddr sdk.AccAddress) { func GetDelegatorStartingInfoAddresses(key []byte) (valAddr sdk.ValAddress, delAddr sdk.AccAddress) {
kv.AssertKeyAtLeastLength(key, 2+v040auth.AddrLen)
addr := key[1 : 1+v040auth.AddrLen] addr := key[1 : 1+v040auth.AddrLen]
if len(addr) != v040auth.AddrLen { kv.AssertKeyLength(addr, v040auth.AddrLen)
panic("unexpected key length")
}
valAddr = sdk.ValAddress(addr) valAddr = sdk.ValAddress(addr)
addr = key[1+v040auth.AddrLen:] addr = key[1+v040auth.AddrLen:]
if len(addr) != v040auth.AddrLen { kv.AssertKeyLength(addr, v040auth.AddrLen)
panic("unexpected key length")
}
delAddr = sdk.AccAddress(addr) delAddr = sdk.AccAddress(addr)
return return
} }
// gets the address & period from a validator's historical rewards key // gets the address & period from a validator's historical rewards key
func GetValidatorHistoricalRewardsAddressPeriod(key []byte) (valAddr sdk.ValAddress, period uint64) { func GetValidatorHistoricalRewardsAddressPeriod(key []byte) (valAddr sdk.ValAddress, period uint64) {
kv.AssertKeyAtLeastLength(key, 2+v040auth.AddrLen)
addr := key[1 : 1+v040auth.AddrLen] addr := key[1 : 1+v040auth.AddrLen]
if len(addr) != v040auth.AddrLen { kv.AssertKeyLength(addr, v040auth.AddrLen)
panic("unexpected key length")
}
valAddr = sdk.ValAddress(addr) valAddr = sdk.ValAddress(addr)
b := key[1+v040auth.AddrLen:] b := key[1+v040auth.AddrLen:]
if len(b) != 8 { kv.AssertKeyLength(addr, 8)
panic("unexpected key length")
}
period = binary.LittleEndian.Uint64(b) period = binary.LittleEndian.Uint64(b)
return return
} }
// gets the address from a validator's current rewards key // gets the address from a validator's current rewards key
func GetValidatorCurrentRewardsAddress(key []byte) (valAddr sdk.ValAddress) { func GetValidatorCurrentRewardsAddress(key []byte) (valAddr sdk.ValAddress) {
kv.AssertKeyAtLeastLength(key, 2)
addr := key[1:] addr := key[1:]
if len(addr) != v040auth.AddrLen { kv.AssertKeyLength(addr, v040auth.AddrLen)
panic("unexpected key length")
}
return sdk.ValAddress(addr) return sdk.ValAddress(addr)
} }
// gets the address from a validator's accumulated commission key // gets the address from a validator's accumulated commission key
func GetValidatorAccumulatedCommissionAddress(key []byte) (valAddr sdk.ValAddress) { func GetValidatorAccumulatedCommissionAddress(key []byte) (valAddr sdk.ValAddress) {
kv.AssertKeyAtLeastLength(key, 2)
addr := key[1:] addr := key[1:]
if len(addr) != v040auth.AddrLen { kv.AssertKeyLength(addr, v040auth.AddrLen)
panic("unexpected key length")
}
return sdk.ValAddress(addr) return sdk.ValAddress(addr)
} }
// gets the height from a validator's slash event key // gets the height from a validator's slash event key
func GetValidatorSlashEventAddressHeight(key []byte) (valAddr sdk.ValAddress, height uint64) { func GetValidatorSlashEventAddressHeight(key []byte) (valAddr sdk.ValAddress, height uint64) {
kv.AssertKeyAtLeastLength(key, 2+v040auth.AddrLen)
addr := key[1 : 1+v040auth.AddrLen] addr := key[1 : 1+v040auth.AddrLen]
if len(addr) != v040auth.AddrLen { kv.AssertKeyLength(addr, v040auth.AddrLen)
panic("unexpected key length")
}
valAddr = sdk.ValAddress(addr) valAddr = sdk.ValAddress(addr)
startB := 1 + v040auth.AddrLen startB := 1 + v040auth.AddrLen
kv.AssertKeyAtLeastLength(key, startB+9)
b := key[startB : startB+8] // the next 8 bytes represent the height b := key[startB : startB+8] // the next 8 bytes represent the height
height = binary.BigEndian.Uint64(b) height = binary.BigEndian.Uint64(b)
return return

View File

@ -5,6 +5,7 @@ import (
sdk "github.com/cosmos/cosmos-sdk/types" sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/types/address" "github.com/cosmos/cosmos-sdk/types/address"
"github.com/cosmos/cosmos-sdk/types/kv"
) )
const ( const (
@ -60,10 +61,9 @@ func GetValidatorOutstandingRewardsAddress(key []byte) (valAddr sdk.ValAddress)
// 0x02<valAddrLen (1 Byte)><valAddr_Bytes> // 0x02<valAddrLen (1 Byte)><valAddr_Bytes>
// Remove prefix and address length. // Remove prefix and address length.
kv.AssertKeyAtLeastLength(key, 3)
addr := key[2:] addr := key[2:]
if len(addr) != int(key[1]) { kv.AssertKeyLength(addr, int(key[1]))
panic("unexpected key length")
}
return sdk.ValAddress(addr) return sdk.ValAddress(addr)
} }
@ -74,10 +74,9 @@ func GetDelegatorWithdrawInfoAddress(key []byte) (delAddr sdk.AccAddress) {
// 0x03<accAddrLen (1 Byte)><accAddr_Bytes> // 0x03<accAddrLen (1 Byte)><accAddr_Bytes>
// Remove prefix and address length. // Remove prefix and address length.
kv.AssertKeyAtLeastLength(key, 3)
addr := key[2:] addr := key[2:]
if len(addr) != int(key[1]) { kv.AssertKeyLength(addr, int(key[1]))
panic("unexpected key length")
}
return sdk.AccAddress(addr) return sdk.AccAddress(addr)
} }
@ -86,13 +85,14 @@ func GetDelegatorWithdrawInfoAddress(key []byte) (delAddr sdk.AccAddress) {
func GetDelegatorStartingInfoAddresses(key []byte) (valAddr sdk.ValAddress, delAddr sdk.AccAddress) { func GetDelegatorStartingInfoAddresses(key []byte) (valAddr sdk.ValAddress, delAddr sdk.AccAddress) {
// key is in the format: // key is in the format:
// 0x04<valAddrLen (1 Byte)><valAddr_Bytes><accAddrLen (1 Byte)><accAddr_Bytes> // 0x04<valAddrLen (1 Byte)><valAddr_Bytes><accAddrLen (1 Byte)><accAddr_Bytes>
kv.AssertKeyAtLeastLength(key, 2)
valAddrLen := int(key[1]) valAddrLen := int(key[1])
kv.AssertKeyAtLeastLength(key, 3+valAddrLen)
valAddr = sdk.ValAddress(key[2 : 2+valAddrLen]) valAddr = sdk.ValAddress(key[2 : 2+valAddrLen])
delAddrLen := int(key[2+valAddrLen]) delAddrLen := int(key[2+valAddrLen])
kv.AssertKeyAtLeastLength(key, 4+valAddrLen)
delAddr = sdk.AccAddress(key[3+valAddrLen:]) delAddr = sdk.AccAddress(key[3+valAddrLen:])
if len(delAddr.Bytes()) != delAddrLen { kv.AssertKeyLength(delAddr.Bytes(), delAddrLen)
panic("unexpected key length")
}
return return
} }
@ -101,12 +101,12 @@ func GetDelegatorStartingInfoAddresses(key []byte) (valAddr sdk.ValAddress, delA
func GetValidatorHistoricalRewardsAddressPeriod(key []byte) (valAddr sdk.ValAddress, period uint64) { func GetValidatorHistoricalRewardsAddressPeriod(key []byte) (valAddr sdk.ValAddress, period uint64) {
// key is in the format: // key is in the format:
// 0x05<valAddrLen (1 Byte)><valAddr_Bytes><period_Bytes> // 0x05<valAddrLen (1 Byte)><valAddr_Bytes><period_Bytes>
kv.AssertKeyAtLeastLength(key, 2)
valAddrLen := int(key[1]) valAddrLen := int(key[1])
kv.AssertKeyAtLeastLength(key, 3+valAddrLen)
valAddr = sdk.ValAddress(key[2 : 2+valAddrLen]) valAddr = sdk.ValAddress(key[2 : 2+valAddrLen])
b := key[2+valAddrLen:] b := key[2+valAddrLen:]
if len(b) != 8 { kv.AssertKeyLength(b, 8)
panic("unexpected key length")
}
period = binary.LittleEndian.Uint64(b) period = binary.LittleEndian.Uint64(b)
return return
} }
@ -117,10 +117,9 @@ func GetValidatorCurrentRewardsAddress(key []byte) (valAddr sdk.ValAddress) {
// 0x06<valAddrLen (1 Byte)><valAddr_Bytes>: ValidatorCurrentRewards // 0x06<valAddrLen (1 Byte)><valAddr_Bytes>: ValidatorCurrentRewards
// Remove prefix and address length. // Remove prefix and address length.
kv.AssertKeyAtLeastLength(key, 3)
addr := key[2:] addr := key[2:]
if len(addr) != int(key[1]) { kv.AssertKeyLength(addr, int(key[1]))
panic("unexpected key length")
}
return sdk.ValAddress(addr) return sdk.ValAddress(addr)
} }
@ -131,10 +130,9 @@ func GetValidatorAccumulatedCommissionAddress(key []byte) (valAddr sdk.ValAddres
// 0x07<valAddrLen (1 Byte)><valAddr_Bytes>: ValidatorCurrentRewards // 0x07<valAddrLen (1 Byte)><valAddr_Bytes>: ValidatorCurrentRewards
// Remove prefix and address length. // Remove prefix and address length.
kv.AssertKeyAtLeastLength(key, 3)
addr := key[2:] addr := key[2:]
if len(addr) != int(key[1]) { kv.AssertKeyLength(addr, int(key[1]))
panic("unexpected key length")
}
return sdk.ValAddress(addr) return sdk.ValAddress(addr)
} }
@ -143,9 +141,12 @@ func GetValidatorAccumulatedCommissionAddress(key []byte) (valAddr sdk.ValAddres
func GetValidatorSlashEventAddressHeight(key []byte) (valAddr sdk.ValAddress, height uint64) { func GetValidatorSlashEventAddressHeight(key []byte) (valAddr sdk.ValAddress, height uint64) {
// key is in the format: // key is in the format:
// 0x08<valAddrLen (1 Byte)><valAddr_Bytes><height>: ValidatorSlashEvent // 0x08<valAddrLen (1 Byte)><valAddr_Bytes><height>: ValidatorSlashEvent
kv.AssertKeyAtLeastLength(key, 2)
valAddrLen := int(key[1]) valAddrLen := int(key[1])
kv.AssertKeyAtLeastLength(key, 3+valAddrLen)
valAddr = key[2 : 2+valAddrLen] valAddr = key[2 : 2+valAddrLen]
startB := 2 + valAddrLen startB := 2 + valAddrLen
kv.AssertKeyAtLeastLength(key, startB+9)
b := key[startB : startB+8] // the next 8 bytes represent the height b := key[startB : startB+8] // the next 8 bytes represent the height
height = binary.BigEndian.Uint64(b) height = binary.BigEndian.Uint64(b)
return return

View File

@ -4,10 +4,10 @@ package v040
import ( import (
"encoding/binary" "encoding/binary"
"fmt"
"time" "time"
sdk "github.com/cosmos/cosmos-sdk/types" sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/types/kv"
v040auth "github.com/cosmos/cosmos-sdk/x/auth/migrations/v040" v040auth "github.com/cosmos/cosmos-sdk/x/auth/migrations/v040"
) )
@ -113,9 +113,7 @@ func VoteKey(proposalID uint64, voterAddr sdk.AccAddress) []byte {
// SplitProposalKey split the proposal key and returns the proposal id // SplitProposalKey split the proposal key and returns the proposal id
func SplitProposalKey(key []byte) (proposalID uint64) { func SplitProposalKey(key []byte) (proposalID uint64) {
if len(key[1:]) != 8 { kv.AssertKeyLength(key[1:], 8)
panic(fmt.Sprintf("unexpected key length (%d ≠ 8)", len(key[1:])))
}
return GetProposalIDFromBytes(key[1:]) return GetProposalIDFromBytes(key[1:])
} }
@ -143,9 +141,7 @@ func SplitKeyVote(key []byte) (proposalID uint64, voterAddr sdk.AccAddress) {
// private functions // private functions
func splitKeyWithTime(key []byte) (proposalID uint64, endTime time.Time) { func splitKeyWithTime(key []byte) (proposalID uint64, endTime time.Time) {
if len(key[1:]) != 8+lenTime { kv.AssertKeyLength(key[1:], 8+lenTime)
panic(fmt.Sprintf("unexpected key length (%d ≠ %d)", len(key[1:]), lenTime+8))
}
endTime, err := sdk.ParseTimeBytes(key[1 : 1+lenTime]) endTime, err := sdk.ParseTimeBytes(key[1 : 1+lenTime])
if err != nil { if err != nil {
@ -157,10 +153,9 @@ func splitKeyWithTime(key []byte) (proposalID uint64, endTime time.Time) {
} }
func splitKeyWithAddress(key []byte) (proposalID uint64, addr sdk.AccAddress) { func splitKeyWithAddress(key []byte) (proposalID uint64, addr sdk.AccAddress) {
if len(key[1:]) != 8+v040auth.AddrLen { kv.AssertKeyLength(key[1:], 8+v040auth.AddrLen)
panic(fmt.Sprintf("unexpected key length (%d ≠ %d)", len(key), 8+v040auth.AddrLen))
}
kv.AssertKeyAtLeastLength(key, 10)
proposalID = GetProposalIDFromBytes(key[1:9]) proposalID = GetProposalIDFromBytes(key[1:9])
addr = sdk.AccAddress(key[9:]) addr = sdk.AccAddress(key[9:])
return return

View File

@ -2,11 +2,11 @@ package types
import ( import (
"encoding/binary" "encoding/binary"
"fmt"
"time" "time"
sdk "github.com/cosmos/cosmos-sdk/types" sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/types/address" "github.com/cosmos/cosmos-sdk/types/address"
"github.com/cosmos/cosmos-sdk/types/kv"
) )
const ( const (
@ -111,9 +111,7 @@ func VoteKey(proposalID uint64, voterAddr sdk.AccAddress) []byte {
// SplitProposalKey split the proposal key and returns the proposal id // SplitProposalKey split the proposal key and returns the proposal id
func SplitProposalKey(key []byte) (proposalID uint64) { func SplitProposalKey(key []byte) (proposalID uint64) {
if len(key[1:]) != 8 { kv.AssertKeyLength(key[1:], 8)
panic(fmt.Sprintf("unexpected key length (%d ≠ 8)", len(key[1:])))
}
return GetProposalIDFromBytes(key[1:]) return GetProposalIDFromBytes(key[1:])
} }
@ -141,9 +139,7 @@ func SplitKeyVote(key []byte) (proposalID uint64, voterAddr sdk.AccAddress) {
// private functions // private functions
func splitKeyWithTime(key []byte) (proposalID uint64, endTime time.Time) { func splitKeyWithTime(key []byte) (proposalID uint64, endTime time.Time) {
if len(key[1:]) != 8+lenTime { kv.AssertKeyLength(key[1:], 8+lenTime)
panic(fmt.Sprintf("unexpected key length (%d ≠ %d)", len(key[1:]), lenTime+8))
}
endTime, err := sdk.ParseTimeBytes(key[1 : 1+lenTime]) endTime, err := sdk.ParseTimeBytes(key[1 : 1+lenTime])
if err != nil { if err != nil {
@ -157,7 +153,9 @@ func splitKeyWithTime(key []byte) (proposalID uint64, endTime time.Time) {
func splitKeyWithAddress(key []byte) (proposalID uint64, addr sdk.AccAddress) { func splitKeyWithAddress(key []byte) (proposalID uint64, addr sdk.AccAddress) {
// Both Vote and Deposit store keys are of format: // Both Vote and Deposit store keys are of format:
// <prefix (1 Byte)><proposalID (8 bytes)><addrLen (1 Byte)><addr_Bytes> // <prefix (1 Byte)><proposalID (8 bytes)><addrLen (1 Byte)><addr_Bytes>
kv.AssertKeyAtLeastLength(key, 10)
proposalID = GetProposalIDFromBytes(key[1:9]) proposalID = GetProposalIDFromBytes(key[1:9])
kv.AssertKeyAtLeastLength(key, 11)
addr = sdk.AccAddress(key[10:]) addr = sdk.AccAddress(key[10:])
return return
} }

View File

@ -6,6 +6,7 @@ import (
"encoding/binary" "encoding/binary"
sdk "github.com/cosmos/cosmos-sdk/types" sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/types/kv"
v040auth "github.com/cosmos/cosmos-sdk/x/auth/migrations/v040" v040auth "github.com/cosmos/cosmos-sdk/x/auth/migrations/v040"
) )
@ -44,10 +45,9 @@ func ValidatorSigningInfoKey(v sdk.ConsAddress) []byte {
// ValidatorSigningInfoAddress - extract the address from a validator signing info key // ValidatorSigningInfoAddress - extract the address from a validator signing info key
func ValidatorSigningInfoAddress(key []byte) (v sdk.ConsAddress) { func ValidatorSigningInfoAddress(key []byte) (v sdk.ConsAddress) {
kv.AssertKeyAtLeastLength(key, 2)
addr := key[1:] addr := key[1:]
if len(addr) != v040auth.AddrLen { kv.AssertKeyLength(addr, v040auth.AddrLen)
panic("unexpected key length")
}
return sdk.ConsAddress(addr) return sdk.ConsAddress(addr)
} }

View File

@ -5,6 +5,7 @@ import (
sdk "github.com/cosmos/cosmos-sdk/types" sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/types/address" "github.com/cosmos/cosmos-sdk/types/address"
"github.com/cosmos/cosmos-sdk/types/kv"
) )
const ( const (
@ -43,6 +44,7 @@ func ValidatorSigningInfoKey(v sdk.ConsAddress) []byte {
// ValidatorSigningInfoAddress - extract the address from a validator signing info key // ValidatorSigningInfoAddress - extract the address from a validator signing info key
func ValidatorSigningInfoAddress(key []byte) (v sdk.ConsAddress) { func ValidatorSigningInfoAddress(key []byte) (v sdk.ConsAddress) {
// Remove prefix and address length. // Remove prefix and address length.
kv.AssertKeyAtLeastLength(key, 3)
addr := key[2:] addr := key[2:]
return sdk.ConsAddress(addr) return sdk.ConsAddress(addr)

View File

@ -10,6 +10,7 @@ import (
"time" "time"
sdk "github.com/cosmos/cosmos-sdk/types" sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/types/kv"
v040auth "github.com/cosmos/cosmos-sdk/x/auth/migrations/v040" v040auth "github.com/cosmos/cosmos-sdk/x/auth/migrations/v040"
"github.com/cosmos/cosmos-sdk/x/staking/types" "github.com/cosmos/cosmos-sdk/x/staking/types"
) )
@ -66,6 +67,7 @@ func GetValidatorByConsAddrKey(addr sdk.ConsAddress) []byte {
// Get the validator operator address from LastValidatorPowerKey // Get the validator operator address from LastValidatorPowerKey
func AddressFromLastValidatorPowerKey(key []byte) []byte { func AddressFromLastValidatorPowerKey(key []byte) []byte {
kv.AssertKeyAtLeastLength(key, 2)
return key[1:] // remove prefix bytes return key[1:] // remove prefix bytes
} }
@ -112,9 +114,7 @@ func GetLastValidatorPowerKey(operator sdk.ValAddress) []byte {
// parse the validators operator address from power rank key // parse the validators operator address from power rank key
func ParseValidatorPowerRankKey(key []byte) (operAddr []byte) { func ParseValidatorPowerRankKey(key []byte) (operAddr []byte) {
powerBytesLen := 8 powerBytesLen := 8
if len(key) != 1+powerBytesLen+v040auth.AddrLen { kv.AssertKeyLength(key, 1+powerBytesLen+v040auth.AddrLen)
panic("Invalid validator power rank key length")
}
operAddr = sdk.CopyBytes(key[powerBytesLen+1:]) operAddr = sdk.CopyBytes(key[powerBytesLen+1:])
@ -196,11 +196,11 @@ func GetUBDByValIndexKey(delAddr sdk.AccAddress, valAddr sdk.ValAddress) []byte
// rearranges the ValIndexKey to get the UBDKey // rearranges the ValIndexKey to get the UBDKey
func GetUBDKeyFromValIndexKey(indexKey []byte) []byte { func GetUBDKeyFromValIndexKey(indexKey []byte) []byte {
kv.AssertKeyAtLeastLength(indexKey, 2)
addrs := indexKey[1:] // remove prefix bytes addrs := indexKey[1:] // remove prefix bytes
if len(addrs) != 2*v040auth.AddrLen { kv.AssertKeyLength(addrs, 2*v040auth.AddrLen)
panic("unexpected key length")
}
kv.AssertKeyAtLeastLength(addrs, v040auth.AddrLen+1)
valAddr := addrs[:v040auth.AddrLen] valAddr := addrs[:v040auth.AddrLen]
delAddr := addrs[v040auth.AddrLen:] delAddr := addrs[v040auth.AddrLen:]
@ -268,9 +268,7 @@ func GetREDByValDstIndexKey(delAddr sdk.AccAddress, valSrcAddr, valDstAddr sdk.V
// GetREDKeyFromValSrcIndexKey rearranges the ValSrcIndexKey to get the REDKey // GetREDKeyFromValSrcIndexKey rearranges the ValSrcIndexKey to get the REDKey
func GetREDKeyFromValSrcIndexKey(indexKey []byte) []byte { func GetREDKeyFromValSrcIndexKey(indexKey []byte) []byte {
// note that first byte is prefix byte // note that first byte is prefix byte
if len(indexKey) != 3*v040auth.AddrLen+1 { kv.AssertKeyLength(indexKey, 3*v040auth.AddrLen+1)
panic("unexpected key length")
}
valSrcAddr := indexKey[1 : v040auth.AddrLen+1] valSrcAddr := indexKey[1 : v040auth.AddrLen+1]
delAddr := indexKey[v040auth.AddrLen+1 : 2*v040auth.AddrLen+1] delAddr := indexKey[v040auth.AddrLen+1 : 2*v040auth.AddrLen+1]
@ -282,9 +280,7 @@ func GetREDKeyFromValSrcIndexKey(indexKey []byte) []byte {
// GetREDKeyFromValDstIndexKey rearranges the ValDstIndexKey to get the REDKey // GetREDKeyFromValDstIndexKey rearranges the ValDstIndexKey to get the REDKey
func GetREDKeyFromValDstIndexKey(indexKey []byte) []byte { func GetREDKeyFromValDstIndexKey(indexKey []byte) []byte {
// note that first byte is prefix byte // note that first byte is prefix byte
if len(indexKey) != 3*v040auth.AddrLen+1 { kv.AssertKeyLength(indexKey, 3*v040auth.AddrLen+1)
panic("unexpected key length")
}
valDstAddr := indexKey[1 : v040auth.AddrLen+1] valDstAddr := indexKey[1 : v040auth.AddrLen+1]
delAddr := indexKey[v040auth.AddrLen+1 : 2*v040auth.AddrLen+1] delAddr := indexKey[v040auth.AddrLen+1 : 2*v040auth.AddrLen+1]

View File

@ -9,6 +9,7 @@ import (
sdk "github.com/cosmos/cosmos-sdk/types" sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/types/address" "github.com/cosmos/cosmos-sdk/types/address"
"github.com/cosmos/cosmos-sdk/types/kv"
) )
const ( const (
@ -63,11 +64,13 @@ func GetValidatorByConsAddrKey(addr sdk.ConsAddress) []byte {
// AddressFromValidatorsKey creates the validator operator address from ValidatorsKey // AddressFromValidatorsKey creates the validator operator address from ValidatorsKey
func AddressFromValidatorsKey(key []byte) []byte { func AddressFromValidatorsKey(key []byte) []byte {
kv.AssertKeyAtLeastLength(key, 3)
return key[2:] // remove prefix bytes and address length return key[2:] // remove prefix bytes and address length
} }
// AddressFromLastValidatorPowerKey creates the validator operator address from LastValidatorPowerKey // AddressFromLastValidatorPowerKey creates the validator operator address from LastValidatorPowerKey
func AddressFromLastValidatorPowerKey(key []byte) []byte { func AddressFromLastValidatorPowerKey(key []byte) []byte {
kv.AssertKeyAtLeastLength(key, 3)
return key[2:] // remove prefix bytes and address length return key[2:] // remove prefix bytes and address length
} }
@ -196,10 +199,13 @@ func GetUBDByValIndexKey(delAddr sdk.AccAddress, valAddr sdk.ValAddress) []byte
// GetUBDKeyFromValIndexKey rearranges the ValIndexKey to get the UBDKey // GetUBDKeyFromValIndexKey rearranges the ValIndexKey to get the UBDKey
func GetUBDKeyFromValIndexKey(indexKey []byte) []byte { func GetUBDKeyFromValIndexKey(indexKey []byte) []byte {
kv.AssertKeyAtLeastLength(indexKey, 2)
addrs := indexKey[1:] // remove prefix bytes addrs := indexKey[1:] // remove prefix bytes
valAddrLen := addrs[0] valAddrLen := addrs[0]
kv.AssertKeyAtLeastLength(addrs, 2+int(valAddrLen))
valAddr := addrs[1 : 1+valAddrLen] valAddr := addrs[1 : 1+valAddrLen]
kv.AssertKeyAtLeastLength(addrs, 3+int(valAddrLen))
delAddr := addrs[valAddrLen+2:] delAddr := addrs[valAddrLen+2:]
return GetUBDKey(delAddr, valAddr) return GetUBDKey(delAddr, valAddr)
@ -273,12 +279,16 @@ func GetREDByValDstIndexKey(delAddr sdk.AccAddress, valSrcAddr, valDstAddr sdk.V
// GetREDKeyFromValSrcIndexKey rearranges the ValSrcIndexKey to get the REDKey // GetREDKeyFromValSrcIndexKey rearranges the ValSrcIndexKey to get the REDKey
func GetREDKeyFromValSrcIndexKey(indexKey []byte) []byte { func GetREDKeyFromValSrcIndexKey(indexKey []byte) []byte {
// note that first byte is prefix byte, which we remove // note that first byte is prefix byte, which we remove
kv.AssertKeyAtLeastLength(indexKey, 2)
addrs := indexKey[1:] addrs := indexKey[1:]
valSrcAddrLen := addrs[0] valSrcAddrLen := addrs[0]
kv.AssertKeyAtLeastLength(addrs, int(valSrcAddrLen)+2)
valSrcAddr := addrs[1 : valSrcAddrLen+1] valSrcAddr := addrs[1 : valSrcAddrLen+1]
delAddrLen := addrs[valSrcAddrLen+1] delAddrLen := addrs[valSrcAddrLen+1]
kv.AssertKeyAtLeastLength(addrs, int(valSrcAddrLen)+int(delAddrLen)+2)
delAddr := addrs[valSrcAddrLen+2 : valSrcAddrLen+2+delAddrLen] delAddr := addrs[valSrcAddrLen+2 : valSrcAddrLen+2+delAddrLen]
kv.AssertKeyAtLeastLength(addrs, int(valSrcAddrLen)+int(delAddrLen)+4)
valDstAddr := addrs[valSrcAddrLen+delAddrLen+3:] valDstAddr := addrs[valSrcAddrLen+delAddrLen+3:]
return GetREDKey(delAddr, valSrcAddr, valDstAddr) return GetREDKey(delAddr, valSrcAddr, valDstAddr)
@ -287,12 +297,16 @@ func GetREDKeyFromValSrcIndexKey(indexKey []byte) []byte {
// GetREDKeyFromValDstIndexKey rearranges the ValDstIndexKey to get the REDKey // GetREDKeyFromValDstIndexKey rearranges the ValDstIndexKey to get the REDKey
func GetREDKeyFromValDstIndexKey(indexKey []byte) []byte { func GetREDKeyFromValDstIndexKey(indexKey []byte) []byte {
// note that first byte is prefix byte, which we remove // note that first byte is prefix byte, which we remove
kv.AssertKeyAtLeastLength(indexKey, 2)
addrs := indexKey[1:] addrs := indexKey[1:]
valDstAddrLen := addrs[0] valDstAddrLen := addrs[0]
kv.AssertKeyAtLeastLength(addrs, int(valDstAddrLen)+2)
valDstAddr := addrs[1 : valDstAddrLen+1] valDstAddr := addrs[1 : valDstAddrLen+1]
delAddrLen := addrs[valDstAddrLen+1] delAddrLen := addrs[valDstAddrLen+1]
kv.AssertKeyAtLeastLength(addrs, int(valDstAddrLen)+int(delAddrLen)+3)
delAddr := addrs[valDstAddrLen+2 : valDstAddrLen+2+delAddrLen] delAddr := addrs[valDstAddrLen+2 : valDstAddrLen+2+delAddrLen]
kv.AssertKeyAtLeastLength(addrs, int(valDstAddrLen)+int(delAddrLen)+4)
valSrcAddr := addrs[valDstAddrLen+delAddrLen+3:] valSrcAddr := addrs[valDstAddrLen+delAddrLen+3:]
return GetREDKey(delAddr, valSrcAddr, valDstAddr) return GetREDKey(delAddr, valSrcAddr, valDstAddr)