quicklisp在windows+emacs+slime+sbcl下无法使用的问题。可能有初学common lisp的同学会碰到,希望有用。
问题:sbcl+quicklisp在命令行环境下使用正常,但是在emacs+slime下无法使用quicklisp
原因:
sbcl的系统初始化文件内容如下(.sbclrc):
;;; The following lines added by ql:add-to-init-file:
#-quicklisp
(let ((quicklisp-init (merge-pathnames "quicklisp/setup.lisp"
(user-homedir-pathname))))
(when (probe-file quicklisp-init)
(load quicklisp-init)))
其中出问题的部分是(user-homedir-pathname)
在sbcl命令行下执行结果:
* (user-homedir-pathname)
#P"C:/Documents and Settings/user/"
<pre name="code" class="html"> * (user-homedir-pathname)
#P"C:/Documents and Settings/user/Application Data/"
下面代码是sbcl对函数user-homedir-pathname的实现,可以看出sbcl是根据系统的环境变量 HOME/USERPROFILE/HOMEPATH/HOMEDRIVE来计算的。查看系统环境变量(set命令)没有设置HOME,但是有HOMEPATH.
(defun user-homedir-namestring (&optional username)
(flet ((not-empty (x)
(and (not (equal x "")) x)))
(if username
(sb!unix:user-homedir username)
(or (not-empty (posix-getenv "HOME"))
#!+win32
(not-empty (posix-getenv "USERPROFILE"))
#!+win32
(let ((drive (not-empty (posix-getenv "HOMEDRIVE")))
(path (not-empty (posix-getenv "HOMEPATH"))))
(and drive path
(concatenate 'string drive path)))
#!-win32
(not-empty (sb!unix:uid-homedir (sb!unix:unix-getuid)))
(error "Couldn't find home directory.")))))
;;; (This is an ANSI Common Lisp function.)
(defun user-homedir-pathname (&optional host)
#!+sb-doc
"Return the home directory of the user as a pathname. If the HOME
environment variable has been specified, the directory it designates
is returned; otherwise obtains the home directory from the operating
system. HOST argument is ignored by SBCL."
(declare (ignore host))
(values
(parse-native-namestring
(or (user-homedir-namestring)
#!+win32
(sb!win32::get-folder-namestring sb!win32::csidl_profile))
*physical-host*
*default-pathname-defaults*
:as-directory t)))
* (posix-getenv "HOME")
"C:\\Documents and Settings\\user"
* (posix-getenv "HOME")
NIL
解决办法: 在系统目录中加入HOME变量,设置为C:\Documents and Settings\user.