summaryrefslogtreecommitdiff
path: root/src/evr.c
diff options
context:
space:
mode:
authorMichael Schroeder <mls@suse.de>2012-04-20 14:17:11 +0200
committerMichael Schroeder <mls@suse.de>2012-04-20 14:17:11 +0200
commitdda287fc18111054553c6dfd3a0cd7bafe5e6cb9 (patch)
tree0800b56754bedb06db0664dd801a2a48995ec203 /src/evr.c
parent110d964b72381c40af080db682e322e33b5bedb5 (diff)
downloadlibsolv-dda287fc18111054553c6dfd3a0cd7bafe5e6cb9.tar.gz
libsolv-dda287fc18111054553c6dfd3a0cd7bafe5e6cb9.tar.bz2
libsolv-dda287fc18111054553c6dfd3a0cd7bafe5e6cb9.zip
- support tilde in rpm version comparison
Diffstat (limited to 'src/evr.c')
-rw-r--r--src/evr.c77
1 files changed, 76 insertions, 1 deletions
diff --git a/src/evr.c b/src/evr.c
index a27ed09..4de8d64 100644
--- a/src/evr.c
+++ b/src/evr.c
@@ -73,6 +73,77 @@ solv_vercmp_rpm(const char *s1, const char *q1, const char *s2, const char *q2)
int r = 0;
const char *e1, *e2;
+ for (;;)
+ {
+ while (s1 < q1 && !(*s1 >= '0' && *s1 <= '9') &&
+ !(*s1 >= 'a' && *s1 <= 'z') && !(*s1 >= 'A' && *s1 <= 'Z') && *s1 != '~')
+ s1++;
+ while (s2 < q2 && !(*s2 >= '0' && *s2 <= '9') &&
+ !(*s2 >= 'a' && *s2 <= 'z') && !(*s2 >= 'A' && *s2 <= 'Z') && *s2 != '~')
+ s2++;
+ if (s1 < q1 && *s1 == '~')
+ {
+ if (s2 < q2 && *s2 == '~')
+ {
+ s1++;
+ s2++;
+ continue;
+ }
+ return -1;
+ }
+ if (s2 < q2 && *s2 == '~')
+ return 1;
+ if (s1 >= q1 || s2 >= q2)
+ break;
+ if ((*s1 >= '0' && *s1 <= '9') || (*s2 >= '0' && *s2 <= '9'))
+ {
+ while (*s1 == '0' && s1[1] >= '0' && s1[1] <= '9')
+ s1++;
+ while (*s2 == '0' && s2[1] >= '0' && s2[1] <= '9')
+ s2++;
+ for (e1 = s1; *e1 >= '0' && *e1 <= '9'; )
+ e1++;
+ for (e2 = s2; *e2 >= '0' && *e2 <= '9'; )
+ e2++;
+ r = (e1 - s1) - (e2 - s2);
+ if (!r)
+ r = strncmp(s1, s2, e1 - s1);
+ if (r)
+ return r > 0 ? 1 : -1;
+ }
+ else
+ {
+ for (e1 = s1; (*e1 >= 'a' && *e1 <= 'z') || (*e1 >= 'A' && *e1 <= 'Z'); )
+ e1++;
+ for (e2 = s2; (*e2 >= 'a' && *e2 <= 'z') || (*e2 >= 'A' && *e2 <= 'Z'); )
+ e2++;
+ r = (e1 - s1) - (e2 - s2);
+ if (r > 0)
+ {
+ r = strncmp(s1, s2, e2 - s2);
+ return r >= 0 ? 1 : -1;
+ }
+ if (r < 0)
+ {
+ r = strncmp(s1, s2, e1 - s1);
+ return r <= 0 ? -1 : 1;
+ }
+ r = strncmp(s1, s2, e1 - s1);
+ if (r)
+ return r > 0 ? 1 : -1;
+ }
+ s1 = e1;
+ s2 = e2;
+ }
+ return s1 < q1 ? 1 : s2 < q2 ? -1 : 0;
+}
+
+int
+solv_vercmp_rpm_notilde(const char *s1, const char *q1, const char *s2, const char *q2)
+{
+ int r = 0;
+ const char *e1, *e2;
+
while (s1 < q1 && s2 < q2)
{
while (s1 < q1 && !(*s1 >= '0' && *s1 <= '9') &&
@@ -133,8 +204,10 @@ solv_vercmp_rpm(const char *s1, const char *q1, const char *s2, const char *q2)
int
solv_vercmp(const char *s1, const char *q1, const char *s2, const char *q2)
{
-#ifdef DEBIAN
+#if defined(DEBIAN)
return solv_vercmp_deb(s1, q1, s2, q2);
+#elif defined(ARCHLINUX)
+ return solv_vercmp_rpm_notilde(s1, q1, s2, q2);
#else
return solv_vercmp_rpm(s1, q1, s2, q2);
#endif
@@ -144,6 +217,8 @@ solv_vercmp(const char *s1, const char *q1, const char *s2, const char *q2)
# define solv_vercmp (*(pool->disttype == DISTTYPE_DEB ? &solv_vercmp_deb : &solv_ver##cmp_rpm))
#elif defined(DEBIAN)
# define solv_vercmp solv_vercmp_deb
+#elif defined(ARCHLINUX)
+# define solv_vercmp solv_vercmp_rpm_notilde
#else
# define solv_vercmp solv_vercmp_rpm
#endif