Discussion:
[Didier Verna] multiple string reads/writes of SB-IMPL::BAKQ-COMMA
Didier Verna
2013-10-11 08:27:43 UTC
Permalink
Hi,

on second thought, I'm forwarding this to sbcl-devel because I think
this might be a bug. The same scenario works fine with CCL. CMUCL gives
a note and a warning but still works:

CL-USER> (test 'a 'b)
; In: TEST 'A

; (TEST 'A 'B)
; ==>
; (LET (#)
; (SETQ #:G0 #)
; #:G0)
; Note: Variable LISP::BACKQ-COMMA defined but never used.
; ;

; Warning: These variables are undefined:
; #:G0 OBJ
; (A B)

The macroepansion is however similar to that of SBCL:

CL-USER> (macroexpand '(test 'a 'b))
(LET ((LISP::BACKQ-COMMA OBJ))
(SETQ #:G4368 (LIST 'A 'B))
#:G4368)
T
Douglas Katzman
2013-10-11 13:09:38 UTC
Permalink
You'll get correct results doing it this way -

(with-input-from-string (s "(defmacro test (&body body)

(let ((obj (gensym)))

`(let (,obj)

(setq ,obj (list ,@body))

,obj)))")
(eval (with-input-from-string
(s (write-to-string (read s) :pretty nil :readably t))
(read s))))
Post by Didier Verna
Hi,
on second thought, I'm forwarding this to sbcl-devel because I think
this might be a bug. The same scenario works fine with CCL. CMUCL gives
CL-USER> (test 'a 'b)
; In: TEST 'A
; (TEST 'A 'B)
; ==>
; (LET (#)
; (SETQ #:G0 #)
; #:G0)
; Note: Variable LISP::BACKQ-COMMA defined but never used.
; ;
; #:G0 OBJ
; (A B)
CL-USER> (macroexpand '(test 'a 'b))
(LET ((LISP::BACKQ-COMMA OBJ))
(SETQ #:G4368 (LIST 'A 'B))
#:G4368)
T
---------- Forwarded message ----------
Date: Fri, 11 Oct 2013 09:14:06 +0200
Subject: multiple string reads/writes of SB-IMPL::BAKQ-COMMA
Hello,
the backquote syntax gives me a problem when doing multiple (in fact 2)
CL-USER> (defmacro test (&body body)
(let ((obj (gensym)))
`(let (,obj)
,obj)))
TEST
CL-USER> (test 'foo 'bar)
(FOO BAR)
CL-USER> (with-input-from-string (s "(defmacro test (&body body)
(let ((obj (gensym)))
`(let (,obj)
,obj)))")
(eval (read s)))
STYLE-WARNING: redefining COMMON-LISP-USER::TEST in DEFMACRO
TEST
CL-USER> (test 'foo 'bar)
(FOO BAR)
;; Okay, but then...
CL-USER> (with-input-from-string (s "(defmacro test (&body body)
(let ((obj (gensym)))
`(let (,obj)
,obj)))")
(eval (with-input-from-string (s (prin1-to-string (read s)))
(read s))))
STYLE-WARNING: redefining COMMON-LISP-USER::TEST in DEFMACRO
TEST
CL-USER> (test 'foo 'bar)
; in: TEST 'FOO
; (LET ((SB-IMPL::BACKQ-COMMA OBJ))
; (SETQ #:G2191 (LIST 'FOO 'BAR))
; #:G2191)
;
; The variable SB-IMPL::BACKQ-COMMA is defined but never used.
; (SETQ #:G2191 (LIST 'FOO 'BAR))
;
; undefined variable: #:G2191
and it breaks. What happens is that in the first case, SBCL understands
that (SB-IMPL::BACKQ-COMMA OBJ) really means ,obj in the let form, but
if I read this expression, write it to a string and read it again for
evaluation, then it thinks that I'm trying to bind SB-IMPL::BACKQ-COMMA
to OBJ...
How can I avoid this behavior ?
Thanks !
--
Resistance is futile. You will be jazzimilated.
Lisp, Jazz, Aïkido: http://www.didierverna.info
--
Resistance is futile. You will be jazzimilated.
Lisp, Jazz, Aïkido: http://www.didierverna.info
------------------------------------------------------------------------------
October Webinars: Code for Performance
Free Intel webinars can help you accelerate application performance.
Explore tips for MPI, OpenMP, advanced profiling, and more. Get the most
from
the latest Intel processors and coprocessors. See abstracts and register >
http://pubads.g.doubleclick.net/gampad/clk?id=60134071&iu=/4140/ostg.clktrk
_______________________________________________
Sbcl-devel mailing list
https://lists.sourceforge.net/lists/listinfo/sbcl-devel
Faré
2013-10-11 22:46:25 UTC
Permalink
The heart of the issue is that the pretty-printer for LET forms is
confused by the comma.
A workaround would be to use (let ((,obj nil)) ...)
A fix would be to fix the pretty-printer of LET recognize SB-IMPL::BACKQ-COMMA
(and while we're at it FARE-QUASIQUOTE::UNQUOTE, etc.?) or better,
to be less clever with the printing of bindings, just setting the start column?

—♯ƒ • François-René ÐVB Rideau •Reflection&Cybernethics• http://fare.tunes.org
A successful [software] tool is one that was used to do something
undreamed of by its author.
— S. C. Johnson
Post by Douglas Katzman
You'll get correct results doing it this way -
(with-input-from-string (s "(defmacro test (&body body)
(let ((obj (gensym)))
`(let (,obj)
,obj)))")
(eval (with-input-from-string
(s (write-to-string (read s) :pretty nil :readably t))
(read s))))
Post by Didier Verna
Hi,
on second thought, I'm forwarding this to sbcl-devel because I think
this might be a bug. The same scenario works fine with CCL. CMUCL gives
CL-USER> (test 'a 'b)
; In: TEST 'A
; (TEST 'A 'B)
; ==>
; (LET (#)
; (SETQ #:G0 #)
; #:G0)
; Note: Variable LISP::BACKQ-COMMA defined but never used.
; ;
; #:G0 OBJ
; (A B)
CL-USER> (macroexpand '(test 'a 'b))
(LET ((LISP::BACKQ-COMMA OBJ))
(SETQ #:G4368 (LIST 'A 'B))
#:G4368)
T
---------- Forwarded message ----------
Date: Fri, 11 Oct 2013 09:14:06 +0200
Subject: multiple string reads/writes of SB-IMPL::BAKQ-COMMA
Hello,
the backquote syntax gives me a problem when doing multiple (in fact 2)
CL-USER> (defmacro test (&body body)
(let ((obj (gensym)))
`(let (,obj)
,obj)))
TEST
CL-USER> (test 'foo 'bar)
(FOO BAR)
CL-USER> (with-input-from-string (s "(defmacro test (&body body)
(let ((obj (gensym)))
`(let (,obj)
,obj)))")
(eval (read s)))
STYLE-WARNING: redefining COMMON-LISP-USER::TEST in DEFMACRO
TEST
CL-USER> (test 'foo 'bar)
(FOO BAR)
;; Okay, but then...
CL-USER> (with-input-from-string (s "(defmacro test (&body body)
(let ((obj (gensym)))
`(let (,obj)
,obj)))")
(eval (with-input-from-string (s (prin1-to-string (read s)))
(read s))))
STYLE-WARNING: redefining COMMON-LISP-USER::TEST in DEFMACRO
TEST
CL-USER> (test 'foo 'bar)
; in: TEST 'FOO
; (LET ((SB-IMPL::BACKQ-COMMA OBJ))
; (SETQ #:G2191 (LIST 'FOO 'BAR))
; #:G2191)
;
; The variable SB-IMPL::BACKQ-COMMA is defined but never used.
; (SETQ #:G2191 (LIST 'FOO 'BAR))
;
; undefined variable: #:G2191
and it breaks. What happens is that in the first case, SBCL understands
that (SB-IMPL::BACKQ-COMMA OBJ) really means ,obj in the let form, but
if I read this expression, write it to a string and read it again for
evaluation, then it thinks that I'm trying to bind SB-IMPL::BACKQ-COMMA
to OBJ...
How can I avoid this behavior ?
Thanks !
--
Resistance is futile. You will be jazzimilated.
Lisp, Jazz, Aïkido: http://www.didierverna.info
--
Resistance is futile. You will be jazzimilated.
Lisp, Jazz, Aïkido: http://www.didierverna.info
------------------------------------------------------------------------------
October Webinars: Code for Performance
Free Intel webinars can help you accelerate application performance.
Explore tips for MPI, OpenMP, advanced profiling, and more. Get the most
from
the latest Intel processors and coprocessors. See abstracts and register >
http://pubads.g.doubleclick.net/gampad/clk?id=60134071&iu=/4140/ostg.clktrk
_______________________________________________
Sbcl-devel mailing list
https://lists.sourceforge.net/lists/listinfo/sbcl-devel
------------------------------------------------------------------------------
October Webinars: Code for Performance
Free Intel webinars can help you accelerate application performance.
Explore tips for MPI, OpenMP, advanced profiling, and more. Get the most
from
the latest Intel processors and coprocessors. See abstracts and register >
http://pubads.g.doubleclick.net/gampad/clk?id=60134071&iu=/4140/ostg.clktrk
_______________________________________________
Sbcl-devel mailing list
https://lists.sourceforge.net/lists/listinfo/sbcl-devel
Didier Verna
2013-10-14 12:55:08 UTC
Permalink
Post by Douglas Katzman
You'll get correct results doing it this way -
(s (write-to-string (read s) :pretty nil :readably t))
Yes. In fact, I was fooled by the fact that PRIN1 and friends are
described to produce output suitable "for input to READ", but in fact
don't bind *PRINT-READABLY* (this is even mentioned explicitly in the
CLHS...).
--
Resistance is futile. You will be jazzimilated.

Lisp, Jazz, Aïkido: http://www.didierverna.info
Loading...