[erlang-questions] public_key:pem_decode/1 and public_key:verify/4
Ingela Andin
ingela.andin@REDACTED
Mon Jan 24 11:51:40 CET 2011
Hi Seth!
Thank you very much for working on this. I have looked at your branch
and my thoughts are the following.
I think that the decoding of 'SubjectPublicKeyInfo', from
pem_decode_public_key, should rather be handled in the
function pem_entry_decode. As I think the normal thing is that you
want the actual key and not a 'SubjectPublicKeyInfo', that would
mean just a little more decoding is done by pem_entry_decode. (You can
match on the 'SubjectPublicKeyInfo' in the function head to
create a clause for this.)
It will not then be a 100 % symmetric with pem_entry_encode but I
think that is ok, it could be mentioned in the documentation.
Another reason that this is a good idea is that it will not then be
sensitive to that the public_key is the only entry in the file.
PEM files may contain several entries which is not handled by your function.
When it comes to the function der_decode_publick_key I am not sure it
is needed as I think it
is uncommon that you end up with a "DER-blob" that you do not know how
it is encoded.
Regards Ingela Erlang/OTP team - Ericssson AB
2011/1/24 Seth Falcon <seth@REDACTED>:
> Hi,
>
> On Fri, Jan 21, 2011 at 12:48 AM, Ingela Andin <ingela.andin@REDACTED> wrote:
>> Well PEM-files that only BEGIN PUBLIC KEY and not BEGIN RSA PUBLIC
>> KEY are using another ASN1 spec and can contain both RSA and DSA
>> keys. It seems that it is the ASN1-spec SubjectPublicKeyInfo from
>> PKIXExplicit88.asn1 also part of public_key.
>
> Thanks, that was a very useful hint :-)
>
> I can now read RSA public key PEM files as generated by openssl.
> Here's the recipe (assuming stock public_key module):
>
> read_rsa_public_key(Key) ->
> Bin = erlang:iolist_to_binary(public_key_lines(re:split(Key,
> "\n"), [])),
> Spki = public_key:der_decode('SubjectPublicKeyInfo',
> base64:mime_decode(Bin)),
> {_, _, {0, KeyDer}} = Spki,
> public_key:der_decode('RSAPublicKey', KeyDer).
>
> public_key_lines([<<"-----BEGIN PUBLIC KEY-----">>|Rest], Acc) ->
> public_key_lines(Rest, Acc);
> public_key_lines([<<"-----END PUBLIC KEY-----">>|Rest], Acc) ->
> lists:reverse(Acc);
> public_key_lines([Line|Rest], Acc) ->
> public_key_lines(Rest, [Line|Acc]).
>
> I have a patch to the public_key module that makes this easier by
> introducing three new functions: public_key_type/1,
> pem_decode_public_key/1, and der_decode_public_key/1.
>
> public_key_type takes either a SubjectPublicKeyInfo record (as
> returned by der_decode/2 when given type 'SubjectPublicKeyInfo') or
> the algorithm id tuple that is a part of the 'SubjectPublicKeyInfo'
> record. It is a wrapper for
> pubkey_cert_records:supportedPublicKeyAlgorithms/1.
>
>
> pem_decode_public_key
>
> takes a PEM binary and in the case that pem_decode(PEM) returns
> 'SubjectPublicKeyInfo', it determines the public key type and does
> der_decode so that the return value is the public key in a form
> usable by functions like public_key:decrypt_public/2. If the PEM
> does not contain 'SubjectPublicKeyInfo', then it is passed through
> unchanged. I think this would be useful for Joakim's use case.
>
> der_decode_public_key
>
> behaves similarly, but is given the DER encoded version of the
> public key to start with. Here, as I understand it, the problem
> is a bit stickier because you can't know what type it is. So it
> tries each of ['SubjectPublicKeyInfo', 'RSAPublicKey',
> 'DSAPublicKey'] and returns similar to pem_decode_public_key.
>
> I've put the work-in-progress on a branch here:
>
> https://github.com/seth/otp/tree/sf/rsa_pub_key
>
> I'm not sure if this is going in the right direction, so wrote this up
> (sorry for the length) to get some feedback. I'm willing to make
> adjustments and spend time polishing a patch if there is some
> agreement on general direction.
>
> Best,
>
> + seth
>
>
> --
> Seth Falcon | @sfalcon | http://userprimary.net/
>
More information about the erlang-questions
mailing list