* annoying correction of directory name to non-directory name for cd @ 2015-09-16 23:21 Vincent Lefevre 2015-09-17 1:07 ` Bart Schaefer 0 siblings, 1 reply; 7+ messages in thread From: Vincent Lefevre @ 2015-09-16 23:21 UTC (permalink / raw) To: zsh-workers zsh often proposes to correct a directory name to a non-directory name. This is annoying. For instance: % setopt CORRECT_ALL % touch shar % cd share/zsh zsh: correct 'share/zsh' to 'shar/zsh' [nyae]? where "share/zsh" is not in the current directory (but still valid via $cdpath). Or perhaps the correction system should take $cdpath into account. -- Vincent Lefèvre <vincent@vinc17.net> - Web: <https://www.vinc17.net/> 100% accessible validated (X)HTML - Blog: <https://www.vinc17.net/blog/> Work: CR INRIA - computer arithmetic / AriC project (LIP, ENS-Lyon) ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: annoying correction of directory name to non-directory name for cd 2015-09-16 23:21 annoying correction of directory name to non-directory name for cd Vincent Lefevre @ 2015-09-17 1:07 ` Bart Schaefer 2015-10-04 12:17 ` Vincent Lefevre 0 siblings, 1 reply; 7+ messages in thread From: Bart Schaefer @ 2015-09-17 1:07 UTC (permalink / raw) To: zsh-workers On Sep 17, 1:21am, Vincent Lefevre wrote: } } zsh often proposes to correct a directory name to a non-directory } name. This is annoying. } } Or perhaps the correction system should take $cdpath into account. CORRECT_ALL isn't intended to be that smart. It doesn't know or care what the command word is, and doesn't have access to all of the syntax analysis done by the completion system to understand what each word position means. It doesn't know your word is a directory, EXCEPT that, when AUTO_CD and the word is in command position, then it compares it against cdpath if nothing else looks better. alias cd="nocorrect cd" is always an option. We've bandied for years about the possiblity of somehow translating the completion system's syntax knowledge into performing correction, but that all boils down to walking over every word in the command to call the _correct completer on it, which isn't something that belongs in the core shell where CORRECT_ALL sits. ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: annoying correction of directory name to non-directory name for cd 2015-09-17 1:07 ` Bart Schaefer @ 2015-10-04 12:17 ` Vincent Lefevre 2015-10-04 17:06 ` Bart Schaefer 0 siblings, 1 reply; 7+ messages in thread From: Vincent Lefevre @ 2015-10-04 12:17 UTC (permalink / raw) To: zsh-workers On 2015-09-16 18:07:14 -0700, Bart Schaefer wrote: > On Sep 17, 1:21am, Vincent Lefevre wrote: > } zsh often proposes to correct a directory name to a non-directory > } name. This is annoying. > } > } Or perhaps the correction system should take $cdpath into account. > > CORRECT_ALL isn't intended to be that smart. It doesn't know or care > what the command word is, and doesn't have access to all of the syntax > analysis done by the completion system to understand what each word > position means. For the simplest cases, it doesn't need to know the meaning: when the word is followed by a slash, the filename must be a directory name. So, before proposing anything, the correction system should do such an additional check. At least it would avoid some false positives. -- Vincent Lefèvre <vincent@vinc17.net> - Web: <https://www.vinc17.net/> 100% accessible validated (X)HTML - Blog: <https://www.vinc17.net/blog/> Work: CR INRIA - computer arithmetic / AriC project (LIP, ENS-Lyon) ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: annoying correction of directory name to non-directory name for cd 2015-10-04 12:17 ` Vincent Lefevre @ 2015-10-04 17:06 ` Bart Schaefer 2015-10-04 18:29 ` Bart Schaefer 0 siblings, 1 reply; 7+ messages in thread From: Bart Schaefer @ 2015-10-04 17:06 UTC (permalink / raw) To: zsh-workers On Oct 4, 2:17pm, Vincent Lefevre wrote: } Subject: Re: annoying correction of directory name to non-directory name f } } On 2015-09-16 18:07:14 -0700, Bart Schaefer wrote: } > On Sep 17, 1:21am, Vincent Lefevre wrote: } > } zsh often proposes to correct a directory name to a non-directory } > } name. This is annoying. } > } > CORRECT_ALL isn't intended to be that smart. } } For the simplest cases, it doesn't need to know the meaning: when the } word is followed by a slash, the filename must be a directory name. Hmm. Does this do what you want? I've tried to minimize the stat()-ing to the names that are actually candidate corrections. diff --git a/Src/utils.c b/Src/utils.c index ab3b0c2..530b51e 100644 --- a/Src/utils.c +++ b/Src/utils.c @@ -2812,7 +2812,7 @@ spckword(char **s, int hist, int cmd, int ask) * as used in spscan(), so that an autocd is chosen * * only when it is better than anything so far, and * * so we prefer directories earlier in the cdpath. */ - if ((thisdist = mindist(*pp, *s, bestcd)) < d) { + if ((thisdist = mindist(*pp, *s, bestcd, 1)) < d) { best = dupstring(bestcd); d = thisdist; } @@ -4057,7 +4057,8 @@ spname(char *oldname) thresh = 3; else if (thresh > 100) thresh = 100; - if ((thisdist = mindist(newname, spnameguess, spnamebest)) >= thresh) { + thisdist = mindist(newname, spnameguess, spnamebest, *old == '/'); + if (thisdist >= thresh) { /* The next test is always true, except for the first path * * component. We could initialize bestdist to some large * * constant instead, and then compare to that constant here, * @@ -4082,12 +4083,13 @@ spname(char *oldname) /**/ static int -mindist(char *dir, char *mindistguess, char *mindistbest) +mindist(char *dir, char *mindistguess, char *mindistbest, int isdir) { int mindistd, nd; DIR *dd; char *fn; char *buf; + struct stat st; if (dir[0] == '\0') dir = "."; @@ -4096,7 +4098,7 @@ mindist(char *dir, char *mindistguess, char *mindistbest) buf = zalloc(strlen(dir) + strlen(mindistguess) + 2); sprintf(buf, "%s/%s", dir, mindistguess); - if (access(unmeta(buf), F_OK) == 0) { + if (stat(unmeta(buf), &st) == 0 && (!isdir || S_ISDIR(st.st_mode))) { strcpy(mindistbest, mindistguess); free(buf); return 0; @@ -4110,7 +4112,8 @@ mindist(char *dir, char *mindistguess, char *mindistbest) continue; nd = spdist(fn, mindistguess, (int)strlen(mindistguess) / 4 + 1); - if (nd <= mindistd) { + if (nd <= mindistd && + (!isdir || (stat(unmeta(fn), &st) == 0 && S_ISDIR(st.st_mode)))) { strcpy(mindistbest, fn); mindistd = nd; if (mindistd == 0) ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: annoying correction of directory name to non-directory name for cd 2015-10-04 17:06 ` Bart Schaefer @ 2015-10-04 18:29 ` Bart Schaefer 2015-10-04 20:14 ` Bart Schaefer 0 siblings, 1 reply; 7+ messages in thread From: Bart Schaefer @ 2015-10-04 18:29 UTC (permalink / raw) To: zsh-workers On Oct 4, 10:06am, Bart Schaefer wrote: } } - if (nd <= mindistd) { } + if (nd <= mindistd && } + (!isdir || (stat(unmeta(fn), &st) == 0 && S_ISDIR(st.st_mode)))) { That doesn't quite do it -- the stat() needs to be on the catenation of dir and fn. There's a buffer for this but it might need resizing. Updated patch later ... ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: annoying correction of directory name to non-directory name for cd 2015-10-04 18:29 ` Bart Schaefer @ 2015-10-04 20:14 ` Bart Schaefer 2015-10-05 10:10 ` Vincent Lefevre 0 siblings, 1 reply; 7+ messages in thread From: Bart Schaefer @ 2015-10-04 20:14 UTC (permalink / raw) To: zsh-workers On Oct 4, 11:29am, Bart Schaefer wrote: } Subject: Re: annoying correction of directory name to non-directory name f } } Updated patch later ... Mostly re-indentation but it seemed prudent to throw in a check for successful allocation while here. diff --git a/Src/utils.c b/Src/utils.c index ab3b0c2..61cbe84 100644 --- a/Src/utils.c +++ b/Src/utils.c @@ -2812,7 +2812,7 @@ spckword(char **s, int hist, int cmd, int ask) * as used in spscan(), so that an autocd is chosen * * only when it is better than anything so far, and * * so we prefer directories earlier in the cdpath. */ - if ((thisdist = mindist(*pp, *s, bestcd)) < d) { + if ((thisdist = mindist(*pp, *s, bestcd, 1)) < d) { best = dupstring(bestcd); d = thisdist; } @@ -4057,7 +4057,8 @@ spname(char *oldname) thresh = 3; else if (thresh > 100) thresh = 100; - if ((thisdist = mindist(newname, spnameguess, spnamebest)) >= thresh) { + thisdist = mindist(newname, spnameguess, spnamebest, *old == '/'); + if (thisdist >= thresh) { /* The next test is always true, except for the first path * * component. We could initialize bestdist to some large * * constant instead, and then compare to that constant here, * @@ -4082,42 +4083,52 @@ spname(char *oldname) /**/ static int -mindist(char *dir, char *mindistguess, char *mindistbest) +mindist(char *dir, char *mindistguess, char *mindistbest, int wantdir) { int mindistd, nd; DIR *dd; char *fn; char *buf; + struct stat st; + size_t dirlen; if (dir[0] == '\0') dir = "."; mindistd = 100; - buf = zalloc(strlen(dir) + strlen(mindistguess) + 2); + if (!(buf = zalloc((dirlen = strlen(dir)) + strlen(mindistguess) + 2))) + return 0; sprintf(buf, "%s/%s", dir, mindistguess); - if (access(unmeta(buf), F_OK) == 0) { + if (stat(unmeta(buf), &st) == 0 && (!wantdir || S_ISDIR(st.st_mode))) { strcpy(mindistbest, mindistguess); free(buf); return 0; } - free(buf); - if (!(dd = opendir(unmeta(dir)))) - return mindistd; - while ((fn = zreaddir(dd, 0))) { - if (spnamepat && pattry(spnamepat, fn)) - continue; - nd = spdist(fn, mindistguess, - (int)strlen(mindistguess) / 4 + 1); - if (nd <= mindistd) { - strcpy(mindistbest, fn); - mindistd = nd; - if (mindistd == 0) - break; + if ((dd = opendir(unmeta(dir)))) { + while ((fn = zreaddir(dd, 0))) { + if (spnamepat && pattry(spnamepat, fn)) + continue; + nd = spdist(fn, mindistguess, + (int)strlen(mindistguess) / 4 + 1); + if (nd <= mindistd) { + if (wantdir) { + if (!(buf = zrealloc(buf, dirlen + strlen(fn) + 2))) + continue; + sprintf(buf, "%s/%s", dir, fn); + if (stat(unmeta(buf), &st) != 0 || !S_ISDIR(st.st_mode)) + continue; + } + strcpy(mindistbest, fn); + mindistd = nd; + if (mindistd == 0) + break; + } } + closedir(dd); } - closedir(dd); + free(buf); return mindistd; } -- Barton E. Schaefer ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: annoying correction of directory name to non-directory name for cd 2015-10-04 20:14 ` Bart Schaefer @ 2015-10-05 10:10 ` Vincent Lefevre 0 siblings, 0 replies; 7+ messages in thread From: Vincent Lefevre @ 2015-10-05 10:10 UTC (permalink / raw) To: zsh-workers On 2015-10-04 13:14:34 -0700, Bart Schaefer wrote: > On Oct 4, 11:29am, Bart Schaefer wrote: > } Subject: Re: annoying correction of directory name to non-directory name f > } > } Updated patch later ... > > Mostly re-indentation but it seemed prudent to throw in a check for > successful allocation while here. [...] Thanks. It works as expected here. -- Vincent Lefèvre <vincent@vinc17.net> - Web: <https://www.vinc17.net/> 100% accessible validated (X)HTML - Blog: <https://www.vinc17.net/blog/> Work: CR INRIA - computer arithmetic / AriC project (LIP, ENS-Lyon) ^ permalink raw reply [flat|nested] 7+ messages in thread
end of thread, other threads:[~2015-10-05 10:10 UTC | newest] Thread overview: 7+ messages (download: mbox.gz / follow: Atom feed) -- links below jump to the message on this page -- 2015-09-16 23:21 annoying correction of directory name to non-directory name for cd Vincent Lefevre 2015-09-17 1:07 ` Bart Schaefer 2015-10-04 12:17 ` Vincent Lefevre 2015-10-04 17:06 ` Bart Schaefer 2015-10-04 18:29 ` Bart Schaefer 2015-10-04 20:14 ` Bart Schaefer 2015-10-05 10:10 ` Vincent Lefevre
Code repositories for project(s) associated with this public inbox https://git.vuxu.org/mirror/zsh/ This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for NNTP newsgroup(s).