github.com/mre-fog/trillianxx@v1.1.2-0.20180615153820-ae375a99d36a/merkle/hashers/tree_hasher.go (about) 1 // Copyright 2016 Google Inc. All Rights Reserved. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package hashers 16 17 import ( 18 "fmt" 19 20 "github.com/google/trillian" 21 ) 22 23 // LogHasher provides the hash functions needed to compute dense merkle trees. 24 type LogHasher interface { 25 // EmptyRoot supports returning a special case for the root of an empty tree. 26 EmptyRoot() []byte 27 // HashLeaf computes the hash of a leaf that exists. 28 HashLeaf(leaf []byte) ([]byte, error) 29 // HashChildren computes interior nodes. 30 HashChildren(l, r []byte) []byte 31 // Size is the number of bytes in the underlying hash function. 32 // TODO(gbelvin): Replace Size() with BitLength(). 33 Size() int 34 } 35 36 // MapHasher provides the hash functions needed to compute sparse merkle trees. 37 type MapHasher interface { 38 // HashEmpty returns the hash of an empty branch at a given depth. 39 // A height of 0 indicates an empty leaf. The maximum height is Size*8. 40 // TODO(gbelvin) fully define index. 41 HashEmpty(treeID int64, index []byte, height int) []byte 42 // HashLeaf computes the hash of a leaf that exists. 43 HashLeaf(treeID int64, index []byte, leaf []byte) ([]byte, error) 44 // HashChildren computes interior nodes. 45 HashChildren(l, r []byte) []byte 46 // Size is the number of bytes in the underlying hash function. 47 // TODO(gbelvin): Replace Size() with BitLength(). 48 Size() int 49 // BitLen returns the number of bits in the underlying hash function. 50 // It is also the height of the merkle tree. 51 BitLen() int 52 } 53 54 var ( 55 logHashers = make(map[trillian.HashStrategy]LogHasher) 56 mapHashers = make(map[trillian.HashStrategy]MapHasher) 57 ) 58 59 // RegisterLogHasher registers a hasher for use. 60 func RegisterLogHasher(h trillian.HashStrategy, f LogHasher) { 61 if h == trillian.HashStrategy_UNKNOWN_HASH_STRATEGY { 62 panic(fmt.Sprintf("RegisterLogHasher(%s) of unknown hasher", h)) 63 } 64 if logHashers[h] != nil { 65 panic(fmt.Sprintf("%v already registered as a LogHasher", h)) 66 } 67 logHashers[h] = f 68 } 69 70 // RegisterMapHasher registers a hasher for use. 71 func RegisterMapHasher(h trillian.HashStrategy, f MapHasher) { 72 if h == trillian.HashStrategy_UNKNOWN_HASH_STRATEGY { 73 panic(fmt.Sprintf("RegisterMapHasher(%s) of unknown hasher", h)) 74 } 75 if mapHashers[h] != nil { 76 panic(fmt.Sprintf("%v already registered as a MapHasher", h)) 77 } 78 mapHashers[h] = f 79 } 80 81 // NewLogHasher returns a LogHasher. 82 func NewLogHasher(h trillian.HashStrategy) (LogHasher, error) { 83 f := logHashers[h] 84 if f != nil { 85 return f, nil 86 } 87 return nil, fmt.Errorf("LogHasher(%s) is an unknown hasher", h) 88 } 89 90 // NewMapHasher returns a MapHasher. 91 func NewMapHasher(h trillian.HashStrategy) (MapHasher, error) { 92 f := mapHashers[h] 93 if f != nil { 94 return f, nil 95 } 96 return nil, fmt.Errorf("MapHasher(%s) is an unknown hasher", h) 97 }