Browse Source

Store tags in the cache (they are very useful :/).

Jay Freeman (saurik) 7 years ago
parent
commit
a473295d01

+ 45 - 0
apt-pkg/cacheiterators.h

@@ -231,6 +231,7 @@ class pkgCache::VerIterator : public Iterator<Version, VerIterator> {
 	DescIterator TranslatedDescription() const;
 	inline DepIterator DependsList() const;
 	inline PrvIterator ProvidesList() const;
+	inline TagIterator TagList() const;
 	inline VerFileIterator FileList() const;
 	bool Downloadable() const;
 	inline const char *PriorityType() const {return Owner->Priority(S->Priority);}
@@ -247,6 +248,48 @@ class pkgCache::VerIterator : public Iterator<Version, VerIterator> {
 	inline VerIterator() : Iterator<Version, VerIterator>() {}
 };
 									/*}}}*/
+// Tag Iterator								/*{{{*/
+class pkgCache::TagIterator
+{
+   Tag *Tg;
+   pkgCache *Owner;
+
+   void _dummy();
+
+   public:
+
+   // Iteration
+   void operator ++(int) {if (Tg != Owner->TagP) Tg = Owner->TagP + Tg->NextTag;};
+   inline void operator ++() {operator ++(0);};
+   inline bool end() const {return Tg == Owner->TagP?true:false;};
+   inline void operator =(const TagIterator &B) {Tg = B.Tg; Owner = B.Owner;};
+
+   // Comparison
+   inline bool operator ==(const TagIterator &B) const {return Tg == B.Tg;};
+   inline bool operator !=(const TagIterator &B) const {return Tg != B.Tg;};
+   int CompareTag(const TagIterator &B) const;
+
+   // Accessors
+   inline Tag *operator ->() {return Tg;};
+   inline Tag const *operator ->() const {return Tg;};
+   inline Tag &operator *() {return *Tg;};
+   inline Tag const &operator *() const {return *Tg;};
+   inline operator Tag *() {return Tg == Owner->TagP?0:Tg;};
+   inline operator Tag const *() const {return Tg == Owner->TagP?0:Tg;};
+   inline pkgCache *Cache() {return Owner;};
+
+   inline const char *Name() const {return Owner->StrP + Tg->Name;};
+   inline unsigned long Index() const {return Tg - Owner->TagP;};
+
+   inline TagIterator() : Tg(0), Owner(0) {};
+   inline TagIterator(pkgCache &Owner,Tag *Trg = 0) : Tg(Trg),
+              Owner(&Owner)
+   {
+      if (Tg == 0)
+	 Tg = Owner.TagP;
+   };
+};
+									/*}}}*/
 // Description Iterator							/*{{{*/
 class pkgCache::DescIterator : public Iterator<Description, DescIterator> {
 	public:
@@ -515,6 +558,8 @@ inline pkgCache::DescIterator pkgCache::VerIterator::DescriptionList() const
        {return DescIterator(*Owner,Owner->DescP + S->DescriptionList);}
 inline pkgCache::PrvIterator pkgCache::VerIterator::ProvidesList() const
        {return PrvIterator(*Owner,Owner->ProvideP + S->ProvidesList,S);}
+inline pkgCache::TagIterator pkgCache::VerIterator::TagList() const
+       {return TagIterator(*Owner,Owner->TagP + S->TagList);};
 inline pkgCache::DepIterator pkgCache::VerIterator::DependsList() const
        {return DepIterator(*Owner,Owner->DepP + S->DependsList,S);}
 inline pkgCache::VerFileIterator pkgCache::VerIterator::FileList() const

+ 42 - 0
apt-pkg/deb/deblistparser.cc

@@ -244,6 +244,8 @@ bool debListParser::NewVersion(pkgCache::VerIterator &Ver)
    
    if (ParseProvides(Ver) == false)
       return false;
+   if (ParseTag(Ver) == false)
+      return false;
    
    return true;
 }
@@ -950,6 +952,46 @@ bool debListParser::ParseProvides(pkgCache::VerIterator &Ver)
 	    return false;
       }
    }
+   return true;
+}
+									/*}}}*/
+// ListParser::ParseTag - Parse the tag list				/*{{{*/
+// ---------------------------------------------------------------------
+/* */
+bool debListParser::ParseTag(pkgCache::VerIterator &Ver)
+{
+   const char *Start;
+   const char *Stop;
+   if (Section.Find("Tag",Start,Stop) == false)
+      return true;
+
+   while (1) {
+      while (1) {
+         if (Start == Stop)
+            return true;
+         if (Stop[-1] != ' ' && Stop[-1] != '\t')
+            break;
+         --Stop;
+      }
+
+      const char *Begin = Stop - 1;
+      while (Begin != Start && Begin[-1] != ' ' && Begin[-1] != ',')
+         --Begin;
+
+      if (NewTag(Ver, Begin, Stop - Begin) == false)
+         return false;
+
+      while (1) {
+         if (Begin == Start)
+            return true;
+         if (Begin[-1] == ',')
+            break;
+         --Begin;
+      }
+
+      Stop = Begin - 1;
+   }
+
    return true;
 }
 									/*}}}*/

+ 1 - 0
apt-pkg/deb/deblistparser.h

@@ -56,6 +56,7 @@ class APT_HIDDEN debListParser : public pkgCacheListParser
    bool ParseDepends(pkgCache::VerIterator &Ver, pkgTagSection::Key Key,
 		     unsigned int Type);
    bool ParseProvides(pkgCache::VerIterator &Ver);
+   bool ParseTag(pkgCache::VerIterator &Ver);
 
 #ifdef APT_PKG_EXPOSE_STRING_VIEW
    APT_HIDDEN static bool GrabWord(APT::StringView Word,const WordList *List,unsigned char &Out);

+ 1 - 0
apt-pkg/pkgcache.cc

@@ -154,6 +154,7 @@ bool pkgCache::ReMap(bool const &Errorchecks)
    VerP = (Version *)Map.Data();
    DescP = (Description *)Map.Data();
    ProvideP = (Provides *)Map.Data();
+   TagP = (Tag *)Map.Data();
    DepP = (Dependency *)Map.Data();
    DepDataP = (DependencyData *)Map.Data();
    StrP = (char *)Map.Data();

+ 18 - 0
apt-pkg/pkgcache.h

@@ -123,6 +123,7 @@ class pkgCache								/*{{{*/
    struct StringItem;
    struct VerFile;
    struct DescFile;
+   struct Tag;
    
    // Iterators
    template<typename Str, typename Itr> class Iterator;
@@ -136,6 +137,7 @@ class pkgCache								/*{{{*/
    class PkgFileIterator;
    class VerFileIterator;
    class DescFileIterator;
+   class TagIterator;
    
    class Namespace;
    
@@ -214,6 +216,7 @@ class pkgCache								/*{{{*/
    ReleaseFile *RlsFileP;
    PackageFile *PkgFileP;
    Version *VerP;
+   Tag *TagP;
    Description *DescP;
    Provides *ProvideP;
    Dependency *DepP;
@@ -320,6 +323,7 @@ struct pkgCache::Header
    map_number_t ReleaseFileSz;
    map_number_t PackageFileSz;
    map_number_t VersionSz;
+   map_number_t TagSz;
    map_number_t DescriptionSz;
    map_number_t DependencySz;
    map_number_t DependencyDataSz;
@@ -335,6 +339,7 @@ struct pkgCache::Header
    map_id_t GroupCount;
    map_id_t PackageCount;
    map_id_t VersionCount;
+   map_id_t TagCount;
    map_id_t DescriptionCount;
    map_id_t DependsCount;
    map_id_t DependsDataCount;
@@ -585,6 +590,16 @@ struct pkgCache::VerFile
    map_filesize_t Size;
 };
 									/*}}}*/
+// TagFile structure							/*{{{*/
+/** \brief associates a tag with something */
+struct pkgCache::Tag
+{
+   /** \brief name of this tag */
+   map_stringitem_t Name;
+   /** \brief next step in the linked list */
+   map_pointer_t NextTag;       // Tag
+};
+									/*}}}*/
 // DescFile structure							/*{{{*/
 /** \brief associates a description with a Translation file */
 struct pkgCache::DescFile
@@ -656,6 +671,8 @@ struct pkgCache::Version
    map_pointer_t ParentPkg;         // Package
    /** \brief list of pkgCache::Provides */
    map_pointer_t ProvidesList;      // Provides
+   /** \brief list of pkgCache::Tag */
+   map_pointer_t TagList;           // Tag
 
    /** \brief archive size for this version
 
@@ -808,6 +825,7 @@ class pkgCache::Namespace						/*{{{*/
    typedef pkgCache::GrpIterator GrpIterator;
    typedef pkgCache::PkgIterator PkgIterator;
    typedef pkgCache::VerIterator VerIterator;
+   typedef pkgCache::TagIterator TagIterator;
    typedef pkgCache::DescIterator DescIterator;
    typedef pkgCache::DepIterator DepIterator;
    typedef pkgCache::PrvIterator PrvIterator;

+ 30 - 0
apt-pkg/pkgcachegen.cc

@@ -1271,6 +1271,36 @@ bool pkgCacheGenerator::SelectReleaseFile(const string &File,const string &Site,
    Cache.HeaderP->RlsFileList = CurrentRlsFile - Cache.RlsFileP;
    Cache.HeaderP->ReleaseFileCount++;
 
+   return true;
+}
+									/*}}}*/
+// ListParser::NewTag - Create a Tag element				/*{{{*/
+// ---------------------------------------------------------------------
+/* */
+bool pkgCacheListParser::NewTag(pkgCache::VerIterator &Ver,
+					   const char *NameStart,
+					   unsigned int NameSize)
+{
+   return Owner->NewTag(Ver, NameStart, NameSize);
+}
+bool pkgCacheGenerator::NewTag(pkgCache::VerIterator &Ver,
+					   const char *NameStart,
+					   unsigned int NameSize)
+{
+   // Get a structure
+   unsigned long Tagg = AllocateInMap(sizeof(pkgCache::Tag));
+   if (Tagg == 0)
+      return false;
+   Cache.HeaderP->TagCount++;
+   
+   // Fill it in
+   pkgCache::TagIterator Tg(Cache,Cache.TagP + Tagg);
+   Tg->Name = WriteStringInMap(NameStart,NameSize);
+   if (Tg->Name == 0)
+      return false;
+   Tg->NextTag = Ver->TagList;
+   Ver->TagList = Tg.Index();
+   
    return true;
 }
 									/*}}}*/

+ 2 - 0
apt-pkg/pkgcachegen.h

@@ -128,6 +128,7 @@ class APT_HIDDEN pkgCacheGenerator					/*{{{*/
 		   uint8_t const Type, map_pointer_t* &OldDepLast);
    bool NewProvides(pkgCache::VerIterator &Ver, pkgCache::PkgIterator &Pkg,
 		    map_stringitem_t const ProvidesVersion, uint8_t const Flags);
+   bool NewTag(pkgCache::VerIterator &Ver,const char *NameStart,unsigned int NameSize);
 
    public:
 
@@ -209,6 +210,7 @@ class APT_HIDDEN pkgCacheListParser
 		    uint8_t const Flags);
    bool NewProvidesAllArch(pkgCache::VerIterator &Ver, APT::StringView Package,
 			   APT::StringView Version, uint8_t const Flags);
+   bool NewTag(pkgCache::VerIterator &Ver,const char *NameStart,unsigned int NameSize);
 #endif
    public: