From mboxrd@z Thu Jan 1 00:00:00 1970 X-Msuck: nntp://news.gmane.org/gmane.linux.lib.musl.general/2420 Path: news.gmane.org!not-for-mail From: Isaac Dunham Newsgroups: gmane.linux.lib.musl.general Subject: Re: Fix strverscmp Date: Wed, 5 Dec 2012 19:18:19 -0800 Message-ID: <20121205191819.e83c8c3c.idunham@lavabit.com> References: <20121205110959.87b6111a.idunham@lavabit.com> <20121205193520.GN20323@brightrain.aerifal.cx> <20121205164329.c5cd3a20.idunham@lavabit.com> <20121206010000.GO20323@brightrain.aerifal.cx> <20121205182101.d997eb6e.idunham@lavabit.com> <20121206022640.GQ20323@brightrain.aerifal.cx> Reply-To: musl@lists.openwall.com NNTP-Posting-Host: plane.gmane.org Mime-Version: 1.0 Content-Type: multipart/mixed; boundary="Multipart=_Wed__5_Dec_2012_19_18_19_-0800_ocdcEpW2t5Sg1FAj" X-Trace: ger.gmane.org 1354763914 30492 80.91.229.3 (6 Dec 2012 03:18:34 GMT) X-Complaints-To: usenet@ger.gmane.org NNTP-Posting-Date: Thu, 6 Dec 2012 03:18:34 +0000 (UTC) To: musl@lists.openwall.com Original-X-From: musl-return-2421-gllmg-musl=m.gmane.org@lists.openwall.com Thu Dec 06 04:18:48 2012 Return-path: Envelope-to: gllmg-musl@plane.gmane.org Original-Received: from mother.openwall.net ([195.42.179.200]) by plane.gmane.org with smtp (Exim 4.69) (envelope-from ) id 1TgRz2-0002wm-M8 for gllmg-musl@plane.gmane.org; Thu, 06 Dec 2012 04:18:44 +0100 Original-Received: (qmail 5156 invoked by uid 550); 6 Dec 2012 03:18:32 -0000 Mailing-List: contact musl-help@lists.openwall.com; run by ezmlm Precedence: bulk List-Post: List-Help: List-Unsubscribe: List-Subscribe: Original-Received: (qmail 5142 invoked from network); 6 Dec 2012 03:18:32 -0000 DomainKey-Signature: a=rsa-sha1; q=dns; c=nofws; s=lavabit; d=lavabit.com; b=I4y78RVGCAEbnDLtALS2wqaM09jNCSikLD+bJqwP5oTQjtBd536nZw4XyUC4v7COMFjXBTDZT8EwOBiJm86pxCeAXR/HX8zwIB9yrSTkPGOYg5422K3E0+A/mFWTYP2TLR78V30V48LukHYlOeSIrEzpS1ImrYeL57+Idd7KnCY=; h=Date:From:To:Subject:Message-Id:In-Reply-To:References:X-Mailer:Mime-Version:Content-Type; In-Reply-To: <20121206022640.GQ20323@brightrain.aerifal.cx> X-Mailer: Sylpheed 3.0.2 (GTK+ 2.20.1; i486-pc-linux-gnu) Xref: news.gmane.org gmane.linux.lib.musl.general:2420 Archived-At: This is a multi-part message in MIME format. --Multipart=_Wed__5_Dec_2012_19_18_19_-0800_ocdcEpW2t5Sg1FAj Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: 7bit On Wed, 5 Dec 2012 21:26:40 -0500 Rich Felker wrote: > > I'm getting the idea that that may actually work...in which case my > > last version is unneeded. > > Except, it breaks here: > > 00123 > > 001145 <-should be the lesser (the leading zeros) > > Yes, I was unaware of the leading-zero semantics when I wrote that. > See my revised email with a proposed algorithm. Which is almost exactly the same as the method below: > > OTOH, it could be done by recording the zero while walking up the chain: > > /*NOT tested*/ > > while (*l && *r && l[0]==r[0]){ > > if (l[0]='0'){ > > nozero=1; > > It can't set the flag unconditionally, only if the previous byte was > not a digit. Otherwise, non-leading zeros would break handling of > numeric differences. Fortunately for us, that appears to be incorrect: idunham@Caracal:~$ ./a.out jan012 jan0111 1 1 idunham@Caracal:~$ ./a.out jan0001 jan001 -1 -1 idunham@Caracal:~$ ./a.out 0001 001 -1 -1 idunham@Caracal:~$ ./a.out 001 0001 1 1 idunham@Caracal:~$ ./a.out 0012 00111 1 1 idunham@Caracal:~$ ./a.out 00012 00111 -1 -1 idunham@Caracal:~$ ./a.out 00120 00111 1 1 That's testing with the attached version. -- Isaac Dunham --Multipart=_Wed__5_Dec_2012_19_18_19_-0800_ocdcEpW2t5Sg1FAj Content-Type: text/x-csrc; name="strvers.c" Content-Disposition: attachment; filename="strvers.c" Content-Transfer-Encoding: 7bit #define _GNU_SOURCE #define _XOPEN_SOURCE 700 #include #include #include int str_vers_cmp(const char *l, const char *r){ int haszero=0; while (*l && *r && l[0]==r[0]){ if (l[0]=='0'){ haszero=0; } else if (!isdigit(l[0])) { haszero=1; } l++; r++; } if ((isdigit(l[0]) && isdigit(r[0]) ) && haszero) { //return the one with the longer substring of numbers int lenl=0, lenr=0, firstl=l[0], firstr=r[0]; while (isdigit(l++[0]) ) { lenl++; } while (isdigit(r++[0]) ) { lenr++; } if (lenl==lenr) { return (firstl - firstr); } else { return (lenl - lenr); } } else { return (l[0] - r[0]); } } int main(int argc, char **argv){ printf("%d\n%d\n",str_vers_cmp(argv[1], argv[2]), strverscmp(argv[1], argv[2])); } --Multipart=_Wed__5_Dec_2012_19_18_19_-0800_ocdcEpW2t5Sg1FAj--