Coverage Report

Created: 2026-06-07 06:36

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/resiprocate/resip/stack/ParserContainer.hxx
Line
Count
Source
1
#ifndef RESIP_ParserContainer_hxx
2
#define RESIP_ParserContainer_hxx
3
4
#include <algorithm>
5
#include <iterator>
6
7
#include "resip/stack/HeaderFieldValueList.hxx"
8
#include "resip/stack/ParserContainerBase.hxx"
9
10
namespace resip
11
{
12
using std::ptrdiff_t;
13
/**
14
   @brief Container class for ParserCategory, used by SipMessage to represent
15
      multi-valued headers (Contact, Via, etc).
16
17
   This has an interface that is similar to stl containers, but not as complete.
18
19
   @ingroup resip_crit
20
*/
21
template<class T>
22
class ParserContainer : public ParserContainerBase
23
{
24
   public:
25
      typedef T value_type;
26
      typedef value_type* pointer;
27
      typedef const value_type* const_pointer;
28
      typedef value_type& reference;
29
      typedef const value_type& const_reference;
30
      typedef ptrdiff_t difference_type;
31
32
      /**
33
         @brief Default c'tor.
34
      */
35
      ParserContainer()
36
0
         : ParserContainerBase(Headers::UNKNOWN)
37
0
      {}
Unexecuted instantiation: resip::ParserContainer<resip::Token>::ParserContainer()
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::ParserContainer()
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::ParserContainer()
38
      
39
      ParserContainer(PoolBase& pool)
40
         : ParserContainerBase(Headers::UNKNOWN,pool)
41
      {}
42
      
43
      /** 
44
         @internal
45
         @brief Used by SipMessage (using this carries a high risk of blowing 
46
            your feet off).
47
      */
48
      ParserContainer(HeaderFieldValueList* hfvs,
49
                      Headers::Type type = Headers::UNKNOWN)
50
0
         : ParserContainerBase(type)
51
0
      {
52
0
         mParsers.reserve(hfvs->size());
53
0
         for (HeaderFieldValueList::iterator i = hfvs->begin();
54
0
              i != hfvs->end(); i++)
55
0
         {
56
            // create, store without copying -- 
57
            // keeps the HeaderFieldValue from reallocating its buffer
58
0
            mParsers.push_back(HeaderKit::Empty);
59
0
            mParsers.back().hfv.init(i->getBuffer(),i->getLength(),false);
60
0
         }
61
0
      }
Unexecuted instantiation: resip::ParserContainer<resip::Token>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::StringCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::PrivacyCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::Mime>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::GenericUri>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::UInt32Category>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::ExpiresCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::CallID>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::CSeqCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::DateCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::WarningCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::RAckCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::Via>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::TokenOrQuotedStringCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
Unexecuted instantiation: resip::ParserContainer<resip::IdentityCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type)
62
63
      ParserContainer(HeaderFieldValueList* hfvs,
64
                      Headers::Type type,
65
                      PoolBase& pool)
66
301
         : ParserContainerBase(type,pool)
67
301
      {
68
301
         mParsers.reserve(hfvs->size());
69
301
         for (HeaderFieldValueList::iterator i = hfvs->begin();
70
602
              i != hfvs->end(); i++)
71
301
         {
72
            // create, store without copying -- 
73
            // keeps the HeaderFieldValue from reallocating its buffer
74
301
            mParsers.push_back(HeaderKit::Empty);
75
301
            mParsers.back().hfv.init(i->getBuffer(),i->getLength(),false);
76
301
         }
77
301
      }
Unexecuted instantiation: resip::ParserContainer<resip::StringCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::Token>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::IdentityCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::PrivacyCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::Mime>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::GenericUri>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
resip::ParserContainer<resip::UInt32Category>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Line
Count
Source
66
301
         : ParserContainerBase(type,pool)
67
301
      {
68
301
         mParsers.reserve(hfvs->size());
69
301
         for (HeaderFieldValueList::iterator i = hfvs->begin();
70
602
              i != hfvs->end(); i++)
71
301
         {
72
            // create, store without copying -- 
73
            // keeps the HeaderFieldValue from reallocating its buffer
74
301
            mParsers.push_back(HeaderKit::Empty);
75
301
            mParsers.back().hfv.init(i->getBuffer(),i->getLength(),false);
76
301
         }
77
301
      }
Unexecuted instantiation: resip::ParserContainer<resip::ExpiresCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::CallID>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::CSeqCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::DateCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::WarningCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::Via>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::RAckCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
Unexecuted instantiation: resip::ParserContainer<resip::TokenOrQuotedStringCategory>::ParserContainer(resip::HeaderFieldValueList*, resip::Headers::Type, resip::PoolBase&)
78
79
      /**
80
         @brief Copy c'tor.
81
      */
82
      ParserContainer(const ParserContainer& other)
83
0
         : ParserContainerBase(other)
84
0
      {}
Unexecuted instantiation: resip::ParserContainer<resip::Token>::ParserContainer(resip::ParserContainer<resip::Token> const&)
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::ParserContainer(resip::ParserContainer<resip::NameAddr> const&)
Unexecuted instantiation: resip::ParserContainer<resip::StringCategory>::ParserContainer(resip::ParserContainer<resip::StringCategory> const&)
Unexecuted instantiation: resip::ParserContainer<resip::PrivacyCategory>::ParserContainer(resip::ParserContainer<resip::PrivacyCategory> const&)
Unexecuted instantiation: resip::ParserContainer<resip::Mime>::ParserContainer(resip::ParserContainer<resip::Mime> const&)
Unexecuted instantiation: resip::ParserContainer<resip::GenericUri>::ParserContainer(resip::ParserContainer<resip::GenericUri> const&)
Unexecuted instantiation: resip::ParserContainer<resip::UInt32Category>::ParserContainer(resip::ParserContainer<resip::UInt32Category> const&)
Unexecuted instantiation: resip::ParserContainer<resip::ExpiresCategory>::ParserContainer(resip::ParserContainer<resip::ExpiresCategory> const&)
Unexecuted instantiation: resip::ParserContainer<resip::CallID>::ParserContainer(resip::ParserContainer<resip::CallID> const&)
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::ParserContainer(resip::ParserContainer<resip::Auth> const&)
Unexecuted instantiation: resip::ParserContainer<resip::CSeqCategory>::ParserContainer(resip::ParserContainer<resip::CSeqCategory> const&)
Unexecuted instantiation: resip::ParserContainer<resip::DateCategory>::ParserContainer(resip::ParserContainer<resip::DateCategory> const&)
Unexecuted instantiation: resip::ParserContainer<resip::WarningCategory>::ParserContainer(resip::ParserContainer<resip::WarningCategory> const&)
Unexecuted instantiation: resip::ParserContainer<resip::RAckCategory>::ParserContainer(resip::ParserContainer<resip::RAckCategory> const&)
Unexecuted instantiation: resip::ParserContainer<resip::Via>::ParserContainer(resip::ParserContainer<resip::Via> const&)
Unexecuted instantiation: resip::ParserContainer<resip::TokenOrQuotedStringCategory>::ParserContainer(resip::ParserContainer<resip::TokenOrQuotedStringCategory> const&)
Unexecuted instantiation: resip::ParserContainer<resip::IdentityCategory>::ParserContainer(resip::ParserContainer<resip::IdentityCategory> const&)
85
86
      /**
87
         @brief Copy c'tor.
88
      */
89
      ParserContainer(const ParserContainer& other, PoolBase& pool)
90
         : ParserContainerBase(other, pool)
91
      {}
92
93
      /**
94
         @brief Assignment operator.
95
      */
96
      ParserContainer& operator=(const ParserContainer& other)
97
0
      {
98
0
         return static_cast<ParserContainer&>(ParserContainerBase::operator=(other));
99
0
      }
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::operator=(resip::ParserContainer<resip::NameAddr> const&)
Unexecuted instantiation: resip::ParserContainer<resip::Token>::operator=(resip::ParserContainer<resip::Token> const&)
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::operator=(resip::ParserContainer<resip::Auth> const&)
Unexecuted instantiation: resip::ParserContainer<resip::Via>::operator=(resip::ParserContainer<resip::Via> const&)
100
101
      /**
102
         @brief Returns the first header field value in this container.
103
      */
104
      T& front() 
105
3.62k
      {
106
3.62k
         return ensureInitialized(mParsers.front(),this);
107
3.62k
      }
Unexecuted instantiation: resip::ParserContainer<resip::Token>::front()
Unexecuted instantiation: resip::ParserContainer<resip::StringCategory>::front()
Unexecuted instantiation: resip::ParserContainer<resip::Mime>::front()
Unexecuted instantiation: resip::ParserContainer<resip::GenericUri>::front()
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::front()
resip::ParserContainer<resip::UInt32Category>::front()
Line
Count
Source
105
3.62k
      {
106
3.62k
         return ensureInitialized(mParsers.front(),this);
107
3.62k
      }
Unexecuted instantiation: resip::ParserContainer<resip::ExpiresCategory>::front()
Unexecuted instantiation: resip::ParserContainer<resip::CallID>::front()
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::front()
Unexecuted instantiation: resip::ParserContainer<resip::CSeqCategory>::front()
Unexecuted instantiation: resip::ParserContainer<resip::DateCategory>::front()
Unexecuted instantiation: resip::ParserContainer<resip::RAckCategory>::front()
Unexecuted instantiation: resip::ParserContainer<resip::Via>::front()
108
      
109
      /**
110
         @brief Returns the last header field value in this container.
111
      */
112
      T& back() 
113
0
      { 
114
0
         return ensureInitialized(mParsers.back(),this);
115
0
      }
116
      
117
      /**
118
         @brief Returns the first header field value in this container.
119
      */
120
      const T& front() const 
121
0
      { 
122
0
         return ensureInitialized(mParsers.front(),this);
123
0
      }
Unexecuted instantiation: resip::ParserContainer<resip::Via>::front() const
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::front() const
124
      
125
      /**
126
         @brief Returns the last header field value in this container.
127
      */
128
      const T& back() const 
129
      { 
130
         return ensureInitialized(mParsers.back(),this);
131
      }
132
      
133
      /**
134
         @brief Returns a pointer to the header field value at the given 0-based index,
135
            or nullptr if the index is out of range.  O(1) - backed by a vector.
136
      */
137
      T* getByIndex(size_t index)
138
      {
139
         if (index >= mParsers.size()) return nullptr;
140
         return &ensureInitialized(mParsers[index], this);
141
      }
142
143
      const T* getByIndex(size_t index) const
144
      {
145
         if (index >= mParsers.size()) return nullptr;
146
         return &ensureInitialized(mParsers[index], this);
147
      }
148
149
      /**
150
         @brief Inserts a header field value at the front of this container.
151
      */
152
      void push_front(const T & t) 
153
0
      { 
154
0
         mParsers.insert(mParsers.begin(), HeaderKit::Empty);
155
0
         mParsers.front().pc=makeParser(t);
156
0
      }
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::push_front(resip::NameAddr const&)
Unexecuted instantiation: resip::ParserContainer<resip::Via>::push_front(resip::Via const&)
157
158
      /**
159
         @brief Inserts a header field value at the back of this container.
160
      */
161
      void push_back(const T & t) 
162
0
      { 
163
0
         mParsers.push_back(HeaderKit::Empty);
164
0
         mParsers.back().pc=makeParser(t);
165
0
      }
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::push_back(resip::NameAddr const&)
Unexecuted instantiation: resip::ParserContainer<resip::Token>::push_back(resip::Token const&)
Unexecuted instantiation: resip::ParserContainer<resip::Via>::push_back(resip::Via const&)
Unexecuted instantiation: resip::ParserContainer<resip::WarningCategory>::push_back(resip::WarningCategory const&)
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::push_back(resip::Auth const&)
166
            
167
      /**
168
         @brief Returns a copy of this ParserContainer, in reverse order.
169
         @todo !bwc! optimize this (we are copying each ParserContainer twice)
170
      */
171
      ParserContainer reverse() const
172
      {
173
         ParserContainer tmp(*this);
174
         std::reverse(tmp.mParsers.begin(), tmp.mParsers.end());
175
         return tmp;
176
      }
177
178
      typedef ParserContainerBase::Parsers Parsers;
179
      // .dlb. these can be partially hoisted as well
180
      class const_iterator;
181
      
182
      /**
183
         @brief An iterator class (bidirectional)
184
      */
185
      class iterator //: public std::iterator<std::bidirectional_iterator_tag, T>  // Note: std::iterator deprecated in C++17 usings below cover same functionality
186
      {
187
         public:
188
            using iterator_category = std::bidirectional_iterator_tag;
189
            using value_type = T;
190
            using difference_type = std::ptrdiff_t;
191
            using pointer = T*;
192
            using reference = T&;
193
194
0
            iterator(typename Parsers::iterator i,ParserContainer* ref) : mIt(i),mRef(ref){}
195
            iterator() : mRef(0) {}
196
            iterator(const iterator& orig) : mIt(orig.mIt), mRef(orig.mRef) {}
197
198
            iterator operator++() {iterator it(++mIt,mRef); return it;}
199
0
            iterator operator++(int) {iterator it(mIt++,mRef); return it;}
200
            iterator operator--() {iterator it(--mIt,mRef); return it;}
201
            iterator operator--(int) {iterator it(mIt--,mRef); return it;}
202
0
            friend bool operator!=(const iterator& lhs, const iterator& rhs) { return lhs.mIt != rhs.mIt; }
203
            friend bool operator==(const iterator& lhs, const iterator& rhs) { return lhs.mIt == rhs.mIt; }
204
            iterator& operator=(const iterator& rhs) 
205
            {
206
               if (&rhs != this)
207
               {
208
                  mIt = rhs.mIt; 
209
                  mRef = rhs.mRef;
210
               }
211
               return *this;
212
            }
213
0
            T& operator*() {return ensureInitialized(*mIt,mRef);}
214
0
            T* operator->() {return &ensureInitialized(*mIt,mRef);}
215
         private:
216
            typename Parsers::iterator mIt;
217
            ParserContainer* mRef;
218
            friend class const_iterator;
219
            friend class ParserContainer;
220
      };
221
222
      /**
223
         @brief A const_iterator class (bidirectional)
224
      */
225
      class const_iterator //: public std::iterator<std::bidirectional_iterator_tag, T> // Note: std::iterator deprecated in C++17 usings below cover same functionality
226
      {
227
         public:
228
            using iterator_category = std::bidirectional_iterator_tag;
229
            using value_type = T;
230
            using difference_type = std::ptrdiff_t;
231
            using pointer = T*;
232
            using reference = T&;
233
234
0
            const_iterator(Parsers::const_iterator i,const ParserContainer* ref) : mIt(i),mRef(ref){}
Unexecuted instantiation: resip::ParserContainer<resip::Token>::const_iterator::const_iterator(std::__1::__wrap_iter<resip::ParserContainerBase::HeaderKit const*>, resip::ParserContainer<resip::Token> const*)
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::const_iterator::const_iterator(std::__1::__wrap_iter<resip::ParserContainerBase::HeaderKit const*>, resip::ParserContainer<resip::NameAddr> const*)
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::const_iterator::const_iterator(std::__1::__wrap_iter<resip::ParserContainerBase::HeaderKit const*>, resip::ParserContainer<resip::Auth> const*)
Unexecuted instantiation: resip::ParserContainer<resip::Via>::const_iterator::const_iterator(std::__1::__wrap_iter<resip::ParserContainerBase::HeaderKit const*>, resip::ParserContainer<resip::Via> const*)
235
            const_iterator(const const_iterator& orig) : mIt(orig.mIt), mRef(orig.mRef) {}
236
            const_iterator(const iterator& orig) : mIt(orig.mIt), mRef(orig.mRef) {}
237
            const_iterator() : mRef(0) {}
238
239
0
            const_iterator operator++() {const_iterator it(++mIt,mRef); return it;}
240
0
            const_iterator operator++(int) {const_iterator it(mIt++,mRef); return it;}
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::const_iterator::operator++(int)
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::const_iterator::operator++(int)
241
            const_iterator operator--() {const_iterator it(--mIt,mRef); return it;}
242
0
            const_iterator operator--(int) {const_iterator it(mIt--,mRef); return it;}
243
0
            friend bool operator!=(const const_iterator& lhs, const const_iterator& rhs) { return lhs.mIt != rhs.mIt; }
Unexecuted instantiation: resip::operator!=(resip::ParserContainer<resip::Token>::const_iterator const&, resip::ParserContainer<resip::Token>::const_iterator const&)
Unexecuted instantiation: resip::operator!=(resip::ParserContainer<resip::NameAddr>::const_iterator const&, resip::ParserContainer<resip::NameAddr>::const_iterator const&)
Unexecuted instantiation: resip::operator!=(resip::ParserContainer<resip::Auth>::const_iterator const&, resip::ParserContainer<resip::Auth>::const_iterator const&)
244
0
            friend bool operator==(const const_iterator& lhs, const const_iterator& rhs) { return lhs.mIt == rhs.mIt; }
245
            const_iterator& operator=(const const_iterator& rhs) 
246
            {
247
               if (&rhs != this)
248
               {
249
                  mIt = rhs.mIt;
250
                  mRef = rhs.mRef;
251
               }
252
               return *this;
253
            }
254
            const_iterator& operator=(const iterator& rhs) 
255
            {
256
               mIt = rhs.mIt; 
257
               mRef = rhs.mRef;
258
               return *this;
259
            }
260
0
            const T& operator*() {return ensureInitialized(*mIt,mRef);}
261
0
            const T* operator->() {return &ensureInitialized(*mIt,mRef);}
Unexecuted instantiation: resip::ParserContainer<resip::Token>::const_iterator::operator->()
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::const_iterator::operator->()
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::const_iterator::operator->()
Unexecuted instantiation: resip::ParserContainer<resip::Via>::const_iterator::operator->()
262
         private:
263
            friend class iterator;
264
            typename Parsers::const_iterator mIt;
265
            const ParserContainer* mRef;
266
      };
267
268
      /**
269
         @brief Returns an iterator pointing to the first header field value.
270
      */
271
0
      iterator begin() { return iterator(mParsers.begin(),this); }
272
273
      /**
274
         @brief Returns an iterator pointing to the last header field value.
275
      */
276
0
      iterator end() { return iterator(mParsers.end(),this); }
277
278
      /**
279
         @brief Erases the header field value pointed to by i. Invalidates all
280
            existing iterators.
281
      */
282
      iterator erase(iterator i)
283
      {
284
         freeParser(*i.mIt);
285
         return iterator(mParsers.erase(i.mIt),this);
286
      }
287
288
      /**
289
         @brief Finds the first header field value that matches rhs.
290
      */
291
      bool find(const T& rhs) const
292
      {
293
         for (typename Parsers::const_iterator i = mParsers.begin();
294
              i != mParsers.end(); ++i)
295
         {
296
            // operator== defined by default, but often not usefully
297
            if (rhs.isEqual(ensureInitialized(*i,this)))
298
            {
299
               return true;
300
            }
301
         }
302
303
         return false;
304
      }
305
306
      /**
307
         @brief Triggers a parse of all contained header field values.
308
         @throw ParseException if any header field value is malformed.
309
      */
310
      virtual void parseAll()
311
0
      {
312
0
         for (typename Parsers::const_iterator i = mParsers.begin();
313
0
              i != mParsers.end(); ++i)
314
0
         {
315
0
            ensureInitialized(*i,this).checkParsed();
316
0
         }
317
0
      }
Unexecuted instantiation: resip::ParserContainer<resip::Token>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::StringCategory>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::PrivacyCategory>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::Mime>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::GenericUri>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::UInt32Category>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::ExpiresCategory>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::CallID>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::CSeqCategory>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::DateCategory>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::WarningCategory>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::RAckCategory>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::Via>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::TokenOrQuotedStringCategory>::parseAll()
Unexecuted instantiation: resip::ParserContainer<resip::IdentityCategory>::parseAll()
318
319
      /**
320
         @brief Returns a const_iterator pointing to the first header field 
321
            value.
322
      */
323
0
      const_iterator begin() const { return const_iterator(mParsers.begin(),this); }
Unexecuted instantiation: resip::ParserContainer<resip::Token>::begin() const
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::begin() const
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::begin() const
Unexecuted instantiation: resip::ParserContainer<resip::Via>::begin() const
324
325
      /**
326
         @brief Returns a const_iterator pointing to the first header field 
327
            value.
328
      */
329
0
      const_iterator end() const { return const_iterator(mParsers.end(),this); }
Unexecuted instantiation: resip::ParserContainer<resip::Token>::end() const
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::end() const
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::end() const
Unexecuted instantiation: resip::ParserContainer<resip::Via>::end() const
330
331
      /**
332
         @brief Clones this container, and all contained header field values.
333
      */
334
      virtual ParserContainerBase* clone() const
335
0
      {
336
0
         return new ParserContainer(*this);
337
0
      }
Unexecuted instantiation: resip::ParserContainer<resip::Token>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::StringCategory>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::PrivacyCategory>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::Mime>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::GenericUri>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::UInt32Category>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::ExpiresCategory>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::CallID>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::CSeqCategory>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::DateCategory>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::WarningCategory>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::RAckCategory>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::Via>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::TokenOrQuotedStringCategory>::clone() const
Unexecuted instantiation: resip::ParserContainer<resip::IdentityCategory>::clone() const
338
339
   private:
340
      friend class ParserContainer<T>::iterator;
341
      friend class ParserContainer<T>::const_iterator;
342
343
      /**
344
         @internal
345
      */
346
      static T& ensureInitialized(HeaderKit& kit, ParserContainer* ref)
347
3.62k
      {
348
3.62k
         if(!kit.pc)
349
301
         {
350
301
            if(ref)
351
301
            {
352
301
               PoolBase* pool(ref->mPool);
353
301
               kit.pc=new (pool) T(kit.hfv, ref->mType, pool);
354
301
            }
355
0
            else
356
0
            {
357
0
               kit.pc=new T(kit.hfv, Headers::NONE);
358
0
            }
359
301
         }
360
3.62k
         return *static_cast<T*>(kit.pc);
361
3.62k
      }
Unexecuted instantiation: resip::ParserContainer<resip::Token>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::Token>*)
Unexecuted instantiation: resip::ParserContainer<resip::StringCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::StringCategory>*)
Unexecuted instantiation: resip::ParserContainer<resip::Mime>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::Mime>*)
Unexecuted instantiation: resip::ParserContainer<resip::GenericUri>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::GenericUri>*)
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::NameAddr>*)
resip::ParserContainer<resip::UInt32Category>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::UInt32Category>*)
Line
Count
Source
347
3.62k
      {
348
3.62k
         if(!kit.pc)
349
301
         {
350
301
            if(ref)
351
301
            {
352
301
               PoolBase* pool(ref->mPool);
353
301
               kit.pc=new (pool) T(kit.hfv, ref->mType, pool);
354
301
            }
355
0
            else
356
0
            {
357
0
               kit.pc=new T(kit.hfv, Headers::NONE);
358
0
            }
359
301
         }
360
3.62k
         return *static_cast<T*>(kit.pc);
361
3.62k
      }
Unexecuted instantiation: resip::ParserContainer<resip::ExpiresCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::ExpiresCategory>*)
Unexecuted instantiation: resip::ParserContainer<resip::CallID>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::CallID>*)
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::Auth>*)
Unexecuted instantiation: resip::ParserContainer<resip::CSeqCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::CSeqCategory>*)
Unexecuted instantiation: resip::ParserContainer<resip::DateCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::DateCategory>*)
Unexecuted instantiation: resip::ParserContainer<resip::RAckCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::RAckCategory>*)
Unexecuted instantiation: resip::ParserContainer<resip::Via>::ensureInitialized(resip::ParserContainerBase::HeaderKit&, resip::ParserContainer<resip::Via>*)
362
363
      static const T& ensureInitialized(const HeaderKit& kit, 
364
                                 const ParserContainer* ref)
365
0
      {
366
0
         if(!kit.pc)
367
0
         {
368
0
            HeaderKit& nc_kit(const_cast<HeaderKit&>(kit));
369
0
            if(ref)
370
0
            {
371
0
               ParserContainer* nc_ref(const_cast<ParserContainer*>(ref));
372
0
               PoolBase* pool(nc_ref->mPool);
373
0
               nc_kit.pc=new (pool) T(kit.hfv, ref->mType, pool);
374
0
            }
375
0
            else
376
0
            {
377
0
               nc_kit.pc=new T(kit.hfv, Headers::NONE);
378
0
            }
379
0
         }
380
0
         return *static_cast<T*>(kit.pc);
381
0
      }
Unexecuted instantiation: resip::ParserContainer<resip::Token>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::Token> const*)
Unexecuted instantiation: resip::ParserContainer<resip::NameAddr>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::NameAddr> const*)
Unexecuted instantiation: resip::ParserContainer<resip::StringCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::StringCategory> const*)
Unexecuted instantiation: resip::ParserContainer<resip::PrivacyCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::PrivacyCategory> const*)
Unexecuted instantiation: resip::ParserContainer<resip::Mime>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::Mime> const*)
Unexecuted instantiation: resip::ParserContainer<resip::GenericUri>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::GenericUri> const*)
Unexecuted instantiation: resip::ParserContainer<resip::UInt32Category>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::UInt32Category> const*)
Unexecuted instantiation: resip::ParserContainer<resip::ExpiresCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::ExpiresCategory> const*)
Unexecuted instantiation: resip::ParserContainer<resip::CallID>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::CallID> const*)
Unexecuted instantiation: resip::ParserContainer<resip::Auth>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::Auth> const*)
Unexecuted instantiation: resip::ParserContainer<resip::CSeqCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::CSeqCategory> const*)
Unexecuted instantiation: resip::ParserContainer<resip::DateCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::DateCategory> const*)
Unexecuted instantiation: resip::ParserContainer<resip::WarningCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::WarningCategory> const*)
Unexecuted instantiation: resip::ParserContainer<resip::RAckCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::RAckCategory> const*)
Unexecuted instantiation: resip::ParserContainer<resip::Via>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::Via> const*)
Unexecuted instantiation: resip::ParserContainer<resip::TokenOrQuotedStringCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::TokenOrQuotedStringCategory> const*)
Unexecuted instantiation: resip::ParserContainer<resip::IdentityCategory>::ensureInitialized(resip::ParserContainerBase::HeaderKit const&, resip::ParserContainer<resip::IdentityCategory> const*)
382
};
383
384
template <class T>
385
EncodeStream&
386
insert(EncodeStream& s, const resip::ParserContainer<T>& c)
387
{
388
   s << "[";
389
   for (typename resip::ParserContainer <T>::const_iterator i = c.begin();
390
        i != c.end(); i++) 
391
   {
392
      if (i != c.begin()) 
393
      {
394
         s << ", ";
395
      }
396
      // recurse
397
      insert(s, *i);
398
   }
399
   s << "]";
400
   return s;
401
}
402
 
403
}
404
405
#endif
406
407
/* ====================================================================
408
 * The Vovida Software License, Version 1.0 
409
 * 
410
 * Copyright (c) 2026 SIP Spectrum, Inc. https://www.sipspectrum.com
411
 * Copyright (c) 2000-2005 Vovida Networks, Inc.  All rights reserved.
412
 * 
413
 * Redistribution and use in source and binary forms, with or without
414
 * modification, are permitted provided that the following conditions
415
 * are met:
416
 * 
417
 * 1. Redistributions of source code must retain the above copyright
418
 *    notice, this list of conditions and the following disclaimer.
419
 * 
420
 * 2. Redistributions in binary form must reproduce the above copyright
421
 *    notice, this list of conditions and the following disclaimer in
422
 *    the documentation and/or other materials provided with the
423
 *    distribution.
424
 * 
425
 * 3. The names "VOCAL", "Vovida Open Communication Application Library",
426
 *    and "Vovida Open Communication Application Library (VOCAL)" must
427
 *    not be used to endorse or promote products derived from this
428
 *    software without prior written permission. For written
429
 *    permission, please contact vocal@vovida.org.
430
 *
431
 * 4. Products derived from this software may not be called "VOCAL", nor
432
 *    may "VOCAL" appear in their name, without prior written
433
 *    permission of Vovida Networks, Inc.
434
 * 
435
 * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESSED OR IMPLIED
436
 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
437
 * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, TITLE AND
438
 * NON-INFRINGEMENT ARE DISCLAIMED.  IN NO EVENT SHALL VOVIDA
439
 * NETWORKS, INC. OR ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT DAMAGES
440
 * IN EXCESS OF $1,000, NOR FOR ANY INDIRECT, INCIDENTAL, SPECIAL,
441
 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
442
 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
443
 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
444
 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
445
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
446
 * USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
447
 * DAMAGE.
448
 * 
449
 * ====================================================================
450
 * 
451
 * This software consists of voluntary contributions made by Vovida
452
 * Networks, Inc. and many individuals on behalf of Vovida Networks,
453
 * Inc.  For more information on Vovida Networks, Inc., please see
454
 * <http://www.vovida.org/>.
455
 *
456
 */