17 #ifndef __TBB_enumerable_thread_specific_H 18 #define __TBB_enumerable_thread_specific_H 37 #define __TBB_ETS_USE_CPP11 \ 38 (__TBB_CPP11_RVALUE_REF_PRESENT && __TBB_CPP11_VARIADIC_TEMPLATES_PRESENT \ 39 && __TBB_CPP11_DECLTYPE_PRESENT && __TBB_CPP11_LAMBDAS_PRESENT) 46 namespace interface6 {
49 template <
typename T,
typename Allocator, ets_key_usage_type ETS_key_type>
57 template<ets_key_usage_type ETS_key_type>
61 #if __TBB_PROTECTED_NESTED_CLASS_BROKEN 69 slot& at(
size_t k ) {
70 return ((slot*)(
void*)(
this+1))[k];
72 size_t size()
const {
return size_t(1)<<lg_size;}
73 size_t mask()
const {
return size()-1;}
74 size_t start(
size_t h )
const {
75 return h>>(8*
sizeof(size_t)-lg_size);
81 bool empty()
const {
return key == key_type();}
82 bool match( key_type k )
const {
return key == k;}
83 bool claim( key_type k ) {
85 return atomic_compare_and_swap(
key, k, key_type()) == key_type();
88 #if __TBB_PROTECTED_NESTED_CLASS_BROKEN 95 atomic<array*> my_root;
96 atomic<size_t> my_count;
97 virtual void* create_local() = 0;
98 virtual void* create_array(
size_t _size) = 0;
99 virtual void free_array(
void* ptr,
size_t _size) = 0;
100 array* allocate(
size_t lg_size ) {
101 size_t n = size_t(1)<<lg_size;
102 array* a = static_cast<array*>(create_array(
sizeof(array)+n*
sizeof(slot) ));
103 a->lg_size = lg_size;
104 std::memset( a+1, 0, n*
sizeof(slot) );
107 void free(array* a) {
108 size_t n = size_t(1)<<(a->lg_size);
109 free_array( (
void *)a,
size_t(
sizeof(array)+n*
sizeof(slot)) );
112 ets_base() {my_root=NULL; my_count=0;}
114 void* table_lookup(
bool& exists );
118 void table_elementwise_copy(
const ets_base& other,
119 void*(*add_element)(ets_base&,
void*) ) {
122 if( !other.my_root )
return;
123 array* root = my_root = allocate(other.my_root->lg_size);
125 my_count = other.my_count;
126 size_t mask = root->mask();
127 for( array* r=other.my_root; r; r=r->next ) {
128 for(
size_t i=0; i<r->size(); ++i ) {
132 slot& s2 = root->at(j);
134 s2.ptr = add_element(*
this, s1.ptr);
138 else if( s2.match(s1.key) )
145 void table_swap( ets_base& other ) {
146 __TBB_ASSERT(
this!=&other,
"Don't swap an instance with itself");
147 tbb::internal::swap<relaxed>(my_root, other.my_root);
148 tbb::internal::swap<relaxed>(my_count, other.my_count);
152 template<ets_key_usage_type ETS_key_type>
153 ets_base<ETS_key_type>::~ets_base() {
157 template<ets_key_usage_type ETS_key_type>
158 void ets_base<ETS_key_type>::table_clear() {
159 while( array* r = my_root ) {
166 template<ets_key_usage_type ETS_key_type>
167 void* ets_base<ETS_key_type>::table_lookup(
bool& exists ) {
173 for( array* r=my_root; r; r=r->next ) {
175 size_t mask=r->mask();
176 for(
size_t i = r->start(
h); ;i=(i+1)&
mask) {
178 if(
s.empty() )
break;
197 found = create_local();
199 size_t c = ++my_count;
202 if( !r || c>r->size()/2 ) {
203 size_t s = r ? r->lg_size : 2;
204 while( c>
size_t(1)<<(
s-1) ) ++
s;
205 array* a = allocate(
s);
209 array* new_r = my_root.compare_and_swap(a,r);
210 if( new_r==r )
break;
212 if( new_r->lg_size>=
s ) {
227 size_t mask = ir->mask();
228 for(
size_t i = ir->start(
h);;i=(i+1)&
mask) {
242 typedef ets_base<ets_no_key> super;
244 #if __TBB_WIN8UI_SUPPORT 245 typedef DWORD tls_key_t;
246 void create_key() { my_key = FlsAlloc(NULL); }
247 void destroy_key() { FlsFree(my_key); }
248 void set_tls(
void *
value) { FlsSetValue(my_key, (LPVOID)
value); }
249 void* get_tls() {
return (
void *)FlsGetValue(my_key); }
251 typedef DWORD tls_key_t;
252 void create_key() { my_key = TlsAlloc(); }
253 void destroy_key() { TlsFree(my_key); }
254 void set_tls(
void *
value) { TlsSetValue(my_key, (LPVOID)
value); }
255 void* get_tls() {
return (
void *)TlsGetValue(my_key); }
258 typedef pthread_key_t tls_key_t;
259 void create_key() { pthread_key_create(&my_key, NULL); }
260 void destroy_key() { pthread_key_delete(my_key); }
261 void set_tls(
void *
value )
const { pthread_setspecific(my_key,
value); }
262 void* get_tls()
const {
return pthread_getspecific(my_key); }
267 virtual
void free_array(
void* ptr,
size_t _size)
__TBB_override = 0;
269 ets_base() {create_key();}
270 ~ets_base() {destroy_key();}
271 void* table_lookup(
bool& exists ) {
272 void* found = get_tls();
276 found = super::table_lookup(exists);
284 super::table_clear();
286 void table_swap( ets_base& other ) {
288 __TBB_ASSERT(
this!=&other,
"Don't swap an instance with itself");
289 swap(my_key, other.my_key);
290 super::table_swap(other);
295 template<
typename Container,
typename Value >
296 class enumerable_thread_specific_iterator
297 #if defined(_WIN64) && defined(_MSC_VER)
299 : public std::iterator<std::random_access_iterator_tag,Value>
304 Container *my_container;
305 typename Container::size_type my_index;
306 mutable Value *my_value;
308 template<
typename C,
typename T>
309 friend enumerable_thread_specific_iterator<C,T>
310 operator+( ptrdiff_t offset,
const enumerable_thread_specific_iterator<C,T>& v );
312 template<
typename C,
typename T,
typename U>
313 friend bool operator==(
const enumerable_thread_specific_iterator<C,T>& i,
314 const enumerable_thread_specific_iterator<C,U>& j );
316 template<
typename C,
typename T,
typename U>
317 friend bool operator<(
const enumerable_thread_specific_iterator<C,T>& i,
318 const enumerable_thread_specific_iterator<C,U>& j );
320 template<
typename C,
typename T,
typename U>
321 friend ptrdiff_t
operator-(
const enumerable_thread_specific_iterator<C,T>& i,
322 const enumerable_thread_specific_iterator<C,U>& j );
324 template<
typename C,
typename U>
325 friend class enumerable_thread_specific_iterator;
329 enumerable_thread_specific_iterator(
const Container &container,
typename Container::size_type index ) :
330 my_container(&const_cast<Container &>(container)), my_index(index), my_value(NULL) {}
333 enumerable_thread_specific_iterator() : my_container(NULL), my_index(0), my_value(NULL) {}
336 enumerable_thread_specific_iterator(
const enumerable_thread_specific_iterator<Container, U>& other ) :
337 my_container( other.my_container ), my_index( other.my_index), my_value( const_cast<Value *>(other.my_value) ) {}
339 enumerable_thread_specific_iterator
operator+( ptrdiff_t offset )
const {
340 return enumerable_thread_specific_iterator(*my_container, my_index + offset);
343 enumerable_thread_specific_iterator &operator+=( ptrdiff_t offset ) {
349 enumerable_thread_specific_iterator
operator-( ptrdiff_t offset )
const {
350 return enumerable_thread_specific_iterator( *my_container, my_index-offset );
353 enumerable_thread_specific_iterator &operator-=( ptrdiff_t offset ) {
359 Value& operator*()
const {
360 Value*
value = my_value;
362 value = my_value = (*my_container)[my_index].value();
368 Value& operator[]( ptrdiff_t k )
const {
369 return (*my_container)[my_index + k].value;
372 Value* operator->()
const {
return &operator*();}
374 enumerable_thread_specific_iterator& operator++() {
380 enumerable_thread_specific_iterator& operator--() {
387 enumerable_thread_specific_iterator operator++(
int) {
388 enumerable_thread_specific_iterator result = *
this;
395 enumerable_thread_specific_iterator operator--(
int) {
396 enumerable_thread_specific_iterator result = *
this;
403 typedef ptrdiff_t difference_type;
404 typedef Value value_type;
405 typedef Value* pointer;
406 typedef Value& reference;
407 typedef std::random_access_iterator_tag iterator_category;
410 template<
typename Container,
typename T>
411 enumerable_thread_specific_iterator<Container,T>
412 operator+( ptrdiff_t offset,
const enumerable_thread_specific_iterator<Container,T>& v ) {
413 return enumerable_thread_specific_iterator<Container,T>( v.my_container, v.my_index + offset );
416 template<
typename Container,
typename T,
typename U>
417 bool operator==(
const enumerable_thread_specific_iterator<Container,T>& i,
418 const enumerable_thread_specific_iterator<Container,U>& j ) {
419 return i.my_index==j.my_index && i.my_container == j.my_container;
422 template<
typename Container,
typename T,
typename U>
423 bool operator!=(
const enumerable_thread_specific_iterator<Container,T>& i,
424 const enumerable_thread_specific_iterator<Container,U>& j ) {
428 template<
typename Container,
typename T,
typename U>
429 bool operator<(
const enumerable_thread_specific_iterator<Container,T>& i,
430 const enumerable_thread_specific_iterator<Container,U>& j ) {
431 return i.my_index<j.my_index;
434 template<
typename Container,
typename T,
typename U>
435 bool operator>(
const enumerable_thread_specific_iterator<Container,T>& i,
436 const enumerable_thread_specific_iterator<Container,U>& j ) {
440 template<
typename Container,
typename T,
typename U>
441 bool operator>=(
const enumerable_thread_specific_iterator<Container,T>& i,
442 const enumerable_thread_specific_iterator<Container,U>& j ) {
446 template<
typename Container,
typename T,
typename U>
447 bool operator<=(
const enumerable_thread_specific_iterator<Container,T>& i,
448 const enumerable_thread_specific_iterator<Container,U>& j ) {
452 template<
typename Container,
typename T,
typename U>
453 ptrdiff_t
operator-(
const enumerable_thread_specific_iterator<Container,T>& i,
454 const enumerable_thread_specific_iterator<Container,U>& j ) {
455 return i.my_index-j.my_index;
458 template<
typename SegmentedContainer,
typename Value >
459 class segmented_iterator
460 #if defined(_WIN64) && defined(_MSC_VER)
461 : public std::iterator<std::input_iterator_tag, Value>
464 template<
typename C,
typename T,
typename U>
465 friend bool operator==(
const segmented_iterator<C,T>& i,
const segmented_iterator<C,U>& j);
467 template<
typename C,
typename T,
typename U>
468 friend bool operator!=(
const segmented_iterator<C,T>& i,
const segmented_iterator<C,U>& j);
470 template<
typename C,
typename U>
471 friend class segmented_iterator;
475 segmented_iterator() {my_segcont = NULL;}
477 segmented_iterator(
const SegmentedContainer& _segmented_container ) :
478 my_segcont(const_cast<SegmentedContainer*>(&_segmented_container)),
479 outer_iter(my_segcont->
end()) { }
481 ~segmented_iterator() {}
483 typedef typename SegmentedContainer::iterator outer_iterator;
484 typedef typename SegmentedContainer::value_type InnerContainer;
485 typedef typename InnerContainer::iterator inner_iterator;
488 typedef ptrdiff_t difference_type;
489 typedef Value value_type;
490 typedef typename SegmentedContainer::size_type size_type;
491 typedef Value* pointer;
492 typedef Value& reference;
493 typedef std::input_iterator_tag iterator_category;
497 segmented_iterator(
const segmented_iterator<SegmentedContainer, U>& other) :
498 my_segcont(other.my_segcont),
499 outer_iter(other.outer_iter),
501 inner_iter(other.inner_iter)
506 segmented_iterator& operator=(
const segmented_iterator<SegmentedContainer, U>& other) {
508 my_segcont = other.my_segcont;
509 outer_iter = other.outer_iter;
510 if(outer_iter != my_segcont->end()) inner_iter = other.inner_iter;
518 segmented_iterator& operator=(
const outer_iterator& new_outer_iter) {
521 for(outer_iter = new_outer_iter ;outer_iter!=my_segcont->end(); ++outer_iter) {
522 if( !outer_iter->empty() ) {
523 inner_iter = outer_iter->begin();
531 segmented_iterator& operator++() {
537 segmented_iterator operator++(
int) {
538 segmented_iterator tmp = *
this;
543 bool operator==(
const outer_iterator& other_outer)
const {
545 return (outer_iter == other_outer &&
546 (outer_iter == my_segcont->end() || inner_iter == outer_iter->begin()));
549 bool operator!=(
const outer_iterator& other_outer)
const {
555 reference operator*()
const {
557 __TBB_ASSERT(outer_iter != my_segcont->end(),
"Dereferencing a pointer at end of container");
563 pointer operator->()
const {
return &operator*();}
566 SegmentedContainer* my_segcont;
567 outer_iterator outer_iter;
568 inner_iterator inner_iter;
575 while(inner_iter == outer_iter->end() && ++outer_iter != my_segcont->end()) {
576 inner_iter = outer_iter->begin();
581 template<
typename SegmentedContainer,
typename T,
typename U>
582 bool operator==(
const segmented_iterator<SegmentedContainer,T>& i,
583 const segmented_iterator<SegmentedContainer,U>& j ) {
584 if(i.my_segcont != j.my_segcont)
return false;
585 if(i.my_segcont == NULL)
return true;
586 if(i.outer_iter != j.outer_iter)
return false;
587 if(i.outer_iter == i.my_segcont->end())
return true;
588 return i.inner_iter == j.inner_iter;
592 template<
typename SegmentedContainer,
typename T,
typename U>
593 bool operator!=(
const segmented_iterator<SegmentedContainer,T>& i,
594 const segmented_iterator<SegmentedContainer,U>& j ) {
600 void construct(
void*where) {
new(where) T();}
601 construct_by_default(
int ) {}
607 void construct(
void*where) {
new(where) T(exemplar);}
608 construct_by_exemplar(
const T& t ) : exemplar(t) {}
609 #if __TBB_ETS_USE_CPP11 610 construct_by_exemplar( T&& t ) : exemplar(std::
move(t)) {}
614 template<
typename T,
typename Finit>
617 void construct(
void* where) {
new(where) T(f());}
618 construct_by_finit(
const Finit& f_ ) : f(f_) {}
619 #if __TBB_ETS_USE_CPP11 620 construct_by_finit( Finit&& f_ ) : f(std::
move(f_)) {}
624 #if __TBB_ETS_USE_CPP11 625 template<
typename T,
typename... P>
627 internal::stored_pack<P...> pack;
628 void construct(
void* where) {
630 new(where) T(args...);
633 construct_by_args( P&& ... args ) : pack(std::forward<P>(args)...) {}
640 class callback_base {
643 virtual callback_base* clone()
const = 0;
645 virtual void destroy() = 0;
647 virtual ~callback_base() { }
649 virtual void construct(
void* where) = 0;
652 template <
typename T,
typename Constructor>
653 class callback_leaf:
public callback_base<T>, Constructor {
654 #if __TBB_ETS_USE_CPP11 655 template<
typename... P> callback_leaf( P&& ... params ) : Constructor(std::forward<P>(params)...) {}
657 template<
typename X> callback_leaf(
const X& x ) : Constructor(x) {}
667 my_allocator_type().destroy(
this);
668 my_allocator_type().deallocate(
this,1);
672 Constructor::construct(where);
675 #if __TBB_ETS_USE_CPP11 676 template<
typename... P>
677 static callback_base<T>* make( P&& ... params ) {
678 void* where = my_allocator_type().allocate(1);
679 return new(where) callback_leaf( std::forward<P>(params)... );
683 static callback_base<T>* make(
const X& x ) {
684 void* where = my_allocator_type().allocate(1);
685 return new(where) callback_leaf(x);
703 ets_element() { is_built =
false; }
705 U* value_committed() { is_built =
true;
return my_space.
begin(); }
708 my_space.
begin()->~U();
717 template<
typename T,
typename ETS>
struct is_compatible_ets {
static const bool value =
false; };
718 template<
typename T,
typename U,
typename A, ets_key_usage_type C>
721 #if __TBB_ETS_USE_CPP11 723 template <
typename T>
724 class is_callable_no_args {
729 template<
typename U>
static yes& decide( decltype(declval<U>()())* );
730 template<
typename U>
static no& decide(...);
732 static const bool value = (
sizeof(decide<T>(NULL)) ==
sizeof(yes));
759 template <
typename T,
760 typename Allocator=cache_aligned_allocator<T>,
762 class enumerable_thread_specific: internal::ets_base<ETS_key_type> {
794 my_construct_callback->construct(lref.value());
795 return lref.value_committed();
801 new(lref.value()) T(*static_cast<T*>(
p));
802 return lref.value_committed();
805 #if __TBB_ETS_USE_CPP11 809 new(lref.value()) T(
std::move(*static_cast<T*>(
p)));
810 return lref.value_committed();
818 size_t nelements = (_size +
sizeof(uintptr_t) -1) /
sizeof(uintptr_t);
823 size_t nelements = (_size +
sizeof(uintptr_t) -1) /
sizeof(uintptr_t);
840 typedef typename internal::enumerable_thread_specific_iterator< internal_collection_type, value_type >
iterator;
841 typedef typename internal::enumerable_thread_specific_iterator< internal_collection_type, const value_type >
const_iterator;
849 internal::callback_leaf<T,internal::construct_by_default<T> >::make(0)
853 template <
typename Finit
854 #if __TBB_ETS_USE_CPP11 859 internal::callback_leaf<T,internal::construct_by_finit<T,Finit> >::make(
tbb::internal::
move(finit) )
864 internal::callback_leaf<T,internal::construct_by_exemplar<T> >::make( exemplar )
867 #if __TBB_ETS_USE_CPP11 869 internal::callback_leaf<T,internal::construct_by_exemplar<T> >::make( std::
move(exemplar) )
873 template <
typename P1,
typename... P,
879 internal::callback_leaf<T,internal::construct_by_args<T,P1,P...> >::make( std::forward<P1>(arg1), std::forward<P>(args)... )
885 if(my_construct_callback) my_construct_callback->destroy();
887 this->internal::ets_base<ets_no_key>::table_clear();
893 return local(exists);
898 void* ptr = this->table_lookup(exists);
934 template<
typename A2, ets_key_usage_type C2>
936 #if __TBB_ETS_USE_CPP11 && TBB_USE_ASSERT 938 __TBB_STATIC_ASSERT( (internal::is_compatible_ets<T,
typename internal::strip<decltype(other)>::
type>::
value),
"is_compatible_ets fails" );
941 my_construct_callback = other.my_construct_callback->clone();
943 my_locals.
reserve(other.size());
944 this->table_elementwise_copy( other, create_local_by_copy );
950 swap(my_construct_callback, other.my_construct_callback);
953 swap(my_locals, other.my_locals);
954 this->internal::ets_base<ETS_key_type>::table_swap(other);
957 #if __TBB_ETS_USE_CPP11 958 template<
typename A2, ets_key_usage_type C2>
962 __TBB_STATIC_ASSERT( (internal::is_compatible_ets<T,
typename internal::strip<decltype(other)>::
type>::
value),
"is_compatible_ets fails" );
964 my_construct_callback = other.my_construct_callback;
965 other.my_construct_callback = NULL;
967 my_locals.
reserve(other.size());
968 this->table_elementwise_copy( other, create_local_by_move );
975 : internal::ets_base<ETS_key_type>()
977 internal_copy(other);
980 template<
typename Alloc, ets_key_usage_type Cachetype>
983 internal_copy(other);
986 #if __TBB_ETS_USE_CPP11 989 internal_swap(other);
992 template<
typename Alloc, ets_key_usage_type Cachetype>
1001 if(
this != &other ) {
1003 my_construct_callback->destroy();
1004 internal_copy( other );
1009 template<
typename Alloc, ets_key_usage_type Cachetype>
1012 __TBB_ASSERT( static_cast<void*>(
this)!=static_cast<const void*>(&other), NULL );
1014 my_construct_callback->destroy();
1015 internal_copy(other);
1019 #if __TBB_ETS_USE_CPP11 1022 if(
this != &other )
1023 internal_swap(other);
1027 template<
typename Alloc, ets_key_usage_type Cachetype>
1030 __TBB_ASSERT( static_cast<void*>(
this)!=static_cast<const void*>(&other), NULL );
1032 my_construct_callback->destroy();
1039 template <
typename combine_func_t>
1042 internal::ets_element<T> location;
1043 my_construct_callback->construct(location.value());
1044 return *location.value_committed();
1048 while(++ci !=
end())
1049 my_result = f_combine( my_result, *ci );
1054 template <
typename combine_func_t>
1063 template<
typename Container >
1081 typedef typename internal::segmented_iterator<Container, value_type>
iterator;
1082 typedef typename internal::segmented_iterator<Container, const value_type>
const_iterator;
1084 flattened2d(
const Container &c,
typename Container::const_iterator b,
typename Container::const_iterator e ) :
1085 my_container(const_cast<Container*>(&c)), my_begin(b), my_end(e) { }
1088 my_container(const_cast<Container*>(&c)), my_begin(c.
begin()), my_end(c.
end()) { }
1097 for(
typename Container::const_iterator i = my_begin; i != my_end; ++i) {
1098 tot_size += i->size();
1111 template <
typename Container>
1116 template <
typename Container>
1123 namespace internal {
1124 using interface6::internal::segmented_iterator;
1127 using interface6::enumerable_thread_specific;
1128 using interface6::flattened2d;
void combine_each(combine_func_t f_combine)
internal_collection_type::difference_type difference_type
Allocator::template rebind< uintptr_t >::other array_allocator_type
static void * create_local_by_move(internal::ets_base< ets_no_key > &base, void *p)
internal::callback_base< T > * my_construct_callback
enumerable_thread_specific & operator=(const enumerable_thread_specific &other)
const_iterator end() const
end const iterator
static void * create_local_by_copy(internal::ets_base< ets_no_key > &base, void *p)
enumerable_thread_specific & operator=(const enumerable_thread_specific< T, Alloc, Cachetype > &other)
void const char const char int ITT_FORMAT __itt_group_sync x void const char ITT_FORMAT __itt_group_sync s void ITT_FORMAT __itt_group_sync p void ITT_FORMAT p void ITT_FORMAT p no args __itt_suppress_mode_t unsigned int mask
void clear()
Destroys local copies.
enumerable_thread_specific(T &&exemplar)
const T & const_reference
bool operator==(const memory_pool_allocator< T, P > &a, const memory_pool_allocator< U, P > &b)
enumerable_thread_specific()
Default constructor. Each local instance of T is default constructed.
internal::enumerable_thread_specific_iterator< internal_collection_type, value_type > iterator
vector_iterator< Container, T > operator+(ptrdiff_t offset, const vector_iterator< Container, T > &v)
bool operator>=(const concurrent_vector< T, A1 > &a, const concurrent_vector< T, A2 > &b)
bool empty() const
Return false if vector is not empty or has elements under construction at least.
const_iterator begin() const
T combine(combine_func_t f_combine)
const_iterator end() const
range_type range(size_t grainsize=1)
Get range for parallel algorithms.
void * create_local() __TBB_override
void const char const char int ITT_FORMAT __itt_group_sync s
conval_type::const_pointer const_pointer
enumerable_thread_specific & operator=(enumerable_thread_specific &&other)
internal::padded< internal::ets_element< T > > padded_element
void free_array(void *_ptr, size_t _size) __TBB_override
Allocator::template rebind< padded_element >::other padded_allocator_type
void call(F &&f, Pack &&p)
Calls the given function with arguments taken from a stored_pack.
internal_collection_type::size_type size_type
size_type size() const
Return size of vector. It may include elements under construction.
enumerable_thread_specific(const enumerable_thread_specific &other)
iterator grow_by(size_type delta)
Grow by "delta" elements.
#define __TBB_STATIC_ASSERT(condition, msg)
const T & const_reference
const_range_type range(size_t grainsize=1) const
Get const range for parallel algorithms.
enumerable_thread_specific(const enumerable_thread_specific< T, Alloc, Cachetype > &other)
generic_range_type(const generic_range_type< U > &r)
internal::concurrent_vector_base_v3::size_type size_type
reference local()
returns reference to local, discarding exists
Base class for types that should not be copied or assigned.
size_type size() const
Get the number of local copies.
enumerable_thread_specific(const T &exemplar)
Constructor with exemplar. Each local instance of T is copy-constructed from the exemplar.
conval_type::allocator_type allocator_type
void clear()
Clear container while keeping memory allocated.
The enumerable_thread_specific container.
void internal_swap(enumerable_thread_specific &other)
generic_range_type< const_iterator > const_range_type
T * begin() const
Pointer to beginning of array.
void const char const char int ITT_FORMAT __itt_group_sync x void const char ITT_FORMAT __itt_group_sync s void ITT_FORMAT __itt_group_sync p void ITT_FORMAT p void ITT_FORMAT p no args __itt_suppress_mode_t unsigned int void size_t ITT_FORMAT d void ITT_FORMAT p void ITT_FORMAT p __itt_model_site __itt_model_site_instance ITT_FORMAT p __itt_model_task __itt_model_task_instance ITT_FORMAT p void ITT_FORMAT p void ITT_FORMAT p void size_t ITT_FORMAT d void ITT_FORMAT p const wchar_t ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s no args void ITT_FORMAT p size_t ITT_FORMAT d no args const wchar_t const wchar_t ITT_FORMAT s __itt_heap_function void size_t int ITT_FORMAT d __itt_heap_function void ITT_FORMAT p __itt_heap_function void void size_t int ITT_FORMAT d no args no args unsigned int ITT_FORMAT u const __itt_domain __itt_id ITT_FORMAT lu const __itt_domain __itt_id __itt_id __itt_string_handle ITT_FORMAT p const __itt_domain __itt_id ITT_FORMAT p const __itt_domain __itt_id __itt_timestamp __itt_timestamp ITT_FORMAT lu const __itt_domain __itt_id __itt_id __itt_string_handle ITT_FORMAT p const __itt_domain ITT_FORMAT p const __itt_domain __itt_string_handle unsigned long long value
Block of space aligned sufficiently to construct an array T with N elements.
bool operator!=(const memory_pool_allocator< T, P > &a, const memory_pool_allocator< U, P > &b)
conval_type::value_type value_type
iterator begin()
begin iterator
Meets "allocator" requirements of ISO C++ Standard, Section 20.1.5.
enumerable_thread_specific & operator=(enumerable_thread_specific< T, Alloc, Cachetype > &&other)
internal::segmented_iterator< Container, value_type > iterator
#define __TBB_ASSERT(predicate, comment)
No-op version of __TBB_ASSERT.
void reserve(size_type n)
Allocate enough space to grow to size n without having to allocate more memory later.
void move(tbb_thread &t1, tbb_thread &t2)
bool empty() const
true if there have been no local copies created
void const char const char int ITT_FORMAT __itt_group_sync x void const char ITT_FORMAT __itt_group_sync s void ITT_FORMAT __itt_group_sync p void ITT_FORMAT p void ITT_FORMAT p no args __itt_suppress_mode_t unsigned int void size_t ITT_FORMAT d void ITT_FORMAT p void ITT_FORMAT p __itt_model_site __itt_model_site_instance ITT_FORMAT p __itt_model_task __itt_model_task_instance ITT_FORMAT p void ITT_FORMAT p void ITT_FORMAT p void size_t ITT_FORMAT d void ITT_FORMAT p const wchar_t ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s no args void ITT_FORMAT p size_t ITT_FORMAT d no args const wchar_t const wchar_t ITT_FORMAT s __itt_heap_function void size_t int ITT_FORMAT d __itt_heap_function void ITT_FORMAT p __itt_heap_function void void size_t int ITT_FORMAT d no args no args unsigned int ITT_FORMAT u const __itt_domain __itt_id ITT_FORMAT lu const __itt_domain __itt_id __itt_id __itt_string_handle ITT_FORMAT p const __itt_domain __itt_id ITT_FORMAT p const __itt_domain __itt_id __itt_timestamp __itt_timestamp ITT_FORMAT lu const __itt_domain __itt_id __itt_id __itt_string_handle ITT_FORMAT p const __itt_domain ITT_FORMAT p const __itt_domain __itt_string_handle unsigned long long ITT_FORMAT lu const __itt_domain __itt_id __itt_string_handle * key
internal::segmented_iterator< Container, const value_type > const_iterator
tick_count::interval_t operator-(const tick_count &t1, const tick_count &t0)
enumerable_thread_specific(enumerable_thread_specific &&other)
~enumerable_thread_specific()
Destructor.
void * create_array(size_t _size) __TBB_override
ets_key_usage_type
enum for selecting between single key and key-per-instance versions
conval_type::size_type size_type
Basic types.
bool operator<=(const concurrent_vector< T, A1 > &a, const concurrent_vector< T, A2 > &b)
reference local(bool &exists)
Returns reference to calling thread's local copy, creating one if necessary.
A range over which to iterate.
generic_range_type(I begin_, I end_, size_t grainsize_=1)
Container::const_iterator my_end
void internal_copy(const enumerable_thread_specific< T, A2, C2 > &other)
bool operator<(const concurrent_vector< T, A1 > &a, const concurrent_vector< T, A2 > &b)
Base class for types that should not be assigned.
Container::value_type conval_type
generic_range_type< iterator > range_type
conval_type::reference reference
const_iterator begin() const
begin const iterator
bool operator>(const concurrent_vector< T, A1 > &a, const concurrent_vector< T, A2 > &b)
iterator end()
end iterator
void call_itt_notify(notify_type, void *)
void internal_move(enumerable_thread_specific< T, A2, C2 > &&other)
flattened2d(const Container &c, typename Container::const_iterator b, typename Container::const_iterator e)
ptrdiff_t difference_type
flattened2d< Container > flatten2d(const Container &c, const typename Container::const_iterator b, const typename Container::const_iterator e)
enumerable_thread_specific(P1 &&arg1, P &&... args)
Variadic constructor with initializer arguments. Each local instance of T is constructed by T(args....
Identifiers declared inside namespace internal should never be used directly by client code.
enumerable_thread_specific(enumerable_thread_specific< T, Alloc, Cachetype > &&other)
conval_type::difference_type difference_type
Allocator allocator_type
Basic types.
void const char const char int ITT_FORMAT __itt_group_sync x void const char ITT_FORMAT __itt_group_sync s void ITT_FORMAT __itt_group_sync p void ITT_FORMAT p void ITT_FORMAT p no args __itt_suppress_mode_t unsigned int void size_t ITT_FORMAT d void ITT_FORMAT p void ITT_FORMAT p __itt_model_site __itt_model_site_instance ITT_FORMAT p __itt_model_task __itt_model_task_instance ITT_FORMAT p void ITT_FORMAT p void ITT_FORMAT p void size_t ITT_FORMAT d void ITT_FORMAT p const wchar_t ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s no args void ITT_FORMAT p size_t ITT_FORMAT d no args const wchar_t const wchar_t ITT_FORMAT s __itt_heap_function void size_t int ITT_FORMAT d __itt_heap_function void ITT_FORMAT p __itt_heap_function void void size_t int ITT_FORMAT d no args no args unsigned int ITT_FORMAT u const __itt_domain __itt_id ITT_FORMAT lu const __itt_domain __itt_id __itt_id __itt_string_handle ITT_FORMAT p const __itt_domain __itt_id ITT_FORMAT p const __itt_domain __itt_id __itt_timestamp begin
A generic range, used to create range objects from the iterators.
void const char const char int ITT_FORMAT __itt_group_sync p
flattened2d(const Container &c)
void const char const char int ITT_FORMAT __itt_group_sync x void const char ITT_FORMAT __itt_group_sync s void ITT_FORMAT __itt_group_sync p void ITT_FORMAT p void ITT_FORMAT p no args __itt_suppress_mode_t unsigned int void size_t ITT_FORMAT d void ITT_FORMAT p void ITT_FORMAT p __itt_model_site __itt_model_site_instance ITT_FORMAT p __itt_model_task __itt_model_task_instance ITT_FORMAT p void ITT_FORMAT p void ITT_FORMAT p void size_t ITT_FORMAT d void ITT_FORMAT p const wchar_t ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s no args void ITT_FORMAT p size_t ITT_FORMAT d no args const wchar_t const wchar_t ITT_FORMAT s __itt_heap_function void size_t int ITT_FORMAT d __itt_heap_function void ITT_FORMAT p __itt_heap_function void void size_t int ITT_FORMAT d no args no args unsigned int ITT_FORMAT u const __itt_domain __itt_id id
void const char const char int ITT_FORMAT __itt_group_sync x void const char ITT_FORMAT __itt_group_sync s void ITT_FORMAT __itt_group_sync p void ITT_FORMAT p void ITT_FORMAT p no args __itt_suppress_mode_t unsigned int void size_t ITT_FORMAT d void ITT_FORMAT p void ITT_FORMAT p __itt_model_site __itt_model_site_instance ITT_FORMAT p __itt_model_task __itt_model_task_instance ITT_FORMAT p void ITT_FORMAT p void ITT_FORMAT p void size_t ITT_FORMAT d void ITT_FORMAT p const wchar_t ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s no args void ITT_FORMAT p size_t ITT_FORMAT d no args const wchar_t const wchar_t ITT_FORMAT s __itt_heap_function void size_t int ITT_FORMAT d __itt_heap_function void ITT_FORMAT p __itt_heap_function void void size_t int ITT_FORMAT d no args no args unsigned int ITT_FORMAT u const __itt_domain __itt_id ITT_FORMAT lu const __itt_domain __itt_id __itt_id __itt_string_handle ITT_FORMAT p const __itt_domain __itt_id ITT_FORMAT p const __itt_domain __itt_id __itt_timestamp __itt_timestamp end
internal::enumerable_thread_specific_iterator< internal_collection_type, const value_type > const_iterator
void swap(concurrent_hash_map< Key, T, HashCompare, A > &a, concurrent_hash_map< Key, T, HashCompare, A > &b)
tbb::concurrent_vector< padded_element, padded_allocator_type > internal_collection_type
ptrdiff_t difference_type
generic_range_type(generic_range_type &r, split)
void const char const char int ITT_FORMAT __itt_group_sync x void const char ITT_FORMAT __itt_group_sync s void ITT_FORMAT __itt_group_sync p void ITT_FORMAT p void ITT_FORMAT p no args __itt_suppress_mode_t unsigned int void size_t ITT_FORMAT d void ITT_FORMAT p void ITT_FORMAT p __itt_model_site __itt_model_site_instance ITT_FORMAT p __itt_model_task __itt_model_task_instance ITT_FORMAT p void ITT_FORMAT p void ITT_FORMAT p void size_t ITT_FORMAT d void ITT_FORMAT p const wchar_t ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s no args void ITT_FORMAT p size_t ITT_FORMAT d no args const wchar_t const wchar_t ITT_FORMAT s __itt_heap_function void size_t int ITT_FORMAT d __itt_heap_function void ITT_FORMAT p __itt_heap_function void void size_t int ITT_FORMAT d no args no args unsigned int ITT_FORMAT u const __itt_domain __itt_id ITT_FORMAT lu const __itt_domain __itt_id __itt_id __itt_string_handle ITT_FORMAT p const __itt_domain __itt_id ITT_FORMAT p const __itt_domain __itt_id __itt_timestamp __itt_timestamp ITT_FORMAT lu const __itt_domain __itt_id __itt_id __itt_string_handle ITT_FORMAT p const __itt_domain ITT_FORMAT p const __itt_domain __itt_string_handle unsigned long long ITT_FORMAT lu const __itt_domain __itt_id __itt_string_handle __itt_metadata_type type
Container::const_iterator my_begin
Dummy type that distinguishes splitting constructor from copy constructor.
void const char const char int ITT_FORMAT __itt_group_sync x void const char ITT_FORMAT __itt_group_sync s void ITT_FORMAT __itt_group_sync p void ITT_FORMAT p void ITT_FORMAT p no args __itt_suppress_mode_t unsigned int void size_t size
conval_type::pointer pointer
conval_type::const_reference const_reference
internal_collection_type my_locals
enumerable_thread_specific(Finit finit)
Constructor with initializer functor. Each local instance of T is constructed by T(finit()).
void swap(atomic< T > &lhs, atomic< T > &rhs)
void const char const char int ITT_FORMAT __itt_group_sync x void const char ITT_FORMAT __itt_group_sync s void ITT_FORMAT __itt_group_sync p void ITT_FORMAT p void ITT_FORMAT p no args __itt_suppress_mode_t unsigned int void size_t ITT_FORMAT d void ITT_FORMAT p void ITT_FORMAT p __itt_model_site __itt_model_site_instance ITT_FORMAT p __itt_model_task __itt_model_task_instance ITT_FORMAT p void ITT_FORMAT p void ITT_FORMAT p void size_t ITT_FORMAT d void ITT_FORMAT p const wchar_t ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s const char ITT_FORMAT s no args void ITT_FORMAT p size_t ITT_FORMAT d no args const wchar_t const wchar_t ITT_FORMAT s __itt_heap_function h