リスト内のハンドルで free を使用する方法 -> C -> Windows API
-
12-10-2019 - |
質問
C で次のようなリストがあります。
typedef struct _node
{
int number;
DWORD threadID;
HANDLE threadH;
struct *_node next;
} *node;
そして、次のようなものがあります:
node new_node = malloc(sizeof(node));
ご想像のとおり、このリストには、ハンドラーや ID などのスレッドの情報が保存されます。それでもこれをやろうとすると問題が発生します:
free(new_node);
これを実行しようとするたびに、予期しないエラーが発生し、VS はデータの破損があったことを示します。可能な限り固定しましたが、ハンドルを解放して使用しようとすると問題が発生することがわかりました。MSDNでこれを行う方法を検索しましたが、見つけられるのはスレッドを閉じる関数だけです(スレッドを実行してリストからレコードを削除するだけなので、これはここでは意図されていません)。
質問は:メモリからハンドルを解放するにはどうすればよいでしょうか?(これはハンドルの値の単なるコピーであることを考慮すると、アクティブなハンドルは削除されません)。
編集:これはリストからノードを挿入する関数です。
int insereVisitanteLista(node* lista, DWORD threadID, HANDLE threadH, int num_visitante)
{
node visitanteAnterior;
node novoVisitante = (node)malloc(sizeof(node));
if(novoVisitante == NULL)
return 0;
novoVisitante->threadID = threadID;
novoVisitante->threadH = threadH;
novoVisitante->number = num_visitante;
novoVisitante->next = NULL;
if(*lista == NULL)
{
*lista = novoVisitante;
return 1;
}
visitanteAnterior = *lista;
while(visitanteAnterior->next != NULL)
visitanteAnterior = visitanteAnterior->next;
visitanteAnterior->next =novoVisitante;
return 1;
}
これはノードを削除する関数です。
int removeVisitanteLista(node * lista, DWORD threadID)
{
node visitanteAnterior = NULL, visitanteActual;
if(*lista == NULL)
return 0;
visitanteActual = *lista;
if((*lista)->threadID == threadID)
{
*lista = visitanteActual->next;
visitanteActual->next = NULL;
free(visitanteActual);
return 1;
}
while(visitanteActual != NULL && visitanteActual->threadID != threadID)
{
visitanteAnterior = visitanteActual;
visitanteActual = visitanteActual->next;
}
if (visitanteActual == NULL)
return 0;
visitanteAnterior->next = visitanteActual->next;
free(visitanteActual);
return 1;
}
解決
正確には何ですか node
あなたは解放しようとしているのですか?これは構造体へのポインタですか _node
?「はい」の場合、以前に割り当てましたか?いいえの場合、 free
は必要ありません。そうでない場合は、ノードがそうでないかどうかを確認する必要があります。 NULL
そうでないことを確認してください free
それを何度も。問題を再現する最小限の動作例がなければ、何をしているのか、どこにエラーがあるのかを推測するのは困難です。私が提案できる唯一のことは、C のメモリ管理について読むことです。 このリソース 役立つかもしれません。
アップデート:
コード内のnodeは_nodeへのポインタです。つまり、sizeof (node) はポインターのサイズであり、4 バイトまたは 8 バイトになります (アーキテクチャに応じて異なります)。たとえば、8 バイトを割り当てますが、それよりもはるかに大きな構造体へのポインタがあると仮定します。その結果、メモリが破損し、プログラムの動作が不定になります。したがって、ノード novoVisitante = (node)malloc(sizeof(node)) をノード novoVisitante = (node)malloc(sizeof(_node)) に変更すると、問題が解決されるはずです。
他のヒント
free()への呼び出しのコンテキストを表示していないので、少し推測する必要がありますが、私の最初の懸念は、リストを削除する前にノードを削除することについて言及しなかったことです。
以前の(またはヘッド)ノードの次のフィールドを変更して、ノードを解除することから始めます。それでもエラーが発生した場合、割り当てられたメモリ構造の1つまたは同様のものの終わりを過ぎて書くことで、どういうわけかメモリを破損しています。
また、ノードはポインターだと思います。あなたは本当にあなたがしていることについて多くの情報を提供していません。