Unbreak 32-bit ppc
[sbcl.git] / tests / type.impure.lisp
blob5194f78b1698f3a12529d0506951d7c152376af0
1 ;;;; This software is part of the SBCL system. See the README file for
2 ;;;; more information.
3 ;;;;
4 ;;;; While most of SBCL is derived from the CMU CL system, the test
5 ;;;; files (like this one) were written from scratch after the fork
6 ;;;; from CMU CL.
7 ;;;;
8 ;;;; This software is in the public domain and is provided with
9 ;;;; absolutely no warranty. See the COPYING and CREDITS files for
10 ;;;; more information.
12 (with-test (:name (subtypep or))
13 (let ((types '(character
14 integer fixnum (integer 0 10)
15 single-float (single-float -1.0 1.0) (single-float 0.1)
16 (real 4 8) (real -1 7) (real 2 11)
17 null symbol keyword
18 (member #\a #\b #\c) (member 1 #\a) (member 3.0 3.3)
19 (member #\a #\c #\d #\f) (integer -1 1)
20 unsigned-byte
21 (rational -1 7) (rational -2 4)
22 ratio
23 )))
24 (dolist (i types)
25 (dolist (j types)
26 (assert (subtypep i `(or ,i ,j)))
27 (assert (subtypep i `(or ,j ,i)))
28 (assert (subtypep i `(or ,i ,i ,j)))
29 (assert (subtypep i `(or ,j ,i)))
30 (dolist (k types)
31 (assert (subtypep `(or ,i ,j) `(or ,i ,j ,k)))
32 (assert (subtypep `(or ,i ,j) `(or ,k ,j ,i))))))))
34 ;;; gotchas that can come up in handling subtypeness as "X is a
35 ;;; subtype of Y if each of the elements of X is a subtype of Y"
36 (with-test (:name (subtypep single-float real or))
37 ;; The system isn't expected to understand the subtype
38 ;; relationship. But if it does, that'd be neat.
39 (multiple-value-bind (subtypep certainp)
40 (subtypep '(single-float -1.0 1.0)
41 '(or (real -100.0 0.0)
42 (single-float 0.0 100.0)))
43 (assert (or (and subtypep certainp)
44 (and (not subtypep) (not certainp))))))
46 (with-test (:name (subtypep single-float float))
47 (assert (subtypep 'single-float 'float)))
49 (with-test (:name (:type= integer :ranges or))
50 (assert (type-evidently-= '(integer 0 10)
51 '(or (integer 0 5) (integer 4 10)))))
53 ;;; Bug 50(c,d): numeric types with empty ranges should be NIL
54 (with-test (:name (:type= integer rational float :empty :bug-50c :bug-50d))
55 (assert (type-evidently-= 'nil '(integer (0) (0))))
56 (assert (type-evidently-= 'nil '(rational (0) (0))))
57 (assert (type-evidently-= 'nil '(float (0.0) (0.0)))))
59 ;;; sbcl-0.6.10 did (UPGRADED-ARRAY-ELEMENT-TYPE 'SOME-UNDEF-TYPE)=>T
60 ;;; and (UPGRADED-COMPLEX-PART-TYPE 'SOME-UNDEF-TYPE)=>T.
61 (with-test (:name (upgraded-array-element-type :undefined))
62 (assert-error (upgraded-array-element-type 'some-undef-type))
63 (assert (eql (upgraded-array-element-type t) t)))
65 (with-test (:name (upgraded-complex-part-type :undefined))
66 (assert-error (upgraded-complex-part-type 'some-undef-type))
67 (assert (subtypep (upgraded-complex-part-type 'fixnum) 'real)))
69 ;;; Do reasonable things with undefined types, and with compound types
70 ;;; built from undefined types.
71 (with-test (:name (typep :undefined :compound))
72 (assert (typep #(11) '(simple-array t 1)))
73 (assert (typep #(11) '(simple-array (or integer symbol) 1)))
74 (assert-error (typep #(11) '(simple-array undef-type 1)))
75 (assert (not (typep 11 '(simple-array undef-type 1)))))
76 (with-test (:name (subtypep :undefined :compound))
77 (assert (subtypep '(vector some-undef-type) 'vector))
78 (assert (not (subtypep '(vector some-undef-type) 'integer)))
79 (assert-tri-eq nil nil (subtypep 'utype-1 'utype-2))
80 (assert-tri-eq nil nil (subtypep '(vector utype-1) '(vector utype-2)))
81 (assert-tri-eq nil nil (subtypep '(vector utype-1) '(vector t)))
82 (assert-tri-eq nil nil (subtypep '(vector t) '(vector utype-2))))
84 ;;; ANSI specifically disallows bare AND and OR symbols as type specs.
85 (with-test (:name (typep :bare :compound error))
86 (assert-error (typep 11 'and))
87 (assert-error (typep 11 'or))
88 (assert-error (typep 11 'member))
89 (assert-error (typep 11 'values))
90 (assert-error (typep 11 'eql))
91 (assert-error (typep 11 'satisfies))
92 (assert-error (typep 11 'not)))
93 ;;; and while it doesn't specifically disallow illegal compound
94 ;;; specifiers from the CL package, we don't have any.
95 (with-test (:name (subtypep :illegal :compound error))
96 (assert-error (subtypep 'fixnum '(fixnum 1)))
97 (assert-error (subtypep 'class '(list)))
98 (assert-error (subtypep 'foo '(ratio 1/2 3/2)))
99 (assert-error (subtypep 'character '(character 10))))
100 #+nil ; doesn't yet work on PCL-derived internal types
101 (assert-error (subtypep 'lisp '(class)))
102 #+nil
103 (assert-error (subtypep 'bar '(method number number)))
105 ;;; Of course empty lists of subtypes are still OK.
106 (with-test (:name (typep :empty and or))
107 (assert (typep 11 '(and)))
108 (assert (not (typep 11 '(or)))))
110 ;;; bug 12: type system didn't grok nontrivial intersections
111 (with-test (:name (subtypep and :bug-12))
112 (assert-tri-eq t t (subtypep '(and symbol (satisfies keywordp)) 'symbol))
113 ;; I'm not sure this next test was saying what it thinks it's saying.
114 (assert-tri-eq nil t (subtypep '(and symbol (satisfies keywordp)) 'null))
115 (assert-tri-eq nil t (subtypep '(and symbol (satisfies keywordp)) 'nil))
116 ;; would be nice if this one could say T
117 (assert-tri-eq nil nil (subtypep '(satisfies keywordp) 'nil))
118 (assert-tri-eq t t (subtypep 'keyword 'symbol))
119 (assert-tri-eq nil t (subtypep 'symbol 'keyword))
120 (assert-tri-eq t t (subtypep 'ratio 'real))
121 (assert-tri-eq t t (subtypep 'ratio 'number)))
123 ;;; bug 50.g: Smarten up hairy type specifiers slightly. We may wish
124 ;;; to revisit this, perhaps by implementing a COMPLEMENT type
125 ;;; (analogous to UNION and INTERSECTION) to take the logic out of the
126 ;;; HAIRY domain.
127 (with-test (:name (subtypep atom cons :bug-50g))
128 (assert-tri-eq nil t (subtypep 'atom 'cons))
129 (assert-tri-eq nil t (subtypep 'cons 'atom)))
131 ;;; These two are desireable but not necessary for ANSI conformance;
132 ;;; maintenance work on other parts of the system broke them in
133 ;;; sbcl-0.7.13.11 -- CSR
134 (with-test (:name (subtypep not atom list cons))
135 #+nil
136 (assert-tri-eq nil t (subtypep '(not list) 'cons))
137 #+nil
138 (assert-tri-eq nil t (subtypep '(not float) 'single-float))
139 (assert-tri-eq t t (subtypep '(not atom) 'cons))
140 (assert-tri-eq t t (subtypep 'cons '(not atom))))
142 ;;; ANSI requires that SUBTYPEP relationships among built-in primitive
143 ;;; types never be uncertain, i.e. never return NIL as second value.
144 ;;; Prior to about sbcl-0.7.2.6, ATOM caused a lot of problems here
145 ;;; (because it's a negation type, implemented as a HAIRY-TYPE, and
146 ;;; CMU CL's HAIRY-TYPE logic punted a lot).
147 (with-test (:name (subtypep integer function atom list))
148 (assert-tri-eq t t (subtypep 'integer 'atom))
149 (assert-tri-eq t t (subtypep 'function 'atom))
150 (assert-tri-eq nil t (subtypep 'list 'atom))
151 (assert-tri-eq nil t (subtypep 'atom 'integer))
152 (assert-tri-eq nil t (subtypep 'atom 'function))
153 (assert-tri-eq nil t (subtypep 'atom 'list)))
155 ;;; ATOM is equivalent to (NOT CONS):
156 (with-test (:name (subtypep atom cons cons))
157 (assert-tri-eq t t (subtypep 'integer '(not cons)))
158 (assert-tri-eq nil t (subtypep 'list '(not cons)))
159 (assert-tri-eq nil t (subtypep '(not cons) 'integer))
160 (assert-tri-eq nil t (subtypep '(not cons) 'list)))
162 ;;; And we'd better check that all the named types are right. (We also
163 ;;; do some more tests on ATOM here, since once CSR experimented with
164 ;;; making it a named type.)
165 (with-test (:name (subtypep nil atom t))
166 (assert-tri-eq t t (subtypep 'nil 'nil))
167 (assert-tri-eq t t (subtypep 'nil 'atom))
168 (assert-tri-eq t t (subtypep 'nil 't))
169 (assert-tri-eq nil t (subtypep 'atom 'nil))
170 (assert-tri-eq t t (subtypep 'atom 'atom))
171 (assert-tri-eq t t (subtypep 'atom 't))
172 (assert-tri-eq nil t (subtypep 't 'nil))
173 (assert-tri-eq nil t (subtypep 't 'atom))
174 (assert-tri-eq t t (subtypep 't 't)))
176 ;;; Also, LIST is now somewhat special, in that (NOT LIST) should be
177 ;;; recognized as a subtype of ATOM:
178 (with-test (:name (subtypep not list atom))
179 (assert-tri-eq t t (subtypep '(not list) 'atom))
180 (assert-tri-eq nil t (subtypep 'atom '(not list))))
182 ;;; These used to fail, because when the two arguments to subtypep are
183 ;;; of different specifier-type types (e.g. HAIRY and UNION), there
184 ;;; are two applicable type methods -- in this case
185 ;;; HAIRY-COMPLEX-SUBTYPEP-ARG1-TYPE-METHOD and
186 ;;; UNION-COMPLEX-SUBTYPEP-ARG2-TYPE-METHOD. Both of these exist, but
187 ;;; [!%]INVOKE-TYPE-METHOD aren't smart enough to know that if one of
188 ;;; them returns NIL, NIL (indicating uncertainty) it should try the
189 ;;; other. However, as of sbcl-0.7.2.6 or so, CALL-NEXT-METHOD-ish
190 ;;; logic in those type methods fixed it.
191 (with-test (:name (subtypep not list float))
192 (assert-tri-eq nil t (subtypep '(not cons) 'list))
193 (assert-tri-eq nil t (subtypep '(not single-float) 'float)))
195 ;;; Somewhere along the line (probably when adding CALL-NEXT-METHOD-ish
196 ;;; logic in SUBTYPEP type methods) we fixed bug 58 too:
197 (with-test (:name (subtypep and integer :unknown))
198 (assert-tri-eq t t (subtypep '(and zilch integer) 'zilch))
199 (assert-tri-eq t t (subtypep '(and integer zilch) 'zilch)))
201 ;;; Bug 84: SB-KERNEL:CSUBTYPEP was a bit enthusiastic at
202 ;;; special-casing calls to subtypep involving *EMPTY-TYPE*,
203 ;;; corresponding to the NIL type-specifier; we were bogusly returning
204 ;;; NIL, T (indicating surety) for the following:
205 (with-test (:name (subtypep satisfies :undefined-function nil :bug-84))
206 (assert-tri-eq nil nil (subtypep '(satisfies some-undefined-fun) 'nil)))
208 ;;; It turns out that, as of sbcl-0.7.2, we require to be able to
209 ;;; detect this to compile src/compiler/node.lisp (and in particular,
210 ;;; the definition of the component structure). Since it's a sensible
211 ;;; thing to want anyway, let's test for it here:
212 (with-test (:name (subtypep or :unknown member))
213 (assert-tri-eq t t (subtypep '(or some-undefined-type (member :no-ir2-yet :dead))
214 '(or some-undefined-type (member :no-ir2-yet :dead)))))
216 ;;; BUG 158 (failure to compile loops with vector references and
217 ;;; increments of greater than 1) was a symptom of type system
218 ;;; uncertainty, to wit:
219 (with-test (:name (subtypep and or mod integer :bug-158))
220 (assert-tri-eq t t (subtypep '(and (mod 536870911) (or (integer 0 0) (integer 2 536870912)))
221 '(mod 536870911)))) ; aka SB-INT:INDEX.
223 ;;; floating point types can be tricky.
224 (with-test (:name (subtypep float single-float double-float member not))
225 (assert-tri-eq t t (subtypep '(member 0.0) '(single-float 0.0 0.0)))
226 (assert-tri-eq t t (subtypep '(member -0.0) '(single-float 0.0 0.0)))
227 (assert-tri-eq t t (subtypep '(member 0.0) '(single-float -0.0 0.0)))
228 (assert-tri-eq t t (subtypep '(member -0.0) '(single-float 0.0 -0.0)))
229 (assert-tri-eq t t (subtypep '(member 0.0d0) '(double-float 0.0d0 0.0d0)))
230 (assert-tri-eq t t (subtypep '(member -0.0d0) '(double-float 0.0d0 0.0d0)))
231 (assert-tri-eq t t (subtypep '(member 0.0d0) '(double-float -0.0d0 0.0d0)))
232 (assert-tri-eq t t (subtypep '(member -0.0d0) '(double-float 0.0d0 -0.0d0)))
234 (assert-tri-eq nil t (subtypep '(single-float 0.0 0.0) '(member 0.0)))
235 (assert-tri-eq nil t (subtypep '(single-float 0.0 0.0) '(member -0.0)))
236 (assert-tri-eq nil t (subtypep '(single-float -0.0 0.0) '(member 0.0)))
237 (assert-tri-eq nil t (subtypep '(single-float 0.0 -0.0) '(member -0.0)))
238 (assert-tri-eq nil t (subtypep '(double-float 0.0d0 0.0d0) '(member 0.0d0)))
239 (assert-tri-eq nil t (subtypep '(double-float 0.0d0 0.0d0) '(member -0.0d0)))
240 (assert-tri-eq nil t (subtypep '(double-float -0.0d0 0.0d0) '(member 0.0d0)))
241 (assert-tri-eq nil t (subtypep '(double-float 0.0d0 -0.0d0) '(member -0.0d0)))
243 (assert-tri-eq t t (subtypep '(member 0.0 -0.0) '(single-float 0.0 0.0)))
244 (assert-tri-eq t t (subtypep '(single-float 0.0 0.0) '(member 0.0 -0.0)))
245 (assert-tri-eq t t (subtypep '(member 0.0d0 -0.0d0) '(double-float 0.0d0 0.0d0)))
246 (assert-tri-eq t t (subtypep '(double-float 0.0d0 0.0d0) '(member 0.0d0 -0.0d0)))
248 (assert-tri-eq t t (subtypep '(not (single-float 0.0 0.0)) '(not (member 0.0))))
249 (assert-tri-eq t t (subtypep '(not (double-float 0.0d0 0.0d0)) '(not (member 0.0d0))))
251 (assert-tri-eq t t (subtypep '(float -0.0) '(float 0.0)))
252 (assert-tri-eq t t (subtypep '(float 0.0) '(float -0.0)))
253 (assert-tri-eq t t (subtypep '(float (0.0)) '(float (-0.0))))
254 (assert-tri-eq t t (subtypep '(float (-0.0)) '(float (0.0)))))
256 (with-test (:name :member-type-and-numeric)
257 ;; (MEMBER 0s0 -s0) used to appear to parse correctly,
258 ;; but it didn't because MAKE-MEMBER-TYPE returned a union type
259 ;; (OR (MEMBER 0.0) (SINGLE-FLOAT 0.0 0.0)) which was further reduced
260 ;; to just the numeric type, being a supertype of the singleton.
261 ;; The parsing problem became evident when any other member was added in,
262 ;; because in that case the member type is not a subtype of the numeric.
263 (let* ((x (sb-kernel:specifier-type '(member 0s0 foo -0s0)))
264 (m (find-if #'sb-kernel:member-type-p (sb-kernel:union-type-types x))))
265 (assert (equal (sb-kernel:member-type-members m) '(foo)))))
268 ;;;; Douglas Thomas Crosher rewrote the CMU CL type test system to
269 ;;;; allow inline type tests for CONDITIONs and STANDARD-OBJECTs, and
270 ;;;; generally be nicer, and Martin Atzmueller ported the patches.
271 ;;;; They look nice but they're nontrivial enough that it's not
272 ;;;; obvious from inspection that everything is OK. Let's make sure
273 ;;;; that things still basically work.
275 ;; structure type tests setup
276 (defstruct structure-foo1)
277 (defstruct (structure-foo2 (:include structure-foo1))
279 (defstruct (structure-foo3 (:include structure-foo2)))
280 (defstruct (structure-foo4 (:include structure-foo3))
281 y z)
283 ;; structure-class tests setup
284 (defclass structure-class-foo1 () () (:metaclass cl:structure-class))
285 (defclass structure-class-foo2 (structure-class-foo1)
286 () (:metaclass cl:structure-class))
287 (defclass structure-class-foo3 (structure-class-foo2)
288 () (:metaclass cl:structure-class))
289 (defclass structure-class-foo4 (structure-class-foo3)
290 () (:metaclass cl:structure-class))
292 ;; standard-class tests setup
293 (defclass standard-class-foo1 () () (:metaclass cl:standard-class))
294 (defclass standard-class-foo2 (standard-class-foo1)
295 () (:metaclass cl:standard-class))
296 (defclass standard-class-foo3 (standard-class-foo2)
297 () (:metaclass cl:standard-class))
298 (defclass standard-class-foo4 (standard-class-foo3)
299 () (:metaclass cl:standard-class))
301 ;; condition tests setup
302 (define-condition condition-foo1 (condition) ())
303 (define-condition condition-foo2 (condition-foo1) ())
304 (define-condition condition-foo3 (condition-foo2) ())
305 (define-condition condition-foo4 (condition-foo3) ())
306 (with-test (:name :add-subclassoid)
307 (flet ((has-subs (name n)
308 (= n (length (sb-kernel:classoid-subclasses
309 (sb-kernel:find-classoid name))))))
310 (assert (has-subs 'condition-foo1 3)) ; has foo{2,3,4}
311 (assert (has-subs 'condition-foo2 2)) ; has foo{3,4}
312 (assert (has-subs 'condition-foo3 1)) ; has foo4
313 (assert (has-subs 'condition-foo4 0))))
315 ;;; inline type tests
316 (format t "~&/setting up *TESTS-OF-INLINE-TYPE-TESTS*~%")
317 (defparameter *tests-of-inline-type-tests*
318 '(progn
320 ;; structure type tests
321 (assert (typep (make-structure-foo3) 'structure-foo2))
322 (assert (not (typep (make-structure-foo1) 'structure-foo4)))
323 (assert (typep (nth-value 1
324 (ignore-errors (structure-foo2-x
325 (make-structure-foo1))))
326 'type-error))
327 (assert (null (ignore-errors
328 (setf (structure-foo2-x (make-structure-foo1)) 11))))
330 ;; structure-class tests
331 (assert (typep (make-instance 'structure-class-foo3)
332 'structure-class-foo2))
333 (assert (not (typep (make-instance 'structure-class-foo1)
334 'structure-class-foo4)))
335 (assert (null (ignore-errors
336 (setf (slot-value (make-instance 'structure-class-foo1)
338 11))))
340 ;; standard-class tests
341 (assert (typep (make-instance 'standard-class-foo3)
342 'standard-class-foo2))
343 (assert (not (typep (make-instance 'standard-class-foo1)
344 'standard-class-foo4)))
345 (assert (null (ignore-errors
346 (setf (slot-value (make-instance 'standard-class-foo1) 'x)
347 11))))
349 ;; condition tests
350 (assert (typep (make-condition 'condition-foo3)
351 'condition-foo2))
352 (assert (not (typep (make-condition 'condition-foo1)
353 'condition-foo4)))
354 (assert (null (ignore-errors
355 (setf (slot-value (make-condition 'condition-foo1) 'x)
356 11))))
357 (assert (subtypep 'error 't))
358 (assert (subtypep 'simple-condition 'condition))
359 (assert (subtypep 'simple-error 'simple-condition))
360 (assert (subtypep 'simple-error 'error))
361 (assert (not (subtypep 'condition 'simple-condition)))
362 (assert (not (subtypep 'error 'simple-error)))
363 (assert (eq (car (sb-mop:class-direct-superclasses
364 (find-class 'simple-condition)))
365 (find-class 'condition)))
367 #+nil ; doesn't look like a good test
368 (let ((subclasses (mapcar #'find-class
369 '(simple-type-error
370 simple-error
371 simple-warning
372 sb-int:simple-file-error
373 sb-int:simple-style-warning))))
374 (assert (null (set-difference
375 (sb-mop:class-direct-subclasses (find-class
376 'simple-condition))
377 subclasses))))
379 ;; precedence lists
380 (assert (equal (sb-mop:class-precedence-list
381 (find-class 'simple-condition))
382 (mapcar #'find-class '(simple-condition
383 condition
384 sb-pcl::slot-object
385 t))))
386 (sb-mop:finalize-inheritance (find-class 'fundamental-stream))
387 ;; stream classes
388 (assert (equal (sb-mop:class-direct-superclasses (find-class
389 'fundamental-stream))
390 (mapcar #'find-class '(standard-object stream))))
391 (assert (null (set-difference
392 (sb-mop:class-direct-subclasses (find-class
393 'fundamental-stream))
394 (mapcar #'find-class '(fundamental-binary-stream
395 fundamental-character-stream
396 fundamental-output-stream
397 fundamental-input-stream)))))
398 (assert (equal (sb-mop:class-precedence-list (find-class
399 'fundamental-stream))
400 (mapcar #'find-class '(fundamental-stream
401 standard-object
402 sb-pcl::slot-object
403 stream
404 t))))
405 (assert (equal (sb-mop:class-precedence-list (find-class
406 'fundamental-stream))
407 (mapcar #'find-class '(fundamental-stream
408 standard-object
409 sb-pcl::slot-object stream
410 t))))
411 (assert (subtypep (find-class 'stream) (find-class t)))
412 (assert (subtypep (find-class 'fundamental-stream) 'stream))
413 (assert (not (subtypep 'stream 'fundamental-stream)))))
415 ;;; Test under the interpreter.
416 (with-test (:name (:inline-type-tests :interpreted))
417 (eval *tests-of-inline-type-tests*)
418 (format t "~&/done with interpreted *TESTS-OF-INLINE-TYPE-TESTS*~%"))
420 ;;; Test under the compiler.
421 (defun tests-of-inline-type-tests ()
422 #.*tests-of-inline-type-tests*)
423 (with-test (:name (:inline-type-tests :compiled))
424 (tests-of-inline-type-tests)
425 (format t "~&/done with compiled (TESTS-OF-INLINE-TYPE-TESTS)~%"))
427 ;;; Redefinition of classes should alter the type hierarchy (BUG 140):
428 (defclass superclass () ())
429 (defclass maybe-subclass () ())
430 (assert-tri-eq nil t (subtypep 'maybe-subclass 'superclass))
431 (defclass maybe-subclass (superclass) ())
432 (assert-tri-eq t t (subtypep 'maybe-subclass 'superclass))
433 (defclass maybe-subclass () ())
434 (assert-tri-eq nil t (subtypep 'maybe-subclass 'superclass))
436 ;;; Prior to sbcl-0.7.6.27, there was some confusion in ARRAY types
437 ;;; specialized on some as-yet-undefined type which would cause this
438 ;;; program to fail (bugs #123 and #165). Verify that it doesn't.
439 (defun foo (x)
440 (declare (type (vector bar) x))
441 (aref x 1))
442 (deftype bar () 'single-float)
443 (with-test (:name (array :unknown :element-type))
444 (assert (eql (foo (make-array 3 :element-type 'bar :initial-element 0.0f0))
445 0.0f0)))
447 (with-test (:name (sb-kernel:type= :bug-260a))
448 (let* ((s (gensym))
449 (t1 (sb-kernel:specifier-type s)))
450 (eval `(defstruct ,s))
451 (assert-tri-eq t t (sb-kernel:type= t1 (sb-kernel:specifier-type s)))))
453 ;;; bug found by PFD's random subtypep tester
454 (with-test (:name (subtypep cons rational integer single-float))
455 (let ((t1 '(cons rational (cons (not rational) (cons integer t))))
456 (t2 '(not (cons (integer 0 1) (cons single-float long-float)))))
457 (assert-tri-eq t t (subtypep t1 t2))
458 (assert-tri-eq nil t (subtypep t2 t1))
459 (assert-tri-eq t t (subtypep `(not ,t2) `(not ,t1)))
460 (assert-tri-eq nil t (subtypep `(not ,t1) `(not ,t2)))))
462 ;;; not easily visible to user code, but this used to be very
463 ;;; confusing.
464 (with-test (:name (:ctor typep function))
465 (assert (eval '(typep (sb-pcl::ensure-ctor
466 (list 'sb-pcl::ctor (gensym)) nil nil nil)
467 'function))))
468 (with-test (:name (:ctor functionp))
469 (assert (functionp (sb-pcl::ensure-ctor
470 (list 'sb-pcl::ctor (gensym)) nil nil nil))))
471 ;;; some new (2008-10-03) ways of going wrong...
472 (with-test (:name (:ctor allocate-instance typep function))
473 (assert (eval '(typep (allocate-instance (find-class 'sb-pcl::ctor))
474 'function))))
475 (with-test (:name (:ctor allocate-instance functionp))
476 (assert (functionp (allocate-instance (find-class 'sb-pcl::ctor)))))
478 ;;; from PFD ansi-tests
479 (with-test (:name (subtypep :complex-cons-type))
480 (let ((t1 '(cons (cons (cons (real -744833699 -744833699) cons)
481 (integer -234496 215373))
482 integer))
483 (t2 '(cons (cons (cons integer integer)
484 (integer -234496 215373))
485 t)))
486 (assert-tri-eq nil t (subtypep `(not ,t2) `(not ,t1)))))
488 (defstruct misc-629a)
489 (defclass misc-629b () ())
490 (defclass misc-629c () () (:metaclass sb-mop:funcallable-standard-class))
492 (with-test (:name (typep subtypep defstruct defclass))
493 (assert (typep (make-misc-629a) 'sb-kernel:instance))
494 (assert-tri-eq t t (subtypep `(member ,(make-misc-629a)) 'sb-kernel:instance))
495 (assert-tri-eq nil t (subtypep `(and (member ,(make-misc-629a)) sb-kernel:instance)
496 nil))
497 (let ((misc-629a (make-misc-629a)))
498 (assert-tri-eq t t (subtypep `(member ,misc-629a)
499 `(and (member ,misc-629a) sb-kernel:instance)))
500 (assert-tri-eq t t (subtypep `(and (member ,misc-629a)
501 sb-kernel:funcallable-instance)
502 nil)))
504 (assert (typep (make-instance 'misc-629b) 'sb-kernel:instance))
505 (assert-tri-eq t t (subtypep `(member ,(make-instance 'misc-629b))
506 'sb-kernel:instance))
507 (assert-tri-eq nil t (subtypep `(and (member ,(make-instance 'misc-629b))
508 sb-kernel:instance)
509 nil))
510 (let ((misc-629b (make-instance 'misc-629b)))
511 (assert-tri-eq t t (subtypep `(member ,misc-629b)
512 `(and (member ,misc-629b) sb-kernel:instance)))
513 (assert-tri-eq t t (subtypep `(and (member ,misc-629b)
514 sb-kernel:funcallable-instance)
515 nil)))
517 (assert (typep (make-instance 'misc-629c) 'sb-kernel:funcallable-instance))
518 (assert-tri-eq t t (subtypep `(member ,(make-instance 'misc-629c))
519 'sb-kernel:funcallable-instance))
520 (assert-tri-eq nil t (subtypep `(and (member ,(make-instance 'misc-629c))
521 sb-kernel:funcallable-instance)
522 nil))
523 (let ((misc-629c (make-instance 'misc-629c)))
524 (assert-tri-eq t t (subtypep `(member ,misc-629c)
525 `(and (member ,misc-629c)
526 sb-kernel:funcallable-instance)))
527 (assert-tri-eq t t (subtypep `(and (member ,misc-629c)
528 sb-kernel:instance)
529 nil))))
531 ;;; this was broken during the FINALIZE-INHERITANCE rearrangement; the
532 ;;; MAKE-INSTANCE finalizes the superclass, thus invalidating the
533 ;;; subclass, so SUBTYPEP must be prepared to deal with
534 (defclass ansi-tests-defclass1 () ())
535 (defclass ansi-tests-defclass3 (ansi-tests-defclass1) ())
536 (with-test (:name (subtypep defclass make-instance))
537 (make-instance 'ansi-tests-defclass1)
538 (assert-tri-eq t t (subtypep 'ansi-tests-defclass3 'standard-object)))
540 ;;; so was this
541 (with-test (:name (type-of defclass :undefine))
542 (let ((class (eval '(defclass to-be-type-ofed () ()))))
543 (setf (find-class 'to-be-type-ofed) nil)
544 (assert (eq (type-of (make-instance class)) class))))
546 ;;; accuracy of CONS :SIMPLE-TYPE-=
547 (deftype goldbach-1 () '(satisfies even-and-greater-then-two-p))
548 (deftype goldbach-2 () '(satisfies sum-of-two-primes-p))
550 (with-test (:name (sb-kernel:type= cons satisfies integer))
551 (assert-tri-eq t t
552 (sb-kernel:type= (sb-kernel:specifier-type '(cons goldbach-1 integer))
553 (sb-kernel:specifier-type '(cons goldbach-1 integer))))
555 ;; See FIXME in type method for CONS :SIMPLE-TYPE-=
556 #+nil
557 (assert-tri-eq nil t
558 (sb-kernel:type= (sb-kernel:specifier-type '(cons goldbach-1 integer))
559 (sb-kernel:specifier-type '(cons goldbach-1 single-float))))
561 (assert-tri-eq nil nil
562 (sb-kernel:type= (sb-kernel:specifier-type '(cons goldbach-1 integer))
563 (sb-kernel:specifier-type '(cons goldbach-2 single-float)))))
565 ;;; precise unions of array types (was bug 306a)
566 (defun bug-306-a (x)
567 (declare (optimize speed)
568 (type (or (array cons) (array vector)) x))
569 (elt (aref x 0) 0))
570 (with-test (:name (array :element-type aref optimize speed :bug-306-a))
571 (assert (= 0 (bug-306-a #((0))))))
573 ;;; FUNCALLABLE-INSTANCE is a subtype of function.
574 (with-test (:name (subtypep function sb-kernel:funcallable-instance))
575 (assert-tri-eq t t (subtypep '(and pathname function) nil))
576 (assert-tri-eq t t (subtypep '(and pathname sb-kernel:funcallable-instance) nil))
577 (assert (not (subtypep '(and stream function) nil)))
578 (assert (not (subtypep '(and stream sb-kernel:funcallable-instance) nil)))
579 (assert (not (subtypep '(and function standard-object) nil)))
580 (assert (not (subtypep '(and sb-kernel:funcallable-instance standard-object) nil))))
582 ;;; also, intersections of classes with INSTANCE should not be too
583 ;;; general
584 (with-test (:name (subtypep standard-object sb-kernel:instance))
585 (assert (not (typep #'print-object '(and standard-object sb-kernel:instance))))
586 (assert (not (subtypep 'standard-object '(and standard-object sb-kernel:instance)))))
588 (with-test (:name (subtypep simple-array simple-string condition or))
589 (assert-tri-eq t t
590 (subtypep '(or simple-array simple-string) '(or simple-string simple-array)))
591 (assert-tri-eq t t
592 (subtypep '(or simple-string simple-array) '(or simple-array simple-string)))
593 (assert-tri-eq t t
594 (subtypep '(or fixnum simple-string end-of-file parse-error fixnum vector)
595 '(or fixnum vector end-of-file parse-error fixnum simple-string))))
597 (with-test (:name (subtypep function compiled-function :interpreted-function))
598 (assert-tri-eq nil t (subtypep 'compiled-function nil)) ; lp#1537003
599 ;; It is no longer the case that COMPILED-FUNCTION and INTERPRETED-FUNCTION
600 ;; form an exhaustive partition of FUNCTION.
601 ;; CLHS: "Implementations are free to define other subtypes of FUNCTION"
602 (assert-tri-eq nil nil (subtypep '(and function (not compiled-function)
603 (not sb-kernel:interpreted-function))
604 nil)))
606 ;;; weakening of union type checks
607 (defun weaken-union-1 (x)
608 (declare (optimize speed))
609 (car x))
610 (with-test (:name (:weaken-union type-error 1))
611 (assert-error (weaken-union-1 "askdjhasdkj") type-error))
613 (defun weaken-union-2 (x)
614 (declare (optimize speed)
615 (type (or cons fixnum) x))
616 (etypecase x
617 (fixnum x)
618 (cons
619 (setf (car x) 3)
620 x)))
621 (with-test (:name (:weaken-union type-error 2))
622 (multiple-value-bind (res err)
623 (ignore-errors (weaken-union-2 "asdkahsdkhj"))
624 (assert (not res))
625 (assert (typep err 'type-error))
626 (assert (or (equal '(or cons fixnum) (type-error-expected-type err))
627 (equal '(or fixnum cons) (type-error-expected-type err))))))
629 ;;; TYPEXPAND & Co
631 (deftype a-deftype (arg)
632 `(cons (eql ,arg) *))
634 (deftype another-deftype (arg)
635 `(a-deftype ,arg))
637 (deftype list-of-length (length &optional element-type)
638 (assert (not (minusp length)))
639 (if (zerop length)
640 'null
641 `(cons ,element-type (list-of-length ,(1- length) ,element-type))))
643 (with-test (:name sb-ext:typexpand-1)
644 (multiple-value-bind (expansion-1 expandedp-1)
645 (sb-ext:typexpand-1 '(another-deftype symbol))
646 (assert expandedp-1)
647 (assert (equal expansion-1 '(a-deftype symbol)))
648 (multiple-value-bind (expansion-2 expandedp-2)
649 (sb-ext:typexpand-1 expansion-1)
650 (assert expandedp-2)
651 (assert (equal expansion-2 '(cons (eql symbol) *)))
652 (multiple-value-bind (expansion-3 expandedp-3)
653 (sb-ext:typexpand-1 expansion-2)
654 (assert (not expandedp-3))
655 (assert (eq expansion-2 expansion-3))))))
657 (with-test (:name (sb-ext:typexpand 1))
658 (multiple-value-bind (expansion-1 expandedp-1)
659 (sb-ext:typexpand '(another-deftype symbol))
660 (assert expandedp-1)
661 (assert (equal expansion-1 '(cons (eql symbol) *)))
662 (multiple-value-bind (expansion-2 expandedp-2)
663 (sb-ext:typexpand expansion-1)
664 (assert (not expandedp-2))
665 (assert (eq expansion-1 expansion-2)))))
667 (with-test (:name (sb-ext:typexpand 2))
668 (assert (equal (sb-ext:typexpand '(list-of-length 3 fixnum))
669 '(cons fixnum (list-of-length 2 fixnum)))))
671 (with-test (:name sb-ext:typexpand-all)
672 (assert (equal (sb-ext:typexpand-all '(list-of-length 3))
673 '(cons t (cons t (cons t null)))))
674 (assert (equal (sb-ext:typexpand-all '(list-of-length 3 fixnum))
675 '(cons fixnum (cons fixnum (cons fixnum null))))))
677 (defclass a-deftype () ())
679 (with-test (:name (sb-ext:typexpand-1 :after-type-redefinition-to-class))
680 (multiple-value-bind (expansion expandedp)
681 (sb-ext:typexpand-1 '#1=(a-deftype symbol))
682 (assert (not expandedp))
683 (assert (eq expansion '#1#))))
685 (with-test (:name sb-ext:defined-type-name-p)
686 (assert (not (sb-ext:defined-type-name-p '#:foo)))
687 (assert (sb-ext:defined-type-name-p 'a-deftype))
688 (assert (sb-ext:defined-type-name-p 'structure-foo1))
689 (assert (sb-ext:defined-type-name-p 'structure-class-foo1))
690 (assert (sb-ext:defined-type-name-p 'standard-class-foo1))
691 (assert (sb-ext:defined-type-name-p 'condition-foo1))
692 (dolist (prim-type '(t nil fixnum cons atom))
693 (assert (sb-ext:defined-type-name-p prim-type))))
695 (with-test (:name (sb-ext:valid-type-specifier-p))
696 (macrolet ((yes (spec) `(assert (sb-ext:valid-type-specifier-p ',spec)))
697 (no (spec) `(assert (not (sb-ext:valid-type-specifier-p ',spec)))))
698 (no (cons #(frob) *))
699 (no list-of-length)
700 (no (list-of-length 5 #(x)))
701 (yes (list-of-length 5 fixnum))
703 (yes structure-foo1)
704 (no (structure-foo1 x))
705 (yes condition-foo1)
706 (yes standard-class-foo1)
707 (yes structure-class-foo1)
709 (yes readtable)
710 (no (readtable))
711 (no (readtable x))
713 (yes (values))
714 (no values)
715 (yes (and))
716 (no and)))
718 (with-test (:name (sb-ext:valid-type-specifier-p :introspection-test))
719 (flet ((map-functions (fn)
720 (do-all-symbols (s)
721 (when (and (fboundp s)
722 (not (macro-function s))
723 (not (special-operator-p s)))
724 (funcall fn s)))))
725 (map-functions
726 (lambda (name)
727 (let* ((fun (sb-kernel:%fun-fun (fdefinition name)))
728 (ftype (sb-kernel:%simple-fun-type fun)))
729 (unless (sb-ext:valid-type-specifier-p ftype)
730 (error "~@<~S returned NIL on ~S's FTYPE: ~2I~_~S~@:>"
731 'sb-ext:valid-type-specifier-p name ftype)))))))
733 (with-test (:name (:bug-309128 1))
734 (let* ((s (gensym))
735 (t1 (sb-kernel:specifier-type s)))
736 (eval `(defstruct ,s))
737 (assert-tri-eq t t (sb-kernel:csubtypep t1 (sb-kernel:specifier-type s)))))
739 (with-test (:name (:bug-309128 2))
740 (let* ((s (gensym))
741 (t1 (sb-kernel:specifier-type s)))
742 (eval `(defstruct ,s))
743 (assert-tri-eq t t (sb-kernel:csubtypep (sb-kernel:specifier-type s) t1))))
745 (with-test (:name (:bug-309128 3))
746 (let* ((s (gensym))
747 (t1 (sb-kernel:specifier-type s))
748 (s2 (gensym))
749 (t2 (sb-kernel:specifier-type s2)))
750 (eval `(deftype ,s2 () ',s))
751 (eval `(defstruct ,s))
752 (assert-tri-eq t t (sb-kernel:csubtypep t1 t2))))
754 (with-test (:name (sb-kernel:type= :unknown-type :not-equal))
755 (let* ((type (gensym "FOO"))
756 (spec1 (sb-kernel:specifier-type `(vector ,type)))
757 (spec2 (sb-kernel:specifier-type `(vector single-float))))
758 (eval `(deftype ,type () 'double-float))
759 (assert-tri-eq nil t (sb-kernel:type= spec1 spec2))))
761 (defclass subtypep-fwd-test1 (subtypep-fwd-test-unknown1) ())
762 (defclass subtypep-fwd-test2 (subtypep-fwd-test-unknown2) ())
763 (defclass subtypep-fwd-testb1 (subtypep-fwd-testb-unknown1) ())
764 (defclass subtypep-fwd-testb2 (subtypep-fwd-testb-unknown2 subtypep-fwd-testb1) ())
765 (with-test (:name (subtypep :forward-referenced-classes))
766 (flet ((test (c1 c2 b1 b2)
767 (multiple-value-bind (x1 x2) (subtypep c1 c2)
768 (unless (and (eq b1 x1) (eq b2 x2))
769 (error "(subtypep ~S ~S) => ~S, ~S but wanted ~S, ~S"
770 c1 c2 x1 x2 b1 b2)))))
771 (test 'subtypep-fwd-test1 'subtypep-fwd-test1 t t)
772 (test 'subtypep-fwd-test2 'subtypep-fwd-test2 t t)
773 (test 'subtypep-fwd-test1 'subtypep-fwd-test2 nil nil)
774 (test 'subtypep-fwd-test2 'subtypep-fwd-test1 nil nil)
776 (test 'subtypep-fwd-test1 'subtypep-fwd-test-unknown1 t t)
777 (test 'subtypep-fwd-test2 'subtypep-fwd-test-unknown2 t t)
778 (test 'subtypep-fwd-test1 'subtypep-fwd-test-unknown2 nil nil)
779 (test 'subtypep-fwd-test2 'subtypep-fwd-test-unknown1 nil nil)
781 (test 'subtypep-fwd-test-unknown2 'subtypep-fwd-test-unknown2 t t)
782 (test 'subtypep-fwd-test-unknown1 'subtypep-fwd-test-unknown1 t t)
783 (test 'subtypep-fwd-test-unknown1 'subtypep-fwd-test-unknown2 nil nil)
784 (test 'subtypep-fwd-test-unknown2 'subtypep-fwd-test-unknown1 nil nil)
786 (test 'subtypep-fwd-testb1 'subtypep-fwd-testb2 nil nil)
787 (test 'subtypep-fwd-testb2 'subtypep-fwd-testb1 t t)))
789 ;;; Array type unions have some tricky semantics.
791 (macrolet
792 ((disunity-test (name type-specifier-1 type-specifier-2)
793 `(with-test (:name ,name)
794 (let ((type1 (sb-kernel:specifier-type ',type-specifier-1))
795 (type2 (sb-kernel:specifier-type ',type-specifier-2)))
796 (assert (null (sb-kernel::%type-union2 type1 type2)))
797 (assert (null (sb-kernel::%type-union2 type2 type1))))))
798 (unity-test (name type-specifier-1 type-specifier-2 result-type-specifier)
799 `(with-test (:name ,name)
800 (let* ((type1 (sb-kernel:specifier-type ',type-specifier-1))
801 (type2 (sb-kernel:specifier-type ',type-specifier-2))
802 (rtype (sb-kernel:specifier-type ',result-type-specifier))
803 (res1 (sb-kernel::%type-union2 type1 type2))
804 (res2 (sb-kernel::%type-union2 type2 type1)))
805 ;; The (ARRAY :SIMPLE-=) type method doesn't always (or
806 ;; even usually) check the element type, preferring
807 ;; instead to check the upgraded element type. Therefore,
808 ;; check the element types ourselves.
809 (assert (and (sb-kernel:type= res1 rtype)
810 (sb-kernel:type=
811 (sb-kernel:array-type-element-type res1)
812 (sb-kernel:array-type-element-type rtype))))
813 (assert (and (sb-kernel:type= res2 rtype)
814 (sb-kernel:type=
815 (sb-kernel:array-type-element-type res2)
816 (sb-kernel:array-type-element-type rtype))))))))
818 (unity-test (:array-type-union :basic)
819 array
820 array
821 array)
823 (unity-test (:array-type-union :dimensional-compatability :wild)
824 (array * *)
825 (array * (* * *))
826 (array * *))
828 (disunity-test (:array-type-union :dimensional-compatability :incompatible 1)
829 (array * (* *))
830 (array * (* * *)))
832 (disunity-test (:array-type-union :dimensional-compatability :incompatible 2)
833 (array * (* 1 *))
834 (array * (* 2 *)))
836 (disunity-test (:array-type-union :dimensional-unity :only-one-dimension-per-union)
837 (array * (2 *))
838 (array * (* 3)))
840 (unity-test (:array-type-union :complexp-unity :moves-towards-maybe)
841 simple-array
842 (and array (not simple-array))
843 array)
845 (disunity-test (:array-type-union :complexp-and-dimensions-dont-unite 1)
846 (simple-array * (* *))
847 (and (array * (* 3)) (not simple-array)))
849 (disunity-test (:array-type-union :complexp-and-dimensions-dont-unite 2)
850 (simple-array * (* *))
851 (array * (* 3)))
853 (unity-test (:array-type-union :element-subtypes :unite-within-saetp)
854 (array (integer 15 27))
855 (array (integer 15 26))
856 (array (integer 15 27)))
858 (disunity-test (:array-type-union :element-subtypes :dont-unite-across-saetp)
859 (array (unsigned-byte 7))
860 (array (unsigned-byte 3)))
862 (disunity-test (:array-type-union :disjoint-element-types :dont-unite)
863 (array (integer 15 27))
864 (array (integer 17 30)))
866 (unity-test (:array-type-union :wild-element-type :unites)
867 array
868 (array (unsigned-byte 8))
869 array)
871 (disunity-test (:array-type-union :element-type-and-dimensions-dont-unite)
872 (array (unsigned-byte 8))
873 (array * (* *)))
875 (disunity-test (:array-type-union :element-type-and-complexp-dont-unite)
876 (simple-array (unsigned-byte 8))
877 (and array (not simple-array))))
879 ;;; These tests aren't really impure once the SHUFFLE function is provided.
880 ;;; Logically they belong with the above, so here they are.
881 (with-test (:name :union-of-all-arrays-is-array-of-wild)
882 (flet ((huge-union (fn)
883 (map 'list (lambda (x) (funcall fn (sb-vm:saetp-specifier x)))
884 sb-vm:*specialized-array-element-type-properties*)))
886 (let ((answers '(VECTOR
887 (SIMPLE-ARRAY * (*))
888 (AND VECTOR (NOT SIMPLE-ARRAY))
889 (VECTOR * 400)
890 (SIMPLE-ARRAY * (400))
891 (AND (VECTOR * 400) (NOT SIMPLE-ARRAY)))))
892 (dolist (dim '(() (400)))
893 (dolist (simpleness '(() (simple-array) ((not simple-array))))
894 (assert
895 (equal
896 (sb-kernel:type-specifier
897 (sb-kernel:specifier-type
898 `(or ,@(huge-union
899 (lambda (x) `(and ,@simpleness (vector ,x ,@dim)))))))
900 (pop answers))))))
902 ;; The algorithm is indifferent to non-array types.
903 (let ((result (sb-kernel:type-specifier
904 (sb-kernel:specifier-type
905 `(or list ,@(huge-union (lambda (x) `(array ,x (1 1 1)))))))))
906 (assert (or (equal result '(or list (array * (1 1 1))))
907 (equal result '(or (array * (1 1 1)) list)))))
909 ;; And unions of unions of distinct array types should reduce.
910 (assert
911 (equal
912 (sb-kernel:type-specifier
913 (sb-kernel:specifier-type
914 `(or (simple-array bletch (3 2 8))
915 ,@(huge-union
916 (lambda (x) `(and (not simple-array) (array ,x (2 2)))))
917 function
918 ,@(huge-union (lambda (x) `(simple-array ,x (10)))))))
919 '(or (simple-array bletch (3 2 8))
920 (and (array * (2 2)) (not simple-array))
921 function
922 (simple-array * (10)))))
924 ;; After uniting all simple and non-simple arrays of every specializer
925 ;; the result is just ARRAY.
926 (flet ((u (rank)
927 (shuffle ; should be insensitive to ordering
928 (nconc (huge-union
929 (lambda (x) `(and (not simple-array) (array ,x ,rank))))
930 (huge-union
931 (lambda (x) `(and (simple-array) (array ,x ,rank))))))))
932 (assert
933 (equal (sb-kernel:type-specifier
934 (sb-kernel:specifier-type `(or bit-vector ,@(u 2))))
935 '(or bit-vector (array * (* *)))))
936 (assert
937 (equal (sb-kernel:type-specifier
938 (sb-kernel:specifier-type `(or bit-vector ,@(u 1))))
939 'vector)))))
941 (with-test (:name :source-transform-union-of-arrays-typep)
942 ;; Ensure we don't pessimize rank 1 specialized array.
943 ;; (SIMPLE unboxed vector is done differently)
944 (let* ((hair (sb-kernel:specifier-type '(sb-kernel:unboxed-array 1)))
945 (xform (sb-c::source-transform-union-typep 'myobj hair)))
946 (assert (equal xform
947 '(or (typep myobj
948 '(and vector (not (array t)) (not (array nil))))))))
950 ;; Exclude one subtype at a time and make sure they all work.
951 (dotimes (i (length sb-vm:*specialized-array-element-type-properties*))
952 (let* ((excluded-type
953 (sb-vm:saetp-specifier
954 (aref sb-vm:*specialized-array-element-type-properties* i)))
955 (hair
956 (loop for x across sb-vm:*specialized-array-element-type-properties*
957 for j from 0
958 unless (eql i j)
959 collect `(array ,(sb-vm:saetp-specifier x))))
960 (xform
961 (sb-c::source-transform-union-typep 'myobj
962 (sb-kernel:specifier-type `(or ,@(shuffle hair) fixnum)))))
963 (assert (equal xform
964 `(or (typep myobj '(and array (not (array ,excluded-type))))
965 (typep myobj 'fixnum)))))))
967 (with-test (:name :interned-type-specifiers)
968 ;; In general specifiers can repeatedly parse the same due to
969 ;; the caching in VALUES-SPECIFIER-TYPE, provided that the entry
970 ;; was not evicted. Here we want to check a stronger condition,
971 ;; that they really always parse to the identical object.
972 (flet ((try (specifier)
973 (let ((parse1 (sb-kernel:specifier-type specifier)))
974 (sb-int:drop-all-hash-caches)
975 (let ((parse2 (sb-kernel:specifier-type specifier)))
976 (assert (eq parse1 parse2))))))
977 (mapc #'try
978 '((satisfies keywordp) ; not the same as KEYWORD
979 boolean
980 cons
981 null
982 character
983 integer
985 ;; one-dimensional arrays of unknown type
986 (array * (*))
987 (simple-array * (*))
988 (and (array * (*)) (not simple-array))
989 ;; floating-point
990 single-float
991 double-float
992 (complex single-float)
993 (complex double-float)))
994 ;; and check all specialized arrays
995 (sb-int:dovector (saetp sb-vm:*specialized-array-element-type-properties*)
996 (let ((spec (sb-vm:saetp-specifier saetp)))
997 (try `(array ,spec (*)))
998 (try `(simple-array ,spec (*)))
999 (try `(and (not simple-array) (array ,spec (*))))))))
1001 ;; The expansion of FRUITBAT is a class itself, not its name.
1002 (deftype fruitbat () (find-class 'hash-table))
1003 (with-test (:name :typexpand-into-classoid)
1004 (assert (eq (sb-kernel:specifier-type 'fruitbat)
1005 (sb-kernel:find-classoid 'hash-table))))
1007 (deftype foofa () 'single-float)
1008 (with-test (:name :redefine-deftype-to-defstruct)
1009 (defstruct foofa (a nil :type foofa)))
1011 (with-test (:name :undefine-class)
1012 (let ((class (gensym "CLASS")))
1013 (eval `(progn (defclass ,class () ())
1014 (lambda (x) (typep x ',class))
1015 (setf (find-class ',class) nil)))
1016 (checked-compile-and-assert (:allow-style-warnings t)
1017 `(lambda (x) (typep x ',class))
1018 ((10) (condition '(or error sb-kernel:parse-unknown-type))))
1019 (assert (handler-case (not (sb-kernel:specifier-type class))
1020 (sb-kernel:parse-unknown-type ()
1021 t)))))
1023 ;;; Try depthoid in excess of sb-kernel::layout-id-vector-fixed-capacity
1024 (defstruct d2) ; depthoid = 2
1025 (defstruct (d3(:include d2))) ; = 3
1026 (defstruct (d4(:include d3))) ; and so on
1027 (defstruct (d5(:include d4)))
1028 (defstruct (d6(:include d5)))
1029 (defstruct (d7(:include d6)))
1030 (defstruct (d8(:include d7)))
1031 (compile 'd8-p)
1032 (with-test (:name :deep-structure-is-a)
1033 (assert (d8-p (opaque-identity (make-d8)))))
1035 (with-test (:name :intersection-complex-=)
1036 (let ((unk (sb-kernel:specifier-type '(and unknown unknown2))))
1037 (assert-tri-eq nil nil (sb-kernel:type= (sb-kernel:specifier-type t) unk))
1038 (assert-tri-eq nil nil (sb-kernel:type= (sb-kernel:specifier-type 'integer) unk))
1039 (assert-tri-eq nil nil (sb-kernel:type= (sb-kernel:specifier-type 'float) unk))
1040 (assert-tri-eq nil nil (sb-kernel:type= (sb-kernel:specifier-type 'pathname) unk))
1041 (assert-tri-eq nil nil (sb-kernel:type= (sb-kernel:specifier-type 'sequence) unk))))
1043 (with-test (:name :lp-308938) ; got silently fixed in git rev ef8c95377a55
1044 (multiple-value-bind (answer certain)
1045 (subtypep '(or (satisfies x) string)
1046 '(or (satisfies x) integer))
1047 (assert (and (not answer) (not certain))))
1048 (multiple-value-bind (answer certain)
1049 (subtypep 'string '(or (satisfies x) integer))
1050 (assert (and (not answer) (not certain)))))
1052 (deftype jn-even () '(and integer (or (eql 0) (satisfies f))))
1053 (deftype jn-odd () '(and integer (or (eql 1) (satisfies g))))
1054 (with-test (:name :lp-1528837) ; probably the same as the preceding fix
1055 (multiple-value-bind (answer certain) (subtypep 'jn-odd 'jn-even)
1056 (assert (and (not answer) (not certain))))
1057 (multiple-value-bind (answer certain) (subtypep 'jn-even 'jn-odd)
1058 (assert (and (not answer) (not certain)))))