LCOV - code coverage report
Current view: top level - buildbot/coverage/build/src/context - cdqueue.h (source / functions) Hit Total Coverage
Test: coverage.info Lines: 40 40 100.0 %
Date: 2024-10-22 11:38:46 Functions: 53 65 81.5 %
Branches: 14 30 46.7 %

           Branch data     Line data    Source code
       1                 :            : /******************************************************************************
       2                 :            :  * Top contributors (to current version):
       3                 :            :  *   Tim King, Francois Bobot, Mathias Preiner
       4                 :            :  *
       5                 :            :  * This file is part of the cvc5 project.
       6                 :            :  *
       7                 :            :  * Copyright (c) 2009-2024 by the authors listed in the file AUTHORS
       8                 :            :  * in the top-level source directory and their institutional affiliations.
       9                 :            :  * All rights reserved.  See the file COPYING in the top-level source
      10                 :            :  * directory for licensing information.
      11                 :            :  * ****************************************************************************
      12                 :            :  *
      13                 :            :  * Context-dependent First-In-First-Out queue class.
      14                 :            :  *
      15                 :            :  * This implementation may discard elements which are enqueued and dequeued
      16                 :            :  * at the same context level.
      17                 :            :  *
      18                 :            :  * The implementation is based on a CDList with one additional size_t
      19                 :            :  * for tracking the next element to dequeue from the list and additional
      20                 :            :  * size_t for tracking the previous size of the list.
      21                 :            :  */
      22                 :            : 
      23                 :            : #include "cvc5_private.h"
      24                 :            : 
      25                 :            : #ifndef CVC5__CONTEXT__CDQUEUE_H
      26                 :            : #define CVC5__CONTEXT__CDQUEUE_H
      27                 :            : 
      28                 :            : #include "context/context.h"
      29                 :            : #include "context/cdlist.h"
      30                 :            : 
      31                 :            : namespace cvc5::context {
      32                 :            : 
      33                 :            : template <class T, class CleanUp = DefaultCleanUp<T>, class Allocator = std::allocator<T> >
      34                 :            : class CDQueue;
      35                 :            : 
      36                 :            : /** We don't define a template with Allocator for the first implementation */
      37                 :            : template <class T, class CleanUp, class Allocator>
      38                 :            : class CDQueue : public CDList<T, CleanUp, Allocator> {
      39                 :            : private:
      40                 :            :   typedef CDList<T, CleanUp, Allocator> ParentType;
      41                 :            : 
      42                 :            : protected:
      43                 :            : 
      44                 :            :   /** Points to the next element in the current context to dequeue. */
      45                 :            :   size_t d_iter;
      46                 :            : 
      47                 :            :   /** Points to the size at the last save. */
      48                 :            :   size_t d_lastsave;
      49                 :            : 
      50                 :            :   /**
      51                 :            :    * Private copy constructor used only by save().
      52                 :            :    */
      53                 :   15011165 :   CDQueue(const CDQueue<T, CleanUp, Allocator>& l):
      54                 :            :     ParentType(l),
      55                 :   15011165 :     d_iter(l.d_iter),
      56                 :   15011165 :     d_lastsave(l.d_lastsave) {}
      57                 :            : 
      58                 :            :   /** Implementation of mandatory ContextObj method save:
      59                 :            :    *  We assume that the base class do the job inside their copy constructor.
      60                 :            :    */
      61                 :   15011165 :   ContextObj* save(ContextMemoryManager* pCMM) override
      62                 :            :   {
      63                 :   15011165 :     ContextObj* data = new(pCMM) CDQueue<T, CleanUp, Allocator>(*this);
      64                 :            :     // We save the d_size in d_lastsave and we should never destruct below this
      65                 :            :     // indices before the corresponding restore.
      66                 :   15011165 :     d_lastsave = ParentType::d_size;
      67                 :   15011165 :     return data;
      68                 :            :   }
      69                 :            : 
      70                 :            :   /**
      71                 :            :    * Implementation of mandatory ContextObj method restore: simply
      72                 :            :    * restores the previous size, iter and lastsave indices. Note that
      73                 :            :    * the list pointer and the allocated size are not changed.
      74                 :            :    */
      75                 :   15010881 :   void restore(ContextObj* data) override
      76                 :            :   {
      77                 :   15010881 :     CDQueue<T, CleanUp, Allocator>* qdata = static_cast<CDQueue<T, CleanUp, Allocator>*>(data);
      78                 :   15010881 :     d_iter = qdata->d_iter;
      79                 :   15010881 :     d_lastsave = qdata->d_lastsave;
      80                 :   15010881 :     ParentType::restore(data);
      81                 :   15010881 :   }
      82                 :            : 
      83                 :            : 
      84                 :            : 
      85                 :            : public:
      86                 :            : 
      87                 :            :   /** Creates a new CDQueue associated with the current context. */
      88                 :     571125 :  CDQueue(Context* context,
      89                 :            :          bool callCleanup = true,
      90                 :            :          const CleanUp& cleanup = CleanUp(),
      91                 :            :          const Allocator& alloc = Allocator())
      92                 :     571125 :      : ParentType(context, callCleanup, cleanup), d_iter(0), d_lastsave(0)
      93                 :            :  {
      94                 :     571125 :  }
      95                 :            : 
      96                 :            :  /** Returns true if the queue is empty in the current context. */
      97                 :  294729347 :  bool empty() const
      98                 :            :  {
      99 [ -  + ][ -  + ]:  294729347 :    Assert(d_iter <= ParentType::d_size);
                 [ -  - ]
     100                 :  294729347 :    return d_iter == ParentType::d_size;
     101                 :            :   }
     102                 :            : 
     103                 :            :   /** Returns the number of elements that have not been dequeued in the context. */
     104                 :      68131 :   size_t size() const{
     105                 :      68131 :     return ParentType::d_size - d_iter;
     106                 :            :   }
     107                 :            : 
     108                 :            :   /** Enqueues an element in the current context. */
     109                 :   65520360 :   void push(const T& data){
     110                 :   65520360 :     ParentType::push_back(data);
     111                 :   65520360 :   }
     112                 :            : 
     113                 :            :   /**
     114                 :            :    * Delete next element. The destructor of this object will be
     115                 :            :    * called eventually but not necessarily during the call of this
     116                 :            :    * function.
     117                 :            :    */
     118                 :   63070104 :   void pop(){
     119 [ -  + ][ -  + ]:   63070104 :     Assert(!empty()) << "Attempting to pop from an empty queue.";
                 [ -  - ]
     120                 :   63070104 :     ParentType::makeCurrent();
     121                 :   63070104 :     d_iter = d_iter + 1;
     122 [ +  + ][ +  + ]:   63070104 :     if (empty() && d_lastsave != ParentType::d_size) {
                 [ +  + ]
     123                 :            :       // Some elements have been enqueued and dequeued in the same
     124                 :            :       // context and now the queue is empty we can destruct them.
     125                 :   14260599 :       ParentType::truncateList(d_lastsave);
     126 [ -  + ][ -  + ]:   14260599 :       Assert(ParentType::d_size == d_lastsave);
                 [ -  - ]
     127                 :   14260599 :       d_iter = d_lastsave;
     128                 :            :     }
     129                 :   63070104 :   }
     130                 :            : 
     131                 :            :   /** Returns a reference to the next element on the queue. */
     132                 :   63070104 :   const T& front() const{
     133 [ -  + ][ -  + ]:   63070104 :     Assert(!empty()) << "No front in an empty queue.";
                 [ -  - ]
     134                 :   63070104 :     return ParentType::d_list[d_iter];
     135                 :            :   }
     136                 :            : 
     137                 :            :   /**
     138                 :            :    * Returns the most recent item added to the queue.
     139                 :            :    */
     140                 :            :   const T& back() const {
     141                 :            :     Assert(!empty()) << "CDQueue::back() called on empty list";
     142                 :            :     return ParentType::d_list[ParentType::d_size - 1];
     143                 :            :   }
     144                 :            : 
     145                 :            :   typedef typename ParentType::const_iterator const_iterator;
     146                 :            : 
     147                 :     105627 :   const_iterator begin() const {
     148                 :     105627 :     return ParentType::begin() + d_iter;
     149                 :            :   }
     150                 :            : 
     151                 :     105627 :   const_iterator end() const {
     152                 :     105627 :     return ParentType::end();
     153                 :            :   }
     154                 :            : 
     155                 :            : };/* class CDQueue<> */
     156                 :            : 
     157                 :            : }  // namespace cvc5::context
     158                 :            : 
     159                 :            : #endif /* CVC5__CONTEXT__CDQUEUE_H */

Generated by: LCOV version 1.14