Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/sorting/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
为什么我在C malloc的末尾得到一个垃圾值?_C_Encryption_Undefined Behavior_Garbage - Fatal编程技术网

为什么我在C malloc的末尾得到一个垃圾值?

为什么我在C malloc的末尾得到一个垃圾值?,c,encryption,undefined-behavior,garbage,C,Encryption,Undefined Behavior,Garbage,我正在编写加密和解密函数,其工作原理如下: encrypt("string") -> "encryptedString" decrypt("encryptedString") -> "string" 然而,当我运行它们时,我得到了奇怪的结果 在我的示例中,我对abz、A1BZ进行加密以获得:bca、Z1AY和vise versa解密 当我运行代码时,我得到以下输出: Question 3a (encrypt): bc#a,Z1AY Question 3b (decrypt): ab

我正在编写加密和解密函数,其工作原理如下:

encrypt("string") -> "encryptedString"
decrypt("encryptedString") -> "string"
然而,当我运行它们时,我得到了奇怪的结果

在我的示例中,我对abz、A1BZ进行加密以获得:bca、Z1AY和vise versa解密

当我运行代码时,我得到以下输出:

Question 3a (encrypt): bc#a,Z1AY
Question 3b (decrypt): ab#z,A1BZcuments�v�j�
我想强调的是,该函数似乎正确地完成了它的工作。注意,abz,A1BZ是解密输出的一部分。那部分是正确的。然而,它后面紧跟着的是cuments�v�J�

解密BCA,Z1AY应仅导致abz,A1BZ

以下是功能:

其中,C中的大小定义为8个字符串。函数(如printf或strlen)希望字符串末尾有一个空字节,即值为零的字节

当您选择时,操作系统会为您分配它。当调用malloc而不是calloc时,您无法保证在收到内存时内存的内容是什么。这就是代码具有未定义行为的原因-当系统返回的内存恰好有0作为最后一个字节时,代码将正常运行。如果还有其他内容,printf将继续写入输出

您应该考虑此行为,并将字符串的最后一个字节显式设置为0:

int-ciphertext_len=strlenciphertext; //为明文输出分配密文长度+1字节 对于int i=0;i 包括 //以字节为单位存储要分配的内存块的大小 int mem_block_size=strlenciphertext+1*sizeofchar; //分配内存 字符*明文=mallocmem\u块大小; //将内存设置为零 memsetplaintext,0,mem_块大小;
您在哪里终止了您创建的字符串?您在malloc中包含了字节,但忘记写入它,或者假设它是0。您可以使用可以编译的代码吗?非常抱歉,使用memset不起作用。从decrypt返回的指针仍然指向一个最后带有垃圾值的块。我承认犯了一个错误。正如我之前所写的,memset是一种将字符数组归零的通用方法。它不适用于您的场景,因为您有一个指向char*纯文本的指针。调用sizeofplaintext返回指针的大小-可以是4或8字节。在您的情况下,您需要单独存储大小,以便稍后将内存归零。我已经更新了我的答案。
char* encrypt(const char* plaintext){
    char* ciphertext = malloc((strlen(plaintext) + 1) * sizeof(char));
    for (int i = 0; i < strlen(plaintext); i++){
        if (islower(plaintext[i])){
            char c;
            if (plaintext[i] == 'z'){
                c = 'a';
            }
            else {
                c = plaintext[i] + 1;
            }
            ciphertext[i] = c;
        }
        else if (isupper(plaintext[i])){
            char c;
            if (plaintext[i] == 'A'){
            c = 'Z';
            }
            else {
            c = plaintext[i] - 1;
            }
            ciphertext[i] = c;
        }
        else {
            ciphertext[i] = plaintext[i];
        }
    }
    return ciphertext;
}

char* decrypt(const char* ciphertext){
    char* plaintext = malloc((strlen(ciphertext) + 1) * sizeof(char));
    for (int i = 0; i < strlen(ciphertext); i++){
        if (islower(ciphertext[i])){
            char c;
            if (ciphertext[i] == 'a'){
                c = 'z';
            }
            else {
                c = ciphertext[i] - 1;
            }
            plaintext[i] = c;
        }
        else if (isupper(ciphertext[i])){
            char c;
            if (ciphertext[i] == 'Z'){
                 c = 'A';
            }
            else {
                c = ciphertext[i] + 1;
            }
            plaintext[i] = c;
        }
        else {
            plaintext[i] = ciphertext[i];
            }
        }
        return plaintext;
    }
char* ciphertext = encrypt("ab#z,A1BZ");
char* plaintext = decrypt(ciphertext);
printf("Question 3a (encrypt): %s\n", ciphertext);
printf("Question 3b (decrypt): %s\n", plaintext);
free(ciphertext);
free(plaintext);