]>
git.saurik.com Git - apt.git/blob - apt-pkg/depcache.cc
5da411e4d0c8a1cef3a1d5afd4971335162c73e9
1 // -*- mode: cpp; mode: fold -*-
3 // $Id: depcache.cc,v 1.25 2001/05/27 05:36:04 jgg Exp $
4 /* ######################################################################
6 Dependency Cache - Caches Dependency information.
8 ##################################################################### */
10 // Include Files /*{{{*/
12 #pragma implementation "apt-pkg/depcache.h"
14 #include <apt-pkg/depcache.h>
15 #include <apt-pkg/version.h>
16 #include <apt-pkg/error.h>
17 #include <apt-pkg/sptr.h>
18 #include <apt-pkg/algorithms.h>
20 #include <apt-pkg/fileutl.h>
21 #include <apt-pkg/configuration.h>
22 #include <apt-pkg/tagfile.h>
27 // DepCache::pkgDepCache - Constructors /*{{{*/
28 // ---------------------------------------------------------------------
30 pkgDepCache::pkgDepCache(pkgCache
*pCache
,Policy
*Plcy
) :
31 Cache(pCache
), PkgState(0), DepState(0)
36 delLocalPolicy
= LocalPolicy
= new Policy
;
39 // DepCache::~pkgDepCache - Destructor /*{{{*/
40 // ---------------------------------------------------------------------
42 pkgDepCache::~pkgDepCache()
46 delete delLocalPolicy
;
49 // DepCache::Init - Generate the initial extra structures. /*{{{*/
50 // ---------------------------------------------------------------------
51 /* This allocats the extension buffers and initializes them. */
52 bool pkgDepCache::Init(OpProgress
*Prog
)
56 PkgState
= new StateCache
[Head().PackageCount
];
57 DepState
= new unsigned char[Head().DependsCount
];
58 memset(PkgState
,0,sizeof(*PkgState
)*Head().PackageCount
);
59 memset(DepState
,0,sizeof(*DepState
)*Head().DependsCount
);
63 Prog
->OverallProgress(0,2*Head().PackageCount
,Head().PackageCount
,
64 _("Building dependency tree"));
65 Prog
->SubProgress(Head().PackageCount
,_("Candidate versions"));
68 /* Set the current state of everything. In this state all of the
69 packages are kept exactly as is. See AllUpgrade */
71 for (PkgIterator I
= PkgBegin(); I
.end() != true; I
++,Done
++)
76 // Find the proper cache slot
77 StateCache
&State
= PkgState
[I
->ID
];
79 State
.DirtyState
= pkgCache::State::RemoveUnknown
;
80 //State.AutomaticRemove = I->AutomaticRemove;
81 State
.AutomaticRemove
= pkgCache::State::RemoveUnknown
;
83 // Figure out the install version
84 State
.CandidateVer
= GetCandidateVer(I
);
85 State
.InstallVer
= I
.CurrentVer();
86 State
.Mode
= ModeKeep
;
88 State
.Update(I
,*this);
94 Prog
->OverallProgress(Head().PackageCount
,2*Head().PackageCount
,
96 _("Building dependency tree"));
97 Prog
->SubProgress(Head().PackageCount
,_("Dependency generation"));
106 // DepCache::CheckDep - Checks a single dependency /*{{{*/
107 // ---------------------------------------------------------------------
108 /* This first checks the dependency against the main target package and
109 then walks along the package provides list and checks if each provides
110 will be installed then checks the provides against the dep. Res will be
111 set to the package which was used to satisfy the dep. */
112 bool pkgDepCache::CheckDep(DepIterator Dep
,int Type
,PkgIterator
&Res
)
114 Res
= Dep
.TargetPkg();
116 /* Check simple depends. A depends -should- never self match but
117 we allow it anyhow because dpkg does. Technically it is a packaging
118 bug. Conflicts may never self match */
119 if (Dep
.TargetPkg() != Dep
.ParentPkg() ||
120 (Dep
->Type
!= Dep::Conflicts
&& Dep
->Type
!= Dep::Obsoletes
))
122 PkgIterator Pkg
= Dep
.TargetPkg();
123 // Check the base package
124 if (Type
== NowVersion
&& Pkg
->CurrentVer
!= 0)
125 if (VS().CheckDep(Pkg
.CurrentVer().VerStr(),Dep
->CompareOp
,
126 Dep
.TargetVer()) == true)
129 if (Type
== InstallVersion
&& PkgState
[Pkg
->ID
].InstallVer
!= 0)
130 if (VS().CheckDep(PkgState
[Pkg
->ID
].InstVerIter(*this).VerStr(),
131 Dep
->CompareOp
,Dep
.TargetVer()) == true)
134 if (Type
== CandidateVersion
&& PkgState
[Pkg
->ID
].CandidateVer
!= 0)
135 if (VS().CheckDep(PkgState
[Pkg
->ID
].CandidateVerIter(*this).VerStr(),
136 Dep
->CompareOp
,Dep
.TargetVer()) == true)
140 if (Dep
->Type
== Dep::Obsoletes
)
143 // Check the providing packages
144 PrvIterator P
= Dep
.TargetPkg().ProvidesList();
145 PkgIterator Pkg
= Dep
.ParentPkg();
146 for (; P
.end() != true; P
++)
148 /* Provides may never be applied against the same package if it is
149 a conflicts. See the comment above. */
150 if (P
.OwnerPkg() == Pkg
&& Dep
->Type
== Dep::Conflicts
)
153 // Check if the provides is a hit
154 if (Type
== NowVersion
)
156 if (P
.OwnerPkg().CurrentVer() != P
.OwnerVer())
160 if (Type
== InstallVersion
)
162 StateCache
&State
= PkgState
[P
.OwnerPkg()->ID
];
163 if (State
.InstallVer
!= (Version
*)P
.OwnerVer())
167 if (Type
== CandidateVersion
)
169 StateCache
&State
= PkgState
[P
.OwnerPkg()->ID
];
170 if (State
.CandidateVer
!= (Version
*)P
.OwnerVer())
174 // Compare the versions.
175 if (VS().CheckDep(P
.ProvideVersion(),Dep
->CompareOp
,Dep
.TargetVer()) == true)
185 // DepCache::AddSizes - Add the packages sizes to the counters /*{{{*/
186 // ---------------------------------------------------------------------
187 /* Call with Mult = -1 to preform the inverse opration */
188 void pkgDepCache::AddSizes(const PkgIterator
&Pkg
,signed long Mult
)
190 StateCache
&P
= PkgState
[Pkg
->ID
];
192 if (Pkg
->VersionList
== 0)
195 if (Pkg
.State() == pkgCache::PkgIterator::NeedsConfigure
&&
199 // Compute the size data
200 if (P
.NewInstall() == true)
202 iUsrSize
+= (signed)(Mult
*P
.InstVerIter(*this)->InstalledSize
);
203 iDownloadSize
+= (signed)(Mult
*P
.InstVerIter(*this)->Size
);
208 if (Pkg
->CurrentVer
!= 0 &&
209 (P
.InstallVer
!= (Version
*)Pkg
.CurrentVer() ||
210 (P
.iFlags
& ReInstall
) == ReInstall
) && P
.InstallVer
!= 0)
212 iUsrSize
+= (signed)(Mult
*((signed)P
.InstVerIter(*this)->InstalledSize
-
213 (signed)Pkg
.CurrentVer()->InstalledSize
));
214 iDownloadSize
+= (signed)(Mult
*P
.InstVerIter(*this)->Size
);
219 if (Pkg
.State() == pkgCache::PkgIterator::NeedsUnpack
&&
222 iDownloadSize
+= (signed)(Mult
*P
.InstVerIter(*this)->Size
);
227 if (Pkg
->CurrentVer
!= 0 && P
.InstallVer
== 0)
229 iUsrSize
-= (signed)(Mult
*Pkg
.CurrentVer()->InstalledSize
);
234 // DepCache::AddStates - Add the package to the state counter /*{{{*/
235 // ---------------------------------------------------------------------
236 /* This routine is tricky to use, you must make sure that it is never
237 called twice for the same package. This means the Remove/Add section
238 should be as short as possible and not encompass any code that will
239 calld Remove/Add itself. Remember, dependencies can be circular so
240 while processing a dep for Pkg it is possible that Add/Remove
241 will be called on Pkg */
242 void pkgDepCache::AddStates(const PkgIterator
&Pkg
,int Add
)
244 StateCache
&State
= PkgState
[Pkg
->ID
];
246 // The Package is broken
247 if ((State
.DepState
& DepInstMin
) != DepInstMin
)
251 if (Pkg
.State() != PkgIterator::NeedsNothing
)
255 if (Pkg
->CurrentVer
== 0)
257 if (State
.Mode
== ModeDelete
&&
258 (State
.iFlags
| Purge
) == Purge
&& Pkg
.Purge() == false)
261 if (State
.Mode
== ModeInstall
)
266 // Installed, no upgrade
267 if (State
.Status
== 0)
269 if (State
.Mode
== ModeDelete
)
272 if ((State
.iFlags
& ReInstall
) == ReInstall
)
278 // Alll 3 are possible
279 if (State
.Mode
== ModeDelete
)
281 if (State
.Mode
== ModeKeep
)
283 if (State
.Mode
== ModeInstall
)
287 // DepCache::BuildGroupOrs - Generate the Or group dep data /*{{{*/
288 // ---------------------------------------------------------------------
289 /* The or group results are stored in the last item of the or group. This
290 allows easy detection of the state of a whole or'd group. */
291 void pkgDepCache::BuildGroupOrs(VerIterator
const &V
)
293 unsigned char Group
= 0;
295 for (DepIterator D
= V
.DependsList(); D
.end() != true; D
++)
297 // Build the dependency state.
298 unsigned char &State
= DepState
[D
->ID
];
300 /* Invert for Conflicts. We have to do this twice to get the
301 right sense for a conflicts group */
302 if (D
->Type
== Dep::Conflicts
|| D
->Type
== Dep::Obsoletes
)
305 // Add to the group if we are within an or..
309 if ((D
->CompareOp
& Dep::Or
) != Dep::Or
)
312 // Invert for Conflicts
313 if (D
->Type
== Dep::Conflicts
|| D
->Type
== Dep::Obsoletes
)
318 // DepCache::VersionState - Perform a pass over a dependency list /*{{{*/
319 // ---------------------------------------------------------------------
320 /* This is used to run over a dependency list and determine the dep
321 state of the list, filtering it through both a Min check and a Policy
322 check. The return result will have SetMin/SetPolicy low if a check
323 fails. It uses the DepState cache for it's computations. */
324 unsigned char pkgDepCache::VersionState(DepIterator D
,unsigned char Check
,
325 unsigned char SetMin
,
326 unsigned char SetPolicy
)
328 unsigned char Dep
= 0xFF;
330 while (D
.end() != true)
332 // Compute a single dependency element (glob or)
333 DepIterator Start
= D
;
334 unsigned char State
= 0;
335 for (bool LastOR
= true; D
.end() == false && LastOR
== true; D
++)
337 State
|= DepState
[D
->ID
];
338 LastOR
= (D
->CompareOp
& Dep::Or
) == Dep::Or
;
341 // Minimum deps that must be satisfied to have a working package
342 if (Start
.IsCritical() == true)
343 if ((State
& Check
) != Check
)
346 // Policy deps that must be satisfied to install the package
347 if (IsImportantDep(Start
) == true &&
348 (State
& Check
) != Check
)
355 // DepCache::DependencyState - Compute the 3 results for a dep /*{{{*/
356 // ---------------------------------------------------------------------
357 /* This is the main dependency computation bit. It computes the 3 main
358 results for a dependencys, Now, Install and Candidate. Callers must
359 invert the result if dealing with conflicts. */
360 unsigned char pkgDepCache::DependencyState(DepIterator
&D
)
362 unsigned char State
= 0;
364 if (CheckDep(D
,NowVersion
) == true)
366 if (CheckDep(D
,InstallVersion
) == true)
368 if (CheckDep(D
,CandidateVersion
) == true)
374 // DepCache::UpdateVerState - Compute the Dep member of the state /*{{{*/
375 // ---------------------------------------------------------------------
376 /* This determines the combined dependency representation of a package
377 for its two states now and install. This is done by using the pre-generated
378 dependency information. */
379 void pkgDepCache::UpdateVerState(PkgIterator Pkg
)
381 // Empty deps are always true
382 StateCache
&State
= PkgState
[Pkg
->ID
];
383 State
.DepState
= 0xFF;
385 // Check the Current state
386 if (Pkg
->CurrentVer
!= 0)
388 DepIterator D
= Pkg
.CurrentVer().DependsList();
389 State
.DepState
&= VersionState(D
,DepNow
,DepNowMin
,DepNowPolicy
);
392 /* Check the candidate state. We do not compare against the whole as
393 a candidate state but check the candidate version against the
395 if (State
.CandidateVer
!= 0)
397 DepIterator D
= State
.CandidateVerIter(*this).DependsList();
398 State
.DepState
&= VersionState(D
,DepInstall
,DepCandMin
,DepCandPolicy
);
401 // Check target state which can only be current or installed
402 if (State
.InstallVer
!= 0)
404 DepIterator D
= State
.InstVerIter(*this).DependsList();
405 State
.DepState
&= VersionState(D
,DepInstall
,DepInstMin
,DepInstPolicy
);
409 // DepCache::Update - Figure out all the state information /*{{{*/
410 // ---------------------------------------------------------------------
411 /* This will figure out the state of all the packages and all the
412 dependencies based on the current policy. */
413 void pkgDepCache::Update(OpProgress
*Prog
)
423 // Perform the depends pass
425 for (PkgIterator I
= PkgBegin(); I
.end() != true; I
++,Done
++)
427 if (Prog
!= 0 && Done%20
== 0)
428 Prog
->Progress(Done
);
429 for (VerIterator V
= I
.VersionList(); V
.end() != true; V
++)
431 unsigned char Group
= 0;
433 for (DepIterator D
= V
.DependsList(); D
.end() != true; D
++)
435 // Build the dependency state.
436 unsigned char &State
= DepState
[D
->ID
];
437 State
= DependencyState(D
);
439 // Add to the group if we are within an or..
442 if ((D
->CompareOp
& Dep::Or
) != Dep::Or
)
445 // Invert for Conflicts
446 if (D
->Type
== Dep::Conflicts
|| D
->Type
== Dep::Obsoletes
)
451 // Compute the pacakge dependency state and size additions
457 // read the state file ------------------------------
459 string state
= _config
->FindDir("Dir::State") + "pkgstates";
460 if(FileExists(state
)) {
461 state_file
.Open(state
, FileFd::ReadOnly
);
462 int file_size
= state_file
.Size();
463 Prog
->OverallProgress(0, file_size
, 1, _("Reading extended state information"));
465 pkgTagFile
tagfile(&state_file
);
466 pkgTagSection section
;
468 while(tagfile
.Step(section
)) {
469 string pkgname
= section
.FindS("Package");
470 pkgCache::PkgIterator pkg
=Cache
->FindPkg(pkgname
);
471 // Silently ignore unknown packages and packages with no actual
473 if(!pkg
.end() && !pkg
.VersionList().end()) {
474 short reason
= section
.FindI("Remove-Reason", pkgCache::State::RemoveManual
);
475 PkgState
[pkg
->ID
].AutomaticRemove
= reason
;
476 //std::cout << "Set: " << pkgname << " to " << reason << std::endl;
478 Prog
->OverallProgress(amt
, file_size
, 1, _("Reading extended state information"));
480 Prog
->OverallProgress(file_size
, file_size
, 1, _("Reading extended state information"));
483 //--------------------------------------
487 Prog
->Progress(Done
);
490 // DepCache::Update - Update the deps list of a package /*{{{*/
491 // ---------------------------------------------------------------------
492 /* This is a helper for update that only does the dep portion of the scan.
493 It is mainly ment to scan reverse dependencies. */
494 void pkgDepCache::Update(DepIterator D
)
496 // Update the reverse deps
497 for (;D
.end() != true; D
++)
499 unsigned char &State
= DepState
[D
->ID
];
500 State
= DependencyState(D
);
502 // Invert for Conflicts
503 if (D
->Type
== Dep::Conflicts
|| D
->Type
== Dep::Obsoletes
)
506 RemoveStates(D
.ParentPkg());
507 BuildGroupOrs(D
.ParentVer());
508 UpdateVerState(D
.ParentPkg());
509 AddStates(D
.ParentPkg());
513 // DepCache::Update - Update the related deps of a package /*{{{*/
514 // ---------------------------------------------------------------------
515 /* This is called whenever the state of a package changes. It updates
516 all cached dependencies related to this package. */
517 void pkgDepCache::Update(PkgIterator
const &Pkg
)
519 // Recompute the dep of the package
524 // Update the reverse deps
525 Update(Pkg
.RevDependsList());
527 // Update the provides map for the current ver
528 if (Pkg
->CurrentVer
!= 0)
529 for (PrvIterator P
= Pkg
.CurrentVer().ProvidesList();
530 P
.end() != true; P
++)
531 Update(P
.ParentPkg().RevDependsList());
533 // Update the provides map for the candidate ver
534 if (PkgState
[Pkg
->ID
].CandidateVer
!= 0)
535 for (PrvIterator P
= PkgState
[Pkg
->ID
].CandidateVerIter(*this).ProvidesList();
536 P
.end() != true; P
++)
537 Update(P
.ParentPkg().RevDependsList());
542 // DepCache::MarkKeep - Put the package in the keep state /*{{{*/
543 // ---------------------------------------------------------------------
545 void pkgDepCache::MarkKeep(PkgIterator
const &Pkg
,bool Soft
)
547 // Simplifies other routines.
548 if (Pkg
.end() == true)
551 /* Reject an attempt to keep a non-source broken installed package, those
553 if (Pkg
.State() == PkgIterator::NeedsUnpack
&&
554 Pkg
.CurrentVer().Downloadable() == false)
557 /* We changed the soft state all the time so the UI is a bit nicer
559 StateCache
&P
= PkgState
[Pkg
->ID
];
561 P
.iFlags
|= AutoKept
;
563 P
.iFlags
&= ~AutoKept
;
565 // Check that it is not already kept
566 if (P
.Mode
== ModeKeep
)
569 // We dont even try to keep virtual packages..
570 if (Pkg
->VersionList
== 0)
573 P
.Flags
&= ~Flag::Auto
;
578 if (Pkg
->CurrentVer
== 0)
581 P
.InstallVer
= Pkg
.CurrentVer();
590 // DepCache::MarkDelete - Put the package in the delete state /*{{{*/
591 // ---------------------------------------------------------------------
593 void pkgDepCache::MarkDelete(PkgIterator
const &Pkg
, bool rPurge
)
595 // Simplifies other routines.
596 if (Pkg
.end() == true)
599 // Check that it is not already marked for delete
600 StateCache
&P
= PkgState
[Pkg
->ID
];
601 P
.iFlags
&= ~(AutoKept
| Purge
);
605 if ((P
.Mode
== ModeDelete
|| P
.InstallVer
== 0) &&
606 (Pkg
.Purge() == true || rPurge
== false))
609 // We dont even try to delete virtual packages..
610 if (Pkg
->VersionList
== 0)
616 if (Pkg
->CurrentVer
== 0 && (Pkg
.Purge() == true || rPurge
== false))
621 // This was not inverted before, but I think it should be
622 P
.Flags
&= ~Flag::Auto
;
629 // DepCache::MarkInstall - Put the package in the install state /*{{{*/
630 // ---------------------------------------------------------------------
632 void pkgDepCache::MarkInstall(PkgIterator
const &Pkg
,bool AutoInst
,
638 // Simplifies other routines.
639 if (Pkg
.end() == true)
642 /* Check that it is not already marked for install and that it can be
644 StateCache
&P
= PkgState
[Pkg
->ID
];
645 P
.iFlags
&= ~AutoKept
;
646 if (P
.InstBroken() == false && (P
.Mode
== ModeInstall
||
647 P
.CandidateVer
== (Version
*)Pkg
.CurrentVer()))
649 if (P
.CandidateVer
== (Version
*)Pkg
.CurrentVer() && P
.InstallVer
== 0)
654 // See if there is even any possible instalation candidate
655 if (P
.CandidateVer
== 0)
658 // We dont even try to install virtual packages..
659 if (Pkg
->VersionList
== 0)
662 /* Target the candidate version and remove the autoflag. We reset the
663 autoflag below if this was called recursively. Otherwise the user
664 should have the ability to de-auto a package by changing its state */
668 P
.Mode
= ModeInstall
;
669 P
.InstallVer
= P
.CandidateVer
;
670 P
.Flags
&= ~Flag::Auto
;
671 if (P
.CandidateVer
== (Version
*)Pkg
.CurrentVer())
678 if (AutoInst
== false)
681 DepIterator Dep
= P
.InstVerIter(*this).DependsList();
682 for (; Dep
.end() != true;)
685 DepIterator Start
= Dep
;
688 for (bool LastOR
= true; Dep
.end() == false && LastOR
== true; Dep
++,Ors
++)
690 LastOR
= (Dep
->CompareOp
& Dep::Or
) == Dep::Or
;
692 if ((DepState
[Dep
->ID
] & DepInstall
) == DepInstall
)
696 // Dep is satisfied okay.
700 /* Check if this dep should be consider for install. If it is a user
701 defined important dep and we are installed a new package then
702 it will be installed. Otherwise we only worry about critical deps */
703 if (IsImportantDep(Start
) == false)
705 if (Pkg
->CurrentVer
!= 0 && Start
.IsCritical() == false)
708 /* If we are in an or group locate the first or that can
709 succeed. We have already cached this.. */
710 for (; Ors
> 1 && (DepState
[Start
->ID
] & DepCVer
) != DepCVer
; Ors
--)
713 /* This bit is for processing the possibilty of an install/upgrade
714 fixing the problem */
715 SPtrArray
<Version
*> List
= Start
.AllTargets();
716 if ((DepState
[Start
->ID
] & DepCVer
) == DepCVer
)
718 // Right, find the best version to install..
719 Version
**Cur
= List
;
720 PkgIterator P
= Start
.TargetPkg();
721 PkgIterator
InstPkg(*Cache
,0);
723 // See if there are direct matches (at the start of the list)
724 for (; *Cur
!= 0 && (*Cur
)->ParentPkg
== P
.Index(); Cur
++)
726 PkgIterator
Pkg(*Cache
,Cache
->PkgP
+ (*Cur
)->ParentPkg
);
727 if (PkgState
[Pkg
->ID
].CandidateVer
!= *Cur
)
733 // Select the highest priority providing package
734 if (InstPkg
.end() == true)
736 pkgPrioSortList(*Cache
,Cur
);
737 for (; *Cur
!= 0; Cur
++)
739 PkgIterator
Pkg(*Cache
,Cache
->PkgP
+ (*Cur
)->ParentPkg
);
740 if (PkgState
[Pkg
->ID
].CandidateVer
!= *Cur
)
747 if (InstPkg
.end() == false)
749 MarkInstall(InstPkg
,true,Depth
+ 1);
751 // Set the autoflag, after MarkInstall because MarkInstall unsets it
752 if (P
->CurrentVer
== 0)
753 PkgState
[InstPkg
->ID
].Flags
|= Flag::Auto
;
759 /* For conflicts we just de-install the package and mark as auto,
760 Conflicts may not have or groups */
761 if (Start
->Type
== Dep::Conflicts
|| Start
->Type
== Dep::Obsoletes
)
763 for (Version
**I
= List
; *I
!= 0; I
++)
765 VerIterator
Ver(*this,*I
);
766 PkgIterator Pkg
= Ver
.ParentPkg();
769 PkgState
[Pkg
->ID
].Flags
|= Flag::Auto
;
776 // DepCache::SetReInstall - Set the reinstallation flag /*{{{*/
777 // ---------------------------------------------------------------------
779 void pkgDepCache::SetReInstall(PkgIterator
const &Pkg
,bool To
)
784 StateCache
&P
= PkgState
[Pkg
->ID
];
786 P
.iFlags
|= ReInstall
;
788 P
.iFlags
&= ~ReInstall
;
794 // DepCache::SetDirty - Switch the package between dirty states /*{{{*/
795 // ---------------------------------------------------------------------
797 void pkgDepCache::SetDirty(PkgIterator
const &Pkg
, pkgCache::State::PkgRemoveState To
)
799 StateCache
&P
= PkgState
[Pkg
->ID
];
803 // DepCache::SetCandidateVersion - Change the candidate version /*{{{*/
804 // ---------------------------------------------------------------------
806 void pkgDepCache::SetCandidateVersion(VerIterator TargetVer
)
808 pkgCache::PkgIterator Pkg
= TargetVer
.ParentPkg();
809 StateCache
&P
= PkgState
[Pkg
->ID
];
814 if (P
.CandidateVer
== P
.InstallVer
)
815 P
.InstallVer
= (Version
*)TargetVer
;
816 P
.CandidateVer
= (Version
*)TargetVer
;
824 // StateCache::Update - Compute the various static display things /*{{{*/
825 // ---------------------------------------------------------------------
826 /* This is called whenever the Candidate version changes. */
827 void pkgDepCache::StateCache::Update(PkgIterator Pkg
,pkgCache
&Cache
)
830 VerIterator Ver
= CandidateVerIter(Cache
);
832 // Use a null string or the version string
833 if (Ver
.end() == true)
836 CandVersion
= Ver
.VerStr();
838 // Find the current version
840 if (Pkg
->CurrentVer
!= 0)
841 CurVersion
= Pkg
.CurrentVer().VerStr();
843 // Strip off the epochs for display
844 CurVersion
= StripEpoch(CurVersion
);
845 CandVersion
= StripEpoch(CandVersion
);
847 // Figure out if its up or down or equal
848 Status
= Ver
.CompareVer(Pkg
.CurrentVer());
849 if (Pkg
->CurrentVer
== 0 || Pkg
->VersionList
== 0 || CandidateVer
== 0)
853 // StateCache::StripEpoch - Remove the epoch specifier from the version /*{{{*/
854 // ---------------------------------------------------------------------
856 const char *pkgDepCache::StateCache::StripEpoch(const char *Ver
)
862 for (const char *I
= Ver
; *I
!= 0; I
++)
869 // Policy::GetCandidateVer - Returns the Candidate install version /*{{{*/
870 // ---------------------------------------------------------------------
871 /* The default just returns the highest available version that is not
872 a source and automatic. */
873 pkgCache::VerIterator
pkgDepCache::Policy::GetCandidateVer(PkgIterator Pkg
)
875 /* Not source/not automatic versions cannot be a candidate version
876 unless they are already installed */
877 VerIterator
Last(*(pkgCache
*)this,0);
879 for (VerIterator I
= Pkg
.VersionList(); I
.end() == false; I
++)
881 if (Pkg
.CurrentVer() == I
)
884 for (VerFileIterator J
= I
.FileList(); J
.end() == false; J
++)
886 if ((J
.File()->Flags
& Flag::NotSource
) != 0)
889 /* Stash the highest version of a not-automatic source, we use it
890 if there is nothing better */
891 if ((J
.File()->Flags
& Flag::NotAutomatic
) != 0)
893 if (Last
.end() == true)
905 // Policy::IsImportantDep - True if the dependency is important /*{{{*/
906 // ---------------------------------------------------------------------
908 bool pkgDepCache::Policy::IsImportantDep(DepIterator Dep
)
910 return Dep
.IsCritical();