GNU bug report logs - #18031
24.3.92; bad indentation in shell script mode

Previous Next

Package: emacs;

Reported by: Gilles Pion <gpion <at> lfdj.com>

Date: Wed, 16 Jul 2014 12:09:01 UTC

Severity: minor

Found in version 24.3.92

Fixed in version 24.5

Done: Stefan Monnier <monnier <at> iro.umontreal.ca>

Bug is archived. No further changes may be made.

Full log


Message #10 received at 18031-done <at> debbugs.gnu.org (full text, mbox):

From: Stefan Monnier <monnier <at> iro.umontreal.ca>
To: Gilles Pion <gpion <at> lfdj.com>
Cc: 18031-done <at> debbugs.gnu.org
Subject: Re: bug#18031: 24.3.92; bad indentation in shell script mode
Date: Thu, 04 Dec 2014 10:09:59 -0500
Version:24.5

> Here's the result:
> #!/bin/ksh
> grep -e "^$userregexp:" /etc/passwd | cut -d :  -f 1 | while read user ; do
>                                                            print -u2
> "user=$user"
>                                                            sudo -U
> $user -ll | while read line ; do

>             :

>         done
>                                                        done

After fixing the above line-wrapping to really reproduce what Emacs
does, you'll see that it's indented in a way which is sensible:
- The "print -u2" line is indented 4 chars deeper than the "while" in
  which it's nested.
- The "user=$user" line is actually at the end of the previous line.
- The "sudo" line is aligned with the previous line.
- The ":" is indented 4 chars deeper than the "while" in which it's nested.
- The "done" are aligned with the "while" they close.

Now, I understand that "sensible" doesn't mean "good" or "desirable",
but at least the indentation works sanely (contrary to the bug#18756 case).
So it's a "small matter" of teaching sh-mode to indent the body of loops
less deeply when the loop itself doesn't start at the beginning of the line.

I installed the patch below which seems to do the trick.


        Stefan


diff --git a/lisp/ChangeLog b/lisp/ChangeLog
index 12e5ef0..26b09a6 100644
--- a/lisp/ChangeLog
+++ b/lisp/ChangeLog
@@ -1,3 +1,9 @@
+2014-12-04  Stefan Monnier  <monnier <at> iro.umontreal.ca>
+
+	* progmodes/sh-script.el (sh-smie-sh-rules): Go back to the beginning
+	of the whole pipe when indenting an opening keyword after a |.
+	Generalize this treatment to opening keywords like "while" (bug#18031).
+
 2014-12-01  Stefan Monnier  <monnier <at> iro.umontreal.ca>
 
 	* simple.el (newline): Place the hook buffer-locally,
diff --git a/lisp/progmodes/sh-script.el b/lisp/progmodes/sh-script.el
index 724d22a..1165144 100644
--- a/lisp/progmodes/sh-script.el
+++ b/lisp/progmodes/sh-script.el
@@ -1988,12 +1988,12 @@ May return nil if the line should not be treated as continued."
                    (and (numberp indent) (numberp initial)
                         (<= indent initial)))))
      `(column . ,(+ initial sh-indentation)))
-    (`(:before . ,(or `"(" `"{" `"["))
+    (`(:before . ,(or `"(" `"{" `"[" "while" "if" "for" "case"))
      (if (not (smie-rule-prev-p "&&" "||" "|"))
          (when (smie-rule-hanging-p)
            (smie-rule-parent))
        (unless (smie-rule-bolp)
-	 (smie-backward-sexp 'halfexp)
+	 (while (equal "|" (nth 2 (smie-backward-sexp 'halfexp))))
 	 `(column . ,(smie-indent-virtual)))))
     ;; FIXME: Maybe this handling of ;; should be made into
     ;; a smie-rule-terminator function that takes the substitute ";" as arg.




This bug report was last modified 10 years and 176 days ago.

Previous Next


GNU bug tracking system
Copyright (C) 1999 Darren O. Benham, 1997,2003 nCipher Corporation Ltd, 1994-97 Ian Jackson.