Page 1 of 1

PB AES vs php AES

Posted: Wed Aug 14, 2019 4:04 pm
by doctorized
I want to exchange some text between PB app and php file. In PB, I pass the string from AES and then from Base64, with the following code:

Code: Select all

InitNetwork()
key.s = "12345678901234567890123456789012"
InitializationVector.s = "0987654321098765"
String$ = "string coming from the client..."
lenth.i = StringByteLength(String$,#PB_Ascii)
*string = AllocateMemory(lenth+1,#PB_Memory_NoClear)
Debug PokeS(*string,String$,lenth,#PB_Ascii)
StringMemorySize.i = lenth + 1; Space for the string and its null terminating character
*CipheredString = AllocateMemory(StringMemorySize,#PB_Memory_NoClear)   
*DecipheredString = AllocateMemory(StringMemorySize,#PB_Memory_NoClear) 
outsize.i = StringMemorySize*3; for Base64
*str = AllocateMemory(outsize,#PB_Memory_NoClear); for Base64
If AESEncoder(*string, *CipheredString, lenth, @Key, 256, @InitializationVector,#PB_Cipher_CBC)
	Debug  StringByteLength(String$)
	Debug MemorySize(*CipheredString)
	Debug StringMemorySize
	i = Base64EncoderBuffer(*CipheredString, lenth,*str,outsize)
	Debug "base64 = " + i
	Debug "str = " + PeekS(*str,i,#PB_Ascii)
	Debug "str = " + PeekS(*str,i,#PB_UTF8)
	Debug "str = " + PeekS(*str,i,#PB_Unicode)
	
	*Decoded = AllocateMemory(1024)
	Debug "decode = " + Base64DecoderBuffer(@cmd,StringByteLength(cmd),*Decoded, 1024)

	i=AESDecoder(*Decoded, *DecipheredString, lenth, @Key, 256, @InitializationVector)
	Debug "Deciphered: "+PeekS(*DecipheredString,i,#PB_UTF8)
	Debug "Deciphered: "+PeekS(*DecipheredString,i,#PB_Unicode)
	Debug "Deciphered: "+PeekS(*DecipheredString,i,#PB_Ascii)
EndIf

Debug "ok"
Then, I copy paste the result (XbwBpBOPncqGq8vOVuikRfoiQQrC74ymULEa4pQizgI=) and try to decrypt it in php:

Code: Select all

<?php 
function fnDecrypt($sValue, $key, $iv) {
    $cipher="AES-256-CBC";
    return openssl_decrypt($sValue, $cipher, $key, 0, $iv);
}

$key = "12345678901234567890123456789012";
$iv = "0987654321098765";
$str = "/F/9WXb7y6j1tOcKTmFy608wO2BFo8jZ1HUo4+oPUG9AQ/UyY1KxVcVbNfDtRNAQdIqseKNuK5DPpkhooAxVBAAA";

$newStr = fnDecrypt($str, $key, $iv);
echo "<br/>str = " . $str;
echo "<br/>new = " . $newStr;
?>
The string is not decrypted. I also tried the opposite, the string encrypted from the php and PB fails to decrypt it. I did some tests, tried to do the same without the use of AES, just base64, and the string decoded just fine. So, what is wrong? Key, iv, 256 bits, cbc mode, all these the same. Are they different AES approaches?

Re: PB AES vs php AES

Posted: Wed Aug 14, 2019 5:22 pm
by Mijikai
This should probably also be Ascii or UTF8:

Code: Select all

InitializationVector.s = "0987654321098765"
Check if it generates the same Vector as the PHP one!
PokeS() will not include the Null-Char, be careful with #PB_Memory_NoClear.

Example:

Code: Select all

Procedure.i AESEncryptAsciiString(Text.s)
  Protected *blob
  Protected *buffer
  Protected buffer_size.i
  *blob = Ascii(Text)
  If *blob
    buffer_size = MemorySize(*blob)
    If buffer_size > 15
      *buffer = AllocateMemory(buffer_size)
      If *buffer
        If AESEncoder(*blob,*buffer,buffer_size,?AESEncryptAsciiString_Key,256,?AESEncryptAsciiString_Vector,#PB_Cipher_CBC)
          ProcedureReturn *buffer
        EndIf
        FreeMemory(*buffer)
      EndIf
    EndIf 
    FreeMemory(*blob)
  EndIf 
  ProcedureReturn #Null
  AESEncryptAsciiString_Key:
  !db '12345678901234567890123456789012'
  AESEncryptAsciiString_Vector:
  !db '0987654321098765'
EndProcedure

Re: PB AES vs php AES

Posted: Wed Aug 14, 2019 6:21 pm
by doctorized
Here is something interesting. I changed my code, I added:

Code: Select all

lenth2.i =StringByteLength(key,#PB_Ascii)
*key = AllocateMemory(lenth2+1,#PB_Memory_NoClear)
PokeS(*key,key,lenth2,#PB_Ascii)
lenth2 =StringByteLength(InitializationVector,#PB_Ascii)
*iv = AllocateMemory(lenth2,#PB_Memory_NoClear)
PokeS(*iv,InitializationVector,lenth2,#PB_Ascii)
and now I pass them to AESEncoder(). My code now creates this base64 string:

Code: Select all

zs/EU6nxLzE+RjtgnFuIwugLvdc1z6dyFmeleJ+K+Og=
your code creates this base64 string:

Code: Select all

zs/EU6nxLzE+RjtgnFuIwqiw0d8F2Zvl2MCQdjHUuCHo
and php creates this one:

Code: Select all

zs/EU6nxLzE+RjtgnFuIwugLvdc1z6dyFmeleJ+K+OiF1qgYdq8yY5GC4RBbIFrz
So, what is wrong now?

Re: PB AES vs php AES

Posted: Wed Aug 14, 2019 7:18 pm
by Mijikai
Hard to say...
Can you show another example with the actual Text that gets encrypted?

Re: PB AES vs php AES

Posted: Wed Aug 14, 2019 9:58 pm
by infratec
Hi,

this:

Code: Select all

*Vector = UTF8("1234567890abcdef")

*Key = UTF8("abcdefghijuklmno0123456789012345")
*Input = UTF8("hello world from me")

Debug MemorySize(*Input)

If MemorySize(*Input) - 1 % 16
  *Input = ReAllocateMemory(*Input, ((MemorySize(*Input) - 1) / 16 + 1) * 16 + 1)
EndIf

Debug MemorySize(*Input)

*Buffer = AllocateMemory(MemorySize(*Input) - 1)

AESEncoder(*Input, *Buffer, MemorySize(*Input) - 1, *Key, 256, *Vector, #PB_Cipher_CBC)

ShowMemoryViewer(*Buffer, MemorySize(*Input) - 1)

Debug Base64Encoder(*Buffer, MemorySize(*Input) - 1)
returns the same value as:
http://phpaes.com/index.php#encrypt

Re: PB AES vs php AES

Posted: Thu Aug 15, 2019 6:59 am
by Mijikai
Nice @infratec :)

I adjusted my code:

Code: Select all

EnableExplicit

Procedure.i AESEncryptUTF8String(Text.s)
  Protected *blob
  Protected *buffer
  Protected buffer_size.i
  *blob = UTF8(Text)
  If *blob
    buffer_size = MemorySize(*blob)
    If Not buffer_size > 15
      *buffer = ReAllocateMemory(*blob,buffer_size)
      If *buffer
        *blob = *buffer
        buffer_size = 16
      Else
        FreeMemory(*blob)
        ProcedureReturn #Null
      EndIf 
    EndIf
    *buffer = AllocateMemory(buffer_size)
    If *buffer
      If AESEncoder(*blob,*buffer,buffer_size,?AESEncryptUTF8String_Key,256,?AESEncryptUTF8String_Vector,#PB_Cipher_CBC)
        FreeMemory(*blob)
        ProcedureReturn *buffer
      EndIf
      FreeMemory(*buffer)
    EndIf
    FreeMemory(*blob)
  EndIf 
  ProcedureReturn #Null
  AESEncryptUTF8String_Key:
  !db 'abcdefghijuklmno0123456789012345'
  AESEncryptUTF8String_Vector:
  !db '1234567890abcdef'
EndProcedure

Procedure.s AESEncryptUTF8StringBase64(Text.s)
  Protected *encrypted
  Protected result.s
  *encrypted = AESEncryptUTF8String(Text)
  If *encrypted
    result = Base64Encoder(*encrypted,MemorySize(*encrypted))
    FreeMemory(*encrypted)
  EndIf 
  ProcedureReturn result
EndProcedure

Debug AESEncryptUTF8StringBase64("hello world!")

End

Re: PB AES vs php AES

Posted: Thu Aug 15, 2019 2:10 pm
by doctorized
I changed my code, I changed every #PB_Ascii to #PB_UTF8. Now my code creates the same as infratec and Mijikai's codes. I couldn't decrypt it in php. I tried the flags that openSSL uses and with the use of OPENSSL_ZERO_PADDING I managed to get back "hellow world" in php. Thank you very much!!

EDIT: If I change the "hellow world!" string to something else, let's say "hellow world from me", then both of your codes create a base64 string different with the one from http://phpaes.com/index.php#encrypt, so my php cannot decrypt them. Also my php code cannot encrypt a string like "this_string_for_me_please". Test it here: http://users.sch.gr/arahiotis/other/fil ... _me_please. What is going on anyway?

Re: PB AES vs php AES

Posted: Thu Aug 15, 2019 4:43 pm
by infratec
I extended my code above.
PHP want always 16 byte boundaries.

Re: PB AES vs php AES

Posted: Thu Aug 15, 2019 4:49 pm
by doctorized
infratec wrote:I extended my code above.
PHP want always 16 byte boundaries.
I just found it out. Both cases, encryption-and decryption, need a multiple of 16 bytes of initial string. If string len is not a multiple of 16, then error 0606508A is returned for decryption, error 0607F08A for encryption.