PHP openssl_public_encrypt "key parameter is not a valid key"
Asked Answered
A

6

12

I have this RSA public key:

MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAtixUGzGpLXgZ7AV1HfmIHV/FEF+fww77FekRc2oLhUOd4HitwCPo76fjtdsQBEt8w9HZ3CXVphaAU2BA6MEZJ3ShVMsdAXb2ZA1C+lu7k1GV9M/BhucTg35HujSK647Sc5MwVLwFsN80dAnGsZF8gwb2TNUzXHwzbAb30T01zuqf8RCM75OwKZFYqzu7FOVrtk/w9mh92MOXG0l7WSqNIctu8Kxka/tEJJIA5nqMGNMocjwprXy66NS7FFy1GY+NnxfFLtODqq0tllc50UCDsnqSvNmj2wcnAcsCzNOoxPPgp7t8S+sQvOzgc5W3CDjIsYEiGD+vzSVNkGiRou577wIDAQAB

(Every other key I try gives the same error, too)

and this string:

$str = "VOTE\n" .
"server-list\n" .
"$user\n" .
"$userip\n" .
time()."\n";

I use this code to make the string become exactly 256 bytes so that it follows the standard for this specific application:

$leftover = (256 - strlen($str)) / 2;
while ($leftover > 0) {
    $str .= "\x0";
    $leftover--;
}

To format the key, I do this:

    $key = wordwrap($key, 65, "\n", true);
    $key = <<<EOF
    -----BEGIN PUBLIC KEY-----
    $key
    -----END PUBLIC KEY-----
EOF;

When I do openssl_public_encrypt($str, $encrypted, $key); I get the following warning:

Warning: openssl_public_encrypt() function.openssl-public-encrypt: key parameter is not a valid public key in ...

I'm not sure why this is happening. This is what the key looks like when I echo it:

-----BEGIN PUBLIC KEY-----
MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAtixUGzGpLXgZ7AV1HfmIH
V/FEF
fww77FekRc2oLhUOd4HitwCPo76fjtdsQBEt8w9HZ3CXVphaAU2BA6MEZJ3ShVMsd
AXb2ZA1C
lu7k1GV9M/BhucTg35HujSK647Sc5MwVLwFsN80dAnGsZF8gwb2TNUzXHwzbAb30T
01zuqf8RCM75OwKZFYqzu7FOVrtk/w9mh92MOXG0l7WSqNIctu8Kxka/tEJJIA5nq
MGNMocjwprXy66NS7FFy1GY
NnxfFLtODqq0tllc50UCDsnqSvNmj2wcnAcsCzNOoxPPgp7t8S
sQvOzgc5W3CDjIsYEiGD vzSVNkGiRou577wIDAQAB
-----END PUBLIC KEY-----

Any help would be appreciated!

Edit: A working key should look like this:

-----BEGIN PUBLIC KEY-----
MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAmHzD76i8DA25nC+Qsswi
OM0lW+gViiQD4tEm7suxBc2BGibtdlrsprVIId92hSjQKx4x8+XVWU6k89T5vy8Y
txpXN759OWdGkDi8uvZuYclMjW9Rao+oqSvbXH37R7oSY287I+6uOHclGhniQN3q
RyoXBkbhDk0/FTI/i549q/gGk1UZYv449KLrDOqmtohRcIyAYVnvvWtD1kIzourq
hMtEIrPqwoBqTaUA9kOIXw1jMovao2TN52j48KgOg9KjqtdwUwD9e6n7hJd/subF
6woc8L7zjJFOHH5gacUC7vtiMpBpnSyLQpjFLepYYwftjsRmg4xLdh+Zvgw3xqi4
lwIDAQAB
-----END PUBLIC KEY-----
Argosy answered 27/3, 2012 at 0:16 Comment(7)
What happened to the + signs in your key? They're gone in the formatted block.Reynold
Hmm.. I'm not sure. And I really don't know if they're supposed to be there because I quite frankly don't know what I'm doing. I'm trying to work with the protocol of this: github.com/vexsoftware/votifierArgosy
The + signs are representing bytes as much as all the other characters. Base64 encoding uses A-Ba-b0-9 and / & + to encode bytes, and possibly the = character for padding the last part.Latta
It's probably the wordwrap function, it seems aimed at splitting strings on word boundaries. You are better off just counting characters and inserting the newline characters (both of them if I'm not mistaken) manually.Latta
I'm not sure how to do that. o3oArgosy
@DrAgonmoray you don't know how to split/combine strings? Maybe it is time for some tutorials?Latta
@owlstead I really wasn't sure what you're talking about >.>Argosy
A
5

It occured to me why it wasn't working, so I am here to answer my own question. Now that I think about it, it ties into what @sarnold originally said: the + signs are gone (and they got replaced by spaces)

it turns out that because i was getting the key via HTTP POST, it formatted the URL (and thus the key) turning all the + signs into spaces. That threw off the key and caused this conundrum.

Thanks for the help. :)

Argosy answered 28/3, 2012 at 23:0 Comment(0)
L
2

First, I would recommend using phpseclib, a pure PHP RSA implementation. It's a ton more portable and easier to use and all that jazz. Example:

<?php
$key = 'MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAtixUGzGpLXgZ7AV1HfmIHV/FEF+fww77FekRc2oLhUOd4HitwCPo76fjtdsQBEt8w9HZ3CXVphaAU2BA6MEZJ3ShVMsdAXb2ZA1C+lu7k1GV9M/BhucTg35HujSK647Sc5MwVLwFsN80dAnGsZF8gwb2TNUzXHwzbAb30T01zuqf8RCM75OwKZFYqzu7FOVrtk/w9mh92MOXG0l7WSqNIctu8Kxka/tEJJIA5nqMGNMocjwprXy66NS7FFy1GY+NnxfFLtODqq0tllc50UCDsnqSvNmj2wcnAcsCzNOoxPPgp7t8S+sQvOzgc5W3CDjIsYEiGD+vzSVNkGiRou577wIDAQAB';

$rsa = new Crypt_RSA();
$rsa->loadKey($key);
$rsa->setPublicKey($key);

echo $rsa->getPublicKey();

If you insist on using the openssl extension... try this:

"-----BEGIN PUBLIC KEY-----\r\n" . chunk_split($whatever) . "\r\n-----END PUBLIC KEY-----"
Lesko answered 27/3, 2012 at 12:23 Comment(0)
A
2

Simply use str_replace(' ', '+', $string)

Worked for me!

Asberry answered 6/2, 2021 at 18:38 Comment(0)
G
1

I was getting this error in PHP (Laravel Framework) by putting the -----BEGIN PUBLIC KEY----- in first code and putting the -----END PUBLIC KEY----- in last line, the problem was solved

correct syntax

-----BEGIN PUBLIC KEY-----
$key
-----END PUBLIC KEY-----
Germayne answered 20/9, 2023 at 8:13 Comment(0)
S
0

If you are using

openssl_public_encrypt()

Ensure that no spaces in between the key. Adding '+' to eliminate the white spaces ain't recommended as it might change the key-value and lead to the error openssl_public_encrypt(): key parameter is not a valid public key.

I had this issue and my issue was that I had done some code editing which in return added some white spaces in the key. After long attempts and much googling, I generated a new key and maintained it the same without changing or editing the white space and it finally worked.

Hope it helps. openssl is so picky from the few articles I have read. So be carefull not to alter anything in the key as it might be the source of your headaches.

Storms answered 24/6, 2021 at 11:56 Comment(0)
C
0
function encrypt($data, $pubkey)
{
    $pubkey = openssl_get_publickey($pubkey);

    if (openssl_public_encrypt($data, $encrypted, $pubkey))
    {
        $data = base64_encode($encrypted);
    }
    else
        throw new Exception('Unable to encrypt data. Perhaps it is bigger than the key size?');

    return $data;
}

Where public key format like this:

$PUBLIC_KEY  = "-----BEGIN PUBLIC KEY-----
MIGfMA0GCSqG....LosgV4t08P0wIDAQAB
-----END PUBLIC KEY-----";
$token = encrypt($words, ($PUBLIC_KEY))

;

Conscious answered 1/2, 2023 at 13:49 Comment(0)

© 2022 - 2025 — McMap. All rights reserved.