1
;; Copyright (C) 1994 M. Hagiya, W. Schelter, T. Yuasa
3
;; This file is part of GNU Common Lisp, herein referred to as GCL
5
;; GCL is free software; you can redistribute it and/or modify it under
6
;; the terms of the GNU LIBRARY GENERAL PUBLIC LICENSE as published by
7
;; the Free Software Foundation; either version 2, or (at your option)
10
;; GCL is distributed in the hope that it will be useful, but WITHOUT
11
;; ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12
;; FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public
13
;; License for more details.
15
;; You should have received a copy of the GNU Library General Public License
16
;; along with GCL; see the file COPYING. If not, write to the Free Software
17
;; Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
28
(export '(find-all-symbols do-symbols do-external-symbols do-all-symbols with-package-iterator))
29
(export '(apropos apropos-list))
35
(proclaim '(optimize (safety 2) (space 3)))
38
(defmacro coerce-to-package (p)
45
(setq ,g (find-package (string ,g))))
46
(specific-error :package-error "Cannot coerce ~S to a package~%" ,p))
49
(defun find-all-symbols (string-or-symbol)
50
(when (symbolp string-or-symbol)
51
(setq string-or-symbol (symbol-name string-or-symbol)))
53
(multiple-value-bind (s i)
54
(find-symbol string-or-symbol p)
55
(if (or (eq i :internal) (eq i :external))
61
(defmacro do-symbols ((var &optional (package '*package*) (result-form nil))
63
(let ((p (gensym)) (i (gensym)) (l (gensym)) (q (gensym))
64
(loop (gensym)) (x (gensym))(y (gensym)) (break (gensym)) declaration)
65
(multiple-value-setq (declaration body) (find-declarations body))
66
`(let ((,p (coerce-to-package ,package)) ,var ,l )
68
(dolist (,q (cons ,p (package-use-list ,p)) (progn (setq ,var nil) ,result-form))
70
(,y ,x) (package-size ,q)
71
(declare (fixnum ,x ,y))
72
(if (not (eq ,p ,q)) (setq ,x 0))
73
(dotimes (,i (+ ,x ,y))
74
(setq ,l (if (< ,i ,x)
75
(si:package-internal ,q ,i)
76
(si:package-external ,q (- ,i ,x))))
78
(when (null ,l) (go ,break))
81
(eq :inherited (car (last (multiple-value-list
82
(find-symbol (symbol-name ,var) ,p))))))
89
(defmacro do-external-symbols
90
((var &optional (package '*package*) (result-form nil)) . body)
91
(let ((p (gensym)) (i (gensym)) (l (gensym))
92
(loop (gensym)) (break (gensym)) declaration)
93
(multiple-value-setq (declaration body)
94
(find-declarations body))
95
`(let ((,p (coerce-to-package ,package)) ,var ,l)
98
(dotimes (,i (package-size ,p) (progn (setq ,var nil) ,result-form))
99
(setq ,l (si:package-external ,p ,i))
101
(when (null ,l) (go ,break))
108
(defmacro do-all-symbols((var &optional (result-form nil)) . body)
109
`(dolist (.v (list-all-packages) ,result-form)
110
(do-symbols (,var .v)
114
(defun substringp (sub str)
115
(do ((i (- (length str) (length sub)))
119
(when (string-equal sub str :start2 j :end2 (+ j l))
123
(defun print-symbol-apropos (symbol)
125
(when (fboundp symbol)
126
(if (special-form-p symbol)
127
(princ " Special form")
128
(if (macro-function symbol)
130
(princ " Function"))))
131
(when (boundp symbol)
132
(if (constantp symbol)
133
(princ " Constant: ")
134
(princ " has value: "))
135
(prin1 (symbol-value symbol)))
139
;(defun apropos (string &optional package)
140
; (setq string (string string))
142
; (do-symbols (symbol package)
143
; (when (substringp string (string symbol))
144
; (print-symbol-apropos symbol)))
145
; (do ((p (package-use-list package) (cdr p)))
147
; (do-external-symbols (symbol (car p))
148
; (when (substringp string (string symbol))
149
; (print-symbol-apropos symbol)))))
151
; (do-all-symbols (symbol)
152
; (when (substringp string (string symbol))
153
; (print-symbol-apropos symbol)))))
157
(defun apropos-list (string &optional package &aux list)
159
(setq string (string string))
161
(do-symbols (symbol package)
162
(when (substringp string (string symbol))
163
(setq list (cons symbol list))))
164
(do ((p (package-use-list package) (cdr p)))
166
(do-external-symbols (symbol (car p))
167
(when (substringp string (string symbol))
168
(setq list (cons symbol list))))))
170
(do-all-symbols (symbol)
171
(when (substringp string (string symbol))
172
(setq list (cons symbol list))))))
173
(stable-sort (delete-duplicates list :test #'eq)
174
#'string< :key #'symbol-name))
176
(defun apropos (string &optional package)
177
(dolist (symbol (apropos-list string package))
178
(print-symbol-apropos symbol))
181
(defmacro with-package-iterator ((name plist &rest symbol-types) . body)
182
(let ((p (gensym)) (i (gensym)) (l (gensym)) (q (gensym)) (dum (gensym))
183
(x (gensym))(y (gensym)) (access (gensym)) declaration)
184
(multiple-value-setq (declaration body) (si::find-declarations body))
185
(if (null symbol-types)
186
(specific-error :too-few-arguments "Symbol type specifiers must be supplied"))
187
`(let ((,p (cons t (if (atom ,plist) (list ,plist) ,plist))) (,q nil) (,l nil)
188
(,i -1) (,x 0) (,y 0) (,dum nil) (,access nil))
189
(declare (fixnum ,x ,y))
192
(when (null (setq ,l (cdr ,l)))
193
(when (eql (incf ,i) (+ ,x ,y))
194
(when (null (setq ,q (cdr ,q)))
195
(when (null (setq ,p (cdr ,p)))
196
(return-from ,name nil))
197
(rplaca ,p (coerce-to-package (car ,p)))
199
(si::coerce-to-package (car ,p))))
200
(when (member :inherited (list ,@symbol-types))
201
(rplacd ,q (package-use-list (car ,q)))))
202
(multiple-value-setq (,y ,x) (si::package-size (car ,q)))
203
(when (or (not (member :internal (list ,@symbol-types)))
204
(not (eq (car ,p) (car ,q))))
206
(when (and (not (member :external (list ,@symbol-types)))
207
(eq (car ,p) (car ,q)))
209
(when (zerop (+ ,x ,y))
213
(setq ,l (if (< ,i ,x)
214
(si::package-internal (car ,q) ,i)
215
(si::package-external (car ,q) (- ,i ,x)))))
218
(multiple-value-setq (,dum ,access)
220
(symbol-name (car ,l)) (car ,p)))
221
(when (and (not (eq ,access :inherited))
222
(not (eq (car ,p) (car ,q))))
224
(values 't (car ,l) ,access (car ,p))))