2 Copyright (C) 2002-2017 CERN for the benefit of the ATLAS collaboration
11 bool TPIntegerVector_p2::lastElement() const {
12 return m_storage->size() == (m_position>>1) + 1;
16 unsigned TPIntegerVector_p2::startPos() const {
17 return m_position? m_storage->m_endPos[m_position-1] : 0;
21 unsigned TPIntegerVector_p2::size() const {
22 return m_storage->m_endPos[m_position] - startPos();
26 unsigned TPIntegerVector_p2::reserved() const {
27 return m_storage->m_endPos[m_position+1] - startPos();
31 void TPIntegerVector_p2::resize( size_t new_size ) {
32 if( new_size > reserved() && !lastElement() )
33 throw std::runtime_error("TPIntegerVector_p2::resize() can only enlarge the last element beyond its reserved size");
34 size_t end = startPos() + new_size;
35 m_storage->m_endPos[m_position] = end;
37 if( m_storage->m_endPos[m_position+1] < end )
38 m_storage->m_endPos[m_position+1] = end;
39 m_storage->m_data.resize( end );
44 void TPIntegerVector_p2::grow( const size_t diff ) {
45 resize( size() + diff );
49 void TPIntegerVector_p2::reserve( size_t new_size ) {
50 if( new_size > reserved() && !lastElement() )
51 throw std::runtime_error("TPIntegerVector_p2::reserve() can only enlarge the last element!");
52 if( size() >= new_size || !lastElement() )
54 size_t end = startPos() + new_size;
55 m_storage->m_endPos[m_position+1] = end;
56 m_storage->m_data.reserve( end );
62 TPIntegerVector_p2::value_type&
63 TPIntegerVector_p2::operator[]( size_t idx ) {
64 return const_cast<value_type&>(((const TPIntegerVector_p2*)this)->operator[](idx));
68 const TPIntegerVector_p2::value_type&
69 TPIntegerVector_p2::operator[]( size_t idx ) const {
70 return m_storage->m_data[ startPos() + idx ];
76 void TPIntegerVector_p2::push_back( const value_type& val )
79 m_storage->m_data[ m_storage->m_endPos[m_position] - 1 ] = val;
84 void TPIntegerVector_p2::push_int( const int& val )
86 push_back( (value_type)val );
91 void TPIntegerVector_p2::push_float( const float& val )
93 union {unsigned int i; float f;} m_union;
95 push_back( m_union.i );
100 void TPIntegerVector_p2::push_double( const double& val )
102 union {struct{unsigned int i1;unsigned int i2;} c; double d;} m_union;
104 push_back( m_union.c.i1 );
105 push_back( m_union.c.i2 );
109 TPIntegerVector_p2::push_chars( const char * const s )
111 _store_bytes( (void*)s, strlen(s)+1 );
116 TPIntegerVector_p2::push_string( const std::string& str )
118 push_chars( str.c_str() );
123 TPIntegerVector_p2::push_bytes( const void * bytes, size_t bytelen )
125 push_back( bytelen );
126 _store_bytes( bytes, bytelen);
131 TPIntegerVector_p2::_store_bytes( const void * buff, size_t bytelen )
133 size_t intlen( size_for_blob(bytelen) - 1 );
135 // need to grow first and take address later, because of possible memory reallocation
136 value_type& start = m_storage->m_data[ m_storage->m_endPos[m_position] - intlen ];
137 memcpy( (void*)&start, buff, bytelen );
143 void TPIntegerVector_p2::push_TPObjRef( const TPObjRef& val )
145 union {struct{unsigned short i1;unsigned short i2;} c; unsigned int I;} m_union;
146 m_union.c.i1 = val.topLevelCnvID();
147 m_union.c.i2 = val.typeID() & 0xFFFF;
148 push_back( m_union.I );
149 push_back( val.index());
153 void TPIntegerVector_p2::push_vTPObjRef( const std::vector<TPObjRef>& val )
155 size_t size = val.size();
157 for( size_t i=0; i<size; i++ )
158 push_TPObjRef( val[i] );
164 TPIntegerVector_p2::size_for( const T& obj )
166 return ( sizeof(obj) + sizeof(value_type)-1 ) / sizeof(value_type);
171 TPIntegerVector_p2::size_for( const char *s )
173 return strlen(s) / sizeof(value_type) + 1;
177 TPIntegerVector_p2::size_for_ref( )
179 return ( sizeof(TPObjRef) + sizeof(value_type)-1 ) / sizeof(value_type);
186 TPIntegerVector_p2::size_for( const std::string& str )
188 return str.length() / sizeof(value_type) + 1;
192 TPIntegerVector_p2::size_for_blob( size_t blobsize )
194 return ( blobsize + sizeof(value_type)-1 ) / sizeof(value_type) + 1;
199 TPIntegerVector_p2::next_string_size( const TPIntegerVector_p2::const_iterator& iter ) const
201 return strlen( (const char *)&*iter );
205 TPIntegerVector_p2::next_blob_size( const TPIntegerVector_p2::const_iterator& iter ) const
207 return (size_t)*iter;
213 const TPIntegerVector_p2::value_type&
214 TPIntegerVector_p2::next( TPIntegerVector_p2::const_iterator& iter ) const
221 TPIntegerVector_p2::next_int( TPIntegerVector_p2::const_iterator& iter ) const
228 TPIntegerVector_p2::next_float( TPIntegerVector_p2::const_iterator& iter ) const
230 union {unsigned int i; float f;} m_union;
236 TPIntegerVector_p2::next_double( TPIntegerVector_p2::const_iterator& iter ) const
238 union {struct{unsigned int i1;unsigned int i2;} c; double d;} m_union;
239 m_union.c.i1 = *iter++;
240 m_union.c.i2 = *iter++;
245 TPIntegerVector_p2::next_TPObjRef( TPIntegerVector_p2::const_iterator& iter ) const
247 union {struct{unsigned short i1;unsigned short i2;} c; unsigned int I;} m_union;
249 return TPObjRef(TPObjRef::typeID_t(m_union.c.i1, m_union.c.i2), (int)*iter++ );
254 TPIntegerVector_p2::next_chars( TPIntegerVector_p2::const_iterator& iter, char *buff, size_t bufflen ) const
256 const char *s = (const char *)&*iter;
257 size_t slen = strlen(s);
258 iter += slen/sizeof(value_type) + 1;
259 assert( bufflen > slen );
260 if( bufflen <= slen) slen = bufflen-1;
261 memcpy( (void*)buff, (void*)s, slen+1 );
265 TPIntegerVector_p2::next_string( const_iterator& iter ) const
267 const char *s = (const char *)&*iter;
268 iter += strlen(s) / sizeof(value_type) + 1;
269 return std::string( s );
274 TPIntegerVector_p2::next_bytes( TPIntegerVector_p2::const_iterator& iter, void *buff, size_t bufflen ) const
276 value_type size = *iter++;
277 const void *b = &*iter;
278 iter += size/sizeof(value_type);
279 assert( bufflen >= size );
280 if( bufflen < size) size = bufflen;
281 memcpy( buff, b, size );
286 void TPIntegerVector_p2::next_vTPObjRef( TPIntegerVector_p2::const_iterator& iter, std::vector<TPObjRef>& refs ) const
288 value_type size = *iter++;
290 refs.reserve( size );
291 for( value_type i=0; i<size; i++ )
292 refs.push_back( next_TPObjRef(iter) );