Major Section: COMMON-LISP

The discussion below outlines a potential source of unsoundness in ACL2. Although to our knowledge there is no existing Lisp implementation in which this problem can arise, nevertheless we feel compelled to explain this situation.

Consider for example the question: What is the value of
`(equal 3 3)`

? According to the ACL2 axioms, it's `t`

. And as
far as we know, based on considerable testing, the value is `t`

in
every Common Lisp implementation. However, according the Common
Lisp draft proposed ANSI standard, any non-`nil`

value could result.
Thus for example, `(equal 3 3)`

is allowed by the standard to be `17`

.

The Common Lisp standard specifies (or soon will) that a number of
Common Lisp functions that one might expect to return Boolean values
may, in fact, return arbitrary values. Examples of such functions
are `equal`

, `rationalp`

, and `<`

; a much more complete list is
given below. Indeed, we dare to say that every Common Lisp function
that one may believe returns only Booleans is, nevertheless, not
specified by the standard to have that property, with the exceptions
of the functions `not`

and `null`

. The standard refers to such
arbitrary values as ``generalized Booleans,'' but in fact this
terminology makes no restriction on those values. Rather, it merely
specifies that they are to be viewed, in an informal sense, as being
either `nil`

or not `nil`

.

This situation is problematic for ACL2, which axiomatizes these
functions to return Booleans. The problem is that because (for
efficiency and simplicity) ACL2 makes very direct use of compiled
Common Lisp functions to support the execution of its functions,
there is in principle a potential for unsoundness due to these
``generalized Booleans.'' For example, ACL2's `equal`

function is
defined to be Common Lisp's `equal`

. Hence if in Common Lisp the
form `(equal 3 3)`

were to evaluate to 17, then in ACL2 we could
prove (using the `:`

`executable-counterpart`

of `equal`

)
`(equal (equal 3 3) 17)`

. However, ACL2 can also prove
`(equal (equal x x) t)`

, and these two terms together are
contradictory, since they imply (instantiating `x`

in the second
term by `3`

) that `(equal 3 3)`

is both equal to `17`

and to
`t`

.

To make matters worse, the standard allows `(equal 3 3)`

to evaluate
to *different* non-`nil`

values every time. That is: `equal`

need not even be a function!

Fortunately, no existing Lisp implementation takes advantage of the flexibility to have (most of) its predicates return generalized Booleans, as far as we know. We may implement appropriate safeguards in future releases of ACL2, in analogy to (indeed, probably extending) the existing safeguards by way of guards (see guard). For now, we'll sleep a bit better knowing that we have been up-front about this potential problem.

The following list of functions contains all those that are defined
in Common Lisp to return generalized Booleans but are assumed by
ACL2 to return Booleans. In addition, the functions `acl2-numberp`

and `complex-rationalp`

are directly defined in terms of
respective Common Lisp functions `numberp`

and `complexp`

.

/= < = alpha-char-p atom char-equal char< char<= char> char>= characterp consp digit-char-p endp eq eql equal evenp integerp keywordp listp logbitp logtest lower-case-p minusp oddp plusp rationalp standard-char-p string-equal string< string<= string> string>= stringp subsetp symbolp upper-case-p zerop