summaryrefslogtreecommitdiff
path: root/tests/test_memory.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'tests/test_memory.cpp')
-rw-r--r--tests/test_memory.cpp58
1 files changed, 58 insertions, 0 deletions
diff --git a/tests/test_memory.cpp b/tests/test_memory.cpp
index a571353..85d6e86 100644
--- a/tests/test_memory.cpp
+++ b/tests/test_memory.cpp
@@ -4,6 +4,7 @@
#include "allocator.hpp"
#include <string>
+#include <vector>
namespace
{
@@ -137,6 +138,63 @@ TEST(memory_large_allocations)
set_memory_management_functions(old_allocate, old_deallocate);
}
+TEST(memory_page_management)
+{
+ page_allocs = page_deallocs = 0;
+
+ // remember old functions
+ allocation_function old_allocate = get_memory_allocation_function();
+ deallocation_function old_deallocate = get_memory_deallocation_function();
+
+ // replace functions
+ set_memory_management_functions(allocate, deallocate);
+
+ {
+ xml_document doc;
+
+ CHECK(page_allocs == 0 && page_deallocs == 0);
+
+ // initial fill
+ std::vector<xml_node> nodes;
+
+ for (size_t i = 0; i < 4000; ++i)
+ {
+ xml_node node = doc.append_child(STR("node"));
+ CHECK(node);
+
+ nodes.push_back(node);
+ }
+
+ CHECK(page_allocs > 0 && page_deallocs == 0);
+
+ // grow-prune loop
+ size_t offset = 0;
+ size_t prime = 15485863;
+
+ while (nodes.size() > 0)
+ {
+ offset = (offset + prime) % nodes.size();
+
+ doc.remove_child(nodes[offset]);
+
+ nodes[offset] = nodes.back();
+ nodes.pop_back();
+ }
+
+ CHECK(page_allocs == page_deallocs + 1); // only one live page left (it waits for new allocations)
+
+ char buffer;
+ CHECK(doc.load_buffer_inplace(&buffer, 0, parse_fragment, get_native_encoding()));
+
+ CHECK(page_allocs == page_deallocs); // no live pages left
+ }
+
+ CHECK(page_allocs == page_deallocs); // everything is freed
+
+ // restore old functions
+ set_memory_management_functions(old_allocate, old_deallocate);
+}
+
TEST(memory_string_allocate_increasing)
{
xml_document doc;