Security Audit 4.1. Enhanced Persistence encryption salt generation

to be more random based on the password or master password used.
This commit is contained in:
Jim Norman
2006-05-02 21:44:13 +00:00
parent 7e3c1a6dcb
commit 6d5251fe02
6 changed files with 1570 additions and 1041 deletions

View File

@@ -39,19 +39,19 @@ namespace sscs.crypto
private const int ITERATION_COUNT = 1000;
private const int HASH_SIZE = 32;
internal static byte[] Generate16ByteKeyFromString(string sTheString)
internal static byte[] Generate16ByteKeyFromString(string sTheString, string sFilepath, bool bUseOldMethod)
{
byte[] baKey = new byte[16]; //return value
try
{
Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes(sTheString, SALTSIZE, ITERATION_COUNT);
Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes(sTheString, SALTSIZE, ITERATION_COUNT, bUseOldMethod);
baKey = pkcs5.GetBytes(16);
}
catch(Exception e)
{
{
CSSSLogger.ExpLog(e.ToString());
CSSSLogger.DbgLog("Key generation failed");
baKey = null;
baKey = null;
}
return baKey;
}
@@ -68,7 +68,7 @@ namespace sscs.crypto
//Get an encryptor.
RijndaelManaged myRijndael = new RijndaelManaged();
ICryptoTransform encryptor;
encryptor = myRijndael.CreateEncryptor(baMasterPasscode, baMasterPasscode);
encryptor = myRijndael.CreateEncryptor(baMasterPasscode, GenerateAndSaveIV(fileName, myRijndael));
//Encrypt the data to a file
fsEncrypt = new FileStream(fileName, FileMode.Create);
@@ -126,7 +126,7 @@ namespace sscs.crypto
*/
RijndaelManaged myRijndael = new RijndaelManaged();
ICryptoTransform decryptor = myRijndael.CreateDecryptor(baMasterPasscode, baMasterPasscode);
ICryptoTransform decryptor = myRijndael.CreateDecryptor(baMasterPasscode, RetrieveIV(fileName, baMasterPasscode));
//Now decrypt
fsDecrypt = new FileStream(fileName, FileMode.Open);
@@ -176,14 +176,10 @@ namespace sscs.crypto
FileStream fsEncrypt = null;
CryptoStream csEncrypt = null;
try
{
byte[] IV = new byte[16];
for(int z = 0 ; z < 16; z++ )
IV[z] = key[z];
{
//Get an encryptor.
RijndaelManaged myRijndael = new RijndaelManaged();
ICryptoTransform encryptor = myRijndael.CreateEncryptor(key, IV);
ICryptoTransform encryptor = myRijndael.CreateEncryptor(key, GenerateAndSaveIV(fileName, myRijndael));
//Encrypt the data to a file
fsEncrypt = new FileStream(fileName, FileMode.Create);
@@ -196,13 +192,24 @@ namespace sscs.crypto
byte[] hash = sha.ComputeHash(xmlData);
fsEncrypt.Write(hash,0,hash.Length);
fsEncrypt.Flush();
fsEncrypt.Flush();
#if CLEAR
byte[] dup = (byte[])xmlData.Clone();
// write clear file
FileStream fsClear = new FileStream(fileName + ".xml", FileMode.Create);
fsClear.Write(dup, 0, dup.Length);
fsClear.Flush();
fsClear.Close();
#endif
csEncrypt = new CryptoStream(fsEncrypt, encryptor, CryptoStreamMode.Write);
//Write all data to the crypto stream and flush it.
csEncrypt.Write(xmlData, 0, xmlData.Length);
csEncrypt.FlushFinalBlock();
}
catch(Exception e)
{
@@ -228,7 +235,7 @@ namespace sscs.crypto
//Get a decryptor that uses the same key and IV as the encryptor.
RijndaelManaged myRijndael = new RijndaelManaged();
ICryptoTransform decryptor = myRijndael.CreateDecryptor(key, IV);
ICryptoTransform decryptor = myRijndael.CreateDecryptor(key, RetrieveIV(fileName, key));
#if LINUX
UnixFileInfo fsTest = new UnixFileInfo (fileName);
if((fsTest == null) || !(fsTest.Exists) || fsTest.IsSymbolicLink)
@@ -248,8 +255,8 @@ namespace sscs.crypto
if(fsDecrypt.Length < HASH_SIZE )
{
csDecrypt.Close();
fsDecrypt.Close();
return null;
fsDecrypt.Close();
return null;
}
ulong fileLen = (ulong)(fsDecrypt.Length - HASH_SIZE);
@@ -273,15 +280,25 @@ namespace sscs.crypto
fsDecrypt.Close();
return null;
}
}
}
try
{
csDecrypt.Close();
}
catch { }
try
{
fsDecrypt.Close();
}
catch { }
csDecrypt.Close();
fsDecrypt.Close();
return tmpEncrypt;
}
catch(Exception e)
{
Console.WriteLine(e.ToString());
{
CSSSLogger.DbgLog(e.ToString());
}
if (csDecrypt != null)
{
@@ -301,6 +318,7 @@ namespace sscs.crypto
/* Encrypts the data with the key and returns the encrypted buffer.
*/
/*
internal static byte[] EncryptData(byte[] data, byte[] key)
{
@@ -329,10 +347,11 @@ namespace sscs.crypto
return null;
}
*/
/* Decrypts the buffer(encrypted) with the key and returns the
* decrypted data.
*/
/*
internal static byte[] DecryptData(byte[] buffer, byte[] key)
{
try
@@ -356,7 +375,7 @@ namespace sscs.crypto
}
return null;
}
*/
/* This method checks if we can get the master passcode by
* decrypting the passwds file ( where we store all possible
* passwds cross-encrypted.
@@ -373,7 +392,7 @@ namespace sscs.crypto
internal static byte[] GetMasterPasscode(string desktopPasswd, string fileName)
{
byte[] mp = DecryptMasterPasscodeUsingString(desktopPasswd, fileName);
byte[] mp = DecryptMasterPasscodeUsingString(desktopPasswd, fileName, false);
return mp;
}
@@ -394,7 +413,7 @@ namespace sscs.crypto
{
if(File.Exists(fileName))
File.Delete(fileName);
byte[] baKey = Generate16ByteKeyFromString(passwd);
byte[] baKey = Generate16ByteKeyFromString(passwd, null, false);
//Get an encryptor.
@@ -434,61 +453,68 @@ namespace sscs.crypto
}
public static byte[] DecryptMasterPasscodeUsingString(string passwd,
string fileName)
string fileName, bool bTryOldMethod)
{
FileStream fsDecrypt = null;
CryptoStream csDecrypt = null;
byte[] baSavedMasterPasscode = null;
try
{
byte[] baKey = Generate16ByteKeyFromString(passwd);
/* Get a decryptor that uses the same key and
* IV as the encryptor.
*/
RijndaelManaged myRijndael = new RijndaelManaged();
ICryptoTransform decryptor = myRijndael.CreateDecryptor(baKey,
baKey);
//Now decrypt
byte[] baSavedMasterPasscode = null;
try
{
byte[] baKey = Generate16ByteKeyFromString(passwd, fileName, bTryOldMethod);
/* Get a decryptor that uses the same key and
* IV as the encryptor.
*/
RijndaelManaged myRijndael = new RijndaelManaged();
ICryptoTransform decryptor = myRijndael.CreateDecryptor(baKey, RetrieveIV(fileName, baKey));
//Now decrypt
#if LINUX
UnixFileInfo fsTest = new UnixFileInfo (fileName);
if((fsTest == null) || !(fsTest.Exists) || fsTest.IsSymbolicLink)
#else
if(!File.Exists(fileName))
#endif
{
return null;
}
fsDecrypt = new FileStream(fileName, FileMode.Open);
csDecrypt = new CryptoStream(fsDecrypt, decryptor,
CryptoStreamMode.Read);
baSavedMasterPasscode = new byte[16];
//Read the data out of the crypto stream.
csDecrypt.Read(baSavedMasterPasscode, 0, 16);
}
catch(Exception e)
{
CSSSLogger.ExpLog(e.ToString());
CSSSLogger.DbgLog("Unable to decrypt master passode");
baSavedMasterPasscode = null;
}
#else
if (!File.Exists(fileName))
#endif
{
return null;
}
fsDecrypt = new FileStream(fileName, FileMode.Open);
csDecrypt = new CryptoStream(fsDecrypt, decryptor,
CryptoStreamMode.Read);
baSavedMasterPasscode = new byte[16];
//Read the data out of the crypto stream.
csDecrypt.Read(baSavedMasterPasscode, 0, 16);
}
catch (Exception e)
{
CSSSLogger.ExpLog(e.ToString());
CSSSLogger.DbgLog("Unable to decrypt master passode");
baSavedMasterPasscode = null;
}
try
{
if (csDecrypt != null)
csDecrypt.Close();
}
catch { }
if (fsDecrypt != null)
fsDecrypt.Close();
if (csDecrypt != null)
csDecrypt.Close();
if ( fsDecrypt != null )
fsDecrypt.Close();
return baSavedMasterPasscode;
}
internal static byte[] GetMasterPasscodeUsingMasterPasswd(
string mPasswd,
string fileName)
string fileName,
bool bUseOldMethod)
{
byte[] baMasterPasscode;
try
@@ -498,8 +524,7 @@ namespace sscs.crypto
/* Decrypt the passcode from the file using master passwd.
* and return the decrypted passcode.
*/
baMasterPasscode = DecryptMasterPasscodeUsingString(mPasswd,
fileName);
baMasterPasscode = DecryptMasterPasscodeUsingString(mPasswd, fileName, bUseOldMethod);
return baMasterPasscode;
}
else
@@ -515,7 +540,8 @@ namespace sscs.crypto
internal static byte[] GetMasterPasscodeUsingDesktopPasswd(
string desktopPasswd,
string fileName)
string fileName,
bool bUseOldMethod)
{
byte[] passcode;
try
@@ -526,7 +552,7 @@ namespace sscs.crypto
* and return the decrypted passcode.
*/
passcode = DecryptMasterPasscodeUsingString(desktopPasswd,
fileName);
fileName, bUseOldMethod);
return passcode;
}
@@ -581,7 +607,9 @@ namespace sscs.crypto
/* Here we decrpyt a well known string, throw exception
* if not successful
* A well-known string is encrpyted by the Passcode and saved
*/
*/
CSSSLogger.DbgLog("Validate called");
if ((baPasscode == null) || baPasscode.Length < 1 )
return false;
@@ -593,11 +621,13 @@ namespace sscs.crypto
char[] trimChars = {'\0'};
sString = sString.TrimEnd(trimChars);
if( ConstStrings.MICASA_VALIDATION_STRING.Equals(sString))
{
{
CSSSLogger.DbgLog("Passed");
return true;
}
else
{
{
CSSSLogger.DbgLog("Failed");
return false;
}
}
@@ -607,7 +637,49 @@ namespace sscs.crypto
CSSSLogger.DbgLog("Validation of passcode failed.");
}
return false;
}
}
private static byte[] GenerateAndSaveIV(string sFileName, RijndaelManaged theRiManaged)
{
theRiManaged.GenerateIV();
byte[] baIV = theRiManaged.IV;
try
{
// now save this
FileStream fs = new FileStream(sFileName + ".IV", FileMode.Create);
fs.Write(baIV, 0, 16);
fs.Flush();
fs.Close();
File.SetAttributes(sFileName + ".IV", FileAttributes.Hidden);
}
catch (Exception e)
{
CSSSLogger.DbgLog(e.ToString());
}
return baIV;
}
private static byte[] RetrieveIV(string sFileName, byte[] baOrigValue)
{
byte[] IV = new byte[16];
// check for file existence
try
{
FileStream fs = new FileStream(sFileName + ".IV", FileMode.Open);
fs.Read(IV, 0, 16);
fs.Close();
return IV;
}
catch (Exception e)
{
CSSSLogger.DbgLog(e.ToString());
}
return (byte[])baOrigValue.Clone();
}
}
}