From owner-freebsd-ports Thu Oct 26 15: 0:30 2000 Delivered-To: freebsd-ports@freebsd.org Received: from mail.rdc1.kt.home.ne.jp (ha1.rdc1.kt.home.ne.jp [203.165.9.242]) by hub.freebsd.org (Postfix) with ESMTP id 4F2D637B479; Thu, 26 Oct 2000 15:00:19 -0700 (PDT) Received: from daemon.local.idaemons.org ([203.165.161.10]) by mail.rdc1.kt.home.ne.jp (InterMail vM.4.01.02.00 201-229-116) with ESMTP id <20001026220017.CWZU11444.mail.rdc1.kt.home.ne.jp@daemon.local.idaemons.org>; Thu, 26 Oct 2000 15:00:17 -0700 Received: by daemon.local.idaemons.org (8.11.0/3.7W) id e9QM0F105101; Fri, 27 Oct 2000 07:00:16 +0900 (JST) Date: Fri, 27 Oct 2000 07:00:15 +0900 Message-ID: <863dhj2rgw.wl@archon.local.idaemons.org> From: "Akinori MUSHA" To: freebsd-ports@FreeBSD.org Cc: bmah@FreeBSD.org Subject: Re: Enhancement of pkg_version's version comparison routine In-Reply-To: <86vgvi49a0.wl@archon.local.idaemons.org> References: <86k8by6eis.wl@archon.local.idaemons.org> <86wvfy4etq.wl@archon.local.idaemons.org> <86vgvi49a0.wl@archon.local.idaemons.org> User-Agent: Wanderlust/2.3.92 (Roam) EMIKO/1.13.12 (Euglena sociabilis) FLIM/1.13.2 (Kasanui) APEL/10.2 MULE XEmacs/21.1 (patch 12) (Channel Islands) (i386--freebsd) Organization: Associated I. Daemons X-PGP-Public-Key: finger knu@FreeBSD.org X-PGP-Fingerprint: 081D 099C 1705 861D 4B70 B04A 920B EFC7 9FD9 E1EE MIME-Version: 1.0 (generated by EMIKO 1.13.12 - "Euglena sociabilis") Content-Type: text/plain; charset=US-ASCII Sender: owner-freebsd-ports@FreeBSD.ORG Precedence: bulk X-Loop: FreeBSD.org Is this patch forgotten? pkg_version still does not conform to the version comparison rules specified in the Handbook. Aside from the introduction of `-t' option, at least CompareNumbers() part should be taken in unless there is a better implementation, I think. At Wed, 27 Sep 2000 15:51:51 +0900, I wrote: > Index: pkg_version.1 > =================================================================== > RCS file: /home/ncvs/src/usr.sbin/pkg_install/version/pkg_version.1,v > retrieving revision 1.8 > diff -u -r1.8 pkg_version.1 > --- pkg_version.1 2000/09/15 04:16:20 1.8 > +++ pkg_version.1 2000/09/26 20:23:39 > @@ -35,6 +35,8 @@ > .Op Fl cdhv > .Op Fl l Ar limchar > .Op Ar index > +.Nm pkg_version > +.Op Fl t Ar expression > .Sh DESCRIPTION > The > .Nm > @@ -93,6 +95,44 @@ > to the shell, it is best to quote > .Ar limchar > with single quotes. > +.It Fl t > +Test an expression and exit. It returns either 0 (true) or 1 (false). > +.It Ar expression > +Specify the expression to test, in one of the following forms: > +.Bl -tag -width Ar > +.It Ar \&v\&1 Cm \&= Ar \&v\&2 > +True if the versions > +.Ar \&v\&1 > +and > +.Ar \&v\&2 > +are identical. > +.It Ar \&v\&1 Cm \&!= Ar \&v\&2 > +True if the versions > +.Ar \&v\&1 > +and > +.Ar \&v\&2 > +are not identical. > +.It Ar \&v\&1 Cm \&< Ar \&v\&2 > +True if the version > +.Ar \&v\&1 > +is less than the version > +.Ar \&v\&2 . > +.It Ar \&v\&1 Cm \&> Ar \&v\&2 > +True if the version > +.Ar \&v\&1 > +is greater than the version > +.Ar \&v\&2 . > +.It Ar \&v\&1 Cm \&<= Ar \&v\&2 > +True if the version > +.Ar \&v\&1 > +is less than or equal to the version > +.Ar \&v\&2 . > +.It Ar \&v\&1 Cm \&>= Ar \&v\&2 > +True if the version > +.Ar \&v\&1 > +is greater than or equal to the version > +.Ar \&v\&2 . > +.El > .It Fl v > Enable verbose output. Verbose output includes some English-text > interpretations of the version number comparisons, as well as the > @@ -144,18 +184,20 @@ > suggestions, and then cut-and-paste (or retype) the commands you want to run. > .Pp > .Dl % pkg_version -c > do_update > +.Pp > +The following command tests if a version is less than another. > +.Pp > +.Dl % pkg_version -t '1.6.0.p3 < 1.6.0' && echo 'true!' > .Sh AUTHOR > .An Bruce A. Mah Aq bmah@FreeBSD.org > .Sh CONTRIBUTORS > .An Nik Clayton Aq nik@FreeBSD.org , > .An Dominic Mitchell Aq dom@palmerharvey.co.uk , > -.An Mark Ovens Aq marko@FreeBSD.org > +.An Mark Ovens Aq marko@FreeBSD.org , > +.An Akinori MUSHA Aq knu@FreeBSD.org > .Sh BUGS > There should be a better way of dealing with packages that > can have more than one installed version. > -.Pp > -Patch levels aren't handled > -very well (i.e. version numbers of the form 1.2p3 or 1.2pl3). > .Pp > Updates to packages > that don't change the version number (e.g. small delta bugfixes in the > Index: pkg_version.pl > =================================================================== > RCS file: /home/ncvs/src/usr.sbin/pkg_install/version/pkg_version.pl,v > retrieving revision 1.10 > diff -u -r1.10 pkg_version.pl > --- pkg_version.pl 2000/09/15 04:16:20 1.10 > +++ pkg_version.pl 2000/09/27 06:48:31 > @@ -57,38 +57,83 @@ > # This function returns -1, 0, or 1, in the same manner as <=> or cmp. > # > sub CompareNumbers { > - local($v1, $v2); > - $v1 = $_[0]; > - $v2 = $_[1]; > + my($v1, $v2) = @_; > > # Short-cut in case of equality > if ($v1 eq $v2) { > return 0; > } > > - # Loop over different components (the parts separated by dots). > - # If any component differs, we have the basis for an inequality. > - while (1) { > - ($p1, $v1) = split(/\./, $v1, 2); > - ($p2, $v2) = split(/\./, $v2, 2); > - > - # If we\'re out of components, they\'re equal (this probably won\'t > - # happen, since the short-cut case above should get this). > - if (($p1 eq "") && ($p2 eq "")) { > - return 0; > - } > - # Check for numeric inequality. We assume here that (for example) > - # 3.09 < 3.10. > - elsif ($p1 != $p2) { > - return $p1 <=> $p2; > + # Split into subnumbers > + my @s1 = split(/\./, $v1); > + my @s2 = split(/\./, $v2); > + > + # Subnumbers > + my($s1, $s2); > + > + # Seek for the difference > + do { > + last unless @s1 || @s2; > + > + $s1 = shift @s1; > + $s2 = shift @s2; > + } while ($s1 eq $s2); > + > + # Short-cut in case of equality > + if ($s1 eq $s2) { > + return 0; > + } > + > + # Split into sub-subnumbers > + my @x1 = split(/(\D+)/, $s1); > + my @x2 = split(/(\D+)/, $s2); > + > + shift @x1 if ($s1 =~ /^\D/); > + shift @x2 if ($s2 =~ /^\D/); > + > + # Sub-subnumbers > + my $x1 = shift @x1; > + my $x2 = shift @x2; > + > + # Check for alpha, beta, or pre > + if ($x1 =~ /^\D/) { # $x1: non-number > + if ($x2 !~ /^\D/) { # vs. $x2: number or null > + return -1; # -> $x2 wins > } > - # Check for string inequality, given numeric equality. This > - # handles version numbers of the form 3.4j < 3.4k. > - elsif ($p1 ne $p2) { > - return $p1 cmp $p2; > + > + if ($x1 ne $x2) { # vs. $x2: non-number > + return $x1 cmp $x2; # -> Compare in dictionary order > } > + } elsif ($x2 =~ /^\D/) { # $x1: number or null vs. $x2: non-number > + return 1; # -> $x1 wins > } > > + # Seek for the difference > + while ($x1 eq $x2) { > + last unless @x1 || @x2; > + > + $x1 = shift @x1; > + $x2 = shift @x2; > + } > + > + # Short-cut in case of equality > + if ($x1 eq $x2) { > + return 0; > + } > + > + if ($x1 =~ /^\d/) { # $x1: number > + if ($x2 =~ /^\d/) { # vs. $x2: number > + return $x1 <=> $x2; # -> Compare numerically > + } > + # vs. $x2: non-number or null > + return 1; # -> $x1 wins > + } > + # $x1: non-number or null > + if ($x2 =~ /^\d/) { # vs. $x2: number > + return -1; # -> $x2 wins > + } > + # vs. $x2: non-number or null > + return $x1 cmp $x2; # -> Compare in dictionary order > } > > # > @@ -197,6 +242,7 @@ > -d debug Debugging output (debug controls level of output) > -h Help (this message) > -l limchar Limit output > +-t expr Test expression > -v Verbose output > index URL or filename of index file > (Default is $IndexFile) > @@ -206,7 +252,7 @@ > # > # Parse command-line arguments, deal with them > # > -if (!getopts('cdhl:v') || ($opt_h)) { > +if (!getopts('cdhl:t:v') || ($opt_h)) { > &PrintHelp(); > exit; > } > @@ -218,6 +264,34 @@ > } > if ($opt_l) { > $LimitFlag = $opt_l; > +} > +if ($opt_t) { > + my $expr = $opt_t; > + > + $expr =~ s/\s+//g; > + > + my($v1, $op, $v2) = split(/([<>]=?|!?=)/, $expr, 2); > + > + if ($v2 eq '') { > + print "Invalid expression: $expr\n"; > + exit -1; > + } > + > + my $cmp = CompareVersions($v1, $v2); > + > + if ($op =~ / + exit($cmp < 0 ? 0 : 1); > + } > + > + if ($op =~ />/) { > + exit($cmp > 0 ? 0 : 1); > + } > + > + if ($op =~ /!/) { > + exit($cmp != 0 ? 0 : 1); > + } > + > + exit($cmp == 0 ? 0 : 1); > } > if ($opt_v) { > $VerboseFlag = 1; -- / /__ __ / ) ) ) ) / and.or.jp / ruby-lang.org Akinori -Aki- MUSHA aka / (_ / ( (__( @ idaemons.org / FreeBSD.org "We're only at home when we're on the run, on the wing, on the fly" To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe freebsd-ports" in the body of the message