github.com/sixexorg/magnetic-ring@v0.0.0-20191119090307-31705a21e419/merkle/merkle_tree_test.go (about)

     1  /*
     2   * Copyright (C) 2018 The ontology Authors
     3   * This file is part of The ontology library.
     4   *
     5   * The ontology is free software: you can redistribute it and/or modify
     6   * it under the terms of the GNU Lesser General Public License as published by
     7   * the Free Software Foundation, either version 3 of the License, or
     8   * (at your option) any later version.
     9   *
    10   * The ontology is distributed in the hope that it will be useful,
    11   * but WITHOUT ANY WARRANTY; without even the implied warranty of
    12   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    13   * GNU Lesser General Public License for more details.
    14   *
    15   * You should have received a copy of the GNU Lesser General Public License
    16   * along with The ontology.  If not, see <http://www.gnu.org/licenses/>.
    17   */
    18  
    19  package merkle
    20  
    21  import (
    22  	"crypto/sha256"
    23  	"fmt"
    24  	"os"
    25  	"testing"
    26  
    27  	"github.com/sixexorg/magnetic-ring/common"
    28  )
    29  
    30  func TestMerkleLeaf3(t *testing.T) {
    31  	hasher := TreeHasher{}
    32  	leafs := []common.Hash{hasher.hash_leaf([]byte{1}),
    33  		hasher.hash_leaf([]byte{2}),
    34  		hasher.hash_leaf([]byte{3})}
    35  	store, _ := NewFileHashStore("merkletree.db", 0)
    36  	tree := NewTree(0, nil, store)
    37  	if tree.Root() != sha256.Sum256(nil) {
    38  		t.Fatal("root error")
    39  	}
    40  	for i := range leafs {
    41  		tree.Append([]byte{byte(i + 1)})
    42  	}
    43  
    44  	hashes := make([]common.Hash, 5, 5)
    45  	for i := 0; i < 4; i++ {
    46  		hashes[i], _ = tree.hashStore.GetHash(uint64(i))
    47  	}
    48  	hashes[4] = tree.Root()
    49  
    50  	cmp := []common.Hash{
    51  		leafs[0],
    52  		leafs[1],
    53  		hasher.hash_children(leafs[0], leafs[1]),
    54  		leafs[2],
    55  		hasher.hash_children(hasher.hash_children(leafs[0], leafs[1]),
    56  			leafs[2]),
    57  	}
    58  
    59  	for i := 0; i < 5; i++ {
    60  		if hashes[i] != cmp[i] {
    61  			t.Fatal(fmt.Sprintf("error: %d, expected %x, found %x", i, cmp[i], hashes[i]))
    62  		}
    63  	}
    64  
    65  }
    66  
    67  func TestMerkle(t *testing.T) {
    68  	hasher := TreeHasher{}
    69  	leafs := []common.Hash{hasher.hash_leaf([]byte{1}),
    70  		hasher.hash_leaf([]byte{2}),
    71  		hasher.hash_leaf([]byte{3}),
    72  		hasher.hash_leaf([]byte{4})}
    73  
    74  	store, _ := NewFileHashStore("merkletree.db", 0)
    75  	tree := NewTree(0, nil, store)
    76  	if tree.Root() != sha256.Sum256(nil) {
    77  		t.Fatal("root error")
    78  	}
    79  	for i, _ := range leafs {
    80  		tree.Append([]byte{byte(i + 1)})
    81  	}
    82  
    83  	hashes := make([]common.Hash, 6, 6)
    84  	for i := 0; i < 6; i++ {
    85  		hashes[i], _ = tree.hashStore.GetHash(uint64(i))
    86  	}
    87  	cmp := []common.Hash{
    88  		leafs[0],
    89  		leafs[1],
    90  		hasher.hash_children(leafs[0], leafs[1]),
    91  		leafs[2],
    92  		leafs[3],
    93  		hasher.hash_children(leafs[2], leafs[3]),
    94  		hasher.hash_children(hasher.hash_children(leafs[0], leafs[1]),
    95  			hasher.hash_children(leafs[2], leafs[3])),
    96  	}
    97  
    98  	for i := 0; i < 6; i++ {
    99  		if hashes[i] != cmp[i] {
   100  			fmt.Println(hashes)
   101  			fmt.Println(cmp)
   102  			t.Fatal(fmt.Sprintf("error: %d, expected %x, found %x", i, cmp[i], hashes[i]))
   103  		}
   104  	}
   105  
   106  }
   107  
   108  func TestMerkleHashes(t *testing.T) {
   109  	store, _ := NewFileHashStore("merkletree.db", 0)
   110  	tree := NewTree(0, nil, store)
   111  	for i := 0; i < 100; i++ {
   112  		tree.Append([]byte{byte(i + 1)})
   113  	}
   114  
   115  	// 100 == 110 0100
   116  	if len(tree.hashes) != 3 {
   117  		t.Fatal(fmt.Sprintf("error tree hashes size"))
   118  	}
   119  
   120  }
   121  
   122  // zero based return merkle root of D[0:n]
   123  func TestMerkleRoot(t *testing.T) {
   124  	n := 100
   125  	roots := make([]common.Hash, n, n)
   126  	store, _ := NewFileHashStore("merkletree.db", 0)
   127  	tree := NewTree(0, nil, store)
   128  	for i := 0; i < n; i++ {
   129  		tree.Append([]byte{byte(i + 1)})
   130  		roots[i] = tree.Root()
   131  	}
   132  
   133  	cmp := make([]common.Hash, n, n)
   134  	for i := 0; i < n; i++ {
   135  		cmp[i] = tree.merkleRoot(uint64(i) + 1)
   136  		if cmp[i] != roots[i] {
   137  			t.Error(fmt.Sprintf("error merkle root is not equal at %d", i))
   138  		}
   139  	}
   140  
   141  }
   142  
   143  func TestGetSubTreeSize(t *testing.T) {
   144  	sizes := getSubTreeSize(7)
   145  	fmt.Println("sub tree size", sizes)
   146  }
   147  
   148  // zero based return merkle root of D[0:n]
   149  func TestMerkleIncludeProof(t *testing.T) {
   150  	n := uint64(9)
   151  	store, _ := NewFileHashStore("merkletree.db", 0)
   152  	tree := NewTree(0, nil, store)
   153  	for i := uint64(0); i < n; i++ {
   154  		tree.Append([]byte{byte(i + 1)})
   155  	}
   156  
   157  	verify := NewMerkleVerifier()
   158  
   159  	root := tree.Root()
   160  	for i := uint64(0); i < n; i++ {
   161  		proof, _ := tree.InclusionProof(i, n)
   162  		leaf_hash := tree.hasher.hash_leaf([]byte{byte(i + 1)})
   163  		res := verify.VerifyLeafHashInclusion(leaf_hash, i, proof, root, n)
   164  		if res != nil {
   165  			t.Fatal(res, i, proof)
   166  		}
   167  	}
   168  }
   169  
   170  func TestMerkleConsistencyProofLen(t *testing.T) {
   171  	n := uint64(7)
   172  	store, _ := NewFileHashStore("merkletree.db", 0)
   173  	tree := NewTree(0, nil, store)
   174  	for i := uint64(0); i < n; i++ {
   175  		tree.Append([]byte{byte(i + 1)})
   176  	}
   177  
   178  	cmp := []int{3, 2, 4, 1, 4, 3, 0}
   179  	for i := uint64(0); i < n; i++ {
   180  		proof := tree.ConsistencyProof(i+1, n)
   181  		if len(proof) != cmp[i] {
   182  			t.Fatal("error: wrong proof length")
   183  		}
   184  	}
   185  
   186  }
   187  
   188  func TestMerkleConsistencyProof(t *testing.T) {
   189  	n := uint64(140)
   190  	roots := make([]common.Hash, n, n)
   191  	store, _ := NewFileHashStore("merkletree.db", 0)
   192  	tree := NewTree(0, nil, store)
   193  	for i := uint64(0); i < n; i++ {
   194  		tree.Append([]byte{byte(i + 1)})
   195  		roots[i] = tree.Root()
   196  	}
   197  
   198  	verify := NewMerkleVerifier()
   199  
   200  	for i := uint64(0); i < n; i++ {
   201  		proof := tree.ConsistencyProof(i+1, n)
   202  		err := verify.VerifyConsistency(i+1, n, roots[i], roots[n-1], proof)
   203  		if err != nil {
   204  			t.Fatal("verify consistency error:", i, err)
   205  		}
   206  
   207  	}
   208  }
   209  
   210  //~70w
   211  func BenchmarkMerkleInsert(b *testing.B) {
   212  	store, _ := NewFileHashStore("merkletree.db", 0)
   213  	tree := NewTree(0, nil, store)
   214  	for i := 0; i < b.N; i++ {
   215  		//use b.N for looping
   216  		tree.Append([]byte(fmt.Sprintf("bench %d", i)))
   217  	}
   218  }
   219  
   220  var treeTest *CompactMerkleTree
   221  var storeTest HashStore
   222  var N = 100 //00
   223  
   224  func init() {
   225  	storeTest, _ := NewFileHashStore("merkletree.db", 0)
   226  	treeTest := NewTree(0, nil, storeTest)
   227  	for i := 0; i < N; i++ {
   228  		treeTest.Append([]byte(fmt.Sprintf("setup %d", i)))
   229  	}
   230  
   231  }
   232  
   233  /*
   234  // ~20w
   235  func BenchmarkMerkleInclusionProof(b *testing.B) {
   236  	for i := 0; i < b.N; i++ {
   237  		treeTest.InclusionProof(uint32(i), uint32(N))
   238  	}
   239  }
   240  
   241  // ~20w
   242  func BenchmarkMerkleConsistencyProof(b *testing.B) {
   243  	for i := 0; i < b.N; i++ {
   244  		treeTest.ConsistencyProof(uint32(i+1), uint32(N))
   245  	}
   246  }
   247  */
   248  
   249  //~70w
   250  func BenchmarkMerkleInsert2(b *testing.B) {
   251  	for i := 0; i < b.N; i++ {
   252  		treeTest.Append([]byte(fmt.Sprintf("bench %d", i)))
   253  	}
   254  }
   255  
   256  //
   257  
   258  func TestNewFileSeek(t *testing.T) {
   259  	name := "test.txt"
   260  	f, err := os.OpenFile(name, os.O_RDWR|os.O_CREATE, 0755)
   261  	if err != nil {
   262  		t.Fatal("can not open file", err)
   263  	}
   264  	off, err := f.Seek(0, 2)
   265  	f.Write([]byte{12})
   266  	a := float64(9999999999996841)
   267  	b := int64(a)
   268  
   269  	t.Fatal(b, "haha")
   270  
   271  	t.Fatal(off, err)
   272  }