public static void EndEncrypt(ProviderType providerType, SafeKeyHandleImpl symKeyHandle) { uint dataLength = 0; var data = new byte[32]; var success = CryptoApi.CryptEncrypt(symKeyHandle, SafeHashHandleImpl.InvalidHandle, true, 0, data, ref dataLength, (uint)data.Length); if (!success) { throw CreateWin32Error(); } }
public static void EndCrypt(SafeKeyHandleImpl symKeyHandle, Gost28147CryptoTransformMode transformMode) { bool success; uint dataLength = 0; if (transformMode == Gost28147CryptoTransformMode.Encrypt) { var data = new byte[32]; success = CryptoApi.CryptEncrypt(symKeyHandle, SafeHashHandleImpl.InvalidHandle, true, 0, data, ref dataLength, (uint)data.Length); } else { var data = new byte[0]; success = CryptoApi.CryptDecrypt(symKeyHandle, SafeHashHandleImpl.InvalidHandle, true, 0, data, ref dataLength) || (GostCryptoConfig.ProviderType == ProviderTypes.VipNet); } if (!success) { throw CreateWin32Error(); } }
public static int EncryptData(ProviderType providerType, SafeKeyHandleImpl symKeyHandle, byte[] data, int dataOffset, int dataLength, ref byte[] encryptedData, int encryptedDataOffset, PaddingMode paddingMode, bool isDone, bool isStream) { if (dataOffset < 0) { throw ExceptionUtility.ArgumentOutOfRange(nameof(dataOffset)); } if (dataLength < 0) { throw ExceptionUtility.ArgumentOutOfRange(nameof(dataLength)); } if (dataOffset > data.Length) { throw ExceptionUtility.ArgumentOutOfRange(nameof(dataOffset), Resources.InvalidDataOffset); } var length = dataLength; if (isDone) { length += 8; } // Выровненные данные var dataAlignLength = (uint)dataLength; var dataAlignArray = new byte[length]; Array.Clear(dataAlignArray, 0, length); Array.Copy(data, dataOffset, dataAlignArray, 0, dataLength); if (isDone) { var dataPadding = dataLength & 7; var dataPaddingSize = (byte)(8 - dataPadding); // Добпаление дополнения данных в зависимости от настроек switch (paddingMode) { case PaddingMode.None: if ((dataPadding != 0) && !isStream) { throw ExceptionUtility.CryptographicException(Resources.EncryptInvalidDataSize); } break; case PaddingMode.Zeros: if (dataPadding != 0) { dataAlignLength += dataPaddingSize; // Дополнение заполняется нулевыми байтами } break; case PaddingMode.PKCS7: { dataAlignLength += dataPaddingSize; var paddingIndex = dataLength; // Дополнение заполняется байтами, в каждый из которых записывается размер дополнения while (paddingIndex < dataAlignLength) { dataAlignArray[paddingIndex++] = dataPaddingSize; } } break; case PaddingMode.ANSIX923: { dataAlignLength += dataPaddingSize; // Дополнение заполняется нулевыми, кроме последнего - в него записывается размер дополнения dataAlignArray[(int)((IntPtr)(dataAlignLength - 1))] = dataPaddingSize; } break; case PaddingMode.ISO10126: { dataAlignLength += dataPaddingSize; // Дополнение заполняется случайными байтами, кроме последнего - в него записывается размер дополнения var randomPadding = new byte[dataPaddingSize - 1]; GetRandomNumberGenerator(providerType).GetBytes(randomPadding); randomPadding.CopyTo(dataAlignArray, dataLength); dataAlignArray[(int)((IntPtr)(dataAlignLength - 1))] = dataPaddingSize; } break; default: throw ExceptionUtility.Argument(nameof(paddingMode), Resources.InvalidPaddingMode); } } // Шифрование данных if (!CryptoApi.CryptEncrypt(symKeyHandle, SafeHashHandleImpl.InvalidHandle, false, 0, dataAlignArray, ref dataAlignLength, (uint)length)) { throw CreateWin32Error(); } // Копирование результата шифрования данных if (encryptedData == null) { encryptedData = new byte[dataAlignLength]; Array.Copy(dataAlignArray, 0L, encryptedData, 0L, dataAlignLength); } else { if (encryptedDataOffset < 0) { throw ExceptionUtility.ArgumentOutOfRange(nameof(encryptedDataOffset)); } if ((encryptedData.Length < dataAlignLength) || ((encryptedData.Length - dataAlignLength) < encryptedDataOffset)) { throw ExceptionUtility.ArgumentOutOfRange(nameof(encryptedDataOffset), Resources.InvalidDataOffset); } Array.Copy(dataAlignArray, 0L, encryptedData, encryptedDataOffset, dataAlignLength); } return((int)dataAlignLength); }
public static SafeKeyHandleImpl ImportBulkSessionKey(ProviderType providerType, SafeProvHandleImpl providerHandle, byte[] bulkSessionKey, RNGCryptoServiceProvider randomNumberGenerator) { if (bulkSessionKey == null) { throw ExceptionUtility.ArgumentNull(nameof(bulkSessionKey)); } if (randomNumberGenerator == null) { throw ExceptionUtility.ArgumentNull(nameof(randomNumberGenerator)); } var hSessionKey = SafeKeyHandleImpl.InvalidHandle; if (!CryptoApi.CryptGenKey(providerHandle, Constants.CALG_G28147, 0, ref hSessionKey)) { throw CreateWin32Error(); } var keyWrap = new Gost_28147_89_KeyExchangeInfo { EncryptedKey = new byte[32] }; Array.Copy(bulkSessionKey, keyWrap.EncryptedKey, 32); SetKeyParameterInt32(hSessionKey, Constants.KP_MODE, Constants.CRYPT_MODE_ECB); SetKeyParameterInt32(hSessionKey, Constants.KP_ALGID, Constants.CALG_G28147); SetKeyParameterInt32(hSessionKey, Constants.KP_PADDING, Constants.ZERO_PADDING); uint sessionKeySize = 32; if (!CryptoApi.CryptEncrypt(hSessionKey, SafeHashHandleImpl.InvalidHandle, true, 0, keyWrap.EncryptedKey, ref sessionKeySize, sessionKeySize)) { throw CreateWin32Error(); } SetKeyParameterInt32(hSessionKey, Constants.KP_MODE, Constants.CRYPT_MODE_CFB); var hashHandle = CreateHashImit(providerHandle, hSessionKey); keyWrap.Ukm = new byte[8]; randomNumberGenerator.GetBytes(keyWrap.Ukm); if (!CryptoApi.CryptSetHashParam(hashHandle, Constants.HP_HASHSTARTVECT, keyWrap.Ukm, 0)) { throw CreateWin32Error(); } if (!CryptoApi.CryptHashData(hashHandle, bulkSessionKey, 32, 0)) { throw CreateWin32Error(); } keyWrap.Mac = EndHashData(hashHandle); keyWrap.EncryptionParamSet = GetKeyParameterString(hSessionKey, Constants.KP_CIPHEROID); SetKeyExchangeExportAlgId(providerType, hSessionKey, Constants.CALG_SIMPLE_EXPORT); SetKeyParameterInt32(hSessionKey, Constants.KP_MODE, Constants.CRYPT_MODE_ECB); SetKeyParameterInt32(hSessionKey, Constants.KP_PADDING, Constants.ZERO_PADDING); return(ImportKeyExchange(providerHandle, keyWrap, hSessionKey)); }