+
+ lock_acquire (&pool->lock);
+ ASSERT (bitmap_all (pool->used_map, page_idx, page_idx + page_cnt));
+ bitmap_set_multiple (pool->used_map, page_idx, page_idx + page_cnt, false);
+ lock_release (&pool->lock);
+}
+
+/* Frees the page at PAGE. */
+void
+palloc_free_page (void *page)
+{
+ palloc_free_multiple (page, 1);
+}
+
+/* Initializes pool P as starting at START and ending at END,
+ naming it NAME for debugging purposes. */
+static void
+init_pool (struct pool *p, void *start, void *end, const char *name)
+{
+ size_t bitmap_size;
+ size_t page_cnt;
+
+ ASSERT (pg_ofs (start) == 0);
+ ASSERT (pg_ofs (end) == 0);
+ ASSERT (end > start);
+
+ page_cnt = pg_no (end) - pg_no (start);
+ printf ("%d kB allocated for %s.\n", (PGSIZE / 1024) * page_cnt, name);
+
+ lock_init (&p->lock, name);
+ bitmap_size = ROUND_UP (bitmap_needed_bytes (page_cnt), PGSIZE);
+ p->used_map = bitmap_create_preallocated (page_cnt, start, bitmap_size);
+ p->start = start + bitmap_size;
+ p->end = end;
+ ASSERT (p->end > p->start);
+}
+
+/* Returns true if PAGE was allocated from POOL,
+ false otherwise. */
+static bool
+page_from_pool (const struct pool *pool, void *page_)
+{
+ uint8_t *page = page_;
+
+ return page >= pool->start && page < pool->end;