163 std::pair<const Slab_*, Index_>
next(Ifunction_ identify, Ufunction_ upper_size, Afunction_ actual_size, Cfunction_ create, Pfunction_ populate) {
164 Index_ index = this->
next();
165 auto slab_info = identify(index);
166 if (slab_info.first == my_last_slab_id && my_last_slab_num.has_value()) {
167 return std::make_pair(my_all_slabs.data() + *my_last_slab_num, slab_info.second);
169 my_last_slab_id = slab_info.first;
172 if (my_counter - 1 == my_refresh_point) {
176 my_used_size = upper_size(slab_info.first);
177 requisition_new_slab(slab_info.first);
179 auto last_future_slab_id = slab_info.first;
180 while (++my_refresh_point < my_total) {
181 auto future_index = my_oracle->get(my_refresh_point);
182 auto future_slab_info = identify(future_index);
183 if (last_future_slab_id == future_slab_info.first) {
187 last_future_slab_id = future_slab_info.first;
188 if (my_future_cache.find(future_slab_info.first) != my_future_cache.end()) {
192 auto ccIt = my_current_cache.find(future_slab_info.first);
193 if (ccIt != my_current_cache.end()) {
194 auto slab_num = ccIt->second;
195 auto candidate = my_used_size + actual_size(future_slab_info.first, my_all_slabs[slab_num]);
196 if (candidate > my_max_size) {
199 my_used_size = candidate;
200 my_future_cache[future_slab_info.first] = slab_num;
201 my_to_reuse.emplace_back(future_slab_info.first, slab_num);
202 my_current_cache.erase(ccIt);
204 auto candidate = my_used_size + upper_size(future_slab_info.first);
205 if (candidate > my_max_size) {
208 my_used_size = candidate;
209 requisition_new_slab(future_slab_info.first);
213 auto cIt = my_current_cache.begin();
214 for (
auto a : my_in_need) {
215 if (cIt != my_current_cache.end()) {
216 auto slab_num = cIt->second;
217 my_to_populate.emplace_back(a, slab_num);
218 my_future_cache[a] = slab_num;
221 auto slab_num = my_all_slabs.size();
222 my_all_slabs.push_back(create());
223 my_to_populate.emplace_back(a, slab_num);
224 my_future_cache[a] = slab_num;
229 for (; cIt != my_current_cache.end(); ++cIt) {
230 my_free_pool.emplace_back(cIt->second);
233 populate(my_to_populate, my_to_reuse, my_all_slabs);
234 my_to_populate.clear();
237 my_current_cache.clear();
238 my_current_cache.swap(my_future_cache);
242 auto ccIt = my_current_cache.find(slab_info.first);
243 my_last_slab_num = ccIt->second;
244 return std::make_pair(my_all_slabs.data() + *my_last_slab_num, slab_info.second);