On Thu, Jul 12, 2012 at 12:35:26AM +0300, Peter Eisentraut wrote:
> This might be useful for some people. Here is an emacs configuration
> for perl-mode that is compatible with the new perltidy settings. Note
> that the default perl-mode settings produce indentation that will be
> completely shredded by the new perltidy settings.
>
> (defun pgsql-perl-style ()
> "Perl style adjusted for PostgreSQL project"
> (interactive)
> (setq tab-width 4)
> (setq perl-indent-level 4)
> (setq perl-continued-statement-offset 4)
> (setq perl-continued-brace-offset 4)
(Later, commit 56fb890 changed perl-continued-statement-offset to 2.) This
indents braces (perltidy aligns the brace with "if", but perl-mode adds
perl-continued-statement-offset + perl-continued-brace-offset = 6 columns):
if (-s "src/backend/snowball/stopwords/$lang.stop")
{
$stop = ", StopWords=$lang";
}
If I run perltidy on 60d9979, then run perl-mode indent, the diff between the
perltidy run and perl-mode indent run is:
129 files changed, 8468 insertions(+), 8468 deletions(-)
If I add (perl-continued-brace-offset . -2):
119 files changed, 3515 insertions(+), 3515 deletions(-)
If I add (perl-indent-continued-arguments . 4) as well:
86 files changed, 2626 insertions(+), 2626 deletions(-)
If I add (perl-indent-parens-as-block . t) as well:
65 files changed, 2373 insertions(+), 2373 deletions(-)
That's with GNU Emacs 24.5.1. Versions 24.3.1 and 21.4.1 show similar trends,
though 21.4.1 predates perl-indent-continued-arguments and
perl-indent-parens-as-block.
I'm attaching the patch to make it so, along with a patch that illustrates my
testing method. "sh reindent-perl.sh" will test emacs.samples using your
Emacs installation. (I don't plan to push the testing patch.)
diff --git a/.dir-locals.el b/.dir-locals.el
index eff4671..ab6208b 100644
--- a/.dir-locals.el
+++ b/.dir-locals.el
@@ -9,7 +9,7 @@
(indent-tabs-mode . nil)))
(perl-mode . ((perl-indent-level . 4)
(perl-continued-statement-offset . 2)
- (perl-continued-brace-offset . 4)
+ (perl-continued-brace-offset . -2)
(perl-brace-offset . 0)
(perl-brace-imaginary-offset . 0)
(perl-label-offset . -2)
diff --git a/src/tools/editors/emacs.samples b/src/tools/editors/emacs.samples
index a7152b0..529c98a 100644
--- a/src/tools/editors/emacs.samples
+++ b/src/tools/editors/emacs.samples
@@ -47,10 +47,13 @@
(interactive)
(setq perl-brace-imaginary-offset 0)
(setq perl-brace-offset 0)
- (setq perl-continued-brace-offset 4)
(setq perl-continued-statement-offset 2)
+ (setq perl-continued-brace-offset (- perl-continued-statement-offset))
(setq perl-indent-level 4)
(setq perl-label-offset -2)
+ ;; Next two aren't marked safe-local-variable, so .dir-locals.el omits them.
+ (setq perl-indent-continued-arguments 4)
+ (setq perl-indent-parens-as-block t)
(setq indent-tabs-mode t)
(setq tab-width 4))
diff --git a/reindent-perl.el b/reindent-perl.el
new file mode 100644
index 0000000..17ff125
--- /dev/null
+++ b/reindent-perl.el
@@ -0,0 +1,45 @@
+;; Import with-demoted-errors from Emacs 24.5.1 (present in 23.1+).
+(when (not (fboundp 'macroexp-progn))
+ (defun macroexp-progn (exps)
+ "Return an expression equivalent to `(progn ,@EXPS)."
+ (if (cdr exps) `(progn ,@exps) (car exps))))
+
+(when (not (fboundp 'with-demoted-errors))
+ (defmacro with-demoted-errors (format &rest body)
+ "Run BODY and demote any errors to simple messages.
+FORMAT is a string passed to `message' to format any error message.
+It should contain a single %-sequence; e.g., \"Error: %S\".
+
+If `debug-on-error' is non-nil, run BODY without catching its errors.
+This is to be used around code which is not expected to signal an error
+but which should be robust in the unexpected case that an error is signaled.
+
+For backward compatibility, if FORMAT is not a constant string, it
+is assumed to be part of BODY, in which case the message format
+used is \"Error: %S\"."
+ (let ((err (make-symbol "err"))
+ (format (if (and (stringp format) body) format
+ (prog1 "Error: %S"
+ (if format (push format body))))))
+ `(condition-case ,err
+ ,(macroexp-progn body)
+ (error (message ,format ,err) nil)))))
+
+
+(load (expand-file-name "./src/tools/editors/emacs.samples"))
+(setq enable-local-variables :all) ; not actually needed, given emacs.samples
+
+(while (setq fname (read-from-minibuffer "File name: "))
+ (set-buffer "*scratch*")
+ (find-file fname)
+ (message "%s"
+ (list
+ (current-buffer)
+ perl-indent-level
+ tab-width
+ (if (boundp 'perl-indent-continued-arguments)
+ perl-indent-continued-arguments "no-such-var")
+ (if (boundp 'perl-indent-parens-as-block)
+ perl-indent-parens-as-block "no-such-var")))
+ (with-demoted-errors (indent-region (point-min) (point-max) nil))
+ (save-buffer))
diff --git a/reindent-perl.sh b/reindent-perl.sh
new file mode 100644
index 0000000..ae34646
--- /dev/null
+++ b/reindent-perl.sh
@@ -0,0 +1,10 @@
+# Reindent Perl source using Emacs perl-mode. This tests how well perl-mode
+# matches perltidy.
+
+if [ -n "$1" ]; then
+ for arg; do printf '%s\n' "$arg"; done # Try specific files.
+else
+ . src/tools/perlcheck/find_perl_files
+ find_perl_files
+fi | emacs -no-site-file -batch -load reindent-perl.el
+git diff --shortstat