aboutsummaryrefslogtreecommitdiffstats
path: root/lib/public_key/src
diff options
context:
space:
mode:
authorIngela Anderton Andin <[email protected]>2011-10-06 17:37:02 +0200
committerIngela Anderton Andin <[email protected]>2011-11-01 16:46:26 +0100
commitca4d1197fdf66fda5241edd645c12d2451b67ec8 (patch)
tree98ea5d5ab9fedc9a3a263750402c4d3d7464baf8 /lib/public_key/src
parentd5ebc4c1409284e0a343a64edf7d75308a1b3dd2 (diff)
downloadotp-ca4d1197fdf66fda5241edd645c12d2451b67ec8.tar.gz
otp-ca4d1197fdf66fda5241edd645c12d2451b67ec8.tar.bz2
otp-ca4d1197fdf66fda5241edd645c12d2451b67ec8.zip
Add PKCS-8 support to public_key
Diffstat (limited to 'lib/public_key/src')
-rw-r--r--lib/public_key/src/Makefile6
-rw-r--r--lib/public_key/src/pubkey_pbe.erl181
-rw-r--r--lib/public_key/src/pubkey_pem.erl118
-rw-r--r--lib/public_key/src/public_key.app.src4
-rw-r--r--lib/public_key/src/public_key.erl72
5 files changed, 303 insertions, 78 deletions
diff --git a/lib/public_key/src/Makefile b/lib/public_key/src/Makefile
index 5a24b02d2a..062c495a65 100644
--- a/lib/public_key/src/Makefile
+++ b/lib/public_key/src/Makefile
@@ -42,10 +42,11 @@ MODULES = \
public_key \
pubkey_pem \
pubkey_ssh \
+ pubkey_pbe \
pubkey_cert \
- pubkey_cert_records
+ pubkey_cert_records
-HRL_FILES = $(INCLUDE)/public_key.hrl
+HRL_FILES = $(INCLUDE)/public_key.hrl
INTERNAL_HRL_FILES =
@@ -109,4 +110,3 @@ release_spec: opt
$(INSTALL_DATA) $(TARGET_FILES) $(APP_TARGET) $(APPUP_TARGET) $(RELSYSDIR)/ebin
release_docs_spec:
-
diff --git a/lib/public_key/src/pubkey_pbe.erl b/lib/public_key/src/pubkey_pbe.erl
new file mode 100644
index 0000000000..f471871d35
--- /dev/null
+++ b/lib/public_key/src/pubkey_pbe.erl
@@ -0,0 +1,181 @@
+%%
+%% %CopyrightBegin%
+%%
+%% Copyright Ericsson AB 2011-2011. All Rights Reserved.
+%%
+%% The contents of this file are subject to the Erlang Public License,
+%% Version 1.1, (the "License"); you may not use this file except in
+%% compliance with the License. You should have received a copy of the
+%% Erlang Public License along with this software. If not, it can be
+%% retrieved online at http://www.erlang.org/.
+%%
+%% Software distributed under the License is distributed on an "AS IS"
+%% basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+%% the License for the specific language governing rights and limitations
+%% under the License.
+%%
+%% %CopyrightEnd%
+%%
+%% Description: Implements Password Based Encryption PKCS-5, RFC-2898
+
+-module(pubkey_pbe).
+
+-include("public_key.hrl").
+
+-export([encode/4, decode/4, decrypt_parameters/1]).
+-export([pbdkdf1/4, pbdkdf2/6]).
+
+-define(DEFAULT_SHA_MAC_KEYLEN, 20).
+
+-define(OCTET_STR, 4).
+-define(IV_LEN, 8).
+
+%%====================================================================
+%% Internal application API
+%%====================================================================
+
+pbdkdf2(Password, Salt, Count, DerivedKeyLen, PrfLen, Prf)->
+ NumBlocks = ceiling(DerivedKeyLen / PrfLen),
+ NumLastBlockOctets = DerivedKeyLen - (NumBlocks - 1) * PrfLen ,
+ blocks(NumBlocks, NumLastBlockOctets, 1, Password, Salt, Count, Prf, PrfLen, <<>>).
+
+encode(Data, Password, "DES-CBC" = Cipher, KeyDevParams) ->
+ {Key, IV} = password_to_key_and_iv(Password, derived_key_length(Cipher), KeyDevParams),
+ crypto:des_cbc_encrypt(Key, IV, Data);
+
+encode(Data, Password, "DES-EDE3-CBC" = Cipher, KeyDevParams) ->
+ {Key, IV} = password_to_key_and_iv(Password, derived_key_length(Cipher), KeyDevParams),
+ <<Key1:8/binary, Key2:8/binary, Key3:8/binary>> = Key,
+ crypto:des_ede3_cbc_encrypt(Key1, Key2, Key3, IV, Data).
+
+decode(Data, Password,"DES-CBC"= Cipher, KeyDevParams) ->
+ {Key, IV} = password_to_key_and_iv(Password, derived_key_length(Cipher), KeyDevParams),
+ crypto:des_cbc_decrypt(Key, IV, Data);
+
+decode(Data, Password,"DES-EDE3-CBC" = Cipher, KeyDevParams) ->
+ {Key, IV} = password_to_key_and_iv(Password, derived_key_length(Cipher), KeyDevParams),
+ <<Key1:8/binary, Key2:8/binary, Key3:8/binary>> = Key,
+ crypto:des_ede3_cbc_decrypt(Key1, Key2, Key3, IV, Data).
+
+%%--------------------------------------------------------------------
+-spec pbdkdf1(string(), iodata(), integer(), atom()) -> binary().
+%%
+%% Description: Implements password based decryption key derive function 1.
+%% Exported mainly for testing purposes.
+%%--------------------------------------------------------------------
+pbdkdf1(_, _, 0, Acc) ->
+ Acc;
+pbdkdf1(Password, Salt, Count, Hash) ->
+ Result = crypto:Hash([Password, Salt]),
+ do_pbdkdf1(Result, Count-1, Result, Hash).
+
+%%--------------------------------------------------------------------
+-spec pbdkdf2(string(), iodata(), integer(), integer(), fun(), integer())
+ -> binary().
+%%
+%% Description: Implements password based decryption key derive function 2.
+%% Exported mainly for testing purposes.
+%%--------------------------------------------------------------------
+pbdkdf2(Password, Salt, Count, DerivedKeyLen, Prf, PrfOutputLen)->
+ NumBlocks = ceiling(DerivedKeyLen / PrfOutputLen),
+ NumLastBlockOctets = DerivedKeyLen - (NumBlocks - 1) * PrfOutputLen ,
+ blocks(NumBlocks, NumLastBlockOctets, 1, Password, Salt,
+ Count, Prf, PrfOutputLen, <<>>).
+%%--------------------------------------------------------------------
+-spec decrypt_parameters(#'EncryptedPrivateKeyInfo_encryptionAlgorithm'{}) ->
+ {Cipher::string(), #'PBES2-params'{}}.
+%%
+%% Description: Performs ANS1-decoding of encryption parameters.
+%%--------------------------------------------------------------------
+decrypt_parameters(#'EncryptedPrivateKeyInfo_encryptionAlgorithm'{
+ algorithm = Oid, parameters = Param}) ->
+ decrypt_parameters(Oid, Param).
+
+%%--------------------------------------------------------------------
+%%% Internal functions
+%%--------------------------------------------------------------------
+password_to_key_and_iv(Password, KeyLen, {salt, Salt}) ->
+ <<Key:KeyLen/binary, _/binary>> =
+ pem_encrypt(<<>>, Password, Salt, ceiling(KeyLen div 16), <<>>, md5),
+ %% Old PEM encryption does not use standard encryption method
+ %% pbdkdf1 and uses then salt as IV
+ {Key, Salt}.
+
+pem_encrypt(_, _, _, 0, Acc, _) ->
+ Acc;
+pem_encrypt(Prev, Password, Salt, Count, Acc, Hash) ->
+ Result = crypto:Hash([Prev, Password, Salt]),
+ pem_encrypt(Result, Password, Salt, Count-1 , <<Acc/binary, Result/binary>>, Hash).
+
+do_pbdkdf1(_, 0, Acc, _) ->
+ Acc;
+do_pbdkdf1(Prev, Count, Acc, Hash) ->
+ Result = crypto:Hash(Prev),
+ do_pbdkdf1(Result, Count-1 , <<Result/binary, Acc/binary>>, Hash).
+
+iv(#'PBES2-params_encryptionScheme'{algorithm = Algo,
+ parameters = ASNIV}) when (Algo == ?'desCBC') or
+ (Algo == ?'des-EDE3-CBC') ->
+ %% This is an so called open ASN1-type that in this
+ %% case will be an octet-string of length 8
+ <<?OCTET_STR, ?IV_LEN, IV:?IV_LEN/binary>> = ASNIV,
+ IV.
+
+blocks(1, N, Index, Password, Salt, Count, Prf, PrfLen, Acc) ->
+ <<XorSum:N/binary, _/binary>> = xor_sum(Password, Salt, Count, Index, Prf, PrfLen),
+ <<Acc/binary, XorSum/binary>>;
+blocks(NumBlocks, N, Index, Password, Salt, Count, Prf, PrfLen, Acc) ->
+ XorSum = xor_sum(Password, Salt, Count, Index, Prf, PrfLen),
+ blocks(NumBlocks -1, N, Index +1, Password, Salt, Count, Prf, PrfLen, <<Acc/binary, XorSum/binary>>).
+
+xor_sum(Password, Salt, Count, Index, Prf, PrfLen) ->
+ %%Result = Prf(Password, [Salt,<<Index:32/unsigned-big-integer>>], PrfLen),
+ Result = Prf(Password, [Salt,<<Index:32/unsigned-big-integer>>]),
+ do_xor_sum(Prf, PrfLen, Result, Password, Count-1, Result).
+
+do_xor_sum(_, _, _, _, 0, Acc) ->
+ Acc;
+do_xor_sum(Prf, PrfLen, Prev, Password, Count, Acc)->
+ %%Result = Prf(Password, Prev, PrfLen),
+ Result = Prf(Password, Prev),
+ do_xor_sum(Prf, PrfLen, Result, Password, Count-1, crypto:exor(Acc, Result)).
+
+decrypt_parameters(?'id-PBES2', DekParams) ->
+ {ok, Params} = 'PKCS-FRAME':decode('PBES2-params', DekParams),
+ {cipher(Params#'PBES2-params'.encryptionScheme), Params}.
+
+key_derivation_params(#'PBES2-params_keyDerivationFunc'{algorithm = ?'id-PBKDF2',
+ parameters =
+ #'PBKDF2-params'{salt = {specified, OctetSalt},
+ iterationCount = Count,
+ keyLength = Length,
+ prf = Prf}}) ->
+ PseudoRandomFunction = pseudo_random_function(Prf),
+ KeyLen = pseudo_key_length(Length, Prf),
+ {iolist_to_binary(OctetSalt), Count, KeyLen, PseudoRandomFunction}.
+
+pseudo_random_function(#'PBKDF2-params_prf'{algorithm = {_,_, _,'id-hmacWithSHA1'}}) ->
+ %%fun crypto:sha_mac_n/3.
+ fun crypto:sha_mac/2.
+
+pseudo_key_length(asn1_NOVALUE, #'PBKDF2-params_prf'{algorithm = {_,_, _,'id-hmacWithSHA1'}}) ->
+ ?DEFAULT_SHA_MAC_KEYLEN;
+pseudo_key_length(Len, _) when is_integer(Len) ->
+ Len.
+
+derived_key_length("DES-CBC") ->
+ 8;
+%% derived_key_length("RC2-CBC") ->
+%% 5;
+derived_key_length("DES-EDE3-CBC") ->
+ 24.
+
+cipher(#'PBES2-params_encryptionScheme'{algorithm = ?'desCBC'}) ->
+ "DES-CBC";
+cipher(#'PBES2-params_encryptionScheme'{algorithm = ?'des-EDE3-CBC'}) ->
+ "DES-EDE3-CBC".
+%% cipher(#'PBES2-params_encryptionScheme'{algorithm = ?'rc2CBC'}) ->
+%% "RC2-CBC".
+
+ceiling(Float) ->
+ erlang:round(Float + 0.5).
diff --git a/lib/public_key/src/pubkey_pem.erl b/lib/public_key/src/pubkey_pem.erl
index c26815bc04..f19aab0533 100644
--- a/lib/public_key/src/pubkey_pem.erl
+++ b/lib/public_key/src/pubkey_pem.erl
@@ -44,7 +44,7 @@
-export([encode/1, decode/1, decipher/2, cipher/3]).
%% Backwards compatibility
--export([decode_key/2]).
+%%-export([decode_key/2]).
-define(ENCODED_LINE_LENGTH, 64).
@@ -69,23 +69,27 @@ encode(PemEntries) ->
encode_pem_entries(PemEntries).
%%--------------------------------------------------------------------
--spec decipher({pki_asn1_type(), DerEncrypted::binary(),{Cipher :: string(),
- Salt :: binary()}},
- string()) -> Der::binary().
+-spec decipher({pki_asn1_type(), DerEncrypted::binary(), term()},
+ %%{Cipher :: string(),
+ %%Salt :: binary()}},
+ string()) -> Der::binary().
%%
%% Description: Deciphers a decrypted pem entry.
%%--------------------------------------------------------------------
-decipher({_, DecryptDer, {Cipher,Salt}}, Password) ->
- decode_key(DecryptDer, Password, Cipher, Salt).
+decipher({_, DecryptDer, {Cipher, KeyDevParams}}, Password) ->
+ %%decode_key(DecryptDer, Password, Cipher, Salt).
+ pubkey_pbe:decode(DecryptDer, Password, Cipher, KeyDevParams).
%%--------------------------------------------------------------------
--spec cipher(Der::binary(),{Cipher :: string(), Salt :: binary()} ,
+-spec cipher(Der::binary(), term(),
+%%{Cipher :: string(), Hash::atom(), Salt :: binary()} ,
string()) -> binary().
%%
%% Description: Ciphers a PEM entry
%%--------------------------------------------------------------------
-cipher(Der, {Cipher,Salt}, Password)->
- encode_key(Der, Password, Cipher, Salt).
+cipher(Der, {Cipher, KeyDevParams}, Password)->
+ %%encode_key(Der, Password, Cipher, Salt).
+ pubkey_pbe:encode(Der, Password, Cipher, KeyDevParams).
%%--------------------------------------------------------------------
%%% Internal functions
@@ -96,7 +100,7 @@ encode_pem_entries(Entries) ->
encode_pem_entry({Type, Der, not_encrypted}) ->
StartStr = pem_start(Type),
[StartStr, "\n", b64encode_and_split(Der), "\n", pem_end(StartStr) ,"\n\n"];
-encode_pem_entry({Type, Der, {Cipher, Salt}}) ->
+encode_pem_entry({Type, Der, {Cipher, {_, Salt}}}) ->
StartStr = pem_start(Type),
[StartStr,"\n", pem_decrypt(),"\n", pem_decrypt_info(Cipher, Salt),"\n",
b64encode_and_split(Der), "\n", pem_end(StartStr) ,"\n\n"].
@@ -122,13 +126,25 @@ decode_pem_entry(Start, [<<"Proc-Type: 4,ENCRYPTED", _/binary>>, Line | Lines])
Decoded = base64:mime_decode(Cs),
[_, DekInfo0] = string:tokens(binary_to_list(Line), ": "),
[Cipher, Salt] = string:tokens(DekInfo0, ","),
- {Type, Decoded, {Cipher, unhex(Salt)}};
+ {Type, Decoded, {Cipher, {salt, unhex(Salt)}}};
decode_pem_entry(Start, Lines) ->
Type = asn1_type(Start),
Cs = erlang:iolist_to_binary(Lines),
Decoded = base64:mime_decode(Cs),
- {Type, Decoded, not_encrypted}.
+ case Type of
+ 'EncryptedPrivateKeyInfo'->
+ decode_encrypted_private_keyinfo(Decoded);
+ _ ->
+ {Type, Decoded, not_encrypted}
+ end.
+
+decode_encrypted_private_keyinfo(Der) ->
+ #'EncryptedPrivateKeyInfo'{encryptionAlgorithm = AlgorithmInfo,
+ encryptedData = Data} = public_key:der_decode('EncryptedPrivateKeyInfo', Der),
+ DecryptParams = pubkey_pbe:decrypt_parameters(AlgorithmInfo),
+ {'PrivateKeyInfo', iolist_to_binary(Data), DecryptParams}.
+
split_bin(Bin) ->
split_bin(0, Bin).
@@ -160,36 +176,36 @@ join_entry([<<"-----END ", _/binary>>| Lines], Entry) ->
join_entry([Line | Lines], Entry) ->
join_entry(Lines, [Line | Entry]).
-decode_key(Data, Password, "DES-CBC", Salt) ->
- Key = password_to_key(Password, Salt, 8),
- IV = Salt,
- crypto:des_cbc_decrypt(Key, IV, Data);
-decode_key(Data, Password, "DES-EDE3-CBC", Salt) ->
- Key = password_to_key(Password, Salt, 24),
- IV = Salt,
- <<Key1:8/binary, Key2:8/binary, Key3:8/binary>> = Key,
- crypto:des_ede3_cbc_decrypt(Key1, Key2, Key3, IV, Data).
-
-encode_key(Data, Password, "DES-CBC", Salt) ->
- Key = password_to_key(Password, Salt, 8),
- IV = Salt,
- crypto:des_cbc_encrypt(Key, IV, Data);
-encode_key(Data, Password, "DES-EDE3-CBC", Salt) ->
- Key = password_to_key(Password, Salt, 24),
- IV = Salt,
- <<Key1:8/binary, Key2:8/binary, Key3:8/binary>> = Key,
- crypto:des_ede3_cbc_encrypt(Key1, Key2, Key3, IV, Data).
-
-password_to_key(Data, Salt, KeyLen) ->
- <<Key:KeyLen/binary, _/binary>> =
- password_to_key(<<>>, Data, Salt, KeyLen, <<>>),
- Key.
-
-password_to_key(_, _, _, Len, Acc) when Len =< 0 ->
- Acc;
-password_to_key(Prev, Data, Salt, Len, Acc) ->
- M = crypto:md5([Prev, Data, Salt]),
- password_to_key(M, Data, Salt, Len - size(M), <<Acc/binary, M/binary>>).
+%% decode_key(Data, Password, "DES-CBC", Salt) ->
+%% Key = password_to_key(Password, Salt, 8),
+%% IV = Salt,
+%% crypto:des_cbc_decrypt(Key, IV, Data);
+%% decode_key(Data, Password, "DES-EDE3-CBC", Salt) ->
+%% Key = password_to_key(Password, Salt, 24),
+%% IV = Salt,
+%% <<Key1:8/binary, Key2:8/binary, Key3:8/binary>> = Key,
+%% crypto:des_ede3_cbc_decrypt(Key1, Key2, Key3, IV, Data).
+
+%% encode_key(Data, Password, "DES-CBC", Salt) ->
+%% Key = password_to_key(Password, Salt, 8),
+%% IV = Salt,
+%% crypto:des_cbc_encrypt(Key, IV, Data);
+%% encode_key(Data, Password, "DES-EDE3-CBC", Salt) ->
+%% Key = password_to_key(Password, Salt, 24),
+%% IV = Salt,
+%% <<Key1:8/binary, Key2:8/binary, Key3:8/binary>> = Key,
+%% crypto:des_ede3_cbc_encrypt(Key1, Key2, Key3, IV, Data).
+
+%% password_to_key(Data, Salt, KeyLen) ->
+%% <<Key:KeyLen/binary, _/binary>> =
+%% password_to_key(<<>>, Data, Salt, KeyLen, <<>>),
+%% Key.
+
+%% password_to_key(_, _, _, Len, Acc) when Len =< 0 ->
+%% Acc;
+%% password_to_key(Prev, Data, Salt, Len, Acc) ->
+%% M = crypto:md5([Prev, Data, Salt]),
+%% password_to_key(M, Data, Salt, Len - size(M), <<Acc/binary, M/binary>>).
unhex(S) ->
unhex(S, []).
@@ -228,6 +244,10 @@ pem_end(<<"-----BEGIN DSA PRIVATE KEY-----">>) ->
<<"-----END DSA PRIVATE KEY-----">>;
pem_end(<<"-----BEGIN DH PARAMETERS-----">>) ->
<<"-----END DH PARAMETERS-----">>;
+pem_end(<<"-----BEGIN PRIVATE KEY-----">>) ->
+ <<"-----END PRIVATE KEY-----">>;
+pem_end(<<"-----BEGIN ENCRYPTED PRIVATE KEY-----">>) ->
+ <<"-----END ENCRYPTED PRIVATE KEY-----">>;
pem_end(_) ->
undefined.
@@ -242,7 +262,11 @@ asn1_type(<<"-----BEGIN PUBLIC KEY-----">>) ->
asn1_type(<<"-----BEGIN DSA PRIVATE KEY-----">>) ->
'DSAPrivateKey';
asn1_type(<<"-----BEGIN DH PARAMETERS-----">>) ->
- 'DHParameter'.
+ 'DHParameter';
+asn1_type(<<"-----BEGIN PRIVATE KEY-----">>) ->
+ 'PrivateKeyInfo';
+asn1_type(<<"-----BEGIN ENCRYPTED PRIVATE KEY-----">>) ->
+ 'EncryptedPrivateKeyInfo'.
pem_decrypt() ->
<<"Proc-Type: 4,ENCRYPTED">>.
@@ -253,7 +277,7 @@ pem_decrypt_info(Cipher, Salt) ->
%%--------------------------------------------------------------------
%%% Deprecated
%%--------------------------------------------------------------------
-decode_key({_Type, Bin, not_encrypted}, _) ->
- Bin;
-decode_key({_Type, Bin, {Chipher,Salt}}, Password) ->
- decode_key(Bin, Password, Chipher, Salt).
+%% decode_key({_Type, Bin, not_encrypted}, _) ->
+%% Bin;
+%% decode_key({_Type, Bin, {Chipher,Salt}}, Password) ->
+%% decode_key(Bin, Password, Chipher, Salt).
diff --git a/lib/public_key/src/public_key.app.src b/lib/public_key/src/public_key.app.src
index 1963bd05d4..4cc81ea573 100644
--- a/lib/public_key/src/public_key.app.src
+++ b/lib/public_key/src/public_key.app.src
@@ -3,10 +3,12 @@
{vsn, "%VSN%"},
{modules, [ public_key,
pubkey_pem,
+ pubkey_pbe,
pubkey_ssh,
pubkey_cert,
pubkey_cert_records,
- 'OTP-PUB-KEY'
+ 'OTP-PUB-KEY',
+ 'PKCS-FRAME'
]},
{applications, [crypto, kernel, stdlib]},
{registered, []},
diff --git a/lib/public_key/src/public_key.erl b/lib/public_key/src/public_key.erl
index 33fcce2c44..68c7b7ad93 100644
--- a/lib/public_key/src/public_key.erl
+++ b/lib/public_key/src/public_key.erl
@@ -46,11 +46,11 @@
]).
%% Deprecated
--export([decode_private_key/1, decode_private_key/2, pem_to_der/1]).
+%% -export([decode_private_key/1, decode_private_key/2, pem_to_der/1]).
--deprecated({pem_to_der, 1, next_major_release}).
--deprecated({decode_private_key, 1, next_major_release}).
--deprecated({decode_private_key, 2, next_major_release}).
+%% -deprecated({pem_to_der, 1, next_major_release}).
+%% -deprecated({decode_private_key, 1, next_major_release}).
+%% -deprecated({decode_private_key, 2, next_major_release}).
-type rsa_padding() :: 'rsa_pkcs1_padding' | 'rsa_pkcs1_oaep_padding'
| 'rsa_no_padding'.
@@ -104,22 +104,20 @@ pem_entry_decode({Asn1Type, Der, not_encrypted}) when is_atom(Asn1Type),
pem_entry_decode({Asn1Type, Der, not_encrypted}, _) when is_atom(Asn1Type),
is_binary(Der) ->
der_decode(Asn1Type, Der);
-pem_entry_decode({Asn1Type, CryptDer, {Cipher, Salt}} = PemEntry,
+pem_entry_decode({Asn1Type, CryptDer, {Cipher, _Params}} = PemEntry,
Password) when is_atom(Asn1Type),
is_binary(CryptDer),
- is_list(Cipher),
- is_binary(Salt),
- erlang:byte_size(Salt) == 8
- ->
+ is_list(Cipher) ->
Der = pubkey_pem:decipher(PemEntry, Password),
der_decode(Asn1Type, Der).
%%--------------------------------------------------------------------
-spec pem_entry_encode(pki_asn1_type(), term()) -> pem_entry().
-spec pem_entry_encode(pki_asn1_type(), term(),
- {{Cipher :: string(), Salt :: binary()}, string()}) ->
+ %%{{Cipher :: string(), Salt :: binary()}, string()}
+ term()) ->
pem_entry().
-%
+ %
%% Description: Creates a pem entry that can be feed to pem_encode/1.
%%--------------------------------------------------------------------
pem_entry_encode('SubjectPublicKeyInfo', Entity=#'RSAPublicKey'{}) ->
@@ -137,11 +135,11 @@ pem_entry_encode('SubjectPublicKeyInfo',
pem_entry_encode(Asn1Type, Entity) when is_atom(Asn1Type) ->
Der = der_encode(Asn1Type, Entity),
{Asn1Type, Der, not_encrypted}.
-pem_entry_encode(Asn1Type, Entity,
- {{Cipher, Salt}= CipherInfo, Password}) when is_atom(Asn1Type),
- is_list(Cipher),
- is_binary(Salt),
- erlang:byte_size(Salt) == 8,
+pem_entry_encode(Asn1Type, Entity, {CipherInfo, Password}) when is_atom(Asn1Type),
+ %%is_list(Cipher),
+ %%is_binary(Salt),
+ %%is_atom(Hash),
+ %% erlang:byte_size(Salt) == 8,
is_list(Password)->
Der = der_encode(Asn1Type, Entity),
DecryptDer = pubkey_pem:cipher(Der, CipherInfo, Password),
@@ -152,6 +150,17 @@ pem_entry_encode(Asn1Type, Entity,
%%
%% Description: Decodes a public key asn1 der encoded entity.
%%--------------------------------------------------------------------
+der_decode(Asn1Type, Der) when (Asn1Type == 'PrivateKeyInfo') or (Asn1Type == 'EncryptedPrivateKeyInfo')
+ andalso is_binary(Der) ->
+ try
+ {ok, Decoded} = 'PKCS-FRAME':decode(Asn1Type, Der),
+
+ Decoded
+ catch
+ error:{badmatch, {error, _}} = Error ->
+ erlang:error(Error)
+ end;
+
der_decode(Asn1Type, Der) when is_atom(Asn1Type), is_binary(Der) ->
try
{ok, Decoded} = 'OTP-PUB-KEY':decode(Asn1Type, Der),
@@ -166,6 +175,15 @@ der_decode(Asn1Type, Der) when is_atom(Asn1Type), is_binary(Der) ->
%%
%% Description: Encodes a public key entity with asn1 DER encoding.
%%--------------------------------------------------------------------
+der_encode(Asn1Type, Entity) when Asn1Type == 'PrivateKeyInfo'; Asn1Type == 'EncryptedPrivateKeyInfo' ->
+ try
+ {ok, Encoded} = 'PKCS-FRAME':encode(Asn1Type, Entity),
+ iolist_to_binary(Encoded)
+ catch
+ error:{badmatch, {error, _}} = Error ->
+ erlang:error(Error)
+ end;
+
der_encode(Asn1Type, Entity) when is_atom(Asn1Type) ->
try
{ok, Encoded} = 'OTP-PUB-KEY':encode(Asn1Type, Entity),
@@ -636,16 +654,16 @@ sized_binary(Binary) ->
%%--------------------------------------------------------------------
%%% Deprecated functions
%%--------------------------------------------------------------------
-pem_to_der(CertSource) ->
- {ok, Bin} = file:read_file(CertSource),
- {ok, pubkey_pem:decode(Bin)}.
+%% pem_to_der(CertSource) ->
+%% {ok, Bin} = file:read_file(CertSource),
+%% {ok, pubkey_pem:decode(Bin)}.
-decode_private_key(KeyInfo) ->
- decode_private_key(KeyInfo, no_passwd).
+%% decode_private_key(KeyInfo) ->
+%% decode_private_key(KeyInfo, no_passwd).
-decode_private_key(KeyInfo = {'RSAPrivateKey', _, _}, Password) ->
- DerEncoded = pubkey_pem:decode_key(KeyInfo, Password),
- 'OTP-PUB-KEY':decode('RSAPrivateKey', DerEncoded);
-decode_private_key(KeyInfo = {'DSAPrivateKey', _, _}, Password) ->
- DerEncoded = pubkey_pem:decode_key(KeyInfo, Password),
- 'OTP-PUB-KEY':decode('DSAPrivateKey', DerEncoded).
+%% decode_private_key(KeyInfo = {'RSAPrivateKey', _, _}, Password) ->
+%% DerEncoded = pubkey_pem:decode_key(KeyInfo, Password),
+%% 'OTP-PUB-KEY':decode('RSAPrivateKey', DerEncoded);
+%% decode_private_key(KeyInfo = {'DSAPrivateKey', _, _}, Password) ->
+%% DerEncoded = pubkey_pem:decode_key(KeyInfo, Password),
+%% 'OTP-PUB-KEY':decode('DSAPrivateKey', DerEncoded).