LTP GCOV extension - code coverage report
Current view: directory - usr/include/apt-pkg - depcache.h
Test: lcov.info
Date: 2008-08-14 Instrumented lines: 6
Code covered: 100.0 % Executed lines: 6

       1                 : // -*- mode: c++; mode: fold -*-
       2                 : // Description                                                          /*{{{*/
       3                 : // $Id: depcache.h,v 1.14 2001/02/20 07:03:17 jgg Exp $
       4                 : /* ######################################################################
       5                 : 
       6                 :    DepCache - Dependency Extension data for the cache
       7                 :    
       8                 :    This class stores the cache data and a set of extension structures for
       9                 :    monitoring the current state of all the packages. It also generates and
      10                 :    caches the 'install' state of many things. This refers to the state of the
      11                 :    package after an install has been run.
      12                 : 
      13                 :    The StateCache::State field can be -1,0,1,2 which is <,=,>,no current.
      14                 :    StateCache::Mode is which of the 3 fields is active.
      15                 :    
      16                 :    This structure is important to support the readonly status of the cache 
      17                 :    file. When the data is saved the cache will be refereshed from our 
      18                 :    internal rep and written to disk. Then the actual persistant data 
      19                 :    files will be put on the disk.
      20                 : 
      21                 :    Each dependency is compared against 3 target versions to produce to
      22                 :    3 dependency results.
      23                 :      Now - Compared using the Currently install version
      24                 :      Install - Compared using the install version (final state)
      25                 :      CVer - (Candidate Verion) Compared using the Candidate Version
      26                 :    The candidate and now results are used to decide wheather a package
      27                 :    should be automatically installed or if it should be left alone.
      28                 :    
      29                 :    Remember, the Candidate Version is selected based on the distribution
      30                 :    settings for the Package. The Install Version is selected based on the
      31                 :    state (Delete, Keep, Install) field and can be either the Current Version
      32                 :    or the Candidate version.
      33                 :    
      34                 :    The Candidate version is what is shown the 'Install Version' field.
      35                 :    
      36                 :    ##################################################################### */
      37                 :                                                                         /*}}}*/
      38                 : #ifndef PKGLIB_DEPCACHE_H
      39                 : #define PKGLIB_DEPCACHE_H
      40                 : 
      41                 : 
      42                 : #include <apt-pkg/pkgcache.h>
      43                 : #include <apt-pkg/progress.h>
      44                 : 
      45                 : #include <regex.h>
      46                 : 
      47                 : #include <vector>
      48                 : #include <memory>
      49                 : 
      50                 : class pkgDepCache : protected pkgCache::Namespace
      51                 : {
      52                 :    public:
      53                 : 
      54                 :    /** \brief An arbitrary predicate on packages. */
      55                 :    class InRootSetFunc
      56                 :    {
      57                 :    public:
      58                 :      virtual bool InRootSet(const pkgCache::PkgIterator &pkg) {return false;};
      59                 :      virtual ~InRootSetFunc() {};
      60                 :    };
      61                 : 
      62                 :    private:
      63                 :    /** \brief Mark a single package and all its unmarked important
      64                 :     *  dependencies during mark-and-sweep.
      65                 :     *
      66                 :     *  Recursively invokes itself to mark all dependencies of the
      67                 :     *  package.
      68                 :     *
      69                 :     *  \param pkg The package to mark.
      70                 :     *
      71                 :     *  \param ver The version of the package that is to be marked.
      72                 :     *
      73                 :     *  \param follow_recommends If \b true, recommendations of the
      74                 :     *  package will be recursively marked.
      75                 :     *
      76                 :     *  \param follow_suggests If \b true, suggestions of the package
      77                 :     *  will be recursively marked.
      78                 :     */
      79                 :    void MarkPackage(const pkgCache::PkgIterator &pkg,
      80                 :                     const pkgCache::VerIterator &ver,
      81                 :                     bool follow_recommends,
      82                 :                     bool follow_suggests);
      83                 : 
      84                 :    /** \brief Update the Marked field of all packages.
      85                 :     *
      86                 :     *  Each package's StateCache::Marked field will be set to \b true
      87                 :     *  if and only if it can be reached from the root set.  By
      88                 :     *  default, the root set consists of the set of manually installed
      89                 :     *  or essential packages, but it can be extended using the
      90                 :     *  parameter #rootFunc.
      91                 :     *
      92                 :     *  \param rootFunc A callback that can be used to add extra
      93                 :     *  packages to the root set.
      94                 :     *
      95                 :     *  \return \b false if an error occurred.
      96                 :     */
      97                 :    bool MarkRequired(InRootSetFunc &rootFunc);
      98                 : 
      99                 :    /** \brief Set the StateCache::Garbage flag on all packages that
     100                 :     *  should be removed.
     101                 :     *
     102                 :     *  Packages that were not marked by the last call to #MarkRequired
     103                 :     *  are tested to see whether they are actually garbage.  If so,
     104                 :     *  they are marked as such.
     105                 :     *
     106                 :     *  \return \b false if an error occurred.
     107                 :     */
     108                 :    bool Sweep();
     109                 : 
     110                 :    public:
     111                 :    
     112                 :    // These flags are used in DepState
     113                 :    enum DepFlags {DepNow = (1 << 0),DepInstall = (1 << 1),DepCVer = (1 << 2),
     114                 :                   DepGNow = (1 << 3),DepGInstall = (1 << 4),DepGCVer = (1 << 5)};
     115                 : 
     116                 :    // These flags are used in StateCache::DepState
     117                 :    enum DepStateFlags {DepNowPolicy = (1 << 0), DepNowMin = (1 << 1),
     118                 :                        DepInstPolicy = (1 << 2), DepInstMin = (1 << 3),
     119                 :                        DepCandPolicy = (1 << 4), DepCandMin = (1 << 5)};
     120                 :    
     121                 :    // These flags are used in StateCache::iFlags
     122                 :    enum InternalFlags {AutoKept = (1 << 0), Purge = (1 << 1), ReInstall = (1 << 2)};
     123                 :       
     124                 :    enum VersionTypes {NowVersion, InstallVersion, CandidateVersion};
     125                 :    enum ModeList {ModeDelete = 0, ModeKeep = 1, ModeInstall = 2};
     126                 : 
     127                 :    /** \brief Represents an active action group.
     128                 :     *
     129                 :     *  An action group is a group of actions that are currently being
     130                 :     *  performed.  While an active group is active, certain routine
     131                 :     *  clean-up actions that would normally be performed after every
     132                 :     *  cache operation are delayed until the action group is
     133                 :     *  completed.  This is necessary primarily to avoid inefficiencies
     134                 :     *  when modifying a large number of packages at once.
     135                 :     *
     136                 :     *  This class represents an active action group.  Creating an
     137                 :     *  instance will create an action group; destroying one will
     138                 :     *  destroy the corresponding action group.
     139                 :     *
     140                 :     *  The following operations are suppressed by this class:
     141                 :     *
     142                 :     *    - Keeping the Marked and Garbage flags up to date.
     143                 :     *
     144                 :     *  \note This can be used in the future to easily accumulate
     145                 :     *  atomic actions for undo or to display "what apt did anyway";
     146                 :     *  e.g., change the counter of how many action groups are active
     147                 :     *  to a std::set of pointers to them and use those to store
     148                 :     *  information about what happened in a group in the group.
     149                 :     */
     150                 :    class ActionGroup
     151                 :    {
     152                 :        pkgDepCache &cache;
     153                 : 
     154                 :        bool released;
     155                 : 
     156                 :        /** Action groups are noncopyable. */
     157                 :        ActionGroup(const ActionGroup &other);
     158                 :    public:
     159                 :        /** \brief Create a new ActionGroup.
     160                 :         *
     161                 :         *  \param cache The cache that this ActionGroup should
     162                 :         *  manipulate.
     163                 :         *
     164                 :         *  As long as this object exists, no automatic cleanup
     165                 :         *  operations will be undertaken.
     166                 :         */
     167                 :        ActionGroup(pkgDepCache &cache);
     168                 : 
     169                 :        /** \brief Clean up the action group before it is destroyed.
     170                 :         *
     171                 :         *  If it is destroyed later, no second cleanup wil be run.
     172                 :         */
     173                 :        void release();
     174                 : 
     175                 :        /** \brief Destroy the action group.
     176                 :         *
     177                 :         *  If this is the last action group, the automatic cache
     178                 :         *  cleanup operations will be undertaken.
     179                 :         */
     180                 :        ~ActionGroup();
     181                 :    };
     182                 : 
     183                 :    /** \brief Returns \b true for packages matching a regular
     184                 :     *  expression in APT::NeverAutoRemove.
     185                 :     */
     186                 :    class DefaultRootSetFunc : public InRootSetFunc
     187                 :    {
     188                 :      std::vector<regex_t *> rootSetRegexp;
     189                 :      bool constructedSuccessfully;
     190                 : 
     191                 :    public:
     192                 :      DefaultRootSetFunc();
     193                 :      ~DefaultRootSetFunc();
     194                 : 
     195                 :      /** \return \b true if the class initialized successfully, \b
     196                 :       *  false otherwise.  Used to avoid throwing an exception, since
     197                 :       *  APT classes generally don't.
     198                 :       */
     199                 :      bool wasConstructedSuccessfully() const { return constructedSuccessfully; }
     200                 : 
     201                 :      bool InRootSet(const pkgCache::PkgIterator &pkg);
     202                 :    };
     203                 : 
     204                 :    struct StateCache
     205                 :    {
     206                 :       // Epoch stripped text versions of the two version fields
     207                 :       const char *CandVersion;
     208                 :       const char *CurVersion;
     209                 : 
     210                 :       // Pointer to the candidate install version. 
     211                 :       Version *CandidateVer;
     212                 : 
     213                 :       // Pointer to the install version.
     214                 :       Version *InstallVer;
     215                 :       
     216                 :       // Copy of Package::Flags
     217                 :       unsigned short Flags;
     218                 :       unsigned short iFlags;           // Internal flags
     219                 : 
     220                 :       /** \brief \b true if this package can be reached from the root set. */
     221                 :       bool Marked;
     222                 : 
     223                 :       /** \brief \b true if this package is unused and should be removed.
     224                 :        *
     225                 :        *  This differs from !#Marked, because it is possible that some
     226                 :        *  unreachable packages will be protected from becoming
     227                 :        *  garbage.
     228                 :        */
     229                 :       bool Garbage;
     230                 : 
     231                 :       // Various tree indicators
     232                 :       signed char Status;              // -1,0,1,2
     233                 :       unsigned char Mode;              // ModeList
     234                 :       unsigned char DepState;          // DepState Flags
     235                 : 
     236                 :       // Update of candidate version
     237                 :       const char *StripEpoch(const char *Ver);
     238                 :       void Update(PkgIterator Pkg,pkgCache &Cache);
     239                 :       
     240                 :       // Various test members for the current status of the package
     241                 :       inline bool NewInstall() const {return Status == 2 && Mode == ModeInstall;};
     242            3785 :       inline bool Delete() const {return Mode == ModeDelete;};
     243            3785 :       inline bool Keep() const {return Mode == ModeKeep;};
     244                 :       inline bool Upgrade() const {return Status > 0 && Mode == ModeInstall;};
     245                 :       inline bool Upgradable() const {return Status >= 1;};
     246                 :       inline bool Downgrade() const {return Status < 0 && Mode == ModeInstall;};
     247                 :       inline bool Held() const {return Status != 0 && Keep();};
     248            3785 :       inline bool NowBroken() const {return (DepState & DepNowMin) != DepNowMin;};
     249                 :       inline bool NowPolicyBroken() const {return (DepState & DepNowPolicy) != DepNowPolicy;};
     250            3785 :       inline bool InstBroken() const {return (DepState & DepInstMin) != DepInstMin;};
     251                 :       inline bool InstPolicyBroken() const {return (DepState & DepInstPolicy) != DepInstPolicy;};
     252            3785 :       inline bool Install() const {return Mode == ModeInstall;};
     253                 :       inline VerIterator InstVerIter(pkgCache &Cache)
     254                 :                 {return VerIterator(Cache,InstallVer);};
     255                 :       inline VerIterator CandidateVerIter(pkgCache &Cache)
     256                 :                 {return VerIterator(Cache,CandidateVer);};
     257                 :    };
     258                 :    
     259                 :    // Helper functions
     260                 :    void BuildGroupOrs(VerIterator const &V);
     261                 :    void UpdateVerState(PkgIterator Pkg);
     262                 : 
     263                 :    // User Policy control
     264                 :    class Policy
     265                 :    {
     266                 :       public:
     267                 :       
     268                 :       virtual VerIterator GetCandidateVer(PkgIterator Pkg);
     269                 :       virtual bool IsImportantDep(DepIterator Dep);
     270                 :       
     271                 :       virtual ~Policy() {};
     272                 :    };
     273                 : 
     274                 :    private:
     275                 :    /** The number of open "action groups"; certain post-action
     276                 :     *  operations are suppressed if this number is > 0.
     277                 :     */
     278                 :    int group_level;
     279                 : 
     280                 :    friend class ActionGroup;
     281                 :      
     282                 :    protected:
     283                 : 
     284                 :    // State information
     285                 :    pkgCache *Cache;
     286                 :    StateCache *PkgState;
     287                 :    unsigned char *DepState;
     288                 :    
     289                 :    double iUsrSize;
     290                 :    double iDownloadSize;
     291                 :    unsigned long iInstCount;
     292                 :    unsigned long iDelCount;
     293                 :    unsigned long iKeepCount;
     294                 :    unsigned long iBrokenCount;
     295                 :    unsigned long iPolicyBrokenCount;
     296                 :    unsigned long iBadCount;
     297                 :    
     298                 :    Policy *delLocalPolicy;           // For memory clean up..
     299                 :    Policy *LocalPolicy;
     300                 :    
     301                 :    // Check for a matching provides
     302                 :    bool CheckDep(DepIterator Dep,int Type,PkgIterator &Res);
     303                 :    inline bool CheckDep(DepIterator Dep,int Type)
     304                 :    {
     305                 :       PkgIterator Res(*this,0);
     306                 :       return CheckDep(Dep,Type,Res);
     307                 :    }
     308                 :    
     309                 :    // Computes state information for deps and versions (w/o storing)
     310                 :    unsigned char DependencyState(DepIterator &D);
     311                 :    unsigned char VersionState(DepIterator D,unsigned char Check,
     312                 :                               unsigned char SetMin,
     313                 :                               unsigned char SetPolicy);
     314                 : 
     315                 :    // Recalculates various portions of the cache, call after changing something
     316                 :    void Update(DepIterator Dep);           // Mostly internal
     317                 :    void Update(PkgIterator const &P);
     318                 :    
     319                 :    // Count manipulators
     320                 :    void AddSizes(const PkgIterator &Pkg,signed long Mult = 1);
     321                 :    inline void RemoveSizes(const PkgIterator &Pkg) {AddSizes(Pkg,-1);};
     322                 :    void AddStates(const PkgIterator &Pkg,int Add = 1);
     323                 :    inline void RemoveStates(const PkgIterator &Pkg) {AddStates(Pkg,-1);};
     324                 :    
     325                 :    public:
     326                 : 
     327                 :    // Legacy.. We look like a pkgCache
     328                 :    inline operator pkgCache &() {return *Cache;};
     329                 :    inline Header &Head() {return *Cache->HeaderP;};
     330                 :    inline PkgIterator PkgBegin() {return Cache->PkgBegin();};
     331                 :    inline PkgIterator FindPkg(string const &Name) {return Cache->FindPkg(Name);};
     332                 : 
     333                 :    inline pkgCache &GetCache() {return *Cache;};
     334                 :    inline pkgVersioningSystem &VS() {return *Cache->VS;};
     335                 :    
     336                 :    // Policy implementation
     337                 :    inline VerIterator GetCandidateVer(PkgIterator Pkg) {return LocalPolicy->GetCandidateVer(Pkg);};
     338                 :    inline bool IsImportantDep(DepIterator Dep) {return LocalPolicy->IsImportantDep(Dep);};
     339                 :    inline Policy &GetPolicy() {return *LocalPolicy;};
     340                 :    
     341                 :    // Accessors
     342            3787 :    inline StateCache &operator [](PkgIterator const &I) {return PkgState[I->ID];};
     343                 :    inline unsigned char &operator [](DepIterator const &I) {return DepState[I->ID];};
     344                 : 
     345                 :    /** \return A function identifying packages in the root set other
     346                 :     *  than manually installed packages and essential packages, or \b
     347                 :     *  NULL if an error occurs.
     348                 :     *
     349                 :     *  \todo Is this the best place for this function?  Perhaps the
     350                 :     *  settings for mark-and-sweep should be stored in a single
     351                 :     *  external class?
     352                 :     */
     353                 :    virtual InRootSetFunc *GetRootSetFunc();
     354                 : 
     355                 :    /** \return \b true if the garbage collector should follow recommendations.
     356                 :     */
     357                 :    virtual bool MarkFollowsRecommends();
     358                 : 
     359                 :    /** \return \b true if the garbage collector should follow suggestions.
     360                 :     */
     361                 :    virtual bool MarkFollowsSuggests();
     362                 : 
     363                 :    /** \brief Update the Marked and Garbage fields of all packages.
     364                 :     *
     365                 :     *  This routine is implicitly invoked after all state manipulators
     366                 :     *  and when an ActionGroup is destroyed.  It invokes #MarkRequired
     367                 :     *  and #Sweep to do its dirty work.
     368                 :     *
     369                 :     *  \param rootFunc A predicate that returns \b true for packages
     370                 :     *  that should be added to the root set.
     371                 :     */
     372                 :    bool MarkAndSweep(InRootSetFunc &rootFunc)
     373                 :    {
     374                 :      return MarkRequired(rootFunc) && Sweep();
     375                 :    }
     376                 : 
     377                 :    bool MarkAndSweep()
     378                 :    {
     379                 :      std::auto_ptr<InRootSetFunc> f(GetRootSetFunc());
     380                 :      if(f.get() != NULL)
     381                 :        return MarkAndSweep(*f.get());
     382                 :      else
     383                 :        return false;
     384                 :    }
     385                 : 
     386                 :    /** \name State Manipulators
     387                 :     */
     388                 :    // @{
     389                 :    void MarkKeep(PkgIterator const &Pkg, bool Soft = false,
     390                 :                  bool FromUser = true);
     391                 :    void MarkDelete(PkgIterator const &Pkg,bool Purge = false);
     392                 :    void MarkInstall(PkgIterator const &Pkg,bool AutoInst = true,
     393                 :                     unsigned long Depth = 0, bool FromUser = true,
     394                 :                     bool ForceImportantDeps = false);
     395                 :    void SetReInstall(PkgIterator const &Pkg,bool To);
     396                 :    void SetCandidateVersion(VerIterator TargetVer);
     397                 : 
     398                 :    /** Set the "is automatically installed" flag of Pkg. */
     399                 :    void MarkAuto(const PkgIterator &Pkg, bool Auto);
     400                 :    // @}
     401                 :    
     402                 :    // This is for debuging
     403                 :    void Update(OpProgress *Prog = 0);
     404                 : 
     405                 :    // read persistent states
     406                 :    bool readStateFile(OpProgress *prog);
     407                 :    bool writeStateFile(OpProgress *prog, bool InstalledOnly=false);
     408                 :    
     409                 :    // Size queries
     410                 :    inline double UsrSize() {return iUsrSize;};
     411                 :    inline double DebSize() {return iDownloadSize;};
     412                 :    inline unsigned long DelCount() {return iDelCount;};
     413                 :    inline unsigned long KeepCount() {return iKeepCount;};
     414                 :    inline unsigned long InstCount() {return iInstCount;};
     415                 :    inline unsigned long BrokenCount() {return iBrokenCount;};
     416                 :    inline unsigned long PolicyBrokenCount() {return iPolicyBrokenCount;};
     417                 :    inline unsigned long BadCount() {return iBadCount;};
     418                 : 
     419                 :    bool Init(OpProgress *Prog);
     420                 :    
     421                 :    pkgDepCache(pkgCache *Cache,Policy *Plcy = 0);
     422                 :    virtual ~pkgDepCache();
     423                 : };
     424                 : 
     425                 : #endif

Generated by: LTP GCOV extension version 1.6