newtree/source/ver_check.c
Jeff Teunissen 8465917ed1 Stole a proper version comparison function from dpkg. Version strings
(for sv_minqfversion) are no longer compared as floats, so a server admin
can require client versions with a lot more granularity. (e.g. 0.2.99beta5
is greater than 0.2.99beta4, but lower than 0.3.0)
2000-11-26 09:48:01 +00:00

102 lines
2.2 KiB
C

/*
ver_check.c
Version number comparisons
Copyright (C) 1995 Ian Jackson <iwj10@cus.cam.ac.uk>
Copyright (C) 2000 Jeff Teunissen <deek@dusknet.dhs.org>
This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 2
of the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
See the GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to:
Free Software Foundation, Inc.
59 Temple Place - Suite 330
Boston, MA 02111-1307, USA
$Id$
*/
#ifdef HAVE_CONFIG_H
# include <config.h>
#endif
#include <stdlib.h>
#include <ctype.h>
/*
ver_compare
Compare two ASCII version strings. If the first is greater than the second,
return a positive number. If the second is greater, return a negative. If
they are equal, return zero.
*/
int
ver_compare (const char *value, const char *reference)
{
const char *valptr, *refptr;
int vc, rc;
long vl, rl;
if (!value)
value = "";
if (!reference)
reference = "";
for (;;) {
valptr = value;
while (*valptr && !isdigit(*valptr)) // Scan past any non-digit chars
valptr++;
refptr = reference;
while (*refptr && !isdigit(*refptr)) // get past non-digits here too
refptr++;
for (;;) {
vc = (value == valptr) ? 0 : *value++;
rc = (reference == refptr) ? 0 : *reference++;
if ((!vc) && (!rc))
break;
if (vc && !isalpha (vc)) vc += 256; // ASCII charset
if (rc && !isalpha (rc)) rc += 256;
if (vc != rc)
return (vc - rc);
}
value = valptr;
reference = refptr;
vl = rl = 0;
if (isdigit (*valptr))
vl = strtol (value, (char **) &value, 10);
if (isdigit (*refptr))
rl = strtol (reference, (char **) &reference, 10);
if (vl != rl)
return (vl - rl);
if ((!*value) && (!*reference))
return 0;
if (!*value)
return -1;
if (!*reference)
return 1;
}
}