diff options
Diffstat (limited to 'apt-pkg/deb')
-rw-r--r-- | apt-pkg/deb/debindexfile.cc | 108 | ||||
-rw-r--r-- | apt-pkg/deb/debindexfile.h | 31 | ||||
-rw-r--r-- | apt-pkg/deb/deblistparser.cc | 20 | ||||
-rw-r--r-- | apt-pkg/deb/deblistparser.h | 15 | ||||
-rw-r--r-- | apt-pkg/deb/debmetaindex.cc | 29 | ||||
-rw-r--r-- | apt-pkg/deb/debmetaindex.h | 24 | ||||
-rw-r--r-- | apt-pkg/deb/debrecords.h | 18 |
7 files changed, 237 insertions, 8 deletions
diff --git a/apt-pkg/deb/debindexfile.cc b/apt-pkg/deb/debindexfile.cc index eee758b7a..1cecb42cf 100644 --- a/apt-pkg/deb/debindexfile.cc +++ b/apt-pkg/deb/debindexfile.cc @@ -30,6 +30,7 @@ #include <apt-pkg/pkgcachegen.h> #include <apt-pkg/pkgrecords.h> #include <apt-pkg/srcrecords.h> +#include <apt-pkg/sptr.h> #include <stdio.h> #include <iostream> @@ -667,6 +668,98 @@ APT_CONST bool debStatusIndex::Exists() const } /*}}}*/ +// debDebPkgFile - Single .deb file /*{{{*/ +// --------------------------------------------------------------------- +debDebPkgFileIndex::debDebPkgFileIndex(std::string DebFile) + : pkgIndexFile(true), DebFile(DebFile) +{ + // FIXME: we need to os.normpath(DebFile) here, this is a lame workaround + DebFileFullPath = SafeGetCWD() + DebFile; +} + +std::string debDebPkgFileIndex::ArchiveURI(std::string /*File*/) const +{ + return "file:" + DebFileFullPath; +} + +bool debDebPkgFileIndex::Exists() const +{ + return FileExists(DebFile); +} +bool debDebPkgFileIndex::Merge(pkgCacheGenerator& Gen, OpProgress* Prog) const +{ + if(Prog) + Prog->SubProgress(0, "Reading deb file"); + + // get the control data out of the deb file vid dpkg -I + // ... can I haz libdpkg? + const char *Args[5] = {"/usr/bin/dpkg", + "-I", + DebFile.c_str(), + "control", + NULL}; + FileFd PipeFd; + pid_t Child; + if(Popen(Args, PipeFd, Child, FileFd::ReadOnly) == false) + return _error->Error("Popen failed"); + // FIXME: static buffer + char buf[8*1024]; + unsigned long long n = 0; + if(PipeFd.Read(buf, sizeof(buf)-1, &n) == false) + return _error->Errno("read", "Failed to read dpkg pipe"); + ExecWait(Child, "Popen"); + + // now write the control data to a tempfile + SPtr<FileFd> DebControl = GetTempFile("deb-file-" + DebFile); + if(DebControl == NULL) + return false; + DebControl->Write(buf, n); + // append size of the file + FileFd Fd(DebFile, FileFd::ReadOnly); + string Size; + strprintf(Size, "Size: %llu\n", Fd.Size()); + DebControl->Write(Size.c_str(), Size.size()); + // and rewind for the listparser + DebControl->Seek(0); + + // and give it to the list parser + debDebFileParser Parser(DebControl, DebFile); + if(Gen.SelectFile(DebFile, "local", *this) == false) + return _error->Error("Problem with SelectFile %s", DebFile.c_str()); + + pkgCache::PkgFileIterator File = Gen.GetCurFile(); + File->Size = DebControl->Size(); + File->mtime = DebControl->ModificationTime(); + + if (Gen.MergeList(Parser) == false) + return _error->Error("Problem with MergeLister for %s", DebFile.c_str()); + + return true; +} +pkgCache::PkgFileIterator debDebPkgFileIndex::FindInCache(pkgCache &Cache) const +{ + // FIXME: we could simply always return pkgCache::PkgFileIterator(Cache); + // to indicate its never in the cache which will force a Merge() + pkgCache::PkgFileIterator File = Cache.FileBegin(); + for (; File.end() == false; ++File) + { + if (File.FileName() == NULL || DebFile != File.FileName()) + continue; + + return File; + } + + return File; +} +unsigned long debDebPkgFileIndex::Size() const +{ + struct stat buf; + if(stat(DebFile.c_str(), &buf) != 0) + return 0; + return buf.st_size; +} + /*}}}*/ + // Index File types for Debian /*{{{*/ class debIFTypeSrc : public pkgIndexFile::Type { @@ -699,10 +792,20 @@ class debIFTypeStatus : public pkgIndexFile::Type }; debIFTypeStatus() {Label = "Debian dpkg status file";}; }; +class debIFTypeDebPkgFile : public pkgIndexFile::Type +{ + public: + virtual pkgRecords::Parser *CreatePkgParser(pkgCache::PkgFileIterator File) const + { + return new debDebFileRecordParser(File.FileName(),*File.Cache()); + }; + debIFTypeDebPkgFile() {Label = "deb Package file";}; +}; static debIFTypeSrc _apt_Src; static debIFTypePkg _apt_Pkg; static debIFTypeTrans _apt_Trans; static debIFTypeStatus _apt_Status; +static debIFTypeDebPkgFile _apt_DebPkgFile; const pkgIndexFile::Type *debSourcesIndex::GetType() const { @@ -720,5 +823,8 @@ const pkgIndexFile::Type *debStatusIndex::GetType() const { return &_apt_Status; } - +const pkgIndexFile::Type *debDebPkgFileIndex::GetType() const +{ + return &_apt_DebPkgFile; +} /*}}}*/ diff --git a/apt-pkg/deb/debindexfile.h b/apt-pkg/deb/debindexfile.h index 017c69a0a..69754e79d 100644 --- a/apt-pkg/deb/debindexfile.h +++ b/apt-pkg/deb/debindexfile.h @@ -164,4 +164,35 @@ class debSourcesIndex : public pkgIndexFile virtual ~debSourcesIndex() {}; }; +class debDebPkgFileIndex : public pkgIndexFile +{ + private: + void *d; + std::string DebFile; + std::string DebFileFullPath; + + public: + virtual const Type *GetType() const APT_CONST; + + virtual std::string Describe(bool /*Short*/) const { + return DebFile; + } + + // Interface for the Cache Generator + virtual bool Exists() const; + virtual bool HasPackages() const { + return true; + }; + virtual unsigned long Size() const; + virtual bool Merge(pkgCacheGenerator &Gen,OpProgress *Prog) const; + virtual pkgCache::PkgFileIterator FindInCache(pkgCache &Cache) const; + + // Interface for acquire + virtual std::string ArchiveURI(std::string /*File*/) const; + + debDebPkgFileIndex(std::string DebFile); + virtual ~debDebPkgFileIndex() {}; + +}; + #endif diff --git a/apt-pkg/deb/deblistparser.cc b/apt-pkg/deb/deblistparser.cc index a1bcfb710..d5e3ccb65 100644 --- a/apt-pkg/deb/deblistparser.cc +++ b/apt-pkg/deb/deblistparser.cc @@ -959,3 +959,23 @@ bool debListParser::SameVersion(unsigned short const Hash, /*{{{*/ } /*}}}*/ #endif + + +debDebFileParser::debDebFileParser(FileFd *File, std::string const &DebFile) + : debListParser(File, ""), DebFile(DebFile) +{ +} + +bool debDebFileParser::UsePackage(pkgCache::PkgIterator &Pkg, + pkgCache::VerIterator &Ver) +{ + bool res = debListParser::UsePackage(Pkg, Ver); + // we use the full file path as a provides so that the file is found + // by its name + if(NewProvidesAllArch(Ver, DebFile, Ver.VerStr()) == false) + return false; + return res; +} + + + diff --git a/apt-pkg/deb/deblistparser.h b/apt-pkg/deb/deblistparser.h index baace79fe..92ec048b1 100644 --- a/apt-pkg/deb/deblistparser.h +++ b/apt-pkg/deb/deblistparser.h @@ -56,7 +56,8 @@ class debListParser : public pkgCacheGenerator::ListParser bool ParseProvides(pkgCache::VerIterator &Ver); bool NewProvidesAllArch(pkgCache::VerIterator &Ver, std::string const &Package, std::string const &Version); static bool GrabWord(std::string Word,WordList *List,unsigned char &Out); - + APT_HIDDEN unsigned char ParseMultiArch(bool const showErrors); + public: static unsigned char GetPrio(std::string Str); @@ -101,9 +102,17 @@ class debListParser : public pkgCacheGenerator::ListParser debListParser(FileFd *File, std::string const &Arch = ""); virtual ~debListParser() {}; +}; - private: - APT_HIDDEN unsigned char ParseMultiArch(bool const showErrors); +class debDebFileParser : public debListParser +{ + private: + std::string DebFile; + + public: + debDebFileParser(FileFd *File, std::string const &DebFile); + virtual bool UsePackage(pkgCache::PkgIterator &Pkg, + pkgCache::VerIterator &Ver); }; #endif diff --git a/apt-pkg/deb/debmetaindex.cc b/apt-pkg/deb/debmetaindex.cc index 6fd12add8..56eecdca1 100644 --- a/apt-pkg/deb/debmetaindex.cc +++ b/apt-pkg/deb/debmetaindex.cc @@ -471,6 +471,15 @@ class debSLTypeDebian : public pkgSourceList::Type } }; +debDebFileMetaIndex::debDebFileMetaIndex(std::string const &DebFile) + : metaIndex(DebFile, "local-uri", "deb-dist"), DebFile(DebFile) +{ + DebIndex = new debDebPkgFileIndex(DebFile); + Indexes = new vector<pkgIndexFile *>(); + Indexes->push_back(DebIndex); +} + + class debSLTypeDeb : public debSLTypeDebian { public: @@ -507,5 +516,25 @@ class debSLTypeDebSrc : public debSLTypeDebian } }; +class debSLTypeDebFile : public pkgSourceList::Type +{ + public: + + bool CreateItem(vector<metaIndex *> &List, string const &URI, + string const &Dist, string const &Section, + std::map<string, string> const &Options) const + { + metaIndex *mi = new debDebFileMetaIndex(URI); + List.push_back(mi); + return true; + } + + debSLTypeDebFile() + { + Name = "deb-file"; + Label = "Debian Deb File"; + } +}; debSLTypeDeb _apt_DebType; debSLTypeDebSrc _apt_DebSrcType; +debSLTypeDebFile _apt_DebFileType; diff --git a/apt-pkg/deb/debmetaindex.h b/apt-pkg/deb/debmetaindex.h index 2286fa8b2..0e70bba87 100644 --- a/apt-pkg/deb/debmetaindex.h +++ b/apt-pkg/deb/debmetaindex.h @@ -18,6 +18,7 @@ class pkgAcquire; class pkgIndexFile; +class debDebPkgFileIndex; class debReleaseIndex : public metaIndex { public: @@ -71,4 +72,27 @@ class debReleaseIndex : public metaIndex { void PushSectionEntry(const debSectionEntry *Entry); }; +class debDebFileMetaIndex : public metaIndex +{ + private: + std::string DebFile; + debDebPkgFileIndex *DebIndex; + public: + virtual std::string ArchiveURI(std::string const& /*File*/) const { + return DebFile; + } + virtual bool GetIndexes(pkgAcquire* /*Owner*/, const bool& /*GetAll=false*/) const { + return true; + } + virtual std::vector<pkgIndexFile *> *GetIndexFiles() { + return Indexes; + } + virtual bool IsTrusted() const { + return true; + } + debDebFileMetaIndex(std::string const &DebFile); + virtual ~debDebFileMetaIndex() {}; + +}; + #endif diff --git a/apt-pkg/deb/debrecords.h b/apt-pkg/deb/debrecords.h index bdac6c90b..d572bc5c2 100644 --- a/apt-pkg/deb/debrecords.h +++ b/apt-pkg/deb/debrecords.h @@ -29,17 +29,16 @@ class debRecordParser : public pkgRecords::Parser { /** \brief dpointer placeholder (for later in case we need it) */ void *d; - + + protected: FileFd File; pkgTagFile Tags; pkgTagSection Section; - protected: - virtual bool Jump(pkgCache::VerFileIterator const &Ver); virtual bool Jump(pkgCache::DescFileIterator const &Desc); - public: + public: // These refer to the archive file for the Version virtual std::string FileName(); @@ -66,4 +65,15 @@ class debRecordParser : public pkgRecords::Parser virtual ~debRecordParser() {}; }; +// custom record parser that reads deb files directly +class debDebFileRecordParser : public debRecordParser +{ + public: + virtual std::string FileName() { + return File.Name(); + } + debDebFileRecordParser(std::string FileName,pkgCache &Cache) + : debRecordParser(FileName, Cache) {}; +}; + #endif |