5

引用:

テスト if (allocbuf + ALLOCSIZE - allocp >= n) { は、n 文字の要求を満たすのに十分なスペースがあるかどうかを確認します。存在する場合、allocp の新しい値は、allocbuf の終わりを超えて最大 1 になります。

関連するコード:

#define ALLOCSIZE 10000 /* size of available space */
static char allocbuf[ALLOCSIZE]; /* storage for alloc */
static char *allocp = allocbuf; /* next free position */

char *alloc(int n)
/* return pointer to n characters */
{
    if (allocbuf + ALLOCSIZE - allocp >= n) { /* it fits */
        allocp += n;
        return allocp - n; /* old p */
    } else
/* not enough room */
        return 0;
}
void afree(char *p) /* free storage pointed to by p */
{
    if (p >= allocbuf && p < allocbuf + ALLOCSIZE)
        allocp = p;
}

では、どうすれば allocbuf の最後の位置を超えることができるのでしょうか? 私の意見では allocbuf[9999]

それを超えるもの。allocbuf[10000] は正しくなく、メモリ リークですよね?


質問の 2 番目の部分 - その名前によると、afree 関数は配列内の特定の場所に保存された値を削除していると思います。しかし、私が見ることができるように、「記録ヘッド」を配列の左側に数か所移動するだけですか?そこに保存されたデータはそのまま残ります。

4

2 に答える 2

5

allocpは常に最後の空きメモリ位置を指す必要がありますが、空きメモリ位置がない場合は、 の末尾を 1 つ超えた位置になりますallocbuf

バッファに 1 つのメモリ セルしか残っていない状況を考えてみましょう:は、最後の空きメモリ セルであるため、allocpを指します。allocbuffer[9999]関数alloc(1)にテストを呼び出すと

allocbuf + ALLOCSIZE - allocp >= n

割り当てようとしていて、charちょうど1つしか残っていないため、trueを返す必要がありますchar。次に、最後のメモリ位置が割り当てられます。今allocbuf - allocp == ALLOCSIZEと は の終わりを超えた 1 つですallocbuf。ただし、その場合、上記のテストは常に false を返すため、 の範囲を超えてメモリにアクセスすることはありませんallocbuf


に関するご質問についてafree: によって返されるメモリの初期値mallocは未定義です。これは、それについて何の仮定もすることができず、使用する前に上書きしなければならないことを意味します。したがってafree、想定に反してデータを削除する必要はありません。もう使用されておらず、将来の割り当てに使用できるようにマークするだけでもまったく問題ありません。

malloc補足として、 namedに非常によく似た関数があります。この関数はcalloc、要求されたメモリ ブロックを割り当てた後、すべてをゼロに初期化します。

于 2012-08-14T15:03:00.487 に答える
2

質問の 2 番目の部分について:afree()またはCライブラリのようなメモリ管理関数は、通常、メモリをゼロにしたりクリアしたりfree()しません。彼らはそれを再利用できるようにするだけです。パフォーマンス コストがかからないので、これは良いことです。残念ながら、所有していないメモリを使用するなどのバグを隠すことができます。

free()一部のヒープ マネージャーは、セキュリティ上の理由やデバッグを支援するために呼び出すときに、メモリをゼロにしたり、特別な値で埋めたりする場合があります。これは標準では必須ではないため、この動作を具体的に有効にする必要があります。

于 2012-08-14T15:32:20.010 に答える