;;; fortran.el --- Fortran mode for GNU Emacs
-;; Copyright (c) 1986, 1993, 1994, 1995, 1997, 1998 Free Software Foundation, Inc.
+;; Copyright (c) 1986, 93, 94, 95, 97, 98, 1999 Free Software Foundation, Inc.
;; Author: Michael D. Prange <prange@erl.mit.edu>
;; Maintainer: Dave Love <fx@gnu.org>
;; This mode is documented in the Emacs manual.
;;
;; Note that it is for editing Fortran77 or Fortran90 fixed source
-;; form. For editing Fortran90 free format source, use `f90-mode'
+;; form. For editing Fortran 90 free format source, use `f90-mode'
;; (f90.el).
;;; History:
;;; Code:
-;; Todo:
+;; Todo:
+;; * Tidy it all up! (including renaming non-`fortran' prefixed
+;; functions).
;; * Implement insertion and removal of statement continuations in
;; mixed f77/f90 style, with the first `&' past column 72 and the
;; second in column 6.
-;; * Support other f90-style stuff grokked by GNU Fortran.
+;; * Support any other extensions to f77 grokked by GNU Fortran.
+;; * Change fontification to use font-lock-syntactic-keywords for
+;; fixed-form comments. (Done, but doesn't work properly with
+;; lazy-lock in pre-20.4.)
(require 'easymenu)
(defgroup fortran nil
"Fortran mode for Emacs"
+ :link '(custom-manual "(emacs)Fortran")
:group 'languages)
(defgroup fortran-indent nil
(modify-syntax-entry ?/ "." fortran-mode-syntax-table)
(modify-syntax-entry ?\' "\"" fortran-mode-syntax-table)
(modify-syntax-entry ?\" "\"" fortran-mode-syntax-table)
- (modify-syntax-entry ?\\ "/" fortran-mode-syntax-table)
+ (modify-syntax-entry ?\\ "\\" fortran-mode-syntax-table)
;; This might be better as punctuation, as for C, but this way you
;; can treat floating-point numbers as symbols.
(modify-syntax-entry ?. "_" fortran-mode-syntax-table) ; e.g. `a.ne.b'
(modify-syntax-entry ?\! "<" fortran-mode-syntax-table)
(modify-syntax-entry ?\n ">" fortran-mode-syntax-table))
-;; Comments are real pain in Fortran because there is no way to represent the
-;; standard comment syntax in an Emacs syntax table (we can for VAX-style).
-;; Therefore an unmatched quote in a standard comment will throw fontification
-;; off on the wrong track. So we do syntactic fontification with regexps.
+;; Comments are real pain in Fortran because there is no way to
+;; represent the standard comment syntax in an Emacs syntax table.
+;; (We can do so for F90-style). Therefore an unmatched quote in a
+;; standard comment will throw fontification off on the wrong track.
+;; So we do syntactic fontification with regexps.
\f
;; Regexps done by simon@gnu with help from Ulrik Dickow <dickow@nbi.dk> and
;; probably others Si's forgotten about (sorry).
(defconst fortran-font-lock-keywords-3 nil
"Gaudy level highlighting for Fortran mode.")
-(let ((comment-chars "c!*")
+(defconst fortran-font-lock-syntactic-keywords nil
+ "`font-lock-syntactic-keywords' for Fortran.
+These get fixed-format comments fontified.")
+
+(let ((comment-chars "cd") ; `d' for `debugging' comments
(fortran-type-types
(eval-when-compile
- (regexp-opt
- (let ((simple-types '("character" "byte" "integer" "logical"
- "none" "real" "complex"
- "double[ \t]*precision" "double[ \t]*complex"))
- (structured-types '("structure" "union" "map"))
- (other-types '("record" "dimension" "parameter" "common" "save"
- "external" "intrinsic" "data" "equivalence")))
- (append
- (mapcar (lambda (x) (concat "implicit[ \t]*" x)) simple-types)
- simple-types
- (mapcar (lambda (x) (concat "end[ \t]*" x)) structured-types)
- structured-types
- other-types)))))
+ (let ((re (regexp-opt
+ (let ((simple-types
+ '("character" "byte" "integer" "logical"
+ "none" "real" "complex"
+ "double precision" "double complex"))
+ (structured-types '("structure" "union" "map"))
+ (other-types '("record" "dimension"
+ "parameter" "common" "save"
+ "external" "intrinsic" "data"
+ "equivalence")))
+ (append
+ (mapcar (lambda (x) (concat "implicit " x))
+ simple-types)
+ simple-types
+ (mapcar (lambda (x) (concat "end " x))
+ structured-types)
+ structured-types
+ other-types)))))
+ ;; In the optimized regexp above, replace spaces by regexp
+ ;; for optional whitespace, which regexp-opt would have
+ ;; escaped.
+ (mapconcat #'identity (split-string re) "[ \t]*"))))
(fortran-keywords
(eval-when-compile
(regexp-opt '("continue" "format" "end" "enddo" "if" "then"
"else" "endif" "elseif" "while" "inquire" "stop"
"return" "include" "open" "close" "read" "write"
- "format" "print" "select" "case"))))
+ "format" "print" "select" "case" "cycle" "exit"))))
(fortran-logicals
(eval-when-compile
(regexp-opt '("and" "or" "not" "lt" "le" "eq" "ge" "gt" "ne"
"true" "false")))))
+ (setq fortran-font-lock-syntactic-keywords
+ ;; Fixed format comments. (!-style handled normally.)
+ (list
+ (list (concat "^[" comment-chars "]") 0 '(11))
+ (list (concat "^[^" comment-chars "\t\n]" (make-string 71 ?.)
+ "\\([^\n]+\\)")
+ 1 '(11))))
+
(setq fortran-font-lock-keywords-1
(list
- ;;
- ;; Fontify syntactically (assuming strings cannot be quoted
- ;; or span lines).
- (cons (concat "^[" comment-chars "].*") 'font-lock-comment-face)
- '(fortran-match-!-comment . font-lock-comment-face)
- (list (concat "^[^" comment-chars "\t\n]" (make-string 71 ?.)
- "\\(.*\\)")
- '(1 font-lock-comment-face))
- '("\\(\\s\"\\)\"[^\n]*\\1?" . font-lock-string-face)
;;
;; Program, subroutine and function declarations, plus calls.
(list (concat "\\<\\(block[ \t]*data\\|call\\|entry\\|function\\|"
(list
;;
;; Fontify all type specifiers (must be first; see below).
- (cons (concat "\\<\\(" fortran-type-types "\\)\\>")
+ (cons (concat "\\<\\(" fortran-type-types "\\)\\>")
'font-lock-type-face)
;;
;; Fontify all builtin keywords (except logical, do
;; Fontify the type specifier.
'(1 font-lock-type-face)
;; Fontify each declaration item (or just the /.../ block name).
- '(font-lock-match-c-style-declaration-item-and-skip-to-next
+ `(font-lock-match-c-style-declaration-item-and-skip-to-next
;; Start after any *(...) expression.
- (and (match-beginning 15) (forward-sexp))
+ (condition-case nil
+ (and (and (match-beginning ,(+ 2 (regexp-opt-depth
+ fortran-type-types)))
+ (forward-sexp))
+ (forward-sexp))
+ (error nil))
;; No need to clean up.
nil
;; Fontify as a variable name, functions are
3)
;; Un-named block data
(list nil "^\\s-+\\(block\\s-*data\\)\\s-*$" 1))
- "imenu generic expression for `imenu-default-create-index-function'.")
+ "Imenu generic expression for `imenu-default-create-index-function'.")
(defvar fortran-mode-map ()
"Keymap used in Fortran mode.")
["Momentary 72-column window" fortran-window-create-momentarily t]
"----"
["Break Line at Point" fortran-split-line t]
- ["Join Continuation Line" fortran-join-line t]
+ ["Join Line" fortran-join-line t]
["Fill Statement/Comment" fill-paragraph t]
"----"
["Add imenu menu"
Variables controlling indentation style and extra features:
- comment-start
+ `comment-start'
Normally nil in Fortran mode. If you want to use comments
starting with `!', set this to the string \"!\".
- fortran-do-indent
+ `fortran-do-indent'
Extra indentation within do blocks. (default 3)
- fortran-if-indent
+ `fortran-if-indent'
Extra indentation within if blocks. (default 3)
- fortran-structure-indent
+ `fortran-structure-indent'
Extra indentation within structure, union, map and interface blocks.
(default 3)
- fortran-continuation-indent
+ `fortran-continuation-indent'
Extra indentation applied to continuation statements. (default 5)
- fortran-comment-line-extra-indent
- Amount of extra indentation for text within full-line comments. (default 0)
- fortran-comment-indent-style
+ `fortran-comment-line-extra-indent'
+ Amount of extra indentation for text within full-line comments. (default 0)
+ `fortran-comment-indent-style'
nil means don't change indentation of text in full-line comments,
fixed means indent that text at `fortran-comment-line-extra-indent' beyond
the value of `fortran-minimum-statement-indent-fixed' (for fixed
relative means indent at `fortran-comment-line-extra-indent' beyond the
indentation for a line of code.
(default 'fixed)
- fortran-comment-indent-char
+ `fortran-comment-indent-char'
Single-character string to be inserted instead of space for
full-line comment indentation. (default \" \")
- fortran-minimum-statement-indent-fixed
- Minimum indentation for Fortran statements in fixed format mode. (def.6)
- fortran-minimum-statement-indent-tab
- Minimum indentation for Fortran statements in TAB format mode. (default 9)
- fortran-line-number-indent
+ `fortran-minimum-statement-indent-fixed'
+ Minimum indentation for Fortran statements in fixed format mode. (def.6)
+ `fortran-minimum-statement-indent-tab'
+ Minimum indentation for Fortran statements in TAB format mode. (default 9)
+ `fortran-line-number-indent'
Maximum indentation for line numbers. A line number will get
less than this much indentation if necessary to avoid reaching
column 5. (default 1)
- fortran-check-all-num-for-matching-do
+ `fortran-check-all-num-for-matching-do'
Non-nil causes all numbered lines to be treated as possible \"continue\"
statements. (default nil)
- fortran-blink-matching-if
+ `fortran-blink-matching-if'
Non-nil causes \\[fortran-indent-line] on an ENDIF statement to blink on
matching IF. Also, from an ENDDO statement, blink on matching DO [WHILE]
statement. (default nil)
- fortran-continuation-string
+ `fortran-continuation-string'
Single-character string to be inserted in column 5 of a continuation
line. (default \"$\")
- fortran-comment-region
+ `fortran-comment-region'
String inserted by \\[fortran-comment-region] at start of each line in
region. (default \"c$$$\")
- fortran-electric-line-number
+ `fortran-electric-line-number'
Non-nil causes line number digits to be moved to the correct column
as typed. (default t)
- fortran-break-before-delimiters
+ `fortran-break-before-delimiters'
Non-nil causes `fortran-fill' to break lines before delimiters.
(default t)
fortran-font-lock-keywords-1
fortran-font-lock-keywords-2
fortran-font-lock-keywords-3)
- t t ((?/ . "$/") ("_$" . "w"))))
+ nil t ((?/ . "$/") ("_$" . "w"))
+ beginning-of-fortran-subprogram))
+ (set (make-local-variable 'font-lock-syntactic-keywords)
+ fortran-font-lock-syntactic-keywords)
(make-local-variable 'fortran-break-before-delimiters)
(setq fortran-break-before-delimiters t)
(make-local-variable 'indent-line-function)
(make-local-variable 'fortran-minimum-statement-indent-fixed)
(make-local-variable 'fortran-minimum-statement-indent-tab)
(make-local-variable 'fortran-column-ruler-fixed)
- (make-local-variable 'fortran-column-ruler-tab)
+ (make-local-variable 'fortran-column-ruler-tab)
(setq fortran-tab-mode-string " TAB-format")
(setq indent-tabs-mode (fortran-analyze-file-format))
(setq imenu-case-fold-search t)
(if (< (window-width) (frame-width))
(enlarge-window-horizontally (- (frame-width)
(window-width) 1)))
- (split-window-horizontally 73)
+ (let* ((window-edges (window-edges))
+ (scroll-bar-width (- (nth 2 window-edges)
+ (car window-edges)
+ (window-width))))
+ (split-window-horizontally (+ 72 scroll-bar-width)))
(other-window 1)
(switch-to-buffer " fortran-window-extra" t)
(select-window (previous-window))))
(delete-indentation)
t)))
-(defun fortran-join-line ()
- "Join a continuation line to the previous one and re-indent."
- (interactive)
+(defun fortran-join-line (arg)
+ "Join current line to the previous one and re-indent.
+With a prefix argument, repeat this operation that many times.
+If the prefix argument ARG is negative, join the next -ARG lines.
+Continuation lines are correctly handled."
+ (interactive "*p")
(save-excursion
- (beginning-of-line)
- (if (not (fortran-remove-continuation))
- (error "Not a continuation line"))
+ (when (> 0 arg)
+ (setq arg (- arg))
+ (forward-line arg))
+ (while (not (zerop arg))
+ (beginning-of-line)
+ (or (fortran-remove-continuation)
+ (delete-indentation))
+ (setq arg (1- arg)))
(fortran-indent-line)))
(defun fortran-numerical-continuation-char ()
(fortran-indent-line))))
\f
(defvar fortran-end-prog-re1
- "end\\b[ \t]*\\(\\(program\\|subroutine\\|function\\)[ \t]*\\)?[^ \t=\(a-z]")
+ "end\
+\\([ \t]*\\(program\\|subroutine\\|function\\|block[ \t]*data\\)\\>\
+\\([ \t]*\\(\\sw\\|\\s_\\)+\\)?\\)?")
(defvar fortran-end-prog-re
- (concat "^[ \t0-9]*" fortran-end-prog-re1))
-
+ (concat "^[ \t0-9]*" fortran-end-prog-re1)
+ "Regexp possibly marking subprogram end.")
+
+(defun fortran-check-end-prog-re ()
+ "Check a preliminary match against `fortran-end-prog-re'."
+ ;; Having got a possible match for the subprogram end, we need a
+ ;; match of whitespace, avoiding possible column 73+ stuff.
+ (save-match-data
+ (string-match "^\\s-*\\(\\'\\|\\s<\\)"
+ (buffer-substring (match-end 0)
+ (min (line-end-position)
+ (+ 72 (line-beginning-position)))))))
+
+;; Note that you can't just check backwards for `subroutine' &c in
+;; case of un-marked main programs not at the start of the file.
(defun beginning-of-fortran-subprogram ()
"Moves point to the beginning of the current Fortran subprogram."
(interactive)
- (let ((case-fold-search t))
- (beginning-of-line -1)
- (if (re-search-backward fortran-end-prog-re nil 'move)
- (forward-line))))
+ (save-match-data
+ (let ((case-fold-search t))
+ (beginning-of-line -1)
+ (if (catch 'ok
+ (while (re-search-backward fortran-end-prog-re nil 'move)
+ (if (fortran-check-end-prog-re)
+ (throw 'ok t))))
+ (forward-line)))))
(defun end-of-fortran-subprogram ()
"Moves point to the end of the current Fortran subprogram."
(interactive)
- (let ((case-fold-search t))
- (beginning-of-line 2)
- (re-search-forward fortran-end-prog-re nil 'move)
- (goto-char (match-beginning 0))
- (forward-line)))
+ (save-match-data
+ (let ((case-fold-search t))
+ (if (save-excursion ; on END
+ (beginning-of-line)
+ (and (looking-at fortran-end-prog-re)
+ (fortran-check-end-prog-re)))
+ (forward-line)
+ (beginning-of-line 2)
+ (catch 'ok
+ (while (re-search-forward fortran-end-prog-re nil 'move)
+ (if (fortran-check-end-prog-re)
+ (throw 'ok t))))
+ (goto-char (match-beginning 0))
+ (forward-line)))))
(defun mark-fortran-subprogram ()
"Put mark at end of Fortran subprogram, point at beginning.
The marks are pushed."
(interactive)
(end-of-fortran-subprogram)
- (push-mark (point))
+ (push-mark (point) nil t)
(beginning-of-fortran-subprogram))
(defun fortran-previous-statement ()
"Make text outside the current subprogram invisible.
The subprogram visible is the one that contains or follows point."
(interactive)
- (save-excursion
- (mark-fortran-subprogram)
- (narrow-to-region (region-beginning)
- (region-end))))
+ (save-excursion
+ (mark-fortran-subprogram)
+ (narrow-to-region (point) (mark))))
+
+(defmacro fortran-with-subprogram-narrowing (&rest forms)
+ "Execute FORMS with buffer temporarily narrowed to current subprogram.
+Doesn't push a mark."
+ `(save-restriction
+ (save-excursion
+ (narrow-to-region (progn
+ (beginning-of-fortran-subprogram)
+ (point))
+ (progn
+ (end-of-fortran-subprogram)
+ (point))))
+ ,@forms))
\f
(defun fortran-blink-matching-if ()
- ;; From a Fortran ENDIF statement, blink the matching IF statement.
+ "From an ENDIF statement, blink the matching IF statement."
(let ((top-of-window (window-start))
(endif-point (point))
(case-fold-search t)
message)
(if (save-excursion (beginning-of-line)
(skip-chars-forward " \t0-9")
- (looking-at "end[ \t]*if\\b"))
+ (looking-at "e\\(nd[ \t]*if\\|lse\\([ \t]*if\\)?\\)\\b"))
(progn
(if (not (setq matching-if (fortran-beginning-if)))
(setq message "No matching if.")
(goto-char endif-point))))))
(defun fortran-blink-matching-do ()
- ;; From a Fortran ENDDO statement, blink on the matching DO or DO WHILE
- ;; statement. This is basically copied from fortran-blink-matching-if.
+ "From an ENDDO statement, blink the matching DO or DO WHILE statement."
+ ;; This is basically copied from fortran-blink-matching-if.
(let ((top-of-window (window-start))
(enddo-point (point))
(case-fold-search t)
(goto-char do-point)))))
(defun fortran-end-do ()
- ;; Search forward for first unmatched ENDDO. Return point or nil.
+ "Search forward for first unmatched ENDDO.
+Return point or nil."
(let ((case-fold-search t))
(if (save-excursion (beginning-of-line)
(skip-chars-forward " \t0-9")
(while (and (not (= count 0))
(not (eq (fortran-next-statement) 'last-statement))
;; Keep local to subprogram
- (not (looking-at fortran-end-prog-re)))
+ (not (and (looking-at fortran-end-prog-re)
+ (fortran-check-end-prog-re))))
(skip-chars-forward " \t0-9")
(cond ((looking-at "end[ \t]*do\\b")
(point)))))))
(defun fortran-beginning-do ()
- ;; Search backwards for first unmatched DO [WHILE]. Return point or nil.
+ "Search backwards for first unmatched DO [WHILE].
+Return point or nil."
(let ((case-fold-search t))
(if (save-excursion (beginning-of-line)
(skip-chars-forward " \t0-9")
(while (and (not (= count 0))
(not (eq (fortran-previous-statement) 'first-statement))
;; Keep local to subprogram
- (not (looking-at fortran-end-prog-re)))
+ (not (and (looking-at fortran-end-prog-re)
+ (fortran-check-end-prog-re))))
(skip-chars-forward " \t0-9")
(cond ((looking-at "\\(\\(\\sw\\|\\s_\\)+:[ \t]*\\)?do[ \t]+[^0-9]")
(defvar fortran-if-start-re "\\(\\(\\sw\\|\\s_\\)+:[ \t]*\\)?if[ \t]*(")
(defun fortran-end-if ()
- ;; Search forwards for first unmatched ENDIF. Return point or nil.
+ "Search forwards for first unmatched ENDIF.
+Return point or nil."
(let ((case-fold-search t))
(if (save-excursion (beginning-of-line)
(skip-chars-forward " \t0-9")
(while (and (not (= count 0))
(not (eq (fortran-next-statement) 'last-statement))
;; Keep local to subprogram.
- (not (looking-at fortran-end-prog-re)))
+ (not (and (looking-at fortran-end-prog-re)
+ (fortran-check-end-prog-re))))
(skip-chars-forward " \t0-9")
(cond ((looking-at "end[ \t]*if\\b")
(point)))))))
(defun fortran-beginning-if ()
- ;; Search backwards for first unmatched IF-THEN. Return point or nil.
+ "Search backwards for first unmatched IF-THEN.
+Return point or nil."
(let ((case-fold-search t))
(if (save-excursion
;; May be sitting on multi-line if-then statement, first move to
(while (and (not (= count 0))
(not (eq (fortran-previous-statement) 'first-statement))
;; Keep local to subprogram.
- (not (looking-at fortran-end-prog-re)))
+ (not (and (looking-at fortran-end-prog-re)
+ (fortran-check-end-prog-re))))
(skip-chars-forward " \t0-9")
(cond ((looking-at fortran-if-start-re)
(defun fortran-indent-new-line ()
"Reindent the current Fortran line, insert a newline and indent the newline.
-An abbrev before point is expanded if `abbrev-mode' is non-nil."
+An abbrev before point is expanded if variable `abbrev-mode' is non-nil."
(interactive)
(if abbrev-mode (expand-abbrev))
(save-excursion
((looking-at
"\\(structure\\|union\\|map\\|interface\\)\\b[ \t]*[^ \t=(a-z]")
(setq icol (+ icol fortran-structure-indent)))
- ((looking-at fortran-end-prog-re1)
+ ((and (looking-at fortran-end-prog-re1)
+ (fortran-check-end-prog-re))
;; Previous END resets indent to minimum
(setq icol fortran-minimum-statement-indent))))))
(save-excursion
\\(structure\\|union\\|map\\|interface\\)\\b[ \t]*[^ \t=(a-z]")
(setq icol (- icol fortran-structure-indent)))
((and (looking-at fortran-end-prog-re1)
+ (fortran-check-end-prog-re)
(not (= icol fortran-minimum-statement-indent)))
(message "Warning: `end' not in column %d. Probably\
an unclosed block." fortran-minimum-statement-indent))))))
(progn (skip-chars-forward "0-9")
(point))))
(beginning-of-line)
- (and (re-search-backward
- (concat "\\(" fortran-end-prog-re "\\)\\|"
- "\\(^[ \t0-9]*do[ \t]*0*" charnum "\\b\\)\\|"
- "\\(^[ \t]*0*" charnum "\\b\\)")
- nil t)
- (looking-at (concat "^[ \t0-9]*do[ \t]*0*" charnum))))))))
+ (fortran-with-subprogram-narrowing
+ (and (re-search-backward
+ (concat "\\(^[ \t0-9]*do[ \t]*0*" charnum "\\b\\)\\|"
+ "\\(^[ \t]*0*" charnum "\\b\\)")
+ nil t)
+ (looking-at (concat "^[ \t0-9]*do[ \t]*0*" charnum)))))))))
(defun fortran-find-comment-start-skip ()
"Move to past `comment-start-skip' found on current line.
t))
nil))
-;;From: simon@gnu (Simon Marshall)
-;; Find the next ! not in a string.
-(defun fortran-match-!-comment (limit)
- (let (found)
- (while (and (setq found (search-forward "!" limit t))
- (fortran-is-in-string-p (point))))
- (if (not found)
- nil
- ;; Cheaper than `looking-at' "!.*".
- (set-match-data
- (list (1- (point)) (progn (end-of-line) (min (point) limit))))
- t)))
-
-;; The above function is about 10% faster than the below...
-;;(defun fortran-match-!-comment (limit)
-;; (let (found)
-;; (while (and (setq found (re-search-forward "!.*" limit t))
-;; (fortran-is-in-string-p (match-beginning 0))))
-;; found))
-
;;From: ralf@up3aud1.gwdg.de (Ralf Fassel)
;; Test if TAB format continuation lines work.
(defun fortran-is-in-string-p (where)
(defun fortran-fill ()
(interactive)
- (let* ((opoint (point))
+ (let* ((auto-fill-function #'fortran-do-auto-fill)
+ (opoint (point))
(bol (save-excursion (beginning-of-line) (point)))
(eol (save-excursion (end-of-line) (point)))
(bos (min eol (+ bol (fortran-current-line-indentation))))
(defun fortran-fill-statement ()
"Fill a fortran statement up to `fill-column'."
(interactive)
- (if (not (save-excursion
- (beginning-of-line)
- (or (looking-at "[ \t]*$")
- (looking-at comment-line-start-skip)
- (and comment-start-skip
- (looking-at (concat "[ \t]*" comment-start-skip))))))
- (save-excursion
- ;; Find beginning of statement.
- (fortran-next-statement)
- (fortran-previous-statement)
- ;; Re-indent initially.
- (fortran-indent-line)
- ;; Replace newline plus continuation field plus indentation with
- ;; single space.
- (while (progn
- (forward-line)
- (fortran-remove-continuation)))
- (fortran-previous-statement)))
- (fortran-indent-line))
+ (let ((auto-fill-function #'fortran-do-auto-fill))
+ (if (not (save-excursion
+ (beginning-of-line)
+ (or (looking-at "[ \t]*$")
+ (looking-at comment-line-start-skip)
+ (and comment-start-skip
+ (looking-at (concat "[ \t]*" comment-start-skip))))))
+ (save-excursion
+ ;; Find beginning of statement.
+ (fortran-next-statement)
+ (fortran-previous-statement)
+ ;; Re-indent initially.
+ (fortran-indent-line)
+ ;; Replace newline plus continuation field plus indentation with
+ ;; single space.
+ (while (progn
+ (forward-line)
+ (fortran-remove-continuation)))
+ (fortran-previous-statement)))
+ (fortran-indent-line)))
(provide 'fortran)