github.com/keybase/client/go@v0.0.0-20240309051027-028f7c731f8b/merkletree2/config.go (about) 1 package merkletree2 2 3 import "fmt" 4 5 // Config defines the shape of the MerkleTree. 6 type Config struct { 7 // An encoder is used to compute hashes in this configuration, and also 8 // manages the blinding secrets (see UseBlindedValueHashes). 9 Encoder Encoder 10 11 // UseBlindedValueHashes controls whether this tree blinds hashes of 12 // KeyValuePairs with a per (Key,Seqno) specific secret (which is itself 13 // derived from a per Seqno specific secret which is stored together with 14 // the tree). This ensures values stored in the tree cannot are not leaked 15 // by the membership proofs (but keys can leak, as well as the rough tree 16 // size). If the tree is rebuilt at every Seqno, this also hides whether 17 // values are changing (but not when a value is first inserted). 18 UseBlindedValueHashes bool 19 20 // The number of children per node. Must be a power of two. Some children 21 // can be empty. 22 ChildrenPerNode int 23 24 // The maximum number of KeyValuePairs in a leaf node before we split 25 MaxValuesPerLeaf int 26 27 // The number of bits necessary to represent a ChildIndex, i.e. 28 // log2(childrenPerNode) 29 BitsPerIndex uint8 30 31 // The length of all the keys which will be stored in the tree. For 32 // simplicity, we enforce that all the keys have the same length and that 33 // bitsPerIndex divides keyByteLength*8 34 KeysByteLength int 35 36 // The maximum depth of the tree. Should always equal keysByteLength*8/bitsPerIndex 37 MaxDepth int 38 39 // ConstructValueContainer constructs a new empty value for the value in a KeyValuePair, so that the 40 // decoding routine has the correct type template. 41 ConstructValueContainer func() interface{} 42 } 43 44 // NewConfig makes a new config object. It takes a a Hasher, logChildrenPerNode 45 // which is the base 2 logarithm of the number of children per interior node, 46 // maxValuesPerLeaf the maximum number of entries in a leaf before the leaf is 47 // split into multiple nodes (at a lower level in the tree), keyByteLength the 48 // length of the Keys which the tree will store, and a ConstructValueContainer function (so that 49 // typed values can be pulled out of the Merkle Tree). 50 func NewConfig(e Encoder, useBlindedValueHashes bool, logChildrenPerNode uint8, maxValuesPerLeaf int, keysByteLength int, constructValueFunc func() interface{}) (Config, error) { 51 childrenPerNode := 1 << logChildrenPerNode 52 if (keysByteLength*8)%int(logChildrenPerNode) != 0 { 53 return Config{}, NewInvalidConfigError("The key bit length does not divide logChildrenPerNode") 54 } 55 if logChildrenPerNode > 63 { 56 return Config{}, NewInvalidConfigError("This package does not support more than 2^63 children per internal node") 57 } 58 if logChildrenPerNode < 1 { 59 return Config{}, NewInvalidConfigError(fmt.Sprintf("Need at least 2 children per node, but logChildrenPerNode = %v", logChildrenPerNode)) 60 } 61 maxDepth := keysByteLength * 8 / int(logChildrenPerNode) 62 return Config{Encoder: e, UseBlindedValueHashes: useBlindedValueHashes, ChildrenPerNode: childrenPerNode, MaxValuesPerLeaf: maxValuesPerLeaf, BitsPerIndex: logChildrenPerNode, KeysByteLength: keysByteLength, MaxDepth: maxDepth, ConstructValueContainer: constructValueFunc}, nil 63 } 64 65 // MasterSecret is a secret used to hide wether a leaf value has changed between 66 // different versions (Seqnos) in a blinded merkle tree. One MasterSecret per 67 // tree is generated for each Seqno, and such secret is then used to generate a 68 // KeySpecific secret per leaf. 69 type MasterSecret []byte 70 71 // MasterSecret is a secret used to hide wether a leaf value has changed between 72 // different versions (Seqnos) in a blinded merkle tree. This is derived from a 73 // per-Seqno MasterSecret as specified by the Encoder 74 type KeySpecificSecret []byte 75 76 // Encoder is an interface for cryptographically hashing MerkleTree data 77 // structures. It also manages blinding secrets. 78 type Encoder interface { 79 Decode(dest interface{}, src []byte) error 80 Encode(src interface{}) (dst []byte, err error) 81 // takes as input a []byte pointer dst to avoid creating new objects 82 EncodeTo(o interface{}, dst *[]byte) (err error) 83 84 EncodeAndHashGeneric(interface{}) (encoded []byte, hash Hash, err error) 85 // takes as input an hash pointer ret to avoid creating new objects 86 HashGeneric(o interface{}, ret *Hash) error 87 88 GenerateMasterSecret(Seqno) (MasterSecret, error) 89 ComputeKeySpecificSecret(MasterSecret, Key) KeySpecificSecret 90 // takes as input a KeySpecificSecret pointer to avoid creating new objects 91 ComputeKeySpecificSecretTo(MasterSecret, Key, *KeySpecificSecret) 92 93 HashKeyValuePairWithKeySpecificSecret(KeyValuePair, KeySpecificSecret) (Hash, error) 94 HashKeyEncodedValuePairWithKeySpecificSecret(KeyEncodedValuePair, KeySpecificSecret) (Hash, error) 95 // takes as input an hash pointer ret to avoid creating new objects 96 HashKeyEncodedValuePairWithKeySpecificSecretTo(KeyEncodedValuePair, KeySpecificSecret, *Hash) error 97 98 GetEncodingType() EncodingType 99 }