@@ -30,7 +30,7 @@ namespace WalletConnectSharp.Crypto
30
30
public class Crypto : ICrypto
31
31
{
32
32
private readonly string CRYPTO_CLIENT_SEED = $ "client_ed25519_seed";
33
-
33
+
34
34
private const string MULTICODEC_ED25519_ENCODING = "base58btc" ;
35
35
private const string MULTICODEC_ED25519_BASE = "z" ;
36
36
private const string MULTICODEC_ED25519_HEADER = "K36" ;
@@ -48,7 +48,7 @@ public class Crypto : ICrypto
48
48
private const int TYPE_LENGTH = 1 ;
49
49
private const int IV_LENGTH = 12 ;
50
50
private const int KEY_LENGTH = 32 ;
51
-
51
+
52
52
/// <summary>
53
53
/// The name of the crypto module
54
54
/// </summary>
@@ -71,19 +71,20 @@ public string Context
71
71
return "walletconnectsharp" ;
72
72
}
73
73
}
74
-
74
+
75
75
/// <summary>
76
76
/// The current KeyChain this crypto module instance is using
77
77
/// </summary>
78
78
public IKeyChain KeyChain { get ; private set ; }
79
-
79
+
80
80
/// <summary>
81
81
/// The current storage module this crypto module instance is using
82
82
/// </summary>
83
83
public IKeyValueStorage Storage { get ; private set ; }
84
84
85
85
private bool _initialized ;
86
86
private bool _newStorage ;
87
+ protected bool Disposed ;
87
88
88
89
/// <summary>
89
90
/// Create a new instance of the crypto module, with a given storage module.
@@ -97,7 +98,7 @@ public Crypto(IKeyValueStorage storage)
97
98
this . KeyChain = new KeyChain ( storage ) ;
98
99
this . Storage = storage ;
99
100
}
100
-
101
+
101
102
/// <summary>
102
103
/// Create a new instance of the crypto module, with a given keychain.
103
104
/// </summary>
@@ -128,7 +129,7 @@ public async Task Init()
128
129
{
129
130
if ( _newStorage )
130
131
await this . Storage . Init ( ) ;
131
-
132
+
132
133
await this . KeyChain . Init ( ) ;
133
134
this . _initialized = true ;
134
135
}
@@ -159,7 +160,7 @@ public Task<string> GenerateKeyPair()
159
160
var options = new KeyGenerationParameters ( SecureRandom . GetInstance ( "SHA256PRNG" ) , 1 ) ;
160
161
X25519KeyPairGenerator generator = new X25519KeyPairGenerator ( ) ;
161
162
generator . Init ( options ) ;
162
-
163
+
163
164
var keypair = generator . GenerateKeyPair ( ) ;
164
165
var publicKeyData = keypair . Public as X25519PublicKeyParameters ;
165
166
var privateKeyData = keypair . Private as X25519PrivateKeyParameters ;
@@ -281,7 +282,7 @@ public Task<string> Encrypt(EncryptParams @params)
281
282
282
283
var typeRaw = Bases . Base10 . Decode ( $ "{ @params . Type } ") ;
283
284
var iv = @params . Iv ;
284
-
285
+
285
286
byte [ ] rawIv ;
286
287
if ( iv == null )
287
288
{
@@ -308,7 +309,7 @@ public Task<string> Encrypt(EncryptParams @params)
308
309
{
309
310
byte [ ] temp = new byte [ encoded . Length * 3 ] ;
310
311
int len = aead . ProcessBytes ( encoded , 0 , encoded . Length , temp , 0 ) ;
311
-
312
+
312
313
if ( len > 0 )
313
314
{
314
315
encryptedStream . Write ( temp , 0 , len ) ;
@@ -327,7 +328,7 @@ public Task<string> Encrypt(EncryptParams @params)
327
328
{
328
329
if ( senderPublicKey == null )
329
330
throw new ArgumentException ( "Missing sender public key for type1 envelope" ) ;
330
-
331
+
331
332
return Task . FromResult ( Convert . ToBase64String (
332
333
typeRaw . Concat ( senderPublicKey ) . Concat ( rawIv ) . Concat ( encrypted ) . ToArray ( )
333
334
) ) ;
@@ -380,10 +381,7 @@ public async Task<string> Encode(string topic, IJsonRpcPayload payload, EncodeOp
380
381
var message = JsonConvert . SerializeObject ( payload ) ;
381
382
var results = await Encrypt ( new EncryptParams ( )
382
383
{
383
- Message = message ,
384
- Type = type ,
385
- SenderPublicKey = senderPublicKey ,
386
- SymKey = symKey
384
+ Message = message , Type = type , SenderPublicKey = senderPublicKey , SymKey = symKey
387
385
} ) ;
388
386
389
387
return results ;
@@ -398,7 +396,8 @@ public async Task<string> Encode(string topic, IJsonRpcPayload payload, EncodeOp
398
396
/// <param name="options">(optional) Decoding options</param>
399
397
/// <typeparam name="T">The type of the IJsonRpcPayload to convert the encoded Json to</typeparam>
400
398
/// <returns>The decoded, decrypted and deserialized object of type T from an async task</returns>
401
- public async Task < T > Decode < T > ( string topic , string encoded , DecodeOptions options = null ) where T : IJsonRpcPayload
399
+ public async Task < T > Decode < T > ( string topic , string encoded , DecodeOptions options = null )
400
+ where T : IJsonRpcPayload
402
401
{
403
402
this . IsInitialized ( ) ;
404
403
var @params = ValidateDecoding ( encoded , options ) ;
@@ -430,7 +429,8 @@ private EncodingParams Deserialize(string encoded)
430
429
var slice3 = slice2 + IV_LENGTH ;
431
430
var senderPublicKey = new ArraySegment < byte > ( bytes , slice1 , KEY_LENGTH ) ;
432
431
var iv = new ArraySegment < byte > ( bytes , slice2 , IV_LENGTH ) ;
433
- var @sealed = new ArraySegment < byte > ( bytes , slice3 , bytes . Length - ( TYPE_LENGTH + KEY_LENGTH + IV_LENGTH ) ) ;
432
+ var @sealed =
433
+ new ArraySegment < byte > ( bytes , slice3 , bytes . Length - ( TYPE_LENGTH + KEY_LENGTH + IV_LENGTH ) ) ;
434
434
435
435
return new EncodingParams ( )
436
436
{
@@ -446,12 +446,7 @@ private EncodingParams Deserialize(string encoded)
446
446
var iv = new ArraySegment < byte > ( bytes , slice1 , IV_LENGTH ) ;
447
447
var @sealed = new ArraySegment < byte > ( bytes , slice2 , bytes . Length - ( IV_LENGTH + TYPE_LENGTH ) ) ;
448
448
449
- return new EncodingParams ( )
450
- {
451
- Type = typeRaw ,
452
- Sealed = @sealed . ToArray ( ) ,
453
- Iv = iv . ToArray ( )
454
- } ;
449
+ return new EncodingParams ( ) { Type = typeRaw , Sealed = @sealed . ToArray ( ) , Iv = iv . ToArray ( ) } ;
455
450
}
456
451
}
457
452
@@ -493,12 +488,7 @@ public async Task<string> SignJwt(string aud)
493
488
signer . BlockUpdate ( data , 0 , data . Length ) ;
494
489
495
490
var signature = signer . GenerateSignature ( ) ;
496
- return EncodeJwt ( new IridiumJWTSigned ( )
497
- {
498
- Header = header ,
499
- Payload = payload ,
500
- Signature = signature
501
- } ) ;
491
+ return EncodeJwt ( new IridiumJWTSigned ( ) { Header = header , Payload = payload , Signature = signature } ) ;
502
492
}
503
493
504
494
/// <summary>
@@ -516,8 +506,8 @@ public async Task<string> GetClientId()
516
506
517
507
private string EncodeJwt ( IridiumJWTSigned data )
518
508
{
519
- return string . Join ( JWT_DELIMITER ,
520
- EncodeJson ( data . Header ) ,
509
+ return string . Join ( JWT_DELIMITER ,
510
+ EncodeJson ( data . Header ) ,
521
511
EncodeJson ( data . Payload ) ,
522
512
EncodeSig ( data . Signature )
523
513
) ;
@@ -549,7 +539,7 @@ private string EncodeIss(Ed25519PublicKeyParameters publicKey)
549
539
private Ed25519PrivateKeyParameters KeypairFromSeed ( byte [ ] seed )
550
540
{
551
541
return new Ed25519PrivateKeyParameters ( seed ) ;
552
-
542
+
553
543
/*var options = new KeyCreationParameters()
554
544
{
555
545
ExportPolicy = KeyExportPolicies.AllowPlaintextExport
@@ -578,10 +568,8 @@ private void IsInitialized()
578
568
{
579
569
if ( ! this . _initialized )
580
570
{
581
- throw WalletConnectException . FromType ( ErrorType . NOT_INITIALIZED , new Dictionary < string , object > ( )
582
- {
583
- { "Name" , Name }
584
- } ) ;
571
+ throw WalletConnectException . FromType ( ErrorType . NOT_INITIALIZED ,
572
+ new Dictionary < string , object > ( ) { { "Name" , Name } } ) ;
585
573
}
586
574
}
587
575
@@ -616,7 +604,7 @@ private byte[] DeriveSharedKey(string privateKeyA, string publicKeyB)
616
604
{
617
605
var keyB = PublicKey.Import(KeyAgreementAlgorithm.X25519, publicKeyB.HexToByteArray(),
618
606
KeyBlobFormat.RawPublicKey);
619
-
607
+
620
608
var options = new SharedSecretCreationParameters
621
609
{
622
610
ExportPolicy = KeyExportPolicies.AllowPlaintextArchiving
@@ -632,7 +620,7 @@ private byte[] DeriveSymmetricKey(byte[] secretKey)
632
620
generator . Init ( new HkdfParameters ( secretKey , Array . Empty < byte > ( ) , Array . Empty < byte > ( ) ) ) ;
633
621
634
622
byte [ ] key = new byte [ 32 ] ;
635
- generator . GenerateBytes ( key , 0 , 32 ) ;
623
+ generator . GenerateBytes ( key , 0 , 32 ) ;
636
624
637
625
return key ;
638
626
}
@@ -644,14 +632,14 @@ private string DeserializeAndDecrypt(string symKey, string encoded)
644
632
var iv = param . Iv ;
645
633
var type = int . Parse ( Bases . Base10 . Encode ( param . Type ) ) ;
646
634
var isType1 = type == TYPE_1 ;
647
-
635
+
648
636
var aead = new ChaCha20Poly1305 ( ) ;
649
637
aead . Init ( false , new ParametersWithIV ( new KeyParameter ( symKey . HexToByteArray ( ) ) , iv ) ) ;
650
638
651
639
using MemoryStream rawDecrypted = new MemoryStream ( ) ;
652
640
byte [ ] temp = new byte [ @sealed . Length ] ;
653
641
int len = aead . ProcessBytes ( @sealed , 0 , @sealed . Length , temp , 0 ) ;
654
-
642
+
655
643
if ( len > 0 )
656
644
{
657
645
rawDecrypted . Write ( temp , 0 , len ) ;
@@ -663,7 +651,7 @@ private string DeserializeAndDecrypt(string symKey, string encoded)
663
651
{
664
652
rawDecrypted . Write ( temp , 0 , len ) ;
665
653
}
666
-
654
+
667
655
return Encoding . UTF8 . GetString ( rawDecrypted . ToArray ( ) ) ;
668
656
}
669
657
@@ -687,7 +675,21 @@ private async Task<byte[]> GetClientSeed()
687
675
688
676
public void Dispose ( )
689
677
{
690
- KeyChain ? . Dispose ( ) ;
678
+ Dispose ( true ) ;
679
+ GC . SuppressFinalize ( this ) ;
680
+ }
681
+
682
+ protected virtual void Dispose ( bool disposing )
683
+ {
684
+ if ( Disposed )
685
+ return ;
686
+
687
+ if ( disposing )
688
+ {
689
+ KeyChain ? . Dispose ( ) ;
690
+ }
691
+
692
+ Disposed = true ;
691
693
}
692
694
}
693
695
}
0 commit comments