基本的に次のようなプログラムがあります。
typedef struct cpl_def
{
int A;
int B;
int OK;
struct cpls *link;
}cpls;
int main(void)
{
int n1, n2;
int num = 300; /* say */
int *a;
a = NULL;
int *apt;
int *b;
b = NULL;
int *bpt;
cpls *cplptr;
cplptr = NULL;
int i, j;
for (i=0; i < 2000; i++)
{
if (i == 0)
{
cplptr = (cpls *) malloc(num*sizeof(cpls) ); /* create the structure */
initalize(cplptr);
}
/*
...operations on cplptr ... */
FOO(cplptr);
/*
...determine I need a subset of size n1 (a positive integer of size n1 which changes during the loop) entries from cplptr ... */
n1 = FOO2(cplptr);
n2 = FOO3(cplptr);
/*
...figure out the values of A, B for additional n2 entries into cplptr ...
*/
cplptr2 = (cpls *) malloc(n2*sizeof(cpls) ); /* a second structure to store additional entries */
/* .... operations on cplptr2 ...*/
/* ...copy subset of n1 entries from cplptr into dynamically allocated arrays a,b of size n1... */
a = malloc(n1 * sizeof(int));
apt = &a[0];
b = malloc(n1 * sizeof(int));
bpt = &b[0];
for (j=0; j < num; j++)
{
if (cplptr[j].OK==1)
{
(*apt++) = cplptr[j].a;
(*bpt++) = cplptr[j].b;
}
}
free(cplptr); /* free the first structure */
cplptr = (cpls *) malloc((n1+n2)*sizeof(cpls) ); /* redeclare the first structure to reflect the proper sizes */
for (j = 0; j < n1; j++) /* transfer a subset of size n1 to the first structure */
{
cplptr[j].a = a[j];
cplptr[j].b = b[j];
cplptr[j].OK = 1;
}
for (j = n1; j < n1 + n2; j++) /* transfer things to the first structure */
{
cplptr[j].a = cplptr2[j].a;
cplptr[j].b = cplptr2[j].b;
cplptr[j].OK = cplptr2[j].OK;
}
free(a)
free(b)
free(cplptr2); /* free the second structure */
} /* End iteration i
} /* End main() */
これは単なる骨格ですが、うまくいけば十分な画像が得られます. A とにかく、通常は正常に動作しますが、n1、n2 の一部の値では、free(cplptr) がセグメンテーション違反を引き起こすようです。これは 1 回だけ呼び出され、cplptr への malloc() 呼び出しの後、cplptr の対応する free() の前にアドレスをチェックします。
....
cplptr = (cpls *) malloc(num*sizeof(cpls) );
printf("fine to this %p\n", &cplptr[0]);
...
printf("fine to this %p\n", &cplptr[0]);
free(cplptr) <- segmentation fault happens here.
アドレスが一致しているということは、free() が解放すべきものを解放しているということですよね?? gdb は、プログラムが受信したシグナル SIGSEGV、セグメンテーション違反を示します。0xb7ce179b in ?? () /lib/tls/i686/cmov/libc.so.6 およびステップから 現在の関数の境界が見つかりません
セグメンテーション違反を回避するようなものを実装する別の方法はありますか?
あなたの提案をありがとう!何が起こっているのか分かりますか??