diff options
| author | Gareth Rees | 2013-05-27 12:58:05 +0100 |
|---|---|---|
| committer | Gareth Rees | 2013-05-27 12:58:05 +0100 |
| commit | 3aa19f30a4837dad85c76bfb8f3ca12b1b77e179 (patch) | |
| tree | 7ffafe50c42bf9633053d6c38507497d76c2f2ec /mps/code | |
| parent | 4bd6bde6049ab0c90b95b91f465a889facc57e73 (diff) | |
| download | emacs-3aa19f30a4837dad85c76bfb8f3ca12b1b77e179.tar.gz emacs-3aa19f30a4837dad85c76bfb8f3ca12b1b77e179.zip | |
Assert instead of crashing in mps_arena_destroy when the client has failed to destroy some data structures.
Also, don't forget to finish the chainRing.
Copied from Perforce
Change: 182258
ServerID: perforce.ravenbrook.com
Diffstat (limited to 'mps/code')
| -rw-r--r-- | mps/code/global.c | 22 |
1 files changed, 21 insertions, 1 deletions
diff --git a/mps/code/global.c b/mps/code/global.c index a1204332d9c..1ba7db30d86 100644 --- a/mps/code/global.c +++ b/mps/code/global.c | |||
| @@ -381,8 +381,27 @@ void GlobalsFinish(Globals arenaGlobals) | |||
| 381 | Arena arena; | 381 | Arena arena; |
| 382 | Rank rank; | 382 | Rank rank; |
| 383 | 383 | ||
| 384 | AVERT(Globals, arenaGlobals); | 384 | /* The client may have failed to destroy all data structures |
| 385 | * associated with the arena. If this happens we must assert (and | ||
| 386 | * not crash). But at this point in the code the control pool has | ||
| 387 | * been destroyed and so the address space containing these rings | ||
| 388 | * has potentially been unmapped. GlobalsCheck calls RingCheck, | ||
| 389 | * which (if the ring is not single) will dereference a pointer into | ||
| 390 | * the space formerly occupied by the control pool and so crash. | ||
| 391 | * Hence we must check that these rings are single *before* calling | ||
| 392 | * GlobalsCheck via the AVERT. See job000652. | ||
| 393 | */ | ||
| 385 | arena = GlobalsArena(arenaGlobals); | 394 | arena = GlobalsArena(arenaGlobals); |
| 395 | AVER(RingIsSingle(&arena->formatRing)); | ||
| 396 | AVER(RingIsSingle(&arena->chainRing)); | ||
| 397 | AVER(RingIsSingle(&arena->messageRing)); | ||
| 398 | AVER(RingIsSingle(&arena->threadRing)); | ||
| 399 | for(rank = 0; rank < RankLIMIT; ++rank) | ||
| 400 | AVER(RingIsSingle(&arena->greyRing[rank])); | ||
| 401 | AVER(RingIsSingle(&arenaGlobals->poolRing)); | ||
| 402 | AVER(RingIsSingle(&arenaGlobals->rootRing)); | ||
| 403 | |||
| 404 | AVERT(Globals, arenaGlobals); | ||
| 386 | 405 | ||
| 387 | STATISTIC_STAT(EVENT2(ArenaWriteFaults, arena, | 406 | STATISTIC_STAT(EVENT2(ArenaWriteFaults, arena, |
| 388 | arena->writeBarrierHitCount)); | 407 | arena->writeBarrierHitCount)); |
| @@ -390,6 +409,7 @@ void GlobalsFinish(Globals arenaGlobals) | |||
| 390 | arenaGlobals->sig = SigInvalid; | 409 | arenaGlobals->sig = SigInvalid; |
| 391 | 410 | ||
| 392 | RingFinish(&arena->formatRing); | 411 | RingFinish(&arena->formatRing); |
| 412 | RingFinish(&arena->chainRing); | ||
| 393 | RingFinish(&arena->messageRing); | 413 | RingFinish(&arena->messageRing); |
| 394 | RingFinish(&arena->threadRing); | 414 | RingFinish(&arena->threadRing); |
| 395 | for(rank = 0; rank < RankLIMIT; ++rank) | 415 | for(rank = 0; rank < RankLIMIT; ++rank) |