You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

216 lines
5.4 KiB

  1. // Copyright (c) 2016 Andreas Auernhammer. All rights reserved.
  2. // Use of this source code is governed by a license that can be
  3. // found in the LICENSE file.
  4. package threefish
  5. func (t *threefish256) Encrypt(dst, src []byte) {
  6. var block [4]uint64
  7. bytesToBlock256(&block, src)
  8. Encrypt256(&block, &(t.keys), &(t.tweak))
  9. block256ToBytes(dst, &block)
  10. }
  11. func (t *threefish256) Decrypt(dst, src []byte) {
  12. var block [4]uint64
  13. bytesToBlock256(&block, src)
  14. Decrypt256(&block, &(t.keys), &(t.tweak))
  15. block256ToBytes(dst, &block)
  16. }
  17. func newCipher256(tweak *[TweakSize]byte, key []byte) *threefish256 {
  18. c := new(threefish256)
  19. c.tweak[0] = uint64(tweak[0]) | uint64(tweak[1])<<8 | uint64(tweak[2])<<16 | uint64(tweak[3])<<24 |
  20. uint64(tweak[4])<<32 | uint64(tweak[5])<<40 | uint64(tweak[6])<<48 | uint64(tweak[7])<<56
  21. c.tweak[1] = uint64(tweak[8]) | uint64(tweak[9])<<8 | uint64(tweak[10])<<16 | uint64(tweak[11])<<24 |
  22. uint64(tweak[12])<<32 | uint64(tweak[13])<<40 | uint64(tweak[14])<<48 | uint64(tweak[15])<<56
  23. c.tweak[2] = c.tweak[0] ^ c.tweak[1]
  24. for i := range c.keys[:4] {
  25. j := i * 8
  26. c.keys[i] = uint64(key[j]) | uint64(key[j+1])<<8 | uint64(key[j+2])<<16 | uint64(key[j+3])<<24 |
  27. uint64(key[j+4])<<32 | uint64(key[j+5])<<40 | uint64(key[j+6])<<48 | uint64(key[j+7])<<56
  28. }
  29. c.keys[4] = C240 ^ c.keys[0] ^ c.keys[1] ^ c.keys[2] ^ c.keys[3]
  30. return c
  31. }
  32. // Encrypt256 encrypts the 4 words of block using the expanded 256 bit key and
  33. // the 128 bit tweak. The keys[4] must be keys[0] xor keys[1] xor ... keys[3] xor C240.
  34. // The tweak[2] must be tweak[0] xor tweak[1].
  35. func Encrypt256(block *[4]uint64, keys *[5]uint64, tweak *[3]uint64) {
  36. b0, b1, b2, b3 := block[0], block[1], block[2], block[3]
  37. for r := 0; r < 17; r++ {
  38. b0 += keys[r%5]
  39. b1 += keys[(r+1)%5] + tweak[r%3]
  40. b2 += keys[(r+2)%5] + tweak[(r+1)%3]
  41. b3 += keys[(r+3)%5] + uint64(r)
  42. b0 += b1
  43. b1 = ((b1 << 14) | (b1 >> (64 - 14))) ^ b0
  44. b2 += b3
  45. b3 = ((b3 << 16) | (b3 >> (64 - 16))) ^ b2
  46. b0 += b3
  47. b3 = ((b3 << 52) | (b3 >> (64 - 52))) ^ b0
  48. b2 += b1
  49. b1 = ((b1 << 57) | (b1 >> (64 - 57))) ^ b2
  50. b0 += b1
  51. b1 = ((b1 << 23) | (b1 >> (64 - 23))) ^ b0
  52. b2 += b3
  53. b3 = ((b3 << 40) | (b3 >> (64 - 40))) ^ b2
  54. b0 += b3
  55. b3 = ((b3 << 5) | (b3 >> (64 - 5))) ^ b0
  56. b2 += b1
  57. b1 = ((b1 << 37) | (b1 >> (64 - 37))) ^ b2
  58. r++
  59. b0 += keys[r%5]
  60. b1 += keys[(r+1)%5] + tweak[r%3]
  61. b2 += keys[(r+2)%5] + tweak[(r+1)%3]
  62. b3 += keys[(r+3)%5] + uint64(r)
  63. b0 += b1
  64. b1 = ((b1 << 25) | (b1 >> (64 - 25))) ^ b0
  65. b2 += b3
  66. b3 = ((b3 << 33) | (b3 >> (64 - 33))) ^ b2
  67. b0 += b3
  68. b3 = ((b3 << 46) | (b3 >> (64 - 46))) ^ b0
  69. b2 += b1
  70. b1 = ((b1 << 12) | (b1 >> (64 - 12))) ^ b2
  71. b0 += b1
  72. b1 = ((b1 << 58) | (b1 >> (64 - 58))) ^ b0
  73. b2 += b3
  74. b3 = ((b3 << 22) | (b3 >> (64 - 22))) ^ b2
  75. b0 += b3
  76. b3 = ((b3 << 32) | (b3 >> (64 - 32))) ^ b0
  77. b2 += b1
  78. b1 = ((b1 << 32) | (b1 >> (64 - 32))) ^ b2
  79. }
  80. b0 += keys[3]
  81. b1 += keys[4] + tweak[0]
  82. b2 += keys[0] + tweak[1]
  83. b3 += keys[1] + uint64(18)
  84. block[0], block[1], block[2], block[3] = b0, b1, b2, b3
  85. }
  86. // Decrypt256 decrypts the 4 words of block using the expanded 256 bit key and
  87. // the 128 bit tweak. The keys[4] must be keys[0] xor keys[1] xor ... keys[3] xor C240.
  88. // The tweak[2] must be tweak[0] xor tweak[1].
  89. func Decrypt256(block *[4]uint64, keys *[5]uint64, tweak *[3]uint64) {
  90. b0, b1, b2, b3 := block[0], block[1], block[2], block[3]
  91. var tmp uint64
  92. for r := 18; r > 1; r-- {
  93. b0 -= keys[r%5]
  94. b1 -= keys[(r+1)%5] + tweak[r%3]
  95. b2 -= keys[(r+2)%5] + tweak[(r+1)%3]
  96. b3 -= keys[(r+3)%5] + uint64(r)
  97. tmp = b1 ^ b2
  98. b1 = (tmp >> 32) | (tmp << (64 - 32))
  99. b2 -= b1
  100. tmp = b3 ^ b0
  101. b3 = (tmp >> 32) | (tmp << (64 - 32))
  102. b0 -= b3
  103. tmp = b3 ^ b2
  104. b3 = (tmp >> 22) | (tmp << (64 - 22))
  105. b2 -= b3
  106. tmp = b1 ^ b0
  107. b1 = (tmp >> 58) | (tmp << (64 - 58))
  108. b0 -= b1
  109. tmp = b1 ^ b2
  110. b1 = (tmp >> 12) | (tmp << (64 - 12))
  111. b2 -= b1
  112. tmp = b3 ^ b0
  113. b3 = (tmp >> 46) | (tmp << (64 - 46))
  114. b0 -= b3
  115. tmp = b3 ^ b2
  116. b3 = (tmp >> 33) | (tmp << (64 - 33))
  117. b2 -= b3
  118. tmp = b1 ^ b0
  119. b1 = (tmp >> 25) | (tmp << (64 - 25))
  120. b0 -= b1
  121. r--
  122. b0 -= keys[r%5]
  123. b1 -= keys[(r+1)%5] + tweak[r%3]
  124. b2 -= keys[(r+2)%5] + tweak[(r+1)%3]
  125. b3 -= keys[(r+3)%5] + uint64(r)
  126. tmp = b1 ^ b2
  127. b1 = (tmp >> 37) | (tmp << (64 - 37))
  128. b2 -= b1
  129. tmp = b3 ^ b0
  130. b3 = (tmp >> 5) | (tmp << (64 - 5))
  131. b0 -= b3
  132. tmp = b3 ^ b2
  133. b3 = (tmp >> 40) | (tmp << (64 - 40))
  134. b2 -= b3
  135. tmp = b1 ^ b0
  136. b1 = (tmp >> 23) | (tmp << (64 - 23))
  137. b0 -= b1
  138. tmp = b1 ^ b2
  139. b1 = (tmp >> 57) | (tmp << (64 - 57))
  140. b2 -= b1
  141. tmp = b3 ^ b0
  142. b3 = (tmp >> 52) | (tmp << (64 - 52))
  143. b0 -= b3
  144. tmp = b3 ^ b2
  145. b3 = (tmp >> 16) | (tmp << (64 - 16))
  146. b2 -= b3
  147. tmp = b1 ^ b0
  148. b1 = (tmp >> 14) | (tmp << (64 - 14))
  149. b0 -= b1
  150. }
  151. b0 -= keys[0]
  152. b1 -= keys[1] + tweak[0]
  153. b2 -= keys[2] + tweak[1]
  154. b3 -= keys[3]
  155. block[0], block[1], block[2], block[3] = b0, b1, b2, b3
  156. }
  157. // UBI256 does a Threefish256 encryption of the given block using
  158. // the chain values hVal and the tweak.
  159. // The chain values are updated through hVal[i] = block[i] ^ Enc(block)[i]
  160. func UBI256(block *[4]uint64, hVal *[5]uint64, tweak *[3]uint64) {
  161. b0, b1, b2, b3 := block[0], block[1], block[2], block[3]
  162. hVal[4] = C240 ^ hVal[0] ^ hVal[1] ^ hVal[2] ^ hVal[3]
  163. tweak[2] = tweak[0] ^ tweak[1]
  164. Encrypt256(block, hVal, tweak)
  165. hVal[0] = block[0] ^ b0
  166. hVal[1] = block[1] ^ b1
  167. hVal[2] = block[2] ^ b2
  168. hVal[3] = block[3] ^ b3
  169. }