emacs-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

master 45c32d7 6/7: Fix byte-compiler crash for legal dynamic-binding co


From: Mattias Engdegård
Subject: master 45c32d7 6/7: Fix byte-compiler crash for legal dynamic-binding code
Date: Sat, 25 Sep 2021 14:30:50 -0400 (EDT)

branch: master
commit 45c32d7f00e225a78e6c8b2251de335e93e556e0
Author: Mattias Engdegård <mattiase@acm.org>
Commit: Mattias Engdegård <mattiase@acm.org>

    Fix byte-compiler crash for legal dynamic-binding code
    
    This should really be taken care of by a syntax normalisation step in
    the frontend, but there is no such step for non-lexbind code yet.
    
    * lisp/emacs-lisp/byte-opt.el (byte-optimize-letX): Tolerate bindingsa
    without initialising expressions.
    * test/lisp/emacs-lisp/bytecomp-tests.el (bytecomp-tests--test-cases):
    Add test cases.
---
 lisp/emacs-lisp/byte-opt.el            | 17 ++++++++++++-----
 test/lisp/emacs-lisp/bytecomp-tests.el |  8 ++++++++
 2 files changed, 20 insertions(+), 5 deletions(-)

diff --git a/lisp/emacs-lisp/byte-opt.el b/lisp/emacs-lisp/byte-opt.el
index c8a96fa..c8990f2 100644
--- a/lisp/emacs-lisp/byte-opt.el
+++ b/lisp/emacs-lisp/byte-opt.el
@@ -1367,17 +1367,24 @@ See Info node `(elisp) Integer Basics'."
                              (and (consp binding) (cadr binding)))
                            bindings)
                  ,const)
-       `(let* ,(butlast bindings) ,(cadar (last bindings)) ,const)))
+       `(let* ,(butlast bindings)
+          ,@(and (consp (car (last bindings)))
+                 (cdar (last bindings)))
+          ,const)))
 
     ;; Body is last variable.
-    (`(,head ,bindings ,(and var (pred symbolp) (pred (not keywordp))
-                             (pred (not booleanp))
-                             (guard (eq var (caar (last bindings))))))
+    (`(,head ,(and bindings
+                   (let last-var (let ((last (car (last bindings))))
+                                   (if (consp last) (car last) last))))
+             ,(and last-var             ; non-linear pattern
+                   (pred symbolp) (pred (not keywordp)) (pred (not booleanp))))
      (if (eq head 'let)
          `(progn ,@(mapcar (lambda (binding)
                              (and (consp binding) (cadr binding)))
                            bindings))
-       `(let* ,(butlast bindings) ,(cadar (last bindings)))))
+       `(let* ,(butlast bindings)
+          ,@(and (consp (car (last bindings)))
+                 (cdar (last bindings))))))
 
     (_ form)))
 
diff --git a/test/lisp/emacs-lisp/bytecomp-tests.el 
b/test/lisp/emacs-lisp/bytecomp-tests.el
index ded6351..d56c60b 100644
--- a/test/lisp/emacs-lisp/bytecomp-tests.el
+++ b/test/lisp/emacs-lisp/bytecomp-tests.el
@@ -573,6 +573,14 @@ inner loops respectively."
     (let ((_a 1)
           (_b 2))
       'z)
+    (let (x y)
+      y)
+    (let* (x y)
+      y)
+    (let (x y)
+      'a)
+    (let* (x y)
+      'a)
 
     ;; Check empty-list optimisations.
     (mapcar (lambda (x) (member x nil)) '("a" 2 nil))



reply via email to

[Prev in Thread] Current Thread [Next in Thread]