finish method

Poly1305 finish(
  1. Uint8List mac,
  2. int macpos
)

Implementation

Poly1305 finish(Uint8List mac, int macpos) {
  List<Int32> g = List<Int32>.filled(10, Int32(0));
  int i;
  Int32 c, mask, f;

  if (this._leftover != 0) {
    i = this._leftover;
    this._buffer![i++] = 1;
    for (; i < 16; i++) this._buffer![i] = 0;
    this._fin = 1;
    this.blocks(this._buffer, 0, 16);
  }

  c = this._h[1].shiftRightUnsigned(13);
  this._h[1] &= 0x1fff;
  for (i = 2; i < 10; i++) {
    this._h[i] += c;
    c = this._h[i].shiftRightUnsigned(13);
    this._h[i] &= 0x1fff;
  }
  this._h[0] += (c * 5);
  c = this._h[0].shiftRightUnsigned(13);
  this._h[0] &= 0x1fff;
  this._h[1] += c;
  c = this._h[1].shiftRightUnsigned(13);
  this._h[1] &= 0x1fff;
  this._h[2] += c;

  g[0] = this._h[0] + 5 as Int32;
  c = g[0].shiftRightUnsigned(13);
  g[0] &= 0x1fff;
  for (i = 1; i < 10; i++) {
    g[i] = this._h[i] + c as Int32;
    c = g[i].shiftRightUnsigned(13);
    g[i] &= 0x1fff;
  }
  g[9] -= (1 << 13);
  g[9] &= 0xffff;

  /*
                      backport from tweetnacl-fast.js https://github.com/dchest/tweetnacl-js/releases/tag/v0.14.3
                      <<<
                      "The issue was not properly detecting if st->h was >= 2^130 - 5,
                      coupled with [testing mistake] not catching the failure.
                      The chance of the bug affecting anything in the real world is essentially zero luckily,
                      but it's good to have it fixed."
                      >>>
                      */
  ///change mask = (g[9] >>> ((2 * 8) - 1)) - 1; to as
  mask = (c ^ 1) - 1 as Int32;
  mask &= 0xffff;
  ///////////////////////////////////////

  for (i = 0; i < 10; i++) g[i] &= mask;
  mask = ~mask;
  for (i = 0; i < 10; i++) this._h[i] = (this._h[i] & mask) | g[i];

  this._h[0] = ((this._h[0]) | (this._h[1] << 13)) & 0xffff;
  this._h[1] =
      ((this._h[1].shiftRightUnsigned(3)) | (this._h[2] << 10)) & 0xffff;
  this._h[2] =
      ((this._h[2].shiftRightUnsigned(6)) | (this._h[3] << 7)) & 0xffff;
  this._h[3] =
      ((this._h[3].shiftRightUnsigned(9)) | (this._h[4] << 4)) & 0xffff;
  this._h[4] = ((this._h[4].shiftRightUnsigned(12)) |
          (this._h[5] << 1) |
          (this._h[6] << 14)) &
      0xffff;
  this._h[5] =
      ((this._h[6].shiftRightUnsigned(2)) | (this._h[7] << 11)) & 0xffff;
  this._h[6] =
      ((this._h[7].shiftRightUnsigned(5)) | (this._h[8] << 8)) & 0xffff;
  this._h[7] =
      ((this._h[8].shiftRightUnsigned(8)) | (this._h[9] << 5)) & 0xffff;

  f = this._h[0] + this._pad[0] as Int32;
  this._h[0] = f & 0xffff;
  for (i = 1; i < 8; i++) {
    f = (((this._h[i] + this._pad[i]) | 0) + (f.shiftRightUnsigned(16))) | 0
        as Int32;
    this._h[i] = f & 0xffff;
  }

  mac[macpos + 0] = ((this._h[0].shiftRightUnsigned(0)) & 0xff).toInt();
  mac[macpos + 1] = ((this._h[0].shiftRightUnsigned(8)) & 0xff).toInt();
  mac[macpos + 2] = ((this._h[1].shiftRightUnsigned(0)) & 0xff).toInt();
  mac[macpos + 3] = ((this._h[1].shiftRightUnsigned(8)) & 0xff).toInt();
  mac[macpos + 4] = ((this._h[2].shiftRightUnsigned(0)) & 0xff).toInt();
  mac[macpos + 5] = ((this._h[2].shiftRightUnsigned(8)) & 0xff).toInt();
  mac[macpos + 6] = ((this._h[3].shiftRightUnsigned(0)) & 0xff).toInt();
  mac[macpos + 7] = ((this._h[3].shiftRightUnsigned(8)) & 0xff).toInt();
  mac[macpos + 8] = ((this._h[4].shiftRightUnsigned(0)) & 0xff).toInt();
  mac[macpos + 9] = ((this._h[4].shiftRightUnsigned(8)) & 0xff).toInt();
  mac[macpos + 10] = ((this._h[5].shiftRightUnsigned(0)) & 0xff).toInt();
  mac[macpos + 11] = ((this._h[5].shiftRightUnsigned(8)) & 0xff).toInt();
  mac[macpos + 12] = ((this._h[6].shiftRightUnsigned(0)) & 0xff).toInt();
  mac[macpos + 13] = ((this._h[6].shiftRightUnsigned(8)) & 0xff).toInt();
  mac[macpos + 14] = ((this._h[7].shiftRightUnsigned(0)) & 0xff).toInt();
  mac[macpos + 15] = ((this._h[7].shiftRightUnsigned(8)) & 0xff).toInt();

  return this;
}