1 //////////////////////////////////////////////////////////////////////////////
3 // (C) Copyright Ion Gaztanaga 2007-2013. Distributed under the Boost
4 // Software License, Version 1.0. (See accompanying file
5 // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
7 // See http://www.boost.org/libs/container for documentation.
9 //////////////////////////////////////////////////////////////////////////////
12 #pragma warning (disable : 4512)
15 #include <boost/container/detail/dlmalloc.hpp>
16 #include <boost/core/no_exceptions_support.hpp>
17 #include <boost/container/throw_exception.hpp>
19 #define BOOST_INTERPROCESS_VECTOR_ALLOC_STATS
21 #include <iostream> //std::cout, std::endl
22 #include <typeinfo> //typeid
23 #include <cassert> //assert
25 #include <boost/move/detail/nsec_clock.hpp>
26 using boost::move_detail::cpu_timer
;
27 using boost::move_detail::cpu_times
;
28 using boost::move_detail::nanosecond_type
;
30 using namespace boost::container
;
33 void allocation_timing_test(std::size_t num_iterations
, std::size_t num_elements
)
36 std::size_t numalloc
= 0, numexpand
= 0;
39 << " ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ \n"
40 << " Iterations/Elements: " << num_iterations
<< "/" << num_elements
<< '\n'
41 << " ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ \n"
45 allocation_type malloc_types
[] = { BOOST_CONTAINER_EXPAND_BWD
, BOOST_CONTAINER_EXPAND_FWD
, BOOST_CONTAINER_ALLOCATE_NEW
};
46 const char * malloc_names
[] = { "Backwards expansion", "Forward expansion", "New allocation" };
47 for(size_t i
= 0; i
< sizeof(malloc_types
)/sizeof(allocation_type
); ++i
){
48 numalloc
= 0; numexpand
= 0;
49 const allocation_type m_mode
= malloc_types
[i
];
50 const char *malloc_name
= malloc_names
[i
];
55 for(std::size_t r
= 0; r
!= num_iterations
; ++r
){
57 if(m_mode
!= BOOST_CONTAINER_EXPAND_FWD
)
58 first_mem
= dlmalloc_malloc(sizeof(POD
)*num_elements
*3/2);
59 void *addr
= dlmalloc_malloc(1*sizeof(POD
));
60 if(m_mode
== BOOST_CONTAINER_EXPAND_FWD
)
61 first_mem
= dlmalloc_malloc(sizeof(POD
)*num_elements
*3/2);
62 capacity
= dlmalloc_size(addr
)/sizeof(POD
);
63 dlmalloc_free(first_mem
);
67 dlmalloc_command_ret_t ret
;
68 for(size_t e
= capacity
+ 1; e
< num_elements
; ++e
){
70 size_t min
= (capacity
+1)*sizeof(POD
);
71 size_t max
= (capacity
*3/2)*sizeof(POD
);
74 ret
= dlmalloc_allocation_command
76 , min
, max
, &received_size
, addr
);
78 throw_runtime_error("!ret.first)");
81 assert(m_mode
== BOOST_CONTAINER_ALLOCATE_NEW
);
82 if(m_mode
!= BOOST_CONTAINER_ALLOCATE_NEW
){
83 std::cout
<< "m_mode != BOOST_CONTAINER_ALLOCATE_NEW!" << std::endl
;
91 assert(m_mode
!= BOOST_CONTAINER_ALLOCATE_NEW
);
92 if(m_mode
== BOOST_CONTAINER_ALLOCATE_NEW
){
93 std::cout
<< "m_mode == BOOST_CONTAINER_ALLOCATE_NEW!" << std::endl
;
98 capacity
= received_size
/sizeof(POD
);
111 assert( dlmalloc_allocated_memory() == 0);
112 if(dlmalloc_allocated_memory()!= 0){
113 std::cout
<< "Memory leak!" << std::endl
;
118 nanosecond_type nseconds
= timer
.elapsed().wall
;
120 std::cout
<< " Malloc type: " << malloc_name
122 << " allocation ns: "
123 << float(nseconds
)/float(num_iterations
*num_elements
)
125 << " capacity - alloc calls (new/expand): "
126 << (std::size_t)capacity
<< " - "
127 << (float(numalloc
) + float(numexpand
))/float(num_iterations
)
128 << "(" << float(numalloc
)/float(num_iterations
) << "/" << float(numexpand
)/float(num_iterations
) << ")"
129 << std::endl
<< std::endl
;
141 int allocation_loop()
143 std::cout
<< std::endl
144 << "-------------------------------------------\n"
145 << "-------------------------------------------\n"
146 << " Type(sizeof): " << typeid(POD
).name() << " (" << sizeof(POD
) << ")\n"
147 << "-------------------------------------------\n"
148 << "-------------------------------------------\n"
151 //#define SINGLE_TEST
155 std::size_t numrep
[] = { 50000 };
157 std::size_t numrep
[] = { 5000 };
159 std::size_t numele
[] = { 100 };
160 #elif defined(SIMPLE_IT)
161 std::size_t numrep
[] = { 3 };
162 std::size_t numele
[] = { 100 };
165 std::size_t numrep
[] = { /*10000, */10000, 100000, 1000000 };
167 std::size_t numrep
[] = { /*10000, */1000, 10000, 100000 };
169 std::size_t numele
[] = { /*10000, */1000, 100, 10 };
172 for(std::size_t i
= 0; i
< sizeof(numele
)/sizeof(numele
[0]); ++i
){
173 allocation_timing_test
<POD
>(numrep
[i
], numele
[i
]);
181 dlmalloc_mallopt( (-3)//M_MMAP_THRESHOLD
183 //allocation_loop<char_holder<4> >();
184 //allocation_loop<char_holder<6> >();
185 allocation_loop
<char_holder
<8> >();
186 allocation_loop
<char_holder
<12> >();
187 //allocation_loop<char_holder<14> >();
188 allocation_loop
<char_holder
<24> >();