internal override bool Decrypt(int recordType, int version, byte[] data, ref int off, ref int len) { /* * Make the "additional data" for the MAC: * -- sequence number (8 bytes, big-endian) * -- header with plaintext length (5 bytes) */ len -= 16; IO.Enc64be(seq, tmp, 0); IO.WriteHeader(recordType, version, len, tmp, 8); /* * The ChaCha20+Poly1305 IV consists in the * implicit IV (12 bytes), with the sequence number * "XORed" in the last 8 bytes (big-endian). */ Array.Copy(iv, 0, nonce, 0, 12); for (int i = 0; i < 8; i++) { nonce[i + 4] ^= tmp[i]; } /* * Do encryption and compute tag. */ pp.Run(nonce, data, off, len, tmp, 0, 13, tag, false); /* * Each record has its own sequence number. */ seq++; /* * Compare the tag value. */ int z = 0; for (int i = 0; i < 16; i++) { z |= tag[i] ^ data[off + len + i]; } return(z == 0); }
internal override void Encrypt(int recordType, int version, byte[] data, ref int off, ref int len) { /* * Make the "additional data" for the MAC: * -- sequence number (8 bytes, big-endian) * -- header with plaintext length (5 bytes) */ IO.Enc64be(seq, tmp, 0); IO.WriteHeader(recordType, version, len, tmp, 8); /* * The ChaCha20+Poly1305 IV consists in the * implicit IV (12 bytes), with the sequence number * "XORed" in the last 8 bytes (big-endian). */ Array.Copy(iv, 0, nonce, 0, 12); for (int i = 0; i < 8; i++) { nonce[i + 4] ^= tmp[i]; } /* * Do encryption and compute tag. */ pp.Run(nonce, data, off, len, tmp, 0, 13, tag, true); /* * Copy back tag where appropriate and add header. */ Array.Copy(tag, 0, data, off + len, 16); off -= 5; len += 16; IO.WriteHeader(recordType, version, len, data, off); len += 5; /* * Each record has its own sequence number. */ seq++; }