Rabbit.js 7.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186
  1. (function () {
  2. var C = typeof window === 'undefined' ? require('./Crypto').Crypto : window.Crypto;
  3. // Shortcuts
  4. var util = C.util;
  5. var charenc = C.charenc;
  6. var UTF8 = charenc.UTF8;
  7. var Binary = charenc.Binary; // Inner state
  8. var x = [];
  9. var c = [];
  10. var b;
  11. var Rabbit = (C.Rabbit = {
  12. /**
  13. * Public API
  14. */
  15. encrypt: function (message, password) {
  16. var // Convert to bytes
  17. m = UTF8.stringToBytes(message);
  18. var // Generate random IV
  19. iv = util.randomBytes(8);
  20. var // Generate key
  21. k =
  22. password.constructor == String
  23. ? // Derive key from passphrase
  24. C.PBKDF2(password, iv, 32, {
  25. asBytes: true
  26. })
  27. : // else, assume byte array representing cryptographic key
  28. password; // Encrypt
  29. Rabbit._rabbit(m, k, util.bytesToWords(iv));
  30. // Return ciphertext
  31. return util.bytesToBase64(iv.concat(m));
  32. },
  33. decrypt: function (ciphertext, password) {
  34. var // Convert to bytes
  35. c = util.base64ToBytes(ciphertext);
  36. var // Separate IV and message
  37. iv = c.splice(0, 8);
  38. var // Generate key
  39. k =
  40. password.constructor == String
  41. ? // Derive key from passphrase
  42. C.PBKDF2(password, iv, 32, {
  43. asBytes: true
  44. })
  45. : // else, assume byte array representing cryptographic key
  46. password; // Decrypt
  47. Rabbit._rabbit(c, k, util.bytesToWords(iv));
  48. // Return plaintext
  49. return UTF8.bytesToString(c);
  50. },
  51. /**
  52. * Internal methods
  53. */
  54. // Encryption/decryption scheme
  55. _rabbit: function (m, k, iv) {
  56. Rabbit._keysetup(k);
  57. if (iv) {
  58. Rabbit._ivsetup(iv);
  59. }
  60. for (var s = [], i = 0; i < m.length; i++) {
  61. if (i % 16 == 0) {
  62. // Iterate the system
  63. Rabbit._nextstate();
  64. // Generate 16 bytes of pseudo-random data
  65. s[0] = x[0] ^ (x[5] >>> 16) ^ (x[3] << 16);
  66. s[1] = x[2] ^ (x[7] >>> 16) ^ (x[5] << 16);
  67. s[2] = x[4] ^ (x[1] >>> 16) ^ (x[7] << 16);
  68. s[3] = x[6] ^ (x[3] >>> 16) ^ (x[1] << 16);
  69. // Swap endian
  70. for (var j = 0; j < 4; j++) {
  71. s[j] = (((s[j] << 8) | (s[j] >>> 24)) & 16711935) | (((s[j] << 24) | (s[j] >>> 8)) & 4278255360);
  72. }
  73. // Convert words to bytes
  74. for (var b = 120; b >= 0; b -= 8) {
  75. s[b / 8] = (s[b >>> 5] >>> (24 - (b % 32))) & 255;
  76. }
  77. }
  78. m[i] ^= s[i % 16];
  79. }
  80. },
  81. // Key setup scheme
  82. _keysetup: function (k) {
  83. // Generate initial state values
  84. x[0] = k[0];
  85. x[2] = k[1];
  86. x[4] = k[2];
  87. x[6] = k[3];
  88. x[1] = (k[3] << 16) | (k[2] >>> 16);
  89. x[3] = (k[0] << 16) | (k[3] >>> 16);
  90. x[5] = (k[1] << 16) | (k[0] >>> 16);
  91. x[7] = (k[2] << 16) | (k[1] >>> 16);
  92. // Generate initial counter values
  93. c[0] = util.rotl(k[2], 16);
  94. c[2] = util.rotl(k[3], 16);
  95. c[4] = util.rotl(k[0], 16);
  96. c[6] = util.rotl(k[1], 16);
  97. c[1] = (k[0] & 4294901760) | (k[1] & 65535);
  98. c[3] = (k[1] & 4294901760) | (k[2] & 65535);
  99. c[5] = (k[2] & 4294901760) | (k[3] & 65535);
  100. c[7] = (k[3] & 4294901760) | (k[0] & 65535);
  101. // Clear carry bit
  102. b = 0;
  103. // Iterate the system four times
  104. for (var i = 0; i < 4; i++) {
  105. Rabbit._nextstate();
  106. }
  107. // Modify the counters
  108. for (var i = 0; i < 8; i++) {
  109. c[i] ^= x[(i + 4) & 7];
  110. }
  111. },
  112. // IV setup scheme
  113. _ivsetup: function (iv) {
  114. // Generate four subvectors
  115. var i0 = util.endian(iv[0]);
  116. var i2 = util.endian(iv[1]);
  117. var i1 = (i0 >>> 16) | (i2 & 4294901760);
  118. var i3 = (i2 << 16) | (i0 & 65535); // Modify counter values
  119. c[0] ^= i0;
  120. c[1] ^= i1;
  121. c[2] ^= i2;
  122. c[3] ^= i3;
  123. c[4] ^= i0;
  124. c[5] ^= i1;
  125. c[6] ^= i2;
  126. c[7] ^= i3;
  127. // Iterate the system four times
  128. for (var i = 0; i < 4; i++) {
  129. Rabbit._nextstate();
  130. }
  131. },
  132. // Next-state function
  133. _nextstate: function () {
  134. // Save old counter values
  135. for (var c_old = [], i = 0; i < 8; i++) {
  136. c_old[i] = c[i];
  137. }
  138. // Calculate new counter values
  139. c[0] = (c[0] + 1295307597 + b) >>> 0;
  140. c[1] = (c[1] + 3545052371 + (c[0] >>> 0 < c_old[0] >>> 0 ? 1 : 0)) >>> 0;
  141. c[2] = (c[2] + 886263092 + (c[1] >>> 0 < c_old[1] >>> 0 ? 1 : 0)) >>> 0;
  142. c[3] = (c[3] + 1295307597 + (c[2] >>> 0 < c_old[2] >>> 0 ? 1 : 0)) >>> 0;
  143. c[4] = (c[4] + 3545052371 + (c[3] >>> 0 < c_old[3] >>> 0 ? 1 : 0)) >>> 0;
  144. c[5] = (c[5] + 886263092 + (c[4] >>> 0 < c_old[4] >>> 0 ? 1 : 0)) >>> 0;
  145. c[6] = (c[6] + 1295307597 + (c[5] >>> 0 < c_old[5] >>> 0 ? 1 : 0)) >>> 0;
  146. c[7] = (c[7] + 3545052371 + (c[6] >>> 0 < c_old[6] >>> 0 ? 1 : 0)) >>> 0;
  147. b = c[7] >>> 0 < c_old[7] >>> 0 ? 1 : 0;
  148. // Calculate the g-values
  149. for (var g = [], i = 0; i < 8; i++) {
  150. var gx = (x[i] + c[i]) >>> 0;
  151. // Construct high and low argument for squaring
  152. var ga = gx & 65535;
  153. var gb = gx >>> 16; // Calculate high and low result of squaring
  154. var gh = ((((ga * ga) >>> 17) + ga * gb) >>> 15) + gb * gb;
  155. var gl = ((((gx & 4294901760) * gx) >>> 0) + (((gx & 65535) * gx) >>> 0)) >>> 0; // High XOR low
  156. g[i] = gh ^ gl;
  157. }
  158. // Calculate new state values
  159. x[0] = g[0] + ((g[7] << 16) | (g[7] >>> 16)) + ((g[6] << 16) | (g[6] >>> 16));
  160. x[1] = g[1] + ((g[0] << 8) | (g[0] >>> 24)) + g[7];
  161. x[2] = g[2] + ((g[1] << 16) | (g[1] >>> 16)) + ((g[0] << 16) | (g[0] >>> 16));
  162. x[3] = g[3] + ((g[2] << 8) | (g[2] >>> 24)) + g[1];
  163. x[4] = g[4] + ((g[3] << 16) | (g[3] >>> 16)) + ((g[2] << 16) | (g[2] >>> 16));
  164. x[5] = g[5] + ((g[4] << 8) | (g[4] >>> 24)) + g[3];
  165. x[6] = g[6] + ((g[5] << 16) | (g[5] >>> 16)) + ((g[4] << 16) | (g[4] >>> 16));
  166. x[7] = g[7] + ((g[6] << 8) | (g[6] >>> 24)) + g[5];
  167. }
  168. });
  169. })();