проверить знак RSA из Java в PHP - PullRequest
1 голос
/ 04 февраля 2012

Через несколько дней у меня возникла проблема, которую я не могу решить самостоятельно:

На JavaCard я генерирую RSA KeyPair (длина: 1024) и подпись (Mode: ALG_RSA_MD5_PKCS1),Теперь мне нужно проверить подпись в php.

. С моей карты JavaCard я получаю экспоненту, модуль и сигнатуру в шестнадцатеричном формате:

    $mod = '951ADDA04637190B6202BB52787D3C19160A383C80C2E7242D0A7850FDD80C1CD1CCCF1395F8CA0B20270E3BC6C86F78232D65D148258BEFD0884563C60AB2C327506FB4FA0095CF0B1C527D942155731451F790EC0A227D38613C9EBFB2E04A657B3BA5456B35F71E92E14B7E1CB38DB6572559BFCA3B0AD8AA061D48F68931';
    $exp = '010001';
    $sign ='75867D42BDE6DF1066D4AF69418FCDD4B0F19173141128DFEBC64AF6C014CB92D38F4824E52BB064A610E07C7783AE57AE993A792F15208FB199CB1F45B64623AACB7FBA07AD89513C8DBA893C9FA6939857AA2CA53AAD99D9A9C1C32DF4E2769FCACB72E2C2C495727D368D953A911D32E79E230751202714DD15C0B6A34782';
    $plaintext = '01020304';

. Проверка в Java - не проблема.Но знайте, я должен проверить подпись в PHP (я беру phpseclib).

В PHP я генерирую свой public_key с помощью CRYPT_RSA_PUBLIC_FORMAT_RAW:

    $rsa = new Crypt_RSA();
    $pk = array(
        'e' => new Math_BigInteger($exp, 16),
        'n' => new Math_BigInteger($mod, 16)
    );
    $rsa->loadKey($pk, CRYPT_RSA_PUBLIC_FORMAT_RAW);

    $rsa->setSignatureMode(CRYPT_RSA_SIGNATURE_PKCS1);
    echo $rsa->verify($plaintext, $sign) ? 'verified' : 'unverified';

Проблема в том, чтобы установить правильные значения вфункцию проверки.Если я просто поставил свою подпись в шестнадцатеричном формате, я получу уведомление:

Invalid signature: length = 256, k = 128 in C:\xampp\php\PEAR\Crypt\RSA.php on line 2175

Поэтому мне нужно настроить длину своей подписи:

    $sign_bigInteger = new Math_BigInteger($sign, 16);
    $sign_bytes = $sign_bigInteger->toBytes();

    echo $rsa->verify($plaintext, $sign_bytes) ? 'verified' : 'unverified';

Но проверка неверна.

Я получаю выходные данные функции проверки в RSA.php (_rsassa_pkcs1_v1_5_verify), где открытый текст сравнивается с подписью:

    //sign
    "ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ0 0*†H†÷ ÖÀZ!Q*y¡ßë*&/" 
    //plaintext
    "ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ0!0 +•q£îê“O•äQ».åüÓSœÝ["

Я не совсем понимаю, что происходит в классе RSA.php,Кто-нибудь может мне помочь и сказать, что я делаю неправильно?

РЕДАКТИРОВАТЬ:

Теперь я попытался преобразовать свою hexString.

    $plaintext_bin = pack("H*", $plaintext);
    $sign_bin = pack("H*", $sign);

Я думаю, что мой открытый ключ сгенерирован правильно, поэтому я просто изменяю ввод моего подтверждения:

    $rsa->verify($plaintext_bin, $sign_bin) ? 'verified' : 'unverified';

Вывод:

    em: string(128) "ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ0 0*†H†÷ ÖÀZ!Q*y¡ßë*&/"
    em2: string(128) "ÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿ0!0 +ÚÚÿMG‡­ã31G ,;D>7o" 

Этовсе еще не то же самое.

РЕДАКТИРОВАТЬ:

Я исправил свою проблему.Я забыл установить хэш:

    $rsa1->setHash('md5');

Теперь все работает!

Спасибо, Грегс.

1 Ответ

1 голос
/ 04 февраля 2012

Все ваши значения являются шестнадцатеричными строками.Просто конвертируйте их, используя hex2bin() или pack("H*", $hex_string);

...