1 //////////////////////////////////////////////////////////////////////////////
3 // (C) Copyright Ion Gaztanaga 2004-2012. 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/interprocess for documentation.
9 //////////////////////////////////////////////////////////////////////////////
11 #if defined(BOOST_INTERPROCESS_MAPPED_FILES)
13 #include <boost/interprocess/detail/config_begin.hpp>
14 #include <boost/interprocess/allocators/allocator.hpp>
15 #include <boost/interprocess/containers/vector.hpp>
16 #include <boost/interprocess/managed_mapped_file.hpp>
19 #include "get_process_id_name.hpp"
21 using namespace boost::interprocess
;
23 inline std::string
get_filename()
25 std::string
ret (ipcdetail::get_temporary_path());
27 ret
+= test::get_process_id_name();
33 const int FileSize
= 65536*10;
34 std::string
filename(get_filename());
35 const char *FileName
= filename
.c_str();
37 //STL compatible allocator object for memory-mapped file
38 typedef allocator
<int, managed_mapped_file::segment_manager
>
40 //A vector that uses that allocator
41 typedef boost::interprocess::vector
<int, allocator_int_t
> MyVect
;
44 //Remove the file it is already created
45 file_mapping::remove(FileName
);
49 //Named allocate capable shared memory allocator
50 managed_mapped_file
mfile(create_only
, FileName
, FileSize
);
53 //Let's allocate some memory
54 for(i
= 0; i
< max
; ++i
){
55 array
[i
] = mfile
.allocate(i
+1);
58 //Deallocate allocated memory
59 for(i
= 0; i
< max
; ++i
){
60 mfile
.deallocate(array
[i
]);
65 //Remove the file it is already created
66 file_mapping::remove(FileName
);
68 //Named allocate capable memory mapped file managed memory class
69 managed_mapped_file
mfile(create_only
, FileName
, FileSize
);
71 //Construct the STL-like allocator with the segment manager
72 const allocator_int_t
myallocator (mfile
.get_segment_manager());
75 MyVect
*mfile_vect
= mfile
.construct
<MyVect
> ("MyVector") (myallocator
);
77 //Test that vector can be found via name
78 if(mfile_vect
!= mfile
.find
<MyVect
>("MyVector").first
)
81 //Destroy and check it is not present
82 mfile
.destroy
<MyVect
> ("MyVector");
83 if(0 != mfile
.find
<MyVect
>("MyVector").first
)
86 //Construct a vector in the memory-mapped file
87 mfile_vect
= mfile
.construct
<MyVect
> ("MyVector") (myallocator
);
89 //Flush cached data from memory-mapped file to disk
93 //Map preexisting file again in memory
94 managed_mapped_file
mfile(open_only
, FileName
);
96 //Check vector is still there
97 MyVect
*mfile_vect
= mfile
.find
<MyVect
>("MyVector").first
;
104 //Map preexisting file again in copy-on-write
105 managed_mapped_file
mfile(open_copy_on_write
, FileName
);
107 //Check vector is still there
108 MyVect
*mfile_vect
= mfile
.find
<MyVect
>("MyVector").first
;
113 mfile
.destroy_ptr(mfile_vect
);
115 //Make sure vector is erased
116 mfile_vect
= mfile
.find
<MyVect
>("MyVector").first
;
120 //Now check vector is still in the file
122 //Map preexisting file again in copy-on-write
123 managed_mapped_file
mfile(open_copy_on_write
, FileName
);
125 //Check vector is still there
126 MyVect
*mfile_vect
= mfile
.find
<MyVect
>("MyVector").first
;
132 //Map preexisting file again in copy-on-write
133 managed_mapped_file
mfile(open_read_only
, FileName
);
135 //Check vector is still there
136 MyVect
*mfile_vect
= mfile
.find
<MyVect
>("MyVector").first
;
141 managed_mapped_file::size_type old_free_memory
;
143 //Map preexisting file again in memory
144 managed_mapped_file
mfile(open_only
, FileName
);
145 old_free_memory
= mfile
.get_free_memory();
149 managed_mapped_file::grow(FileName
, FileSize
);
151 //Map preexisting file again in memory
152 managed_mapped_file
mfile(open_only
, FileName
);
154 //Check vector is still there
155 MyVect
*mfile_vect
= mfile
.find
<MyVect
>("MyVector").first
;
159 if(mfile
.get_size() != (FileSize
*2))
161 if(mfile
.get_free_memory() <= old_free_memory
)
165 managed_mapped_file::size_type old_free_memory
, next_free_memory
,
166 old_file_size
, next_file_size
, final_file_size
;
168 //Map preexisting file again in memory
169 managed_mapped_file
mfile(open_only
, FileName
);
170 old_free_memory
= mfile
.get_free_memory();
171 old_file_size
= mfile
.get_size();
174 //Now shrink the file
175 managed_mapped_file::shrink_to_fit(FileName
);
178 //Map preexisting file again in memory
179 managed_mapped_file
mfile(open_only
, FileName
);
180 next_file_size
= mfile
.get_size();
182 //Check vector is still there
183 MyVect
*mfile_vect
= mfile
.find
<MyVect
>("MyVector").first
;
187 next_free_memory
= mfile
.get_free_memory();
188 if(next_free_memory
>= old_free_memory
)
190 if(old_file_size
<= next_file_size
)
194 //Now destroy the vector
196 //Map preexisting file again in memory
197 managed_mapped_file
mfile(open_only
, FileName
);
199 //Destroy and check it is not present
200 mfile
.destroy
<MyVect
>("MyVector");
201 if(0 != mfile
.find
<MyVect
>("MyVector").first
)
205 //Now shrink the file
206 managed_mapped_file::shrink_to_fit(FileName
);
208 //Map preexisting file again in memory
209 managed_mapped_file
mfile(open_only
, FileName
);
210 final_file_size
= mfile
.get_size();
211 if(next_file_size
<= final_file_size
)
215 //Now test move semantics
216 managed_mapped_file
original(open_only
, FileName
);
217 managed_mapped_file
move_ctor(boost::move(original
));
218 managed_mapped_file move_assign
;
219 move_assign
= boost::move(move_ctor
);
220 move_assign
.swap(original
);
224 file_mapping::remove(FileName
);
228 #include <boost/interprocess/detail/config_end.hpp>
230 #else //#if defined(BOOST_INTERPROCESS_MAPPED_FILES)
237 #endif//#if defined(BOOST_INTERPROCESS_MAPPED_FILES)