如何将OpenSSH公钥文件格式转换为PEM [英] How to convert OpenSSH public key file format to PEM

查看:1585
本文介绍了如何将OpenSSH公钥文件格式转换为PEM的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我具有OpenSSH格式的RSA公钥:

I have RSA public key in OpenSSH format:

ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQC9xmJumsHeLEDcJwf3LYONZholP3+pDHJYen4w+gm8o1r7t6oq825Gmjr7pjsQ+ZDxWivkI4vMW9RyFevPg09ljW+V7lZInBpRtB6v1s8PdmV9YVk4R3S0e7sPMPXuM7ocPLh5yKZ9f7JZwQlpp4ww/RE7blbXywjwCxngT7+G+J6HJB0UcR8xR8t6z8qDrDTAJA7pFFFNliw9M+I8tbrFl8HmoyudOFsGsYOd5hjemy4ivW88XcXzfHJdKnmD9FHVZv/GUXgErVMHS25xLcJfPalm5R8BFQrgl8SiqXj9i2vEVct9ZGydG0/Zyh2eX98D82pJhgIBmpJC4JUGv+Mt user@host

如何在PHP中将此密钥转换为适合 openssl_pkey_get_public()的格式?

How to convert in PHP this key into format suitable for openssl_pkey_get_public()?

提取两个RSA公钥编号(n和e)很容易,因为OpenSSH字符串的第二部分只是

It is easy to extract both RSA public key numbers (n and e), because second part of OpenSSH string is just base64 encoded key format described in RFC4253. So in fact the question is how to encode these numbers into PEM RSA public key format?

推荐答案

解决方案:

function len($s)
{
    $len = strlen($s);

    if ($len < 0x80) {
        return chr($len);
    }

    $data = dechex($len);
    $data = pack('H*', (strlen($data) & 1 ? '0' : '') . $data);
    return chr(strlen($data) | 0x80) . $data;
}

function openssh2pem($file)
{
    list(,$data) = explode(' ', trim(file_get_contents($file)), 3);
    $data = base64_decode($data);

    list(,$alg_len) = unpack('N', substr($data, 0, 4));
    $alg = substr($data, 4, $alg_len);

    if ($alg !== 'ssh-rsa') {
        return FALSE;
    }

    list(,$e_len) = unpack('N', substr($data, 4 + strlen($alg), 4));
    $e = substr($data, 4 + strlen($alg) + 4, $e_len);
    list(,$n_len) = unpack('N', substr($data, 4 + strlen($alg) + 4 + strlen($e), 4));
    $n = substr($data, 4 + strlen($alg) + 4 + strlen($e) + 4, $n_len);

    $algid = pack('H*', '06092a864886f70d0101010500');                // algorithm identifier (id, null)
    $algid = pack('Ca*a*', 0x30, len($algid), $algid);                // wrap it into sequence
    $data = pack('Ca*a*Ca*a*', 0x02, len($n), $n, 0x02, len($e), $e); // numbers
    $data = pack('Ca*a*', 0x30, len($data), $data);                   // wrap it into sequence
    $data = "\x00" . $data;                                           // don't know why, but needed
    $data = pack('Ca*a*', 0x03, len($data), $data);                   // wrap it into bitstring
    $data = $algid . $data;                                           // prepend algid
    $data = pack('Ca*a*', 0x30, len($data), $data);                   // wrap it into sequence

    return "-----BEGIN PUBLIC KEY-----\n" .
           chunk_split(base64_encode($data), 64, "\n") .
           "-----END PUBLIC KEY-----\n";
}

资源: http://tools.ietf.org/html/rfc3447 #appendix-A.1 http://luca.ntop.org /Teaching/Appunti/asn1.html

这篇关于如何将OpenSSH公钥文件格式转换为PEM的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆