#include <stdio.h> // temporary
#include <stdlib.h>
+#ifndef NDEBUG
#include <string.h>
+#endif
#include "core.h"
#include "process.h"
#include "rassert.h"
struct pool_item victim_core_item, victim_swap_item;
#if 1
+// won't work when compiled with NDEBUG
static void check_invariants() {
int avail =
core_head.item.base -
swap_head.spare -
process_spare;
if (victim) {
- assert(victim_core_item.prev);
- assert(victim_swap_item.prev);
+ assert(victim_core_item.prev && victim_core_item.next);
+ assert(victim_swap_item.prev && victim_core_item.next);
}
else {
- assert(victim_core_item.prev == NULL);
- assert(victim_swap_item.prev == NULL);
+ assert(victim_core_item.prev == NULL && victim_core_item.next == NULL);
+ assert(victim_swap_item.prev == NULL && victim_swap_item.prev == NULL);
}
for (int i = 0; i < n_processes; ++i)
if (processes[i].size != -1) {
if (processes + i == victim) {
assert(processes[i].lru_item.prev == NULL);
- assert(processes[i].pool_item.prev == NULL);
+ assert(
+ processes[i].pool_item.prev == NULL &&
+ processes[i].pool_item.next == NULL
+ );
assert(
processes[i].size ==
victim_core_item.limit -
lru_head.next = &lru_head;
victim = NULL;
+#ifndef NDEBUG
memset(&victim_core_item, 0, sizeof(victim_core_item));
memset(&victim_swap_item, 0, sizeof(victim_swap_item));
+#endif
check_invariants();
}
printf("victimized %d\n", (int)(victim - processes));
// remove from core pool, using dedicated core item
pool_free(&core_head, &victim_core_item);
- victim_core_item.prev = NULL;
// move dedicated to per-process swap item
pool_move_item(&victim_swap_item, &victim->pool_item);
- victim_swap_item.prev = NULL;
no_victim:
// take next least recently used process as victim
// move per-process to dedicated core item
pool_move_item(&victim->pool_item, &victim_core_item);
- victim->pool_item.prev = NULL;
// add to swap pool, using dedicated swap item
rassert(pool_alloc_moveable(&swap_head, &victim_swap_item, 0));
}
else {
// no, need to swap some in
+#ifndef NDEBUG
memset(&process_core_item, 0, sizeof(process_core_item));
memset(&process_swap_item, 0, sizeof(process_swap_item));
+#endif
// see whether victim or fully in swap
if (process == victim) {
// victim, take over the dedicated pool items
victim = NULL;
-
pool_move_item(&victim_core_item, &process_core_item);
- victim_core_item.prev = NULL;
-
pool_move_item(&victim_swap_item, &process_swap_item);
- victim_swap_item.prev = NULL;
}
else {
// fully in swap, take over only the per-process swap item
pool_move_item(&process->pool_item, &process_swap_item);
- process->pool_item.prev = NULL;
-
rassert(pool_alloc_moveable(&core_head, &process_core_item, 0));
}
// move dedicated to per-process core item
pool_move_item(&process_core_item, &process->pool_item);
- //process_core_item.prev = NULL;
// remove from swap pool, using dedicated swap item
pool_free(&swap_head, &process_swap_item);
- //process_swap_item.prev = NULL;
}
// insert at head of LRU list
process->lru_item.next->prev = process->lru_item.prev;
pool_free(&core_head, &process->pool_item);
- process->pool_item.prev = NULL;
}
else if (process == victim) {
// victim, free the dedicated pool items
victim = NULL;
-
pool_free(&core_head, &victim_core_item);
- victim_core_item.prev = NULL;
-
pool_free(&swap_head, &victim_swap_item);
- victim_swap_item.prev = NULL;
}
else {
// fully in swap, remove from swap pool
pool_free(&swap_head, &process->pool_item);
- process->pool_item.prev = NULL;
}
// track total allocation