99using System . Collections . Generic ;
1010using Keyfactor . Extensions . Orchestrator . RemoteFile . RemoteHandlers ;
1111using Keyfactor . Extensions . Orchestrator . RemoteFile . Models ;
12+ using Keyfactor . Extensions . Orchestrator . RemoteFile . PKCS12 ;
1213
1314using Keyfactor . Logging ;
1415
@@ -30,6 +31,8 @@ public JKSCertificateStoreSerializer(string storeProperties)
3031 logger = LogHandler . GetClassLogger ( this . GetType ( ) ) ;
3132 }
3233
34+ private bool IsTypeJKS { get ; set ; }
35+
3336 public Pkcs12Store DeserializeRemoteCertificateStore ( byte [ ] storeContents , string storePath , string storePassword , IRemoteHandler remoteHandler , bool isInventory )
3437 {
3538 logger . MethodEntry ( LogLevel . Debug ) ;
@@ -38,42 +41,58 @@ public Pkcs12Store DeserializeRemoteCertificateStore(byte[] storeContents, strin
3841 Pkcs12Store pkcs12Store = storeBuilder . Build ( ) ;
3942 Pkcs12Store pkcs12StoreNew = storeBuilder . Build ( ) ;
4043
41- JksStore jksStore = new JksStore ( ) ;
42-
4344 using ( MemoryStream ms = new MemoryStream ( storeContents ) )
4445 {
45- jksStore . Load ( ms , string . IsNullOrEmpty ( storePassword ) ? new char [ 0 ] : storePassword . ToCharArray ( ) ) ;
46+ IsTypeJKS = new JksStore ( ) . Probe ( ms ) ;
4647 }
4748
48- foreach ( string alias in jksStore . Aliases )
49+ if ( IsTypeJKS )
4950 {
50- if ( jksStore . IsKeyEntry ( alias ) )
51+ logger . LogDebug ( "Store is of type JKS" ) ;
52+ JksStore jksStore = new JksStore ( ) ;
53+
54+ using ( MemoryStream ms = new MemoryStream ( storeContents ) )
5155 {
52- AsymmetricKeyParameter keyParam = jksStore . GetKey ( alias , string . IsNullOrEmpty ( storePassword ) ? new char [ 0 ] : storePassword . ToCharArray ( ) ) ;
53- AsymmetricKeyEntry keyEntry = new AsymmetricKeyEntry ( keyParam ) ;
56+ ms . Position = 0 ;
57+ jksStore . Load ( ms , string . IsNullOrEmpty ( storePassword ) ? new char [ 0 ] : storePassword . ToCharArray ( ) ) ;
58+ }
5459
55- X509Certificate [ ] certificateChain = jksStore . GetCertificateChain ( alias ) ;
56- List < X509CertificateEntry > certificateChainEntries = new List < X509CertificateEntry > ( ) ;
57- foreach ( X509Certificate certificate in certificateChain )
60+ foreach ( string alias in jksStore . Aliases )
61+ {
62+ if ( jksStore . IsKeyEntry ( alias ) )
5863 {
59- certificateChainEntries . Add ( new X509CertificateEntry ( certificate ) ) ;
60- }
64+ AsymmetricKeyParameter keyParam = jksStore . GetKey ( alias , string . IsNullOrEmpty ( storePassword ) ? new char [ 0 ] : storePassword . ToCharArray ( ) ) ;
65+ AsymmetricKeyEntry keyEntry = new AsymmetricKeyEntry ( keyParam ) ;
6166
62- pkcs12Store . SetKeyEntry ( alias , keyEntry , certificateChainEntries . ToArray ( ) ) ;
63- }
64- else
65- {
66- pkcs12Store . SetCertificateEntry ( alias , new X509CertificateEntry ( jksStore . GetCertificate ( alias ) ) ) ;
67+ X509Certificate [ ] certificateChain = jksStore . GetCertificateChain ( alias ) ;
68+ List < X509CertificateEntry > certificateChainEntries = new List < X509CertificateEntry > ( ) ;
69+ foreach ( X509Certificate certificate in certificateChain )
70+ {
71+ certificateChainEntries . Add ( new X509CertificateEntry ( certificate ) ) ;
72+ }
73+
74+ pkcs12Store . SetKeyEntry ( alias , keyEntry , certificateChainEntries . ToArray ( ) ) ;
75+ }
76+ else
77+ {
78+ pkcs12Store . SetCertificateEntry ( alias , new X509CertificateEntry ( jksStore . GetCertificate ( alias ) ) ) ;
79+ }
6780 }
68- }
6981
70- // Second Pkcs12Store necessary because of an obscure BC bug where creating a Pkcs12Store without .Load (code above using "Set" methods only) does not set all internal hashtables necessary to avoid an error later
71- // when processing store.
72- MemoryStream ms2 = new MemoryStream ( ) ;
73- pkcs12Store . Save ( ms2 , string . IsNullOrEmpty ( storePassword ) ? new char [ 0 ] : storePassword . ToCharArray ( ) , new Org . BouncyCastle . Security . SecureRandom ( ) ) ;
74- ms2 . Position = 0 ;
82+ // Second Pkcs12Store necessary because of an obscure BC bug where creating a Pkcs12Store without .Load (code above using "Set" methods only) does not set all internal hashtables necessary to avoid an error later
83+ // when processing store.
84+ MemoryStream ms2 = new MemoryStream ( ) ;
85+ pkcs12Store . Save ( ms2 , string . IsNullOrEmpty ( storePassword ) ? new char [ 0 ] : storePassword . ToCharArray ( ) , new Org . BouncyCastle . Security . SecureRandom ( ) ) ;
86+ ms2 . Position = 0 ;
7587
76- pkcs12StoreNew . Load ( ms2 , string . IsNullOrEmpty ( storePassword ) ? new char [ 0 ] : storePassword . ToCharArray ( ) ) ;
88+ pkcs12StoreNew . Load ( ms2 , string . IsNullOrEmpty ( storePassword ) ? new char [ 0 ] : storePassword . ToCharArray ( ) ) ;
89+ }
90+ else
91+ {
92+ logger . LogDebug ( "Store is of type PKCS12" ) ;
93+ PKCS12CertificateStoreSerializer pkcs12Serializer = new PKCS12CertificateStoreSerializer ( string . Empty ) ;
94+ pkcs12StoreNew = pkcs12Serializer . DeserializeRemoteCertificateStore ( storeContents , storePath , storePassword , remoteHandler , isInventory ) ;
95+ }
7796
7897 logger . MethodExit ( LogLevel . Debug ) ;
7998 return pkcs12StoreNew ;
@@ -83,39 +102,50 @@ public List<SerializedStoreInfo> SerializeRemoteCertificateStore(Pkcs12Store cer
83102 {
84103 logger . MethodEntry ( LogLevel . Debug ) ;
85104
86- JksStore jksStore = new JksStore ( ) ;
105+ List < SerializedStoreInfo > storeInfo = new List < SerializedStoreInfo > ( ) ;
87106
88- foreach ( string alias in certificateStore . Aliases )
107+ if ( IsTypeJKS )
89108 {
90- if ( certificateStore . IsKeyEntry ( alias ) )
109+ JksStore jksStore = new JksStore ( ) ;
110+
111+ foreach ( string alias in certificateStore . Aliases )
91112 {
92- AsymmetricKeyEntry keyEntry = certificateStore . GetKey ( alias ) ;
93- X509CertificateEntry [ ] certificateChain = certificateStore . GetCertificateChain ( alias ) ;
113+ if ( certificateStore . IsKeyEntry ( alias ) )
114+ {
115+ AsymmetricKeyEntry keyEntry = certificateStore . GetKey ( alias ) ;
116+ X509CertificateEntry [ ] certificateChain = certificateStore . GetCertificateChain ( alias ) ;
94117
95- List < X509Certificate > certificates = new List < X509Certificate > ( ) ;
96- foreach ( X509CertificateEntry certificateEntry in certificateChain )
118+ List < X509Certificate > certificates = new List < X509Certificate > ( ) ;
119+ foreach ( X509CertificateEntry certificateEntry in certificateChain )
120+ {
121+ certificates . Add ( certificateEntry . Certificate ) ;
122+ }
123+
124+ jksStore . SetKeyEntry ( alias , keyEntry . Key , string . IsNullOrEmpty ( storePassword ) ? new char [ 0 ] : storePassword . ToCharArray ( ) , certificates . ToArray ( ) ) ;
125+ }
126+ else
97127 {
98- certificates . Add ( certificateEntry . Certificate ) ;
128+ jksStore . SetCertificateEntry ( alias , certificateStore . GetCertificate ( alias ) . Certificate ) ;
99129 }
100-
101- jksStore . SetKeyEntry ( alias , keyEntry . Key , string . IsNullOrEmpty ( storePassword ) ? new char [ 0 ] : storePassword . ToCharArray ( ) , certificates . ToArray ( ) ) ;
102130 }
103- else
131+
132+ using ( MemoryStream outStream = new MemoryStream ( ) )
104133 {
105- jksStore . SetCertificateEntry ( alias , certificateStore . GetCertificate ( alias ) . Certificate ) ;
134+ jksStore . Save ( outStream , string . IsNullOrEmpty ( storePassword ) ? new char [ 0 ] : storePassword . ToCharArray ( ) ) ;
135+
136+ storeInfo . Add ( new SerializedStoreInfo ( ) { FilePath = storePath + storeFileName , Contents = outStream . ToArray ( ) } ) ;
137+
138+ logger . MethodExit ( LogLevel . Debug ) ;
139+ return storeInfo ;
106140 }
107141 }
108-
109- using ( MemoryStream outStream = new MemoryStream ( ) )
142+ else
110143 {
111- jksStore . Save ( outStream , string . IsNullOrEmpty ( storePassword ) ? new char [ 0 ] : storePassword . ToCharArray ( ) ) ;
112-
113- List < SerializedStoreInfo > storeInfo = new List < SerializedStoreInfo > ( ) ;
114- storeInfo . Add ( new SerializedStoreInfo ( ) { FilePath = storePath + storeFileName , Contents = outStream . ToArray ( ) } ) ;
115-
116- logger . MethodExit ( LogLevel . Debug ) ;
117- return storeInfo ;
144+ PKCS12CertificateStoreSerializer pkcs12Serializer = new PKCS12CertificateStoreSerializer ( string . Empty ) ;
145+ storeInfo = pkcs12Serializer . SerializeRemoteCertificateStore ( certificateStore , storePath , storeFileName , storePassword , remoteHandler ) ;
118146 }
147+
148+ return storeInfo ;
119149 }
120150
121151 public string GetPrivateKeyPath ( )
0 commit comments