1 // Copyright 2016 Google LLC. 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 rfc6962 provides hashing functionality according to RFC6962. 16 package rfc6962 17 18 import ( 19 "crypto" 20 _ "crypto/sha256" // SHA256 is the default algorithm. 21 ) 22 23 // Domain separation prefixes 24 const ( 25 RFC6962LeafHashPrefix = 0 26 RFC6962NodeHashPrefix = 1 27 ) 28 29 // DefaultHasher is a SHA256 based LogHasher. 30 var DefaultHasher = New(crypto.SHA256) 31 32 // Hasher implements the RFC6962 tree hashing algorithm. 33 type Hasher struct { 34 crypto.Hash 35 } 36 37 // New creates a new Hashers.LogHasher on the passed in hash function. 38 func New(h crypto.Hash) *Hasher { 39 return &Hasher{Hash: h} 40 } 41 42 // EmptyRoot returns a special case for an empty tree. 43 func (t *Hasher) EmptyRoot() []byte { 44 return t.New().Sum(nil) 45 } 46 47 // HashLeaf returns the Merkle tree leaf hash of the data passed in through leaf. 48 // The data in leaf is prefixed by the LeafHashPrefix. 49 func (t *Hasher) HashLeaf(leaf []byte) []byte { 50 h := t.New() 51 h.Write([]byte{RFC6962LeafHashPrefix}) 52 h.Write(leaf) 53 return h.Sum(nil) 54 } 55 56 // HashChildren returns the inner Merkle tree node hash of the two child nodes l and r. 57 // The hashed structure is NodeHashPrefix||l||r. 58 func (t *Hasher) HashChildren(l, r []byte) []byte { 59 h := t.New() 60 b := append(append(append( 61 make([]byte, 0, 1+len(l)+len(r)), 62 RFC6962NodeHashPrefix), 63 l...), 64 r...) 65 66 h.Write(b) 67 return h.Sum(nil) 68 } 69