changeset 14665:c8d0095b3744 gui

maint: periodic merge with default.
author Jacob Dawid <jacob.dawid@googlemail.com>
date Fri, 18 May 2012 09:59:23 +0200
parents c2ca3b71cd7c (current diff) 7c463e490062 (diff)
children 7925a7d6547b
files NEWS configure.ac doc/interpreter/munge-texi.cc scripts/gethelp.cc
diffstat 106 files changed, 1129 insertions(+), 1187 deletions(-) [+]
line wrap: on
line diff
--- a/.hgtags
+++ b/.hgtags
@@ -64,3 +64,4 @@
 e320928eeb3aa2370b792e83dafc3e0ddecdc871 release-3-2-4
 ba4d6343524b406b0d15aee34579f80783581c54 release-3-6-1
 704f7895eef03008dd79848eb9da4bfb40787d73 release-3-6-0
+f947d2922febf12dcd1fb6e21b356756ecb54e55 rc-3-6-2-0
--- a/NEWS
+++ b/NEWS
@@ -94,6 +94,11 @@
 
       static
 
+ ** The colormap function now provides new options "list", "register",
+    and "unregister" to list all available colormap functions, and to
+    add or remove a function name from teh list of known colormap
+    functions.  Packages that implement extra colormaps should use these
+    commands with PKG_ADD and PKG_DEL statements.
 
 Summary of important user-visible changes for version 3.6:
 ---------------------------------------------------------
--- a/build-aux/common.mk
+++ b/build-aux/common.mk
@@ -342,6 +342,9 @@
 # The full path to the default doc cache file.
 doc_cache_file = @doc_cache_file@
 
+# The full path to the default texi macros file.
+texi_macros_file_file = @texi_macros_file@
+
 # Where to install and expect the info files describing Octave..
 infodir = @infodir@
 
@@ -632,6 +635,7 @@
   -e "s|%OCTAVE_PREFIX%|\"${prefix}\"|" \
   -e "s|%OCTAVE_API_VERSION%|\"${api_version}\"|" \
   -e "s|%OCTAVE_RELEASE%|\"${OCTAVE_RELEASE}\"|" \
+  -e "s|%OCTAVE_TEXI_MACROS_FILE%|\"${texi_macros_file}\"|" \
   -e "s|%OCTAVE_VERSION%|\"${version}\"|"
 $(simple_move_if_change_rule)
 endef
--- a/configure.ac
+++ b/configure.ac
@@ -118,6 +118,7 @@
 OCTAVE_SET_DEFAULT(man1dir, '$(mandir)/man1')
 OCTAVE_SET_DEFAULT(man1ext, '.1')
 OCTAVE_SET_DEFAULT(doc_cache_file, '$(octetcdir)/doc-cache')
+OCTAVE_SET_DEFAULT(texi_macros_file, '$(octetcdir)/macros.texi')
 OCTAVE_SET_DEFAULT(infofile, '$(infodir)/octave.info')
 OCTAVE_SET_DEFAULT(octincludedir, '$(includedir)/octave-$(version)/octave')
 OCTAVE_SET_DEFAULT(fcnfiledir, '$(datadir)/octave/$(version)/m')
--- a/doc/interpreter/Makefile.am
+++ b/doc/interpreter/Makefile.am
@@ -179,23 +179,17 @@
 	@$(GREP) '#define HAVE_UMFPACK 1' $(top_builddir)/config.h > /dev/null || { echo "Documentation creation requires missing UMFPACK library.  Cannot package distribution!" ; exit 1; }
 	@$(GREP) '#define HAVE_QHULL 1' $(top_builddir)/config.h > /dev/null || { echo "Documentation creation requires missing QHULL library.  Cannot package distribution!" ; exit 1; }
 
-octetc_DATA = doc-cache
+octetc_DATA = doc-cache macros.texi
 
 DOCSTRING_FILES = $(shell $(srcdir)/find-docstring-files.sh "$(top_srcdir)")
 
 doc-cache: $(DOCSTRING_FILES) mk_doc_cache.m
-	$(top_builddir)/run-octave -f -q -H $(srcdir)/mk_doc_cache.m doc-cache $(DOCSTRING_FILES) || { rm -f doc-cache; exit 1; }
-
-## Program compiled only to help build documentation.  No need to install
-noinst_PROGRAMS = munge-texi
-
-munge_texi_SOURCES = munge-texi.cc
+	$(top_builddir)/run-octave -f -q -H $(srcdir)/mk_doc_cache.m doc-cache $(srcdir)/macros.texi $(DOCSTRING_FILES) || { rm -f doc-cache; exit 1; }
 
 $(MUNGED_TEXI_SRC): $(DOCSTRING_FILES) $(munge_texi_SOURCES)
 
-%.texi: %.txi
-	@$(MAKE) $(AM_MAKEFLAGS) munge-texi$(BUILD_EXEEXT)
-	./munge-texi $(top_srcdir) $(DOCSTRING_FILES) < $< > $@-t
+%.texi: %.txi munge-texi.pl
+	$(PERL) $(srcdir)/munge-texi.pl $(top_srcdir) $(DOCSTRING_FILES) < $< > $@-t
 	mv $@-t $@
 
 contributors.texi: contributors.in
@@ -253,6 +247,7 @@
   images.mk \
   mk_doc_cache.m \
   mkcontrib.awk \
+  munge-texi.pl \
   octave.dvi \
   octave.html \
   octave.pdf \
--- a/doc/interpreter/basics.txi
+++ b/doc/interpreter/basics.txi
@@ -389,6 +389,8 @@
 
 @DOCSTRING(makeinfo_program)
 
+@DOCSTRING(texi_macros_file)
+
 @DOCSTRING(doc_cache_file)
 
 @DOCSTRING(suppress_verbose_help_message)
--- a/doc/interpreter/doccheck/aspell-octave.en.pws
+++ b/doc/interpreter/doccheck/aspell-octave.en.pws
@@ -534,6 +534,7 @@
 Mahalanobis
 makefile
 makefiles
+makeinfo
 Mandriva
 MANOVA
 manova
@@ -862,6 +863,7 @@
 stringanchors
 strncmp
 strncmpi
+strread
 struct
 structs
 subarrays
--- a/doc/interpreter/install.txi
+++ b/doc/interpreter/install.txi
@@ -196,7 +196,7 @@
 @end table
 
 If you wish to build Octave without GNU readline installed, you must use
-the @code{--disable-readline} option when running the configure script.
+the @option{--disable-readline} option when running the configure script.
 
 The following external software packages are optional but recommended:
 
new file mode 100644
--- /dev/null
+++ b/doc/interpreter/macros.texi
@@ -0,0 +1,65 @@
+@c Copyright (C) 2012 John W. Eaton
+@c
+@c This file is part of Octave.
+@c
+@c Octave is free software; you can redistribute it and/or modify it
+@c under the terms of the GNU General Public License as published by the
+@c Free Software Foundation; either version 3 of the License, or (at
+@c your option) any later version.
+@c 
+@c Octave is distributed in the hope that it will be useful, but WITHOUT
+@c ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+@c FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+@c for more details.
+@c 
+@c You should have received a copy of the GNU General Public License
+@c along with Octave; see the file COPYING.  If not, see
+@c <http://www.gnu.org/licenses/>.
+
+@c FIXME -- someday, we might replace this with @backslashchar, which
+@c has been added to Texinfo.
+
+@macro xbackslashchar
+\\
+@end macro
+
+@c The following macro is used for the on-line help system, but we don't
+@c want lots of `See also: foo, bar, and baz' strings cluttering the
+@c printed manual (that information should be in the supporting text for
+@c each group of functions and variables).
+
+@macro seealso {args}
+@iftex
+@vskip 2pt
+@end iftex
+@ifnottex
+@c Texinfo @sp should work but in practice produces ugly results for HTML.
+@c A simple blank line produces the correct behavior. 
+@c @sp 1
+
+@end ifnottex
+@noindent
+@strong{See also:} \args\.
+@end macro
+
+@c The following macro marks words that aspell should ignore during
+@c spellchecking.  Within Texinfo it has no effect as it merely replaces
+@c the macro call with the argument itself.
+
+@macro nospell {arg}
+\arg\
+@end macro
+
+@c The following macro works around a situation where the Info/plain text
+@c expansion of the @code{XXX} macro is `XXX'.  The use of the apostrophe
+@c can be confusing if the code segment itself ends with a transpose operator.
+@ifinfo
+@macro xcode{arg}
+\arg\
+@end macro
+@end ifinfo
+@ifnotinfo
+@macro xcode{arg}
+@code{\arg\}
+@end macro
+@end ifnotinfo
--- a/doc/interpreter/mk_doc_cache.m
+++ b/doc/interpreter/mk_doc_cache.m
@@ -38,17 +38,20 @@
     error ("unable to open %s for reading", file);
   else
     tmp = fread (fid, Inf, "*char")';
-    ## Strip off header lines
-    [~, text{i}] = strtok (tmp, doc_delim);
+    if (isempty (strfind (tmp, doc_delim)))
+      ## No delimiter, copy verbatim (this is the case for the file
+      ## containing macro definitions, for example).
+      text{i} = tmp;
+    else
+      ## Strip off header lines
+      [~, text{i}] = strtok (tmp, doc_delim);
+    endif
   endif
 endfor
 text = [text{:}, doc_delim];
 
-## Modify Octave-specific macros before passing to makeinfo
+## Strip Texinfo markers and docstring separators.
 text = regexprep (text, "-\\*- texinfo -\\*-[ \t]*[\r\n]*", "");
-text = regexprep (text, '@seealso *\{([^}]*)\}', "See also: $1.");
-text = regexprep (text, '@nospell *\{([^}]*)\}', "$1");
-text = regexprep (text, '@xcode *\{([^}]*)\}', "$1");
 text = strrep (text, '@', "@@");
 
 ## Write data to temporary file for input to makeinfo
deleted file mode 100644
--- a/doc/interpreter/munge-texi.cc
+++ /dev/null
@@ -1,403 +0,0 @@
-/*
-
-Copyright (C) 1999-2012 John W. Eaton
-
-This file is part of Octave.
-
-Octave is free software; you can redistribute it and/or modify it
-under the terms of the GNU General Public License as published by the
-Free Software Foundation; either version 3 of the License, or (at your
-option) any later version.
-
-Octave is distributed in the hope that it will be useful, but WITHOUT
-ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
-FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
-for more details.
-
-You should have received a copy of the GNU General Public License
-along with Octave; see the file COPYING.  If not, see
-<http://www.gnu.org/licenses/>.
-
-*/
-
-#include <cctype>
-#include <iostream>
-#include <fstream>
-#include <string>
-#include <map>
-
-#include <cstdlib>
-#include <cstring>
-
-static std::string top_srcdir;
-
-static const char doc_delim = '';
-
-static std::map<std::string, std::string> help_text;
-
-static void
-fatal (const std::string& msg)
-{
-  std::cerr << msg << "\n";
-  exit (1);
-}
-
-static void
-usage (void)
-{
-  std::cerr << "usage: munge-texi TOP-SRCDIR DOCSTRING-FILE < file\n";
-  exit (1);
-}
-
-static std::string
-extract_symbol_name (std::istream& is)
-{
-  std::string symbol_name;
-
-  int c;
-  while ((c = is.get ()) != EOF && c != '\n')
-    symbol_name += static_cast<char> (c);
-
-  return symbol_name;
-}
-
-static std::string
-extract_docstring (std::istream& is)
-{
-  std::string doc;
-
-  int c;
-  while ((c = is.get ()) != EOF && c != doc_delim)
-    {
-      // Expand @seealso commands to Texinfo references.
-      if (c == '@')
-        {
-          char buf[16];
-          int i = 0;
-          buf[i++] = static_cast<char> (c);
-
-          if ((   buf[i++] = static_cast<char> (is.get ())) == 's'
-              && (buf[i++] = static_cast<char> (is.get ())) == 'e'
-              && (buf[i++] = static_cast<char> (is.get ())) == 'e'
-              && (buf[i++] = static_cast<char> (is.get ())) == 'a'
-              && (buf[i++] = static_cast<char> (is.get ())) == 'l'
-              && (buf[i++] = static_cast<char> (is.get ())) == 's'
-              && (buf[i++] = static_cast<char> (is.get ())) == 'o'
-              && (buf[i++] = static_cast<char> (is.get ())) == '{')
-            {
-              doc += "@seealso{";
-
-              bool first = true;
-
-              // process @seealso parameters
-              while ((c = is.get ()) != EOF
-                     && c != doc_delim
-                     && c != '}')
-                {
-                  // ignore whitespace and delimiters
-                  while (   c == ' '
-                         || c == '\t'
-                         || c == '\r'
-                         || c == '\n'
-                         || c == ',')
-                    {
-                      c = is.get ();
-                    }
-
-                  // test for end of @seealso
-                  if (c == '}')
-                    break;
-
-                  // get function name
-                  std::string function_name;
-                  do
-                    function_name += static_cast<char> (c);
-                  while ((c = is.get ()) != EOF
-                          && c != doc_delim
-                          && c != ' '
-                          && c != '\t'
-                          && c != '\r'
-                          && c != '\n'
-                          && c != ','
-                          && c != '}');
-                  if (first)
-                    first = false;
-                  else
-                    doc += ", ";
-
-                  if (function_name[0] == '@')
-                    function_name = "@" + function_name;
-
-                  doc += "@ref{doc-" + function_name + ",,"
-                    + function_name + "}";
-
-                  // test for end of @seealso
-                  if (c == '}')
-                    break;
-                }
-              if (c == '}')
-                doc += static_cast<char> (c);
-            }
-          else
-            {
-              for (int j = 0; j < i; j++)
-                doc += buf[j];
-            }
-        }
-      else
-        doc += static_cast<char> (c);
-    }
-  return doc;
-}
-
-static void
-skip_comments (std::ifstream& is)
-{
-  int c;
-
-  bool in_comment = false;
-
-  while ((c = is.get ()) != EOF)
-    {
-      if (c == '#')
-        in_comment = true;
-      else if (c == '\n')
-        in_comment = false;
-      else if (! (in_comment || ::isspace (c)))
-        {
-          is.putback (c);
-          break;
-        }
-    }
-}
-
-static void
-process_doc_file (const std::string& fname)
-{
-  std::ifstream infile (fname.c_str ());
-
-  if (infile)
-    {
-      skip_comments (infile);
-
-      if (infile.get () != doc_delim)
-        fatal ("invalid doc file format");
-
-      std::string symbol_name;
-
-      do
-        {
-          symbol_name = extract_symbol_name (infile);
-
-          if (! symbol_name.empty ())
-            {
-              std::string doc_string = extract_docstring (infile);
-
-              if (help_text.find (symbol_name) != help_text.end ())
-                std::cerr << "ignoring duplicate entry for "
-                          << symbol_name << "\n";
-              else
-                help_text[symbol_name] = doc_string;
-            }
-        }
-      while (! symbol_name.empty ());
-    }
-  else
-    fatal ("unable to open docfile");
-}
-
-static bool
-recover_from_macro (std::ostream& os, char *buf, int i)
-{
-  bool bol = false;
-
-  buf[i] = '\0';
-  os << buf;
-
-  if (buf[i - 1] == '\n')
-    bol = true;
-
-  return bol;
-}
-
-static void
-process_example_file (const std::string& file_name, std::ostream& os)
-{
-  std::ifstream infile (file_name.c_str ());
-
-  if (infile)
-    {
-      os << "@verbatim\n";
-
-      int c;
-      int clast = 0;
-
-      while ((c = infile.get ()) != EOF)
-        {
-          os << static_cast<char> (c);
-          clast = c;
-        }
-
-      if (clast != '\n')
-        os << "\n";
-
-      os << "@end verbatim\n";
-    }
-  else
-    fatal ("unable to open example file " + file_name);
-}
-
-static void
-process_texi_input_file (std::istream& is, std::ostream& os)
-{
-  os << "@c DO NOT EDIT!  Generated automatically by munge-texi.\n\n";
-
-  bool bol = true;
-
-  int c;
-  while ((c = is.get ()) != EOF)
-    {
-      if (bol)
-        {
-          if (c == '@')
-            {
-              char buf[16];
-              int i = 0;
-              buf[i++] = static_cast<char> (c);
-
-              buf[i++] = c = static_cast<char> (is.get ());
-
-              if (c == 'D')
-                {
-                  std::string symbol_name;
-
-                  if (   (buf[i++] = static_cast<char> (is.get ())) == 'O'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'C'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'S'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'T'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'R'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'I'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'N'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'G'
-                      && (buf[i++] = static_cast<char> (is.get ())) == '(')
-                    {
-                      while ((c = is.get ()) != EOF && c != ')')
-                        symbol_name += static_cast<char> (c);
-
-                      if (is.eof ())
-                        fatal ("end of file while reading @DOCSTRING command");
-                      else
-                        {
-                          std::string doc_string = help_text[symbol_name];
-
-                          size_t len = doc_string.length ();
-
-                          int j = 0;
-
-                          // If there is a leading comment with the file
-                          // name, copy it to the output.
-                          if (len > 1
-                              && doc_string[j] == '@'
-                              && doc_string[j+1] == 'c')
-                            {
-                              j = 2;
-                              while (doc_string[j++] != '\n')
-                                /* find eol */;
-
-                              os << doc_string.substr (0, j);
-                            }
-
-                          while (doc_string[j] == ' ')
-                            j++;
-
-                          if (doc_string.substr (j, 15) == "-*- texinfo -*-")
-                            {
-                              j += 15;
-
-                              while (isspace (doc_string[j]))
-                                j++;
-
-                              // Make `see also' references in functions
-                              // possible using @anchor{TAG} (new with
-                              // Texinfo 4.0).
-
-                              if (symbol_name[0] == '@')
-                                symbol_name = "@" + symbol_name;
-
-                              os << "@anchor{doc-" << symbol_name << "}\n";
-
-                              os << doc_string.substr (j);
-                            }
-                          else
-                            os << doc_string;
-                        }
-                    }
-                  else
-                    bol = recover_from_macro (os, buf, i);
-                }
-              else if (c == 'E')
-                {
-                  std::string file_name;
-
-                  if (   (buf[i++] = static_cast<char> (is.get ())) == 'X'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'A'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'M'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'P'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'L'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'E'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'F'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'I'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'L'
-                      && (buf[i++] = static_cast<char> (is.get ())) == 'E'
-                      && (buf[i++] = static_cast<char> (is.get ())) == '(')
-                    {
-                      while ((c = is.get ()) != EOF && c != ')')
-                        file_name += static_cast<char> (c);
-
-                      file_name = top_srcdir + "/examples/" + file_name;
-
-                      process_example_file (file_name, os);
-                    }
-                  else
-                    bol = recover_from_macro (os, buf, i);
-                }
-              else
-                bol = recover_from_macro (os, buf, i);
-            }
-          else
-            os.put (static_cast<char> (c));
-        }
-      else
-        {
-          if (c == '\n')
-            bol = true;
-
-          os.put (static_cast<char> (c));
-        }
-    }
-}
-
-int
-main (int argc, char **argv)
-{
-  int retval = 0;
-
-  if (argc > 1)
-    {
-      top_srcdir = *++argv;
-
-      while (*++argv)
-        process_doc_file (*argv);
-
-      process_texi_input_file (std::cin, std::cout);
-    }
-  else
-    {
-      usage ();
-
-      retval = 1;
-    }
-
-  return retval;
-
-}
new file mode 100755
--- /dev/null
+++ b/doc/interpreter/munge-texi.pl
@@ -0,0 +1,124 @@
+#!/usr/bin/perl -w
+
+# Validate program call
+die "usage: munge-texi TOP-SRCDIR DOCSTRING-FILE < file" if (@ARGV < 2);
+
+$top_srcdir = shift (@ARGV);
+
+# Constant patterns
+$doc_delim = qr/^\c_/;
+$tex_delim = qr/\Q-*- texinfo -*-\E/;
+$comment_line = qr/^\s*(?:$|#)/;
+# Pre-declare hash size for efficiency
+keys(%help_text) = 1800;
+
+################################################################################
+# Load DOCSTRINGS into memory while expanding @seealso references
+foreach $DOCSTRING_file (@ARGV)
+{
+   open (DOCFH, $DOCSTRING_file) or die "Unable to open $DOCSTRING_file\n";
+
+   # Skip comments
+   while (defined ($_ = <DOCFH>) and /$comment_line/o) {;}
+
+   # Validate DOCSTRING file format
+   die "invalid doc file format\n" if (! /$doc_delim/o);
+   
+   do 
+   {
+     chomp;
+     $symbol = substr ($_,1);
+     $docstring = extract_docstring ();
+     if ($help_text{$symbol})
+     {
+        warn "ignoring duplicate entry for $symbol\n";
+     }
+     else
+     {
+       $help_text{$symbol} = $docstring;
+     }
+
+   } while (! eof);
+
+}
+
+################################################################################
+# Process .txi to .texi by expanding @DOCSTRING, @EXAMPLEFILE macros
+
+# Add warning header
+print '@c DO NOT EDIT!  Generated automatically by munge-texi.',"\n\n";
+
+TXI_LINE: while (<STDIN>)
+{
+   if (/^\s*\@DOCSTRING\((\S+)\)/)
+   {
+      $func = $1;
+      $docstring = $help_text{$func};
+      if (! $docstring)
+      {
+        warn "no docstring entry for $func\n";
+        next TXI_LINE;
+      }
+
+      $func =~ s/^@/@@/;   # Texinfo uses @@ to produce '@'
+      $docstring =~ s/^$tex_delim$/\@anchor{doc-$func}/m;
+      print $docstring,"\n";
+
+      next TXI_LINE;
+   }
+   if (/^\s*\@EXAMPLEFILE\((\S+)\)/)
+   {
+      $fname = "$top_srcdir/examples/$1";
+      print '@verbatim',"\n";
+      open (EXAMPFH, $fname) or die "unable to open example file $fname\n";
+      while (<EXAMPFH>) 
+      { 
+         print $_;
+         print "\n" if (eof and substr ($_, -1) ne "\n");
+      }
+      close (EXAMPFH);
+      print '@end verbatim',"\n\n";
+
+      next TXI_LINE;
+   }
+
+   # pass ordinary lines straight through to output
+   print $_;
+}
+
+
+################################################################################
+# Subroutines 
+################################################################################
+sub extract_docstring
+{
+   my ($docstring, $arg_list, $func_list, $repl, $rest_of_line);
+   
+   while (defined ($_ = <DOCFH>) and ! /$doc_delim/o)
+   {
+      # expand any @seealso references
+      if (m'^@seealso{')
+      {
+         # Join multiple lines until full macro body found
+         while (! /}/m) { $_ .= <DOCFH>; }
+
+         ($arg_list, $rest_of_line) = m'^@seealso{(.*)}(.*)?'s;
+        
+         $func_list = $arg_list;
+         $func_list =~ s/\s+//gs;
+         $repl = "";
+         foreach $func (split (/,/, $func_list))
+         {
+            $func =~ s/^@/@@/;   # Texinfo uses @@ to produce '@'
+            $repl .= "\@ref{doc-$func,,$func}, ";
+         }
+         substr($repl,-2) = "";   # Remove last ', ' 
+         $_ = "\@seealso{$repl}$rest_of_line";
+      }
+
+      $docstring .= $_;
+   }
+
+   return $docstring;
+}
+
--- a/doc/interpreter/octave.texi
+++ b/doc/interpreter/octave.texi
@@ -19,46 +19,7 @@
 \input texinfo
 @setfilename octave.info
 
-@c The following macro is used for the on-line help system, but we don't
-@c want lots of `See also: foo, bar, and baz' strings cluttering the
-@c printed manual (that information should be in the supporting text for
-@c each group of functions and variables).
-
-@macro seealso {args}
-@iftex
-@vskip 2pt
-@end iftex
-@ifnottex
-@c Texinfo @sp should work but in practice produces ugly results for HTML.
-@c A simple blank line produces the correct behavior. 
-@c @sp 1
-
-@end ifnottex
-@noindent
-@strong{See also:} \args\.
-@end macro
-
-@c The following macro marks words that aspell should ignore during
-@c spellchecking.  Within Texinfo it has no effect as it merely replaces
-@c the macro call with the argument itself.
-
-@macro nospell {arg}
-\arg\
-@end macro
-
-@c The following macro works around a situation where the Info/plain text
-@c expansion of the @code{XXX} macro is `XXX'.  The use of the apostrophe
-@c can be confusing if the code segment itself ends with a transpose operator.
-@ifinfo
-@macro xcode{arg}
-\arg\
-@end macro
-@end ifinfo
-@ifnotinfo
-@macro xcode{arg}
-@code{\arg\}
-@end macro
-@end ifnotinfo
+@include macros.texi
 
 @ifinfo
 @format
--- a/etc/HACKING
+++ b/etc/HACKING
@@ -5,7 +5,7 @@
 
 * Working from the repository
 
-These notes are intended to help people working on sources checked-out from
+These notes are intended to help people working on sources cloned from
 the savannah source code repository.
 These requirements do not apply when building from a distribution tarball.
 
@@ -13,7 +13,7 @@
 
 We've opted to keep only the highest-level sources in the repository.
 This eases our maintenance burden, (fewer merges, etc.), but imposes
-more requirements on anyone wishing to build from the just-checked-out
+more requirements on anyone wishing to build from the just-cloned
 sources.  For example, you have to use the latest stable versions of
 the maintainer tools we depend upon, including:
 
@@ -35,15 +35,15 @@
 Later, after synchronizing from the repository, a plain `make' should
 be sufficient.
 
-** First checkout
+** First clone
 
-Obviously, if you are reading these notes, you did manage to check out
+If you are reading these notes, you may have already managed to clone
 this package from the repository.  For the record, you will find all the
 relevant information on downloading sources at:
 
   http://www.gnu.org/software/octave/download.html
 
-After checking out Octave, you will need to run the autogen.sh script:
+After cloning Octave, you will need to run the autogen.sh script:
 
   $ ./autogen.sh
 
@@ -51,8 +51,7 @@
 fragments and then runs the bootstrap script.  The bootstrap script comes
 from gnulib, but is kept in the Octave source archive.  It should be
 updated from the gnulib sources as necssary.  The bootstrap script takes
-care of checking out a copy of gnulib, running the autotools, and
-generating the configure script.
+care of running the autotools and generating the configure script.
 
 If you have a copy of gnulib in some directory apart from the Octave
 source tree, then pass the name of the directory containing gnulib-tool
@@ -66,12 +65,10 @@
 gnulib-tool script resides).
 
 By using an external gnulib directory, you can share a single gnulib source
-tree among several projects.  Regardless of the location of the gnulib
-sources, the bootstrap script will try to update them if it appears
-that they are checked out using git.  Otherwise, it is your
-responsibility to keep the gnulib sources up to date.  They change
-frequently, so the best way to stay current is probably to use git to
-do the job.
+tree among several projects.  Since 2011, the gnulib sources are a Mercurial
+subrepository, so they will be automatically updated to the
+corresponding Mercurial revision if you update the working directory to
+a past revision not too far in the past.
 
 Additional options besides --gnulib-srcdir can be passed to autogen.sh and
 they will be forwarded without modification to the bootstrap script.
@@ -83,8 +80,8 @@
   $ make
   $ make check
 
-At this point, there should be no difference between your local copy,
-and the master copy:
+At this point, there should be no difference between your working tree
+and the currently visited hg revision:
 
   $ hg diff
 
--- a/liboctave/Array.cc
+++ b/liboctave/Array.cc
@@ -884,7 +884,8 @@
 // The default fill value.  Override if you want a different one.
 
 template <class T>
-const T& Array<T>::resize_fill_value ()
+T
+Array<T>::resize_fill_value (void) const
 {
   static T zero = T ();
   return zero;
@@ -1164,16 +1165,21 @@
 Array<T>::assign (const idx_vector& i, const idx_vector& j,
                   const Array<T>& rhs, const T& rfv)
 {
+  bool initial_dims_all_zero = dimensions.all_zero ();
+
   // Get RHS extents, discarding singletons.
   dim_vector rhdv = rhs.dims ();
+
   // Get LHS extents, allowing Fortran indexing in the second dim.
   dim_vector dv = dimensions.redim (2);
+
   // Check for out-of-bounds and form resizing dimensions.
   dim_vector rdv;
+
   // In the special when all dimensions are zero, colons are allowed
   // to inquire the shape of RHS.  The rules are more obscure, so we
   // solve that elsewhere.
-  if (dv.all_zero ())
+  if (initial_dims_all_zero)
     rdv = zero_dims_inquire (i, j, rhdv);
   else
     {
@@ -1267,6 +1273,8 @@
     assign (ia(0), ia(1), rhs, rfv);
   else if (ial > 0)
     {
+      bool initial_dims_all_zero = dimensions.all_zero ();
+
       // Get RHS extents, discarding singletons.
       dim_vector rhdv = rhs.dims ();
 
@@ -1279,7 +1287,7 @@
       // In the special when all dimensions are zero, colons are
       // allowed to inquire the shape of RHS.  The rules are more
       // obscure, so we solve that elsewhere.
-      if (dv.all_zero ())
+      if (initial_dims_all_zero)
         rdv = zero_dims_inquire (ia, rhdv);
       else
         {
--- a/liboctave/Array.h
+++ b/liboctave/Array.h
@@ -450,46 +450,69 @@
 
   Array<T> index (const Array<idx_vector>& ia) const;
 
-  static const T& resize_fill_value ();
+  virtual T resize_fill_value (void) const;
 
   // Resizing (with fill).
 
-  void resize1 (octave_idx_type n, const T& rfv = resize_fill_value ());
+  void resize1 (octave_idx_type n, const T& rfv);
+  void resize1 (octave_idx_type n) { resize1 (n, resize_fill_value ()); }
 
-  void resize (octave_idx_type n) GCC_ATTR_DEPRECATED
-    { resize1 (n); }
+  void resize (octave_idx_type n) GCC_ATTR_DEPRECATED { resize1 (n); }
 
-  void resize (octave_idx_type nr, octave_idx_type nc,
-               const T& rfv = resize_fill_value ()) GCC_ATTR_DEPRECATED
+  void resize (octave_idx_type nr, octave_idx_type nc, const T& rfv) GCC_ATTR_DEPRECATED
   {
     resize2 (nr, nc, rfv);
   }
 
-  void resize (const dim_vector& dv, const T& rfv = resize_fill_value ());
+  void resize (octave_idx_type nr, octave_idx_type nc) GCC_ATTR_DEPRECATED
+  {
+    resize2 (nr, nc, resize_fill_value ());
+  }
+
+  void resize (const dim_vector& dv, const T& rfv);
+  void resize (const dim_vector& dv) { resize (dv, resize_fill_value ()); }
 
   // Indexing with possible resizing and fill
   // FIXME -- this is really a corner case, that should better be
   // handled directly in liboctinterp.
 
-  Array<T> index (const idx_vector& i, bool resize_ok,
-                  const T& rfv = resize_fill_value ()) const;
+  Array<T> index (const idx_vector& i, bool resize_ok, const T& rfv) const;
+  Array<T> index (const idx_vector& i, bool resize_ok) const
+  {
+    return index (i, resize_ok, resize_fill_value ());
+  }
 
-  Array<T> index (const idx_vector& i, const idx_vector& j,
-                  bool resize_ok, const T& rfv = resize_fill_value ()) const;
+  Array<T> index (const idx_vector& i, const idx_vector& j, bool resize_ok, const T& rfv) const;
+  Array<T> index (const idx_vector& i, const idx_vector& j, bool resize_ok) const
+  {
+    return index (i, j, resize_ok, resize_fill_value ());
+  }
 
-  Array<T> index (const Array<idx_vector>& ia,
-                  bool resize_ok, const T& rfv = resize_fill_value ()) const;
+  Array<T> index (const Array<idx_vector>& ia, bool resize_ok, const T& rfv) const;
+  Array<T> index (const Array<idx_vector>& ia, bool resize_ok) const
+  {
+    return index (ia, resize_ok, resize_fill_value ());
+  }
 
   // Indexed assignment (always with resize & fill).
 
-  void assign (const idx_vector& i, const Array<T>& rhs,
-               const T& rfv = resize_fill_value ());
+  void assign (const idx_vector& i, const Array<T>& rhs, const T& rfv);
+  void assign (const idx_vector& i, const Array<T>& rhs)
+  {
+    assign (i, rhs, resize_fill_value ());
+  }
 
-  void assign (const idx_vector& i, const idx_vector& j, const Array<T>& rhs,
-               const T& rfv = resize_fill_value ());
+  void assign (const idx_vector& i, const idx_vector& j, const Array<T>& rhs, const T& rfv);
+  void assign (const idx_vector& i, const idx_vector& j, const Array<T>& rhs)
+  {
+    assign (i, j, rhs, resize_fill_value ());
+  }
 
-  void assign (const Array<idx_vector>& ia, const Array<T>& rhs,
-               const T& rfv = resize_fill_value ());
+  void assign (const Array<idx_vector>& ia, const Array<T>& rhs, const T& rfv);
+  void assign (const Array<idx_vector>& ia, const Array<T>& rhs)
+  {
+    assign (ia, rhs, resize_fill_value ());
+  }
 
   // Deleting elements.
 
@@ -672,8 +695,11 @@
 
 private:
 
-  void resize2 (octave_idx_type nr, octave_idx_type nc,
-                const T& rfv = resize_fill_value ());
+  void resize2 (octave_idx_type nr, octave_idx_type nc, const T& rfv);
+  void resize2 (octave_idx_type nr, octave_idx_type nc)                
+  {
+    resize2 (nr, nc, resize_fill_value ());
+  }
 
   static void instantiation_guard ();
 };
--- a/liboctave/CColVector.h
+++ b/liboctave/CColVector.h
@@ -132,8 +132,7 @@
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const ComplexColumnVector& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, ComplexColumnVector& a);
 
-  void resize (octave_idx_type n,
-               const Complex& rfv = Array<Complex>::resize_fill_value ())
+  void resize (octave_idx_type n, const Complex& rfv = Complex (0))
   {
     Array<Complex>::resize (dim_vector (n, 1), rfv);
   }
--- a/liboctave/CMatrix.h
+++ b/liboctave/CMatrix.h
@@ -152,7 +152,7 @@
   ComplexColumnVector column (octave_idx_type i) const;
 
   void resize (octave_idx_type nr, octave_idx_type nc,
-               const Complex& rfv = resize_fill_value ())
+               const Complex& rfv = Complex (0))
   {
     MArray<Complex>::resize (dim_vector (nr, nc), rfv);
   }
@@ -378,9 +378,6 @@
 
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const ComplexMatrix& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, ComplexMatrix& a);
-
-  static Complex resize_fill_value (void) { return Complex (0.0, 0.0); }
-
 };
 
 extern OCTAVE_API ComplexMatrix conj (const ComplexMatrix& a);
--- a/liboctave/CNDArray.h
+++ b/liboctave/CNDArray.h
@@ -135,8 +135,6 @@
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const ComplexNDArray& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, ComplexNDArray& a);
 
-  static Complex resize_fill_value (void) { return Complex (0.0, 0.0); }
-
   //  bool all_elements_are_real (void) const;
   //  bool all_integers (double& max_val, double& min_val) const;
 
--- a/liboctave/CRowVector.h
+++ b/liboctave/CRowVector.h
@@ -112,8 +112,7 @@
   friend std::ostream& operator << (std::ostream& os, const ComplexRowVector& a);
   friend std::istream& operator >> (std::istream& is, ComplexRowVector& a);
 
-  void resize (octave_idx_type n,
-               const Complex& rfv = Array<Complex>::resize_fill_value ())
+  void resize (octave_idx_type n, const Complex& rfv = Complex (0))
   {
     Array<Complex>::resize (dim_vector (1, n), rfv);
   }
--- a/liboctave/DiagArray2.cc
+++ b/liboctave/DiagArray2.cc
@@ -82,16 +82,6 @@
 
 // A two-dimensional array with diagonal elements only.
 
-template <typename T>
-void
-DiagArray2<T>::check_idx (octave_idx_type r, octave_idx_type c) const
-{
-  if (r < 0 || r >= dim1 ())
-    gripe_index_out_of_range (2, 1, r+1, dim1 ());
-  if (c < 0 || c >= dim2 ())
-    gripe_index_out_of_range (2, 2, c+1, dim2 ());
-}
-
 template <class T>
 void
 DiagArray2<T>::resize (octave_idx_type r, octave_idx_type c,
@@ -121,3 +111,24 @@
 
   return result;
 }
+
+template <typename T>
+bool
+DiagArray2<T>::check_idx (octave_idx_type r, octave_idx_type c) const
+{
+  bool ok = true;
+
+  if (r < 0 || r >= dim1 ())
+    {
+      gripe_index_out_of_range (2, 1, r+1, dim1 ());
+      ok = false;
+    }
+
+  if (c < 0 || c >= dim2 ())
+    {
+      gripe_index_out_of_range (2, 2, c+1, dim2 ());
+      ok = false;
+    }
+
+  return ok;
+}
--- a/liboctave/DiagArray2.h
+++ b/liboctave/DiagArray2.h
@@ -119,22 +119,33 @@
   T& dgelem (octave_idx_type i)
     { return Array<T>::elem (i); }
 
-  void check_idx (octave_idx_type r, octave_idx_type c) const;
+  T checkelem (octave_idx_type r, octave_idx_type c) const
+    {
+      return check_idx (r, c) ? elem (r, c) : T (0);
+    }
 
   T operator () (octave_idx_type r, octave_idx_type c) const
     {
 #if defined (BOUNDS_CHECKING)
-      check_idx (r, c);
+      checkelem (r, c);
+#else
+      return elem (r, c);
 #endif
-      return elem (r, c);
+    }
+
+  T& checkelem (octave_idx_type r, octave_idx_type c)
+    {
+      static T zero (0);
+      return check_idx (r, c) ? elem (r, c) : zero;
     }
 
   T& operator () (octave_idx_type r, octave_idx_type c)
     {
 #if defined (BOUNDS_CHECKING)
-      check_idx (r, c);
+      return checkelem (r, c);
+#else
+      return elem (r, c);
 #endif
-      return elem (r, c);
     }
 
   // No checking.
@@ -150,8 +161,11 @@
   T dgxelem (octave_idx_type i) const
     { return Array<T>::xelem (i); }
 
-  void resize (octave_idx_type n, octave_idx_type m,
-               const T& rfv = Array<T>::resize_fill_value ());
+  void resize (octave_idx_type n, octave_idx_type m, const T& rfv);
+  void resize (octave_idx_type n, octave_idx_type m)
+  {
+    resize (n, m, Array<T>::resize_fill_value ());
+  }
 
   DiagArray2<T> transpose (void) const;
   DiagArray2<T> hermitian (T (*fcn) (const T&) = 0) const;
@@ -166,6 +180,10 @@
 
   void print_info (std::ostream& os, const std::string& prefix) const
     { Array<T>::print_info (os, prefix); }
+
+private:
+
+  bool check_idx (octave_idx_type r, octave_idx_type c) const;
 };
 
 #endif
--- a/liboctave/boolMatrix.h
+++ b/liboctave/boolMatrix.h
@@ -84,14 +84,10 @@
   friend std::istream& operator >> (std::istream& is, Matrix& a);
 #endif
 
-  void resize (octave_idx_type nr, octave_idx_type nc,
-               bool rfv = resize_fill_value ())
+  void resize (octave_idx_type nr, octave_idx_type nc, bool rfv = false)
   {
     Array<bool>::resize (dim_vector (nr, nc), rfv);
   }
-
-  static bool resize_fill_value (void) { return false; }
-
 };
 
 MM_BOOL_OP_DECLS (boolMatrix, boolMatrix, OCTAVE_API)
--- a/liboctave/boolNDArray.h
+++ b/liboctave/boolNDArray.h
@@ -96,8 +96,6 @@
   // friend std::ostream& operator << (std::ostream& os, const NDArray& a);
   // friend std::istream& operator >> (std::istream& is, NDArray& a);
 
-  static bool resize_fill_value (void) { return false; }
-
   //  bool all_elements_are_real (void) const;
   //  bool all_integers (double& max_val, double& min_val) const;
 
--- a/liboctave/chMatrix.h
+++ b/liboctave/chMatrix.h
@@ -86,8 +86,7 @@
 
   charMatrix extract (octave_idx_type r1, octave_idx_type c1, octave_idx_type r2, octave_idx_type c2) const;
 
-  void resize (octave_idx_type nr, octave_idx_type nc,
-               char rfv = resize_fill_value ())
+  void resize (octave_idx_type nr, octave_idx_type nc, char rfv = 0)
   {
     Array<char>::resize (dim_vector (nr, nc), rfv);
   }
@@ -103,9 +102,6 @@
   friend std::ostream& operator << (std::ostream& os, const Matrix& a);
   friend std::istream& operator >> (std::istream& is, Matrix& a);
 #endif
-
-  static char resize_fill_value (void) { return '\0'; }
-
 };
 
 MS_CMP_OP_DECLS (charMatrix, char, OCTAVE_API)
--- a/liboctave/chNDArray.h
+++ b/liboctave/chNDArray.h
@@ -92,8 +92,6 @@
   // friend std::ostream& operator << (std::ostream& os, const charNDArray& a);
   // friend std::istream& operator >> (std::istream& is, charNDArray& a);
 
-  static char resize_fill_value (void) { return '\0'; }
-
   charNDArray diag (octave_idx_type k = 0) const;
 
   charNDArray diag (octave_idx_type m, octave_idx_type n) const;
--- a/liboctave/dColVector.h
+++ b/liboctave/dColVector.h
@@ -99,8 +99,7 @@
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const ColumnVector& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, ColumnVector& a);
 
-  void resize (octave_idx_type n,
-               const double& rfv = Array<double>::resize_fill_value ())
+  void resize (octave_idx_type n, const double& rfv = 0)
   {
     Array<double>::resize (dim_vector (n, 1), rfv);
   }
--- a/liboctave/dMatrix.h
+++ b/liboctave/dMatrix.h
@@ -125,8 +125,7 @@
 
   ColumnVector column (octave_idx_type i) const;
 
-  void resize (octave_idx_type nr, octave_idx_type nc,
-               double rfv = resize_fill_value ())
+  void resize (octave_idx_type nr, octave_idx_type nc, double rfv = 0)
   {
     MArray<double>::resize (dim_vector (nr, nc), rfv);
   }
@@ -334,8 +333,6 @@
 
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const Matrix& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, Matrix& a);
-
-  static double resize_fill_value (void) { return 0; }
 };
 
 // Publish externally used friend functions.
--- a/liboctave/dNDArray.h
+++ b/liboctave/dNDArray.h
@@ -150,8 +150,6 @@
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const NDArray& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, NDArray& a);
 
-  static double resize_fill_value (void) { return 0; }
-
   NDArray diag (octave_idx_type k = 0) const;
 
   NDArray diag (octave_idx_type m, octave_idx_type n) const;
--- a/liboctave/dRowVector.h
+++ b/liboctave/dRowVector.h
@@ -92,8 +92,7 @@
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const RowVector& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, RowVector& a);
 
-  void resize (octave_idx_type n,
-               const double& rfv = Array<double>::resize_fill_value ())
+  void resize (octave_idx_type n, const double& rfv = 0)
   {
     Array<double>::resize (dim_vector (1, n), rfv);
   }
--- a/liboctave/dim-vector.cc
+++ b/liboctave/dim-vector.cc
@@ -272,16 +272,11 @@
     {
       dim_vector retval = alloc (n);
 
-      int pad = 0;
       for (int i = 0; i < n_dims; i++)
-        {
-          retval.rep[i] = rep[i];
-          if (rep[i] != 0)
-            pad = 1;
-        }
+        retval.rep[i] = rep[i];
 
       for (int i = n_dims; i < n; i++)
-        retval.rep[i] = pad;
+        retval.rep[i] = 1;
 
       return retval;
     }
--- a/liboctave/dim-vector.h
+++ b/liboctave/dim-vector.h
@@ -381,8 +381,7 @@
   // Force certain dimensionality, preserving numel ().  Missing
   // dimensions are set to 1, redundant are folded into the trailing
   // one.  If n = 1, the result is 2d and the second dim is 1
-  // (dim_vectors are always at least 2D).  If the original dimensions
-  // were all zero, the padding value is zero.
+  // (dim_vectors are always at least 2D).
 
   dim_vector redim (int n) const;
 
--- a/liboctave/fCColVector.h
+++ b/liboctave/fCColVector.h
@@ -134,8 +134,7 @@
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const FloatComplexColumnVector& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, FloatComplexColumnVector& a);
 
-  void resize (octave_idx_type n,
-               const FloatComplex& rfv = Array<FloatComplex>::resize_fill_value ())
+  void resize (octave_idx_type n, const FloatComplex& rfv = FloatComplex (0))
   {
     Array<FloatComplex>::resize (dim_vector (n, 1), rfv);
   }
--- a/liboctave/fCMatrix.h
+++ b/liboctave/fCMatrix.h
@@ -157,7 +157,7 @@
   FloatComplexColumnVector column (octave_idx_type i) const;
 
   void resize (octave_idx_type nr, octave_idx_type nc,
-               const FloatComplex& rfv = resize_fill_value ())
+               const FloatComplex& rfv = FloatComplex (0))
   {
     MArray<FloatComplex>::resize (dim_vector (nr, nc), rfv);
   }
@@ -383,9 +383,6 @@
 
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const FloatComplexMatrix& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, FloatComplexMatrix& a);
-
-  static FloatComplex resize_fill_value (void) { return FloatComplex (0.0, 0.0); }
-
 };
 
 extern OCTAVE_API FloatComplexMatrix conj (const FloatComplexMatrix& a);
--- a/liboctave/fCNDArray.h
+++ b/liboctave/fCNDArray.h
@@ -135,8 +135,6 @@
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const FloatComplexNDArray& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, FloatComplexNDArray& a);
 
-  static FloatComplex resize_fill_value (void) { return FloatComplex (0.0, 0.0); }
-
   //  bool all_elements_are_real (void) const;
   //  bool all_integers (float& max_val, float& min_val) const;
 
--- a/liboctave/fCRowVector.h
+++ b/liboctave/fCRowVector.h
@@ -116,8 +116,7 @@
   friend std::ostream& operator << (std::ostream& os, const FloatComplexRowVector& a);
   friend std::istream& operator >> (std::istream& is, FloatComplexRowVector& a);
 
-  void resize (octave_idx_type n,
-               const FloatComplex& rfv = Array<FloatComplex>::resize_fill_value ())
+  void resize (octave_idx_type n, const FloatComplex& rfv = FloatComplex (0))
   {
     Array<FloatComplex>::resize (dim_vector (1, n), rfv);
   }
--- a/liboctave/fColVector.h
+++ b/liboctave/fColVector.h
@@ -102,8 +102,7 @@
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const FloatColumnVector& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, FloatColumnVector& a);
 
-  void resize (octave_idx_type n,
-               const float& rfv = Array<float>::resize_fill_value ())
+  void resize (octave_idx_type n, const float& rfv = 0)
   {
     Array<float>::resize (dim_vector (n, 1), rfv);
   }
--- a/liboctave/fMatrix.h
+++ b/liboctave/fMatrix.h
@@ -126,8 +126,7 @@
 
   FloatColumnVector column (octave_idx_type i) const;
 
-  void resize (octave_idx_type nr, octave_idx_type nc,
-               float rfv = resize_fill_value ())
+  void resize (octave_idx_type nr, octave_idx_type nc, float rfv = 0)
   {
     MArray<float>::resize (dim_vector (nr, nc), rfv);
   }
@@ -334,9 +333,6 @@
 
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const FloatMatrix& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, FloatMatrix& a);
-
-  static float resize_fill_value (void) { return 0; }
-
 };
 
 // Publish externally used friend functions.
--- a/liboctave/fNDArray.h
+++ b/liboctave/fNDArray.h
@@ -147,8 +147,6 @@
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const FloatNDArray& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, FloatNDArray& a);
 
-  static float resize_fill_value (void) { return 0; }
-
   FloatNDArray diag (octave_idx_type k = 0) const;
 
   FloatNDArray diag (octave_idx_type m, octave_idx_type n) const;
--- a/liboctave/fRowVector.h
+++ b/liboctave/fRowVector.h
@@ -93,8 +93,7 @@
   friend OCTAVE_API std::ostream& operator << (std::ostream& os, const FloatRowVector& a);
   friend OCTAVE_API std::istream& operator >> (std::istream& is, FloatRowVector& a);
 
-  void resize (octave_idx_type n,
-               const float& rfv = Array<float>::resize_fill_value ())
+  void resize (octave_idx_type n, const float& rfv = 0)
   {
     Array<float>::resize (dim_vector (1, n), rfv);
   }
--- a/liboctave/intNDArray.h
+++ b/liboctave/intNDArray.h
@@ -115,9 +115,6 @@
 
   static octave_idx_type compute_index (Array<octave_idx_type>& ra_idx,
                             const dim_vector& dimensions);
-
-  static T resize_fill_value (void) { return 0; }
-
 };
 
 // i/o
--- a/liboctave/str-vec.h
+++ b/liboctave/str-vec.h
@@ -88,7 +88,7 @@
     return longest;
   }
 
-  void resize (octave_idx_type n, const std::string& rfv = resize_fill_value ())
+  void resize (octave_idx_type n, const std::string& rfv = std::string ())
   {
     Array<std::string>::resize (dim_vector (n, 1), rfv);
   }
--- a/run-octave.in
+++ b/run-octave.in
@@ -45,6 +45,7 @@
 LOADPATH="$d1_path:$d2_path:$d3_path"
 IMAGEPATH="$top_srcdir/scripts/image"
 DOCFILE="$builddir/doc/interpreter/doc-cache"
+TEXIMACROSFILE="$top_srcdir/doc/interpreter/macros.texi"
 INFOFILE="$top_srcdir/doc/interpreter/octave.info"
 
 ## Checking for string equality below with prepended x's in order to
@@ -70,4 +71,4 @@
   exec $builddir/libtool --mode=execute $driver \
     "$builddir/src/octave" --no-init-path --path="$LOADPATH" \
     --image-path="$IMAGEPATH" --doc-cache-file="$DOCFILE" \
-    --info-file="$INFOFILE" "$@"
+    --texi-macros-file="$TEXIMACROSFILE" --info-file="$INFOFILE" "$@"
--- a/scripts/Makefile.am
+++ b/scripts/Makefile.am
@@ -325,21 +325,17 @@
 	: > time/$(octave_dirstamp)
 
 if AMCOND_BUILD_DOCS
-## Program compiled only to help build documentation.  No installation needed.
-noinst_PROGRAMS = gethelp
 
-gethelp_SOURCES = gethelp.cc
-
-.DOCSTRINGS: $(FCN_FILES) $(GEN_FCN_FILES) mkdoc $(gethelp_SOURCES) Makefile
-	@$(MAKE) $(AM_MAKEFLAGS) gethelp$(BUILD_EXEEXT)
+.DOCSTRINGS: $(FCN_FILES) $(GEN_FCN_FILES) mkdoc.pl Makefile
 	if [ "x$(srcdir)" != "x." ] && [ -f $(srcdir)/DOCSTRINGS ] && [ ! -f DOCSTRINGS ]; then \
 		cp $(srcdir)/DOCSTRINGS DOCSTRINGS; \
 		touch -r $(srcdir)/DOCSTRINGS DOCSTRINGS; \
 	fi
 	@echo "creating .DOCSTRINGS from .m script files"
-	@$(srcdir)/mkdoc "$(srcdir)" $(FCN_FILES) -- $(GEN_FCN_FILES) > $@
+	@$(PERL) $(srcdir)/mkdoc.pl "$(srcdir)" $(FCN_FILES) -- $(GEN_FCN_FILES) > $@
 	$(top_srcdir)/build-aux/move-if-change $@ DOCSTRINGS
 	touch $@
+
 endif
 
 $(GEN_FCN_FILES) : %.m : %.in Makefile
@@ -427,7 +423,7 @@
   $(FCN_FILES_IN) \
   $(GEN_FCN_FILES) \
   DOCSTRINGS \
-  mkdoc \
+  mkdoc.pl \
   mk-pkg-add
 
 DISTCLEANFILES = \
--- a/scripts/general/bitset.m
+++ b/scripts/general/bitset.m
@@ -1,4 +1,5 @@
 ## Copyright (C) 2004-2012 David Bateman
+## Copyright (C) 2012 Jordi Gutiérrez Hermoso
 ##
 ## This file is part of Octave.
 ##
@@ -21,7 +22,8 @@
 ## @deftypefnx {Function File} {@var{C} =} bitset (@var{A}, @var{n}, @var{val})
 ## Set or reset bit(s) @var{n} of unsigned integers in @var{A}.
 ## @var{val} = 0 resets and @var{val} = 1 sets the bits.
-## The lowest significant bit is: @var{n} = 1
+## The lowest significant bit is: @var{n} = 1.  All variables must be the
+## same size or scalars.
 ##
 ## @example
 ## @group
@@ -32,65 +34,58 @@
 ## @seealso{bitand, bitor, bitxor, bitget, bitcmp, bitshift, bitmax}
 ## @end deftypefn
 
-## Liberally based on the version by Kai Habel from octave-forge
-
 function C = bitset (A, n, val)
 
   if (nargin < 2 || nargin > 3)
     print_usage ();
   endif
 
+  if (any (A(:) < 0))
+    error ("bitset: A must be >= 0");
+  endif
+
+  sz = size (A);
+
   if (nargin == 2)
-    val = 1;
+    val = true (sz);
   endif
 
-  if (isa (A, "double"))
-    Bmax = bitmax;
-    Amax = log2 (Bmax) + 1;
-    _conv = @double;
+  cl = class (A);
+
+  if (isfloat (A) && isreal (A))
+    Bmax = bitmax (cl);
+    Amax = log2 (Bmax);
+  elseif (isinteger (A))
+    Bmax = intmax (cl);
+    Amax = round (log2 (Bmax));
   else
-    if (isa (A, "uint8"))
-      Amax = 8;
-      _conv = @uint8;
-    elseif (isa (A, "uint16"))
-      Amax = 16;
-      _conv = @uint16;
-    elseif (isa (A, "uint32"))
-      Amax = 32;
-      _conv = @uint32;
-    elseif (isa (A, "uint64"))
-      Amax = 64;
-      _conv = @uint64;
-    elseif (isa (A, "int8"))
-      Amax = 8;
-      _conv = @int8;
-    elseif (isa (A, "int16"))
-      Amax = 16;
-      _conv = @int16;
-    elseif (isa (A, "int32"))
-      Amax = 32;
-      _conv = @int32;
-    elseif (isa (A, "int64"))
-      Amax = 64;
-      _conv = @int64;
-    else
-      error ("bitset: invalid class %s", class (A));
-    endif
-    Bmax = intmax (class (A));
+    error ("bitset: invalid class %s", cl);
   endif
 
-  m = double (n(:));
-  if (any (m < 1) || any (m > Amax))
+  if (any ((n < 1)(:)) || any ((n > Amax)(:)))
     error ("bitset: N must be in the range [1,%d]", Amax);
   endif
 
-  mask = bitshift (_conv (1), uint8 (n) - uint8 (1));
-  C = bitxor (A, bitand (A, mask));
+  mask = bitshift (cast (1, cl), uint8 (n) - uint8 (1));
+
+  on = logical (val);
+  off = !on;
 
-  if (val)
-    C = bitor (A, mask);
+  if (isscalar (mask))
+    onmask = mask;
+    offmask = mask;
+  else
+    if (! size_equal (A, n))
+      error ("bitset: N must be scalar or the same size as A");
+    endif
+    onmask = mask(on);
+    offmask = mask(off);
   endif
 
+  C = zeros (sz, cl);
+  C(on) = bitor (A(on), onmask);
+  C(off) = bitand (A(off), bitcmp (offmask));
+
 endfunction
 
 
@@ -104,17 +99,24 @@
 %!   endfor
 %! endfor
 
-%!error bitset (0, 0)
-%!error bitset (0, 55)
-%!error bitset (int8 (0), 9)
-%!error bitset (uint8 (0), 9)
-%!error bitset (int16 (0), 17)
-%!error bitset (uint16 (0), 17)
-%!error bitset (int32 (0), 33)
-%!error bitset (uint32 (0), 33)
-%!error bitset (int64 (0), 65)
-%!error bitset (uint64 (0), 65)
+## Bug #36458
+%!assert (bitset (uint8 ([1, 2;3 4]), 1, [0 1; 0 1]), uint8 ([0, 3; 2 5]))
 
 %!error bitset (1)
 %!error bitset (1, 2, 3, 4)
+%!error <A must be .= 0> bitset (-1, 2)
+%!error <invalid class char> bitset ("1", 2)
+%!error <N must be in the range \[1,53\]> bitset (0, 0)
+%!error <N must be in the range \[1,53\]> bitset (0, 55)
+%!error <N must be in the range \[1,8\]> bitset (uint8 (0), 0)
+%!error <N must be in the range \[1,8\]> bitset (uint8 (0), 9)
+%!error <N must be in the range \[1,7\]> bitset (int8 (0), 9)
+%!error <N must be in the range \[1,15\]> bitset (int16 (0), 17)
+%!error <N must be in the range \[1,16\]> bitset (uint16 (0), 17)
+%!error <N must be in the range \[1,31\]> bitset (int32 (0), 33)
+%!error <N must be in the range \[1,32\]> bitset (uint32 (0), 33)
+%!error <N must be in the range \[1,63\]> bitset (int64 (0), 65)
+%!error <N must be in the range \[1,64\]> bitset (uint64 (0), 65)
+%!error <N must be scalar or the same size as A> bitset (uint8 (1), [1 3])
+%!error <N must be scalar or the same size as A> bitset (uint8 (1:3), [1 3])
 
deleted file mode 100644
--- a/scripts/gethelp.cc
+++ /dev/null
@@ -1,160 +0,0 @@
-/*
-
-Copyright (C) 1999-2012 John W. Eaton
-
-This file is part of Octave.
-
-Octave is free software; you can redistribute it and/or modify it
-under the terms of the GNU General Public License as published by the
-Free Software Foundation; either version 3 of the License, or (at your
-option) any later version.
-
-Octave is distributed in the hope that it will be useful, but WITHOUT
-ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
-FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
-for more details.
-
-You should have received a copy of the GNU General Public License
-along with Octave; see the file COPYING.  If not, see
-<http://www.gnu.org/licenses/>.
-
-*/
-
-#include <cstdio>
-
-#include <iostream>
-#include <string>
-
-static bool
-looks_like_octave_copyright (const std::string& s)
-{
-  // Perhaps someday we will want to do more here, so leave this as a
-  // separate function.
-
-  return (s.substr (0, 9) == "Copyright" || s.substr (0, 6) == "Author");
-}
-
-// Eat whitespace and comments from FFILE, returning the text of the
-// first block of comments that doesn't look like a copyright notice,
-
-static std::string
-extract_help_text (void)
-{
-  std::string help_txt;
-
-  bool first_comments_seen = false;
-  bool begin_comment = false;
-  bool have_help_text = false;
-  bool in_comment = false;
-  bool discard_space = true;
-  int c;
-
-  while ((c = std::cin.get ()) != EOF)
-    {
-      if (begin_comment)
-        {
-          if (c == '%' || c == '#')
-            continue;
-          else if (discard_space && c == ' ')
-            {
-              discard_space = false;
-              continue;
-            }
-          else
-            begin_comment = false;
-        }
-
-      if (in_comment)
-        {
-          if (! have_help_text)
-            {
-              first_comments_seen = true;
-              help_txt += static_cast<char> (c);
-            }
-
-          if (c == '\n')
-            {
-              in_comment = false;
-              discard_space = true;
-
-              if ((c = std::cin.get ()) != EOF)
-                {
-                  if (c == '\n')
-                    break;
-                }
-              else
-                break;
-            }
-        }
-      else
-        {
-          switch (c)
-            {
-            case ' ':
-            case '\t':
-              if (first_comments_seen)
-                have_help_text = true;
-              break;
-
-            case '\n':
-              if (first_comments_seen)
-                have_help_text = true;
-              continue;
-
-            case '%':
-            case '#':
-              begin_comment = true;
-              in_comment = true;
-              break;
-
-            default:
-              goto done;
-            }
-        }
-    }
-
- done:
-
-  if (! help_txt.empty ())
-    {
-      if (looks_like_octave_copyright (help_txt))
-        help_txt.resize (0);
-
-      if (help_txt.empty ())
-        help_txt = extract_help_text ();
-    }
-
-  return help_txt;
-}
-
-int
-main (int argc, char **argv)
-{
-  std::string name;
-  std::string file_name;
-
-  if (argc != 3)
-    {
-      std::cerr << "usage: gethelp name file-name\n";
-      return 1;
-    }
-  else
-    {
-      name = argv[1];
-      file_name = argv[2];
-    }
-
-  std::string help_text = extract_help_text ();
-
-  if (! help_text.empty ())
-    {
-      std::cout << "" << name << "\n"
-                << "@c " << name << " " << file_name << "\n"
-                << help_text;
-
-      if (help_text[help_text.length () - 1] != '\n')
-        std::cout << "\n";
-    }
-
-  return 0;
-}
--- a/scripts/help/__makeinfo__.m
+++ b/scripts/help/__makeinfo__.m
@@ -94,18 +94,15 @@
   ## Texinfo crashes if @end tex does not appear first on the line.
   text = regexprep (text, '^ +@end tex', '@end tex', 'lineanchors');
 
-  ## Handle @seealso macro
-  see_also_pat = '@seealso *\{(.*)\}';
-  args = regexp (text, see_also_pat, 'tokens');
-  for ii = 1:numel (args)
-    expanded = fsee_also (strtrim (strsplit (args{ii}{:}, ',', true)));
-    text = regexprep (text, see_also_pat, expanded, 'once');
-  endfor
-
-  ## Handle @nospell macro
-  text = regexprep (text, '@nospell *\{([^}]*)\}', "$1");
-  ## Handle @xcode macro
-  text = regexprep (text, '@xcode *\{([^}]*)\}', "$1");
+  file = texi_macros_file ();
+  fid = fopen (file, "r");
+  if (fid < 0)
+    error ("unable to open %s for reading", file);
+  else
+    macros_text = fread (fid, Inf, "*char")';
+    text = cstrcat (macros_text, text);
+  endif
+  fclose (fid);
 
   if (strcmpi (output_type, "texinfo"))
     status = 0;
--- a/scripts/help/doc.m
+++ b/scripts/help/doc.m
@@ -86,7 +86,7 @@
     have_fname = ! isempty (fname);
 
     if (have_fname)
-      status = system (sprintf ("%s --index-search %s", cmd, fname));
+      status = system (sprintf ("%s --index-search \"%s\"", cmd, fname));
     endif
 
     if (! (have_fname && status == 0))
--- a/scripts/image/autumn.m
+++ b/scripts/image/autumn.m
@@ -28,6 +28,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "autumn");
+## PKG_DEL: colormap ("unregister", "autumn");
+
 function map = autumn (n)
 
   if (nargin == 0)
@@ -48,7 +51,7 @@
     b = zeros (n, 1);
     map = [r, g, b];
   else
-    map = [];
+    map = zeros (0, 3);
   endif
 
 endfunction
--- a/scripts/image/bone.m
+++ b/scripts/image/bone.m
@@ -28,6 +28,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "bone");
+## PKG_DEL: colormap ("unregister", "bone");
+
 function map = bone (n)
 
   if (nargin == 0)
@@ -41,7 +44,7 @@
   endif
 
   if (n == 1)
-    map = [0, 0, 0];
+    map = [0.125, 0.125, 0.125];
   elseif (n > 1)
     x = linspace (0, 1, n)';
     r = (x < 3/4) .* (7/8 * x) ...
@@ -53,7 +56,7 @@
       + (x >= 3/8) .* (7/8 * x + 1/8);
     map = [r, g, b];
   else
-    map = [];
+    map = zeros (0, 3);
   endif
 
 endfunction
--- a/scripts/image/colormap.m
+++ b/scripts/image/colormap.m
@@ -1,4 +1,5 @@
 ## Copyright (C) 1994-2012 John W. Eaton
+## Copyright (C) 2012 Carnë Draug
 ##
 ## This file is part of Octave.
 ##
@@ -20,6 +21,9 @@
 ## @deftypefn  {Function File} {@var{cmap} =} colormap ()
 ## @deftypefnx {Function File} {@var{cmap} =} colormap (@var{map})
 ## @deftypefnx {Function File} {@var{cmap} =} colormap ("default")
+## @deftypefnx {Function File} {@var{cmap} =} colormap ("list")
+## @deftypefnx {Function File} {@var{cmap} =} colormap ("register", "name")
+## @deftypefnx {Function File} {@var{cmap} =} colormap ("unregister", "name")
 ## Query or set the current colormap.
 ##
 ## @code{colormap (@var{map})} sets the current colormap to @var{map}.  The
@@ -30,6 +34,10 @@
 ## @code{colormap ("default")} restores the default colormap (the
 ## @code{jet} map with 64 entries).  The default colormap is returned.
 ##
+## @code{colormap ("list")} returns a cell array with all the available
+## colormaps.  The options `register' and `unregister' will add or remove the
+## colormap @var{name} to it.
+##
 ## With no arguments, @code{colormap} returns the current color map.
 ## @seealso{jet}
 ## @end deftypefn
@@ -38,17 +46,22 @@
 ## Created: July 1994
 ## Adapted-By: jwe
 
-function cmap = colormap (map)
+function cmap = colormap (map, name)
 
-  if (nargin > 1)
+  if (nargin > 2)
     print_usage ();
   endif
 
+  persistent map_list = cell ();
+
   if (nargin == 1)
 
     if (ischar (map))
       if (strcmp (map, "default"))
         map = jet (64);
+      elseif (strcmp (map, "list"))
+        cmap = map_list;
+        return;
       else
         map = feval (map);
       endif
@@ -65,6 +78,16 @@
       set (gcf (), "colormap", map);
     endif
 
+  elseif (nargin == 2)
+    if (! ischar (map) || all (! strcmp (map, {"register", "unregister"})))
+      print_usage ();
+    elseif (! ischar (name))
+      error ("colormap: to register/unregister a colormap, NAME must be a string");
+    elseif (strcmp (map, "register"))
+      map_list{end+1} = name;
+    elseif (strcmp (map, "unregister"))
+      map_list(strcmp (name, map_list)) = [];
+    endif
   endif
 
   ## Return current color map.
--- a/scripts/image/cool.m
+++ b/scripts/image/cool.m
@@ -27,6 +27,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "cool");
+## PKG_DEL: colormap ("unregister", "cool");
+
 function map = cool (n)
 
   if (nargin == 0)
@@ -47,7 +50,7 @@
     b = ones (n, 1);
     map = [r, g, b];
   else
-    map = [];
+    map = zeros (0, 3);
   endif
 
 endfunction
--- a/scripts/image/copper.m
+++ b/scripts/image/copper.m
@@ -28,6 +28,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "copper");
+## PKG_DEL: colormap ("unregister", "copper");
+
 function map = copper (n)
 
   if (nargin == 0)
@@ -50,7 +53,7 @@
     b = 1/2 * x;
     map = [r, g, b];
   else
-    map = [];
+    map = zeros (0, 3);
   endif
 
 endfunction
--- a/scripts/image/flag.m
+++ b/scripts/image/flag.m
@@ -28,6 +28,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "flag");
+## PKG_DEL: colormap ("unregister", "flag");
+
 function map = flag (n)
 
   if (nargin == 0)
@@ -40,8 +43,14 @@
     print_usage ();
   endif
 
-  C = [1, 0, 0; 1, 1, 1; 0, 0, 1; 0, 0, 0];
-  map = C(rem (0:(n-1), 4) + 1, :);
+  if (n == 1)
+    map = [1, 0, 0];
+  elseif (n > 1)
+    C = [1, 0, 0; 1, 1, 1; 0, 0, 1; 0, 0, 0];
+    map = C(rem (0:(n-1), 4) + 1, :);
+  else
+    map = zeros (0, 3);
+  endif
 
 endfunction
 
--- a/scripts/image/gmap40.m
+++ b/scripts/image/gmap40.m
@@ -28,6 +28,9 @@
 ## @seealso{colormap}
 ## @end deftypefn
 
+## PKG_ADD: colormap ("register", "gmap40");
+## PKG_DEL: colormap ("unregister", "gmap40");
+
 function map = gmap40 (n)
 
   if (nargin == 0)
@@ -40,8 +43,12 @@
     print_usage ();
   endif
 
-  C = [1, 0, 0; 0, 1, 0; 0, 0, 1; 1, 1, 0; 1, 0, 1; 0, 1, 1];
-  map = C(rem (0:(n-1), 6) + 1, :);
+  if (n > 1)
+    C = [1, 0, 0; 0, 1, 0; 0, 0, 1; 1, 1, 0; 1, 0, 1; 0, 1, 1];
+    map = C(rem (0:(n-1), 6) + 1, :);
+  else
+    map = zeros (0, 3);
+  endif
 
 endfunction
 
--- a/scripts/image/gray.m
+++ b/scripts/image/gray.m
@@ -30,6 +30,9 @@
 ## Created: July 1994
 ## Adapted-By: jwe
 
+## PKG_ADD: colormap ("register", "gray");
+## PKG_DEL: colormap ("unregister", "gray");
+
 function map = gray (n)
 
   if (nargin == 0)
@@ -42,9 +45,14 @@
     print_usage ();
   endif
 
-  gr = [0:(n-1)]' / (n - 1);
-
-  map = [gr, gr, gr];
+  if (n == 1)
+    map = [0, 0, 0];
+  elseif (n > 1)
+    gr = [0:(n-1)]' / (n - 1);
+    map = [gr, gr, gr];
+  else
+    map = zeros (0, 3);
+  endif
 
 endfunction
 
--- a/scripts/image/hot.m
+++ b/scripts/image/hot.m
@@ -28,6 +28,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "hot");
+## PKG_DEL: colormap ("unregister", "hot");
+
 function map = hot (n)
 
   if (nargin == 0)
@@ -41,7 +44,7 @@
   endif
 
   if (n == 1)
-    map = [0, 0, 0];
+    map = [1, 1, 1];
   elseif (n > 1)
     x = linspace (0, 1, n)';
     r = (x < 2/5) .* (5/2 * x) ...
@@ -51,7 +54,7 @@
     b = (x >= 4/5) .* (5 * x - 4);
     map = [r, g, b];
   else
-    map = [];
+    map = zeros (0, 3);
   endif
 
 endfunction
--- a/scripts/image/hsv.m
+++ b/scripts/image/hsv.m
@@ -32,6 +32,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "hsv");
+## PKG_DEL: colormap ("unregister", "hsv");
+
 function map = hsv (n)
 
   if (nargin == 0)
@@ -50,7 +53,7 @@
     hue = linspace (0, 1, n)';
     map = hsv2rgb ([hue, ones(n,1), ones(n,1)]);
   else
-    map = [];
+    map = zeros (0, 3);
   endif
 
 endfunction
--- a/scripts/image/jet.m
+++ b/scripts/image/jet.m
@@ -28,6 +28,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "jet");
+## PKG_DEL: colormap ("unregister", "jet");
+
 function map = jet (n)
 
   if (nargin == 0)
@@ -41,7 +44,7 @@
   endif
 
   if (n == 1)
-    map = [0, 0, 0.5];
+    map = [0, 1, 1];
   elseif (n > 1)
     x = linspace (0, 1, n)';
     r = (x >= 3/8 & x < 5/8) .* (4 * x - 3/2) ...
@@ -55,7 +58,7 @@
       + (x >= 3/8 & x < 5/8) .* (-4 * x + 5/2);
     map = [r, g, b];
   else
-    map = [];
+    map = zeros (0, 3);
   endif
 
 endfunction
--- a/scripts/image/lines.m
+++ b/scripts/image/lines.m
@@ -27,6 +27,9 @@
 ## @seealso{colormap}
 ## @end deftypefn
 
+## PKG_ADD: colormap ("register", "lines");
+## PKG_DEL: colormap ("unregister", "lines");
+
 function map = lines (n)
 
   if (nargin == 0)
@@ -39,9 +42,15 @@
     print_usage ();
   endif
 
-  C = get (gca, "colororder");
-  nr = rows (C);
-  map = C(rem (0:(n-1), nr) + 1, :);
+  if (n == 1)
+    map = [0, 0, 1];
+  elseif (n > 1)
+    C = get (gca, "colororder");
+    nr = rows (C);
+    map = C(rem (0:(n-1), nr) + 1, :);
+  else
+    map = zeros (0, 3);
+  endif
 
 endfunction
 
--- a/scripts/image/ocean.m
+++ b/scripts/image/ocean.m
@@ -30,6 +30,9 @@
 ## Created: July 1994
 ## Adapted-By: jwe
 
+## PKG_ADD: colormap ("register", "ocean");
+## PKG_DEL: colormap ("unregister", "ocean");
+
 function map = ocean (n)
 
   if (nargin == 0)
@@ -42,17 +45,23 @@
     print_usage ();
   endif
 
-  cutin = fix (n/3);
+  if (n == 1)
+    map = [0, 0, 0];
+  elseif (n > 1)
+    cutin = fix (n/3);
 
-  dr = (n - 1) / cutin;
-  r = prepad ([0:dr:(n-1)], n)';
+    dr = (n - 1) / cutin;
+    r = prepad ([0:dr:(n-1)], n)';
 
-  dg = (n - 1) / (2 * cutin);
-  g = prepad ([0:dg:(n-1)], n)';
+    dg = (n - 1) / (2 * cutin);
+    g = prepad ([0:dg:(n-1)], n)';
+
+    b = [0:(n-1)]';
 
-  b = [0:(n-1)]';
-
-  map = [r, g, b] / (n - 1);
+    map = [r, g, b] / (n - 1);
+  else
+    map = zeros (0, 3);
+  endif
 
 endfunction
 
--- a/scripts/image/pink.m
+++ b/scripts/image/pink.m
@@ -28,6 +28,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "pink");
+## PKG_DEL: colormap ("unregister", "pink");
+
 function map = pink (n)
 
   if (nargin == 0)
@@ -41,7 +44,7 @@
   endif
 
   if (n == 1)
-    map = [0, 0, 0];
+    map = sqrt([1/3, 1/3, 1/3]);
   elseif (n > 1)
     x = linspace (0, 1, n)';
     r = (x < 3/8) .* (14/9 * x) ...
@@ -53,7 +56,7 @@
       + (x >= 3/4) .* (2 * x - 1);
     map = sqrt ([r, g, b]);
   else
-    map = [];
+    map = zeros (0, 3);
   endif
 
 endfunction
--- a/scripts/image/prism.m
+++ b/scripts/image/prism.m
@@ -28,6 +28,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "prism");
+## PKG_DEL: colormap ("unregister", "prism");
+
 function map = prism (n)
 
   if (nargin == 0)
@@ -40,8 +43,14 @@
     print_usage ();
   endif
 
-  C = [1, 0, 0; 1, 1/2, 0; 1, 1, 0; 0, 1, 0; 0, 0, 1; 2/3, 0, 1];
-  map = C(rem (0:(n-1), 6) + 1, :);
+  if (n == 1)
+    map = [1 0 0];
+  elseif (n > 1)
+    C = [1, 0, 0; 1, 1/2, 0; 1, 1, 0; 0, 1, 0; 0, 0, 1; 2/3, 0, 1];
+    map = C(rem (0:(n-1), 6) + 1, :);
+  else
+    map = zeros (0, 3);
+  endif
 
 endfunction
 
--- a/scripts/image/rainbow.m
+++ b/scripts/image/rainbow.m
@@ -31,6 +31,9 @@
 ## this colormap is not part of matlab, it is like the prism
 ## colormap map but with a continuous map
 
+## PKG_ADD: colormap ("register", "rainbow");
+## PKG_DEL: colormap ("unregister", "rainbow");
+
 function map = rainbow (n)
 
   if (nargin == 0)
@@ -60,7 +63,7 @@
 
     map = [r, g, b];
   else
-    map = [];
+    map = zeros (0, 3);
   endif
 
 endfunction
--- a/scripts/image/spring.m
+++ b/scripts/image/spring.m
@@ -27,6 +27,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "spring");
+## PKG_DEL: colormap ("unregister", "spring");
+
 function map = spring (n)
 
   if (nargin == 0)
@@ -47,7 +50,7 @@
     b = 1 - g;
     map = [r, g, b];
   else
-    map = [];
+    map = zeros (0, 3);
   endif
 
 endfunction
--- a/scripts/image/summer.m
+++ b/scripts/image/summer.m
@@ -28,6 +28,9 @@
 ## Author:  Kai Habel <kai.habel@gmx.de>
 ## Date:  06/03/2000
 
+## PKG_ADD: colormap ("register", "summer");
+## PKG_DEL: colormap ("unregister", "summer");
+
 function map = summer (n)
 
   if (nargin == 0)
@@ -48,7 +51,7 @@
     b = 0.4 * ones (n, 1);
     map = [r, g, b];
   else
-    map = [];
+    map = zeros (0, 3);
   endif
 
 endfunction
--- a/scripts/image/white.m
+++ b/scripts/image/white.m
@@ -27,6 +27,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "white");
+## PKG_DEL: colormap ("unregister", "white");
+
 function map = white (n)
 
   if (nargin == 0)
--- a/scripts/image/winter.m
+++ b/scripts/image/winter.m
@@ -27,6 +27,9 @@
 
 ## Author:  Kai Habel <kai.habel@gmx.de>
 
+## PKG_ADD: colormap ("register", "winter");
+## PKG_DEL: colormap ("unregister", "winter");
+
 function map = winter (n)
 
   if (nargin == 0)
@@ -47,7 +50,7 @@
     b = 1 - g / 2;
     map = [r, g, b];
   else
-    map = [];
+    map = zeros (0, 3);
   endif
 
 endfunction
--- a/scripts/io/textread.m
+++ b/scripts/io/textread.m
@@ -41,7 +41,7 @@
 ## delimiters.
 ## @end itemize
 ##
-## The optional input @var{n} specifes the number of data lines to read; in
+## The optional input @var{n} specifies the number of data lines to read; in
 ## this sense it differs slightly from the format repeat count in strread.
 ##
 ## @seealso{strread, load, dlmread, fscanf, textscan}
--- a/scripts/io/textscan.m
+++ b/scripts/io/textscan.m
@@ -53,9 +53,9 @@
 ## @end itemize
 ##
 ## When reading from a character string, optional input argument @var{n}
-## specifes the number of times @var{format} should be used (i.e., to limit
+## specifies the number of times @var{format} should be used (i.e., to limit
 ## the amount of data read).
-## When reading fro file, @var{n} specifes the number of data lines to read;
+## When reading fro file, @var{n} specifies the number of data lines to read;
 ## in this sense it differs slightly from the format repeat count in strread.
 ##
 ## The output @var{C} is a cell array whose length is given by the number
new file mode 100755
--- /dev/null
+++ b/scripts/mkdoc.pl
@@ -0,0 +1,104 @@
+#! /usr/bin/perl -w
+#
+# Copyright (C) 2012 Rik Wehbring
+#
+# This file is part of Octave.
+#
+# Octave is free software; you can redistribute it and/or modify it
+# under the terms of the GNU General Public License as published by the
+# Free Software Foundation; either version 3 of the License, or (at
+# your option) any later version.
+#
+# Octave is distributed in the hope that it will be useful, but WITHOUT
+# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+# FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+# for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with Octave; see the file COPYING.  If not, see
+# <http://www.gnu.org/licenses/>.
+
+## Expecting arguments in this order:
+##
+##  SRCDIR SRCDIR-FILES ... -- LOCAL-FILES ...
+
+unless (@ARGV >= 2) { die "Usage: $0 srcdir m_filename1 ..." ; }
+
+$srcdir = shift (@ARGV) . '/';
+
+print <<__END_OF_MSG__;
+### DO NOT EDIT!
+###
+### This file is generated automatically from Octave source files.
+### Edit source files directly and run make to update this file.
+
+__END_OF_MSG__
+
+MFILE: foreach $m_fname (@ARGV)
+{
+  if ($m_fname eq "--")
+  {
+    $srcdir = "./";
+    next MFILE;
+  }
+
+  $full_fname = $srcdir . $m_fname;
+  next MFILE unless ( $full_fname =~ m{(.*)/(@|)([^/]*)/(.*)\.m} );
+  if ($2) {
+    $fcn = "$2$3/$4";
+  } else {
+    $fcn = $4;
+  }
+
+  @help_txt = gethelp ($fcn, $full_fname);
+  next MFILE if ($help_txt[0] eq "");
+
+  print "$fcn\n";
+  print "\@c $fcn scripts/$m_fname\n";
+
+  foreach $_ (@help_txt)
+  {
+    s/^\s+\@/\@/ unless $in_example;
+    s/^\s+\@group/\@group/;
+    s/^\s+\@end\s+group/\@end group/;
+    $in_example = (/\s*\@example\b/ .. /\s*\@end\s+example\b/);
+    print $_;
+  }
+}
+
+################################################################################
+# Subroutines
+################################################################################
+sub gethelp
+{
+  ($fcn, $fname) = @_[0..1]; 
+  open (FH, $fname) or return "";
+
+  do
+  {
+    @help_txt = ();
+
+    ## Advance to non-blank line
+    while (defined ($_ = <FH>) and /^\s*$/) {;}
+
+    if (! /^\s*(?:#|%)/ or eof (FH))
+    {
+      ## No comment block found.  Return empty string
+      close (FH);
+      return "";
+    }
+
+    ## Extract help text stopping when comment block ends
+    do
+    {
+      ## Remove comment characters at start of line
+      s/^\s*(?:#|%){1,2} ?//;
+      push (@help_txt, $_);
+    } until (! defined ($_ = <FH>) or ! /^\s*(?:#|%)/);
+
+  } until ($help_txt[0] !~ /^(?:Copyright|Author)/); 
+
+  close (FH);
+
+  return @help_txt;
+}
--- a/scripts/pkg/private/get_unsatisfied_deps.m
+++ b/scripts/pkg/private/get_unsatisfied_deps.m
@@ -18,7 +18,7 @@
 ## <http://www.gnu.org/licenses/>.
 
 ## -*- texinfo -*-
-## @deftypefn {Function File} {@var{bad_deps} =} get_unsatisfied_deps (@var{desc},@var{installed_pkgs_lst})
+## @deftypefn {Function File} {@var{bad_deps} =} get_unsatisfied_deps (@var{desc}, @var{installed_pkgs_lst})
 ## Undocumented internal function.
 ## @end deftypefn
 
--- a/scripts/pkg/private/installed_packages.m
+++ b/scripts/pkg/private/installed_packages.m
@@ -40,11 +40,11 @@
   ## Locally installed packages take precedence.
   dup = [];
   for i = 1:length (installed_pkgs_lst)
-    if (find (dup, i))
+    if (any (dup == i))
       continue;
     endif
     for j = (i+1):length (installed_pkgs_lst)
-      if (find (dup, j))
+      if (any (dup == j))
         continue;
       endif
       if (strcmp (installed_pkgs_lst{i}.name, installed_pkgs_lst{j}.name))
--- a/scripts/pkg/private/rebuild.m
+++ b/scripts/pkg/private/rebuild.m
@@ -81,11 +81,11 @@
 
     dup = [];
     for i = 1:length (descriptions)
-      if (find (dup, i))
+      if (any (dup == i))
         continue;
       endif
       for j = (i+1):length (descriptions)
-        if (find (dup, j))
+        if (any (dup == j))
           continue;
         endif
         if (strcmp (descriptions{i}.name, descriptions{j}.name))
--- a/scripts/plot/hist.m
+++ b/scripts/plot/hist.m
@@ -149,7 +149,7 @@
   if (nargin > 2 && ! ischar (varargin{iarg}))
     ## Normalise the histogram.
     norm = varargin{iarg++};
-    freq = freq / rows (y) * norm;
+    freq = freq / sum(! isnan (y)) * norm;
   endif
 
   if (nargout > 0)
@@ -182,6 +182,10 @@
 %! assert (xx, [1,2,3]);
 %! assert (nn, [3,2,1]);
 %!test
+%! [nn,xx] = hist ([1 1 1 NaN NaN NaN 2 2 3],[1 2 3], 6);
+%! assert (xx, [1,2,3]);
+%! assert (nn, [3,2,1]);
+%!test
 %! [nn,xx] = hist ([[1:4]', [1:4]'], 3);
 %! assert (xx, [1.5;2.5;3.5]);
 %! assert (nn, [[2,1,1]',[2,1,1]']);
--- a/scripts/plot/print.m
+++ b/scripts/plot/print.m
@@ -21,7 +21,7 @@
 ## @deftypefnx {Function File} {} print (@var{options})
 ## @deftypefnx {Function File} {} print (@var{filename}, @var{options})
 ## @deftypefnx {Function File} {} print (@var{h}, @var{filename}, @var{options})
-## Print a graph, or save it to a file. Both output formatted for 
+## Print a graph, or save it to a file.  Both output formatted for 
 ## printing (PDF and PostScript), and many bitmapped and vector
 ## image formats are supported.
 ##
@@ -35,8 +35,8 @@
 ##
 ## For output to a printer, to a PostScript file, or a PDF file,
 ## the paper size is specified by the figure's @code{papersize}
-## property. The location and size of the image on the page are
-## specified by the figure's @code{paperposition} property. The
+## property.  The location and size of the image on the page are
+## specified by the figure's @code{paperposition} property.  The
 ## orientation of the page is specified by the figure's
 ## @code{paperorientation} property.
 ##
--- a/scripts/plot/shrinkfaces.m
+++ b/scripts/plot/shrinkfaces.m
@@ -17,7 +17,7 @@
 ## <http://www.gnu.org/licenses/>.
 
 ## -*- texinfo -*-
-## @deftypefn {Function File} {} shrinkfaces (@var{p}, @var{sf})
+## @deftypefn  {Function File} {} shrinkfaces (@var{p}, @var{sf})
 ## @deftypefnx {Function File} {@var{nfv} =} shrinkfaces (@var{p}, @var{sf})
 ## @deftypefnx {Function File} {@var{nfv} =} shrinkfaces (@var{fv}, @var{sf})
 ## @deftypefnx {Function File} {@var{nfv} =} shrinkfaces (@var{f}, @var{v}, @var{sf})
@@ -40,7 +40,7 @@
 ## Performing the shrinking on faces which are not convex can lead to
 ## undesired results.
 ##
-## For example
+## For example,
 ##
 ## @example
 ## @group
@@ -57,7 +57,7 @@
 ## @end example
 ##
 ## @noindent
-## draws a triangulated 3/4 circle and the corresponding shrinked
+## draws a triangulated 3/4 circle and the corresponding shrunken
 ## version.
 ## @seealso{patch}
 ## @end deftypefn
--- a/scripts/plot/tetramesh.m
+++ b/scripts/plot/tetramesh.m
@@ -17,9 +17,9 @@
 ## <http://www.gnu.org/licenses/>.
 
 ## -*- texinfo -*-
-## @deftypefn  {Function File} tetramesh (@var{T}, @var{X})
-## @deftypefnx {Function File} tetramesh (@var{T}, @var{X}, @var{C})
-## @deftypefnx {Function File} tetramesh (@dots{}, @var{property}, @var{val}, @dots{})
+## @deftypefn  {Function File} {} tetramesh (@var{T}, @var{X})
+## @deftypefnx {Function File} {} tetramesh (@var{T}, @var{X}, @var{C})
+## @deftypefnx {Function File} {} tetramesh (@dots{}, @var{property}, @var{val}, @dots{})
 ## @deftypefnx {Function File} {@var{h} =} tetramesh (@dots{})
 ##
 ## Display the tetrahedrons defined in the m-by-4 matrix @var{T}
--- a/scripts/polynomial/polyfit.m
+++ b/scripts/polynomial/polyfit.m
@@ -22,7 +22,7 @@
 ## @deftypefnx {Function File} {[@var{p}, @var{s}, @var{mu}] =} polyfit (@var{x}, @var{y}, @var{n})
 ## Return the coefficients of a polynomial @var{p}(@var{x}) of degree
 ## @var{n} that minimizes the least-squares-error of the fit to the points
-## @code{[@var{x}, @var{y}]}. If @var{n} is a logical vector, it is used
+## @code{[@var{x}, @var{y}]}.  If @var{n} is a logical vector, it is used
 ## as a mask to selectively force the corresponding polynomial
 ## coefficients to be used or ignored.
 ##
@@ -53,7 +53,7 @@
 ## @end table
 ##
 ## The second output may be used by @code{polyval} to calculate the
-## statistical error limits of the predicted values. In particular, the
+## statistical error limits of the predicted values.  In particular, the
 ## standard deviation of @var{p} coefficients is given by @*
 ## @code{sqrt (diag (s.C)/s.df)*s.normr}.
 ##
--- a/scripts/polynomial/splinefit.m
+++ b/scripts/polynomial/splinefit.m
@@ -17,18 +17,18 @@
 ## <http://www.gnu.org/licenses/>.
 
 ## -*- texinfo -*-
-## @deftypefn  {Function File} {@var{pp} =} splinefit (@var{x}, @var{y}, @var{breaks})
-## Fits a piecewise cubic spline with breaks (knots) @var{breaks} to the
+## @deftypefn {Function File} {@var{pp} =} splinefit (@var{x}, @var{y}, @var{breaks})
+## Fit a piecewise cubic spline with breaks (knots) @var{breaks} to the
 ## noisy data, @var{x} and @var{y}.  @var{x} is a vector, and @var{y}
-## a vector or ND array.  If @var{y} is an ND array, then @var{x}(j)
-## is matched to @var{y}(:,...,:,j).
+## a vector or N-D array.  If @var{y} is an N-D array, then @var{x}(j)
+## is matched to @var{y}(:,@dots{},:,j).
 ##
-## The fitted spline is returned as a piece-wise polynomial, @var{pp}, and
+## The fitted spline is returned as a piecewise polynomial, @var{pp}, and
 ## may be evaluated using @code{ppval}.
 ##
 ## @deftypefnx {Function File} {@var{pp} =} splinefit (@var{x}, @var{y}, @var{p})
 ## @var{p} is a positive integer defining the number of intervals along @var{x},
-## and @var{p}+1 is the number of breaks. The number of points in each interval
+## and @var{p}+1 is the number of breaks.  The number of points in each interval
 ## differ by no more than 1.
 ##
 ## @deftypefnx {Function File} {@var{pp} =} splinefit (@dots{}, "periodic", @var{periodic})
@@ -39,7 +39,7 @@
 ##
 ## The optional property @var{periodic} is a logical value which specifies
 ## whether a periodic boundary condition is applied to the spline.  The
-## length of the period  is @code{max(@var{breaks})-min(@var{breaks})}.
+## length of the period is @code{max(@var{breaks})-min(@var{breaks})}.
 ## The default value is @code{false}.
 ##
 ## The optional property @var{robust} is a logical value which specifies
@@ -65,12 +65,14 @@
 ## @table @asis
 ## @item "xc"
 ## Vector of the x-locations of the constraints.
+##
 ## @item "yc"
-## Constaining values at the locations, @var{xc}.
+## Constraining values at the locations, @var{xc}.
 ## The default is an array of zeros.
+##
 ## @item "cc"
 ## Coefficients (matrix).  The default is an array of ones.  The number of
-## rows is limited to the order of the piece-wise polynomials, @var{order}.
+## rows is limited to the order of the piecewise polynomials, @var{order}.
 ## @end table
 ##
 ## Constraints are linear combinations of derivatives of order 0 to
--- a/scripts/sparse/bicg.m
+++ b/scripts/sparse/bicg.m
@@ -15,7 +15,6 @@
 ## along with this program; If not, see <http://www.gnu.org/licenses/>.
 
 ## -*- texinfo -*-
-##
 ## @deftypefn  {Function File} {@var{x} =} bicg (@var{A}, @var{b}, @var{rtol}, @var{maxit}, @var{M1}, @var{M2}, @var{x0})
 ## @deftypefnx {Function File} {@var{x} =} bicg (@var{A}, @var{b}, @var{rtol}, @var{maxit}, @var{P})
 ## @deftypefnx {Function File} {[@var{x}, @var{flag}, @var{relres}, @var{iter}, @var{resvec}] =} bicg (@var{A}, @var{b}, @dots{})
--- a/scripts/sparse/bicgstab.m
+++ b/scripts/sparse/bicgstab.m
@@ -18,7 +18,6 @@
 ## <http://www.gnu.org/licenses/>.
 
 ## -*- texinfo -*-
-##
 ## @deftypefn  {Function File} {@var{x} =} bicgstab (@var{A}, @var{b}, @var{rtol}, @var{maxit}, @var{M1}, @var{M2}, @var{x0})
 ## @deftypefnx {Function File} {@var{x} =} bicgstab (@var{A}, @var{b}, @var{rtol}, @var{maxit}, @var{P})
 ## @deftypefnx {Function File} {[@var{x}, @var{flag}, @var{relres}, @var{iter}, @var{resvec}] =} bicgstab (@var{A}, @var{b}, @dots{})
--- a/scripts/sparse/cgs.m
+++ b/scripts/sparse/cgs.m
@@ -18,7 +18,6 @@
 ## <http://www.gnu.org/licenses/>.
 
 ## -*- texinfo -*-
-##
 ## @deftypefn  {Function File} {@var{x} =} cgs (@var{A}, @var{b}, @var{rtol}, @var{maxit}, @var{M1}, @var{M2}, @var{x0})
 ## @deftypefnx {Function File} {@var{x} =} cgs (@var{A}, @var{b}, @var{rtol}, @var{maxit}, @var{P})
 ## @deftypefnx {Function File} {[@var{x}, @var{flag}, @var{relres}, @var{iter}, @var{resvec}] =} cgs (@var{A}, @var{b}, @dots{})
--- a/src/Cell.cc
+++ b/src/Cell.cc
@@ -97,7 +97,7 @@
 // SV as possible.
 
 Cell::Cell (const dim_vector& dv, const string_vector& sv, bool trim)
-  : Array<octave_value> (dv, resize_fill_value ())
+  : Array<octave_value> (dv, Matrix ())
 {
   octave_idx_type n = sv.length ();
 
@@ -173,8 +173,7 @@
         idx_vector i = idx_arg(0).index_vector ();
 
         if (! error_state)
-          retval = Array<octave_value>::index (i, resize_ok,
-                                               resize_fill_value ());
+          retval = Array<octave_value>::index (i, resize_ok, Matrix ());
       }
       break;
 
@@ -187,8 +186,7 @@
             idx_vector j = idx_arg(1).index_vector ();
 
             if (! error_state)
-              retval = Array<octave_value>::index (i, j, resize_ok,
-                                                    resize_fill_value ());
+              retval = Array<octave_value>::index (i, j, resize_ok, Matrix ());
           }
       }
       break;
@@ -206,8 +204,7 @@
           }
 
         if (!error_state)
-          retval = Array<octave_value>::index (iv, resize_ok,
-                                                resize_fill_value ());
+          retval = Array<octave_value>::index (iv, resize_ok, Matrix ());
       }
       break;
     }
--- a/src/Cell.h
+++ b/src/Cell.h
@@ -48,10 +48,10 @@
   Cell (const octave_value_list& ovl);
 
   Cell (octave_idx_type n, octave_idx_type m,
-        const octave_value& val = resize_fill_value ())
+        const octave_value& val = Matrix ())
     : Array<octave_value> (dim_vector (n, m), val) { }
 
-  Cell (const dim_vector& dv, const octave_value& val = resize_fill_value ())
+  Cell (const dim_vector& dv, const octave_value& val = Matrix ())
     : Array<octave_value> (dv, val) { }
 
   Cell (const Array<octave_value>& c)
@@ -86,7 +86,7 @@
   using Array<octave_value>::assign;
 
   void assign (const octave_value_list& idx, const Cell& rhs,
-               const octave_value& fill_val = resize_fill_value ());
+               const octave_value& fill_val = Matrix ());
 
   Cell reshape (const dim_vector& new_dims) const
     { return Array<octave_value>::reshape (new_dims); }
@@ -110,7 +110,11 @@
   bool any_element_is_nan (void) const { return false; }
   bool is_true (void) const { return false; }
 
-  static octave_value resize_fill_value (void) { return Matrix (); }
+  octave_value resize_fill_value (void) const
+  {
+    static Matrix rfv;
+    return rfv;
+  }
 
   Cell diag (octave_idx_type k = 0) const;
 
--- a/src/DLD-FUNCTIONS/chol.cc
+++ b/src/DLD-FUNCTIONS/chol.cc
@@ -129,9 +129,9 @@
 \n\
 @end ifnottex\n\
 \n\
-For full matrices, if the \"lower\" flag is set only the lower triangular part\n\
-of the matrix is used for the factorization, otherwise the upper triangular\n\
-part is used.\n\
+For full matrices, if the \"lower\" flag is set only the lower triangular\n\
+part of the matrix is used for the factorization, otherwise the upper\n\
+triangular part is used.\n\
 \n\
 In general the lower triangular factorization is significantly faster for\n\
 sparse matrices.\n\
@@ -623,6 +623,7 @@
 Update or downdate a Cholesky@tie{}factorization.  Given an upper triangular\n\
 matrix @var{R} and a column vector @var{u}, attempt to determine another\n\
 upper triangular matrix @var{R1} such that\n\
+\n\
 @itemize @bullet\n\
 @item\n\
 @var{R1}'*@var{R1} = @var{R}'*@var{R} + @var{u}*@var{u}'\n\
@@ -634,6 +635,7 @@
 @end itemize\n\
 \n\
 If @var{op} is \"-\", @var{info} is set to\n\
+\n\
 @itemize\n\
 @item 0 if the downdate was successful,\n\
 \n\
@@ -833,6 +835,7 @@
 @var{A1}, where @w{A1(p,p) = A}, @w{A1(:,j) = A1(j,:)' = u} and\n\
 @w{p = [1:j-1,j+1:n+1]}.  @w{u(j)} should be positive.\n\
 On return, @var{info} is set to\n\
+\n\
 @itemize\n\
 @item 0 if the insertion was successful,\n\
 \n\
--- a/src/DLD-FUNCTIONS/rand.cc
+++ b/src/DLD-FUNCTIONS/rand.cc
@@ -358,7 +358,10 @@
 \n\
 By default, the generator is initialized from @code{/dev/urandom} if it is\n\
 available, otherwise from CPU time, wall clock time, and the current\n\
-fraction of a second.\n\
+fraction of a second.  Note that this differs from @sc{matlab}, which\n\
+always initializes the state to the same state at startup.  To obtain\n\
+behavior comparable to @sc{matlab}, initialize with a deterministic state\n\
+vector in Octave's startup files (@pxref{Startup Files}).\n\
 \n\
 To compute the pseudo-random sequence, @code{rand} uses the Mersenne\n\
 Twister with a period of @math{2^{19937}-1} (See M. Matsumoto and\n\
--- a/src/bitfcns.cc
+++ b/src/bitfcns.cc
@@ -42,224 +42,248 @@
 #include "ov-re-mat.h"
 #include "ov-bool.h"
 
-// FIXME -- could probably eliminate some code duplication by
-// clever use of templates.
+#include <functional>
+
+template <typename OP, typename T>
+octave_value
+bitopxx(const OP& op, const std::string& fname,
+        const Array<T>& x, const Array<T>& y)
+{
+  int nelx = x.numel ();
+  int nely = y.numel ();
+
+  bool is_scalar_op = (nelx == 1 || nely == 1);
+
+  dim_vector dvx = x.dims ();
+  dim_vector dvy = y.dims ();
+
+  bool is_array_op = (dvx == dvy);
+
+  octave_value retval;
+  if (is_array_op || is_scalar_op)
+    {
+      Array<T> result;
+
+      if (nelx != 1)
+        result.resize (dvx);
+      else
+        result.resize (dvy);
+
+      for (int i = 0; i < nelx; i++)
+        if (is_scalar_op)
+          for (int k = 0; k < nely; k++)
+            result(i+k) = op(x(i), y(k));
+        else
+          result(i) = op(x(i), y(i));
+
+      retval = result;
+    }
+  else
+    error ("%s: size of X and Y must match, or one operand must be a scalar",
+           fname.c_str());
+
+  return retval;
+}
 
-#define BITOPX(OP, FNAME, RET) \
-      { \
-        int nelx = x.numel (); \
-        int nely = y.numel (); \
- \
-        bool is_scalar_op = (nelx == 1 || nely == 1); \
- \
-        dim_vector dvx = x.dims (); \
-        dim_vector dvy = y.dims (); \
- \
-        bool is_array_op = (dvx == dvy); \
- \
-        if (is_array_op || is_scalar_op) \
-          { \
-            RET result; \
- \
-            if (nelx != 1) \
-              result.resize (dvx); \
-            else \
-              result.resize (dvy); \
- \
-            for (int i = 0; i < nelx; i++) \
-              if (is_scalar_op) \
-                for (int k = 0; k < nely; k++) \
-                  result(i+k) = x(i) OP y(k); \
-              else \
-                result(i) = x(i) OP y(i); \
- \
-              retval = result; \
-          } \
-        else \
-          error ("%s: size of X and Y must match, or one operand must be a scalar", FNAME); \
-      }
+// Trampoline function, instantiates the proper template above, with
+// reflective information hardwired. We can't hardwire this information
+// in Fbitxxx DEFUNs below, because at that moment, we still don't have
+// information about which integer types we need to instantiate.
+template<typename T>
+octave_value
+bitopx(const std::string& fname, const Array<T>& x, const Array<T>& y)
+{
+  if (fname == "bitand")
+    return bitopxx (std::bit_and<T>(), fname, x, y);
+  if (fname == "bitor")
+    return bitopxx (std::bit_or<T>(), fname, x, y);
+
+  //else (fname == "bitxor")
+  return bitopxx (std::bit_xor<T>(), fname, x, y);
+}
+
+octave_value
+bitop(const std::string& fname, const octave_value_list& args)
+{
+  octave_value retval;
+
+  int nargin = args.length ();
+
+  if (nargin == 2)
+    {
+      if ((args(0).class_name () == octave_scalar::static_class_name ())
+          || (args(0).class_name () == octave_bool::static_class_name ())
+          || (args(1).class_name () == octave_scalar::static_class_name ())
+          || (args(1).class_name () == octave_bool::static_class_name ()))
+        {
+          bool arg0_is_int = (args(0).class_name () !=
+                              octave_scalar::static_class_name () &&
+                              args(0).class_name () !=
+                              octave_bool::static_class_name ());
+          bool arg1_is_int = (args(1).class_name () !=
+                              octave_scalar::static_class_name () &&
+                              args(1).class_name () !=
+                              octave_bool::static_class_name ());
+
+          if (! (arg0_is_int || arg1_is_int))
+            {
+              uint64NDArray x (args(0).array_value ());
+              uint64NDArray y (args(1).array_value ());
+              if (! error_state)
+                retval = bitopx (fname, x, y).array_value();
+            }
+          else
+            {
+              int p = (arg0_is_int ? 1 : 0);
+              int q = (arg0_is_int ? 0 : 1);
+
+              NDArray dx = args(p).array_value ();
 
-#define BITOP(OP, FNAME) \
- \
-  octave_value retval; \
- \
-  int nargin = args.length (); \
- \
-  if (nargin == 2) \
-    { \
-      if ((args(0).class_name () == octave_scalar::static_class_name ()) \
-          || (args(0).class_name () == octave_bool::static_class_name ()) \
-          || (args(1).class_name () == octave_scalar::static_class_name ()) \
-          || (args(1).class_name () == octave_bool::static_class_name ())) \
-        { \
-          bool arg0_is_int = (args(0).class_name () !=  \
-                              octave_scalar::static_class_name () && \
-                              args(0).class_name () != \
-                              octave_bool::static_class_name ()); \
-          bool arg1_is_int = (args(1).class_name () !=  \
-                              octave_scalar::static_class_name () && \
-                              args(1).class_name () != \
-                              octave_bool::static_class_name ()); \
-          \
-          if (! (arg0_is_int || arg1_is_int))   \
-            { \
-              uint64NDArray x (args(0).array_value ()); \
-              uint64NDArray y (args(1).array_value ()); \
-              if (! error_state) \
-                BITOPX (OP, FNAME, uint64NDArray); \
-              retval = retval.array_value (); \
-            } \
-          else \
-            { \
-              int p = (arg0_is_int ? 1 : 0); \
-              int q = (arg0_is_int ? 0 : 1); \
- \
-              NDArray dx = args(p).array_value (); \
- \
-              if (args(q).type_id () == octave_uint64_matrix::static_type_id () \
-                  || args(q).type_id () == octave_uint64_scalar::static_type_id ()) \
-                { \
-                  uint64NDArray x (dx); \
-                  uint64NDArray y = args(q).uint64_array_value (); \
-                  if (! error_state) \
-                    BITOPX (OP, FNAME, uint64NDArray); \
-                 } \
-              else if (args(q).type_id () == octave_uint32_matrix::static_type_id () \
-                       || args(q).type_id () == octave_uint32_scalar::static_type_id ()) \
-                { \
-                  uint32NDArray x (dx); \
-                  uint32NDArray y = args(q).uint32_array_value (); \
-                  if (! error_state) \
-                    BITOPX (OP, FNAME, uint32NDArray); \
-                } \
-              else if (args(q).type_id () == octave_uint16_matrix::static_type_id () \
-                       || args(q).type_id () == octave_uint16_scalar::static_type_id ()) \
-                { \
-                  uint16NDArray x (dx); \
-                  uint16NDArray y = args(q).uint16_array_value (); \
-                  if (! error_state) \
-                    BITOPX (OP, FNAME, uint16NDArray); \
-                } \
-              else if (args(q).type_id () == octave_uint8_matrix::static_type_id () \
-                       || args(q).type_id () == octave_uint8_scalar::static_type_id ()) \
-                { \
-                  uint8NDArray x (dx); \
-                  uint8NDArray y = args(q).uint8_array_value (); \
-                  if (! error_state) \
-                    BITOPX (OP, FNAME, uint8NDArray); \
-                } \
-              else if (args(q).type_id () == octave_int64_matrix::static_type_id () \
-                       || args(q).type_id () == octave_int64_scalar::static_type_id ()) \
-                { \
-                  int64NDArray x (dx); \
-                  int64NDArray y = args(q).int64_array_value (); \
-                  if (! error_state) \
-                    BITOPX (OP, FNAME, int64NDArray); \
-                } \
-              else if (args(q).type_id () == octave_int32_matrix::static_type_id () \
-                       || args(q).type_id () == octave_int32_scalar::static_type_id ()) \
-                { \
-                  int32NDArray x (dx); \
-                  int32NDArray y = args(q).int32_array_value (); \
-                  if (! error_state) \
-                    BITOPX (OP, FNAME, int32NDArray); \
-                } \
-              else if (args(q).type_id () == octave_int16_matrix::static_type_id () \
-                       || args(q).type_id () == octave_int16_scalar::static_type_id ()) \
-                { \
-                  int16NDArray x (dx); \
-                  int16NDArray y = args(q).int16_array_value (); \
-                  if (! error_state) \
-                    BITOPX (OP, FNAME, int16NDArray); \
-                } \
-              else if (args(q).type_id () == octave_int8_matrix::static_type_id () \
-                       || args(q).type_id () == octave_int8_scalar::static_type_id ()) \
-                { \
-                  int8NDArray x (dx); \
-                  int8NDArray y = args(q).int8_array_value (); \
-                  if (! error_state) \
-                    BITOPX (OP, FNAME, int8NDArray); \
-                } \
-              else \
-                error ("%s: invalid operand type", FNAME); \
-            } \
-        } \
-      else if (args(0).class_name () == args(1).class_name ()) \
-        { \
-          if (args(0).type_id () == octave_uint64_matrix::static_type_id () \
-              || args(0).type_id () == octave_uint64_scalar::static_type_id ()) \
-            { \
-              uint64NDArray x = args(0).uint64_array_value (); \
-              uint64NDArray y = args(1).uint64_array_value (); \
-              if (! error_state) \
-                BITOPX (OP, FNAME, uint64NDArray); \
-            } \
-          else if (args(0).type_id () == octave_uint32_matrix::static_type_id () \
-                   || args(0).type_id () == octave_uint32_scalar::static_type_id ()) \
-            { \
-              uint32NDArray x = args(0).uint32_array_value (); \
-              uint32NDArray y = args(1).uint32_array_value (); \
-              if (! error_state) \
-                BITOPX (OP, FNAME, uint32NDArray); \
-            } \
-          else if (args(0).type_id () == octave_uint16_matrix::static_type_id () \
-                   || args(0).type_id () == octave_uint16_scalar::static_type_id ()) \
-            { \
-              uint16NDArray x = args(0).uint16_array_value (); \
-              uint16NDArray y = args(1).uint16_array_value (); \
-              if (! error_state) \
-                BITOPX (OP, FNAME, uint16NDArray); \
-            } \
-          else if (args(0).type_id () == octave_uint8_matrix::static_type_id () \
-                   || args(0).type_id () == octave_uint8_scalar::static_type_id ()) \
-            { \
-              uint8NDArray x = args(0).uint8_array_value (); \
-              uint8NDArray y = args(1).uint8_array_value (); \
-              if (! error_state) \
-                BITOPX (OP, FNAME, uint8NDArray); \
-            } \
-          else if (args(0).type_id () == octave_int64_matrix::static_type_id () \
-                   || args(0).type_id () == octave_int64_scalar::static_type_id ()) \
-            { \
-              int64NDArray x = args(0).int64_array_value (); \
-              int64NDArray y = args(1).int64_array_value (); \
-              if (! error_state) \
-                BITOPX (OP, FNAME, int64NDArray); \
-            } \
-          else if (args(0).type_id () == octave_int32_matrix::static_type_id () \
-                   || args(0).type_id () == octave_int32_scalar::static_type_id ()) \
-            { \
-              int32NDArray x = args(0).int32_array_value (); \
-              int32NDArray y = args(1).int32_array_value (); \
-              if (! error_state) \
-                BITOPX (OP, FNAME, int32NDArray); \
-            } \
-          else if (args(0).type_id () == octave_int16_matrix::static_type_id () \
-                   || args(0).type_id () == octave_int16_scalar::static_type_id ()) \
-            { \
-              int16NDArray x = args(0).int16_array_value (); \
-              int16NDArray y = args(1).int16_array_value (); \
-              if (! error_state) \
-                BITOPX (OP, FNAME, int16NDArray); \
-            } \
-          else if (args(0).type_id () == octave_int8_matrix::static_type_id () \
-                   || args(0).type_id () == octave_int8_scalar::static_type_id ()) \
-            { \
-              int8NDArray x = args(0).int8_array_value (); \
-              int8NDArray y = args(1).int8_array_value (); \
-              if (! error_state) \
-                BITOPX (OP, FNAME, int8NDArray); \
-            } \
-          else \
-            error ("%s: invalid operand type", FNAME); \
-        } \
-      else \
-        error ("%s: must have matching operand types", FNAME); \
-    } \
-  else \
-    print_usage (); \
- \
-  return retval
+              if (args(q).type_id () == octave_uint64_matrix::static_type_id ()
+                  || args(q).type_id () == octave_uint64_scalar::static_type_id ())
+                {
+                  uint64NDArray x (dx);
+                  uint64NDArray y = args(q).uint64_array_value ();
+                  if (! error_state)
+                    retval = bitopx (fname, x, y);
+                }
+              else if (args(q).type_id () == octave_uint32_matrix::static_type_id ()
+                       || args(q).type_id () == octave_uint32_scalar::static_type_id ())
+                {
+                  uint32NDArray x (dx);
+                  uint32NDArray y = args(q).uint32_array_value ();
+                  if (! error_state)
+                    retval = bitopx (fname, x, y);
+                }
+              else if (args(q).type_id () == octave_uint16_matrix::static_type_id ()
+                       || args(q).type_id () == octave_uint16_scalar::static_type_id ())
+                {
+                  uint16NDArray x (dx);
+                  uint16NDArray y = args(q).uint16_array_value ();
+                  if (! error_state)
+                    retval = bitopx (fname, x, y);
+                }
+              else if (args(q).type_id () == octave_uint8_matrix::static_type_id ()
+                       || args(q).type_id () == octave_uint8_scalar::static_type_id ())
+                {
+                  uint8NDArray x (dx);
+                  uint8NDArray y = args(q).uint8_array_value ();
+                  if (! error_state)
+                    retval = bitopx (fname, x, y);
+                }
+              else if (args(q).type_id () == octave_int64_matrix::static_type_id ()
+                       || args(q).type_id () == octave_int64_scalar::static_type_id ())
+                {
+                  int64NDArray x (dx);
+                  int64NDArray y = args(q).int64_array_value ();
+                  if (! error_state)
+                    retval = bitopx (fname, x, y);
+                }
+              else if (args(q).type_id () == octave_int32_matrix::static_type_id ()
+                       || args(q).type_id () == octave_int32_scalar::static_type_id ())
+                {
+                  int32NDArray x (dx);
+                  int32NDArray y = args(q).int32_array_value ();
+                  if (! error_state)
+                    retval = bitopx (fname, x, y);
+                }
+              else if (args(q).type_id () == octave_int16_matrix::static_type_id ()
+                       || args(q).type_id () == octave_int16_scalar::static_type_id ())
+                {
+                  int16NDArray x (dx);
+                  int16NDArray y = args(q).int16_array_value ();
+                  if (! error_state)
+                    retval  = bitopx (fname, x, y);
+                }
+              else if (args(q).type_id () == octave_int8_matrix::static_type_id ()
+                       || args(q).type_id () == octave_int8_scalar::static_type_id ())
+                {
+                  int8NDArray x (dx);
+                  int8NDArray y = args(q).int8_array_value ();
+                  if (! error_state)
+                    retval = bitopx (fname, x, y);
+                }
+              else
+                error ("%s: invalid operand type", fname.c_str());
+            }
+        }
+      else if (args(0).class_name () == args(1).class_name ())
+        {
+          if (args(0).type_id () == octave_uint64_matrix::static_type_id ()
+              || args(0).type_id () == octave_uint64_scalar::static_type_id ())
+            {
+              uint64NDArray x = args(0).uint64_array_value ();
+              uint64NDArray y = args(1).uint64_array_value ();
+              if (! error_state)
+                retval = bitopx (fname, x, y);
+            }
+          else if (args(0).type_id () == octave_uint32_matrix::static_type_id ()
+                   || args(0).type_id () == octave_uint32_scalar::static_type_id ())
+            {
+              uint32NDArray x = args(0).uint32_array_value ();
+              uint32NDArray y = args(1).uint32_array_value ();
+              if (! error_state)
+                retval = bitopx (fname, x, y);
+            }
+          else if (args(0).type_id () == octave_uint16_matrix::static_type_id ()
+                   || args(0).type_id () == octave_uint16_scalar::static_type_id ())
+            {
+              uint16NDArray x = args(0).uint16_array_value ();
+              uint16NDArray y = args(1).uint16_array_value ();
+              if (! error_state)
+                retval = bitopx (fname, x, y);
+            }
+          else if (args(0).type_id () == octave_uint8_matrix::static_type_id ()
+                   || args(0).type_id () == octave_uint8_scalar::static_type_id ())
+            {
+              uint8NDArray x = args(0).uint8_array_value ();
+              uint8NDArray y = args(1).uint8_array_value ();
+              if (! error_state)
+                retval = bitopx (fname, x, y);
+            }
+          else if (args(0).type_id () == octave_int64_matrix::static_type_id ()
+                   || args(0).type_id () == octave_int64_scalar::static_type_id ())
+            {
+              int64NDArray x = args(0).int64_array_value ();
+              int64NDArray y = args(1).int64_array_value ();
+              if (! error_state)
+                retval = bitopx (fname, x, y);
+            }
+          else if (args(0).type_id () == octave_int32_matrix::static_type_id ()
+                   || args(0).type_id () == octave_int32_scalar::static_type_id ())
+            {
+              int32NDArray x = args(0).int32_array_value ();
+              int32NDArray y = args(1).int32_array_value ();
+              if (! error_state)
+                retval = bitopx (fname, x, y);
+            }
+          else if (args(0).type_id () == octave_int16_matrix::static_type_id ()
+                   || args(0).type_id () == octave_int16_scalar::static_type_id ())
+            {
+              int16NDArray x = args(0).int16_array_value ();
+              int16NDArray y = args(1).int16_array_value ();
+              if (! error_state)
+                retval = bitopx (fname, x, y);
+            }
+          else if (args(0).type_id () == octave_int8_matrix::static_type_id ()
+                   || args(0).type_id () == octave_int8_scalar::static_type_id ())
+            {
+              int8NDArray x = args(0).int8_array_value ();
+              int8NDArray y = args(1).int8_array_value ();
+              if (! error_state)
+                retval = bitopx (fname, x, y);
+            }
+          else
+            error ("%s: invalid operand type", fname.c_str());
+        }
+      else
+        error ("%s: must have matching operand types", fname.c_str());
+    }
+  else
+    print_usage ();
+
+  return retval;
+}
 
 DEFUN (bitand, args, ,
   "-*- texinfo -*-\n\
@@ -269,7 +293,7 @@
 @seealso{bitor, bitxor, bitset, bitget, bitcmp, bitshift, bitmax}\n\
 @end deftypefn")
 {
-  BITOP (&, "bitand");
+  return bitop ("bitand", args);
 }
 
 DEFUN (bitor, args, ,
@@ -280,7 +304,7 @@
 @seealso{bitor, bitxor, bitset, bitget, bitcmp, bitshift, bitmax}\n\
 @end deftypefn")
 {
-  BITOP (|, "bitor");
+  return bitop ("bitor", args);
 }
 
 DEFUN (bitxor, args, ,
@@ -291,7 +315,7 @@
 @seealso{bitand, bitor, bitset, bitget, bitcmp, bitshift, bitmax}\n\
 @end deftypefn")
 {
-  BITOP (^, "bitxor");
+  return bitop ("bitxor", args);
 }
 
 static int64_t
--- a/src/data.cc
+++ b/src/data.cc
@@ -5477,7 +5477,7 @@
   "-*- texinfo -*-\n\
 @deftypefn {Built-in Function} {} mldivide (@var{x}, @var{y})\n\
 Return the matrix left division of @var{x} and @var{y}.\n\
-This function and @w{@xcode{x \\ y}} are equivalent.\n\
+This function and @w{@xcode{x @xbackslashchar{} y}} are equivalent.\n\
 @seealso{mrdivide, ldivide}\n\
 @end deftypefn")
 {
@@ -5594,7 +5594,7 @@
   "-*- texinfo -*-\n\
 @deftypefn {Built-in Function} {} ldivide (@var{x}, @var{y})\n\
 Return the element-by-element left division of @var{x} and @var{y}.\n\
-This function and @w{@xcode{x .\\ y}} are equivalent.\n\
+This function and @w{@xcode{x .@xbackslashchar{} y}} are equivalent.\n\
 @seealso{rdivide, mldivide}\n\
 @end deftypefn")
 {
@@ -5648,10 +5648,14 @@
 DEFUN (tic, args, nargout,
   "-*- texinfo -*-\n\
 @deftypefn  {Built-in Function} {} tic ()\n\
+@deftypefnx  {Built-in Function} {@var{id} =} tic ()\n\
 @deftypefnx {Built-in Function} {} toc ()\n\
+@deftypefnx {Built-in Function} {} toc (@var{id})\n\
+@deftypefnx {Built-in Function} {@var{val} =} toc (@dots{})\n\
 Set or check a wall-clock timer.  Calling @code{tic} without an\n\
-output argument sets the timer.  Subsequent calls to @code{toc}\n\
-return the number of seconds since the timer was set.  For example,\n\
+output argument sets the internal timer state.  Subsequent calls\n\
+to @code{toc} return the number of seconds since the timer was set.\n\
+For example,\n\
 \n\
 @example\n\
 @group\n\
@@ -5665,38 +5669,23 @@
 will set the variable @code{elapsed_time} to the number of seconds since\n\
 the most recent call to the function @code{tic}.\n\
 \n\
-If called with one output argument then this function returns a scalar\n\
-of type @code{uint64} and the wall-clock timer is not started.\n\
+If called with one output argument, @code{tic} returns a scalar\n\
+of type @code{uint64} that may be later passed to @code{toc}.\n\
 \n\
 @example\n\
 @group\n\
-t = tic; sleep (5); (double (tic ()) - double (t)) * 1e-6\n\
-      @result{} 5\n\
+id = tic; sleep (5); toc (id)\n\
+      @result{} 5.0010\n\
 @end group\n\
 @end example\n\
 \n\
-Nested timing with @code{tic} and @code{toc} is not supported.\n\
-Therefore @code{toc} will always return the elapsed time from the most\n\
-recent call to @code{tic}.\n\
+Calling @code{tic} and @code{toc} this way allows nested timing calls.\n\
 \n\
 If you are more interested in the CPU time that your process used, you\n\
 should use the @code{cputime} function instead.  The @code{tic} and\n\
 @code{toc} functions report the actual wall clock time that elapsed\n\
 between the calls.  This may include time spent processing other jobs or\n\
-doing nothing at all.  For example:\n\
-\n\
-@example\n\
-@group\n\
-tic (); sleep (5); toc ()\n\
-     @result{} 5\n\
-t = cputime (); sleep (5); cputime () - t\n\
-     @result{} 0\n\
-@end group\n\
-@end example\n\
-\n\
-@noindent\n\
-(This example also illustrates that the CPU timer may have a fairly\n\
-coarse resolution.)\n\
+doing nothing at all.\n\
 @end deftypefn")
 {
   octave_value retval;
@@ -5711,7 +5700,13 @@
   double tmp = now.double_value ();
 
   if (nargout > 0)
-    retval = static_cast<octave_uint64> (1e6 * tmp);
+    {
+      double ip = 0.0;
+      double frac = modf (tmp, &ip);
+      uint64_t microsecs = static_cast<uint64_t> (CLOCKS_PER_SEC * frac);
+      microsecs += CLOCKS_PER_SEC * static_cast<uint64_t> (ip);
+      retval = octave_uint64 (microsecs);
+    }
   else
     tic_toc_timestamp = tmp;
 
@@ -5721,6 +5716,8 @@
 DEFUN (toc, args, nargout,
   "-*- texinfo -*-\n\
 @deftypefn {Built-in Function} {} toc ()\n\
+@deftypefnx {Built-in Function} {} toc (@var{id})\n\
+@deftypefnx {Built-in Function} {@var{val} = } toc (@dots{})\n\
 See tic.\n\
 @end deftypefn")
 {
@@ -5728,30 +5725,59 @@
 
   int nargin = args.length ();
 
-  if (nargin != 0)
-    warning ("tic: ignoring extra arguments");
-
-  if (tic_toc_timestamp < 0)
-    {
-      warning ("toc called before timer set");
-      if (nargout > 0)
-        retval = Matrix ();
-    }
+  double start_time = tic_toc_timestamp;
+
+  if (nargin > 1)
+    print_usage ();
   else
     {
-      octave_time now;
-
-      double tmp = now.double_value () - tic_toc_timestamp;
-
-      if (nargout > 0)
-        retval = tmp;
-      else
-        octave_stdout << "Elapsed time is " << tmp << " seconds.\n";
+      if (nargin == 1)
+        {
+          octave_uint64 id = args(0).uint64_scalar_value ();
+
+          if (! error_state)
+            {
+              uint64_t val = id.value ();
+
+              start_time
+                = (static_cast<double> (val / CLOCKS_PER_SEC)
+                   + static_cast<double> (val % CLOCKS_PER_SEC) / CLOCKS_PER_SEC);
+
+              // FIXME -- should we also check to see whether the start
+              // time is after the beginning of this Octave session?
+            }
+          else
+            error ("toc: invalid ID");
+        }
+
+      if (! error_state)
+        {
+          if (start_time < 0)
+            error ("toc called before timer set");
+          else
+            {
+              octave_time now;
+
+              double tmp = now.double_value () - start_time;
+
+              if (nargout > 0)
+                retval = tmp;
+              else
+                octave_stdout << "Elapsed time is " << tmp << " seconds.\n";
+            }
+        }
     }
 
   return retval;
 }
 
+/*
+%!shared id
+%! id = tic ();
+%!assert (isa (id, "uint64"));
+%!assert (isa (toc (id), "double"));
+*/
+
 DEFUN (cputime, args, ,
   "-*- texinfo -*-\n\
 @deftypefn {Built-in Function} {[@var{total}, @var{user}, @var{system}] =} cputime ();\n\
--- a/src/defaults.cc
+++ b/src/defaults.cc
@@ -294,6 +294,16 @@
 }
 
 static void
+set_default_texi_macros_file (void)
+{
+  std::string def_file = subst_octave_home (OCTAVE_TEXI_MACROS_FILE);
+
+  std::string env_file = octave_env::getenv ("OCTAVE_TEXI_MACROS_FILE");
+
+  Vtexi_macros_file = env_file.empty () ? def_file : env_file;
+}
+
+static void
 set_default_info_file (void)
 {
   std::string std_info_file = subst_octave_home (OCTAVE_INFOFILE);
@@ -393,6 +403,8 @@
 
   set_default_doc_cache_file ();
 
+  set_default_texi_macros_file ();
+
   set_default_info_file ();
 
   set_default_info_prog ();
--- a/src/defaults.in.h
+++ b/src/defaults.in.h
@@ -56,6 +56,10 @@
 #define OCTAVE_DOC_CACHE_FILE %OCTAVE_DOC_CACHE_FILE%
 #endif
 
+#ifndef OCTAVE_TEXI_MACROS_FILE
+#define OCTAVE_TEXI_MACROS_FILE %OCTAVE_TEXI_MACROS_FILE%
+#endif
+
 #ifndef OCTAVE_EXEC_PREFIX
 #define OCTAVE_EXEC_PREFIX %OCTAVE_EXEC_PREFIX%
 #endif
--- a/src/help.cc
+++ b/src/help.cc
@@ -71,6 +71,11 @@
 // (--doc-cache-file file)
 std::string Vdoc_cache_file;
 
+// Name of the file containing local Texinfo macros that are prepended
+// to doc strings before processing.
+// (--texi-macros-file)
+std::string Vtexi_macros_file;
+
 // Name of the info file specified on command line.
 // (--info-file file)
 std::string Vinfo_file;
@@ -1291,6 +1296,30 @@
   return SET_NONEMPTY_INTERNAL_STRING_VARIABLE (doc_cache_file);
 }
 
+DEFUN (texi_macros_file, args, nargout,
+  "-*- texinfo -*-\n\
+@deftypefn  {Built-in Function} {@var{val} =} texi_macros_file ()\n\
+@deftypefnx {Built-in Function} {@var{old_val} =} texi_macros_file (@var{new_val})\n\
+@deftypefnx {Built-in Function} {} texi_macros_file (@var{new_val}, \"local\")\n\
+Query or set the internal variable that specifies the name of the\n\
+file containing Texinfo macros that are prepended to documentation strings\n\
+before they are passed to makeinfo.  The default value is \n\
+@file{@var{octave-home}/share/octave/@var{version}/etc/macros.texi},\n\
+in which @var{octave-home} is the root directory of the Octave installation,\n\
+and @var{version} is the Octave version number.\n\
+The default value may be overridden by the environment variable\n\
+@w{@env{OCTAVE_TEXI_MACROS_FILE}}, or the command line argument\n\
+@samp{--texi-macros-file NAME}.\n\
+\n\
+When called from inside a function with the \"local\" option, the variable is\n\
+changed locally for the function and any subroutines it calls.  The original\n\
+variable value is restored when exiting the function.\n\
+@seealso{makeinfo_program}\n\
+@end deftypefn")
+{
+  return SET_NONEMPTY_INTERNAL_STRING_VARIABLE (texi_macros_file);
+}
+
 DEFUN (info_file, args, nargout,
   "-*- texinfo -*-\n\
 @deftypefn  {Built-in Function} {@var{val} =} info_file ()\n\
@@ -1349,7 +1378,7 @@
 When called from inside a function with the \"local\" option, the variable is\n\
 changed locally for the function and any subroutines it calls.  The original\n\
 variable value is restored when exiting the function.\n\
-@seealso{info_file, info_program, doc, help}\n\
+@seealso{texi_macros_file, info_file, info_program, doc, help}\n\
 @end deftypefn")
 {
   return SET_NONEMPTY_INTERNAL_STRING_VARIABLE (makeinfo_program);
--- a/src/help.h
+++ b/src/help.h
@@ -36,6 +36,11 @@
 // (--doc-cache-file file)
 extern std::string Vdoc_cache_file;
 
+// Name of the file containing local Texinfo macros that are prepended
+// to doc strings before processing.
+// (--texi-macros-file)
+extern std::string Vtexi_macros_file;
+
 // Name of the info file specified on command line.
 // (--info-file file)
 extern std::string Vinfo_file;
--- a/src/lex.ll
+++ b/src/lex.ll
@@ -765,8 +765,8 @@
 %}
 
 \?{IDENT}{S}* |
-\?{IDENT}.{IDENT}{S}* {
-    LEXER_DEBUG ("\?{IDENT}{S}* | \?{IDENT}.{IDENT}{S}*");
+\?{IDENT}\.{IDENT}{S}* {
+    LEXER_DEBUG ("\\?{IDENT}{S}*|\\?{IDENT}\\.{IDENT}{S}*");
 
     int id_tok = handle_meta_identifier ();
 
@@ -1525,9 +1525,9 @@
           break;
 
         case end_kw:
-          if (! reading_classdef_file
-              && (inside_any_object_index ()
-                  || (lexer_flags.defining_func
+          if (inside_any_object_index ()
+              || (! reading_classdef_file
+                  && (lexer_flags.defining_func
                       && ! (lexer_flags.looking_at_return_list
                             || lexer_flags.parsed_function_name.top ()))))
             return 0;
--- a/src/mex.cc
+++ b/src/mex.cc
@@ -1188,7 +1188,7 @@
         for (size_t i = 0; i < tmp_len; i++)
           cpr[m*i+j] = static_cast<mxChar> (ptr[i]);
 
-        for (size_t i = tmp_len; i < nc; i++)
+        for (size_t i = tmp_len; i < static_cast<size_t>(nc); i++)
           cpr[m*i+j] = static_cast<mxChar> (' ');
       }
   }
--- a/src/oct-map.cc
+++ b/src/oct-map.cc
@@ -557,7 +557,7 @@
       for (octave_idx_type i = 0; i < nf; i++)
         {
           if (fill)
-            xvals[i].resize (dv, Cell::resize_fill_value ());
+            xvals[i].resize (dv, Matrix ());
           else
             xvals[i].resize (dv);
         }
@@ -1160,7 +1160,7 @@
       for (octave_idx_type i = 0; i < nf; i++)
         {
           if (&xvals[i] != &ref)
-            xvals[i].resize (dimensions, Cell::resize_fill_value ());
+            xvals[i].resize (dimensions, Matrix ());
         }
 
       optimize_dimensions ();
@@ -1426,7 +1426,7 @@
 string_vector
 Octave_map::keys (void) const
 {
-  assert (nfields () == key_list.size ());
+  assert (static_cast<size_t>(nfields ()) == key_list.size ());
 
   return string_vector (key_list);
 }
@@ -1489,7 +1489,7 @@
               Cell tmp = contents(p);
 
               if (fill)
-                tmp.resize (dv, Cell::resize_fill_value ());
+                tmp.resize (dv, Matrix ());
               else
                 tmp.resize (dv);
 
@@ -1669,7 +1669,7 @@
       if (tmp_dims != dimensions)
         {
           for (iterator p = begin (); p != end (); p++)
-            contents(p).resize (tmp_dims, Cell::resize_fill_value ());
+            contents(p).resize (tmp_dims, Matrix ());
 
           dimensions = tmp_dims;
         }
--- a/src/oct-obj.h
+++ b/src/oct-obj.h
@@ -91,8 +91,7 @@
 
   bool empty (void) const { return length () == 0; }
 
-  void resize (octave_idx_type n, const octave_value& rfv
-               = Array<octave_value>::resize_fill_value ())
+  void resize (octave_idx_type n, const octave_value& rfv = octave_value ())
   {
     data.resize (dim_vector (1, n), rfv);
   }
--- a/src/octave.cc
+++ b/src/octave.cc
@@ -150,7 +150,8 @@
 #define NO_SITE_FILE_OPTION 11
 #define NO_WINDOW_SYSTEM_OPTION 12
 #define PERSIST_OPTION 13
-#define TRADITIONAL_OPTION 14
+#define TEXI_MACROS_FILE_OPTION 14
+#define TRADITIONAL_OPTION 15
 struct option long_opts[] =
   {
     { "braindead",        no_argument,       0, TRADITIONAL_OPTION },
@@ -176,6 +177,7 @@
     { "persist",          no_argument,       0, PERSIST_OPTION },
     { "quiet",            no_argument,       0, 'q' },
     { "silent",           no_argument,       0, 'q' },
+    { "texi-macros-file", required_argument, 0, TEXI_MACROS_FILE_OPTION },
     { "traditional",      no_argument,       0, TRADITIONAL_OPTION },
     { "verbose",          no_argument,       0, 'V' },
     { "version",          no_argument,       0, 'v' },
@@ -534,6 +536,7 @@
   --path PATH, -p PATH    Add PATH to head of function search path.\n\
   --persist               Go interactive after --eval or reading from FILE.\n\
   --silent, -q            Don't print message at startup.\n\
+  --texi-macros-file FILE Use Texinfo macros in FILE for makeinfo command.\n\
   --traditional           Set variables for closer MATLAB compatibility.\n\
   --verbose, -V           Enable verbose output in some cases.\n\
   --version, -v           Print version number and exit.\n\
@@ -811,6 +814,11 @@
           persist = true;
           break;
 
+        case TEXI_MACROS_FILE_OPTION:
+          if (optarg)
+            bind_internal_variable ("texi_macros_file", optarg);
+          break;
+
         case TRADITIONAL_OPTION:
           traditional = true;
           break;
--- a/src/ov-complex.cc
+++ b/src/ov-complex.cc
@@ -225,7 +225,7 @@
 {
   if (fill)
     {
-      ComplexNDArray retval (dv, ComplexNDArray::resize_fill_value ());
+      ComplexNDArray retval (dv, Complex (0));
 
       if (dv.numel ())
         retval(0) = scalar;
--- a/src/ov-float.cc
+++ b/src/ov-float.cc
@@ -79,7 +79,7 @@
 {
   if (fill)
     {
-      FloatNDArray retval (dv, NDArray::resize_fill_value());
+      FloatNDArray retval (dv, 0);
 
       if (dv.numel ())
         retval(0) = scalar;
--- a/src/ov-flt-complex.cc
+++ b/src/ov-flt-complex.cc
@@ -210,7 +210,7 @@
 {
   if (fill)
     {
-      FloatComplexNDArray retval (dv, FloatComplexNDArray::resize_fill_value ());
+      FloatComplexNDArray retval (dv, FloatComplex (0));
 
       if (dv.numel ())
         retval(0) = scalar;
--- a/src/ov-range.cc
+++ b/src/ov-range.cc
@@ -335,7 +335,7 @@
 {
   NDArray retval = array_value ();
   if (fill)
-    retval.resize (dv, NDArray::resize_fill_value ());
+    retval.resize (dv, 0);
   else
     retval.resize (dv);
   return retval;
--- a/src/ov-scalar.cc
+++ b/src/ov-scalar.cc
@@ -94,7 +94,7 @@
 {
   if (fill)
     {
-      NDArray retval (dv, NDArray::resize_fill_value());
+      NDArray retval (dv, 0);
 
       if (dv.numel ())
         retval(0) = scalar;
--- a/src/ov-str-mat.cc
+++ b/src/ov-str-mat.cc
@@ -143,7 +143,7 @@
 {
   charNDArray retval (matrix);
   if (fill)
-    retval.resize (dv, charNDArray::resize_fill_value ());
+    retval.resize (dv, 0);
   else
     retval.resize (dv);
   return octave_value (retval, is_sq_string () ? '\'' : '"');
--- a/src/ov-struct.cc
+++ b/src/ov-struct.cc
@@ -2133,6 +2133,8 @@
 %! assert (fieldnames (s), keys');
 
 %!assert (cell2struct ({1; 2}, {"a"; "b"}), struct ("a", 1, "b", 2));
+
+%!assert (cell2struct ({}, {"f"}, 3), struct ("f", {}));
 */
 
 
--- a/src/sparse.cc
+++ b/src/sparse.cc
@@ -78,7 +78,7 @@
 \n\
 @strong{Note}: if multiple values are specified with the same\n\
 @var{i}, @var{j} indices, the corresponding values in @var{s} will\n\
-be added. See @code{accumarray} for an example of how to produce different\n\
+be added.  See @code{accumarray} for an example of how to produce different\n\
 behavior, such as taking the minimum instead.\n\
 \n\
 The following are all equivalent:\n\