blocks_test.go 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141
  1. // Copyright (C) 2014 The Syncthing Authors.
  2. //
  3. // This Source Code Form is subject to the terms of the Mozilla Public
  4. // License, v. 2.0. If a copy of the MPL was not distributed with this file,
  5. // You can obtain one at https://mozilla.org/MPL/2.0/.
  6. package scanner
  7. import (
  8. "bytes"
  9. "context"
  10. "crypto/sha256"
  11. "fmt"
  12. mrand "math/rand"
  13. "testing"
  14. )
  15. var blocksTestData = []struct {
  16. data []byte
  17. blocksize int
  18. hash []string
  19. }{
  20. {
  21. []byte(""), 1024,
  22. []string{
  23. "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855",
  24. },
  25. },
  26. {
  27. []byte("contents"), 1024,
  28. []string{
  29. "d1b2a59fbea7e20077af9f91b27e95e865061b270be03ff539ab3b73587882e8",
  30. },
  31. },
  32. {
  33. []byte("contents"), 9,
  34. []string{
  35. "d1b2a59fbea7e20077af9f91b27e95e865061b270be03ff539ab3b73587882e8",
  36. },
  37. },
  38. {
  39. []byte("contents"), 8,
  40. []string{
  41. "d1b2a59fbea7e20077af9f91b27e95e865061b270be03ff539ab3b73587882e8",
  42. },
  43. },
  44. {
  45. []byte("contents"), 7,
  46. []string{
  47. "ed7002b439e9ac845f22357d822bac1444730fbdb6016d3ec9432297b9ec9f73",
  48. "043a718774c572bd8a25adbeb1bfcd5c0256ae11cecf9f9c3f925d0e52beaf89",
  49. },
  50. },
  51. {
  52. []byte("contents"), 3,
  53. []string{
  54. "1143da2bc54c495c4be31d3868785d39ffdfd56df5668f0645d8f14d47647952",
  55. "e4432baa90819aaef51d2a7f8e148bf7e679610f3173752fabb4dcb2d0f418d3",
  56. "44ad63f60af0f6db6fdde6d5186ef78176367df261fa06be3079b6c80c8adba4",
  57. },
  58. },
  59. {
  60. []byte("conconts"), 3,
  61. []string{
  62. "1143da2bc54c495c4be31d3868785d39ffdfd56df5668f0645d8f14d47647952",
  63. "1143da2bc54c495c4be31d3868785d39ffdfd56df5668f0645d8f14d47647952",
  64. "44ad63f60af0f6db6fdde6d5186ef78176367df261fa06be3079b6c80c8adba4",
  65. },
  66. },
  67. {
  68. []byte("contenten"), 3,
  69. []string{
  70. "1143da2bc54c495c4be31d3868785d39ffdfd56df5668f0645d8f14d47647952",
  71. "e4432baa90819aaef51d2a7f8e148bf7e679610f3173752fabb4dcb2d0f418d3",
  72. "e4432baa90819aaef51d2a7f8e148bf7e679610f3173752fabb4dcb2d0f418d3",
  73. },
  74. },
  75. }
  76. func TestBlocks(t *testing.T) {
  77. for testNo, test := range blocksTestData {
  78. buf := bytes.NewBuffer(test.data)
  79. blocks, err := Blocks(context.TODO(), buf, test.blocksize, -1, nil)
  80. if err != nil {
  81. t.Fatal(err)
  82. }
  83. if l := len(blocks); l != len(test.hash) {
  84. t.Fatalf("%d: Incorrect number of blocks %d != %d", testNo, l, len(test.hash))
  85. } else {
  86. i := 0
  87. for off := int64(0); off < int64(len(test.data)); off += int64(test.blocksize) {
  88. if blocks[i].Offset != off {
  89. t.Errorf("%d/%d: Incorrect offset %d != %d", testNo, i, blocks[i].Offset, off)
  90. }
  91. bs := test.blocksize
  92. if rem := len(test.data) - int(off); bs > rem {
  93. bs = rem
  94. }
  95. if int(blocks[i].Size) != bs {
  96. t.Errorf("%d/%d: Incorrect length %d != %d", testNo, i, blocks[i].Size, bs)
  97. }
  98. if h := fmt.Sprintf("%x", blocks[i].Hash); h != test.hash[i] {
  99. t.Errorf("%d/%d: Incorrect block hash %q != %q", testNo, i, h, test.hash[i])
  100. }
  101. i++
  102. }
  103. }
  104. }
  105. }
  106. func BenchmarkValidate(b *testing.B) {
  107. type block struct {
  108. data []byte
  109. hash [sha256.Size]byte
  110. }
  111. var blocks []block
  112. const blocksPerType = 100
  113. r := mrand.New(mrand.NewSource(0x136bea689e851))
  114. // Valid blocks.
  115. for i := 0; i < blocksPerType; i++ {
  116. var b block
  117. b.data = make([]byte, 128<<10)
  118. r.Read(b.data)
  119. b.hash = sha256.Sum256(b.data)
  120. blocks = append(blocks, b)
  121. }
  122. b.ReportAllocs()
  123. b.ResetTimer()
  124. for i := 0; i < b.N; i++ {
  125. for _, b := range blocks {
  126. Validate(b.data, b.hash[:])
  127. }
  128. }
  129. }