[mcclim-devel] pathname completion on SBCL

Cyrus Harmon ch-mcclim at bobobeach.com
Fri Jun 19 05:19:17 UTC 2009


So it turns out that this was caused by a regression in SBCL, which  
has since been fixed. However, the current pathname completion is  
suboptimal in a couple of regards:

1. We attempt to match the pathname to the pathnames returned from the  
call to directory with the partial pathname, which correspond to the  
truenames of those files, which means that if there's a symbolic link  
in the path, we give up the completion.

2. currently, at least on SBCL, we still don't match files to a so-far  
that ends in a period, so that if we have foo.lisp and foo.asd, we  
type f-TAB, we get foo. and if we type l-TAB we expect to get  
foo.lisp, but we don't since the foo.*.* doesn't pick up foo.lisp due  
to the way we handle pathname types. Arguably this is a bug in SBCL,  
but I'm not convinced of this, nor of my ability to convince the other  
SBCL developers to change the current behavior to make mcclim pathname  
completion happy.

The following patch makes things better, but has the annoying bug that  
if we're matching a so-far of foo. and there's a file named foo, it  
backs up to "foo". Oh, the whole two directory calls thing reeks of a  
big, but I think this is an improvement. Of course it could still be  
better. I'm open to suggestions to how to fix it, but I feel strongly  
that good pathname completion is a must-have for a decent editing  
environment like climacs.

thanks,

cyrus

diff --git a/presentation-defs.lisp b/presentation-defs.lisp
index 8661046..ae203c4 100644
--- a/presentation-defs.lisp
+++ b/presentation-defs.lisp
@@ -1629,17 +1629,26 @@ protocol retrieving gestures from a provided  
string."))
                                               do (replace so-far "\ 
\*" :start1 occurence)
                                                  (setf start (+  
occurence 2))
                                               finally (return so-far)))
+                #+sbcl and #+sbcl wildcard2 #+sbcl = #+sbcl (format  
nil "~A*"
+                                       (loop for start = 0 ; Replace  
* -> \*
+                                             for occurence =  
(position #\* so-far :start start)
+                                             until (= start (length  
so-far))
+                                             until (null occurence)
+                                             do (replace so-far "\ 
\*" :start1 occurence)
+                                                (setf start (+  
occurence 2))
+                                             finally (return so-far)))
                  for path in
-                #+(or sbcl cmu lispworks) (directory wildcard)
+                #+sbcl (remove-duplicates (append (directory wildcard)
+                                                  (directory  
wildcard2))
+                                          :test #'equalp)
+                #+(or cmu lispworks) (directory wildcard)
                  #+openmcl (directory wildcard :directories t)
                  #+allegro (directory wildcard :directories-are-files  
nil)
                  #+cormanlisp (nconc (directory wildcard)
                                      (cl::directory-subdirs dirname))
                  #-(or sbcl cmu lispworks openmcl allegro cormanlisp)
                  (directory wildcard)
-                when (let ((mismatch (mismatch (namestring path) full- 
so-far)))
-                       (or (null mismatch) (= mismatch length)))
-                  collect path))
+                collect path))
           (strings (mapcar #'namestring pathnames))
           (first-string (car strings))
           (length-common-prefix nil)


but

On Jun 15, 2009, at 11:22 AM, Cyrus Harmon wrote:

> On recent SBCLs, at least, (directory "fo*.*") only finds foo if foo
> is a file, not a directory. Not sure if this is a bug or a feature,
> but it breaks my understanding of how filename completion should work.
> The following (slightly ugly) patch fixes things for me:
>
> diff --git a/presentation-defs.lisp b/presentation-defs.lisp
> index 8661046..fb2de97 100644
> --- a/presentation-defs.lisp
> +++ b/presentation-defs.lisp
> @@ -1629,8 +1629,21 @@ protocol retrieving gestures from a provided
> string."))
>                                               do (replace so-far "\
> \*" :start1 occurence)
>                                                  (setf start (+
> occurence 2))
>                                               finally (return so- 
> far)))
> +                #+sbcl and #+sbcl wildcard-directories #+sbcl =
> +                #+sbcl (format nil "~A*"
> +                        (loop for start = 0 ; Replace * -> \*
> +                          for occurence = (position #\* so-far :start
> start)
> +                          until (= start (length so-far))
> +                          until (null occurence)
> +                          do (replace so-far "\\*" :start1 occurence)
> +                            (setf start (+ occurence 2))
> +                          finally (return so-far)))
>                  for path in
> -                #+(or sbcl cmu lispworks) (directory wildcard)
> +                #+sbcl (remove-duplicates
> +                        (append (directory wildcard)
> +                                (directory wildcard-directories))
> +                        :test #'equal)
> +                #+(or cmu lispworks) (directory wildcard)
>                  #+openmcl (directory wildcard :directories t)
>                  #+allegro (directory wildcard :directories-are-files
> nil)
>                  #+cormanlisp (nconc (directory wildcard)
>
>
> Any suggestions on the best way to handle this?
>
> thanks,
>
> cyrus
>
>
> _______________________________________________
> mcclim-devel mailing list
> mcclim-devel at common-lisp.net
> http://common-lisp.net/cgi-bin/mailman/listinfo/mcclim-devel





More information about the mcclim-devel mailing list