私はパス(環境変数)のリストを取り、パスを分割して印刷するプログラムを書いています。それをコンパイルすると、私はsegfaultを取得します。以下は、GDBの私の出力です:valgrindのオンSegfault in Cプログラム、mallocコール
Program received signal SIGSEGV, Segmentation fault.
0x0000000000400eb0 in dest (name=0x7fffffffbce0 "PATH") at executables.c:100
100 dest[i] = malloc(srclen+1);
:
char** dest(char *name){
int i=0;
char *vp;
const char s[2]=":";
char *token;
char **dest;
name[strlen(name)-1]='\0';
vp=getenv(name);
if(vp == NULL){
exit(1);
}
token =strtok(vp,s);
while(token != NULL){
size_t srclen = strlen(token);
dest[i] = malloc(srclen+1);
strcpy(dest[i], token);
token = strtok(NULL, s);
i++;
}
dest[i]=NULL;
return dest;
}
そして、これは私のメインです:
==21574== 1 errors in context 2 of 3:
==21574== Use of uninitialised value of size 8
==21574== at 0x400EB0: dest (executables.c:100)
==21574== by 0x400B5B: main (main.c:9)
は、これは私の関数である
#include "executables.h"
int main(int argc, char **argv){
char *path;
char name[BUFSIZ];
printf("enter name of environment variable:\n");
fgets(name,BUFSIZ,stdin);
char **p=dest(name);
int j=0;
while(p[j]!=NULL){
printf("%s\n",p[j]);
j++;
}
return(0);
}
0x400EB0での初期化されていない値[...]の使用:dest' – tkausl
私は自分の答えを修正しなければならなかったので、関数はスタックに割り当てられた静的にスタックに割り当てられませんでした変数は未定義/ガーベジであり、コンパイラが望むものはすぐに再利用されます。そこでポインタの配列malloc()に変更し、メインにもそのレベルの空きを追加しました。 – clearlight
もう1つのこと - malloc、zalloc、calloc、strdupなどでメモリを割り当てる関数では、呼び出し元までコメントブロックを置いて、割り当てられたメモリを解放して、誤用やメモリリークのリスク。一般的な問題は、プログラムや別の解決策の別の機能ですぐに使用できるように変更を加えて、その事実を逃してリークを導入するために人々が後で戻ってくることです。それは良い予防措置です。 – clearlight