11

文字列を暗号化してから、再度復号化できるようにする必要があります。

ここでソリューションを実装しましたが、うまく機能しますが、結果の文字列は、ユーザーが使用できるようにシンプルで短い必要があるため、適切ではありません。

増分データベース ID を (1 から) 暗号化していますが、500 を超えることはありません。理想的には、暗号化された文字列の長さは 6 文字を超えないようにしたいと考えています。

どんなアイデアでも大歓迎..

編集:ユーザーがこの生成された文字列を使用して後日再開できる長いフォームです

4

4 に答える 4

8

パディングなしで AES をCTR モードで使用できます。このモードでは、暗号化されたカウンターがあり、結果は数値である平文と xor されます。結果は小さいはずであり、使用する置換暗号よりも優れた AES の暗号化が得られます (これはおそらく手で破ることができます)。ただし、 BouncyCastle 暗号ライブラリを取得する必要があります。Rijndaelの Microsoft 実装には、使用可能なモードとして CTR がないためです。以下は、実装する必要がある AES クラスの例です。暗号化と復号化の例と同様に。

using System;
using System.Text;
using Org.BouncyCastle.Crypto;
using Org.BouncyCastle.Crypto.Engines;
using Org.BouncyCastle.Crypto.Modes;
using Org.BouncyCastle.Crypto.Parameters;

public class AES
{
    private readonly Encoding encoding;

    private SicBlockCipher mode;


    public AES(Encoding encoding)
    {
        this.encoding = encoding;
        this.mode = new SicBlockCipher(new AesFastEngine());
    }

    public static string ByteArrayToString(byte[] bytes)
    {
        return BitConverter.ToString(bytes).Replace("-", string.Empty);
    }

    public static byte[] StringToByteArray(string hex)
    {
        int numberChars = hex.Length;
        byte[] bytes = new byte[numberChars / 2];

        for (int i = 0; i < numberChars; i += 2)
        {
            bytes[i / 2] = Convert.ToByte(hex.Substring(i, 2), 16);
        }

        return bytes;
    }


    public string Encrypt(string plain, byte[] key, byte[] iv)
    {
        byte[] input = this.encoding.GetBytes(plain);

        byte[] bytes = this.BouncyCastleCrypto(true, input, key, iv);

        string result = ByteArrayToString(bytes);

        return result;
    }


    public string Decrypt(string cipher, byte[] key, byte[] iv)
    {
        byte[] bytes = this.BouncyCastleCrypto(false, StringToByteArray(cipher), key, iv);

        string result = this.encoding.GetString(bytes);

        return result;
    }


    private byte[] BouncyCastleCrypto(bool forEncrypt, byte[] input, byte[] key, byte[] iv)
    {
        try
        {
            this.mode.Init(forEncrypt, new ParametersWithIV(new KeyParameter(key), iv));

            BufferedBlockCipher cipher = new BufferedBlockCipher(this.mode);

            return cipher.DoFinal(input);
        }
        catch (CryptoException)
        {
            throw;
        }
    }
}

使用例

string test = "1";

AES aes = new AES(System.Text.Encoding.UTF8);

RNGCryptoServiceProvider rngCsp = new RNGCryptoServiceProvider();
byte[] key = new byte[32];
byte[] iv = new byte[32];

// Generate random key and IV
rngCsp.GetBytes(key);
rngCsp.GetBytes(iv);

string cipher = aes.Encrypt(test, key, iv);

string plaintext = aes.Decrypt(cipher, key, iv);

Response.Write(cipher + "<BR/>");

Response.Write(plaintext);

出力例

CB
1 
于 2012-11-08T21:21:19.927 に答える
3
//encryption   
string output="";   
char[] readChar = yourInput.ToCharArray();   
for (int i = 0; i < readChar.Length; i++)  
{   
    int no = Convert.ToInt32(readChar[i]) + 10;   
    string r = Convert.ToChar(no).ToString();   
    output+=r;   
}  
//decryption  
string output="";   
char[] readChar = yourInput.ToCharArray();   
for (int i = 0; i < readChar.Length; i++)   
{   
    int no = Convert.ToInt32(readChar[i]) - 10;   
    string r = Convert.ToChar(no).ToString();   
    output+=r;   
}
于 2012-11-08T20:31:39.763 に答える
1

シンプルにしたい場合は、6文字のメインキーを使用して、6文字の入力に追加します許可された入力文字に基づいてモジュロを実行します

=1のようなもの

b = 2

c = 3

次に、単に数字を追加するだけです + 13 mod 24 > ...

安全だとは言いませんが、あなたが要求したように簡単です次の文字がdeodedされているようないくつかの組み合わせを行うこともできます prev char as +xx

于 2012-11-08T19:58:28.423 に答える
0

これらは増分するデータベース ID だとおっしゃっていたので、正の整数について話していると思います。暗号化を制限することは、実際には良い考えではありません。暗号化を制限すればするほど、破られやすくなるからです。あなたの目標はよくわかりませんが、ID を「暗号化」してエンド ユーザーから隠したいと思うかもしれません。したがって、これらが 1 から 999 までの正の整数であるという私の仮定がある場合、私の提案は次のとおりです。1つは、単純な文字の置換です。キャラ数が10人に制限されているのでわかりやすいです。2、16 進数に変換します。多くの人をだますことはありませんが、平均的なエ​​ンドユーザーはそれを認識しないかもしれません. 3 番目に、数値を Base64 に変換します。これは、16 進数ほど簡単には認識されません。最後、常に一意の結果が得られる数値に適用できる、ある種の式を考え出してください。ただし、かなり難しいのでお勧めしません。

于 2012-11-08T20:33:27.863 に答える