Преглед изворни кода

* apt-pkg/deb/deblistparser.cc:
- use PackageArchitectureMatchesSpecification filter
* apt-pkg/cachefilter.cc:
- add PackageArchitectureMatchesSpecification (Closes: #672603)

David Kalnischkies пре 14 година
родитељ
комит
424ff669be
4 измењених фајлова са 90 додато и 28 уклоњено
  1. 51 0
      apt-pkg/cachefilter.cc
  2. 30 0
      apt-pkg/cachefilter.h
  3. 5 27
      apt-pkg/deb/deblistparser.cc
  4. 4 1
      debian/changelog

+ 51 - 0
apt-pkg/cachefilter.cc

@@ -9,10 +9,12 @@
 #include <apt-pkg/cachefilter.h>
 #include <apt-pkg/error.h>
 #include <apt-pkg/pkgcache.h>
+#include <apt-pkg/strutl.h>
 
 #include <string>
 
 #include <regex.h>
+#include <fnmatch.h>
 
 #include <apti18n.h>
 									/*}}}*/
@@ -52,5 +54,54 @@ PackageNameMatchesRegEx::~PackageNameMatchesRegEx() {			/*{{{*/
 	delete pattern;
 }
 									/*}}}*/
+
+// CompleteArch to <kernel>-<cpu> tuple					/*{{{*/
+//----------------------------------------------------------------------
+/* The complete architecture, consisting of <kernel>-<cpu>. */
+static std::string CompleteArch(std::string const &arch) {
+	if (arch.find('-') != std::string::npos) {
+		// ensure that only -any- is replaced and not something like company-
+		std::string complete = std::string("-").append(arch).append("-");
+		complete = SubstVar(complete, "-any-", "-*-");
+		complete = complete.substr(1, complete.size()-2);
+		return complete;
+	}
+	else if (arch == "armel")		return "linux-arm";
+	else if (arch == "armhf")		return "linux-arm";
+	else if (arch == "lpia")		return "linux-i386";
+	else if (arch == "powerpcspe")		return "linux-powerpc";
+	else if (arch == "uclibc-linux-armel")	return "linux-arm";
+	else if (arch == "uclinux-armel")	return "uclinux-arm";
+	else if (arch == "any")			return "*-*";
+	else					return "linux-" + arch;
+}
+									/*}}}*/
+PackageArchitectureMatchesSpecification::PackageArchitectureMatchesSpecification(std::string const &pattern, bool const isPattern) :/*{{{*/
+					literal(pattern), isPattern(isPattern), d(NULL) {
+	complete = CompleteArch(pattern);
+}
+									/*}}}*/
+bool PackageArchitectureMatchesSpecification::operator() (char const * const &arch) {/*{{{*/
+	if (strcmp(literal.c_str(), arch) == 0 ||
+	    strcmp(complete.c_str(), arch) == 0)
+		return true;
+	std::string const pkgarch = CompleteArch(arch);
+	if (isPattern == true)
+		return fnmatch(complete.c_str(), pkgarch.c_str(), 0) == 0;
+	return fnmatch(pkgarch.c_str(), complete.c_str(), 0) == 0;
+}
+									/*}}}*/
+bool PackageArchitectureMatchesSpecification::operator() (pkgCache::PkgIterator const &Pkg) {/*{{{*/
+	return (*this)(Pkg.Arch());
+}
+									/*}}}*/
+bool PackageArchitectureMatchesSpecification::operator() (pkgCache::VerIterator const &Ver) {/*{{{*/
+	return (*this)(Ver.ParentPkg());
+}
+									/*}}}*/
+PackageArchitectureMatchesSpecification::~PackageArchitectureMatchesSpecification() {	/*{{{*/
+}
+									/*}}}*/
+
 }
 }

+ 30 - 0
apt-pkg/cachefilter.h

@@ -26,6 +26,36 @@ public:
 	~PackageNameMatchesRegEx();
 };
 									/*}}}*/
+// PackageArchitectureMatchesSpecification				/*{{{*/
+/** \class PackageArchitectureMatchesSpecification
+   \brief matching against architecture specification strings
+
+   The strings are of the format <kernel>-<cpu> where either component,
+   or the whole string, can be the wildcard "any" as defined in
+   debian-policy §11.1 "Architecture specification strings".
+
+   Examples: i386, mipsel, linux-any, any-amd64, any */
+class PackageArchitectureMatchesSpecification {
+	std::string literal;
+	std::string complete;
+	bool isPattern;
+	/** \brief dpointer placeholder (for later in case we need it) */
+	void *d;
+public:
+	/** \brief matching against architecture specification strings
+	 *
+	 * @param pattern is the architecture specification string
+	 * @param isPattern defines if the given \b pattern is a
+	 *        architecture specification pattern to match others against
+	 *        or if it is the fixed string and matched against patterns
+	 */
+	PackageArchitectureMatchesSpecification(std::string const &pattern, bool const isPattern = true);
+	bool operator() (char const * const &arch);
+	bool operator() (pkgCache::PkgIterator const &Pkg);
+	bool operator() (pkgCache::VerIterator const &Ver);
+	~PackageArchitectureMatchesSpecification();
+};
+									/*}}}*/
 }
 }
 #endif

+ 5 - 27
apt-pkg/deb/deblistparser.cc

@@ -15,6 +15,7 @@
 #include <apt-pkg/deblistparser.h>
 #include <apt-pkg/error.h>
 #include <apt-pkg/configuration.h>
+#include <apt-pkg/cachefilter.h>
 #include <apt-pkg/aptconfiguration.h>
 #include <apt-pkg/strutl.h>
 #include <apt-pkg/fileutl.h>
@@ -22,7 +23,6 @@
 #include <apt-pkg/md5.h>
 #include <apt-pkg/macros.h>
 
-#include <fnmatch.h>
 #include <ctype.h>
 									/*}}}*/
 
@@ -464,22 +464,6 @@ const char *debListParser::ConvertRelation(const char *I,unsigned int &Op)
    }
    return I;
 }
-
-/*
- * CompleteArch:
- *
- * The complete architecture, consisting of <kernel>-<cpu>.
- */
-static string CompleteArch(std::string const &arch) {
-    if (arch == "armel")              return "linux-arm";
-    if (arch == "armhf")              return "linux-arm";
-    if (arch == "lpia")               return "linux-i386";
-    if (arch == "powerpcspe")         return "linux-powerpc";
-    if (arch == "uclibc-linux-armel") return "linux-arm";
-    if (arch == "uclinux-armel")      return "uclinux-arm";
-
-    return (arch.find("-") != string::npos) ? arch : "linux-" + arch;
-}
 									/*}}}*/
 // ListParser::ParseDepends - Parse a dependency element		/*{{{*/
 // ---------------------------------------------------------------------
@@ -556,7 +540,7 @@ const char *debListParser::ParseDepends(const char *Start,const char *Stop,
 
    if (ParseArchFlags == true)
    {
-      string completeArch = CompleteArch(arch);
+      APT::CacheFilter::PackageArchitectureMatchesSpecification matchesArch(arch, false);
 
       // Parse an architecture
       if (I != Stop && *I == '[')
@@ -583,16 +567,10 @@ const char *debListParser::ParseDepends(const char *Start,const char *Stop,
 	       ++I;
 	    }
 
-	    if (stringcmp(arch,I,End) == 0) {
-	       Found = true;
-	    } else {
-	       std::string wildcard = SubstVar(string(I, End), "any", "*");
-	       if (fnmatch(wildcard.c_str(), completeArch.c_str(), 0) == 0)
-	          Found = true;
-	    }
-
-	    if (Found == true)
+	    std::string arch(I, End);
+	    if (arch.empty() == false && matchesArch(arch.c_str()) == true)
 	    {
+	       Found = true;
 	       if (I[-1] != '!')
 		  NegArch = false;
 	       // we found a match, so fast-forward to the end of the wildcards

+ 4 - 1
debian/changelog

@@ -1,9 +1,12 @@
 apt (0.9.6.1) UNRELEASED; urgency=low
 
   [ David Kalnischkies ]
-  * deb/deblistparser.cc:
+  * apt-pkg/deb/deblistparser.cc:
     - ensure that mixed positive/negative architecture wildcards
       are handled in the same way as dpkg handles them
+    - use PackageArchitectureMatchesSpecification filter
+  * apt-pkg/cachefilter.cc:
+    - add PackageArchitectureMatchesSpecification (Closes: #672603)
 
  -- David Kalnischkies <kalnischkies@gmail.com>  Thu, 14 Jun 2012 15:45:13 +0200