C语言 如何解密简单的异或加密

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/20579363/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-02 10:30:42  来源:igfitidea点击:

How to decrypt simple XOR encryption

cencryptionxor

提问by user3101398

I found the following XOR encryption function on the internet:

我在网上找到了如下XOR加密函数:

void xor_encrypt(char *key, char *string)
{
    int i, string_length = strlen(string);
    for(i=0; i<string_length; i++)
    {
        string[i]=string[i]^key[i];
        printf("%i", string[i]);
    }
}

It works perfect, but I would like to decrypt the string also.

它工作完美,但我也想解密字符串。

For example:

例如:

void xor_decrypt(char *key, char *encrypted_string)
{
    //decrypt method goes here
}

So basically after I encrypt the string, I would use the same encryption key to decrypt the previously encrypted string.

所以基本上在我加密字符串之后,我会使用相同的加密密钥来解密之前加密的字符串。

I'm pretty new to programming and I would just like to know how to decrypt the previously encrypted string. Thanks, all help is appreciated.

我对编程很陌生,我只想知道如何解密以前加密的字符串。谢谢,感谢所有帮助。

回答by dmitrig01

One of the cool things about XOR encryption is that when you apply it twice, you get back the original string –?see http://en.wikipedia.org/wiki/XOR_cipher.

XOR 加密的一个很酷的事情是,当你应用它两次时,你会得到原始字符串——?参见http://en.wikipedia.org/wiki/XOR_cipher

In your function, xor_decrypt, you take string and key and return string ^ key. If, now, you xor that with the key again, you get (string ^ key) ^ key = string ^ (key ^ key) = string ^ identity = string (by properties of XOR operator: http://en.wikipedia.org/wiki/Exclusive_or#Properties)

在您的函数 xor_decrypt 中,您获取字符串和密钥并返回字符串 ^ 密钥。现在,如果您再次使用密钥进行异或,您将得到 (string ^ key) ^ key = string ^ (key ^ key) = string ^ identity = string(根据 XOR 运算符的属性:http://en.wikipedia。 org/wiki/Exclusive_or#Properties)

Thus, you can just run your function, xor_encrypt, a second time on the output of the first xor_encrypt.

因此,您可以在第一个 xor_encrypt 的输出上第二次运行您的函数 xor_encrypt。

回答by Floris

With XOR, decrypting is exactly the same operation as encrypting. Run the encrypted string through the xor_encryptmethod again same key) and you have the plain text back.

使用 XOR,解密与加密完全相同。xor_encrypt再次通过该方法运行加密的字符串相同的密钥),您将获得纯文本。

warning 1: null characters

警告 1:空字符

One thing to watch out for: if the character in the string matches the corresponding character in the key, your result will be '\0'. This will be interpreted by your current code as the "end of string" and would stop the decryption short. To circumvent this, you want to pass the length of the "actual" string as a parameter to your function.

需要注意的一件事是:如果字符串中的字符与键中的相应字符匹配,则结果将为'\0'. 这将被您当前的代码解释为“字符串结尾”,并会停止解密。为了避免这种情况,您希望将“实际”字符串的长度作为参数传递给您的函数。

warning 2: short keys

警告 2:快捷键

You also want to make sure you don't run past the end of your key - if the plain text is very long you might have to repeat the key. You can do this with the %operator - just recycle the key from the beginning.

您还需要确保不会越过密钥的末尾——如果纯文本很长,您可能需要重复密钥。您可以与%操作员一起执行此操作 - 只需从一开始就回收密钥。

Here is a complete example that shows these techniques:

这是一个完整的示例,展示了这些技术:

#include <stdio.h>
#include <string.h>

void xor_encrypt(char *key, char *string, int n)
{
    int i;
    int keyLength = strlen(key);
    for( i = 0 ; i < n ; i++ )
    {
        string[i]=string[i]^key[i%keyLength];
    }
}

int main(void) {
  char plain[] = "This is plain text";
  char key[] = "Abcdabcdabciabcdabcd";
  int n = strlen(plain);
  // encrypt:
  xor_encrypt(key, plain, n);
  printf("encrypted string: \n");
  for(int ii = 0; ii < n; ii++) {
    if(plain[ii] > 0x32 && plain[ii] < 0x7F ) printf("%c", plain[ii]);
   else printf(" 0x%02x ", plain[ii]);
  }
  printf("\n");
  // **** if you include this next line, things go wrong!
  n = strlen(plain);
  xor_encrypt(key, plain, n);
  printf("after round trip, plain string is '%s'\n", plain);
}

This (not realizing the problem with kay == string) results in truncated decryption (the iin plainmatches the same letter in key):

这(没有意识到 kay == string 的问题)会导致解密被截断(iinplain与in中的相同字母匹配key):

encrypted string: 
 0x15  0x0a  0x0a  0x17 A 0x0b  0x10 D 0x11  0x0e  0x02  0x00  0x0f B 0x17  0x01  0x19  0x16 
after round trip, plain string is 'This is pla'

Leaving out the line I marked above (i.e., keeping the value of nas the original length of the string), your result is

省略我在上面标记的行(即,将 的值保留n为字符串的原始长度),您的结果是

encrypted string: 
 0x15  0x0a  0x0a  0x17 A 0x0b  0x10 D 0x11  0x0e  0x02  0x00  0x0f B 0x17  0x01  0x19  0x16 
after round trip, plain string is 'This is plain text'

exactly as you would expect.

正如您所期望的那样。