changeset 109874:832428782d9f

merge from trunk, no conflicts
author Joakim <joakim@localhost.localdomain>
date Wed, 18 Aug 2010 13:11:01 +0200
parents fa7968a7972f (current diff) f2b0181ddf31 (diff)
children ce46135d2b98
files etc/NEWS lisp/image.el
diffstat 23 files changed, 601 insertions(+), 277 deletions(-) [+]
line wrap: on
line diff
--- a/etc/NEWS	Wed Aug 18 12:35:23 2010 +0200
+++ b/etc/NEWS	Wed Aug 18 13:11:01 2010 +0200
@@ -230,6 +230,8 @@
 
 * Changes in Specialized Modes and Packages in Emacs 24.1
 
+** FIXME: xdg-open for browse-url and reportbug, 2010/08.  (Close bug#4546?)
+
 ** Archive Mode has basic support to browse 7z archives.
 
 ** ERC changes
--- a/lisp/ChangeLog	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/ChangeLog	Wed Aug 18 13:11:01 2010 +0200
@@ -1,3 +1,61 @@
+2010-08-18  Stefan Monnier  <monnier@iro.umontreal.ca>
+
+	* progmodes/prolog.el (smie): Require.
+
+	* emacs-lisp/smie.el (smie-default-backward-token)
+	(smie-default-forward-token): Strip properties.
+	(smie-next-sexp): Be more careful with associative operators.
+	(smie-forward-sexp-command): Generalize.
+	(smie-backward-sexp-command): Simplify.
+	(smie-closer-alist): New var.
+	(smie-close-block): New command.
+	(smie-indent-debug-log): New var.
+	(smie-indent-offset-rule): Add a few more cases.
+	(smie-indent-column): New function.
+	(smie-indent-after-keyword): Use it.
+	(smie-indent-keyword): Use it.
+	Fix up the opener code's point position.
+	(smie-indent-comment): Only applies at BOL.
+	(smie-indent-debug): New command.
+
+	* emacs-lisp/autoload.el (make-autoload): Preload the macros's
+	declarations that are useful before running the macro.
+
+2010-08-18  Katsumi Yamaoka  <yamaoka@jpl.org>
+
+	* image.el (create-animated-image): Don't add heuristic mask to image
+	(Bug#6839).
+
+2010-08-18  Jan Djärv  <jan.h.d@swipnet.se>
+
+	* term/ns-win.el (ns-get-pasteboard, ns-set-pasteboard):
+	Use QCLIPBOARD instead of QPRIMARY (Bug#6677).
+
+2010-08-17  Stefan Monnier  <monnier@iro.umontreal.ca>
+
+	* emacs-lisp/lisp.el (up-list): Obey forward-sexp-function if set.
+
+	Font-lock '...' strings, plus various simplifications and fixes.
+	* progmodes/octave-mod.el (octave-font-lock-keywords): Use regexp-opt.
+	(octave-font-lock-close-quotes): New function.
+	(octave-font-lock-syntactic-keywords): New var.
+	(octave-mode): Use it.  Set beginning-of-defun-function.
+	(octave-mode-map): Don't override the <foo>-defun commands.
+	(octave-mode-menu): Pass it directly to easy-menu-define;
+	remove (now generic) <foo>-defun commands; use info-lookup-symbol.
+	(octave-block-match-alist): Fix up last change so that
+	octave-close-block uses the more specific keyword.
+	(info-lookup-mode): Silence byte-compiler.
+	(octave-beginning-of-defun): Not interactive any more.
+	Optimize slightly.
+	(octave-end-of-defun, octave-mark-defun, octave-in-defun-p): Remove.
+	(octave-indent-defun, octave-send-defun): Use mark-defun instead.
+	(octave-completion-at-point-function): Make sure point is within
+	beg..end.
+	(octave-reindent-then-newline-and-indent):
+	Use reindent-then-newline-and-indent.
+	(octave-add-octave-menu): Remove.
+
 2010-08-17  Jan Djärv  <jan.h.d@swipnet.se>
 
 	* mail/emacsbug.el (report-emacs-bug-insert-to-mailer)
@@ -7,6 +65,20 @@
 	\C-cm to report-emacs-bug-insert-to-mailer and add help text
 	about it.
 
+	* net/browse-url.el (browse-url-default-browser): Add cond
+	for browse-url-xdg-open.
+	(browse-url-can-use-xdg-open, browse-url-xdg-open): New functions.
+
+2010-08-17  Glenn Morris  <rgm@gnu.org>
+
+	* progmodes/cc-engine.el (c-new-BEG, c-new-END)
+	(c-fontify-recorded-types-and-refs): Define for compiler.
+	* progmodes/cc-mode.el (c-new-BEG, c-new-END): Move definitions
+	before use.
+
+	* calendar/icalendar.el (icalendar--convert-recurring-to-diary):
+	Fix format call.
+
 2010-08-17  Michael Albinus  <michael.albinus@gmx.de>
 
 	* net/tramp.el (tramp-handle-make-symbolic-link): Flush file
@@ -34,8 +106,8 @@
 2010-08-15  Chong Yidong  <cyd@stupidchicken.com>
 
 	* mouse.el (mouse--drag-set-mark-and-point): New function.
-	(mouse-drag-track): Use LOCATION arg to push-mark.  Use
-	mouse--drag-set-mark-and-point to take click-count into
+	(mouse-drag-track): Use LOCATION arg to push-mark.
+	Use mouse--drag-set-mark-and-point to take click-count into
 	consideration when updating point and mark (Bug#6840).
 
 2010-08-15  Chong Yidong  <cyd@stupidchicken.com>
@@ -45,8 +117,8 @@
 
 2010-08-14  Štěpán Němec  <stepnem@gmail.com>  (tiny change)
 
-	* font-lock.el (lisp-font-lock-keywords-2): Add
-	combine-after-change-calls, condition-case-no-debug,
+	* font-lock.el (lisp-font-lock-keywords-2):
+	Add combine-after-change-calls, condition-case-no-debug,
 	with-demoted-errors, and with-silent-modifications (Bug#6025).
 
 2010-08-14  Kevin Ryde  <user42@zip.com.au>
@@ -71,8 +143,8 @@
 	(menu-bar-showhide-tool-bar-menu-customize-enable-left)
 	(menu-bar-showhide-tool-bar-menu-customize-enable-right)
 	(menu-bar-showhide-tool-bar-menu-customize-enable-top)
-	(menu-bar-showhide-tool-bar-menu-customize-enable-bottom): Call
-	menu-bar-set-tool-bar-position.
+	(menu-bar-showhide-tool-bar-menu-customize-enable-bottom):
+	Call menu-bar-set-tool-bar-position.
 
 2010-08-12  Stefan Monnier  <monnier@iro.umontreal.ca>
 
--- a/lisp/emacs-lisp/autoload.el	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/emacs-lisp/autoload.el	Wed Aug 18 13:11:01 2010 +0200
@@ -109,29 +109,48 @@
       (let* ((macrop (memq car '(defmacro defmacro*)))
 	     (name (nth 1 form))
 	     (args (case car
-		    ((defun defmacro defun* defmacro*
-		       define-overloadable-function) (nth 2 form))
-		    ((define-skeleton) '(&optional str arg))
-		    ((define-generic-mode define-derived-mode
-                       define-compilation-mode) nil)
-		    (t)))
+                     ((defun defmacro defun* defmacro*
+                        define-overloadable-function) (nth 2 form))
+                     ((define-skeleton) '(&optional str arg))
+                     ((define-generic-mode define-derived-mode
+                        define-compilation-mode) nil)
+                     (t)))
 	     (body (nthcdr (get car 'doc-string-elt) form))
 	     (doc (if (stringp (car body)) (pop body))))
 	(when (listp args)
 	  ;; Add the usage form at the end where describe-function-1
 	  ;; can recover it.
 	  (setq doc (help-add-fundoc-usage doc args)))
-	;; `define-generic-mode' quotes the name, so take care of that
-	(list 'autoload (if (listp name) name (list 'quote name)) file doc
-	      (or (and (memq car '(define-skeleton define-derived-mode
-				    define-generic-mode
-				    easy-mmode-define-global-mode
-				    define-global-minor-mode
-				    define-globalized-minor-mode
-				    easy-mmode-define-minor-mode
-				    define-minor-mode)) t)
-		  (eq (car-safe (car body)) 'interactive))
-	      (if macrop (list 'quote 'macro) nil))))
+        (let ((exp
+               ;; `define-generic-mode' quotes the name, so take care of that
+               (list 'autoload (if (listp name) name (list 'quote name))
+                     file doc
+                     (or (and (memq car '(define-skeleton define-derived-mode
+                                           define-generic-mode
+                                           easy-mmode-define-global-mode
+                                           define-global-minor-mode
+                                           define-globalized-minor-mode
+                                           easy-mmode-define-minor-mode
+                                           define-minor-mode)) t)
+                         (eq (car-safe (car body)) 'interactive))
+                     (if macrop (list 'quote 'macro) nil))))
+          (when macrop
+            ;; Special case to autoload some of the macro's declarations.
+            (let ((decls (nth (if (stringp (nth 3 form)) 4 3) form))
+                  (exps '()))
+              (when (eq (car decls) 'declare)
+                ;; FIXME: We'd like to reuse macro-declaration-function,
+                ;; but we can't since it doesn't return anything.
+                (dolist (decl decls)
+                  (case (car-safe decl)
+                    (indent
+                     (push `(put ',name 'lisp-indent-function ',(cadr decl))
+                           exps))
+                    (doc-string
+                     (push `(put ',name 'doc-string-elt ',(cadr decl)) exps))))
+                (when exps
+                  (setq exp `(progn ,exp ,@exps))))))
+          exp)))
 
      ;; For defclass forms, use `eieio-defclass-autoload'.
      ((eq car 'defclass)
--- a/lisp/emacs-lisp/lisp.el	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/emacs-lisp/lisp.el	Wed Aug 18 13:11:01 2010 +0200
@@ -142,7 +142,13 @@
   (or arg (setq arg 1))
   (let ((inc (if (> arg 0) 1 -1)))
     (while (/= arg 0)
-      (goto-char (or (scan-lists (point) inc 1) (buffer-end arg)))
+      (if forward-sexp-function
+          (condition-case err
+              (while (let ((pos (point)))
+                       (forward-sexp inc)
+                       (/= (point) pos)))
+            (scan-error (goto-char (nth 2 err))))
+        (goto-char (or (scan-lists (point) inc 1) (buffer-end arg))))
       (setq arg (- arg inc)))))
 
 (defun kill-sexp (&optional arg)
--- a/lisp/emacs-lisp/smie.el	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/emacs-lisp/smie.el	Wed Aug 18 13:11:01 2010 +0200
@@ -65,6 +65,9 @@
 
 ;;; Code:
 
+;; FIXME: I think the behavior on empty lines is wrong.  It shouldn't
+;; look at the next token on subsequent lines.
+
 (eval-when-compile (require 'cl))
 
 (defvar comment-continue)
@@ -204,6 +207,17 @@
     prec2))
 
 (defun smie-prec2-levels (prec2)
+  ;; FIXME: Rather than only return an alist of precedence levels, we should
+  ;; also extract other useful data from it:
+  ;; - matching sets of block openers&closers (which can otherwise become
+  ;;   collapsed into a single equivalence class in smie-op-levels) for
+  ;;   smie-close-block as well as to detect mismatches in smie-next-sexp
+  ;;   or in blink-paren (as well as to do the blink-paren for inner
+  ;;   keywords like the "in" of "let..in..end").
+  ;; - better default indentation rules (i.e. non-zero indentation after inner
+  ;;   keywords like the "in" of "let..in..end") for smie-indent-after-keyword.
+  ;; Of course, maybe those things would be even better handled in the
+  ;; bnf->prec function.
   "Take a 2D precedence table and turn it into an alist of precedence levels.
 PREC2 is a table as returned by `smie-precs-precedence-table' or
 `smie-bnf-precedence-table'."
@@ -321,32 +335,30 @@
 
 (defun smie-default-backward-token ()
   (forward-comment (- (point)))
-  (buffer-substring (point)
-                    (progn (if (zerop (skip-syntax-backward "."))
-                               (skip-syntax-backward "w_'"))
-                           (point))))
+  (buffer-substring-no-properties
+   (point)
+   (progn (if (zerop (skip-syntax-backward "."))
+              (skip-syntax-backward "w_'"))
+          (point))))
 
 (defun smie-default-forward-token ()
   (forward-comment (point-max))
-  (buffer-substring (point)
-                    (progn (if (zerop (skip-syntax-forward "."))
-                               (skip-syntax-forward "w_'"))
-                           (point))))
+  (buffer-substring-no-properties
+   (point)
+   (progn (if (zerop (skip-syntax-forward "."))
+              (skip-syntax-forward "w_'"))
+          (point))))
 
 (defun smie-associative-p (toklevels)
   ;; in "a + b + c" we want to stop at each +, but in
-  ;; "if a then b else c" we don't want to stop at each keyword.
+  ;; "if a then b elsif c then d else c" we don't want to stop at each keyword.
   ;; To distinguish the two cases, we made smie-prec2-levels choose
   ;; different levels for each part of "if a then b else c", so that
   ;; by checking if the left-level is equal to the right level, we can
   ;; figure out that it's an associative operator.
-  ;; This is not 100% foolproof, tho, since a grammar like
-  ;;   (exp ("A" exp "C") ("A" exp "B" exp "C"))
-  ;; will cause "B" to have equal left and right levels, even though
-  ;; it is not an associative operator.
-  ;; A better check would be the check the actual previous operator
-  ;; against this one to see if it's the same, but we'd have to change
-  ;; `levels' to keep a stack of operators rather than only levels.
+  ;; This is not 100% foolproof, tho, since the "elsif" will have to have
+  ;; equal left and right levels (since it's optional), so smie-next-sexp
+  ;; has to be careful to distinguish those different cases.
   (eq (smie-op-left toklevels) (smie-op-right toklevels)))
 
 (defun smie-next-sexp (next-token next-sexp op-forw op-back halfsexp)
@@ -371,51 +383,71 @@
           (let* ((pos (point))
                  (token (funcall next-token))
                  (toklevels (cdr (assoc token smie-op-levels))))
-
             (cond
              ((null toklevels)
               (when (zerop (length token))
                   (condition-case err
                       (progn (goto-char pos) (funcall next-sexp 1) nil)
-                  (scan-error (throw 'return (list t (caddr err)))))
+                  (scan-error (throw 'return
+                                     (list t (caddr err)
+                                           (buffer-substring-no-properties
+                                            (caddr err)
+                                            (+ (caddr err)
+                                               (if (< (point) (caddr err))
+                                                   -1 1)))))))
                 (if (eq pos (point))
                     ;; We did not move, so let's abort the loop.
                     (throw 'return (list t (point))))))
              ((null (funcall op-back toklevels))
               ;; A token like a paren-close.
               (assert (funcall op-forw toklevels)) ;Otherwise, why mention it?
-              (push (funcall op-forw toklevels) levels))
+              (push toklevels levels))
              (t
-              (while (and levels (< (funcall op-back toklevels) (car levels)))
+              (while (and levels (< (funcall op-back toklevels)
+                                    (funcall op-forw (car levels))))
                 (setq levels (cdr levels)))
               (cond
                ((null levels)
                 (if (and halfsexp (funcall op-forw toklevels))
-                    (push (funcall op-forw toklevels) levels)
+                    (push toklevels levels)
                   (throw 'return
                          (prog1 (list (or (car toklevels) t) (point) token)
                            (goto-char pos)))))
                (t
-                (if (and levels (= (funcall op-back toklevels) (car levels)))
+                (let ((lastlevels levels))
+                  (if (and levels (= (funcall op-back toklevels)
+                                     (funcall op-forw (car levels))))
                     (setq levels (cdr levels)))
+                  ;; We may have found a match for the previously pending
+                  ;; operator.  Is this the end?
                 (cond
-                 ((null levels)
-                  (cond
+                   ;; Keep looking as long as we haven't matched the
+                   ;; topmost operator.
+                   (levels
+                    (if (funcall op-forw toklevels)
+                        (push toklevels levels)))
+                   ;; We matched the topmost operator.  If the new operator
+                   ;; is the last in the corresponding BNF rule, we're done.
                    ((null (funcall op-forw toklevels))
+                    ;; It is the last element, let's stop here.
                     (throw 'return (list nil (point) token)))
-                   ((smie-associative-p toklevels)
+                   ;; If the new operator is not the last in the BNF rule,
+                   ;; ans is not associative, it's one of the inner operators
+                   ;; (like the "in" in "let .. in .. end"), so keep looking.
+                   ((not (smie-associative-p toklevels))
+                    (push toklevels levels))
+                   ;; The new operator is associative.  Two cases:
+                   ;; - it's really just an associative operator (like + or ;)
+                   ;;   in which case we should have stopped right before.
+                   ((and lastlevels
+                         (smie-associative-p (car lastlevels)))
                     (throw 'return
                            (prog1 (list (or (car toklevels) t) (point) token)
                              (goto-char pos))))
-                   ;; We just found a match to the previously pending operator
-                   ;; but this new operator is still part of a larger RHS.
-                   ;; E.g. we're now looking at the "then" in
-                   ;; "if a then b else c".  So we have to keep parsing the
-                   ;; rest of the construct.
-                   (t (push (funcall op-forw toklevels) levels))))
-                 (t
-                  (if (funcall op-forw toklevels)
-                      (push (funcall op-forw toklevels) levels))))))))
+                   ;; - it's an associative operator within a larger construct
+                   ;;   (e.g. an "elsif"), so we should just ignore it and keep
+                   ;;   looking for the closing element.
+                   (t (setq levels lastlevels))))))))
             levels)
         (setq halfsexp nil)))))
 
@@ -455,37 +487,78 @@
      (indirect-function 'smie-op-left)
    halfsexp))
 
+;;; Miscellanous commands using the precedence parser.
+
 (defun smie-backward-sexp-command (&optional n)
   "Move backward through N logical elements."
-  (interactive "p")
-  (if (< n 0)
-      (smie-forward-sexp-command (- n))
-    (let ((forward-sexp-function nil))
-      (while (> n 0)
-        (decf n)
+  (interactive "^p")
+  (smie-forward-sexp-command (- n)))
+
+(defun smie-forward-sexp-command (&optional n)
+  "Move forward through N logical elements."
+  (interactive "^p")
+  (let ((forw (> n 0))
+        (forward-sexp-function nil))
+    (while (/= n 0)
+      (setq n (- n (if forw 1 -1)))
         (let ((pos (point))
-              (res (smie-backward-sexp 'halfsexp)))
-          (if (and (car res) (= pos (point)) (not (bolp)))
+            (res (if forw
+                     (smie-forward-sexp 'halfsexp)
+                   (smie-backward-sexp 'halfsexp))))
+        (if (and (car res) (= pos (point)) (not (if forw (eolp) (bobp))))
               (signal 'scan-error
                       (list "Containing expression ends prematurely"
                             (cadr res) (cadr res)))
-            nil))))))
+          nil)))))
+
+(defvar smie-closer-alist nil
+  "Alist giving the closer corresponding to an opener.")
 
-(defun smie-forward-sexp-command (&optional n)
-  "Move forward through N logical elements."
-  (interactive "p")
-  (if (< n 0)
-      (smie-backward-sexp-command (- n))
-    (let ((forward-sexp-function nil))
-      (while (> n 0)
-        (decf n)
-        (let ((pos (point))
-              (res (smie-forward-sexp 'halfsexp)))
-          (if (and (car res) (= pos (point)) (not (bolp)))
-              (signal 'scan-error
-                      (list "Containing expression ends prematurely"
-                            (cadr res) (cadr res)))
-            nil))))))
+(defun smie-close-block ()
+  "Close the closest surrounding block."
+  (interactive)
+  (let ((closer
+         (save-excursion
+           (backward-up-list 1)
+           (if (looking-at "\\s(")
+               (string (cdr (syntax-after (point))))
+             (let* ((open (funcall smie-forward-token-function))
+                    (closer (cdr (assoc open smie-closer-alist)))
+                    (levels (list (assoc open smie-op-levels)))
+                    (seen '())
+                    (found '()))
+               (cond
+                ;; Even if we improve the auto-computation of closers,
+                ;; there are still cases where we need manual
+                ;; intervention, e.g. for Octave's use of `until'
+                ;; as a pseudo-closer of `do'.
+                (closer)
+                ((or (equal levels '(nil)) (nth 1 (car levels)))
+                 (error "Doesn't look like a block"))
+                (t
+                 ;; FIXME: With grammars like Octave's, every closer ("end",
+                 ;; "endif", "endwhile", ...) has the same level, so we'd need
+                 ;; to look at the BNF or at least at the 2D prec-table, in
+                 ;; order to find the right closer for a given opener.
+                 (while levels
+                   (let ((level (pop levels)))
+                     (dolist (other smie-op-levels)
+                       (when (and (eq (nth 2 level) (nth 1 other))
+                                  (not (memq other seen)))
+                         (push other seen)
+                         (if (nth 2 other)
+                             (push other levels)
+                           (push (car other) found))))))
+                 (cond
+                  ((null found) (error "No known closer for opener %s" open))
+                  ;; FIXME: what should we do if there are various closers?
+                  (t (car found))))))))))
+    (unless (save-excursion (skip-chars-backward " \t") (bolp))
+      (newline))
+    (insert closer)
+    (if (save-excursion (skip-chars-forward " \t") (eolp))
+        (indent-according-to-mode)
+      (reindent-then-newline-and-indent))))
 
 ;;; The indentation engine.
 
@@ -505,22 +578,33 @@
   "Rules of the following form.
 \((:before . TOK) . OFFSET-RULES)	how to indent TOK itself.
 \(TOK . OFFSET-RULES)	how to indent right after TOK.
-\((T1 . T2) . OFFSET)	how to indent token T2 w.r.t T1.
-\((t . TOK) . OFFSET)	how to indent TOK with respect to its parent.
 \(list-intro . TOKENS)	declare TOKENS as being followed by what may look like
 			  a funcall but is just a sequence of expressions.
 \(t . OFFSET)		basic indentation step.
 \(args . OFFSET)		indentation of arguments.
+\((T1 . T2) OFFSET)	like ((:before . T2) (:parent T1 OFFSET)).
 
 OFFSET-RULES is a list of elements which can each either be:
 
 \(:hanging . OFFSET-RULES)	if TOK is hanging, use OFFSET-RULES.
 \(:parent PARENT . OFFSET-RULES) if TOK's parent is PARENT, use OFFSET-RULES.
 \(:next TOKEN . OFFSET-RULES)	if TOK is followed by TOKEN, use OFFSET-RULES.
-\(:prev TOKEN . OFFSET-RULES)	if TOK is preceded by TOKEN, use OFFSET-RULES.
-a number				the offset to use.
+\(:prev TOKEN . OFFSET-RULES)	if TOK is preceded by TOKEN, use
+\(:bolp . OFFSET-RULES)		If TOK is first on a line, use OFFSET-RULES.
+OFFSET				the offset to use.
+
+PARENT can be either the name of the parent or `open' to mean any parent
+which acts as an open-paren (i.e. has a nil left-precedence).
+
+OFFSET can be of the form:
 `point'				align with the token.
 `parent'				align with the parent.
+NUMBER				offset by NUMBER.
+\(+ OFFSETS...)			use the sum of OFFSETS.
+
+The precise meaning of `point' depends on various details: it can
+either mean the position of the token we're indenting, or the
+position of its parent, or the position right after its parent.
 
 A nil offset for indentation after a token defaults to `smie-indent-basic'.")
 
@@ -543,21 +627,33 @@
       (cdr (assq t smie-indent-rules))
       smie-indent-basic))
 
-(defun smie-indent-offset-rule (tokinfo &optional after)
+(defvar smie-indent-debug-log)
+
+(defun smie-indent-offset-rule (tokinfo &optional after parent)
   "Apply the OFFSET-RULES in TOKINFO.
 Point is expected to be right in front of the token corresponding to TOKINFO.
 If computing the indentation after the token, then AFTER is the position
-after the token."
+after the token, otherwise it should be nil.
+PARENT if non-nil should be the parent info returned by `smie-backward-sexp'."
   (let ((rules (cdr tokinfo))
-        parent next prev
+        next prev
         offset)
     (while (consp rules)
       (let ((rule (pop rules)))
         (cond
          ((not (consp rule)) (setq offset rule))
+         ((eq (car rule) '+) (setq offset rule))
          ((eq (car rule) :hanging)
           (when (smie-indent-hanging-p)
             (setq rules (cdr rule))))
+         ((eq (car rule) :bolp)
+          (when (smie-bolp)
+            (setq rules (cdr rule))))
+         ((eq (car rule) :eolp)
+          (unless after
+            (error "Can't use :eolp in :before indentation rules"))
+          (when (> after (line-end-position))
+            (setq rules (cdr rule))))
          ((eq (car rule) :prev)
           (unless prev
             (save-excursion
@@ -578,12 +674,60 @@
             (save-excursion
               (if after (goto-char after))
               (setq parent (smie-backward-sexp 'halfsexp))))
-          (when (equal (nth 2 parent) (cadr rule))
+          (when (or (equal (nth 2 parent) (cadr rule))
+                    (and (eq (cadr rule) 'open) (null (car parent))))
             (setq rules (cddr rule))))
          (t (error "Unknown rule %s for indentation of %s"
                    rule (car tokinfo))))))
+    ;; If `offset' is not set yet, use `rules' to handle the case where
+    ;; the tokinfo uses the old-style ((PARENT . TOK). OFFSET).
+    (unless offset (setq offset rules))
+    (when (boundp 'smie-indent-debug-log)
+      (push (list (point) offset tokinfo) smie-indent-debug-log))
     offset))
 
+(defun smie-indent-column (offset &optional base parent virtual-point)
+  "Compute the actual column to use for a given OFFSET.
+BASE is the base position to use, and PARENT is the parent info, if any.
+If VIRTUAL-POINT is non-nil, then `point' is virtual."
+  (cond
+   ((eq (car-safe offset) '+)
+    (apply '+ (mapcar (lambda (offset) (smie-indent-column offset nil parent))
+                      (cdr offset))))
+   ((integerp offset)
+    (+ offset
+       (case base
+         ((nil) 0)
+         (parent (goto-char (cadr parent))
+                 (smie-indent-virtual))
+         (t
+          (goto-char base)
+          ;; For indentation after "(let" in SML-mode, we end up accumulating
+          ;; the offset of "(" and the offset of "let", so we use `min' to try
+          ;; and get it right either way.
+          (min (smie-indent-virtual) (current-column))))))
+   ((eq offset 'point)
+    ;; In indent-keyword, if we're indenting `then' wrt `if', we want to use
+    ;; indent-virtual rather than use just current-column, so that we can
+    ;; apply the (:before . "if") rule which does the "else if" dance in SML.
+    ;; But in other cases, we do not want to use indent-virtual
+    ;; (e.g. indentation of "*" w.r.t "+", or ";" wrt "(").  We could just
+    ;; always use indent-virtual and then have indent-rules say explicitly
+    ;; to use `point' after things like "(" or "+" when they're not at EOL,
+    ;; but you'd end up with lots of those rules.
+    ;; So we use a heuristic here, which is that we only use virtual if
+    ;; the parent is tightly linked to the child token (they're part of
+    ;; the same BNF rule).
+    (if (and virtual-point (null (car parent))) ;Black magic :-(
+        (smie-indent-virtual) (current-column)))
+   ((eq offset 'parent)
+    (unless parent
+      (setq parent (or (smie-backward-sexp 'halfsexp) :notfound)))
+    (if (consp parent) (goto-char (cadr parent)))
+    (smie-indent-virtual))
+   ((eq offset nil) nil)
+   (t (error "Unknown indentation offset %s" offset))))
+
 (defun smie-indent-forward-token ()
   "Skip token forward and return it, along with its levels."
   (let ((tok (funcall smie-forward-token-function)))
@@ -655,7 +799,9 @@
            (toklevels (smie-indent-forward-token))
            (token (pop toklevels)))
       (if (null (car toklevels))
-          ;; Different case:
+          (save-excursion
+            (goto-char pos)
+            ;; Different cases:
           ;; - smie-bolp: "indent according to others".
           ;; - common hanging: "indent according to others".
           ;; - SML-let hanging: "indent like parent".
@@ -668,72 +814,115 @@
             ;; based on other rules (typically smie-indent-after-keyword).
             nil)
            (t
-            (let* ((tokinfo (or (assoc (cons :before token) smie-indent-rules)
+              ;; We're only ever here for virtual-indent, which is why
+              ;; we can use (current-column) as answer for `point'.
+              (let* ((tokinfo (or (assoc (cons :before token)
+                                         smie-indent-rules)
                                 ;; By default use point unless we're hanging.
-                                (cons (cons :before token)
-                                      '((:hanging nil) point))))
-                   (after (prog1 (point) (goto-char pos)))
+                                  `((:before . ,token) (:hanging nil) point)))
+                     ;; (after (prog1 (point) (goto-char pos)))
                    (offset (smie-indent-offset-rule tokinfo)))
-              (cond
-               ((eq offset 'point) (current-column))
-               ((eq offset 'parent)
-                (let ((parent (smie-backward-sexp 'halfsexp)))
-                  (if parent (goto-char (cadr parent))))
-                (smie-indent-virtual))
-               ((eq offset nil) nil)
-               (t (error "Unhandled offset %s in %s"
-                         offset (cons :before token)))))))
+                (smie-indent-column offset)))))
 
         ;; FIXME: This still looks too much like black magic!!
         ;; FIXME: Rather than a bunch of rules like (PARENT . TOKEN), we
         ;; want a single rule for TOKEN with different cases for each PARENT.
-        (let ((res (smie-backward-sexp 'halfsexp)) tmp)
+        (let* ((parent (smie-backward-sexp 'halfsexp))
+               (tokinfo
+                (or (assoc (cons (caddr parent) token)
+                           smie-indent-rules)
+                    (assoc (cons :before token) smie-indent-rules)
+                    ;; Default rule.
+                    `((:before . ,token)
+                      ;; (:parent open 0)
+                      point)))
+               (offset (save-excursion
+                         (goto-char pos)
+                         (smie-indent-offset-rule tokinfo nil parent))))
+          ;; Different behaviors:
+          ;; - align with parent.
+          ;; - parent + offset.
+          ;; - after parent's column + offset (actually, after or before
+          ;;   depending on where backward-sexp stopped).
+          ;; ? let it drop to some other indentation function (almost never).
+          ;; ? parent + offset + parent's own offset.
+          ;; Different cases:
+          ;; - bump into a same-level operator.
+          ;; - bump into a specific known parent.
+          ;; - find a matching open-paren thingy.
+          ;; - bump into some random parent.
+          ;; ? borderline case (almost never).
+          ;; ? bump immediately into a parent.
           (cond
            ((not (or (< (point) pos)
-                     (and (cadr res) (< (cadr res) pos))))
+                     (and (cadr parent) (< (cadr parent) pos))))
             ;; If we didn't move at all, that means we didn't really skip
-            ;; what we wanted.
+            ;; what we wanted.  Should almost never happen, other than
+            ;; maybe when an infix or close-paren is at the beginning
+            ;; of a buffer.
             nil)
-           ((eq (car res) (car toklevels))
+           ((eq (car parent) (car toklevels))
             ;; We bumped into a same-level operator. align with it.
-            (goto-char (cadr res))
+            (if (and (smie-bolp) (/= (point) pos)
+                     (save-excursion
+                       (goto-char (goto-char (cadr parent)))
+                       (not (smie-bolp)))
+                     ;; Check the offset of `token' rather then its parent
+                     ;; because its parent may have used a special rule.  E.g.
+                     ;;    function foo;
+                     ;;      line2;
+                     ;;      line3;
+                     ;; The ; on the first line had a special rule, but when
+                     ;; indenting line3, we don't care about it and want to
+                     ;; align with line2.
+                     (memq offset '(point nil)))
+                ;; If the parent is at EOL and its children are indented like
+                ;; itself, then we can just obey the indentation chosen for the
+                ;; child.
+                ;; This is important for operators like ";" which
+                ;; are usually at EOL (and have an offset of 0): otherwise we'd
+                ;; always go back over all the statements, which is
+                ;; a performance problem and would also mean that fixindents
+                ;; in the middle of such a sequence would be ignored.
+                ;;
+                ;; This is a delicate point!
+                ;; Even if the offset is not 0, we could follow the same logic
+                ;; and subtract the offset from the child's indentation.
+                ;; But that would more often be a bad idea: OT1H we generally
+                ;; want to reuse the closest similar indentation point, so that
+                ;; the user's choice (or the fixindents) are obeyed.  But OTOH
+                ;; we don't want this to affect "unrelated" parts of the code.
+                ;; E.g. a fixindent in the body of a "begin..end" should not
+                ;; affect the indentation of the "end".
+                (current-column)
+              (goto-char (cadr parent))
             ;; Don't use (smie-indent-virtual :not-hanging) here, because we
             ;; want to jump back over a sequence of same-level ops such as
             ;;    a -> b -> c
             ;;    -> d
             ;; So as to align with the earliest appropriate place.
-            (smie-indent-virtual))
-           ((setq tmp (assoc (cons (caddr res) token)
-                             smie-indent-rules))
-            (goto-char (cadr res))
-            (+ (cdr tmp) (smie-indent-virtual))) ;:not-hanging
-           ;; FIXME: The rules ((t . TOK) . OFFSET) either indent
-           ;; relative to "before the parent" or "after the parent",
-           ;; depending on details of the grammar.
-           ((null (car res))
-            (assert (eq (point) (cadr res)))
-            (goto-char (cadr res))
-            (+ (or (cdr (assoc (cons t token) smie-indent-rules)) 0)
-               (smie-indent-virtual)))  ;:not-hanging
-           ((and (= (point) pos) (smie-bolp))
+              (smie-indent-virtual)))
+           (tokinfo
+            (if (and (= (point) pos) (smie-bolp)
+                     (or (eq offset 'point)
+                         (and (consp offset) (memq 'point offset))))
             ;; Since we started at BOL, we're not computing a virtual
-            ;; indentation, and we're still at the starting point, so the
-            ;; next (default) rule can't be used since it uses `current-column'
-            ;; which would cause. indentation to depend on itself.
-            ;; We could just return nil, but OTOH that's not good enough in
-            ;; some cases.  Instead, we want to combine the offset-rules for
-            ;; the current token with the offset-rules of the previous one.
-            (+ (or (cdr (assoc (cons t token) smie-indent-rules)) 0)
-               ;; FIXME: This is odd.  Can't we make it use
-               ;; smie-indent-(calculate|virtual) somehow?
-               (smie-indent-after-keyword)))
-           (t
-            (+ (or (cdr (assoc (cons t token) smie-indent-rules)) 0)
-               (current-column)))))))))
+                ;; indentation, and we're still at the starting point, so
+                ;; we can't use `current-column' which would cause
+                ;; indentation to depend on itself.
+                nil
+              (smie-indent-column offset 'parent parent
+                                  ;; If we're still at pos, indent-virtual
+                                  ;; will inf-loop.
+                                  (unless (= (point) pos) 'virtual))))))))))
 
 (defun smie-indent-comment ()
-  ;; Indentation of a comment.
-  (and (looking-at comment-start-skip)
+  "Compute indentation of a comment."
+  ;; Don't do it for virtual indentations.  We should normally never be "in
+  ;; front of a comment" when doing virtual-indentation anyway.  And if we are
+  ;; (as can happen in octave-mode), moving forward can lead to inf-loops.
+  (and (smie-bolp)
+       (looking-at comment-start-skip)
        (save-excursion
          (forward-comment (point-max))
          (skip-chars-forward " \t\r\n")
@@ -761,26 +950,25 @@
            (toklevel (smie-indent-backward-token))
            (tok (car toklevel))
            (tokinfo (assoc tok smie-indent-rules)))
+      ;; Set some default indent rules.
       (if (and toklevel (null (cadr toklevel)) (null tokinfo))
           (setq tokinfo (list (car toklevel))))
       ;; (if (and tokinfo (null toklevel))
       ;;     (error "Token %S has indent rule but has no parsing info" tok))
       (when toklevel
+        (unless tokinfo
+          ;; The default indentation after a keyword/operator is 0 for
+          ;; infix and t for prefix.
+          ;; Using the BNF syntax, we could come up with better
+          ;; defaults, but we only have the precedence levels here.
+          (setq tokinfo (list tok 'default-rule
+                              (if (cadr toklevel) 0 (smie-indent-offset t)))))
         (let ((offset
-               (cond
-                (tokinfo (or (smie-indent-offset-rule tokinfo pos)
-                             (smie-indent-offset t)))
-                ;; The default indentation after a keyword/operator
-                ;; is 0 for infix and t for prefix.
-                ;; Using the BNF syntax, we could come up with
-                ;; better defaults, but we only have the
-                ;; precedence levels here.
-                ((null (cadr toklevel)) (smie-indent-offset t))
-                (t 0))))
-          ;; For indentation after "(let" in SML-mode, we end up accumulating
-          ;; the offset of "(" and the offset of "let", so we use `min' to try
-          ;; and get it right either way.
-          (+ (min (smie-indent-virtual) (current-column)) offset))))))
+               (or (smie-indent-offset-rule tokinfo pos)
+                   (smie-indent-offset t))))
+          (let ((before (point)))
+            (goto-char pos)
+            (smie-indent-column offset before)))))))
 
 (defun smie-indent-exps ()
   ;; Indentation of sequences of simple expressions without
@@ -851,7 +1039,7 @@
   "Indent current line using the SMIE indentation engine."
   (interactive)
   (let* ((savep (point))
-	 (indent (condition-case nil
+	 (indent (condition-case-no-debug nil
 		     (save-excursion
                        (forward-line 0)
                        (skip-chars-forward " \t")
@@ -866,7 +1054,14 @@
           (save-excursion (indent-line-to indent))
         (indent-line-to indent)))))
 
-;;;###autoload
+(defun smie-indent-debug ()
+  "Show the rules used to compute indentation of current line."
+  (interactive)
+  (let ((smie-indent-debug-log '()))
+    (smie-indent-calculate)
+    ;; FIXME: please improve!
+    (message "%S" smie-indent-debug-log)))
+
 (defun smie-setup (op-levels indent-rules)
   (set (make-local-variable 'smie-indent-rules) indent-rules)
   (set (make-local-variable 'smie-op-levels) op-levels)
--- a/lisp/gnus/gnus-sum.el	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/gnus/gnus-sum.el	Wed Aug 18 13:11:01 2010 +0200
@@ -12627,7 +12627,7 @@
 (declare-function bookmark-default-handler "bookmark" (bmk))
 (declare-function bookmark-get-bookmark-record "bookmark" (bmk))
 (defvar bookmark-yank-point)
-(defvar bookmark-current-bookmark)
+(defvar bookmark-current-buffer)
 
 (defun gnus-summary-bookmark-make-record ()
   "Make a bookmark entry for a Gnus summary buffer."
--- a/lisp/image.el	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/image.el	Wed Aug 18 13:11:01 2010 +0200
@@ -616,7 +616,7 @@
     (let* ((animate (memq type image-animated-types))
 	   (image
 	    (append (list 'image :type type (if data-p :data :file) file-or-data)
-		    (if animate '(:index 0 :mask heuristic))
+		    (if animate '(:index 0))
 		    props)))
       (if animate
 	  (image-animate-start image))
--- a/lisp/newcomment.el	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/newcomment.el	Wed Aug 18 13:11:01 2010 +0200
@@ -945,12 +945,12 @@
 		   (delete-char n)
 		   (setq ,bindent (- ,bindent n)))))))))))
 
-;; Compute the number of extra comment starter characters
-;; (extra semicolons in Lisp mode, extra stars in C mode, etc.)
-;; If ARG is non-nil, just follow ARG.
-;; If the comment-starter is multi-char, just follow ARG.
-;; Otherwise obey comment-add, and double it if EXTRA is non-nil.
 (defun comment-add (arg)
+  "Compute the number of extra comment starter characters
+\(extra semicolons in Lisp mode, extra stars in C mode, etc.)
+If ARG is non-nil, just follow ARG.
+If the comment starter is multi-char, just follow ARG.
+Otherwise obey `comment-add'."
   (if (and (null arg) (= (string-match "[ \t]*\\'" comment-start) 1))
       (* comment-add 1)
     (1- (prefix-numeric-value arg))))
--- a/lisp/org/ChangeLog	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/org/ChangeLog	Wed Aug 18 13:11:01 2010 +0200
@@ -1,3 +1,13 @@
+2010-08-18  Glenn Morris  <rgm@gnu.org>
+
+	* ob.el: Require org when compiling.
+	(org-save-outline-visibility): Remove macro declaration.
+	* ob-emacs-lisp.el: Require ob-comint when compiling, for macros.
+	Remove unnecessary/macro declarations.
+	* org-docview.el: Require doc-view when compiling.
+	(doc-view-goto-page): Autoload rather than declaring.
+	(doc-view-current-page): Remove macro declaration.
+
 2010-08-17  Glenn Morris  <rgm@gnu.org>
 
 	* ob.el (tramp-compat-make-temp-file, org-edit-src-code)
--- a/lisp/org/ob-emacs-lisp.el	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/org/ob-emacs-lisp.el	Wed Aug 18 13:11:01 2010 +0200
@@ -28,15 +28,12 @@
 
 ;;; Code:
 (require 'ob)
+(eval-when-compile (require 'ob-comint))
 
 (defvar org-babel-default-header-args:emacs-lisp
   '((:hlines . "yes") (:colnames . "no"))
   "Default arguments for evaluating an emacs-lisp source block.")
 
-(declare-function org-babel-comint-with-output "ob-comint" (&rest body))
-(declare-function org-babel-comint-buffer-livep "ob-comint" (buffer))
-(declare-function org-babel-comint-wait-for-output "ob-comint" (buffer))
-(declare-function org-babel-comint-in-buffer "ob-comint" (buffer &rest body))
 (declare-function orgtbl-to-generic "org-table" (table params))
 
 (defun org-babel-expand-body:emacs-lisp (body params &optional processed-params)
--- a/lisp/org/ob.el	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/org/ob.el	Wed Aug 18 13:11:01 2010 +0200
@@ -29,7 +29,9 @@
 ;;   http://orgmode.org/worg/org-contrib/babel/
 
 ;;; Code:
-(eval-when-compile (require 'cl))
+(eval-when-compile
+  (require 'cl)
+  (require 'org))                  ; org-save-outline-visibility macro
 (require 'org-macs)
 
 (defvar org-babel-call-process-region-original)
@@ -40,10 +42,9 @@
 (declare-function tramp-file-name-user "tramp" (vec))
 (declare-function tramp-file-name-host "tramp" (vec))
 (declare-function org-icompleting-read "org" (&rest args))
-(declare-function org-edit-src-code "org-src" 
+(declare-function org-edit-src-code "org-src"
                   (&optional context code edit-buffer-name))
 (declare-function org-open-at-point "org" (&optional in-emacs reference-buffer))
-(declare-function org-save-outline-visibility "org" (use-markers &rest body))
 (declare-function org-narrow-to-subtree "org" ())
 (declare-function org-entry-get "org" (pom property &optional inherit literal-nil))
 (declare-function org-make-options-regexp "org" (kwds &optional extra))
--- a/lisp/org/org-docview.el	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/org/org-docview.el	Wed Aug 18 13:11:01 2010 +0200
@@ -45,9 +45,9 @@
 
 
 (require 'org)
+(eval-when-compile (require 'doc-view))	; doc-view-current-page macro
 
-(declare-function doc-view-goto-page "doc-view" (page))
-(declare-function doc-view-current-page "doc-view"  (&optional win))
+(autoload 'doc-view-goto-page "doc-view")
 
 (org-add-link-type "docview" 'org-docview-open)
 (add-hook 'org-store-link-functions 'org-docview-store-link)
--- a/lisp/progmodes/octave-mod.el	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/progmodes/octave-mod.el	Wed Aug 18 13:11:01 2010 +0200
@@ -171,9 +171,7 @@
 	     'font-lock-builtin-face
 	   'font-lock-preprocessor-face))
    ;; Fontify all builtin variables.
-   (cons (concat "\\<\\("
-		 (mapconcat 'identity octave-variables "\\|")
-		 "\\)\\>")
+   (cons (concat "\\<" (regexp-opt octave-variables) "\\>")
 	 'font-lock-variable-name-face)
    ;; Fontify all function declarations.
    (list octave-function-header-regexp
@@ -181,6 +179,30 @@
 	 '(3 font-lock-function-name-face nil t)))
   "Additional Octave expressions to highlight.")
 
+(defvar octave-font-lock-syntactic-keywords
+  ;; Try to distinguish the string-quotes from the transpose-quotes.
+  '(("[[({,; ]\\('\\)" (1 "\"'"))
+    (octave-font-lock-close-quotes)))
+
+(defun octave-font-lock-close-quotes (limit)
+  "Fix the syntax-table of the closing quotes of single-quote strings."
+  ;; Freely inspired from perl-font-lock-special-syntactic-constructs.
+  (let ((state (syntax-ppss)))
+    (while (< (point) limit)
+      (cond
+       ((eq (nth 3 state) ?\')
+        ;; A '..' string.
+        (save-excursion
+          (when (and (or (looking-at "\\('\\)")
+                         (re-search-forward "[^\\]\\(?:\\\\\\\\\\)*\\('\\)"
+                                            nil t))
+                     (not (eobp)))
+            (put-text-property (match-beginning 1) (match-end 1)
+                               'syntax-table (string-to-syntax "\"'"))))))
+
+      (setq state (parse-partial-sexp (point) limit nil nil state
+				      'syntax-table)))))
+
 (defcustom inferior-octave-buffer "*Inferior Octave*"
   "Name of buffer for running an inferior Octave process."
   :type 'string
@@ -195,9 +217,6 @@
     (define-key map " " 'octave-electric-space)
     (define-key map "\n" 'octave-reindent-then-newline-and-indent)
     (define-key map "\e\n" 'octave-indent-new-comment-line)
-    (define-key map "\M-\C-a" 'octave-beginning-of-defun)
-    (define-key map "\M-\C-e" 'octave-end-of-defun)
-    (define-key map "\M-\C-h" 'octave-mark-defun)
     (define-key map "\M-\C-q" 'octave-indent-defun)
     (define-key map "\C-c\C-b" 'octave-submit-bug-report)
     (define-key map "\C-c\C-p" 'octave-previous-code-line)
@@ -231,7 +250,9 @@
   "Keymap used in Octave mode.")
 
 
-(defvar octave-mode-menu
+
+(easy-menu-define octave-mode-menu octave-mode-map
+  "Menu for Octave mode."
   '("Octave"
     ("Lines"
       ["Previous Code Line"	octave-previous-code-line t]
@@ -247,9 +268,6 @@
       ["Mark Block"		octave-mark-block t]
       ["Close Block"		octave-close-block t])
     ("Functions"
-      ["Begin of Function"	octave-beginning-of-defun t]
-      ["End of Function"	octave-end-of-defun t]
-      ["Mark Function"		octave-mark-defun t]
       ["Indent Function"	octave-indent-defun t]
       ["Insert Function"	octave-insert-defun t])
     "-"
@@ -265,14 +283,14 @@
     ["Indent Line"		indent-according-to-mode t]
     ["Complete Symbol"		completion-at-point t]
     "-"
+    ;; FIXME: Make them toggle-buttons.
     ["Toggle Abbrev Mode"	abbrev-mode t]
     ["Toggle Auto-Fill Mode"	auto-fill-mode t]
     "-"
     ["Submit Bug Report"	octave-submit-bug-report t]
     "-"
     ["Describe Octave Mode"	describe-mode t]
-    ["Lookup Octave Index"	octave-help t])
-  "Menu for Octave mode.")
+    ["Lookup Octave Index"	info-lookup-symbol t]))
 
 (defvar octave-mode-syntax-table
   (let ((table (make-syntax-table)))
@@ -324,6 +342,7 @@
 newline or semicolon after an else or end keyword."
   :type 'boolean
   :group 'octave)
+
 (defcustom octave-block-offset 2
   "Extra indentation applied to statements in Octave block structures."
   :type 'integer
@@ -347,13 +366,13 @@
   (concat octave-block-else-regexp "\\|" octave-block-end-regexp))
 (defvar octave-block-match-alist
   '(("do" . ("until"))
-    ("for" . ("endfor" "end"))
-    ("function" . ("endfunction"))
-    ("if" . ("else" "elseif" "endif" "end"))
-    ("switch" . ("case" "otherwise" "endswitch" "end"))
-    ("try" . ("catch" "end_try_catch"))
-    ("unwind_protect" . ("unwind_protect_cleanup" "end_unwind_protect"))
-    ("while" . ("endwhile" "end")))
+    ("for" . ("end" "endfor"))
+    ("function" . ("end" "endfunction"))
+    ("if" . ("else" "elseif" "end" "endif"))
+    ("switch" . ("case" "otherwise" "end" "endswitch"))
+    ("try" . ("catch" "end" "end_try_catch"))
+    ("unwind_protect" . ("unwind_protect_cleanup" "end" "end_unwind_protect"))
+    ("while" . ("end" "endwhile")))
   "Alist with Octave's matching block keywords.
 Has Octave's begin keywords as keys and a list of the matching else or
 end keywords as associated values.")
@@ -514,7 +533,9 @@
   (set (make-local-variable 'normal-auto-fill-function) 'octave-auto-fill)
 
   (set (make-local-variable 'font-lock-defaults)
-       '(octave-font-lock-keywords nil nil))
+       '(octave-font-lock-keywords nil nil nil nil
+         (font-lock-syntactic-keywords . octave-font-lock-syntactic-keywords)
+         (parse-sexp-lookup-properties . t)))
 
   (set (make-local-variable 'imenu-generic-expression)
        octave-mode-imenu-generic-expression)
@@ -522,11 +543,15 @@
 
   (add-hook 'completion-at-point-functions
             'octave-completion-at-point-function nil t)
+  (set (make-local-variable 'beginning-of-defun-function)
+       'octave-beginning-of-defun)
 
-  (octave-add-octave-menu)
+  (easy-menu-add octave-mode-menu)
   (octave-initialize-completions)
   (run-mode-hooks 'octave-mode-hook))
 
+(defvar info-lookup-mode)
+
 (defun octave-help ()
   "Get help on Octave symbols from the Octave info files.
 Look up symbol in the function, operator and variable indices of the info files."
@@ -583,22 +608,6 @@
   (let ((case-fold-search nil))
     (re-search-backward regexp nil 'move count)))
 
-(defun octave-in-defun-p ()
-  "Return t if point is inside an Octave function declaration.
-The function is taken to start at the `f' of `function' and to end after
-the end keyword."
-  (let ((pos (point)))
-    (save-excursion
-      (or (and (octave-looking-at-kw "\\<function\\>")
-	       (octave-not-in-string-or-comment-p))
-	  (and (octave-beginning-of-defun)
-	       (condition-case nil
-		   (progn
-		     (octave-forward-block)
-		     t)
-		 (error nil))
-	       (< pos (point)))))))
-
 (defun octave-maybe-insert-continuation-string ()
   (if (or (octave-in-comment-p)
 	  (save-excursion
@@ -733,7 +742,7 @@
   "Properly indent the Octave function which contains point."
   (interactive)
   (save-excursion
-    (octave-mark-defun)
+    (mark-defun)
     (message "Indenting function...")
     (indent-region (point) (mark) nil))
   (message "Indenting function...done."))
@@ -990,16 +999,16 @@
 With positive ARG, do it that many times.  Negative argument -N means
 move forward to Nth following beginning of a function.
 Returns t unless search stops at the beginning or end of the buffer."
-  (interactive "p")
   (let* ((arg (or arg 1))
 	 (inc (if (> arg 0) 1 -1))
-	 (found))
+	 (found nil)
+         (case-fold-search nil))
     (and (not (eobp))
-	 (not (and (> arg 0) (octave-looking-at-kw "\\<function\\>")))
+	 (not (and (> arg 0) (looking-at "\\<function\\>")))
 	 (skip-syntax-forward "w"))
     (while (and (/= arg 0)
 		(setq found
-		      (octave-re-search-backward-kw "\\<function\\>" inc)))
+		      (re-search-backward "\\<function\\>" inc)))
       (if (octave-not-in-string-or-comment-p)
 	  (setq arg (- arg inc))))
     (if found
@@ -1007,40 +1016,6 @@
 	  (and (< inc 0) (goto-char (match-beginning 0)))
 	  t))))
 
-(defun octave-end-of-defun (&optional arg)
-  "Move forward to the end of an Octave function.
-With positive ARG, do it that many times.  Negative argument -N means
-move back to Nth preceding end of a function.
-
-An end of a function occurs right after the end keyword matching the
-`function' keyword that starts the function."
-  (interactive "p")
-  (or arg (setq arg 1))
-  (and (< arg 0) (skip-syntax-backward "w"))
-  (and (> arg 0) (skip-syntax-forward "w"))
-  (if (octave-in-defun-p)
-      (setq arg (- arg 1)))
-  (if (= arg 0) (setq arg -1))
-  (if (octave-beginning-of-defun (- arg))
-      (octave-forward-block)))
-
-(defun octave-mark-defun ()
-  "Put point at the beginning of this Octave function, mark at its end.
-The function marked is the one containing point or following point."
-  (interactive)
-  (let ((pos (point)))
-    (if (or (octave-in-defun-p)
-	    (and (octave-beginning-of-defun -1)
-		 (octave-in-defun-p)))
-	(progn
-	  (skip-syntax-forward "w")
-	  (octave-beginning-of-defun)
-	  (push-mark (point))
-	  (octave-end-of-defun)
-	  (exchange-point-and-mark))
-      (goto-char pos)
-      (message "No function to mark found"))))
-
 
 ;;; Filling
 (defun octave-auto-fill ()
@@ -1195,9 +1170,11 @@
 (defun octave-completion-at-point-function ()
   "Find the text to complete and the corresponding table."
   (let* ((beg (save-excursion (backward-sexp 1) (point)))
-         (end (if (< beg (point))
-                  (save-excursion (goto-char beg) (forward-sexp 1) (point))
-                (point))))
+         (end (point)))
+    (if (< beg (point))
+        ;; Extend region past point, if applicable.
+        (save-excursion (goto-char beg) (forward-sexp 1)
+                        (setq end (max end (point)))))
     (list beg end octave-completion-alist)))
 
 (defun octave-complete-symbol ()
@@ -1211,15 +1188,12 @@
 (defun octave-reindent-then-newline-and-indent ()
   "Reindent current Octave line, insert newline, and indent the new line.
 If Abbrev mode is on, expand abbrevs first."
+  ;; FIXME: None of this is Octave-specific.
   (interactive)
   (if abbrev-mode (expand-abbrev))
   (if octave-blink-matching-block
       (octave-blink-matching-block-open))
-  (save-excursion
-    (delete-region (point) (progn (skip-chars-backward " \t") (point)))
-    (indent-according-to-mode))
-  (insert "\n")
-  (indent-according-to-mode))
+  (reindent-then-newline-and-indent))
 
 (defun octave-electric-semi ()
   "Insert a semicolon in Octave mode.
@@ -1301,15 +1275,6 @@
   \n _ \n
   "endfunction" > \n)
 
-;;; Menu
-(defun octave-add-octave-menu ()
-  "Add the `Octave' menu to the menu bar in Octave mode."
-  (require 'easymenu)
-  (easy-menu-define octave-mode-menu-map octave-mode-map
-		    "Menu keymap for Octave mode." octave-mode-menu)
-  (easy-menu-add octave-mode-menu-map octave-mode-map))
-
-
 ;;; Communication with the inferior Octave process
 (defun octave-kill-process ()
   "Kill inferior Octave process and its buffer."
@@ -1375,7 +1340,7 @@
   "Send current Octave function to the inferior Octave process."
   (interactive)
   (save-excursion
-    (octave-mark-defun)
+    (mark-defun)
     (octave-send-region (point) (mark))))
 
 (defun octave-send-line (&optional arg)
--- a/lisp/progmodes/prolog.el	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/progmodes/prolog.el	Wed Aug 18 13:11:01 2010 +0200
@@ -31,7 +31,7 @@
 
 (defvar comint-prompt-regexp)
 (defvar comint-process-echoes)
-(defvar smie-indent-basic)
+(require 'smie)
 
 (defgroup prolog nil
   "Major mode for editing and running Prolog under Emacs."
--- a/lisp/term/ns-win.el	Wed Aug 18 12:35:23 2010 +0200
+++ b/lisp/term/ns-win.el	Wed Aug 18 13:11:01 2010 +0200
@@ -1003,7 +1003,7 @@
 
 (defun ns-get-pasteboard ()
   "Returns the value of the pasteboard."
-  (ns-get-cut-buffer-internal 'PRIMARY))
+  (ns-get-cut-buffer-internal 'CLIPBOARD))
 
 (declare-function ns-store-cut-buffer-internal "nsselect.m" (buffer string))
 
@@ -1011,7 +1011,7 @@
   "Store STRING into the pasteboard of the Nextstep display server."
   ;; Check the data type of STRING.
   (if (not (stringp string)) (error "Nonstring given to pasteboard"))
-  (ns-store-cut-buffer-internal 'PRIMARY string))
+  (ns-store-cut-buffer-internal 'CLIPBOARD string))
 
 ;; We keep track of the last text selected here, so we can check the
 ;; current selection against it, and avoid passing back our own text
--- a/src/ChangeLog	Wed Aug 18 12:35:23 2010 +0200
+++ b/src/ChangeLog	Wed Aug 18 13:11:01 2010 +0200
@@ -1,3 +1,44 @@
+2010-08-18  Stefan Monnier  <monnier@iro.umontreal.ca>
+
+	* eval.c (Fdefmacro): Only obey one declaration.
+
+	* casefiddle.c (casify_region): Setup gl_state.
+
+2010-08-18  Jan Djärv  <jan.h.d@swipnet.se>
+
+	* nsterm.m (ns_define_frame_cursor): Call x_update_cursor (Bug#6868).
+
+2010-08-18  Jan Djärv  <jan.h.d@swipnet.se>
+
+	* gtkutil.c (update_frame_tool_bar): Literal stings are const char*.
+
+2010-08-18  David De La Harpe Golden  <david@harpegolden.net>
+
+	* nsselect.m (QCLIPBOARD, NXPrimaryPboard): Define.
+	(symbol_to_nsstring): Map QCLIPBOARD => NSGeneralPboard,
+	QPRIMARY => NXPrimaryPboard.
+	(ns_string_to_symbol): NSGeneralPboard => QCLIPBOARD,
+	NXPrimaryPboard => QPRIMARY.
+	(nxatoms_of_nsselect): NXPrimaryPboard = PrimarySelection,
+	NXSecondaryPboard = SecondarySelection.
+	(syms_of_nsselect): Intern QCLIPBOARD (Bug#6677).
+
+2010-08-17  Stefan Monnier  <monnier@iro.umontreal.ca>
+
+	* gtkutil.c (update_frame_tool_bar): Don't assume TOOL_BAR_ITEM_LABEL
+	is a string.
+
+2010-08-17  Jan Djärv  <jan.h.d@swipnet.se>
+
+	* nsfns.m (ns_frame_parm_handlers): Add a slot for the
+	x_set_tool_bar_position handler.
+
+2010-08-17  Eli Zaretskii  <eliz@gnu.org>
+
+	* w32fns.c <w32_frame_parm_handlers>: Add a slot for the
+	x_set_tool_bar_position handler, needed to support changes from
+	2010-07-29 (revno 100939) for positioning the tool bar.  (Bug#6796)
+
 2010-08-16  Jan Djärv  <jan.h.d@swipnet.se>
 
 	* nsselect.m: include keyboard.h for QPRIMARY, remove its
@@ -30,8 +71,9 @@
 
 2010-08-15  Jan Djärv  <jan.h.d@swipnet.se>
 
-	* keyboard.c (parse_tool_bar_item): malloc buf.  Set TOOL_BAR_ITEM_LABEL
-	to empty string if not set to new_lbl (Bug#6855).
+	* keyboard.c (parse_tool_bar_item): malloc buf.
+	Set TOOL_BAR_ITEM_LABEL to empty string if not set to
+	new_lbl (Bug#6855).
 
 2010-08-14  Eli Zaretskii  <eliz@gnu.org>
 
@@ -39,8 +81,8 @@
 	* w32term.c (x_draw_stretch_glyph_string): In R2L rows, display
 	the cursor on the right edge of the stretch glyph.
 
-	* xdisp.c (window_box_right_offset, window_box_right): Fix
-	commentary.
+	* xdisp.c (window_box_right_offset, window_box_right):
+	Fix commentary.
 
 	* xdisp.c (Fcurrent_bidi_paragraph_direction): Fix paragraph
 	direction when point is inside a run of whitespace characters.
--- a/src/casefiddle.c	Wed Aug 18 12:35:23 2010 +0200
+++ b/src/casefiddle.c	Wed Aug 18 13:11:01 2010 +0200
@@ -221,6 +221,8 @@
   start_byte = CHAR_TO_BYTE (start);
   end_byte = CHAR_TO_BYTE (end);
 
+  SETUP_BUFFER_SYNTAX_TABLE();	/* For syntax_prefix_flag_p.  */
+
   while (start < end)
     {
       int c2, len;
--- a/src/eval.c	Wed Aug 18 12:35:23 2010 +0200
+++ b/src/eval.c	Wed Aug 18 13:11:01 2010 +0200
@@ -690,8 +690,8 @@
       tail = XCDR (tail);
     }
 
-  while (CONSP (Fcar (tail))
-	 && EQ (Fcar (Fcar (tail)), Qdeclare))
+  if (CONSP (Fcar (tail))
+      && EQ (Fcar (Fcar (tail)), Qdeclare))
     {
       if (!NILP (Vmacro_declaration_function))
 	{
--- a/src/gtkutil.c	Wed Aug 18 12:35:23 2010 +0200
+++ b/src/gtkutil.c	Wed Aug 18 13:11:01 2010 +0200
@@ -4292,7 +4292,8 @@
       GtkWidget *wbutton = NULL;
       GtkWidget *weventbox;
       Lisp_Object specified_file;
-      char *label = SSDATA (PROP (TOOL_BAR_ITEM_LABEL));
+      const char *label = (STRINGP (PROP (TOOL_BAR_ITEM_LABEL))
+                           ? SSDATA (PROP (TOOL_BAR_ITEM_LABEL)) : "");
       
       ti = gtk_toolbar_get_nth_item (GTK_TOOLBAR (wtoolbar), i);
 
--- a/src/nsfns.m	Wed Aug 18 12:35:23 2010 +0200
+++ b/src/nsfns.m	Wed Aug 18 13:11:01 2010 +0200
@@ -1041,6 +1041,7 @@
   x_set_font_backend, /* generic OK */
   x_set_alpha,
   0, /* x_set_sticky */  
+  0, /* x_set_tool_bar_position */  
 };
 
 
--- a/src/nsselect.m	Wed Aug 18 12:35:23 2010 +0200
+++ b/src/nsselect.m	Wed Aug 18 13:11:01 2010 +0200
@@ -37,7 +37,7 @@
 
 #define CUT_BUFFER_SUPPORT
 
-Lisp_Object QSECONDARY, QTEXT, QFILE_NAME;
+Lisp_Object QCLIPBOARD, QSECONDARY, QTEXT, QFILE_NAME;
 
 static Lisp_Object Vns_sent_selection_hooks;
 static Lisp_Object Vns_lost_selection_hooks;
@@ -46,6 +46,8 @@
 
 static Lisp_Object Qforeign_selection;
 
+/* NSGeneralPboard is pretty much analogous to X11 CLIPBOARD */
+NSString *NXPrimaryPboard;
 NSString *NXSecondaryPboard;
 
 
@@ -61,7 +63,8 @@
 symbol_to_nsstring (Lisp_Object sym)
 {
   CHECK_SYMBOL (sym);
-  if (EQ (sym, QPRIMARY))     return NSGeneralPboard;
+  if (EQ (sym, QCLIPBOARD))     return NSGeneralPboard;
+  if (EQ (sym, QPRIMARY))     return NXPrimaryPboard;
   if (EQ (sym, QSECONDARY))   return NXSecondaryPboard;
   if (EQ (sym, QTEXT))        return NSStringPboardType;
   return [NSString stringWithUTF8String: SDATA (XSYMBOL (sym)->xname)];
@@ -72,6 +75,8 @@
 ns_string_to_symbol (NSString *t)
 {
   if ([t isEqualToString: NSGeneralPboard])
+    return QCLIPBOARD;
+  if ([t isEqualToString: NXPrimaryPboard])
     return QPRIMARY;
   if ([t isEqualToString: NXSecondaryPboard])
     return QSECONDARY;
@@ -537,12 +542,14 @@
 void
 nxatoms_of_nsselect (void)
 {
-  NXSecondaryPboard = @"Selection";
+  NXPrimaryPboard = @"PrimarySelection";
+  NXSecondaryPboard = @"SecondarySelection";
 }
 
 void
 syms_of_nsselect (void)
 {
+  QCLIPBOARD = intern ("CLIPBOARD");	staticpro (&QCLIPBOARD);
   QSECONDARY = intern ("SECONDARY");	staticpro (&QSECONDARY);
   QTEXT      = intern ("TEXT"); 	staticpro (&QTEXT);
   QFILE_NAME = intern ("FILE_NAME"); 	staticpro (&QFILE_NAME);
--- a/src/nsterm.m	Wed Aug 18 12:35:23 2010 +0200
+++ b/src/nsterm.m	Wed Aug 18 13:11:01 2010 +0200
@@ -1792,6 +1792,9 @@
       EmacsView *view = FRAME_NS_VIEW (f);
       FRAME_POINTER_TYPE (f) = cursor;
       [[view window] invalidateCursorRectsForView: view];
+      /* Redisplay assumes this function also draws the changed frame
+         cursor, but this function doesn't, so do it explicitly.  */
+      x_update_cursor (f, 1);
     }
 }
 
--- a/src/w32fns.c	Wed Aug 18 12:35:23 2010 +0200
+++ b/src/w32fns.c	Wed Aug 18 13:11:01 2010 +0200
@@ -6812,6 +6812,7 @@
   x_set_font_backend,
   x_set_alpha,
   0, /* x_set_sticky */
+  0, /* x_set_tool_bar_position */
 };
 
 void