diff options
author | Sebastien Pouliot <sebastien@ximian.com> | 2002-10-12 05:26:11 +0400 |
---|---|---|
committer | Sebastien Pouliot <sebastien@ximian.com> | 2002-10-12 05:26:11 +0400 |
commit | d8299b0ed37e93971f7c66a055194a51d319a041 (patch) | |
tree | 1c58ec76893d78f9b6aa9a18f67db4178758e389 /mcs/class | |
parent | 216e5bdccc807b79acbeb97b86063baee4ea5c27 (diff) |
2002-10-11 Sebastien Pouliot <spouliot@videotron.ca>
* DES.cs: Create() using CryptoConfig, fix #30256
* DESCryptoServiceProvider.cs: fix #30256
* RandomNumberGenerator.cs: uncomment in Create(rng) for CryptoConfig
svn path=/trunk/mcs/; revision=8195
Diffstat (limited to 'mcs/class')
4 files changed, 113 insertions, 106 deletions
diff --git a/mcs/class/corlib/System.Security.Cryptography/ChangeLog b/mcs/class/corlib/System.Security.Cryptography/ChangeLog index 99797b4f65f..625fdccbc9f 100644 --- a/mcs/class/corlib/System.Security.Cryptography/ChangeLog +++ b/mcs/class/corlib/System.Security.Cryptography/ChangeLog @@ -1,3 +1,9 @@ +2002-10-11 Sebastien Pouliot <spouliot@videotron.ca> + + * DES.cs: Create() using CryptoConfig, fix #30256 + * DESCryptoServiceProvider.cs: fix #30256 + * RandomNumberGenerator.cs: uncomment in Create(rng) for CryptoConfig + 2002-10-10 Sebastien Pouliot <spouliot@videotron.ca> * AsymmetricAlgorithm.cs: Inherit from IDisposable, common support from XML import diff --git a/mcs/class/corlib/System.Security.Cryptography/DES.cs b/mcs/class/corlib/System.Security.Cryptography/DES.cs index f2d344f21c2..993f71937e3 100644 --- a/mcs/class/corlib/System.Security.Cryptography/DES.cs +++ b/mcs/class/corlib/System.Security.Cryptography/DES.cs @@ -3,6 +3,9 @@ // // Author: // Sergey Chaban (serge@wildwestsoftware.com) +// Sebastien Pouliot (spouliot@motus.com) +// +// Portions (C) 2002 Motus Technologies Inc. (http://www.motus.com) // using System; @@ -521,35 +524,29 @@ namespace System.Security.Cryptography { } // DESCore - - public abstract class DES : SymmetricAlgorithm { - private byte [] key; public DES () { + KeySizeValue = 64; + BlockSizeValue = 64; + FeedbackSizeValue = 64; } - [MonoTODO] - public static new DES Create() + public static new DES Create () { - // TODO: implement - return null; + return Create ("System.Security.Cryptography.DES"); } - [MonoTODO] - public static new DES Create(string name) - { - // TODO: implement - return null; + public static new DES Create (string algo) + { + return (DES) CryptoConfig.CreateFromName (algo); } - public static bool IsWeakKey (byte [] rgbKey) { - if (!DESCore.IsValidKeySize (rgbKey)) { + if (!DESCore.IsValidKeySize (rgbKey)) throw new CryptographicException (); - } ulong lk = DESCore.PackKey (rgbKey); foreach (ulong wk in DESCore.weakKeys) { @@ -558,12 +555,10 @@ namespace System.Security.Cryptography { return false; } - public static bool IsSemiWeakKey (byte [] rgbKey) { - if (!DESCore.IsValidKeySize (rgbKey)) { + if (!DESCore.IsValidKeySize (rgbKey)) throw new CryptographicException (); - } ulong lk = DESCore.PackKey (rgbKey); foreach (ulong swk in DESCore.semiweakKeys) { @@ -573,12 +568,17 @@ namespace System.Security.Cryptography { } public override byte[] Key { - get { - return this.key; - } + get { return KeyValue; } set { - this.key = new byte [DESCore.KEY_BYTE_SIZE]; - Array.Copy (value, 0, this.key, 0, DESCore.KEY_BYTE_SIZE); + if (value == null) + throw new ArgumentNullException (); + if (value.Length != (BlockSizeValue >> 3)) + throw new ArgumentException (); + if (IsWeakKey (value) || IsSemiWeakKey (value)) + throw new CryptographicException (); + + KeyValue = new byte [DESCore.KEY_BYTE_SIZE]; + Array.Copy (value, 0, KeyValue, 0, DESCore.KEY_BYTE_SIZE); } } diff --git a/mcs/class/corlib/System.Security.Cryptography/DESCryptoServiceProvider.cs b/mcs/class/corlib/System.Security.Cryptography/DESCryptoServiceProvider.cs index e04c3d36227..35a4878aad8 100644 --- a/mcs/class/corlib/System.Security.Cryptography/DESCryptoServiceProvider.cs +++ b/mcs/class/corlib/System.Security.Cryptography/DESCryptoServiceProvider.cs @@ -3,8 +3,10 @@ // // Author: // Sergey Chaban (serge@wildwestsoftware.com) +// Sebastien Pouliot (spouliot@motus.com) +// +// Portions (C) 2002 Motus Technologies Inc. (http://www.motus.com) // - using System; @@ -13,10 +15,9 @@ using System.Security.Cryptography; namespace System.Security.Cryptography { - internal class DESTransformBase : ICryptoTransform { - internal enum Mode : int { + internal enum Action : int { ENCRYPTOR = 0, DECRYPTOR = 1 } @@ -31,16 +32,21 @@ namespace System.Security.Cryptography { private byte [] iv; private byte [] tmpBlock; + private CipherMode mode; + private Action action; - protected DESTransformBase (Mode mode, byte [] key, byte [] iv) + protected DESTransformBase (Action action, byte [] key, byte [] iv, CipherMode mode) { core = new DESCore (); + this.action = action; + this.mode = mode; - if (mode == Mode.ENCRYPTOR) { + if (action == Action.ENCRYPTOR) { cryptFn = new DESCore.DESCall (core.Encrypt); preprocess = new Filter (this.EncPreprocess); postprocess = new Filter (this.EncPostprocess); - } else { + } + else { cryptFn = new DESCore.DESCall (core.Decrypt); preprocess = new Filter (this.DecPreprocess); postprocess = new Filter (this.DecPostprocess); @@ -53,13 +59,17 @@ namespace System.Security.Cryptography { tmpBlock = new byte [DESCore.BLOCK_BYTE_SIZE]; } + void System.IDisposable.Dispose () + { + } public virtual bool CanTransformMultipleBlocks { - get { - return true; - } + get { return false; } } + public bool CanReuseTransform { + get { return true; } + } public virtual int InputBlockSize { get { @@ -73,7 +83,7 @@ namespace System.Security.Cryptography { } } - private void EncPreprocess (byte [] workBuff) + private void EncPreprocess (byte [] workBuff) { byte [] iv = this.iv; for (int i = 0; i < DESCore.BLOCK_BYTE_SIZE; i++) { @@ -81,34 +91,31 @@ namespace System.Security.Cryptography { } } - private void EncPostprocess (byte [] workBuff) + private void EncPostprocess (byte [] workBuff) { Array.Copy (workBuff, 0, iv, 0, DESCore.BLOCK_BYTE_SIZE); } - private void DecPreprocess (byte [] workBuff) + private void DecPreprocess (byte [] workBuff) { Array.Copy (workBuff, 0, tmpBlock, 0, DESCore.BLOCK_BYTE_SIZE); } - private void DecPostprocess (byte [] workBuff) + private void DecPostprocess (byte [] workBuff) { EncPreprocess (workBuff); Array.Copy (tmpBlock, 0, iv, 0, DESCore.BLOCK_BYTE_SIZE); } - - - private void Transform (byte [] workBuff) + private void Transform (byte [] workBuff) { preprocess (workBuff); cryptFn (workBuff, null); postprocess (workBuff); } - - public virtual int TransformBlock (byte [] inputBuffer, int inputOffset, int inputCount, byte [] outputBuffer, int outputOffset) + public virtual int TransformBlock (byte [] inputBuffer, int inputOffset, int inputCount, byte [] outputBuffer, int outputOffset) { if ((inputCount & (DESCore.BLOCK_BYTE_SIZE-1)) != 0) throw new CryptographicException ("Invalid input block size."); @@ -133,12 +140,8 @@ namespace System.Security.Cryptography { return (full * step); } - - [MonoTODO] - public virtual byte [] TransformFinalBlock (byte [] inputBuffer, int inputOffset, int inputCount) + public virtual byte [] TransformFinalBlock (byte [] inputBuffer, int inputOffset, int inputCount) { - // TODO: add decryption support - int num = (inputCount + DESCore.BLOCK_BYTE_SIZE) & (~(DESCore.BLOCK_BYTE_SIZE-1)); byte [] res = new byte [num]; int full = num - DESCore.BLOCK_BYTE_SIZE; @@ -147,15 +150,26 @@ namespace System.Security.Cryptography { int rem = inputCount & (DESCore.BLOCK_BYTE_SIZE-1); - // PKCS-5 padding - for (int i = num; --i >= (num - rem);) { - res [i] = (byte) rem; - } + if (action == Action.ENCRYPTOR) { + // PKCS#7 padding + int p7Padding = DESCore.BLOCK_BYTE_SIZE - (inputCount % DESCore.BLOCK_BYTE_SIZE); + for (int i = DESCore.BLOCK_BYTE_SIZE; --i >= (DESCore.BLOCK_BYTE_SIZE - p7Padding);) { + res [i] = (byte) p7Padding; + } - Array.Copy (inputBuffer, inputOffset + full, res, full, rem); + Array.Copy (inputBuffer, inputOffset + full, res, full, rem); - // the last padded block will be transformed in-place - TransformBlock (res, full, DESCore.BLOCK_BYTE_SIZE, res, full); + // the last padded block will be transformed in-place + TransformBlock (res, full, DESCore.BLOCK_BYTE_SIZE, res, full); + } + else { + // PKCS#7 padding + byte padding = res [inputCount - 1]; + for (int i = 0; i < padding; i++) { + if (res [inputCount - 1 - i] == padding) + res[inputCount - 1 - i] = 0x00; + } + } /* byte [] workBuff = new byte [DESCore.BLOCK_BYTE_SIZE]; @@ -168,81 +182,69 @@ namespace System.Security.Cryptography { return res; } - } // DESTransformBase internal sealed class DESEncryptor : DESTransformBase { - internal DESEncryptor (byte [] key, byte [] iv) - : base (DESTransformBase.Mode.ENCRYPTOR, key, iv) + internal DESEncryptor (byte [] key, byte [] iv, CipherMode mode) + : base (DESTransformBase.Action.ENCRYPTOR, key, iv, mode) { } } // DESEncryptor internal sealed class DESDecryptor : DESTransformBase { - internal DESDecryptor (byte [] key, byte [] iv) - : base (DESTransformBase.Mode.DECRYPTOR, key, iv) + internal DESDecryptor (byte [] key, byte [] iv, CipherMode mode) + : base (DESTransformBase.Action.DECRYPTOR, key, iv, mode) { } } // DESDecryptor - public sealed class DESCryptoServiceProvider { - private byte [] iv; - private byte [] key; + public sealed class DESCryptoServiceProvider : DES { + private RandomNumberGenerator rng; public DESCryptoServiceProvider () { + // there are no constructor accepting a secret key + // so we always need the RNG (using the default one) + rng = RandomNumberGenerator.Create(); + // there's always a default key/iv available when + // creating a symmetric algorithm object + GenerateKey(); + GenerateIV(); } - - // - // Factories - // - - public ICryptoTransform CreateEncryptor() + public override ICryptoTransform CreateEncryptor (byte[] rgbKey, byte[] rgbIV) { - return new DESEncryptor (key, iv); + // by using Key/IV (instead of KeyValue/IVValue) we get + // all validation done by "set" + Key = rgbKey; + IV = rgbIV; + return new DESEncryptor (KeyValue, IVValue, ModeValue); } - public ICryptoTransform CreateDecryptor() + public override ICryptoTransform CreateDecryptor (byte[] rgbKey, byte[] rgbIV) { - return new DESDecryptor (key, iv); - } - - - - // FIXME: Ought to be in DES.cs - - [MonoTODO ("Ought to be in DES.cs")] - public /*override*/ byte[] Key { - get { - return this.key; - } - set { - this.key = new byte [DESCore.KEY_BYTE_SIZE]; - Array.Copy (value, 0, this.key, 0, DESCore.KEY_BYTE_SIZE); - } + // by using Key/IV (instead of KeyValue/IVValue) we get + // all validation done by "set" + Key = rgbKey; + IV = rgbIV; + return new DESDecryptor (KeyValue, IVValue, ModeValue); } - public byte[] IV { - get { - return this.iv; - } - set { - this.iv = new byte [DESCore.KEY_BYTE_SIZE]; - Array.Copy (value, 0, this.iv, 0, DESCore.KEY_BYTE_SIZE); - } + public override void GenerateIV () + { + IVValue = new byte [DESCore.BLOCK_BYTE_SIZE]; + rng.GetBytes (IVValue); } - - - - - public override string ToString () + public override void GenerateKey () { - return "mono::System.Security.Cryptography.DESCryptoServiceProvider"; + KeyValue = new byte [DESCore.KEY_BYTE_SIZE]; + rng.GetBytes (KeyValue); + while (IsWeakKey (KeyValue) || IsSemiWeakKey (KeyValue)) + rng.GetBytes (KeyValue); } } // DESCryptoServiceProvider diff --git a/mcs/class/corlib/System.Security.Cryptography/RandomNumberGenerator.cs b/mcs/class/corlib/System.Security.Cryptography/RandomNumberGenerator.cs index f6bc1c51608..a2bcace42c7 100755 --- a/mcs/class/corlib/System.Security.Cryptography/RandomNumberGenerator.cs +++ b/mcs/class/corlib/System.Security.Cryptography/RandomNumberGenerator.cs @@ -13,18 +13,17 @@ namespace System.Security.Cryptography { public abstract class RandomNumberGenerator { - public RandomNumberGenerator () { - } + public RandomNumberGenerator () {} - public static RandomNumberGenerator Create () { + public static RandomNumberGenerator Create () + { // create the default random number generator return Create ("System.Security.Cryptography.RandomNumberGenerator"); } - [MonoTODO] - public static RandomNumberGenerator Create (string rngName) { - return null; - // return (RandomNumberGenerator) (CryptoConfig.CreateFromName (rngName)); + public static RandomNumberGenerator Create (string rngName) + { + return (RandomNumberGenerator) (CryptoConfig.CreateFromName (rngName)); } public abstract void GetBytes (byte[] data); |