freeotfecypherdes.c
来自「文件驱动加密,功能强大,可产生加密分区,支持AES,MD2,MD4,MD5MD2」· C语言 代码 · 共 400 行
C
400 行
// Description:
// By Sarah Dean
// Email: sdean12@sdean12.org
// WWW: http://www.FreeOTFE.org/
//
// -----------------------------------------------------------------------------
//
#ifndef WINCE
#include <ntddk.h>
#endif
#include "FreeOTFECypherDES.h"
#include "FreeOTFECypherImpl.h"
#include "FreeOTFECypherAPICommon.h"
#ifdef WINCE
#include "FreeOTFE4PDACypherDriver.h" // Required for DRIVER_CYPHER_VERSION
#else
#include "FreeOTFECypherDriver.h" // Required for DRIVER_CYPHER_VERSION
#endif
#include "FreeOTFEPlatform.h"
#include "FreeOTFEDebug.h"
#include "FreeOTFElib.h"
// Include libtomcrypt DES library...
//#define CBC 1
//#include <mycrypt.h>
//#include <mycrypt_cipher.h>
#include <mycrypt_custom.h>
// =========================================================================
// Cypher driver init function
// driverInfo - The structure to be initialized
NTSTATUS
ImpCypherDriverExtDetailsInit(
IN OUT CYPHER_DRIVER_INFO* driverInfo
)
{
NTSTATUS status = STATUS_SUCCESS;
int idx = -1;
DEBUGOUTCYPHERIMPL(DEBUGLEV_ENTER, (TEXT("ImpCypherDriverExtDetailsInit\n")));
// -- POPULATE DRIVER IDENTIFICATION --
FREEOTFE_MEMZERO(driverInfo->DriverTitle, sizeof(driverInfo->DriverTitle));
FREEOTFE_MEMCPY(
driverInfo->DriverTitle,
DRIVER_TITLE,
strlen(DRIVER_TITLE)
);
driverInfo->DriverGUID = DRIVER_GUID;
driverInfo->DriverVersionID = DRIVER_CYPHER_VERSION;
// -- POPULATE cyphers SUPPORTED --
driverInfo->CypherDetails = FREEOTFE_MEMALLOC((sizeof(CYPHER) * CYPHERS_SUPPORTED));
driverInfo->CypherCount = CYPHERS_SUPPORTED;
// -- DES --
idx++;
FREEOTFE_MEMZERO(driverInfo->CypherDetails[idx].Title, MAX_CYPHER_TITLE);
FREEOTFE_MEMCPY(
driverInfo->CypherDetails[idx].Title,
DRIVER_CIPHER_TITLE_DES,
strlen(DRIVER_CIPHER_TITLE_DES)
);
driverInfo->CypherDetails[idx].Mode = CYPHER_MODE_CBC;
driverInfo->CypherDetails[idx].KeySize = (des_desc.max_key_length * 8);
driverInfo->CypherDetails[idx].BlockSize = (des_desc.block_length * 8);
driverInfo->CypherDetails[idx].VersionID = DRIVER_CYPHER_IMPL_VERSION;
driverInfo->CypherDetails[idx].CypherGUID = CIPHER_GUID_DES;
// -- 3DES --
idx++;
FREEOTFE_MEMZERO(driverInfo->CypherDetails[idx].Title, MAX_CYPHER_TITLE);
FREEOTFE_MEMCPY(
driverInfo->CypherDetails[idx].Title,
DRIVER_CIPHER_TITLE_3DES,
strlen(DRIVER_CIPHER_TITLE_3DES)
);
driverInfo->CypherDetails[idx].Mode = CYPHER_MODE_CBC;
driverInfo->CypherDetails[idx].KeySize = (des3_desc.max_key_length * 8);
driverInfo->CypherDetails[idx].BlockSize = (des3_desc.block_length * 8);
driverInfo->CypherDetails[idx].VersionID = DRIVER_CYPHER_IMPL_VERSION;
driverInfo->CypherDetails[idx].CypherGUID = CIPHER_GUID_3DES;
DEBUGOUTCYPHERIMPL(DEBUGLEV_EXIT, (TEXT("ImpCypherDriverExtDetailsInit\n")));
return status;
}
// =========================================================================
// Cypher driver cleardown function
// driverInfo - The structure to be cleared down
NTSTATUS
ImpCypherDriverExtDetailsCleardown(
IN OUT CYPHER_DRIVER_INFO* driverInfo
)
{
NTSTATUS status = STATUS_SUCCESS;
DEBUGOUTCYPHERIMPL(DEBUGLEV_ENTER, (TEXT("ImpCypherDriverExtDetailsCleardown\n")));
if (driverInfo->CypherDetails != NULL)
{
FREEOTFE_FREE(driverInfo->CypherDetails);
}
driverInfo->CypherDetails = NULL;
driverInfo->CypherCount = 0;
DEBUGOUTCYPHERIMPL(DEBUGLEV_EXIT, (TEXT("ImpCypherDriverExtDetailsCleardown\n")));
return status;
}
// =========================================================================
// Encryption function
// Note: CyphertextLength must be set to the size of the CyphertextData buffer on
// entry; on exit, this will be set to the size of the buffer used.
NTSTATUS
ImpCypherEncryptData(
IN GUID* CypherGUID,
IN int KeyLength, // In bits
IN char *Key,
IN char *KeyASCII, // ASCII representation of "Key"
IN int IVLength, // In bits
IN char *IV,
IN int PlaintextLength, // In bytes
IN char *PlaintextData,
OUT char *CyphertextData
)
{
NTSTATUS status = STATUS_SUCCESS;
// libtomcrypt can't handle NULL IVs in CBC mode - it ASSERTs that IV != NULL
char ltcNullIV[FREEOTFE_MAX_CYPHER_BLOCKSIZE];
int cipher;
unsigned int i;
symmetric_CBC *cbc;
int errnum;
unsigned char* inBufPtr;
unsigned char* outBufPtr;
unsigned int x;
unsigned int blockLength;
DEBUGOUTCYPHERIMPL(DEBUGLEV_ENTER, (TEXT("ImpCypherEncryptData\n")));
cbc = FREEOTFE_MEMALLOC(sizeof(symmetric_CBC));
FREEOTFE_MEMZERO(cbc, sizeof(symmetric_CBC));
if (IsEqualGUID(&CIPHER_GUID_DES, CypherGUID))
{
status = InitLTCDESCypher(&cipher);
blockLength = des_desc.block_length;
}
else if (IsEqualGUID(&CIPHER_GUID_3DES, CypherGUID))
{
status = InitLTC3DESCypher(&cipher);
blockLength = des3_desc.block_length;
}
else
{
DEBUGOUTCYPHERIMPL(DEBUGLEV_ERROR, (TEXT("Unsupported cipher GUID passed in.\n")));
status = STATUS_INVALID_PARAMETER;
}
// libtomcrypt can't handle NULL IVs in CBC mode - it ASSERTs that IV != NULL
if ( (IVLength == 0) || (IV == NULL) )
{
FREEOTFE_MEMZERO(<cNullIV, sizeof(ltcNullIV));
IV = (char*)<cNullIV;
}
if NT_SUCCESS(status)
{
// Start a CBC session
if ((errnum = cbc_start(cipher, IV, Key, (KeyLength/8), 0, cbc)) != CRYPT_OK)
{
status = STATUS_UNSUCCESSFUL;
DEBUGOUTCYPHERIMPL(DEBUGLEV_ERROR, (TEXT("Unable to start CBC session (errnum: %d)\n"), errnum));
}
}
if NT_SUCCESS(status)
{
x = (unsigned int)(int)(PlaintextLength / blockLength);
inBufPtr = PlaintextData;
outBufPtr = CyphertextData;
for (i = 0; i < x; i++)
{
if ((errnum = cbc_encrypt(inBufPtr, outBufPtr, cbc)) != CRYPT_OK)
{
DEBUGOUTCYPHERIMPL(DEBUGLEV_ERROR, (TEXT("Unable to encrypt/decrypt block (errnum: %d)\n"), errnum));
status = STATUS_UNSUCCESSFUL;
}
inBufPtr += blockLength;
outBufPtr += blockLength;
}
}
SecZeroMemory(cbc, sizeof(symmetric_CBC));
FREEOTFE_FREE(cbc);
DEBUGOUTCYPHERIMPL(DEBUGLEV_EXIT, (TEXT("ImpCypherEncryptData\n")));
return status;
}
// =========================================================================
// Decryption function
// Note: PlaintextLength must be set to the size of the PlaintextData buffer on
// entry; on exit, this will be set to the size of the buffer used.
NTSTATUS
ImpCypherDecryptData(
IN GUID* CypherGUID,
IN int KeyLength, // In bits
IN char *Key,
IN char *KeyASCII, // ASCII representation of "Key"
IN int IVLength, // In bits
IN char *IV,
IN int CyphertextLength, // In bytes
IN char *CyphertextData,
OUT char *PlaintextData
)
{
NTSTATUS status = STATUS_SUCCESS;
// libtomcrypt can't handle NULL IVs in CBC mode - it ASSERTs that IV != NULL
char ltcNullIV[FREEOTFE_MAX_CYPHER_BLOCKSIZE];
int cipher;
unsigned int i;
symmetric_CBC *cbc;
int errnum;
unsigned char* inBufPtr;
unsigned char* outBufPtr;
unsigned int x;
unsigned int blockLength;
DEBUGOUTCYPHERIMPL(DEBUGLEV_ENTER, (TEXT("ImpCypherDecryptData\n")));
cbc = FREEOTFE_MEMALLOC(sizeof(symmetric_CBC));
FREEOTFE_MEMZERO(cbc, sizeof(symmetric_CBC));
if (IsEqualGUID(&CIPHER_GUID_DES, CypherGUID))
{
status = InitLTCDESCypher(&cipher);
blockLength = des_desc.block_length;
}
else if (IsEqualGUID(&CIPHER_GUID_3DES, CypherGUID))
{
status = InitLTC3DESCypher(&cipher);
blockLength = des3_desc.block_length;
}
else
{
DEBUGOUTCYPHERIMPL(DEBUGLEV_ERROR, (TEXT("Unsupported cipher GUID passed in.\n")));
status = STATUS_INVALID_PARAMETER;
}
// libtomcrypt can't handle NULL IVs in CBC mode - it ASSERTs that IV != NULL
if ( (IVLength == 0) || (IV == NULL) )
{
FREEOTFE_MEMZERO(<cNullIV, sizeof(ltcNullIV));
IV = (char*)<cNullIV;
}
if NT_SUCCESS(status)
{
// Start a CBC session
if ((errnum = cbc_start(cipher, IV, Key, (KeyLength/8), 0, cbc)) != CRYPT_OK)
{
status = STATUS_UNSUCCESSFUL;
DEBUGOUTCYPHERIMPL(DEBUGLEV_ERROR, (TEXT("Unable to start CBC session (errnum: %d)\n"), errnum));
}
}
if NT_SUCCESS(status)
{
x = (unsigned int)(int)(CyphertextLength / blockLength);
inBufPtr = CyphertextData;
outBufPtr = PlaintextData;
for (i = 0; i < x; i++)
{
if ((errnum = cbc_decrypt(inBufPtr, outBufPtr, cbc)) != CRYPT_OK)
{
DEBUGOUTCYPHERIMPL(DEBUGLEV_ERROR, (TEXT("Unable to encrypt/decrypt block (errnum: %d)\n"), errnum));
status = STATUS_UNSUCCESSFUL;
}
inBufPtr += blockLength;
outBufPtr += blockLength;
}
}
SecZeroMemory(cbc, sizeof(symmetric_CBC));
FREEOTFE_FREE(cbc);
DEBUGOUTCYPHERIMPL(DEBUGLEV_EXIT, (TEXT("ImpCypherDecryptData\n")));
return status;
}
// =========================================================================
// Initialize libtomcrypt DES cypher
NTSTATUS
InitLTCDESCypher(
OUT int *cipher
)
{
NTSTATUS status = STATUS_CRYPTO_SYSTEM_INVALID;
DEBUGOUTCYPHERIMPL(DEBUGLEV_ENTER, (TEXT("InitLTCDESCypher\n")));
// Initialize cipher
*cipher = register_cipher(&des_desc);
if (*cipher == -1)
{
DEBUGOUTCYPHERIMPL(DEBUGLEV_ERROR, (TEXT("Could not register cipher\n")));
}
else
{
*cipher = find_cipher("des");
if (*cipher == -1)
{
DEBUGOUTCYPHERIMPL(DEBUGLEV_ERROR, (TEXT("Could not find cipher\n")));
}
else
{
status = STATUS_SUCCESS;
}
}
DEBUGOUTCYPHERIMPL(DEBUGLEV_EXIT, (TEXT("InitLTCDESCypher\n")));
return status;
}
// =========================================================================
// Initialize libtomcrypt 3DES cypher
NTSTATUS
InitLTC3DESCypher(
OUT int *cipher
)
{
NTSTATUS status = STATUS_CRYPTO_SYSTEM_INVALID;
DEBUGOUTCYPHERIMPL(DEBUGLEV_ENTER, (TEXT("InitLTC3DESCypher\n")));
// Initialize cipher
*cipher = register_cipher(&des3_desc);
if (*cipher == -1)
{
DEBUGOUTCYPHERIMPL(DEBUGLEV_ERROR, (TEXT("Could not register cipher\n")));
}
else
{
*cipher = find_cipher("3des");
if (*cipher == -1)
{
DEBUGOUTCYPHERIMPL(DEBUGLEV_ERROR, (TEXT("Could not find cipher\n")));
}
else
{
status = STATUS_SUCCESS;
}
}
DEBUGOUTCYPHERIMPL(DEBUGLEV_EXIT, (TEXT("InitLTC3DESCypher\n")));
return status;
}
// =========================================================================
// =========================================================================
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?