protected bool Equals(KeygenDerivedkeys other) { return (NativeHelpers.MemCmp(aesKey, other.aesKey, 0, aesKey.Length) && NativeHelpers.MemCmp(aesIV, other.aesIV, 0, aesIV.Length) && NativeHelpers.MemCmp(hmacKey, other.hmacKey, 0, hmacKey.Length)); }
public bool Unpack(byte[] tag, byte[] plain) { byte[] internalBytes = NtagHelpers.GetInternalTag(tag); // Generate keys KeygenDerivedkeys dataKeys = GenerateKey(this.data, internalBytes); KeygenDerivedkeys tagKeys = GenerateKey(this.tag, internalBytes); // Decrypt dataKeys.Cipher(internalBytes, plain, false); // Init OpenSSL HMAC context HMac hmacCtx = new HMac(new Sha256Digest()); // Regenerate tag HMAC. Note: order matters, data HMAC depends on tag HMAC! hmacCtx.Init(new KeyParameter(tagKeys.hmacKey)); hmacCtx.BlockUpdate(plain, 0x1D4, 0x34); hmacCtx.DoFinal(plain, HMAC_POS_TAG); // Regenerate data HMAC hmacCtx.Init(new KeyParameter(dataKeys.hmacKey)); hmacCtx.BlockUpdate(plain, 0x029, 0x1DF); hmacCtx.DoFinal(plain, HMAC_POS_DATA); Array.Copy(tag, 0x208, plain, 0x208, 0x014); return (NativeHelpers.MemCmp(plain, internalBytes, HMAC_POS_DATA, 32) && NativeHelpers.MemCmp(plain, internalBytes, HMAC_POS_TAG, 32)); }
public static KeygenDerivedkeys GenerateBytes(byte[] hmacKey, byte[] seed, int seedSize) { int offset = 0; int outputSize = 16 * 3; byte[] temp = new byte[NFC3D_DRBG_OUTPUT_SIZE]; byte[] output = new byte[outputSize]; DrbgCtx rngCtx = new DrbgCtx(hmacKey, seed, seedSize); while (outputSize > 0) { if (outputSize < NFC3D_DRBG_OUTPUT_SIZE) { rngCtx.Step(temp, 0); Array.Copy(temp, 0, output, offset, outputSize); break; } rngCtx.Step(output, offset); offset += NFC3D_DRBG_OUTPUT_SIZE; outputSize -= NFC3D_DRBG_OUTPUT_SIZE; } var outkeys = new KeygenDerivedkeys { aesKey = new byte[16], aesIV = new byte[16], hmacKey = new byte[16] }; Array.Copy(output, 0, outkeys.aesKey, 0, outkeys.aesKey.Length); Array.Copy(output, 16, outkeys.aesIV, 0, outkeys.aesIV.Length); Array.Copy(output, 32, outkeys.hmacKey, 0, outkeys.hmacKey.Length); return(outkeys); }