📄 kblock.cpp
字号:
{ alg_free_key( Alg, keyHandle ); ShredData( keyAndDigest, MAXIMUM_KEY_SIZE_BYTES + MAXIMUM_DIGEST_SIZE_BYTES); ShredData( iVector, IVECTOR_LENGTH); return ERROR_INVALID_ALGORITHM; } /* erase storageKey from the Algorithm driver memory */ alg_free_key( Alg, keyHandle ); /* calculate digest of the key and compare it with digest */ if ( !CalculateDigest( keyAndDigest, MAXIMUM_KEY_SIZE_BYTES, calculatedDigest ) ) { ShredData( keyAndDigest, MAXIMUM_KEY_SIZE_BYTES + MAXIMUM_DIGEST_SIZE_BYTES); ShredData( iVector, IVECTOR_LENGTH); return ERROR_INVALID_ALGORITHM; }//----------------------------------------------------------- if ( memcmp( calculatedDigest, &(keyAndDigest[MAXIMUM_KEY_SIZE_BYTES]), SHA256_DIGEST_SIZE) == 0 ) { kbFound = kb; break; }// kbFound = kb; } if ( !kbFound ) { ShredData( iVector, IVECTOR_LENGTH); return ERROR_INCORRECT_PASSWORD; } memcpy( Key, keyAndDigest, MAXIMUM_KEY_SIZE_BYTES ); /* In the following part we will decrypt and place a correct pool data to the PoolBuffer, Now everything is Ok, and we have correct IVector. */ if ( getAttribute(DataBlock->header.state) == STATE_POOL_NOT_INITIALIZED ) { ShredData( iVector, IVECTOR_LENGTH); return ERROR_INCORRECT_POOL; } /* Load the Key into the Algorithm driver and again, the Pool is filled by zeros, because we are going to decrypt random data (Pool stored in the DataBlock) */ /* Load the Key to encryption algorithm module */ if ( alg_make_key (Alg, Key, AlgKeyLength, PoolBuffer, &keyHandle ) ) { ShredData( iVector, IVECTOR_LENGTH); return ERROR_INVALID_ALGORITHM; } /* copy encrypted pool from DataBlock to the PoolBuffer */ memcpy( PoolBuffer, DataBlock->pool, POOL_SIZE_BYTES ); /* Decrypt pool */ if ( alg_decrypt( Alg, keyHandle, iVector, PoolBuffer, POOL_SIZE_BYTES ) ) { alg_free_key( Alg, keyHandle ); ShredData( iVector, IVECTOR_LENGTH); return ERROR_INVALID_ALGORITHM; } /* Erase and free the Key data from the encryption algorithm module */ ShredData( iVector, IVECTOR_LENGTH); alg_free_key( Alg, keyHandle ); return ERROR_NO;}DWORD DataBlockChangePassword( DATA_BLOCK *DataBlock, ALG_SERV Alg, DWORD AlgKeyLength, char * Password, char * NewPassword, BYTE *PoolBuffer ){ KEY_BLOCK *kb; BYTE storageKey[ MAXIMUM_KEY_SIZE_BYTES ]; BYTE keyAndDigest[ MAXIMUM_KEY_SIZE_BYTES + MAXIMUM_DIGEST_SIZE_BYTES ]; BYTE calculatedDigest[ MAXIMUM_DIGEST_SIZE_BYTES ]; DWORD keyHandle; BYTE iVector[ IVECTOR_LENGTH ]; BOOL result = FALSE; kb = DataBlock->keys; /* we fill the PoolBuffer with zeros, because the buffers in the DataBlock we are going to decrypt contain random data */ memset( PoolBuffer, 0, POOL_SIZE_BYTES ); for ( int i=0; i<MAXIMUM_NUMBER_OF_KEYS; i++, kb++ ) { if ( getAttribute(kb->keyAttribute) == KATTRIBUTE_KEY_EMPTY ) continue; /* Calculate encryption key for decrypting KEY_BLOCK */ if ( !GetStorageKeyFromPassword( Password, storageKey ) ) return ERROR_INVALID_ALGORITHM; /* Decrypt KEY_BLOCK kb */ /* First, load storageKey into the Algorithm driver */ if ( alg_make_key( Alg, storageKey, AlgKeyLength, PoolBuffer, &keyHandle ) ) return ERROR_INVALID_ALGORITHM; /* Now we don't need in storageKey, because it is copied to the Algorithm Driver */ ShredData( storageKey, MAXIMUM_KEY_SIZE_BYTES ); /* decrypt the key and its digest copied to the KEY_BLOCK */ memcpy( keyAndDigest, kb->key, MAXIMUM_KEY_SIZE_BYTES + MAXIMUM_DIGEST_SIZE_BYTES ); /* initialize iVector with any value. After first decrypting we will define it exactly */ for ( i=0; i<IVECTOR_LENGTH; i++ ) iVector[i] = 0; /* first decryption */ if ( alg_decrypt( Alg, keyHandle, iVector, keyAndDigest, MAXIMUM_KEY_SIZE_BYTES + MAXIMUM_DIGEST_SIZE_BYTES) ) { alg_free_key( Alg, keyHandle ); ShredData( keyAndDigest, MAXIMUM_KEY_SIZE_BYTES + MAXIMUM_DIGEST_SIZE_BYTES); return ERROR_INVALID_ALGORITHM; } /* define Initial Vector */ memcpy( iVector, &(keyAndDigest[MAXIMUM_KEY_SIZE_BYTES]), IVECTOR_LENGTH ); /* second decryption with exact Initial Vector */ memcpy( keyAndDigest, kb->key, MAXIMUM_KEY_SIZE_BYTES + MAXIMUM_DIGEST_SIZE_BYTES ); if ( alg_decrypt( Alg, keyHandle, iVector, keyAndDigest, MAXIMUM_KEY_SIZE_BYTES + MAXIMUM_DIGEST_SIZE_BYTES) ) { alg_free_key( Alg, keyHandle ); ShredData( keyAndDigest, MAXIMUM_KEY_SIZE_BYTES + MAXIMUM_DIGEST_SIZE_BYTES); return ERROR_INVALID_ALGORITHM; } /* erase storageKey from the Algorithm driver memory */ alg_free_key( Alg, keyHandle ); /* calculate digest of the key and compare it with digest */ if ( !CalculateDigest( keyAndDigest, MAXIMUM_KEY_SIZE_BYTES, calculatedDigest ) ) { ShredData( keyAndDigest, MAXIMUM_KEY_SIZE_BYTES + MAXIMUM_DIGEST_SIZE_BYTES); return ERROR_INVALID_ALGORITHM; } if ( memcmp( calculatedDigest, &(keyAndDigest[MAXIMUM_KEY_SIZE_BYTES]), SHA256_DIGEST_SIZE) == 0 ) { /* Check if Alternative Key Block is initialized. If no, initialize it */ createAlternativeKeyBlock( DataBlock, Alg, AlgKeyLength, keyAndDigest, PoolBuffer ); /* Copy decrypted key to the KEY_BLOCK, then we will encrypt it using new password */ memcpy( kb->key, keyAndDigest, MAXIMUM_KEY_SIZE_BYTES + MAXIMUM_DIGEST_SIZE_BYTES); /* We found the KEY_BLOCK encrypted with password, now we will encrypt it using newPassword First of all, calculate storageKey from the newPassword */ if ( !GetStorageKeyFromPassword( NewPassword, storageKey ) ) return ERROR_INVALID_ALGORITHM; /* Load storageKey into the Algorithm driver */ if ( alg_make_key( Alg, storageKey, AlgKeyLength, PoolBuffer, &keyHandle ) ) { ShredData( storageKey, MAXIMUM_KEY_SIZE_BYTES ); return ERROR_INVALID_ALGORITHM; } /* Now we don't need in storageKey, because it is copied to the Algorithm Driver */ ShredData( storageKey, MAXIMUM_KEY_SIZE_BYTES ); /* encrypt the key and its digest in the DataBlock */ if ( alg_encrypt( Alg, keyHandle, iVector, kb->key, MAXIMUM_KEY_SIZE_BYTES + MAXIMUM_DIGEST_SIZE_BYTES) ) { alg_free_key( Alg, keyHandle ); return ERROR_INVALID_ALGORITHM; } /* erase storageKey from the Algorithm driver memory */ alg_free_key( Alg, keyHandle ); result = TRUE; } } if ( !result ) return ERROR_INCORRECT_PASSWORD; /* DataBlock is changed, update DataBlock's digest */ if ( !DataBlockUpdateDigest( DataBlock ) ) return ERROR_INTERNAL_PROBLEM; return ERROR_NO;}DWORD GenerateKey( BYTE *Key, int KeyLength, BYTE *Seed, int SeedLength ){ int k, s, i, kReminder; k = KeyLength / SHA256_DIGEST_SIZE; s = SeedLength / k; if ( s >= SHA256_DIGEST_SIZE ) { for ( i=0; i < k; i++ ) { if ( i == (k-1) ) kReminder = KeyLength - k*SHA256_DIGEST_SIZE; else kReminder = 0; if ( SHA256RandomGenerate( &(Key[ SHA256_DIGEST_SIZE * i ]), SHA256_DIGEST_SIZE + kReminder, &(Seed[ s*i ]), SeedLength - s*i) != ERROR_NO ) return ERROR_INTERNAL_PROBLEM; } } else { if ( SHA256RandomGenerate(Key, KeyLength, Seed, SeedLength) != ERROR_NO ) return ERROR_INTERNAL_PROBLEM; } return ERROR_NO;}/********************************************************************** * * Local useful procedures * **********************************************************************/DWORD getAttribute( DWORD AttBuffer ){ return(AttBuffer & (~KATTRIBUTE_MASK));}void setAttribute( DWORD *AttBuffer, DWORD Attribute ){ // Not all bites in the AttBuffer are used: // in the current version only 2 bites from 32 are valid. // Because all 32 bits was previously initialized by random // data, let unused bits continue to be random to avoid // the known-plaintext attack. *AttBuffer &= KATTRIBUTE_MASK; *AttBuffer |= Attribute;}BOOL CalculateDigest( BYTE *Data, DWORD Length, BYTE *Digest ){ if (SHA256_MakeDigest( Data, (int)Length, Digest ) != SHA256_ERROR_NO) return FALSE; return TRUE;}BOOL DataBlockVerifyDigest( DATA_BLOCK *DataBlock ){ BYTE digest[ MAXIMUM_DIGEST_SIZE_BYTES ]; if ( !CalculateDigest( (BYTE *)DataBlock, sizeof(DB_HEADER) + sizeof(KEY_BLOCK)*MAXIMUM_NUMBER_OF_KEYS, digest) ) return FALSE; if ( memcmp( DataBlock->digest, digest, SHA256_DIGEST_SIZE ) != 0 ) return FALSE; return TRUE;}BOOL DataBlockUpdateDigest( DATA_BLOCK *DataBlock ){ BYTE digest[ MAXIMUM_DIGEST_SIZE_BYTES ]; if ( !CalculateDigest( (BYTE *)DataBlock, sizeof(DB_HEADER) + sizeof(KEY_BLOCK)*MAXIMUM_NUMBER_OF_KEYS, digest) ) return FALSE; memcpy( DataBlock->digest, digest, SHA256_DIGEST_SIZE ); return TRUE;}BOOL GetStorageKeyFromPassword( char *Password, BYTE *StorageKey ){ if ( ((DWORD)SHA256RandomGenerate( StorageKey, MAXIMUM_KEY_SIZE_BYTES, (BYTE *)Password, strlen(Password))) != ERROR_NO ) return FALSE; return TRUE;}//________________________________________________________________BOOL createAlternativeKeyBlock( DATA_BLOCK *DataBlock, ALG_SERV Alg, DWORD AlgKeyLength, BYTE *Key, BYTE *PoolBuffer ){ DWORD keyHandle, i; KEY_BLOCK *kb; KEY_BLOCK_ALTERNATIVE *kbFound; BYTE iVector[ IVECTOR_LENGTH ]; /* check if Alternative Key Block already exists */ kb = DataBlock->keys; for ( i=0; i<MAXIMUM_NUMBER_OF_KEYS; i++, kb++ ) { if ( getAttribute(kb->keyAttribute) == KATTRIBUTE_ALTERNATIVE_BLOCK ) return TRUE; } /* find empty KEY_BLOCK inside DataBlock*/ kb = DataBlock->keys; kbFound = NULL; for ( i=0; i<MAXIMUM_NUMBER_OF_KEYS; i++, kb++ ) { if ( getAttribute(kb->keyAttribute) == KATTRIBUTE_KEY_EMPTY ) { kbFound = (KEY_BLOCK_ALTERNATIVE *)kb; break; }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -