2015-03-07 15 views
7

Ho un problema nella riproduzione dello stesso risultato generato in PHP vs Coldfusion.Crittografia in Coldfusion e decrittografia in PHP

In PHP cifrare questo modo:

<?php 
    $key = "[email protected]"; 
    $Valor = "TESTE"; 

    $base = chop(base64_encode(mcrypt_encrypt(MCRYPT_DES, $key, $Valor, MCRYPT_MODE_ECB)));  
?> 

ho il risultato:

TzwRx5Bxoa0 =

in ColdFusion fecero così:

<cfset Valor = "TESTE"> 
<cfset Key = "[email protected]"> 
<cfset base = Encrypt(Valor,ToBase64(Key),"DES/ECB/PKCS5Padding","BASE64")> 

Risultato:

qOQnhdxiIKs =

Ciò che non è ColdFusion dando lo stesso valore di PHP?

Grazie mille

risposta

5

(troppo lungo per i commenti)

Artjom B. already provided the answer above. Artjom B. ha scritto

Il problema è il riempimento. L'estensione mcrypt di PHP utilizza solo ZeroPadding in cui [...] è necessario eseguire il pad in testo in php [...] o utilizzare un codice diverso in ColdFusion come "DES/ECB/NoPadding". I consiglia il primo, perché se si utilizza NoPadding, il testo in chiaro deve essere già un multiplo della dimensione del blocco.

Sfortunatamente, è difficile produrre uno null character in CF. AFAIK, l'unica tecnica che funziona è use URLDecode("%00"). Se non riesci a modificare il codice PHP come suggerito da @Artjom B., puoi provare a utilizzare la funzione seguente per inserire il testo in CF.Disclaimer: è solo leggermente testato (CF10), ma sembra produrre lo stesso risultato di cui sopra.

Aggiornamento: Poiché la funzione CF cifrare() always interprets the plain text input as a UTF-8 string, è anche possibile utilizzare charsetEncode(bytes, "utf-8") per creare un carattere nullo da un singolo array elemento byte, cioècharsetEncode(javacast("byte[]", [0]), "utf-8")


Esempio:

Valor = nullPad("TESTE", 8); 
Key = "[email protected]"; 
result = Encrypt(Valor, ToBase64(Key), "DES/ECB/NoPadding", "BASE64"); 
// Result: TzwRx5Bxoa0= 
WriteDump("Encrypted Text = "& Result); 

Funzione:

/* 
    Pads a string, with null bytes, to a multiple of the given block size 

    @param plainText - string to pad 
    @param blockSize - pad string so it is a multiple of this size 
    @param encoding - charset encoding of text 
*/ 
string function nullPad(string plainText, numeric blockSize, string encoding="UTF-8") 
{ 
    local.newText = arguments.plainText; 
    local.bytes = charsetDecode(arguments.plainText, arguments.encoding); 
    local.remain = arrayLen(local.bytes) % arguments.blockSize; 

    if (local.remain neq 0) 
    { 
     local.padSize = arguments.blockSize - local.remain; 
     local.newText &= repeatString(urlDecode("%00"), local.padSize); 
    } 

    return local.newText; 
} 
+0

Personal, ora ha funzionato perfettamente nel test iniziale, farò diversi test più tardi, ma credo che la soluzione sia la stessa. Grazie per l'aiuto e prontezza. Mi ha aiutato molto. Grazie –

+0

ArtjomB. capito il vero problema, ma felice quanto sopra aiutato :) – Leigh

+0

Naturalmente, i due hanno aiutato molto =] –

5

Il problema è il riempimento. L'estensione mcrypt di PHP utilizza solo ZeroPadding. Significa che il testo in chiaro è riempito con 0x00 byte finché non viene raggiunto il multiplo della dimensione del blocco.

PKCS # 5/PKCS # 7 il riempimento, invece, lo riempie con byte che indicano il numero di byte mancanti fino al successivo multiplo della dimensione del blocco. La dimensione del blocco per DES è di 8 byte.

Quindi è necessario eseguire il pad in testo normale in php (vedere questo codice di accesso: A: How to add/remove PKCS7 padding from an AES encrypted string?) o utilizzare un codice diverso in ColdFusion come "DES/ECB/NoPadding". Raccomando il primo, perché se usi NoPadding, il testo in chiaro deve essere già un multiplo della dimensione del blocco.

$key = "[email protected]"; 
$Valor = "TESTE"; 
function pkcs7pad($plaintext, $blocksize) 
{ 
    $padsize = $blocksize - (strlen($plaintext) % $blocksize); 
    return $plaintext . str_repeat(chr($padsize), $padsize); 
} 

$base = chop(base64_encode(mcrypt_encrypt(MCRYPT_DES, $key, pkcs7pad($Valor, 8), MCRYPT_MODE_ECB))); 

risultati:

qOQnhdxiIKs =

non dimenticate di unpad il testo in chiaro recuperato se si sta Decifrare in PHP.

+0

Se non codificare la chiave con l'errore Base64 è verificato un errore durante il tentativo di crittografare o decrittografare la stringa di input: '' Non è possibile decodificare stringa "$ 224455 @" .. –

+0

ho trovato il problema. Mi ci è voluto abbastanza. –

+0

(Modifica) @ArtjomB. - Come vengono decodificati in php la stringa e la chiave del testo in chiaro? CF [* sempre * tratta il piano come codificato UTF8 e il tasto come base64] (https://helpx.adobe.com/coldfusion/kb/strong-encryption-coldfusion-mx-7.html). Quindi il richiedente probabilmente avrà bisogno di aggiustare la chiave a seconda di come la funzione php interpreta il valore. – Leigh

Problemi correlati