@@ -25,6 +25,7 @@ public class SecurityUtils
2525 /// Constants for formatting the request textual representation for signing.
2626 /// </summary>
2727 private const string NEWLINE = "\n " ;
28+ private const string WINDOWS_NEWLINE = "\r \n " ;
2829 private const string FORMAT_METHOD_AND_ENDPOINT_STRING = "{0} /v1/{1}" ;
2930 private const string HEADER_NAME_PREFIX_X_BUNQ = "X-Bunq-" ;
3031 private const string DELIMITER_HEADER_VALUE = "," ;
@@ -38,12 +39,17 @@ public class SecurityUtils
3839 /// <summary>
3940 /// Constants for formatting RSA keys.
4041 /// </summary>
41- private const string PUBLIC_KEY_START = "-----BEGIN PUBLIC KEY-----\n " ;
42- private const string PUBLIC_KEY_END = "\n -----END PUBLIC KEY-----\n " ;
43- private const string FORMAT_PUBLIC_KEY = PUBLIC_KEY_START + "{0}" + PUBLIC_KEY_END ;
44- private const string PRIVATE_KEY_START = "-----BEGIN PRIVATE KEY-----\n " ;
45- private const string PRIVATE_KEY_END = "\n -----END PRIVATE KEY-----\n " ;
46- private const string FORMAT_PRIVATE_KEY = PRIVATE_KEY_START + "{0}" + PRIVATE_KEY_END ;
42+ private const string PUBLIC_KEY_START = "-----BEGIN PUBLIC KEY-----" + NEWLINE ;
43+ private const string PUBLIC_KEY_END = NEWLINE + "-----END PUBLIC KEY-----" ;
44+ private const string FORMAT_PUBLIC_KEY = PUBLIC_KEY_START + "{0}" + PUBLIC_KEY_END + NEWLINE ;
45+ private const string PRIVATE_KEY_START = "-----BEGIN PRIVATE KEY-----" + NEWLINE ;
46+ private const string PRIVATE_KEY_END = NEWLINE + "-----END PRIVATE KEY-----" ;
47+ private const string FORMAT_PRIVATE_KEY = PRIVATE_KEY_START + "{0}" + PRIVATE_KEY_END + NEWLINE ;
48+ private const string RSA_PRIVATE_KEY_START = "-----BEGIN RSA PRIVATE KEY-----" + NEWLINE ;
49+ private const string RSA_PRIVATE_KEY_END = NEWLINE + "-----END RSA PRIVATE KEY-----" ;
50+ private const string CERTIFICATE_START = "-----BEGIN CERTIFICATE-----" + NEWLINE ;
51+ private const string CERTIFICATE_END = NEWLINE + "-----END CERTIFICATE-----" ;
52+ private const string FORMAT_CERTIFICATE = CERTIFICATE_START + "{0}" + CERTIFICATE_END + NEWLINE ;
4753
4854 /// <summary>
4955 /// Size of the encryption key.
@@ -209,8 +215,10 @@ public static string GetPrivateKeyFormattedString(RSA keyPair)
209215 public static RSA CreateKeyPairFromPrivateKeyFormattedString ( string privateKeyString )
210216 {
211217 var privateKeyStringTrimmed = privateKeyString
218+ . Replace ( WINDOWS_NEWLINE , NEWLINE )
212219 . Replace ( PRIVATE_KEY_START , string . Empty )
213- . Replace ( PRIVATE_KEY_END , string . Empty ) ;
220+ . Replace ( PRIVATE_KEY_END , string . Empty )
221+ . Trim ( ) ;
214222
215223 return RsaKeyUtils . DecodePrivateKeyInfo ( Convert . FromBase64String ( privateKeyStringTrimmed ) ) ;
216224 }
@@ -221,8 +229,10 @@ public static RSA CreateKeyPairFromPrivateKeyFormattedString(string privateKeySt
221229 public static RSA CreateKeyPairFromRsaPrivateKeyFormattedString ( string privateKeyString )
222230 {
223231 var privateKeyStringTrimmed = privateKeyString
224- . Replace ( "-----BEGIN RSA PRIVATE KEY-----\n " , "" )
225- . Replace ( "\n -----END RSA PRIVATE KEY-----\n " , "" ) ;
232+ . Replace ( WINDOWS_NEWLINE , NEWLINE )
233+ . Replace ( RSA_PRIVATE_KEY_START , String . Empty )
234+ . Replace ( RSA_PRIVATE_KEY_END , String . Empty )
235+ . Trim ( ) ;
226236
227237 return RsaKeyUtils . DecodeRsaPrivateKey ( Convert . FromBase64String ( privateKeyStringTrimmed ) ) ;
228238 }
@@ -233,8 +243,10 @@ public static RSA CreateKeyPairFromRsaPrivateKeyFormattedString(string privateKe
233243 public static RSA CreatePublicKeyFromPublicKeyFormattedString ( string publicKeyString )
234244 {
235245 var publicKeyStringTrimmed = publicKeyString
246+ . Replace ( WINDOWS_NEWLINE , NEWLINE )
236247 . Replace ( PUBLIC_KEY_START , string . Empty )
237- . Replace ( PUBLIC_KEY_END , string . Empty ) ;
248+ . Replace ( PUBLIC_KEY_END , string . Empty )
249+ . Trim ( ) ;
238250
239251 return RsaKeyUtils . DecodePublicKey ( Convert . FromBase64String ( publicKeyStringTrimmed ) ) ;
240252 }
@@ -355,27 +367,32 @@ private static string GenerateResponseHeadersSortedString(HttpResponseMessage re
355367 ) ;
356368 }
357369
370+ /// <summary>
371+ /// Creates a PEM-formatted certificate string from a given X509Certificate object
372+ /// string.
373+ /// </summary>
358374 public static string ExportCertificateToPEM ( X509Certificate cert )
359375 {
360- StringBuilder builder = new StringBuilder ( ) ;
376+ var certificateBytes = cert . Export ( X509ContentType . Cert ) ;
361377
362- builder . AppendLine ( "-----BEGIN CERTIFICATE-----" ) ;
363- var base64 = Convert . ToBase64String ( cert . Export ( X509ContentType . Cert ) ) ;
364- builder . AppendLine ( WrapBase64 ( base64 ) ) ;
365- builder . AppendLine ( "-----END CERTIFICATE-----" ) ;
366-
367- return builder . ToString ( ) ;
378+ return string . Format ( FORMAT_CERTIFICATE , WrapBase64 ( Convert . ToBase64String ( certificateBytes ) ) ) ;
368379 }
369-
380+
381+ /// <summary>
382+ /// Wraps a base64 string to 64-character wide lines according to typical certificate/key export rules.
383+ /// </summary>
384+ /// <param name="base64">base64 string without line breaks</param>
385+ /// <returns>base64-string formatted with line breaks</returns>
370386 private static string WrapBase64 ( string base64 )
371387 {
372- StringBuilder builder = new StringBuilder ( ) ;
388+ var builder = new StringBuilder ( ) ;
373389 for ( var ctr = 0 ; ctr <= base64 . Length / 64 ; ctr ++ )
374390 {
375- builder . AppendLine ( base64 . Substring ( ctr * 64 ,
391+ builder . Append ( base64 . Substring ( ctr * 64 ,
376392 ctr * 64 + 64 <= base64 . Length
377393 ? 64
378- : base64 . Length - ctr * 64 ) ) ;
394+ : base64 . Length - ctr * 64 ) )
395+ . Append ( NEWLINE ) ;
379396 }
380397
381398 return builder . ToString ( ) . Trim ( ) ;
@@ -387,7 +404,7 @@ public static string ExportCertificateCollectionToPEM(X509CertificateCollection
387404
388405 foreach ( var chainElement in certChain )
389406 {
390- builder . AppendLine ( ExportCertificateToPEM ( chainElement ) ) ;
407+ builder . Append ( ExportCertificateToPEM ( chainElement ) ) . Append ( NEWLINE ) ;
391408 }
392409
393410 return builder . ToString ( ) ;
0 commit comments