servlib/prophet/BundleTLVEntryList.h
changeset 0 2b3e5ec03512
equal deleted inserted replaced
-1:000000000000 0:2b3e5ec03512
       
     1 /*
       
     2  *    Copyright 2007 Baylor University
       
     3  *
       
     4  *    Licensed under the Apache License, Version 2.0 (the "License");
       
     5  *    you may not use this file except in compliance with the License.
       
     6  *    You may obtain a copy of the License at
       
     7  *
       
     8  *        http://www.apache.org/licenses/LICENSE-2.0
       
     9  *
       
    10  *    Unless required by applicable law or agreed to in writing, software
       
    11  *    distributed under the License is distributed on an "AS IS" BASIS,
       
    12  *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
       
    13  *    See the License for the specific language governing permissions and
       
    14  *    limitations under the License.
       
    15  */
       
    16 
       
    17 #ifndef _PROPHET_BUNDLE_ENTRY_LIST_H_
       
    18 #define _PROPHET_BUNDLE_ENTRY_LIST_H_
       
    19 
       
    20 #include <map>
       
    21 #include <string>
       
    22 
       
    23 #include "PointerList.h"
       
    24 #include "BundleTLVEntry.h"
       
    25 #include "Dictionary.h"
       
    26 #include "Table.h"
       
    27 
       
    28 namespace prophet
       
    29 {
       
    30 
       
    31 /**
       
    32  * BundleEntryList is the in-memory representation of the Bundle offer that
       
    33  * is exchanged between peers as Bundle TLV.
       
    34  */
       
    35 template <class BundleEntryType>
       
    36 class BundleEntryList
       
    37 {
       
    38 public:
       
    39     typedef PointerList<BundleEntryType> List;
       
    40     typedef typename PointerList<BundleEntryType>::iterator
       
    41         iterator;
       
    42     typedef typename PointerList<BundleEntryType>::const_iterator
       
    43         const_iterator;
       
    44 
       
    45     /**
       
    46      * Default constructor
       
    47      */
       
    48     BundleEntryList(BundleTLVEntry::bundle_entry_t type =
       
    49             BundleTLVEntry::UNDEFINED)
       
    50         : type_(type) {}
       
    51 
       
    52     /**
       
    53      * Copy constructor
       
    54      */
       
    55     BundleEntryList(const BundleEntryList& list)
       
    56         : type_(list.type_), list_(list.list_) {}
       
    57 
       
    58     /**
       
    59      * Destructor
       
    60      */
       
    61     virtual ~BundleEntryList() { list_.clear(); }
       
    62 
       
    63     /**
       
    64      * Return number of Bundle offers in list 
       
    65      */
       
    66     size_t size() const { return list_.size(); }
       
    67 
       
    68     /**
       
    69      * Return whether list is empty 
       
    70      */
       
    71     bool empty() const { return list_.empty(); }
       
    72 
       
    73     /**
       
    74      * Remove all entries from internal list
       
    75      */
       
    76     void clear() { list_.clear(); }
       
    77 
       
    78     /**
       
    79      * Add a Bundle entry to this list; return whether successful
       
    80      */
       
    81     bool add_entry(const BundleEntryType* entry)
       
    82     {
       
    83         // weed out the oddball
       
    84         if (entry == NULL) return false;
       
    85 
       
    86         // pass on the parameters to the "other" add_entry
       
    87         return add_entry(entry->type(), entry->creation_ts(),
       
    88                          entry->seqno(), entry->sid(),
       
    89                          entry->custody(), entry->accept(),
       
    90                          entry->ack());
       
    91     }
       
    92 
       
    93     /**
       
    94      * Remove entry from Bundle offer list; returns true if found (and
       
    95      * removed) else false if it did not exist
       
    96      */
       
    97     bool remove_entry(u_int32_t cts, u_int32_t seq, u_int16_t sid)
       
    98     {
       
    99         // walk the list in search of these unique identifiers
       
   100         for (iterator i = list_.begin(); i != list_.end(); i++)
       
   101         {
       
   102             if ((*i)->creation_ts() == cts &&
       
   103                 (*i)->seqno() == seq &&
       
   104                 (*i)->sid() == sid)
       
   105             {
       
   106                 // erase if found
       
   107                 list_.erase(i);
       
   108                 return true;
       
   109             }
       
   110         }
       
   111         // not found
       
   112         return false;
       
   113     }
       
   114 
       
   115     /**
       
   116      * Return pointer to entry if found, else return NULL
       
   117      */
       
   118     const BundleEntryType* find(u_int32_t cts,
       
   119                                 u_int32_t seq,
       
   120                                 u_int16_t sid) const
       
   121     {
       
   122         BundleEntryType* bo = NULL;
       
   123         for (const_iterator i = list_.begin(); i != list_.end(); i++)
       
   124         {
       
   125             if ((*i)->creation_ts() == cts &&
       
   126                 (*i)->seqno() == seq &&
       
   127                 (*i)->sid() == sid)
       
   128             {
       
   129                 bo = *i;
       
   130                 break;
       
   131             }
       
   132         }
       
   133         return bo;
       
   134     }
       
   135 
       
   136     /**
       
   137      * Return type of entries hosted by this list
       
   138      */
       
   139     BundleTLVEntry::bundle_entry_t type() const { return type_; }
       
   140 
       
   141     ///@{ These iterators are not thread safe
       
   142     iterator begin() { return list_.begin(); }
       
   143     iterator end() { return list_.end(); }
       
   144     const_iterator begin() const { return (const_iterator) list_.begin(); }
       
   145     const_iterator end() const { return (const_iterator) list_.end(); }
       
   146     ///@}
       
   147 
       
   148     /**
       
   149      * Convenience method to access first entry in list, or NULL if empty
       
   150      */
       
   151     const BundleEntryType* front() const { return list_.front(); }
       
   152 
       
   153     /**
       
   154      * Convenience method to access last entry in list, or NULL if empty
       
   155      */
       
   156     const BundleEntryType* back() const { return list_.back(); }
       
   157 
       
   158     /**
       
   159      * Estimate serialized buffer length
       
   160      */
       
   161     size_t guess_size(size_t BOEsz) const { return BOEsz * size(); }
       
   162 
       
   163     /**
       
   164      * Assignment operator
       
   165      */
       
   166     BundleEntryList& operator= (const BundleEntryList& list) 
       
   167     {
       
   168         list_ = list.list_;
       
   169         type_ = list.type_;
       
   170         return *this;
       
   171     }
       
   172 
       
   173 protected:
       
   174     /**
       
   175      * Convenience method for adding new entry to this Bundle offer list,
       
   176      * return whether successful
       
   177      */
       
   178     bool add_entry(BundleTLVEntry::bundle_entry_t type,
       
   179                    u_int32_t cts, u_int32_t seq, u_int16_t sid,
       
   180                    bool custody=false,
       
   181                    bool accept=false,
       
   182                    bool ack=false)
       
   183     {
       
   184         // there can only be one type in this list, and UNDEFINED
       
   185         // isn't one of them
       
   186         if (type_ == BundleTLVEntry::UNDEFINED)
       
   187             return false;
       
   188         else if (type_ != type)
       
   189             return false;
       
   190 
       
   191         // attempt to create new entry
       
   192         BundleTLVEntry* b =
       
   193             BundleTLVEntry::create_entry(cts,seq,sid,custody,accept,ack);
       
   194 
       
   195         // fail out on error
       
   196         if (b == NULL)
       
   197             return false;
       
   198         else
       
   199         if (type_ != b->type())
       
   200         {
       
   201             delete b;
       
   202             return false;
       
   203         }
       
   204 
       
   205         // push back upon success
       
   206         return push_back(dynamic_cast<BundleEntryType*>(b));
       
   207     }
       
   208 
       
   209     /**
       
   210      * Add entry to back of list
       
   211      */
       
   212     virtual bool push_back(BundleEntryType* bo) = 0;
       
   213 
       
   214     BundleTLVEntry::bundle_entry_t type_; ///< type of Bundle entry in list
       
   215     List list_;
       
   216 }; // class BundleEntryList
       
   217 
       
   218 /**
       
   219  * In-memory representation of list of bundle offer entries
       
   220  * from a Bundle TLV sent by WAIT_RIB or OFFER
       
   221  */
       
   222 class BundleOfferList : public BundleEntryList<BundleOfferEntry>
       
   223 {
       
   224 public:
       
   225     /**
       
   226      * Constructor
       
   227      */
       
   228     BundleOfferList()
       
   229         : BundleEntryList<BundleOfferEntry>(BundleTLVEntry::OFFER) {}
       
   230 
       
   231     /**
       
   232      * Destructor
       
   233      */
       
   234     virtual ~BundleOfferList() {}
       
   235 
       
   236     /**
       
   237      * Convenience method to add Bundle to the list; return
       
   238      * whether successful
       
   239      */
       
   240     bool add_offer(const Bundle* b, u_int16_t sid)
       
   241     {
       
   242         // weed out the oddball
       
   243         if (b == NULL) return false;
       
   244 
       
   245         return add_offer(b->creation_ts(),
       
   246                          b->sequence_num(),
       
   247                          sid,
       
   248                          b->custody_requested(),
       
   249                          false);
       
   250     }
       
   251 
       
   252     /**
       
   253      * Convenience wrapper around base class's add_entry
       
   254      */
       
   255     bool add_offer(u_int32_t cts,
       
   256                    u_int32_t seq,
       
   257                    u_int16_t sid,
       
   258                    bool custody,
       
   259                    bool ack)
       
   260     {
       
   261         return
       
   262             add_entry(BundleTLVEntry::OFFER,cts,seq,sid,custody,false,ack);
       
   263     }
       
   264 protected:
       
   265     virtual bool push_back(BundleOfferEntry* b)
       
   266     {
       
   267         if (b == NULL) return false;
       
   268         if (find(b->creation_ts(),b->seqno(),b->sid()) == NULL)
       
   269         {
       
   270             list_.push_back(b);
       
   271             return true;
       
   272         }
       
   273         return false;
       
   274     }
       
   275 }; // class BundleOfferList 
       
   276 
       
   277 /**
       
   278  * In-memory representation of list of bundle response entries
       
   279  * from a Bundle TLV sent by SEND_DR or REQUEST
       
   280  */
       
   281 class BundleResponseList : public BundleEntryList<BundleResponseEntry>
       
   282 {
       
   283 public:
       
   284     /**
       
   285      * Constructor
       
   286      */
       
   287     BundleResponseList()
       
   288         : BundleEntryList<BundleResponseEntry>(BundleTLVEntry::RESPONSE) {}
       
   289 
       
   290     /**
       
   291      * Destructor
       
   292      */
       
   293     virtual ~BundleResponseList() {}
       
   294 
       
   295     /**
       
   296      * Convenience wrapper around base class's add_entry
       
   297      */
       
   298     bool add_response(u_int32_t cts,
       
   299                       u_int32_t seq,
       
   300                       u_int16_t sid,
       
   301                       bool custody, 
       
   302                       bool accept = true)
       
   303     {
       
   304         return
       
   305             add_entry(BundleTLVEntry::RESPONSE,cts,seq,sid,custody,accept,false);
       
   306     }
       
   307 protected:
       
   308     virtual bool push_back(BundleResponseEntry* b)
       
   309     {
       
   310         if (b == NULL) return false;
       
   311         if (find(b->creation_ts(),b->seqno(),b->sid()) == NULL)
       
   312         {
       
   313             list_.push_back(b);
       
   314             return true;
       
   315         }
       
   316         return false;
       
   317     }
       
   318 }; // class BundleResponseList 
       
   319 
       
   320 }; // namespace prophet
       
   321 
       
   322 #endif // _PROPHET_BUNDLE_ENTRY_LIST_H_