So I am trying to decrypt a connection over SSH using pycryptodome.
I have the key and the IV extracted from memory (I am working inside a virtual environment), which are 100% correct, which were used for encrypting the data.
Now I want to decrypt the stuff afterwards.
My code looks as follows:
key="1A0A3EBF96277C6109632C5D96AC5AF890693AC829552F33769D6B1A4275EAE2"
iv="EB6444718D73887B1DF8E1D5E6C3ECFC"
key_hex=binascii_a2b_hex(key)
iv_hex=binascii_a2b_hex(iv)
ctr = Counter.new(128, prefix=iv_hex, initial_value = 0)
aes = AES.new(key, AES.MODE_CTR, counter = ctr)
decrypted = aes.decrypt(binascii.a2b_hex(cipher).rstrip())
print(decrypted)
The problem is now that the counter is too big (32 bytes) for the blocksize which is 16 byte in AES. However, I found out that you need the IV as the prefix in your counter if you want to decrypt AES-CTR plus the initial_value set to 0.
Therefore I already have 16 Byte with only the Prefix. When I know want to set the first value in the counter object to 0 it does not work.
Is it even possible to decrypt AES-CTR with a 16 Byte IV using pycryptodome? Or maybe someone of you sees my error.
Any help would be much appreciated.
Thanks in advance!
Edit: Thanks to SquareRootOfTwentyThree I solved the pycryptodome problem. Unfortunately the decryption is still not working so I opened a new Thread. openssh/opensshportable, which key should I extract from memory?
As per Chapter 4 in RFC4344, SSH uses SDCTR mode (stateful-decryption CTR mode), which means that the counter block is a 128-bit counter, starting with a value represented in the IV as encoded in network order, and with no fixed parts (unlike NIST CTR mode).
With PyCryptodome, you do that with:
aes = AES.new(key_hex, AES.MODE_CTR, initial_value=iv_hex, nonce=b'')
Note: there seems to be an error in your code - you initialize the cipher with key (hexadecimal string) and not key_hex (bytes).
Related
I am using C_Decrypt with the CKM_AES_CBC_PAD mechanism. I know that my ciphertext which is 272 bytes long should actually decrypt to 256 bytes, which means a full block of padding was added.
I know that according to the standard when invoking C_Decrypt with a NULL output buffer the function may return an output length which is somewhat longer than the actual required length, in particular when padding is used this is understandable, as the function can't know how many padding bytes are in the final block without carrying out the actual decryption.
So the question is whether if I know that I should get exactly 256 bytes back, such as in the scenario I explained above, does it make sense that I am still getting a CKR_BUFFER_TOO_SMALL error as a result, despite passing a 256 bytes buffer? (To make it clear: I am indicating that this is the length of the output buffer in the appropriate output buffer length parameter, see the parameters of C_Decrypt to observe what I mean)
I am encountering this behavior with a Safenet Luna device and am not sure what to make of it. Is it my code's fault for not querying for the length first by passing NULL in the output buffer, or is this a bug on the HSM/PKCS11 library side?
One more thing I should perhaps mention is that when I provide a 272 (256+16) bytes output buffer, the call succeeds and I am noticing that I am getting back my expected plaintext, but also the padding block which means 16 final bytes with the value 0x10. However, the output length is updated correctly to 256, not 272 - this also proves that I am not using CKM_AES_CBC instead of CKM_AES_CBC_PAD accidentally, which I suspected for a moment as well :)
I have used CKM.AES_CBC_PAD padding mechanism with C_Decrypt in past. You have to make 2 calls to C_Decrypt (1st ==> To get the size of the plain text, 2nd ==> Actual decryption). see the documentation here which talks about determining the length of the buffer needed to hold the plain-text.
Below is the step-by-step code to show the behavior of decryption:
//Defining the decryption mechanism
CK_MECHANISM mechanism = new CK_MECHANISM(CKM.AES_CBC_PAD);
//Initialize to zero -> variable to hold size of plain text
LongRef lRefDec = new LongRef();
// Get ready to decrypt
CryptokiEx.C_DecryptInit(session_1, mechanism, key_handleId_in_hsm);
// Get the size of the plain text -> 1st call to decrypt
CryptokiEx.C_Decrypt(session_1, your_cipher, your_cipher.length, null, lRefDec);
// Allocate space to the buffer to store plain text.
byte[] clearText = new byte[(int)lRefDec.value];
// Actual decryption -> 2nd call to decrypt
CryptokiEx.C_Decrypt(session_1, eFileCipher, eFileCipher.length, eFileInClear,lRefDec);
Sometimes, decryption fails because your input encryption data was misleading (however, encryption is successful but corresponding decryption will fail) the decryption algorithm. So it is important not to send raw bytes directly to the encryption algorithm; rather encoding the input data with UTF-8/16 schema's preserves the data from getting misunderstood as network control bytes.
I'm using AT24C512 EEPROM which is 512KB along with my STM32
I'm able to write 128bytes of data at once using
HAL_I2C_Mem_Write(&_EEPROM24XX_I2C,0xa0,Address,I2C_MEMADD_SIZE_16BIT,(uint8_t*)data,size_of_data,100)
but the issue is that i want to write more data after the data that was just wrote, but the EEPROM will replace the data as the Address is the same
so how can i skip the written address ?
This answer is not about using HAL with I2C, but hope it will point you
Just check datasheet (I looking into STM32F0) and you can see that the limit is 255 bytes (register CR2:NBYTES), I'm not sure if there is another limitation in HAL, but using direct access to registers you can sent 255 bytes at once or fragment it and sent how much you want.
For fragmenting there is bit CR2:RELOAD, if you set this, then at the end will be not transfer stopped, and you can update next NBYTES, .. when you will set last block of bytes (which will fit into NBYTES) then clear bit CR2:RELOAD.
This has one disadvantage, that every 255 bytes, you will be interrupted.
i think you should check the AT24C512 datasheet page 7.
If more
than 128 data words are transmitted to the EEPROM, the
data word address will
“
roll over
”
and previous data will be
overwritten. The address
“
roll over
”
during write is from the
last byte of the current page to the first byte of the same
page.
I have seen this thread, and the encryption techniques mentioned there is working well. But not in all cases.
Requirement:
Simple, take one image, encrypt it, and store the encrypted data. Later, get the encrypted data, decrypt it, recreate the original image and show.
What I have done
From the above mentioned thread, I found NSData additions for AES 256 encryption. I tried to use it but with partial success. This is the code
//encryption
NSData *srcData = UIImageJPEGRepresentation(srcImage, 1.0);
NSLog(#"srcData length : %d",[srcData length]);
NSData *encryptedData = [srcData AES256EncryptWithKey:KEY];
NSLog(#"encrypted data length : %d",[encryptedData length]);
........
//later..
//decryption
decryptedImage = [UIImage imageWithData:[encryptedData AES256DecryptWithKey:KEY]];
imageView.image = decryptedImage;
What is happening
For a small image, say image with resolution 48*48, this code is working successfully. But when I run the code in an image with higher resolutions, say 256 * 256, the method AES256EncryptWithKey failing with error kCCBufferTooSmall (-4301).
Questions
Does AES 256 impose any limit on the size (in bytes) of the payload
to be encrypted?
If the answer to first question is YES, then what kind of
encryption algorithm to use in iphone, to encrypt image (probably
big ones)?
If the answer to the first question is NO, then why this error?
No, not really. Some hash functions do have a maximum, but that's more in the order of 2^64, so generally you don't have to worry.
N/A
It has probably something to do with the dataWithBytesNoCopy in combination with the malloc call, but it is hard to find out without actually running the code.
Note that that wrapper is pretty braindead, as it does require encrypting all at once, without using CCCryptorUpdate. It does not use an IV which jeopardizes security. It handles the keys as strings. Finally, it creates too big a buffer size for decryption. You are better off creating your own using a more reliable source.
Every iPhone has a NORID (8 bytes) & CHIPID (12 bytes) unique to each phone.
Where is this stored? NOR? seczone? Can it be dumped?
An iPhone requires a NCK to unlock. From what I understand the NCK is 15 characters.
Is it numeric, alpha or alphanumeric?
The security token for check if the NCK is valid is stored encrypted at +0x400 in the seczone.
Is this correct?
Based on what I've read from dogbert's blog, the security token is created using a method similar to the following pseudo code:
deviceKey = SHA1_hash(norID+chipID)
nckKey = custom_hash(norID, chipID, SHA1_hash(NCK), deviceKey)
rawSignature = generateSignature(SHA1_hash(norID+chipID), SHA1_hash(chipID))
Signature = RSA_encrypt(rawSignature, RSAkey)
security token = TEA_encrypt_cbc(Signature, nckKey)
Is the pseudocode correct? If it is then what is the custom hash that is being used? What is being used to generate the rawSignature? What is the RSAKey that is being used? Is it a public key that can be found in the phone?
If the above pseudocode is CORRECT. Then we would have to bruteforce all 15 character combinations to find the correct NCK key right? Because, even though we are able to recover the NORID and CHIPID, we will not be able to use that information to shorten the amount of characters which we need to find.
Correct?
New generations of iPhone OS contains a wildcardticket that is generated during activation process.
but this should be no problem generating once we have the NCK right? Correct?
The NOR ID is the hardware chip id burned into the baseband chip of the device. I don't know where you are getting the 8 bytes from but it is actually burned into the chip and the size is 64 bytes for iPhone 3G and 128 bytes for the iPhone 3GS.
The NCK is a 15 digit (base 10 so it is not alpha-numeric). ie. the max NCK would be 999999999999999
Your device key is wrong.
It should read:
deviceUniqueKey = SHA(NCK + CHIPID + NORID)
teaEncryptedData = &seczone[0x400]
rsaEncryptedData = TEA_DECRYPT(teaEncryptedData, deviceUniqueKey)
validRSAMessage = RSA_DECRYPT(rsaEncryptedData, rsaKey)
When your NCK produces a valid RSA message, you have found the correct NCK to unlock your device.
Here is the python script that can decrypt iPhone baseband memory so you will be able to get all NCK tokens like
CHIP ID
NOR ID
IMEI hushes
Tea hashes
But this script was used only for old basebands (S-Gold chipset) but you can always make your own.
Also here are some ways to dump iphone baseband into the file by using iPhone core dump function or by other script like NOR dumper. Hope this help
I'm using Apple's SecKeyWrapper class from the CryptoExercise sample code in the Apple docs to do some symmetric encryption with AES128. For some reason, when I encrypt 1-15 characters or 17 characters, it encrypts and decrypts correctly. With 16 characters, I can encrypt, but on decrypt it throws an exception after the CCCryptorFinal call with ccStatus == -4304, which indicates a decode error. (Go figure.)
I understand that AES128 uses 16 bytes per encrypted block, so I get the impression that the error has something to do with the plaintext length falling on the block boundary. Has anyone run into this issue using CommonCryptor or SecKeyWrapper?
The following lines...
// We don't want to toss padding on if we don't need to
if (*pkcs7 != kCCOptionECBMode) {
if ((plainTextBufferSize % kChosenCipherBlockSize) == 0) {
*pkcs7 = 0x0000;
} else {
*pkcs7 = kCCOptionPKCS7Padding;
}
}
... are the culprits of my issue. To solve it, I simply had to comment them out.
As far as I can tell, the encryption process was not padding on the encryption side, but was then still expecting padding on the decryption side, causing the decryption process to fail (which is generally what I was experiencing).
Always using kCCOptionPKCS7Padding to encrypt/decrypt is working for me so far, for strings that satisfy length % 16 == 0 and those that don't. And, again, this is a modification to the SecKeyWrapper class of the CryptoExercise example code. Not sure how this impacts those of you using CommonCrypto with home-rolled wrappers.
I too have encountered this issue using the CommonCrypto class but for ANY string with a length that was a multiple of 16.
My solution is a total hack since I have not yet found a real solution to the problem.
I pad my string with a space at the end if it is a multiple of 16. It works for my particular scenario since the extra space on the data does not affect the receipt of the data on the other side but I doubt it would work for anyone else's scenario.
Hopefully somebody smarter can point us in the right direction to a real solution.