C程序中的内存泄漏,无法看到释放内存的位置

时间:2014-04-01 23:42:59

标签: c memory-management memory-leaks

我正在编写一个C程序来生成密钥并在加密函数中对它们进行测试。但是,由于我以前从未编写过C程序,而且我完全不习惯手动管理内存,所以我遇到了一个问题。我有内存泄漏,说实话,我不知道如何解决它。我知道我需要在某个时候释放内存,但是直到我通过所有密钥并且在完成所有操作之前我的内存耗尽。用不同语言编写程序不是一种选择,所以请不要这样做。泄漏的代码如下所示,任何帮助都将受到赞赏。

编辑:我知道我还没有调用免费功能来释放内存。我不知道我可以把它放在哪里,因为我需要记忆,直到我通过所有键。将它放在循环外部并不能解决问题,因为泄漏发生在循环内部

第二次编辑:发布完整的程序。我没有选择使用除了那些之外的数据结构(即bool数组),因为DES加密函数(我没写的)如何工作

#include <stdio.h>
#include <stdlib.h>
#include "des.h"

void dec2bin(bool *testaRR, bool *to_return, int convert);

int main(int argc, const char * argv[])
{

// insert code here...
bool testKey[56] = {
    0, 1, 0, 0, 0, 0, 0, 1,
    0, 1, 0, 0, 0, 0, 0, 1,
    0, 1, 0, 0, 0, 0, 0, 1,
    0, 1, 0, 0, 0, 0, 0, 1,
    0, 1, 0, 0, 0, 0, 0, 1,
    0, 1, 0, 0, 0, 0, 0, 1,
    0, 1, 0, 0, 0, 0, 0, 1
};
bool testKey2[56] = {//intuitive key reversed for testing
    1, 0, 0, 0, 0, 0, 1, 0,
     1, 0, 0, 0, 0, 0, 1, 0,
     1, 0, 0, 0, 0, 0, 1, 0,
     1, 0, 0, 0, 0, 0, 1, 0,
     1, 0, 0, 0, 0, 0, 1, 0,
     1, 0, 0, 0, 0, 0, 1, 0,
    1, 0, 0, 0, 0, 0, 1, 0
};
 bool output[64];

 bool input[64] = {//the reverse of below...  DES bits are numbered left to right, in order of least to most significant so we must enter the bit values in reverse.
     //forexample the binary vale of N is 01001110 but below is displayed as 01110010
 1, 0, 0, 0, 1, 1, 0, 0,//1
 0, 0, 0, 0, 1, 1, 0, 0,//0
 1, 1, 0, 0, 0, 0, 1, 0,//C
 1, 0, 1, 0, 0, 0, 1, 0,//E
 1, 1, 0, 0, 1, 0, 1, 0,//S
 0, 0, 1, 0, 1, 0, 1, 0,//T
 1, 0, 1, 0, 0, 0, 1, 0,//E
 0, 1, 1, 1, 0, 0, 1, 0 //N
 };
 int y = sizeof(input);
 printf("(Input MSG: ");
 for (int i = y-4; i >= 0; i-=4)
 printf("%X", input[i]+2*input[i+1]+4*input[i+2]+8*input[i+3]);//this is the conversion to    hex code
 printf(")\n");

/*
 use char[] to store the key as set of 
 */
/*bool input[64] = {//this is the given plaintext message in the intuitive order (opposite of what it is)   
    0, 1, 0, 0, 1, 1, 1, 0,//N
    0, 1, 0, 0, 0, 1, 0, 1,//E

    0, 1, 0, 1, 0, 1, 0, 0,//T
    0, 1, 0, 1, 0, 0, 1, 1,//S
    0, 1, 0, 0, 0, 1, 0, 1,//E
    0, 1, 0, 0, 0, 0, 1, 1,//C
    0, 0, 1, 1, 0, 0, 0, 0,//0
    0, 0, 1, 1, 0, 0, 0, 1 //1
};


int y = sizeof(input);
printf("(Input MSG: ");
for (int j = 0; j < y; j+=4)
    printf("%X", input[j+3]+2*input[j+2]+4*input[j+1]+8*input[j]);//this is the conversion to hex code
printf(")\n");*/
bool test [8];
bool returned[8];
char keyphrase [8];
keyphrase[7] = 0;

for(int start = 65; start<=90; start++)
{
     //dec2bin(test, returned, start);
 keyphrase[0] = start;
    for(int two = 65; two<=90; two++){
        keyphrase[1]=two;
        for(int three = 65; three<=90; three++){
            keyphrase[2]=three;
            for(int four = 65; four<=90; four++){
                keyphrase[3]=four;
                for(int five = 65;five<=90;five++){
                    keyphrase[4]=five;
                    for( int six = 65; six <=90; six++){
                        keyphrase[5]=six;
                        for(int seven = 65; seven <=90; seven++){
                            keyphrase[6]=seven;
                            printf("%s \n", keyphrase);
                        }

                            }}
                        }
                    }
                }
 //once i fix the memory leak I will be calling the EncryptDes Function here and checking the outputblk agains the given cipher text
}
free(keyphrase);

int k = sizeof(testKey);
printf("(Test Key: ");
for (int z = 0; z < k; z+=7)
    printf("%d", testKey[z+7]+2*testKey[z+6]+4*testKey[z+5]+8*testKey[z+4]+16*testKey[z+3]+32*testKey[z+2]+64*testKey[z+1]+ 128*testKey[z]);//this is the conversion to hex code
printf(")\n");

//loop on the key (starting at
EncryptDES(testKey, output, input, 0);
int x = sizeof(output);
printf("(Output MSG: ");
for (int i = 0; i < x; i+=4)
    printf("%X", output[i+3]+2*output[i+2]+4*output[i+1]+8*output[i]);//this is the conversion to hex code
printf(")\n");


return 0;
}
void dec2bin (bool *testaRR, bool *to_return, int convert)

{
 printf("%d : ", convert);
 printf("%c", convert);
 printf("\n ");

//bool testaRR [8];
for(int st = 0; st<8; st++){
    testaRR[st] = convert%2;
    to_return[7-st] = testaRR[st];
    //printf("%d :", 7-st);
   //printf(" %d spot ", st);
    convert = convert/2;
    //testaRR stores the arrays in one direction
    //to_return stores them in the other
    //Example:
    //65 = 01000001 testaRR least significant on the far right (m0st sig is in index 7)better for storage and keeping track of where the bits actually are in binary
    //65 = 10000010 to_return least significant on the far left (same as DES) (most significant bit is index 0) good for printing to screen
}

4 个答案:

答案 0 :(得分:3)

这里不需要动态内存管理。

开始
char keyphrase[8];
keyphrase[7]=0;

而不是你的malloc,你会很高兴。您的最高数组索引是7(终止NUL),因此您需要一个包含8个项目(0..7)的数组。

如果您真的想使用malloc,最后只需free()即可,但您需要malloc 8个字符并将keyphrase[7]设置为0才能停止NUL终止。

这是一个有效的测试版本:

#include <stdio.h>

/* compile with gcc -Wall -std=c99 keyphrase.c -o keyphrase */

int
main (int argc, char **argv)
{
  char keyphrase[8];
  keyphrase[7] = 0;
  for (int start = 65; start <= 90; start++)
    {
      //dec2bin(test, returned, start);
      keyphrase[0] = start;
      for (int two = 65; two <= 90; two++)
        {
          keyphrase[1] = two;
          for (int three = 65; three <= 90; three++)
            {
              keyphrase[2] = three;
              for (int four = 65; four <= 90; four++)
                {
                  keyphrase[3] = four;
                  for (int five = 65; five <= 90; five++)
                    {
                      keyphrase[4] = five;
                      for (int six = 65; six <= 90; six++)
                        {
                          keyphrase[5] = six;
                          for (int seven = 65; seven <= 90; seven++)
                            {
                              keyphrase[6] = seven;
                              printf ("%s \n", keyphrase);
                            }
                        }
                    }
                }
            }
        }
    }
}

答案 1 :(得分:2)

真正的问题是使用printf。你没有NULL终止keyphrase,所以每当你printf溢出时。

另外,为了避免内存泄漏,只需将char *keyphrase = (char *)malloc(7);替换为char keyphrase[8];

答案 2 :(得分:1)

您在第一行打电话给malloc,但我没有看到一个free来释放您分配的内容。完成所有循环后(即已完成分配数据的使用),您必须调用free(keyphrase);

答案 3 :(得分:1)

程序修改后的新答案。

你说你的程序正在使用所有内存',因为我正在观察可用内存从4个以上的GB下降到大约5 MB'

我猜测的答案不是循环而是这些行:

//loop on the key (starting at
EncryptDES(testKey, output, input, 0);
int x = sizeof(output);

我们无法看到 EncryptDES 的来源或声明,但您没有传递长度。如果0是长度,这可以解释它。

然而,下一行表明output意味着是一个64字节的数组(而不是2个字符串)。但是EncryptDES无法知道这一点。

我建议你在valgrind下运行整个事情来了解发生了什么。