mode-ctr-gladman.js 1.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687
  1. import {
  2. BlockCipherMode,
  3. } from './cipher-core.js';
  4. const incWord = (word) => {
  5. let _word = word;
  6. if (((word >> 24) & 0xff) === 0xff) { // overflow
  7. let b1 = (word >> 16) & 0xff;
  8. let b2 = (word >> 8) & 0xff;
  9. let b3 = word & 0xff;
  10. if (b1 === 0xff) { // overflow b1
  11. b1 = 0;
  12. if (b2 === 0xff) {
  13. b2 = 0;
  14. if (b3 === 0xff) {
  15. b3 = 0;
  16. } else {
  17. b3 += 1;
  18. }
  19. } else {
  20. b2 += 1;
  21. }
  22. } else {
  23. b1 += 1;
  24. }
  25. _word = 0;
  26. _word += (b1 << 16);
  27. _word += (b2 << 8);
  28. _word += b3;
  29. } else {
  30. _word += (0x01 << 24);
  31. }
  32. return _word;
  33. };
  34. const incCounter = (counter) => {
  35. const _counter = counter;
  36. _counter[0] = incWord(_counter[0]);
  37. if (_counter[0] === 0) {
  38. // encr_data in fileenc.c from Dr Brian Gladman's counts only with DWORD j < 8
  39. _counter[1] = incWord(_counter[1]);
  40. }
  41. return _counter;
  42. };
  43. /** @preserve
  44. * Counter block mode compatible with Dr Brian Gladman fileenc.c
  45. * derived from CryptoJS.mode.CTR
  46. * Jan Hruby jhruby.web@gmail.com
  47. */
  48. export class CTRGladman extends BlockCipherMode {
  49. }
  50. CTRGladman.Encryptor = class extends CTRGladman {
  51. processBlock(words, offset) {
  52. const _words = words;
  53. // Shortcuts
  54. const cipher = this._cipher;
  55. const { blockSize } = cipher;
  56. const iv = this._iv;
  57. let counter = this._counter;
  58. // Generate keystream
  59. if (iv) {
  60. this._counter = iv.slice(0);
  61. counter = this._counter;
  62. // Remove IV for subsequent blocks
  63. this._iv = undefined;
  64. }
  65. incCounter(counter);
  66. const keystream = counter.slice(0);
  67. cipher.encryptBlock(keystream, 0);
  68. // Encrypt
  69. for (let i = 0; i < blockSize; i += 1) {
  70. _words[offset + i] ^= keystream[i];
  71. }
  72. }
  73. };
  74. CTRGladman.Decryptor = CTRGladman.Encryptor;