Skip to content

Commit afab4cb

Browse files
MattKaufmannragerdl
authored andcommitted
1. Quoting :doc note-4-4:
| Improvements have been made related to the reading of characters. In | particular, checks are now done for ASCII encoding and for the expected | char-code values for Space,Tab,Newline,Page, and | Rubout. Also, an error no longer occurs with certain uses of | non-standard characters. For example, it had caused an error to certify a | book after a single portcullis command of | (make-event `(defconst *my-null* ,(code-char 0))); but this is no longer | an issue. Thanks to Jared Davis for helpful correspondence that led us to | make these improvements. 2. Do not read .port file when include-book is done under certification.
1 parent a7c4034 commit afab4cb

8 files changed

+293
-138
lines changed

acl2-characters

256 Bytes
Binary file not shown.

acl2-check.lisp

+119-22
Original file line numberDiff line numberDiff line change
@@ -159,28 +159,125 @@ most-negative-fixnum = ~s."
159159
; ACL2 CHARACTERS
160160
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
161161

162-
; At one time we read the legal ACL2 characters from a string in a file, so
163-
; that we could be confident that we know exactly what they are. But if
164-
; code-char is not a function, then we lose anyhow, because we have defined it
165-
; in ACL2. And if code-char is a function, then we can do our checking without
166-
; having to get the characters from a file, the idea being that the range of
167-
; code-char on {0,1,...,255} is exactly the set of legal ACL2 characters.
168-
169-
; Note that this issue is orthogonal to the problem of ensuring that #\c is
170-
; read in as the same character in different ACL2 sessions, for any ACL2
171-
; character c. (Even #\Newline is potentially problematic, as its char-code is
172-
; 10 in most Common Lisps but is 13 in MCL!) Because of the latter issue, our
173-
; story about ACL2 could include a caveat that certified books may only be
174-
; soundly loaded into the same Lisp image in which they were certified. When
175-
; we say ``same lisp image'' we don't mean the same exact process necessarily,
176-
; but rather simply an invocation of the same saved image. Another reason for
177-
; such a caveat, independent of the character-reading issue, is that different
178-
; saved images may be tied into different compilers, thus making the object
179-
; files of the books incompatible.
180-
181-
; However, we believe that we can prevent the most serious assaults on
182-
; soundness due to implementation dependencies, simply by making notes in the
183-
; version string, state global 'acl2-version; see :DOC version.
162+
; It is difficult or impossible to ensure that #\c is read in as the same
163+
; character in different ACL2 sessions, for any ACL2 character c. (Even
164+
; #\Newline is potentially problematic, as its char-code is 10 in most Common
165+
; Lisps but is 13 in [now-obsolete] MCL!) Thus, the soundness of ACL2 rests on
166+
; a caveat that all books are certified using the same Lisp image. When we say
167+
; ``same lisp image'' we don't mean the same exact process necessarily, but
168+
; rather, an invocation of the same saved image. Another reason for such a
169+
; caveat, independent of the character-reading issue, is that different saved
170+
; images may be tied into different compilers, thus making the object files of
171+
; the books incompatible.
172+
173+
; Nevertheless, it would of course be nice if all host Lisp implementations of
174+
; ACL2 actually do agree on character and string constants provided by the Lisp
175+
; reader (based on *acl2-readtable*). Our first check is intended to address
176+
; this point, by providing some confidence that the host Lisp has an ASCII
177+
; character set. As explained above, we only intend soundness in the case that
178+
; all books are certified from scratch using the same host Lisp, and we do not
179+
; actually assume ASCII characters -- more precisely, we do not assume any
180+
; particular values for code-char and code-char -- so this check is not really
181+
; necessary, except for a claim about ASCII characters in "Precise Description
182+
; of the ACL2 Logic", which should perhaps be removed. However, as of January
183+
; 2012 we seem to be able to make the following check in all supported Lisps,
184+
; at least on our Linux and Mac OS platforms. It should be sound for users to
185+
; comment out this check, but with the understanding that ACL2 is taking
186+
; whatever the Lisp reader (using *acl2-readtable*) gives it.
187+
188+
(let ((filename "acl2-characters"))
189+
190+
; Why do we read from a separate file, rather than just saving the relevant
191+
; characters in the present file? For example, it may seem reasonable to use a
192+
; trusted host Lisp to obtain an alist by evaluating the following expression.
193+
194+
; (loop for i from 0 to 255 do (princ (cons i (code-char i))))
195+
196+
; Could the resulting the alist be placed into this file and used for the check
197+
; below?
198+
199+
; We run into a problem right away with that approach because of Control-D.
200+
; For example, try this
201+
202+
; (princ (cons 4 (code-char 4)))
203+
204+
; and then try quoting the output and reading it back in. Or,
205+
; try evaluating the following.
206+
207+
; (read-from-string (format nil "~a" (code-char 4)))
208+
209+
; We have seen an error in both cases.
210+
211+
; So instead, we originally generated the file acl2-characters as follows,
212+
; using an ACL2 image based on CCL.
213+
214+
; (with-open-file (str "acl2-characters" :direction :output)
215+
; (loop for i from 0 to 255
216+
; do (write-char (code-char i) str)))
217+
218+
(with-open-file
219+
(str filename :direction :input
220+
221+
; In SBCL and CLISP we have found the need to specify :external-format in order
222+
; to avoid errors. Note that (for example) in our SBCL,
223+
; (stream-external-format *terminal-io*) evaluates to (:UTF-8 :REPLACEMENT
224+
; #\REPLACEMENT_CHARACTER).
225+
226+
#+(or clisp sbcl) :external-format
227+
#+sbcl :iso-8859-1
228+
#+clisp
229+
; The following came from
230+
; http://en.wikibooks.org/wiki/Common_Lisp/Advanced_topics/Files_and_Directories
231+
; in January 2012.
232+
(ext:make-encoding :charset 'charset:iso-8859-1
233+
:line-terminator :unix))
234+
(loop for i from 0 to 255
235+
236+
; The function legal-acl2-character-p, called in bad-lisp-objectp for
237+
; characters and strings, checks that the char-code of any character that is
238+
; read must be between 0 and 255.
239+
240+
do (let ((temp (read-char str)))
241+
(when #-clisp (not (eql (char-code temp) i))
242+
243+
; In CLISP we find character 10 (Newline) at position 13 (expected Return).
244+
; Perhaps this has something to do CLISP's attempt to comply with the CL
245+
; HyperSpec Section 13.1.8, "Treatment of Newline during Input and Output".
246+
; But something is amiss. Consider for example the following log (with some
247+
; output edited in the case of the first two forms, but no editing of output
248+
; for the third form).
249+
250+
; ACL2 [RAW LISP]> (with-open-file (str "tmp" :direction :output)
251+
; (write-char (code-char 13) str))
252+
; #\Return
253+
; ACL2 [RAW LISP]> (with-open-file (str "tmp" :direction :input)
254+
; (equal (read-char str) (code-char 10)))
255+
; T
256+
; ACL2 [RAW LISP]> (format nil "~a" (code-char 13))
257+
; "
258+
; ACL2 [RAW LISP]>
259+
260+
; So our check for CLISP is incomplete, but as explained in the comment just
261+
; above this check, we can live with that.
262+
263+
#+clisp
264+
(and (not (eql (char-code temp) i))
265+
(not (eql i 13)))
266+
(error "Bad character in file ~s: character ~s at position ~s."
267+
filename (char-code temp) i))))))
268+
269+
; The check just above does not say anything about the five character names
270+
; that we support (see acl2-read-character-string), as described in :doc
271+
; characters; so we add suitable checks on these here.
272+
273+
(loop for pair in (pairlis '(#\Space #\Tab #\Newline #\Page #\Rubout)
274+
'(32 9 10 12 127))
275+
do (let* ((ch (car pair))
276+
(code (cdr pair))
277+
(val (char-code ch)))
278+
(or (eql val code)
279+
(error "(char-code ~s) evaluated to ~s (expected ~s)."
280+
ch val code))))
184281

185282
; Test that all purportedly standard characters are standard, and vice versa.
186283

acl2-startup-info.txt

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
11
"$Revision$"
2-
Mon Jan 2 18:01:03 CST 2012
2+
Mon Jan 9 09:51:15 CST 2012
33
Books Revision: 934

acl2.lisp

+7
Original file line numberDiff line numberDiff line change
@@ -1306,6 +1306,9 @@ which is saved just in case it's needed later.")
13061306
#\u
13071307
#'sharp-u-read))
13081308

1309+
(defvar *old-character-reader*
1310+
(get-dispatch-macro-character #\# #\\))
1311+
13091312
(defun modify-acl2-readtable (do-all-changes)
13101313
(let ((*readtable* *acl2-readtable*))
13111314

@@ -1405,6 +1408,10 @@ which is saved just in case it's needed later.")
14051408
(set-dispatch-macro-character #\#
14061409
#\=
14071410
#'reckless-sharp-equal-read)
1411+
(set-dispatch-macro-character
1412+
#\#
1413+
#\\
1414+
*old-character-reader*)
14081415

14091416
; Thanks to Jared Davis for contributing the code for #\Z and #\z (see
14101417
; serialize-raw.lisp). But is this readtable even necessary now that

all-files.txt

+1
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ Makefile
55
# README-images.html -- developer file
66
# The following is distributed but is not in the svn repository:
77
TAGS
8+
acl2-characters
89
acl2-check.lisp
910
acl2-fns.lisp
1011
acl2-init.lisp

axioms.lisp

+19
Original file line numberDiff line numberDiff line change
@@ -26066,6 +26066,7 @@
2606626066
with-parallelism-hazard-warnings ; for #+acl2-par
2606726067
warn-about-parallelism-hazard ; for #+acl2-par
2606826068
state-global-let* ; raw Lisp version for efficiency
26069+
with-reckless-readtable
2606926070
))
2607026071

2607126072
(defmacro with-live-state (form)
@@ -44951,6 +44952,24 @@ Lisp definition."
4495144952
'(:bt :break-bt :bt-break))
4495244953
(print-call-history)))
4495344954

44955+
(defmacro with-reckless-readtable (form)
44956+
44957+
; This macro creates a context in which reading takes place without usual
44958+
; checks that #n# is only used after #n= and without the usual restrictions on
44959+
; characters (specifically, *old-character-reader* is used rather than the ACL2
44960+
; character reader, #'acl2-character-reader). See *reckless-acl2-readtable*.
44961+
44962+
#+acl2-loop-only
44963+
form
44964+
#-acl2-loop-only
44965+
`(let ((*readtable* *reckless-acl2-readtable*)
44966+
44967+
; Since print-object$ binds *readtable* to *acl2-readtable*, we bind the latter
44968+
; here:
44969+
44970+
(*acl2-readtable* *reckless-acl2-readtable*))
44971+
,form))
44972+
4495444973
(defmacro set-debugger-enable (val)
4495544974

4495644975
; WARNING: Keep this documentation in sync with the initial setting of

ld.lisp

+10
Original file line numberDiff line numberDiff line change
@@ -18352,6 +18352,16 @@
1835218352
called without a ~c[:ttagsx] argument supplied, then the value of ~c[:ttagsx]
1835318353
defaults to the (explicit or default) value of the ~c[:ttags] argument.
1835418354

18355+
Improvements have been made related to the reading of characters. In
18356+
particular, checks are now done for ASCII encoding and for the expected
18357+
~ilc[char-code] values for ~c[Space],~c[Tab],~c[Newline],~c[Page], and
18358+
~c[Rubout]. Also, an error no longer occurs with certain uses of
18359+
non-standard characters. For example, it had caused an error to certify a
18360+
book after a single ~il[portcullis] ~il[command] of
18361+
~c[(make-event `(defconst *my-null* ,(code-char 0)))]; but this is no longer
18362+
an issue. Thanks to Jared Davis for helpful correspondence that led us to
18363+
make these improvements.
18364+
1835518365
~st[NEW FEATURES]
1835618366

1835718367
A new ``tau system'' provides a kind of ``type checker.'' ~l[tau-system].

0 commit comments

Comments
 (0)