这是一个使用DES进行文件加密的类,只有两个方法,一个是加密方法:public void Encrypt(string FileName),另一个是解密方法:public void Decrypt(string FileName),能进行加密,但解密时候出现错误,错误信息为:要解密的数据的长度无效。
请高手赐教!
    class DESCrypt
    {
        private string Key = "12345678";
        public void Encrypt(string FileName)
        {
            DESCryptoServiceProvider des = new DESCryptoServiceProvider();
            des.Key = ASCIIEncoding.Default.GetBytes(Key);
            des.IV = ASCIIEncoding.Default.GetBytes(Key);
            FileStream InputFileStream = File.OpenRead(FileName);
            byte[] FileStreamArray = new byte[InputFileStream.Length-1];
            InputFileStream.Read(FileStreamArray, 0, FileStreamArray.Length);
            InputFileStream.Close();
            MemoryStream ms = new MemoryStream();
            CryptoStream FileCryptoStream = new CryptoStream(ms,des.CreateEncryptor(), CryptoStreamMode.Write);
            FileCryptoStream.Write(FileStreamArray, 0, FileStreamArray.Length);
            FileCryptoStream.FlushFinalBlock();
            InputFileStream = File.OpenWrite(FileName);
            foreach (byte b in ms.ToArray())
            {
                InputFileStream.WriteByte(b);            }
            ms.Close();
            InputFileStream.Close();
            FileCryptoStream.Close();
        }
        public void Decrypt(string FileName) 
        {
            DESCryptoServiceProvider des = new DESCryptoServiceProvider();
            des.Key = ASCIIEncoding.Default.GetBytes(Key);
            des.IV = ASCIIEncoding.Default.GetBytes(Key);
            FileStream InputFileStream = File.OpenRead(FileName);
            byte[] FileStreamArray = new byte[InputFileStream.Length - 1];
            InputFileStream.Read(FileStreamArray, 0, FileStreamArray.Length);
            InputFileStream.Close();
            MemoryStream ms = new MemoryStream();
            CryptoStream FileCryptoStream = new CryptoStream(ms, des.CreateDecryptor(), CryptoStreamMode.Write);
            FileCryptoStream.Write(FileStreamArray, 0, FileStreamArray.Length);
            FileCryptoStream.FlushFinalBlock();
            InputFileStream = File.OpenWrite(FileName);
            foreach (byte b in ms.ToArray())
            {
                InputFileStream.WriteByte(b);            }
            ms.Close();
            InputFileStream.Close();
            FileCryptoStream.Close();
        }
    }

解决方案 »

  1.   

    using System;
    using System.Security.Cryptography;
    using System.Text;
    using System.IO;namespace Common
    ...{
        /**//// <summary>
        /// DESEncrypt加密解密算法。
        /// </summary>
        public sealed class DESEncrypt
        ...{
            private DESEncrypt()
            ...{
                //
                // TODO: 在此处添加构造函数逻辑
                //
            }        private static string key = "zhoufoxcn";        /**//// <summary>
            /// 对称加密解密的密钥
            /// </summary>
            public static string Key
            ...{
                get
                ...{
                    return key;
                }
                set
                ...{
                    key = value;
                }
            }        /**//// <summary>
            /// DES加密
            /// </summary>
            /// <param name="encryptString"></param>
            /// <returns></returns>
            public static string DesEncrypt(string encryptString)
            ...{
                byte[] keyBytes = Encoding.UTF8.GetBytes(key.Substring(0, 8));
                byte[] keyIV = keyBytes;
                byte[] inputByteArray = Encoding.UTF8.GetBytes(encryptString);
                DESCryptoServiceProvider provider = new DESCryptoServiceProvider();
                MemoryStream mStream = new MemoryStream();
                CryptoStream cStream = new CryptoStream(mStream, provider.CreateEncryptor(keyBytes, keyIV), CryptoStreamMode.Write);
                cStream.Write(inputByteArray, 0, inputByteArray.Length);
                cStream.FlushFinalBlock();
                return Convert.ToBase64String(mStream.ToArray());
            }        /**//// <summary>
            /// DES解密
            /// </summary>
            /// <param name="decryptString"></param>
            /// <returns></returns>
            public static string DesDecrypt(string decryptString)
            ...{
                byte[] keyBytes = Encoding.UTF8.GetBytes(key.Substring(0, 8));
                byte[] keyIV = keyBytes;
                byte[] inputByteArray = Convert.FromBase64String(decryptString);
                DESCryptoServiceProvider provider = new DESCryptoServiceProvider();
                MemoryStream mStream = new MemoryStream();
                CryptoStream cStream = new CryptoStream(mStream, provider.CreateDecryptor(keyBytes, keyIV), CryptoStreamMode.Write);
                cStream.Write(inputByteArray, 0, inputByteArray.Length);
                cStream.FlushFinalBlock();
                return Encoding.UTF8.GetString(mStream.ToArray());
            }
        }
    }
    看看这个,我自己用的,也是我自己写的。
      

  2.   

    我也在试,首先我发现一个问题就是那个byte[]的数组初始化的时候,我不明白楼主为什么要-1
    我把-1去掉了就会正常
    但后面会出现一个字符串,而这个字符串在加密后和解密后都是会跟在结尾的(同样的值)
      

  3.   

    试一下我的方法:    public string Encrypt(string stringToEncrypt, string sKey)
        {
            DESCryptoServiceProvider des = new DESCryptoServiceProvider();
            byte[] inputByteArray = Encoding.GetEncoding("UTF-8").GetBytes(stringToEncrypt);
            des.Key = ASCIIEncoding.UTF8.GetBytes(sKey);
            des.IV = ASCIIEncoding.UTF8.GetBytes(sKey);
            MemoryStream ms = new MemoryStream();
            CryptoStream cs = new CryptoStream(ms, des.CreateEncryptor(), CryptoStreamMode.Write);        cs.Write(inputByteArray, 0, inputByteArray.Length);
            cs.FlushFinalBlock();        StringBuilder ret = new StringBuilder();
            foreach (byte b in ms.ToArray())
            {
                ret.AppendFormat("{0:X2}", b);
            }
            ret.ToString();
            return ret.ToString();
        }    public string Decrypt(string stringToDecrypt, string sKey)
        {
            DESCryptoServiceProvider des = new DESCryptoServiceProvider();        byte[] inputByteArray = new byte[stringToDecrypt.Length / 2];
            for (int x = 0; x < stringToDecrypt.Length / 2; x++)
            {
                int i = (Convert.ToInt32(stringToDecrypt.Substring(x * 2, 2), 16));
                inputByteArray[x] = (byte)i;
            }        des.Key = ASCIIEncoding.UTF8.GetBytes(sKey);
            des.IV = ASCIIEncoding.UTF8.GetBytes(sKey);
            MemoryStream ms = new MemoryStream();
            CryptoStream cs = new CryptoStream(ms, des.CreateDecryptor(), CryptoStreamMode.Write);
            cs.Write(inputByteArray, 0, inputByteArray.Length);
            cs.FlushFinalBlock();        StringBuilder ret = new StringBuilder();        return System.Text.Encoding.Default.GetString(ms.ToArray());
        }
      

  4.   

    还有就是,你那个解密的File.OpenWrite( FileName );是不能够覆盖完全的所以顺便把你的类改了一下写入文件和读取密文的地方class DESCrypt
    {
    private string Key = "12345678";
    public void Encrypt( string FileName )
    {
    DESCryptoServiceProvider des = new DESCryptoServiceProvider();
    des.Key = ASCIIEncoding.Default.GetBytes( Key );
    des.IV = ASCIIEncoding.Default.GetBytes( Key ); FileStream InputFileStream = File.OpenRead( FileName );
    byte[] FileStreamArray = new byte[InputFileStream.Length]; InputFileStream.Read( FileStreamArray , 0 , FileStreamArray.Length );
    InputFileStream.Close(); MemoryStream ms = new MemoryStream();
    CryptoStream FileCryptoStream = new CryptoStream( ms , des.CreateEncryptor() , CryptoStreamMode.Write );
    FileCryptoStream.Write( FileStreamArray , 0 , FileStreamArray.Length );
    FileCryptoStream.Close(); InputFileStream = File.OpenWrite( FileName ); foreach( byte b in ms.ToArray() )
    {
    InputFileStream.WriteByte( b );
    }
    ms.Close();
    InputFileStream.Close();
    } public void Decrypt( string FileName )
    {
    //生成Provider并设置钥匙
    DESCryptoServiceProvider des = new DESCryptoServiceProvider();
    des.Key = ASCIIEncoding.Default.GetBytes( Key );
    des.IV = ASCIIEncoding.Default.GetBytes( Key ); //读取已加密数据
    StreamReader reader = new StreamReader( FileName );
    byte[] FileStreamArray = new byte[reader.BaseStream.Length]; reader.BaseStream.Read( FileStreamArray , 0 , FileStreamArray.Length );
    reader.Close(); //生成解密流
    MemoryStream ms = new MemoryStream( FileStreamArray );
    CryptoStream FileCryptoStream = new CryptoStream( ms , des.CreateDecryptor() , CryptoStreamMode.Read );

    //读取解密了的数据,并写入原来的文件
    BinaryReader br = new BinaryReader( FileCryptoStream );
    FileStreamArray = new byte[1000]; BinaryWriter bw = new BinaryWriter( new StreamWriter( FileName ).BaseStream );
    int iReadLength;//读取了多长
    while( ( iReadLength = br.Read( FileStreamArray , 0 , 1000 ) ) > 0 )
    {
    bw.Write( FileStreamArray , 0 , iReadLength );
    } //关闭
    bw.Close();
    FileCryptoStream.Close();
    ms.Close();
    }
    }
      

  5.   

    4楼的方法是正确的,关键是byte[]和String的无损转换问题