emacs-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Emacs-diffs] Changes to emacs/lisp/textmodes/bibtex.el [lexbind]


From: Miles Bader
Subject: [Emacs-diffs] Changes to emacs/lisp/textmodes/bibtex.el [lexbind]
Date: Wed, 08 Dec 2004 19:17:43 -0500

Index: emacs/lisp/textmodes/bibtex.el
diff -c emacs/lisp/textmodes/bibtex.el:1.69.2.8 
emacs/lisp/textmodes/bibtex.el:1.69.2.9
*** emacs/lisp/textmodes/bibtex.el:1.69.2.8     Thu Nov  4 13:12:47 2004
--- emacs/lisp/textmodes/bibtex.el      Wed Dec  8 23:36:34 2004
***************
*** 34,41 ****
  ;;  Major mode for editing and validating BibTeX files.
  
  ;;  Usage:
! ;;  See documentation for function bibtex-mode (or type "\M-x describe-mode"
! ;;  when you are in BibTeX mode).
  
  ;;  Todo:
  ;;  Distribute texinfo file.
--- 34,41 ----
  ;;  Major mode for editing and validating BibTeX files.
  
  ;;  Usage:
! ;;  See documentation for function bibtex-mode or type "\M-x describe-mode"
! ;;  when you are in BibTeX mode.
  
  ;;  Todo:
  ;;  Distribute texinfo file.
***************
*** 63,88 ****
    :type 'hook)
  
  (defcustom bibtex-field-delimiters 'braces
!   "*Type of field delimiters.  Allowed values are `braces' or 
`double-quotes'."
    :group 'bibtex
    :type '(choice (const braces)
                   (const double-quotes)))
  
  (defcustom bibtex-entry-delimiters 'braces
!   "*Type of entry delimiters.  Allowed values are `braces' or `parentheses'."
    :group 'bibtex
    :type '(choice (const braces)
                   (const parentheses)))
  
  (defcustom bibtex-include-OPTcrossref '("InProceedings" "InCollection")
!   "*List of entries that get an OPTcrossref field."
    :group 'bibtex
    :type '(repeat string))
  
  (defcustom bibtex-include-OPTkey t
!   "*If non-nil, all entries will have an OPTkey field.
! If this is a string, it will be used as the initial field text.
! If this is a function, it will be called to generate the initial field text."
    :group 'bibtex
    :type '(choice (const :tag "None" nil)
                   (string :tag "Initial text")
--- 63,88 ----
    :type 'hook)
  
  (defcustom bibtex-field-delimiters 'braces
!   "Type of field delimiters.  Allowed values are `braces' or `double-quotes'."
    :group 'bibtex
    :type '(choice (const braces)
                   (const double-quotes)))
  
  (defcustom bibtex-entry-delimiters 'braces
!   "Type of entry delimiters.  Allowed values are `braces' or `parentheses'."
    :group 'bibtex
    :type '(choice (const braces)
                   (const parentheses)))
  
  (defcustom bibtex-include-OPTcrossref '("InProceedings" "InCollection")
!   "List of BibTeX entries that get an OPTcrossref field."
    :group 'bibtex
    :type '(repeat string))
  
  (defcustom bibtex-include-OPTkey t
!   "If non-nil, all newly created entries get an OPTkey field.
! If this is a string, use it as the initial field text.
! If this is a function, call it to generate the initial field text."
    :group 'bibtex
    :type '(choice (const :tag "None" nil)
                   (string :tag "Initial text")
***************
*** 91,100 ****
  
  (defcustom bibtex-user-optional-fields
    '(("annote" "Personal annotation (ignored)"))
!   "*List of optional fields the user wants to have always present.
  Entries should be of the same form as the OPTIONAL and
! CROSSREF-OPTIONAL lists in `bibtex-entry-field-alist' (see documentation
! of this variable for details)."
    :group 'bibtex
    :type '(repeat (group (string :tag "Field")
                          (string :tag "Comment")
--- 91,99 ----
  
  (defcustom bibtex-user-optional-fields
    '(("annote" "Personal annotation (ignored)"))
!   "List of optional fields the user wants to have always present.
  Entries should be of the same form as the OPTIONAL and
! CROSSREF-OPTIONAL lists in `bibtex-entry-field-alist' (which see)."
    :group 'bibtex
    :type '(repeat (group (string :tag "Field")
                          (string :tag "Comment")
***************
*** 106,112 ****
  
  (defcustom bibtex-entry-format
    '(opts-or-alts required-fields numerical-fields)
!   "*Type of formatting performed by `bibtex-clean-entry'.
  It may be t, nil, or a list of symbols out of the following:
  opts-or-alts        Delete empty optional and alternative fields and
                        remove OPT and ALT prefixes from used fields.
--- 105,111 ----
  
  (defcustom bibtex-entry-format
    '(opts-or-alts required-fields numerical-fields)
!   "Type of formatting performed by `bibtex-clean-entry'.
  It may be t, nil, or a list of symbols out of the following:
  opts-or-alts        Delete empty optional and alternative fields and
                        remove OPT and ALT prefixes from used fields.
***************
*** 114,124 ****
  numerical-fields    Delete delimiters around numeral fields.
  page-dashes         Change double dashes in page field to single dash
                        (for scribe compatibility).
! inherit-booktitle   If entry contains a crossref field and booktitle
!                       field is empty, it is set to the contents of the
!                       title field of the crossreferenced entry.
!                       Caution: this will work only if buffer is
!                        correctly sorted.
  realign             Realign entries, so that field texts and perhaps equal
                        signs (depending on the value of
                        `bibtex-align-at-equal-sign') begin in the same column.
--- 113,121 ----
  numerical-fields    Delete delimiters around numeral fields.
  page-dashes         Change double dashes in page field to single dash
                        (for scribe compatibility).
! inherit-booktitle   If entry contains a crossref field and the booktitle
!                       field is empty, set the booktitle field to the content
!                       of the title field of the crossreferenced entry.
  realign             Realign entries, so that field texts and perhaps equal
                        signs (depending on the value of
                        `bibtex-align-at-equal-sign') begin in the same column.
***************
*** 145,158 ****
                        (const unify-case))))
  
  (defcustom bibtex-clean-entry-hook nil
!   "*List of functions to call when entry has been cleaned.
  Functions are called with point inside the cleaned entry, and the buffer
  narrowed to just the entry."
    :group 'bibtex
    :type 'hook)
  
  (defcustom bibtex-maintain-sorted-entries nil
!   "*If non-nil, BibTeX mode maintains all BibTeX entries in sorted order.
  Allowed non-nil values are:
  plain        All entries are sorted alphabetically.
  crossref     All entries are sorted alphabetically unless an entry has a
--- 142,155 ----
                        (const unify-case))))
  
  (defcustom bibtex-clean-entry-hook nil
!   "List of functions to call when entry has been cleaned.
  Functions are called with point inside the cleaned entry, and the buffer
  narrowed to just the entry."
    :group 'bibtex
    :type 'hook)
  
  (defcustom bibtex-maintain-sorted-entries nil
!   "If non-nil, BibTeX mode maintains all entries in sorted order.
  Allowed non-nil values are:
  plain        All entries are sorted alphabetically.
  crossref     All entries are sorted alphabetically unless an entry has a
***************
*** 168,217 ****
                   (const crossref)
                   (const entry-class)))
  
! (defvar bibtex-sort-entry-class
    '(("String")
      (catch-all)
      ("Book" "Proceedings"))
!   "*List of classes of BibTeX entry names, used for sorting entries.
  If value of `bibtex-maintain-sorted-entries' is `entry-class'
  entries are ordered according to the classes they belong to.  Each
  class contains a list of entry names.  An entry `catch-all' applies
! to all entries not explicitely mentioned.")
  
  (defcustom bibtex-sort-ignore-string-entries t
!   "*If non-nil, BibTeX @String entries are not sort-significant.
  That means they are ignored when determining ordering of the buffer
  \(e.g., sorting, locating alphabetical position for new entries, etc.)."
    :group 'bibtex
    :type 'boolean)
  
  (defcustom bibtex-field-kill-ring-max 20
!   "*Max length of `bibtex-field-kill-ring' before discarding oldest elements."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-entry-kill-ring-max 20
!   "*Max length of `bibtex-entry-kill-ring' before discarding oldest elements."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-parse-keys-timeout 60
!   "*Specify interval for parsing BibTeX buffers.
! All BibTeX buffers in Emacs are parsed if Emacs has been idle
! `bibtex-parse-keys-timeout' seconds.  Only buffers which were modified
! after last parsing and which are maintained in sorted order are parsed."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-parse-keys-fast t
!   "*If non-nil, use fast but simplified algorithm for parsing BibTeX keys.
  If parsing fails, try to set this variable to nil."
    :group 'bibtex
    :type 'boolean)
  
  (defvar bibtex-entry-field-alist
!   '(
!     ("Article"
       ((("author" "Author1 [and Author2 ...] [and others]")
         ("title" "Title of the article (BibTeX converts it to lowercase)")
         ("journal" "Name of the journal (use string, remove braces)")
--- 165,215 ----
                   (const crossref)
                   (const entry-class)))
  
! (defcustom bibtex-sort-entry-class
    '(("String")
      (catch-all)
      ("Book" "Proceedings"))
!   "List of classes of BibTeX entry names, used for sorting entries.
  If value of `bibtex-maintain-sorted-entries' is `entry-class'
  entries are ordered according to the classes they belong to.  Each
  class contains a list of entry names.  An entry `catch-all' applies
! to all entries not explicitely mentioned."
!   :group 'BibTeX
!   :type '(repeat (choice :tag "Class"
!                          (const :tag "catch-all" (catch-all))
!                          (repeat :tag "Entry name" string))))
  
  (defcustom bibtex-sort-ignore-string-entries t
!   "If non-nil, BibTeX @String entries are not sort-significant.
  That means they are ignored when determining ordering of the buffer
  \(e.g., sorting, locating alphabetical position for new entries, etc.)."
    :group 'bibtex
    :type 'boolean)
  
  (defcustom bibtex-field-kill-ring-max 20
!   "Max length of `bibtex-field-kill-ring' before discarding oldest elements."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-entry-kill-ring-max 20
!   "Max length of `bibtex-entry-kill-ring' before discarding oldest elements."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-parse-keys-timeout 60
!   "Time interval in seconds for parsing BibTeX buffers during idle time.
! Parsing initializes `bibtex-reference-keys' and `bibtex-strings'."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-parse-keys-fast t
!   "If non-nil, use fast but simplified algorithm for parsing BibTeX keys.
  If parsing fails, try to set this variable to nil."
    :group 'bibtex
    :type 'boolean)
  
  (defvar bibtex-entry-field-alist
!   '(("Article"
       ((("author" "Author1 [and Author2 ...] [and others]")
         ("title" "Title of the article (BibTeX converts it to lowercase)")
         ("journal" "Name of the journal (use string, remove braces)")
***************
*** 231,238 ****
         ("month" "Month of the publication as a string (remove braces)")
         ("note" "Remarks to be put at the end of the \\bibitem"))))
      ("Book"
!      ((("author" "Author1 [and Author2 ...] [and others]" "" t)
!        ("editor" "Editor1 [and Editor2 ...] [and others]" "" t)
         ("title" "Title of the book")
         ("publisher" "Publishing company")
         ("year" "Year of publication"))
--- 229,236 ----
         ("month" "Month of the publication as a string (remove braces)")
         ("note" "Remarks to be put at the end of the \\bibitem"))))
      ("Book"
!      ((("author" "Author1 [and Author2 ...] [and others]" nil t)
!        ("editor" "Editor1 [and Editor2 ...] [and others]" nil t)
         ("title" "Title of the book")
         ("publisher" "Publishing company")
         ("year" "Year of publication"))
***************
*** 243,250 ****
         ("edition" "Edition of the book as a capitalized English word")
         ("month" "Month of the publication as a string (remove braces)")
         ("note" "Remarks to be put at the end of the \\bibitem")))
!      ((("author" "Author1 [and Author2 ...] [and others]" "" t)
!        ("editor" "Editor1 [and Editor2 ...] [and others]" "" t)
         ("title" "Title of the book"))
        (("publisher" "Publishing company")
         ("year" "Year of publication")
--- 241,248 ----
         ("edition" "Edition of the book as a capitalized English word")
         ("month" "Month of the publication as a string (remove braces)")
         ("note" "Remarks to be put at the end of the \\bibitem")))
!      ((("author" "Author1 [and Author2 ...] [and others]" nil t)
!        ("editor" "Editor1 [and Editor2 ...] [and others]" nil t)
         ("title" "Title of the book"))
        (("publisher" "Publishing company")
         ("year" "Year of publication")
***************
*** 264,271 ****
         ("year" "Year of publication")
         ("note" "Remarks to be put at the end of the \\bibitem"))))
      ("InBook"
!      ((("author" "Author1 [and Author2 ...] [and others]" "" t)
!        ("editor" "Editor1 [and Editor2 ...] [and others]" "" t)
         ("title" "Title of the book")
         ("chapter" "Chapter in the book")
         ("publisher" "Publishing company")
--- 262,269 ----
         ("year" "Year of publication")
         ("note" "Remarks to be put at the end of the \\bibitem"))))
      ("InBook"
!      ((("author" "Author1 [and Author2 ...] [and others]" nil t)
!        ("editor" "Editor1 [and Editor2 ...] [and others]" nil t)
         ("title" "Title of the book")
         ("chapter" "Chapter in the book")
         ("publisher" "Publishing company")
***************
*** 279,286 ****
         ("month" "Month of the publication as a string (remove braces)")
         ("pages" "Pages in the book")
         ("note" "Remarks to be put at the end of the \\bibitem")))
!      ((("author" "Author1 [and Author2 ...] [and others]" "" t)
!        ("editor" "Editor1 [and Editor2 ...] [and others]" "" t)
         ("title" "Title of the book")
         ("chapter" "Chapter in the book"))
        (("pages" "Pages in the book")
--- 277,284 ----
         ("month" "Month of the publication as a string (remove braces)")
         ("pages" "Pages in the book")
         ("note" "Remarks to be put at the end of the \\bibitem")))
!      ((("author" "Author1 [and Author2 ...] [and others]" nil t)
!        ("editor" "Editor1 [and Editor2 ...] [and others]" nil t)
         ("title" "Title of the book")
         ("chapter" "Chapter in the book"))
        (("pages" "Pages in the book")
***************
*** 419,450 ****
         ("title" "Title of the unpublished work (BibTeX converts it to 
lowercase)")
         ("note" "Remarks to be put at the end of the \\bibitem"))
        (("month" "Month of the publication as a string (remove braces)")
!        ("year" "Year of publication"))))
!     )
  
!   "Defines entry types and their associated fields.
! List of
! \(ENTRY-NAME (REQUIRED OPTIONAL) (CROSSREF-REQUIRED CROSSREF-OPTIONAL))
! triples.
! If the third element is nil, the first pair is always used.
! If not, the second pair is used in the case of presence of a crossref
! field and the third in the case of absence.
  REQUIRED, OPTIONAL, CROSSREF-REQUIRED and CROSSREF-OPTIONAL are lists.
  Each element of these lists is a list of the form
  \(FIELD-NAME COMMENT-STRING INIT ALTERNATIVE-FLAG).
  COMMENT-STRING, INIT, and ALTERNATIVE-FLAG are optional.
! FIELD-NAME is the name of the field, COMMENT-STRING the comment to
! appear in the echo area, INIT is either the initial content of the
  field or a function, which is called to determine the initial content
  of the field, and ALTERNATIVE-FLAG (either nil or t) marks if the
  field is an alternative.  ALTERNATIVE-FLAG may be t only in the
  REQUIRED or CROSSREF-REQUIRED lists.")
  
! (defvar bibtex-comment-start "@Comment"
!   "String starting a BibTeX comment.")
  
  (defcustom bibtex-add-entry-hook nil
!   "List of functions to call when entry has been inserted."
    :group 'bibtex
    :type 'hook)
  
--- 417,450 ----
         ("title" "Title of the unpublished work (BibTeX converts it to 
lowercase)")
         ("note" "Remarks to be put at the end of the \\bibitem"))
        (("month" "Month of the publication as a string (remove braces)")
!        ("year" "Year of publication")))))
  
!   "List of BibTeX entry types and their associated fields.
! List elements are triples
! \(ENTRY-NAME (REQUIRED OPTIONAL) (CROSSREF-REQUIRED CROSSREF-OPTIONAL)).
! ENTRY-NAME is the name of a BibTeX entry.  The remaining pairs contain
! the required and optional fields of the BibTeX entry.
! The second pair is used if a crossref field is present
! and the first pair is used if a crossref field is absent.
! If the second pair is nil, the first pair is always used.
  REQUIRED, OPTIONAL, CROSSREF-REQUIRED and CROSSREF-OPTIONAL are lists.
  Each element of these lists is a list of the form
  \(FIELD-NAME COMMENT-STRING INIT ALTERNATIVE-FLAG).
  COMMENT-STRING, INIT, and ALTERNATIVE-FLAG are optional.
! FIELD-NAME is the name of the field, COMMENT-STRING is the comment that
! appears in the echo area, INIT is either the initial content of the
  field or a function, which is called to determine the initial content
  of the field, and ALTERNATIVE-FLAG (either nil or t) marks if the
  field is an alternative.  ALTERNATIVE-FLAG may be t only in the
  REQUIRED or CROSSREF-REQUIRED lists.")
  
! (defcustom bibtex-comment-start "@Comment"
!   "String starting a BibTeX comment."
!   :group 'bibtex
!   :type 'string)
  
  (defcustom bibtex-add-entry-hook nil
!   "List of functions to call when BibTeX entry has been inserted."
    :group 'bibtex
    :type 'hook)
  
***************
*** 497,505 ****
                         (string :tag "String expansion"))))
  
  (defcustom bibtex-string-files nil
!   "*List of BibTeX files containing string definitions.
! List elements can be absolute file names or file names relative to the
! directories specified in `bibtex-string-file-path'."
    :group 'bibtex
    :type '(repeat file))
  
--- 497,505 ----
                         (string :tag "String expansion"))))
  
  (defcustom bibtex-string-files nil
!   "List of BibTeX files containing string definitions.
! List elements can be absolute file names or file names relative
! to the directories specified in `bibtex-string-file-path'."
    :group 'bibtex
    :type '(repeat file))
  
***************
*** 507,513 ****
    "*Colon separated list of paths to search for `bibtex-string-files'.")
  
  (defcustom bibtex-files nil
!   "*List of BibTeX files checked for duplicate keys.
  List elements can be absolute file names or file names relative to the
  directories specified in `bibtex-file-path'.  If an element is a directory,
  check all BibTeX files in this directory.  If an element is the symbol
--- 507,513 ----
    "*Colon separated list of paths to search for `bibtex-string-files'.")
  
  (defcustom bibtex-files nil
!   "List of BibTeX files that are searched for entry keys.
  List elements can be absolute file names or file names relative to the
  directories specified in `bibtex-file-path'.  If an element is a directory,
  check all BibTeX files in this directory.  If an element is the symbol
***************
*** 519,536 ****
    "*Colon separated list of paths to search for `bibtex-files'.")
  
  (defcustom bibtex-help-message t
!   "*If non-nil print help messages in the echo area on entering a new field."
    :group 'bibtex
    :type 'boolean)
  
  (defcustom bibtex-autokey-prefix-string ""
!   "*String to use as a prefix for all generated keys.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'string)
  
  (defcustom bibtex-autokey-names 1
!   "*Number of names to use for the automatically generated reference key.
  Possibly more names are used according to `bibtex-autokey-names-stretch'.
  If this variable is nil, all names are used.
  See `bibtex-generate-autokey' for details."
--- 519,536 ----
    "*Colon separated list of paths to search for `bibtex-files'.")
  
  (defcustom bibtex-help-message t
!   "If non-nil print help messages in the echo area on entering a new field."
    :group 'bibtex
    :type 'boolean)
  
  (defcustom bibtex-autokey-prefix-string ""
!   "String prefix for automatically generated reference keys.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'string)
  
  (defcustom bibtex-autokey-names 1
!   "Number of names to use for the automatically generated reference key.
  Possibly more names are used according to `bibtex-autokey-names-stretch'.
  If this variable is nil, all names are used.
  See `bibtex-generate-autokey' for details."
***************
*** 539,552 ****
                   integer))
  
  (defcustom bibtex-autokey-names-stretch 0
!   "*Number of names that can additionally be used.
  These names are used only, if all names are used then.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'integer)
  
  (defcustom bibtex-autokey-additional-names ""
!   "*String to prepend to the generated key if not all names could be used.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'string)
--- 539,552 ----
                   integer))
  
  (defcustom bibtex-autokey-names-stretch 0
!   "Number of names that can additionally be used for reference keys.
  These names are used only, if all names are used then.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'integer)
  
  (defcustom bibtex-autokey-additional-names ""
!   "String to append to the generated key if not all names could be used.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'string)
***************
*** 581,587 ****
  (defcustom bibtex-autokey-name-change-strings
    bibtex-autokey-transcriptions
    "Alist of (OLD-REGEXP . NEW-STRING) pairs.
! Any part of name matching a OLD-REGEXP is replaced by NEW-STRING.
  Case is significant in OLD-REGEXP.  All regexps are tried in the
  order in which they appear in the list.
  See `bibtex-generate-autokey' for details."
--- 581,587 ----
  (defcustom bibtex-autokey-name-change-strings
    bibtex-autokey-transcriptions
    "Alist of (OLD-REGEXP . NEW-STRING) pairs.
! Any part of a name matching OLD-REGEXP is replaced by NEW-STRING.
  Case is significant in OLD-REGEXP.  All regexps are tried in the
  order in which they appear in the list.
  See `bibtex-generate-autokey' for details."
***************
*** 590,596 ****
                         (string :tag "New"))))
  
  (defcustom bibtex-autokey-name-case-convert 'downcase
!   "*Function called for each name to perform case conversion.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type '(choice (const :tag "Preserve case" identity)
--- 590,596 ----
                         (string :tag "New"))))
  
  (defcustom bibtex-autokey-name-case-convert 'downcase
!   "Function called for each name to perform case conversion.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type '(choice (const :tag "Preserve case" identity)
***************
*** 600,606 ****
                   (function :tag "Conversion function")))
  
  (defcustom bibtex-autokey-name-length 'infty
!   "*Number of characters from name to incorporate into key.
  If this is set to anything but a number, all characters are used.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
--- 600,606 ----
                   (function :tag "Conversion function")))
  
  (defcustom bibtex-autokey-name-length 'infty
!   "Number of characters from name to incorporate into key.
  If this is set to anything but a number, all characters are used.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
***************
*** 608,626 ****
                   integer))
  
  (defcustom bibtex-autokey-name-separator ""
!   "*String that comes between any two names in the key.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'string)
  
  (defcustom bibtex-autokey-year-length 2
!   "*Number of rightmost digits from the year field to incorporate into key.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'integer)
  
  (defcustom bibtex-autokey-use-crossref t
!   "*If non-nil use fields from crossreferenced entry if necessary.
  If this variable is non-nil and some field has no entry, but a
  valid crossref entry, the field from the crossreferenced entry is used.
  See `bibtex-generate-autokey' for details."
--- 608,626 ----
                   integer))
  
  (defcustom bibtex-autokey-name-separator ""
!   "String that comes between any two names in the key.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'string)
  
  (defcustom bibtex-autokey-year-length 2
!   "Number of rightmost digits from the year field to incorporate into key.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'integer)
  
  (defcustom bibtex-autokey-use-crossref t
!   "If non-nil use fields from crossreferenced entry if necessary.
  If this variable is non-nil and some field has no entry, but a
  valid crossref entry, the field from the crossreferenced entry is used.
  See `bibtex-generate-autokey' for details."
***************
*** 628,634 ****
    :type 'boolean)
  
  (defcustom bibtex-autokey-titlewords 5
!   "*Number of title words to use for the automatically generated reference 
key.
  If this is set to anything but a number, all title words are used.
  Possibly more words from the title are used according to
  `bibtex-autokey-titlewords-stretch'.
--- 628,634 ----
    :type 'boolean)
  
  (defcustom bibtex-autokey-titlewords 5
!   "Number of title words to use for the automatically generated reference key.
  If this is set to anything but a number, all title words are used.
  Possibly more words from the title are used according to
  `bibtex-autokey-titlewords-stretch'.
***************
*** 637,652 ****
    :type '(choice (const :tag "All" infty)
                   integer))
  
! (defcustom bibtex-autokey-title-terminators
!   '("\\." "!"  "\\?" ":" ";" "--")
!   "*Regexp list defining the termination of the main part of the title.
! Case of the regexps is ignored.
! See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
!   :type '(repeat regexp))
  
  (defcustom bibtex-autokey-titlewords-stretch 2
!   "*Number of words that can additionally be used from the title.
  These words are used only, if a sentence from the title can be ended then.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
--- 637,650 ----
    :type '(choice (const :tag "All" infty)
                   integer))
  
! (defcustom bibtex-autokey-title-terminators "[.!?:;]\\|--"
!   "Regexp defining the termination of the main part of the title.
! Case of the regexps is ignored.  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
!   :type 'regexp)
  
  (defcustom bibtex-autokey-titlewords-stretch 2
!   "Number of words that can additionally be used from the title.
  These words are used only, if a sentence from the title can be ended then.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
***************
*** 655,661 ****
  (defcustom bibtex-autokey-titleword-ignore
    '("A" "An" "On" "The" "Eine?" "Der" "Die" "Das"
      "[^A-Z].*" ".*[^A-Z0-9].*")
!   "*Determines words from the title that are not to be used in the key.
  Each item of the list is a regexp.  If a word of the title matchs a
  regexp from that list, it is not included in the title part of the key.
  See `bibtex-generate-autokey' for details."
--- 653,659 ----
  (defcustom bibtex-autokey-titleword-ignore
    '("A" "An" "On" "The" "Eine?" "Der" "Die" "Das"
      "[^A-Z].*" ".*[^A-Z0-9].*")
!   "Determines words from the title that are not to be used in the key.
  Each item of the list is a regexp.  If a word of the title matchs a
  regexp from that list, it is not included in the title part of the key.
  See `bibtex-generate-autokey' for details."
***************
*** 663,669 ****
    :type '(repeat regexp))
  
  (defcustom bibtex-autokey-titleword-case-convert 'downcase
!   "*Function called for each titleword to perform case conversion.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type '(choice (const :tag "Preserve case" identity)
--- 661,667 ----
    :type '(repeat regexp))
  
  (defcustom bibtex-autokey-titleword-case-convert 'downcase
!   "Function called for each titleword to perform case conversion.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type '(choice (const :tag "Preserve case" identity)
***************
*** 673,679 ****
                   (function :tag "Conversion function")))
  
  (defcustom bibtex-autokey-titleword-abbrevs nil
!   "*Determines exceptions to the usual abbreviation mechanism.
  An alist of (OLD-REGEXP . NEW-STRING) pairs.  Case is ignored
  in matching against OLD-REGEXP, and the first matching pair is used.
  See `bibtex-generate-autokey' for details."
--- 671,677 ----
                   (function :tag "Conversion function")))
  
  (defcustom bibtex-autokey-titleword-abbrevs nil
!   "Determines exceptions to the usual abbreviation mechanism.
  An alist of (OLD-REGEXP . NEW-STRING) pairs.  Case is ignored
  in matching against OLD-REGEXP, and the first matching pair is used.
  See `bibtex-generate-autokey' for details."
***************
*** 693,699 ****
                         (string :tag "New"))))
  
  (defcustom bibtex-autokey-titleword-length 5
!   "*Number of characters from title words to incorporate into key.
  If this is set to anything but a number, all characters are used.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
--- 691,697 ----
                         (string :tag "New"))))
  
  (defcustom bibtex-autokey-titleword-length 5
!   "Number of characters from title words to incorporate into key.
  If this is set to anything but a number, all characters are used.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
***************
*** 701,770 ****
                   integer))
  
  (defcustom bibtex-autokey-titleword-separator "_"
!   "*String to be put between the title words.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'string)
  
  (defcustom bibtex-autokey-name-year-separator ""
!   "*String to be put between name part and year part of key.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'string)
  
  (defcustom bibtex-autokey-year-title-separator ":_"
!   "*String to be put between name part and year part of key.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'string)
  
  (defcustom bibtex-autokey-edit-before-use t
!   "*If non-nil, user is allowed to edit the generated key before it is used."
    :group 'bibtex-autokey
    :type 'boolean)
  
  (defcustom bibtex-autokey-before-presentation-function nil
!   "*Function to call before the generated key is presented.
! If non-nil this should be a function which is called before the generated key
! is presented.  The function must take one argument (the automatically
! generated key), and must return a string (the key to use)."
    :group 'bibtex-autokey
    :type '(choice (const nil) function))
  
  (defcustom bibtex-entry-offset 0
!   "*Offset for BibTeX entries.
  Added to the value of all other variables which determine colums."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-field-indentation 2
!   "*Starting column for the name part in BibTeX fields."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-text-indentation
    (+ bibtex-field-indentation
       (length "organization = "))
!   "*Starting column for the text part in BibTeX fields.
  Should be equal to the space needed for the longest name part."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-contline-indentation
    (+ bibtex-text-indentation 1)
!   "*Starting column for continuation lines of BibTeX fields."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-align-at-equal-sign nil
!   "*If non-nil, align fields at equal sign instead of field text.
  If non-nil, the column for the equal sign is the value of
  `bibtex-text-indentation', minus 2."
    :group 'bibtex
    :type 'boolean)
  
  (defcustom bibtex-comma-after-last-field nil
!   "*If non-nil, a comma is put at end of last field in the entry template."
    :group 'bibtex
    :type 'boolean)
  
--- 699,767 ----
                   integer))
  
  (defcustom bibtex-autokey-titleword-separator "_"
!   "String to be put between the title words.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'string)
  
  (defcustom bibtex-autokey-name-year-separator ""
!   "String to be put between name part and year part of key.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'string)
  
  (defcustom bibtex-autokey-year-title-separator ":_"
!   "String to be put between name part and year part of key.
  See `bibtex-generate-autokey' for details."
    :group 'bibtex-autokey
    :type 'string)
  
  (defcustom bibtex-autokey-edit-before-use t
!   "If non-nil, user is allowed to edit the generated key before it is used."
    :group 'bibtex-autokey
    :type 'boolean)
  
  (defcustom bibtex-autokey-before-presentation-function nil
!   "If non-nil, function to call before generated key is presented.
! The function must take one argument (the automatically generated key),
! and must return a string (the key to use)."
    :group 'bibtex-autokey
    :type '(choice (const nil) function))
  
  (defcustom bibtex-entry-offset 0
!   "Offset for BibTeX entries.
  Added to the value of all other variables which determine colums."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-field-indentation 2
!   "Starting column for the name part in BibTeX fields."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-text-indentation
    (+ bibtex-field-indentation
       (length "organization = "))
!   "Starting column for the text part in BibTeX fields.
  Should be equal to the space needed for the longest name part."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-contline-indentation
    (+ bibtex-text-indentation 1)
!   "Starting column for continuation lines of BibTeX fields."
    :group 'bibtex
    :type 'integer)
  
  (defcustom bibtex-align-at-equal-sign nil
!   "If non-nil, align fields at equal sign instead of field text.
  If non-nil, the column for the equal sign is the value of
  `bibtex-text-indentation', minus 2."
    :group 'bibtex
    :type 'boolean)
  
  (defcustom bibtex-comma-after-last-field nil
!   "If non-nil, a comma is put at end of last field in the entry template."
    :group 'bibtex
    :type 'boolean)
  
***************
*** 781,787 ****
  (defcustom bibtex-summary-function 'bibtex-summary
    "Function to call for generating a one-line summary of a BibTeX entry.
  It takes one argument, the key of the entry.
! Used by `bibtex-complete-key-cleanup' and `bibtex-copy-summary-as-kill'."
    :group 'bibtex
    :type '(choice (const :tag "Default" bibtex-summary)
                   (function :tag "Personalized function")))
--- 778,784 ----
  (defcustom bibtex-summary-function 'bibtex-summary
    "Function to call for generating a one-line summary of a BibTeX entry.
  It takes one argument, the key of the entry.
! Used by `bibtex-complete-crossref-cleanup' and `bibtex-copy-summary-as-kill'."
    :group 'bibtex
    :type '(choice (const :tag "Default" bibtex-summary)
                   (function :tag "Personalized function")))
***************
*** 790,796 ****
    '((("url" . ".*:.*"))
      ;; Example of a complex setup.
      (("journal" . "\\<\\(PR[ABCDEL]?\\|RMP\\)\\>")
!      "http://publish.aps.org/abstract/";
       ("journal" ".*" downcase)
       "/v"
       ("volume" ".*" 0)
--- 787,793 ----
    '((("url" . ".*:.*"))
      ;; Example of a complex setup.
      (("journal" . "\\<\\(PR[ABCDEL]?\\|RMP\\)\\>")
!      "http://link.aps.org/abstract/";
       ("journal" ".*" downcase)
       "/v"
       ("volume" ".*" 0)
***************
*** 803,810 ****
  
  FIELD is a field name as returned by `bibtex-parse-entry'.
  REGEXP is matched against the text of FIELD.  If the match succeeds, then
! this scheme will be used.  If no STEPS are specified the matched text is used
! as the URL, otherwise the URL is built by concatenating the STEPS.
  
  A STEP can be a string or a list (FIELD REGEXP REPLACE) in which case
  the text of FIELD is matched against REGEXP, and is replaced with REPLACE.
--- 800,807 ----
  
  FIELD is a field name as returned by `bibtex-parse-entry'.
  REGEXP is matched against the text of FIELD.  If the match succeeds, then
! this scheme is used.  If no STEPs are specified the matched text is used
! as the URL, otherwise the URL is built by concatenating the STEPs.
  
  A STEP can be a string or a list (FIELD REGEXP REPLACE) in which case
  the text of FIELD is matched against REGEXP, and is replaced with REPLACE.
***************
*** 862,867 ****
--- 859,865 ----
      (define-key km "\C-c\C-c" 'bibtex-clean-entry)
      (define-key km "\C-c\C-q" 'bibtex-fill-entry)
      (define-key km "\C-c\C-s" 'bibtex-find-entry)
+     (define-key km "\C-c\C-x" 'bibtex-find-crossref)
      (define-key km "\C-c\C-t" 'bibtex-copy-summary-as-kill)
      (define-key km "\C-c?" 'bibtex-print-help-message)
      (define-key km "\C-c\C-p" 'bibtex-pop-previous)
***************
*** 913,924 ****
       ["End of Field" bibtex-find-text t]
       ["Next Field" bibtex-next-field t]
       ["Beginning of Entry" bibtex-beginning-of-entry t]
!      ["End of Entry" bibtex-end-of-entry t])
!     ("Moving in BibTeX Buffer"
       ["Find Entry" bibtex-find-entry t]
       ["Find Crossref Entry" bibtex-find-crossref t])
-     ("Moving between BibTeX Buffers"
-      ["Find Entry Globally" bibtex-find-entry-globally t])
      "--"
      ("Operating on Current Field"
       ["Fill Field" fill-paragraph t]
--- 911,922 ----
       ["End of Field" bibtex-find-text t]
       ["Next Field" bibtex-next-field t]
       ["Beginning of Entry" bibtex-beginning-of-entry t]
!      ["End of Entry" bibtex-end-of-entry t]
!     "--"
!      ["Make Entry Visible" bibtex-reposition-window t])
!     ("Moving in BibTeX Buffers"
       ["Find Entry" bibtex-find-entry t]
       ["Find Crossref Entry" bibtex-find-crossref t])
      "--"
      ("Operating on Current Field"
       ["Fill Field" fill-paragraph t]
***************
*** 950,959 ****
--- 948,960 ----
       ["Paste Previously Killed Entry" bibtex-yank-pop t]
       "--"
       ["Copy Summary to Kill Ring" bibtex-copy-summary-as-kill t]
+      ["Browse URL" bibtex-url t]
       "--"
       ["Ispell Entry" bibtex-ispell-entry t]
       ["Ispell Entry Abstract" bibtex-ispell-abstract t]
+      "--"
       ["Narrow to Entry" bibtex-narrow-to-entry t]
+      ["Mark Entry" bibtex-mark-entry t]
       "--"
       ["View Cite Locations (RefTeX)" reftex-view-crossref-from-bibtex
        (fboundp 'reftex-view-crossref-from-bibtex)])
***************
*** 983,988 ****
--- 984,990 ----
          ["Technical Manual" bibtex-Manual t]
          ["Unpublished" bibtex-Unpublished t]
          ["Miscellaneous" bibtex-Misc t]
+         "--"
          ["String" bibtex-String t]
          ["Preamble" bibtex-Preamble t]))
  
***************
*** 1085,1096 ****
  (defconst bibtex-key-in-head 2
    "Regexp subexpression number of the key part in `bibtex-entry-head'.")
  
  (defconst bibtex-entry-postfix "[ \t\n]*,?[ \t\n]*[})]"
    "Regexp matching the postfix of a BibTeX entry.")
  
  (defvar bibtex-known-entry-type-re
    (regexp-opt (mapcar 'car bibtex-entry-field-alist))
!   "Regexp matching the name of a BibTeX entry type.")
  
  (defvar bibtex-valid-entry-re
    (concat "@[ \t]*\\(" bibtex-known-entry-type-re "\\)")
--- 1087,1104 ----
  (defconst bibtex-key-in-head 2
    "Regexp subexpression number of the key part in `bibtex-entry-head'.")
  
+ (defconst bibtex-string-maybe-empty-head
+   (concat "^[ \t]*\\(@String\\)[ \t]*[({]\\("
+           bibtex-reference-key
+           "\\)?")
+   "Regexp matching the header line of a BibTeX String entry.")
+ 
  (defconst bibtex-entry-postfix "[ \t\n]*,?[ \t\n]*[})]"
    "Regexp matching the postfix of a BibTeX entry.")
  
  (defvar bibtex-known-entry-type-re
    (regexp-opt (mapcar 'car bibtex-entry-field-alist))
!   "Regexp matching the name of a BibTeX entry.")
  
  (defvar bibtex-valid-entry-re
    (concat "@[ \t]*\\(" bibtex-known-entry-type-re "\\)")
***************
*** 1133,1139 ****
  
  (defvar bibtex-font-lock-url-regexp
    ;; Assume that field names begin at the beginning of a line.
!   (concat "^[ \t]*" (regexp-opt (mapcar 'caar bibtex-generate-url-list) t)
            "[ \t]*=[ \t]*")
    "Regexp for `bibtex-font-lock-url'.")
  
--- 1141,1148 ----
  
  (defvar bibtex-font-lock-url-regexp
    ;; Assume that field names begin at the beginning of a line.
!   (concat "^[ \t]*"
!           (regexp-opt (delete-dups (mapcar 'caar bibtex-generate-url-list)) t)
            "[ \t]*=[ \t]*")
    "Regexp for `bibtex-font-lock-url'.")
  
***************
*** 1226,1232 ****
    "Syntax-table to parse matched quotes.")
  
  (defun bibtex-parse-field-string ()
!   "Parse a field string enclosed by braces or quotes.
  If a syntactically correct string is found, a pair containing the start and
  end position of the field string is returned, nil otherwise."
    (let ((end-point
--- 1235,1241 ----
    "Syntax-table to parse matched quotes.")
  
  (defun bibtex-parse-field-string ()
!   "Parse a BibTeX field string enclosed by braces or quotes.
  If a syntactically correct string is found, a pair containing the start and
  end position of the field string is returned, nil otherwise."
    (let ((end-point
***************
*** 1273,1279 ****
                                'bibtex-parse-field-text)))
  
  (defun bibtex-search-forward-field (name &optional bound)
!   "Search forward to find a field of name NAME.
  If a syntactically correct field is found, a pair containing the boundaries of
  the name and text parts of the field is returned.  The search is limited by
  optional arg BOUND.  If BOUND is t the search is limited by the end of the
--- 1282,1288 ----
                                'bibtex-parse-field-text)))
  
  (defun bibtex-search-forward-field (name &optional bound)
!   "Search forward to find a BibTeX field of name NAME.
  If a syntactically correct field is found, a pair containing the boundaries of
  the name and text parts of the field is returned.  The search is limited by
  optional arg BOUND.  If BOUND is t the search is limited by the end of the
***************
*** 1300,1306 ****
          boundaries))))
  
  (defun bibtex-search-backward-field (name &optional bound)
!   "Search backward to find a field of name NAME.
  If a syntactically correct field is found, a pair containing the boundaries of
  the name and text parts of the field is returned.  The search is limited by
  optional arg BOUND.  If BOUND is t the search is limited by the beginning of 
the
--- 1309,1315 ----
          boundaries))))
  
  (defun bibtex-search-backward-field (name &optional bound)
!   "Search backward to find a BibTeX field of name NAME.
  If a syntactically correct field is found, a pair containing the boundaries of
  the name and text parts of the field is returned.  The search is limited by
  optional arg BOUND.  If BOUND is t the search is limited by the beginning of 
the
***************
*** 1352,1364 ****
  if present."
    (let ((content (buffer-substring-no-properties (cadr bounds)
                                                   (cddr bounds))))
!     (if (and remove-delim
!              (string-match "\\`[{\"]\\(.*\\)[}\"]\\'" content))
!         (substring content (match-beginning 1) (match-end 1))
        content)))
  
  (defun bibtex-text-in-field (field &optional follow-crossref)
!   "Get content of field FIELD of current BibTeX entry.  Return nil if not 
found.
  If optional arg FOLLOW-CROSSREF is non-nil, follow crossref."
    (save-excursion
      (save-restriction
--- 1361,1373 ----
  if present."
    (let ((content (buffer-substring-no-properties (cadr bounds)
                                                   (cddr bounds))))
!     (if remove-delim
!         (bibtex-remove-delimiters-string content)
        content)))
  
  (defun bibtex-text-in-field (field &optional follow-crossref)
!   "Get content of field FIELD of current BibTeX entry.
! Return nil if not found.
  If optional arg FOLLOW-CROSSREF is non-nil, follow crossref."
    (save-excursion
      (save-restriction
***************
*** 1458,1466 ****
  delimiters if present."
    (let ((content (buffer-substring-no-properties (nth 0 (cdr bounds))
                                                   (nth 1 (cdr bounds)))))
!     (if (and remove-delim
!              (string-match "\\`[{\"]\\(.*\\)[}\"]\\'" content))
!         (substring content (match-beginning 1) (match-end 1))
        content)))
  
  (defsubst bibtex-start-of-text-in-string (bounds)
--- 1467,1474 ----
  delimiters if present."
    (let ((content (buffer-substring-no-properties (nth 0 (cdr bounds))
                                                   (nth 1 (cdr bounds)))))
!     (if remove-delim
!         (bibtex-remove-delimiters-string content)
        content)))
  
  (defsubst bibtex-start-of-text-in-string (bounds)
***************
*** 1483,1488 ****
--- 1491,1503 ----
  
  ;; Helper Functions
  
+ (defun bibtex-remove-delimiters-string (str)
+   "Remove delimiters of string STR."
+   (if (and (memq (aref str 0) '(?\{ ?\"))
+            (memq (aref str (1- (length str))) '(?\} ?\")))
+       (substring str 1 -1)
+     str))
+ 
  (defsubst bibtex-string= (str1 str2)
    "Return t if STR1 and STR2 are equal, ignoring case."
    (eq t (compare-strings str1 0 nil str2 0 nil t)))
***************
*** 1531,1537 ****
    "Call FUN for each BibTeX entry in buffer (possibly narrowed).
  FUN is called with three arguments, the key of the entry and the buffer
  positions (marker) of beginning and end of entry.  Point is inside the entry.
! If `bibtex-sort-ignore-string-entries' is non-nil, FUN will not be called for
  @String entries."
    (let ((case-fold-search t))
      (save-excursion
--- 1546,1552 ----
    "Call FUN for each BibTeX entry in buffer (possibly narrowed).
  FUN is called with three arguments, the key of the entry and the buffer
  positions (marker) of beginning and end of entry.  Point is inside the entry.
! If `bibtex-sort-ignore-string-entries' is non-nil, FUN is not called for
  @String entries."
    (let ((case-fold-search t))
      (save-excursion
***************
*** 1552,1565 ****
    "Echo a message about progress of current buffer.
  If FLAG is a string, the message is initialized (in this case a
  value for INTERVAL may be given as well (if not this is set to 5)).
! If FLAG is done, the message is deinitialized.
  If FLAG is nil, a message is echoed if point was incremented at least
  `bibtex-progress-interval' percent since last message was echoed."
    (cond ((stringp flag)
!          (setq bibtex-progress-lastmes flag)
!          (setq bibtex-progress-interval (or interval 5)
                 bibtex-progress-lastperc 0))
!         ((equal flag 'done)
           (message  "%s (done)" bibtex-progress-lastmes)
           (setq bibtex-progress-lastmes nil))
          (t
--- 1567,1580 ----
    "Echo a message about progress of current buffer.
  If FLAG is a string, the message is initialized (in this case a
  value for INTERVAL may be given as well (if not this is set to 5)).
! If FLAG is `done', the message is deinitialized.
  If FLAG is nil, a message is echoed if point was incremented at least
  `bibtex-progress-interval' percent since last message was echoed."
    (cond ((stringp flag)
!          (setq bibtex-progress-lastmes flag
!                bibtex-progress-interval (or interval 5)
                 bibtex-progress-lastperc 0))
!         ((eq flag 'done)
           (message  "%s (done)" bibtex-progress-lastmes)
           (setq bibtex-progress-lastmes nil))
          (t
***************
*** 1574,1606 ****
  
  (defun bibtex-field-left-delimiter ()
    "Return a string dependent on `bibtex-field-delimiters'."
!   (if (equal bibtex-field-delimiters 'braces)
        "{"
      "\""))
  
  (defun bibtex-field-right-delimiter ()
    "Return a string dependent on `bibtex-field-delimiters'."
!   (if (equal bibtex-field-delimiters 'braces)
        "}"
      "\""))
  
  (defun bibtex-entry-left-delimiter ()
    "Return a string dependent on `bibtex-entry-delimiters'."
!   (if (equal bibtex-entry-delimiters 'braces)
        "{"
      "("))
  
  (defun bibtex-entry-right-delimiter ()
    "Return a string dependent on `bibtex-entry-delimiters'."
!   (if (equal bibtex-entry-delimiters 'braces)
        "}"
      ")"))
  
  (defun bibtex-search-entry (empty-head &optional bound noerror backward)
    "Search for a BibTeX entry (maybe without reference key if EMPTY-HEAD is t).
  BOUND and NOERROR are exactly as in `re-search-forward'.  If BACKWARD
! is non-nil, search is done in reverse direction.  Point is moved past the
! closing delimiter (at the beginning of entry if BACKWARD is non-nil).
  Return a cons pair with buffer positions of beginning and end of entry.
  After call to this function MATCH-BEGINNING and MATCH-END functions
  are defined, but only for the head part of the entry
--- 1589,1621 ----
  
  (defun bibtex-field-left-delimiter ()
    "Return a string dependent on `bibtex-field-delimiters'."
!   (if (eq bibtex-field-delimiters 'braces)
        "{"
      "\""))
  
  (defun bibtex-field-right-delimiter ()
    "Return a string dependent on `bibtex-field-delimiters'."
!   (if (eq bibtex-field-delimiters 'braces)
        "}"
      "\""))
  
  (defun bibtex-entry-left-delimiter ()
    "Return a string dependent on `bibtex-entry-delimiters'."
!   (if (eq bibtex-entry-delimiters 'braces)
        "{"
      "("))
  
  (defun bibtex-entry-right-delimiter ()
    "Return a string dependent on `bibtex-entry-delimiters'."
!   (if (eq bibtex-entry-delimiters 'braces)
        "}"
      ")"))
  
  (defun bibtex-search-entry (empty-head &optional bound noerror backward)
    "Search for a BibTeX entry (maybe without reference key if EMPTY-HEAD is t).
  BOUND and NOERROR are exactly as in `re-search-forward'.  If BACKWARD
! is non-nil, search in reverse direction.  Move point past the closing
! delimiter (at the beginning of entry if BACKWARD is non-nil).
  Return a cons pair with buffer positions of beginning and end of entry.
  After call to this function MATCH-BEGINNING and MATCH-END functions
  are defined, but only for the head part of the entry
***************
*** 1620,1631 ****
              (cond ((not noerror)
                     ;; yell
                     (error "Backward search of BibTeX entry failed"))
!                   ((equal noerror t)
                     ;; don't move
                     (goto-char pnt)))
              nil))
!       (let ((limit (or bound (point-max)))
!             found)
          (while (and (not found)
                      (re-search-forward entry-head-re bound noerror))
            (save-match-data
--- 1635,1646 ----
              (cond ((not noerror)
                     ;; yell
                     (error "Backward search of BibTeX entry failed"))
!                   ((eq noerror t)
                     ;; don't move
                     (goto-char pnt)))
              nil))
!       (let (found)
!         (unless bound (setq bound (point-max)))
          (while (and (not found)
                      (re-search-forward entry-head-re bound noerror))
            (save-match-data
***************
*** 1639,1647 ****
                    (infix-start (point))
                    finished bounds)
                (while (not finished)
!                 (skip-chars-forward " \t\n" limit)
                  (if (and (setq bounds (bibtex-parse-field bibtex-field-name))
!                          (<= (bibtex-end-of-field bounds) limit))
                      (setq infix-start (bibtex-end-of-field bounds))
                    (setq finished t))
                  (goto-char infix-start))
--- 1654,1662 ----
                    (infix-start (point))
                    finished bounds)
                (while (not finished)
!                 (skip-chars-forward " \t\n" bound)
                  (if (and (setq bounds (bibtex-parse-field bibtex-field-name))
!                          (<= (bibtex-end-of-field bounds) bound))
                      (setq infix-start (bibtex-end-of-field bounds))
                    (setq finished t))
                  (goto-char infix-start))
***************
*** 1649,1655 ****
                ;; that BOUND is respected.
                (when (and (looking-at bibtex-entry-postfix)
                           (eq (char-before (match-end 0)) entry-closer)
!                          (<= (match-end 0) limit))
                  (goto-char (match-end 0))
                  (setq found t)))))
          (if found
--- 1664,1670 ----
                ;; that BOUND is respected.
                (when (and (looking-at bibtex-entry-postfix)
                           (eq (char-before (match-end 0)) entry-closer)
!                          (<= (match-end 0) bound))
                  (goto-char (match-end 0))
                  (setq found t)))))
          (if found
***************
*** 1657,1663 ****
            (cond ((not noerror)
                   ;; yell
                   (error "Search of BibTeX entry failed"))
!                 ((equal noerror t)
                   ;; don't move
                   (goto-char pnt)))
            nil)))))
--- 1672,1678 ----
            (cond ((not noerror)
                   ;; yell
                   (error "Search of BibTeX entry failed"))
!                 ((eq noerror t)
                   ;; don't move
                   (goto-char pnt)))
            nil)))))
***************
*** 1727,1735 ****
  
  (defun bibtex-enclosing-field (&optional noerr)
    "Search for BibTeX field enclosing point.
! Use `match-beginning' and `match-end' to parse the field.  If NOERR is 
non-nil,
! no error is signalled.  In this case, bounds are returned on success,
! nil otherwise.  Does not move point."
    (let ((bounds (bibtex-search-backward-field bibtex-field-name t)))
      (if (and bounds
               (<= (bibtex-start-of-field bounds) (point))
--- 1742,1749 ----
  
  (defun bibtex-enclosing-field (&optional noerr)
    "Search for BibTeX field enclosing point.
! Unless NOERR is non-nil, signal an error if no enclosing field is found.
! On success return bounds, nil otherwise.  Do not move point."
    (let ((bounds (bibtex-search-backward-field bibtex-field-name t)))
      (if (and bounds
               (<= (bibtex-start-of-field bounds) (point))
***************
*** 1751,1786 ****
        (goto-char old-point)
        (error "Can't find end of enclosing BibTeX entry"))))
  
! (defun bibtex-insert-current-kill (n)
    (if (not bibtex-last-kill-command)
        (error "BibTeX kill ring is empty")
!     (let* ((kr (if (equal bibtex-last-kill-command 'field)
                     'bibtex-field-kill-ring
                   'bibtex-entry-kill-ring))
!            (kryp (if (equal bibtex-last-kill-command 'field)
                       'bibtex-field-kill-ring-yank-pointer
                     'bibtex-entry-kill-ring-yank-pointer))
!            (ARGth-kill-element (nthcdr (mod (- n (length (eval kryp)))
!                                             (length (eval kr)))
!                                        (eval kr)))
!            (current (car (set kryp ARGth-kill-element))))
!       (cond
!        ((equal bibtex-last-kill-command 'field)
!         (let (bibtex-help-message)
!           (bibtex-find-text nil t)
!           (if (looking-at "[}\"]")
!               (forward-char)))
!         (set-mark (point))
!         (message "Mark set")
!         (bibtex-make-field (list (elt current 1) nil (elt current 2)) t))
!        ((equal bibtex-last-kill-command 'entry)
          (unless (eobp) (bibtex-beginning-of-entry))
          (set-mark (point))
          (message "Mark set")
!         (insert (elt current 1)))
!        (t
!         (error "Unknown tag field: %s.  Please submit a bug report"
!                bibtex-last-kill-command))))))
  
  (defun bibtex-format-entry ()
    "Helper function for `bibtex-clean-entry'.
--- 1765,1795 ----
        (goto-char old-point)
        (error "Can't find end of enclosing BibTeX entry"))))
  
! (defun bibtex-insert-kill (n)
!   "Reinsert the Nth stretch of killed BibTeX text."
    (if (not bibtex-last-kill-command)
        (error "BibTeX kill ring is empty")
!     (let* ((kr (if (eq bibtex-last-kill-command 'field)
                     'bibtex-field-kill-ring
                   'bibtex-entry-kill-ring))
!            (kryp (if (eq bibtex-last-kill-command 'field)
                       'bibtex-field-kill-ring-yank-pointer
                     'bibtex-entry-kill-ring-yank-pointer))
!            (current (car (set kryp (nthcdr (mod (- n (length (eval kryp)))
!                                                 (length (eval kr)))
!                                            (eval kr))))))
!       (if (eq bibtex-last-kill-command 'field)
!           (let (bibtex-help-message)
!             (bibtex-find-text)
!             (if (looking-at "[}\"]")
!                 (forward-char))
!             (set-mark (point))
!             (message "Mark set")
!             (bibtex-make-field current t))
          (unless (eobp) (bibtex-beginning-of-entry))
          (set-mark (point))
          (message "Mark set")
!         (insert current)))))
  
  (defun bibtex-format-entry ()
    "Helper function for `bibtex-clean-entry'.
***************
*** 1789,1795 ****
      (save-restriction
        (bibtex-narrow-to-entry)
        (let ((case-fold-search t)
!             (format (if (equal bibtex-entry-format t)
                          '(realign opts-or-alts required-fields
                                    numerical-fields
                                    last-comma page-dashes delimiters
--- 1798,1804 ----
      (save-restriction
        (bibtex-narrow-to-entry)
        (let ((case-fold-search t)
!             (format (if (eq bibtex-entry-format t)
                          '(realign opts-or-alts required-fields
                                    numerical-fields
                                    last-comma page-dashes delimiters
***************
*** 1828,1834 ****
            (setq crossref-key (and field
                                    (not (string-match bibtex-empty-field-re
                                                       (cdr field)))
!                                   (cdr field))
                  req-field-list (if crossref-key
                                     (nth 0 (nth 2 entry-list)) ; crossref part
                                   (nth 0 (nth 1 entry-list)))) ; required part
--- 1837,1843 ----
            (setq crossref-key (and field
                                    (not (string-match bibtex-empty-field-re
                                                       (cdr field)))
!                                   (bibtex-remove-delimiters-string (cdr 
field)))
                  req-field-list (if crossref-key
                                     (nth 0 (nth 2 entry-list)) ; crossref part
                                   (nth 0 (nth 1 entry-list)))) ; required part
***************
*** 1843,1849 ****
                    (cond ((not non-empty-alternative)
                           (setq non-empty-alternative t))
                          ((memq 'required-fields format)
!                          (error "More than one non-empty alternative.")))))))
  
          (if (and alternatives-there
                   (not non-empty-alternative)
--- 1852,1858 ----
                    (cond ((not non-empty-alternative)
                           (setq non-empty-alternative t))
                          ((memq 'required-fields format)
!                          (error "More than one non-empty alternative")))))))
  
          (if (and alternatives-there
                   (not non-empty-alternative)
***************
*** 1854,1870 ****
          (goto-char (point-min))
          (while (setq bounds (bibtex-search-forward-field bibtex-field-name))
            (let* ((beg-field (copy-marker (bibtex-start-of-field bounds)))
!                  (end-field (copy-marker (bibtex-end-of-field bounds)))
                   (beg-name  (copy-marker (bibtex-start-of-name-in-field 
bounds)))
                   (end-name  (copy-marker (bibtex-end-of-name-in-field 
bounds)))
                   (beg-text  (copy-marker (bibtex-start-of-text-in-field 
bounds)))
!                  (end-text  (copy-marker (bibtex-end-of-text-in-field 
bounds)))
                   (opt-alt   (string-match "OPT\\|ALT"
!                                           (buffer-substring-no-properties 
beg-name (+ beg-name 3))))
                   (field-name (buffer-substring-no-properties
                                (if opt-alt (+ beg-name 3) beg-name) end-name))
                   (empty-field (string-match bibtex-empty-field-re
!                                             (buffer-substring-no-properties 
beg-field end-field)))
                   deleted)
  
              ;; We have more elegant high-level functions for several
--- 1863,1881 ----
          (goto-char (point-min))
          (while (setq bounds (bibtex-search-forward-field bibtex-field-name))
            (let* ((beg-field (copy-marker (bibtex-start-of-field bounds)))
!                  (end-field (copy-marker (bibtex-end-of-field bounds) t))
                   (beg-name  (copy-marker (bibtex-start-of-name-in-field 
bounds)))
                   (end-name  (copy-marker (bibtex-end-of-name-in-field 
bounds)))
                   (beg-text  (copy-marker (bibtex-start-of-text-in-field 
bounds)))
!                  (end-text  (copy-marker (bibtex-end-of-text-in-field bounds) 
t))
                   (opt-alt   (string-match "OPT\\|ALT"
!                                           (buffer-substring-no-properties
!                                            beg-name (+ beg-name 3))))
                   (field-name (buffer-substring-no-properties
                                (if opt-alt (+ beg-name 3) beg-name) end-name))
                   (empty-field (string-match bibtex-empty-field-re
!                                             (buffer-substring-no-properties
!                                              beg-field end-field)))
                   deleted)
  
              ;; We have more elegant high-level functions for several
***************
*** 1926,1935 ****
                         empty-field
                         (bibtex-string= field-name "booktitle")
                         crossref-key)
!                   (let ((title (save-restriction
!                                  (widen)
!                                  (if (bibtex-find-entry crossref-key)
!                                      (bibtex-text-in-field "title")))))
                      (when title
                        (setq empty-field nil)
                        (goto-char (1+ beg-text))
--- 1937,1947 ----
                         empty-field
                         (bibtex-string= field-name "booktitle")
                         crossref-key)
!                   (let ((title (save-excursion
!                                  (save-restriction
!                                    (widen)
!                                    (if (bibtex-find-entry crossref-key t)
!                                        (bibtex-text-in-field "title"))))))
                      (when title
                        (setq empty-field nil)
                        (goto-char (1+ beg-text))
***************
*** 2055,2061 ****
    (let ((names (bibtex-autokey-get-field "author\\|editor"
                                           bibtex-autokey-name-change-strings)))
      ;; Some entries do not have a name field.
!     (unless (string= "" names)
        (let* ((case-fold-search t)
               (name-list (mapcar 'bibtex-autokey-demangle-name
                                  (split-string names "[ \t\n]+and[ \t\n]+")))
--- 2067,2074 ----
    (let ((names (bibtex-autokey-get-field "author\\|editor"
                                           bibtex-autokey-name-change-strings)))
      ;; Some entries do not have a name field.
!     (if (string= "" names)
!         names
        (let* ((case-fold-search t)
               (name-list (mapcar 'bibtex-autokey-demangle-name
                                  (split-string names "[ \t\n]+and[ \t\n]+")))
***************
*** 2096,2104 ****
                        ;; --> take the last token
                        (match-string 1 fullname))
                       (t (error "Name `%s' is incorrectly formed" fullname)))))
!     (bibtex-autokey-abbrev
!      (funcall bibtex-autokey-name-case-convert name)
!      bibtex-autokey-name-length)))
  
  (defun bibtex-autokey-get-year ()
    "Return year field contents as a string obeying 
`bibtex-autokey-year-length'."
--- 2109,2116 ----
                        ;; --> take the last token
                        (match-string 1 fullname))
                       (t (error "Name `%s' is incorrectly formed" fullname)))))
!     (funcall bibtex-autokey-name-case-convert
!              (bibtex-autokey-abbrev name bibtex-autokey-name-length))))
  
  (defun bibtex-autokey-get-year ()
    "Return year field contents as a string obeying 
`bibtex-autokey-year-length'."
***************
*** 2114,2122 ****
           (bibtex-autokey-get-field "title"
                                     bibtex-autokey-titleword-change-strings)))
      ;; ignore everything past a terminator
!     (dolist (terminator bibtex-autokey-title-terminators)
!       (if (string-match terminator titlestring)
!           (setq titlestring (substring titlestring 0 (match-beginning 0)))))
      ;; gather words from titlestring into a list.  Ignore
      ;; specific words and use only a specific amount of words.
      (let ((counter 0)
--- 2126,2133 ----
           (bibtex-autokey-get-field "title"
                                     bibtex-autokey-titleword-change-strings)))
      ;; ignore everything past a terminator
!     (if (string-match bibtex-autokey-title-terminators titlestring)
!         (setq titlestring (substring titlestring 0 (match-beginning 0))))
      ;; gather words from titlestring into a list.  Ignore
      ;; specific words and use only a specific amount of words.
      (let ((counter 0)
***************
*** 2135,2144 ****
                                                           "\\)\\'") word)))
                      (setq lst (cdr lst)))
                    lst)
!           (setq word (funcall bibtex-autokey-titleword-case-convert word)
!                 counter (1+ counter))
            (if (or (not (numberp bibtex-autokey-titlewords))
!                   (< counter bibtex-autokey-titlewords))
                (push word titlewords)
              (push word titlewords-extra))))
        ;; Obey bibtex-autokey-titlewords-stretch:
--- 2146,2154 ----
                                                           "\\)\\'") word)))
                      (setq lst (cdr lst)))
                    lst)
!           (setq counter (1+ counter))
            (if (or (not (numberp bibtex-autokey-titlewords))
!                   (<= counter bibtex-autokey-titlewords))
                (push word titlewords)
              (push word titlewords-extra))))
        ;; Obey bibtex-autokey-titlewords-stretch:
***************
*** 2161,2243 ****
        (setq alist (cdr alist)))
      (if alist
          (cdar alist)
!       (bibtex-autokey-abbrev titleword
!                              bibtex-autokey-titleword-length))))
  
  (defun bibtex-generate-autokey ()
!   "Generate automatically a key from the author/editor and the title field.
! This will only work for entries where each field begins on a separate line.
! The generation algorithm works as follows:
!  1. Use the value of `bibtex-autokey-prefix-string' as a prefix.
!  2. If there is a non-empty author (preferred) or editor field,
!     use it as the name part of the key.
!  3. Change any substring found in
!     `bibtex-autokey-name-change-strings' to the corresponding new
!     one (see documentation of this variable for further detail).
!  4. For every of at least first `bibtex-autokey-names' names in
!     the name field, determine the last name.  If there are maximal
!     `bibtex-autokey-names' + `bibtex-autokey-names-stretch'
!     names, all names are used.
!  5. From every last name, take at least `bibtex-autokey-name-length'
!     characters (abort only after a consonant or at a word end).
!  6. Convert all last names according to the conversion function
      `bibtex-autokey-name-case-convert'.
!  7. Build the name part of the key by concatenating all
!     abbreviated last names with the string
!     `bibtex-autokey-name-separator' between any two.  If there are
!     more names than are used in the name part, prepend the string
!     contained in `bibtex-autokey-additional-names'.
!  8. Build the year part of the key by truncating the contents of
!     the year field to the rightmost `bibtex-autokey-year-length'
!     digits (useful values are 2 and 4).  If the year field (or any
!     other field required to generate the key) is absent, but the entry
!     has a valid crossref field and the variable
      `bibtex-autokey-use-crossref' is non-nil, use the field of the
      crossreferenced entry instead.
!  9. For the title part of the key change the contents of the
!     title field of the entry according to
!     `bibtex-autokey-titleword-change-strings' to the
!     corresponding new one (see documentation of this variable for
!     further detail).
! 10. Abbreviate the result to the string up to (but not including)
!     the first occurrence of a regexp matched by the items of
!     `bibtex-autokey-title-terminators' and delete those words which
!     appear in `bibtex-autokey-titleword-ignore'.
!     Build the title part of the key by using at least the first
!     `bibtex-autokey-titlewords' words from this
!     abbreviated title.  If the abbreviated title ends after
!     maximal `bibtex-autokey-titlewords' +
!     `bibtex-autokey-titlewords-stretch' words, all
!     words from the abbreviated title are used.
! 11. Convert all used titlewords according to the conversion function
      `bibtex-autokey-titleword-case-convert'.
! 12. For every used title word that appears in
!     `bibtex-autokey-titleword-abbrevs' use the corresponding
!     abbreviation (see documentation of this variable for further
!     detail).
! 13. From every title word not generated by an abbreviation, take
!     at least `bibtex-autokey-titleword-length' characters (abort
!     only after a consonant or at a word end).
! 14. Build the title part of the key by concatenating all
!     abbreviated title words with the string
!     `bibtex-autokey-titleword-separator' between any two.
! 15. At least, to get the key, concatenate
!     `bibtex-autokey-prefix-string', the name part, the year part
!     and the title part with `bibtex-autokey-name-year-separator'
!     between the name part and the year part if both are non-empty
!     and `bibtex-autokey-year-title-separator' between the year
!     part and the title part if both are non-empty.  If the year
!     part is empty, but not the other two parts,
!     `bibtex-autokey-year-title-separator' is used as well.
! 16. If the value of `bibtex-autokey-before-presentation-function'
!     is non-nil, it must be a function taking one argument.  This
!     function is then called with the generated key as the
!     argument.  The return value of this function (a string) is
!     used as the key.
! 17. If the value of `bibtex-autokey-edit-before-use' is non-nil,
!     the key is then presented in the minibuffer to the user,
!     where it can be edited.  The key given by the user is then
!     used."
    (let* ((names (bibtex-autokey-get-names))
           (year (bibtex-autokey-get-year))
           (title (bibtex-autokey-get-title))
--- 2171,2243 ----
        (setq alist (cdr alist)))
      (if alist
          (cdar alist)
!       (funcall bibtex-autokey-titleword-case-convert
!                (bibtex-autokey-abbrev titleword 
bibtex-autokey-titleword-length)))))
  
  (defun bibtex-generate-autokey ()
!   "Generate automatically a key for a BibTeX entry.
! Use the author/editor, the year and the title field.
! The algorithm works as follows.
! 
! The name part:
!  1. Use the author or editor field to generate the name part of the key.
!  2. Change the content of the name field according to
!     `bibtex-autokey-name-change-strings' (see there for further detail).
!  3. Use the first `bibtex-autokey-names' names in the name field.  If there
!     are up to `bibtex-autokey-names' + `bibtex-autokey-names-stretch' names,
!     use all names.
!  4. Use only the last names to form the name part.  From these last names,
!     take at least `bibtex-autokey-name-length' characters (truncate only
!     after a consonant or at a word end).
!  5. Convert all last names using the function
      `bibtex-autokey-name-case-convert'.
!  6. Build the name part of the key by concatenating all abbreviated last
!     names with the string `bibtex-autokey-name-separator' between any two.
!     If there are more names in the name field than names used in the name
!     part, append the string `bibtex-autokey-additional-names'.
! 
! The year part:
!  1. Build the year part of the key by truncating the content of the year
!     field to the rightmost `bibtex-autokey-year-length' digits (useful
!     values are 2 and 4).
!  2. If the year field (or any other field required to generate the key)
!     is absent, but the entry has a valid crossref field and
      `bibtex-autokey-use-crossref' is non-nil, use the field of the
      crossreferenced entry instead.
! 
! The title part
!  1. Change the content of the title field according to
!     `bibtex-autokey-titleword-change-strings' (see there for further detail).
!  2. Truncate the title before the first match of
!     `bibtex-autokey-title-terminators' and delete those words which appear
!     in `bibtex-autokey-titleword-ignore'.  Build the title part using the
!     first `bibtex-autokey-titlewords' words from this truncated title.
!     If the truncated title ends after up to `bibtex-autokey-titlewords' +
!     `bibtex-autokey-titlewords-stretch' words, use all words from the
!     truncated title.
!  3. For every title word that appears in `bibtex-autokey-titleword-abbrevs'
!     use the corresponding abbreviation (see documentation of this variable
!     for further detail).
!  4. From every title word not generated by an abbreviation, take at least
!     `bibtex-autokey-titleword-length' characters (truncate only after
!     a consonant or at a word end).
!  5. Convert all title words using the function
      `bibtex-autokey-titleword-case-convert'.
!  6. Build the title part by concatenating all abbreviated title words with
!     the string `bibtex-autokey-titleword-separator' between any two.
! 
! Concatenate the key:
!  1. Concatenate `bibtex-autokey-prefix-string', the name part, the year
!     part and the title part.  If the name part and the year part are both
!     non-empty insert `bibtex-autokey-name-year-separator' between the two.
!     If the title part and the year (or name) part are non-empty, insert
!     `bibtex-autokey-year-title-separator' between the two.
!  2. If `bibtex-autokey-before-presentation-function' is non-nil, it must be
!     a function taking one argument.  Call this function with the generated
!     key as the argument.  Use the return value of this function (a string)
!     as the key.
!  3. If `bibtex-autokey-edit-before-use' is non-nil, present the key in the
!     minibuffer to the user for editing.  Insert the key given by the user."
    (let* ((names (bibtex-autokey-get-names))
           (year (bibtex-autokey-get-year))
           (title (bibtex-autokey-get-title))
***************
*** 2257,2272 ****
        autokey)))
  
  
! (defun bibtex-read-key (prompt &optional key)
!   "Read BibTeX key from minibuffer using PROMPT and default KEY."
!   (completing-read prompt bibtex-reference-keys
!                    nil nil key 'bibtex-key-history))
  
  (defun bibtex-parse-keys (&optional abortable verbose)
    "Set `bibtex-reference-keys' to the keys used in the whole buffer.
! Find both entry keys and crossref entries.  If ABORTABLE is non-nil abort on
! user input.  If VERBOSE is non-nil gives messages about progress.  Return 
alist
! of keys if parsing was completed, `aborted' otherwise."
    (let (ref-keys crossref-keys)
      (save-excursion
        (save-match-data
--- 2257,2291 ----
        autokey)))
  
  
! (defun bibtex-global-key-alist ()
!   "Return global key alist based on `bibtex-files'."
!   (if bibtex-files
!       (apply 'append
!              (mapcar (lambda (buf)
!                        (with-current-buffer buf bibtex-reference-keys))
!                      (bibtex-files-expand t)))
!     bibtex-reference-keys))
! 
! (defun bibtex-read-key (prompt &optional key global)
!   "Read BibTeX key from minibuffer using PROMPT and default KEY.
! If optional arg GLOBAL is non-nil, completion is based on the keys in
! `bibtex-reference-keys' of `bibtex-files',"
!   (let (completion-ignore-case)
!     (completing-read prompt (if global (bibtex-global-key-alist)
!                               bibtex-reference-keys)
!                      nil nil key 'bibtex-key-history)))
! 
! (defun bibtex-read-string-key (&optional key)
!   "Read BibTeX string key from minibuffer using default KEY."
!   (let ((completion-ignore-case t))
!     (completing-read "String key: " bibtex-strings
!                      nil nil key 'bibtex-key-history)))
  
  (defun bibtex-parse-keys (&optional abortable verbose)
    "Set `bibtex-reference-keys' to the keys used in the whole buffer.
! Find both entry keys and crossref entries.  If ABORTABLE is non-nil abort
! on user input.  If VERBOSE is non-nil give messages about progress.
! Return alist of keys if parsing was completed, `aborted' otherwise."
    (let (ref-keys crossref-keys)
      (save-excursion
        (save-match-data
***************
*** 2325,2331 ****
  
  (defun bibtex-parse-strings (&optional add abortable)
    "Set `bibtex-strings' to the string definitions in the whole buffer.
- The buffer might possibly be restricted.
  If ADD is non-nil add the new strings to `bibtex-strings' instead of
  simply resetting it.  If ADD is an alist of strings, also add ADD to
  `bibtex-strings'.  If ABORTABLE is non-nil abort on user input.
--- 2344,2349 ----
***************
*** 2395,2402 ****
  (defun bibtex-parse-buffers-stealthily ()
    "Parse buffer in the background during idle time.
  Called by `run-with-idle-timer'.  Whenever Emacs has been idle
! for `bibtex-parse-keys-timeout' seconds, all BibTeX buffers (starting
! with the current) are parsed."
    (save-excursion
      (let ((buffers (buffer-list))
            (strings-init (bibtex-string-files-init)))
--- 2413,2421 ----
  (defun bibtex-parse-buffers-stealthily ()
    "Parse buffer in the background during idle time.
  Called by `run-with-idle-timer'.  Whenever Emacs has been idle
! for `bibtex-parse-keys-timeout' seconds, parse all BibTeX buffers
! which have been modified after last parsing.
! Parsing initializes `bibtex-reference-keys' and `bibtex-strings'."
    (save-excursion
      (let ((buffers (buffer-list))
            (strings-init (bibtex-string-files-init)))
***************
*** 2417,2426 ****
                    (setq bibtex-buffer-last-parsed-tick 
(buffer-modified-tick)))))
          (setq buffers (cdr buffers))))))
  
! (defun bibtex-files-expand (&optional current)
    "Return an expanded list of BibTeX buffers based on `bibtex-files'.
  Initialize in these buffers `bibtex-reference-keys' if not yet set.
! List includes current buffer if CURRENT is non-nil."
    (let ((file-path (split-string (or bibtex-file-path default-directory) 
":+"))
          file-list dir-list buffer-list)
      (dolist (file bibtex-files)
--- 2436,2447 ----
                    (setq bibtex-buffer-last-parsed-tick 
(buffer-modified-tick)))))
          (setq buffers (cdr buffers))))))
  
! (defun bibtex-files-expand (&optional current force)
    "Return an expanded list of BibTeX buffers based on `bibtex-files'.
  Initialize in these buffers `bibtex-reference-keys' if not yet set.
! List of BibTeX buffers includes current buffer if CURRENT is non-nil.
! If FORCE is non-nil, (re)initialize `bibtex-reference-keys' even if
! already set."
    (let ((file-path (split-string (or bibtex-file-path default-directory) 
":+"))
          file-list dir-list buffer-list)
      (dolist (file bibtex-files)
***************
*** 2454,2470 ****
        (when (file-readable-p file)
          (push (find-file-noselect file) buffer-list)
          (with-current-buffer (car buffer-list)
!           (unless (listp bibtex-reference-keys)
              (bibtex-parse-keys)))))
      (cond ((and current (not (memq (current-buffer) buffer-list)))
!            (push (current-buffer) buffer-list))
            ((and (not current) (memq (current-buffer) buffer-list))
             (setq buffer-list (delq (current-buffer) buffer-list))))
      buffer-list))
  
  (defun bibtex-complete-internal (completions)
    "Complete word fragment before point to longest prefix of COMPLETIONS.
! COMPLETIONS should be a list of strings.  If point is not after the part
  of a word, all strings are listed.  Return completion."
    (let* ((case-fold-search t)
           (beg (save-excursion
--- 2475,2492 ----
        (when (file-readable-p file)
          (push (find-file-noselect file) buffer-list)
          (with-current-buffer (car buffer-list)
!           (if (or force (not (listp bibtex-reference-keys)))
              (bibtex-parse-keys)))))
      (cond ((and current (not (memq (current-buffer) buffer-list)))
!            (push (current-buffer) buffer-list)
!            (if force (bibtex-parse-keys)))
            ((and (not current) (memq (current-buffer) buffer-list))
             (setq buffer-list (delq (current-buffer) buffer-list))))
      buffer-list))
  
  (defun bibtex-complete-internal (completions)
    "Complete word fragment before point to longest prefix of COMPLETIONS.
! COMPLETIONS is an alist of strings.  If point is not after the part
  of a word, all strings are listed.  Return completion."
    (let* ((case-fold-search t)
           (beg (save-excursion
***************
*** 2491,2543 ****
             ;; return value is handled by choose-completion-string-functions
             nil))))
  
! (defun bibtex-complete-string-cleanup (str strings-alist)
    "Cleanup after inserting string STR.
! Remove enclosing field delimiters for string STR.  Display message with
! expansion of STR using expansion list STRINGS-ALIST."
!   (let ((pair (if (stringp str)
!                   (assoc-string str strings-alist t))))
!     (when pair
!       (if (cdr pair)
!           (message "Abbreviation for `%s'" (cdr pair)))
!       (save-excursion
!         (bibtex-inside-field)
!         (let ((bounds (bibtex-enclosing-field)))
!           (goto-char (bibtex-start-of-text-in-field bounds))
!           (let ((boundaries (bibtex-parse-field-string)))
!             (if (and boundaries
!                      (equal (cdr boundaries)
!                             (bibtex-end-of-text-in-field bounds)))
!                 (bibtex-remove-delimiters))))))))
  
! (defun bibtex-complete-key-cleanup (key)
    "Display summary message on entry KEY after completion of a crossref key.
  Use `bibtex-summary-function' to generate summary."
    (save-excursion
!     ;; Don't do anything if we completed the key of an entry.
!     (let ((pnt (bibtex-beginning-of-entry)))
!       (if (and (stringp key)
!                (bibtex-find-entry key)
!                (/= pnt (point)))
!           (message "Ref: %s" (funcall bibtex-summary-function key))))))
  
! (defun bibtex-copy-summary-as-kill (key)
!   "Push summery of BibTeX entry KEY to kill ring.
  Use `bibtex-summary-function' to generate summary."
!   (interactive
!    (list (bibtex-read-key
!           "Key: " (save-excursion
!                     (bibtex-beginning-of-entry)
!                     (when (re-search-forward bibtex-entry-head nil t)
!                       (bibtex-key-in-head))))))
!   (kill-new (message "%s" (funcall bibtex-summary-function key))))
  
  (defun bibtex-summary (key)
    "Return summary of BibTeX entry KEY.
  Used as default value of `bibtex-summary-function'."
    ;; It would be neat to customize this function.  How?
    (save-excursion
!     (if (bibtex-find-entry key)
          (let* ((bibtex-autokey-name-case-convert 'identity)
                 (bibtex-autokey-name-length 'infty)
                 (bibtex-autokey-names 1)
--- 2513,2560 ----
             ;; return value is handled by choose-completion-string-functions
             nil))))
  
! (defun bibtex-complete-string-cleanup (str compl)
    "Cleanup after inserting string STR.
! Remove enclosing field delimiters for STR.  Display message with
! expansion of STR using expansion list COMPL."
!   (save-excursion
!     (bibtex-inside-field)
!     (let ((bounds (bibtex-enclosing-field))
!           (abbr (cdr (if (stringp str)
!                          (assoc-string str compl t)))))
!       (if abbr (message "Abbreviation for `%s'" abbr))
!       (goto-char (bibtex-start-of-text-in-field bounds))
!       (let ((boundaries (bibtex-parse-field-string)))
!         (if (and boundaries
!                  (equal (cdr boundaries)
!                         (bibtex-end-of-text-in-field bounds)))
!             (bibtex-remove-delimiters))))))
  
! (defun bibtex-complete-crossref-cleanup (key)
    "Display summary message on entry KEY after completion of a crossref key.
  Use `bibtex-summary-function' to generate summary."
    (save-excursion
!     (if (and (stringp key)
!              (bibtex-find-entry key t))
!         (message "Ref: %s" (funcall bibtex-summary-function key)))))
  
! (defun bibtex-copy-summary-as-kill ()
!   "Push summery of current BibTeX entry to kill ring.
  Use `bibtex-summary-function' to generate summary."
!   (interactive)
!   (let ((key (save-excursion
!                (bibtex-beginning-of-entry)
!                (if (looking-at bibtex-entry-maybe-empty-head)
!                    (bibtex-key-in-head)
!                  (error "No key found")))))
!     (kill-new (message "%s" (funcall bibtex-summary-function key)))))
  
  (defun bibtex-summary (key)
    "Return summary of BibTeX entry KEY.
  Used as default value of `bibtex-summary-function'."
    ;; It would be neat to customize this function.  How?
    (save-excursion
!     (if (bibtex-find-entry key t)
          (let* ((bibtex-autokey-name-case-convert 'identity)
                 (bibtex-autokey-name-length 'infty)
                 (bibtex-autokey-names 1)
***************
*** 2563,2575 ****
                       `((" " . ,names) (" " . ,year) (": " . ,title)
                         (", " . ,journal) (" " . ,volume) (":" . ,pages))
                       ""))
!       (error "Key `%s' not found." key))))
  
  (defun bibtex-pop (arg direction)
!   "Fill current field from the ARG'th same field's text in DIRECTION.
  Generic function used by `bibtex-pop-previous' and `bibtex-pop-next'."
    (let (bibtex-help-message)
!     (bibtex-find-text nil))
    (save-excursion
      ;; parse current field
      (bibtex-inside-field)
--- 2580,2592 ----
                       `((" " . ,names) (" " . ,year) (": " . ,title)
                         (", " . ,journal) (" " . ,volume) (":" . ,pages))
                       ""))
!       (error "Key `%s' not found" key))))
  
  (defun bibtex-pop (arg direction)
!   "Fill current field from the ARGth same field's text in DIRECTION.
  Generic function used by `bibtex-pop-previous' and `bibtex-pop-next'."
    (let (bibtex-help-message)
!     (bibtex-find-text))
    (save-excursion
      ;; parse current field
      (bibtex-inside-field)
***************
*** 2613,2619 ****
            (delete-region start-old-text stop-old-text)
            (insert new-text)))))
    (let (bibtex-help-message)
!     (bibtex-find-text nil))
    (setq this-command 'bibtex-pop))
  
  (defun bibtex-beginning-of-field ()
--- 2630,2636 ----
            (delete-region start-old-text stop-old-text)
            (insert new-text)))))
    (let (bibtex-help-message)
!     (bibtex-find-text))
    (setq this-command 'bibtex-pop))
  
  (defun bibtex-beginning-of-field ()
***************
*** 2626,2632 ****
        (re-search-backward field-reg nil t))))
  
  (defun bibtex-font-lock-url (bound)
!   "Font-lock for URLs."
    (let ((case-fold-search t)
          (pnt (point))
          field bounds start end found)
--- 2643,2649 ----
        (re-search-backward field-reg nil t))))
  
  (defun bibtex-font-lock-url (bound)
!   "Font-lock for URLs.  BOUND limits the search."
    (let ((case-fold-search t)
          (pnt (point))
          field bounds start end found)
***************
*** 2657,2663 ****
      found))
  
  (defun bibtex-font-lock-crossref (bound)
!   "Font-lock for crossref fields."
    (let ((case-fold-search t)
          (pnt (point))
          (crossref-reg (concat "^[ \t]*crossref[ \t]*=[ \t\n]*"
--- 2674,2680 ----
      found))
  
  (defun bibtex-font-lock-crossref (bound)
!   "Font-lock for crossref fields.  BOUND limits the search."
    (let ((case-fold-search t)
          (pnt (point))
          (crossref-reg (concat "^[ \t]*crossref[ \t]*=[ \t\n]*"
***************
*** 2690,2695 ****
--- 2707,2713 ----
    'help-echo (purecopy "mouse-2, RET: follow crossref"))
  
  (defun bibtex-button (beg end type &rest args)
+   "Make a BibTeX button from BEG to END of type TYPE in the current buffer."
    (make-text-button beg end 'type type 'bibtex-args args))
  
  
***************
*** 2701,2718 ****
  
  General information on working with BibTeX mode:
  
! You should use commands such as \\[bibtex-Book] to get a template for a
! specific entry.  You should then fill in all desired fields using
! \\[bibtex-next-field] to jump from field to field.  After having filled
! in all desired fields in the entry, you should clean the new entry
! with the command \\[bibtex-clean-entry].
  
  Some features of BibTeX mode are available only by setting the variable
! `bibtex-maintain-sorted-entries' to non-nil.  However, then BibTeX mode will
! work only with buffers containing valid (syntactical correct) entries
! and with entries being sorted.  This is usually the case, if you have
! created a buffer completely with BibTeX mode and finished every new
! entry with \\[bibtex-clean-entry].
  
  For third party BibTeX files, call the function `bibtex-convert-alien'
  to fully take advantage of all features of BibTeX mode.
--- 2719,2734 ----
  
  General information on working with BibTeX mode:
  
! Use commands such as \\[bibtex-Book] to get a template for a specific entry.
! Then fill in all desired fields using \\[bibtex-next-field] to jump from field
! to field.  After having filled in all desired fields in the entry, clean the
! new entry with the command \\[bibtex-clean-entry].
  
  Some features of BibTeX mode are available only by setting the variable
! `bibtex-maintain-sorted-entries' to non-nil.  However, then BibTeX mode
! works only with buffers containing valid (syntactical correct) and sorted
! entries.  This is usually the case, if you have created a buffer completely
! with BibTeX mode and finished every new entry with \\[bibtex-clean-entry].
  
  For third party BibTeX files, call the function `bibtex-convert-alien'
  to fully take advantage of all features of BibTeX mode.
***************
*** 2720,2787 ****
  
  Special information:
  
! A command such as \\[bibtex-Book] will outline the fields for a BibTeX book 
entry.
  
! The optional fields start with the string OPT, and are thus ignored by BibTeX.
! Alternatives from which only one is required start with the string ALT.
! The OPT or ALT string may be removed from a field with 
\\[bibtex-remove-OPT-or-ALT].
  \\[bibtex-make-field] inserts a new field after the current one.
  \\[bibtex-kill-field] kills the current field entirely.
  \\[bibtex-yank] yanks the last recently killed field after the current field.
  \\[bibtex-remove-delimiters] removes the double-quotes or braces around the 
text of the current field.
!  \\[bibtex-empty-field] replaces the text of the current field with the 
default \"\" or {}.
  
  The command \\[bibtex-clean-entry] cleans the current entry, i.e. it removes 
OPT/ALT
! from all non-empty optional or alternative fields, checks that no required
! fields are empty, and does some formatting dependent on the value of
! `bibtex-entry-format'.
  Note: some functions in BibTeX mode depend on entries being in a special
  format (all fields beginning on separate lines), so it is usually a bad
  idea to remove `realign' from `bibtex-entry-format'.
  
! Use \\[bibtex-find-text] to position the cursor at the end of the current 
field.
! Use \\[bibtex-next-field] to move to end of the next field.
! 
! The following may be of interest as well:
  
!   Functions:
!     `bibtex-entry'
!     `bibtex-kill-entry'
!     `bibtex-yank-pop'
!     `bibtex-pop-previous'
!     `bibtex-pop-next'
!     `bibtex-complete'
!     `bibtex-print-help-message'
!     `bibtex-generate-autokey'
!     `bibtex-beginning-of-entry'
!     `bibtex-end-of-entry'
!     `bibtex-reposition-window'
!     `bibtex-mark-entry'
!     `bibtex-ispell-abstract'
!     `bibtex-ispell-entry'
!     `bibtex-narrow-to-entry'
!     `bibtex-sort-buffer'
!     `bibtex-validate'
!     `bibtex-count'
!     `bibtex-fill-entry'
!     `bibtex-reformat'
!     `bibtex-convert-alien'
! 
!   Variables:
!     `bibtex-field-delimiters'
!     `bibtex-include-OPTcrossref'
!     `bibtex-include-OPTkey'
!     `bibtex-user-optional-fields'
!     `bibtex-entry-format'
!     `bibtex-sort-ignore-string-entries'
!     `bibtex-maintain-sorted-entries'
!     `bibtex-entry-field-alist'
!     `bibtex-predefined-strings'
!     `bibtex-string-files'
! 
! ---------------------------------------------------------
! Entry to BibTeX mode calls the value of `bibtex-mode-hook' if that value is
! non-nil.
  
  \\{bibtex-mode-map}"
    (interactive)
--- 2736,2769 ----
  
  Special information:
  
! A command such as \\[bibtex-Book] outlines the fields for a BibTeX book entry.
  
! The names of optional fields start with the string OPT, and are thus ignored
! by BibTeX.  The names of alternative fields from which only one is required
! start with the string ALT.  The OPT or ALT string may be removed from
! the name of a field with \\[bibtex-remove-OPT-or-ALT].
  \\[bibtex-make-field] inserts a new field after the current one.
  \\[bibtex-kill-field] kills the current field entirely.
  \\[bibtex-yank] yanks the last recently killed field after the current field.
  \\[bibtex-remove-delimiters] removes the double-quotes or braces around the 
text of the current field.
! \\[bibtex-empty-field] replaces the text of the current field with the 
default \"\" or {}.
! \\[bibtex-find-text] moves point to the end of the current field.
! \\[bibtex-complete] completes word fragment before point according to context.
  
  The command \\[bibtex-clean-entry] cleans the current entry, i.e. it removes 
OPT/ALT
! from the names of all non-empty optional or alternative fields, checks that
! no required fields are empty, and does some formatting dependent on the value
! of `bibtex-entry-format'.  Furthermore, it can automatically generate a key
! for the BibTeX entry, see `bibtex-generate-autokey'.
  Note: some functions in BibTeX mode depend on entries being in a special
  format (all fields beginning on separate lines), so it is usually a bad
  idea to remove `realign' from `bibtex-entry-format'.
  
! BibTeX mode supports Imenu and hideshow minor mode (`hs-minor-mode').
  
! ----------------------------------------------------------
! Entry to BibTeX mode calls the value of `bibtex-mode-hook'
! if that value is non-nil.
  
  \\{bibtex-mode-map}"
    (interactive)
***************
*** 2824,2832 ****
                (set-mark (bibtex-end-of-entry))
              (bibtex-beginning-of-entry)))))
    (setq imenu-generic-expression
!         (list (list nil bibtex-entry-head bibtex-key-in-head)))
    (make-local-variable 'choose-completion-string-functions)
-   (setq imenu-case-fold-search t)
    ;; XEmacs needs easy-menu-add, Emacs does not care
    (easy-menu-add bibtex-edit-menu)
    (easy-menu-add bibtex-entry-menu)
--- 2806,2814 ----
                (set-mark (bibtex-end-of-entry))
              (bibtex-beginning-of-entry)))))
    (setq imenu-generic-expression
!         (list (list nil bibtex-entry-head bibtex-key-in-head))
!         imenu-case-fold-search t)
    (make-local-variable 'choose-completion-string-functions)
    ;; XEmacs needs easy-menu-add, Emacs does not care
    (easy-menu-add bibtex-edit-menu)
    (easy-menu-add bibtex-entry-menu)
***************
*** 2836,2842 ****
    "Return list of allowed fields for entry ENTRY-TYPE.
  More specifically, the return value is a cons pair (REQUIRED . OPTIONAL),
  where REQUIRED and OPTIONAL are lists of the required and optional field
! names for ENTRY-TYPE according to `bibtex-entry-field-alist'."
    (let ((e (assoc-string entry-type bibtex-entry-field-alist t))
          required optional)
      (unless e
--- 2818,2826 ----
    "Return list of allowed fields for entry ENTRY-TYPE.
  More specifically, the return value is a cons pair (REQUIRED . OPTIONAL),
  where REQUIRED and OPTIONAL are lists of the required and optional field
! names for ENTRY-TYPE according to `bibtex-entry-field-alist',
! `bibtex-include-OPTkey', `bibtex-include-OPTcrossref',
! and `bibtex-user-optional-fields'."
    (let ((e (assoc-string entry-type bibtex-entry-field-alist t))
          required optional)
      (unless e
***************
*** 2862,2874 ****
  
  (defun bibtex-entry (entry-type)
    "Insert a new BibTeX entry of type ENTRY-TYPE.
! After insertion it calls the functions in `bibtex-add-entry-hook'."
!   (interactive (let* ((completion-ignore-case t)
!                       (e-t (completing-read
!                             "Entry Type: "
!                             bibtex-entry-field-alist
!                             nil t nil 'bibtex-entry-type-history)))
!                  (list e-t)))
    (let ((key (if bibtex-maintain-sorted-entries
                   (bibtex-read-key (format "%s key: " entry-type))))
          (field-list (bibtex-field-list entry-type)))
--- 2846,2857 ----
  
  (defun bibtex-entry (entry-type)
    "Insert a new BibTeX entry of type ENTRY-TYPE.
! After insertion call the value of `bibtex-add-entry-hook' if that value
! is non-nil."
!   (interactive
!    (let ((completion-ignore-case t))
!      (list (completing-read "Entry Type: " bibtex-entry-field-alist
!                             nil t nil 'bibtex-entry-type-history))))
    (let ((key (if bibtex-maintain-sorted-entries
                   (bibtex-read-key (format "%s key: " entry-type))))
          (field-list (bibtex-field-list entry-type)))
***************
*** 2893,2899 ****
  (defun bibtex-entry-update ()
    "Update an existing BibTeX entry.
  In the BibTeX entry at point, make new fields for those items that may occur
! according to `bibtex-entry-field-alist', but are not yet present."
    (interactive)
    (save-excursion
      (bibtex-beginning-of-entry)
--- 2876,2882 ----
  (defun bibtex-entry-update ()
    "Update an existing BibTeX entry.
  In the BibTeX entry at point, make new fields for those items that may occur
! according to `bibtex-field-list', but are not yet present."
    (interactive)
    (save-excursion
      (bibtex-beginning-of-entry)
***************
*** 2928,2934 ****
      alist))
  
  (defun bibtex-autofill-entry ()
!   "Try to fill fields based on surrounding entries."
    (interactive)
    (undo-boundary)     ;So you can easily undo it, if it didn't work right.
    (bibtex-beginning-of-entry)
--- 2911,2923 ----
      alist))
  
  (defun bibtex-autofill-entry ()
!   "Try to fill fields of current BibTeX entry based on neighboring entries.
! The current entry must have a key.  Determine the neighboring entry
! \(previouse or next\) whose key is more similar to the key of the current
! entry.  For all empty fields of the current entry insert the corresponding
! field contents of the neighboring entry.  Finally try to update the text
! based on the difference between the keys of the neighboring and the current
! entry (for example, the year parts of the keys)."
    (interactive)
    (undo-boundary)     ;So you can easily undo it, if it didn't work right.
    (bibtex-beginning-of-entry)
***************
*** 2945,2971 ****
        (save-excursion
        (goto-char (1- (match-beginning 0)))
        (bibtex-beginning-of-entry)
!       (when (and
!              (looking-at bibtex-entry-head)
!              (bibtex-string= type (bibtex-type-in-head))
!              ;; In case we found ourselves :-(
!              (not (equal key (setq tmp (bibtex-key-in-head)))))
!         (setq other-key tmp)
!         (setq other (point))))
        (save-excursion
        (bibtex-end-of-entry)
        (bibtex-skip-to-valid-entry)
!       (when (and
!              (looking-at bibtex-entry-head)
!              (bibtex-string= type (bibtex-type-in-head))
!              ;; In case we found ourselves :-(
!              (not (equal key (setq tmp (bibtex-key-in-head))))
!              (or (not other-key)
!                  ;; Check which is the best match.
!                  (< (length (try-completion "" (list key other-key)))
!                     (length (try-completion "" (list key tmp))))))
!         (setq other-key tmp)
!         (setq other (point))))
        ;; Then fill the new entry's fields with the chosen other entry.
        (when other
        (setq other (save-excursion (goto-char other) (bibtex-parse-entry)))
--- 2934,2958 ----
        (save-excursion
        (goto-char (1- (match-beginning 0)))
        (bibtex-beginning-of-entry)
!       (if (and (looking-at bibtex-entry-head)
!                  (bibtex-string= type (bibtex-type-in-head))
!                  ;; In case we found ourselves :-(
!                  (not (equal key (setq tmp (bibtex-key-in-head)))))
!         (setq other-key tmp
!                 other (point))))
        (save-excursion
        (bibtex-end-of-entry)
        (bibtex-skip-to-valid-entry)
!       (if (and (looking-at bibtex-entry-head)
!                  (bibtex-string= type (bibtex-type-in-head))
!                  ;; In case we found ourselves :-(
!                  (not (equal key (setq tmp (bibtex-key-in-head))))
!                  (or (not other-key)
!                      ;; Check which is the best match.
!                      (< (length (try-completion "" (list key other-key)))
!                         (length (try-completion "" (list key tmp))))))
!             (setq other-key tmp
!                   other (point))))
        ;; Then fill the new entry's fields with the chosen other entry.
        (when other
        (setq other (save-excursion (goto-char other) (bibtex-parse-entry)))
***************
*** 3007,3019 ****
            (message (nth 1 comment))
          (message "No comment available")))))
  
! (defun bibtex-make-field (field &optional called-by-yank interactive)
    "Make a field named FIELD in current BibTeX entry.
  FIELD is either a string or a list of the form
  \(FIELD-NAME COMMENT-STRING INIT ALTERNATIVE-FLAG) as in
  `bibtex-entry-field-alist'.
! If CALLED-BY-YANK is non-nil, don't insert delimiters.
! In that case, or when called interactively, also don't do (WHAT?)."
    (interactive
     (list (let ((completion-ignore-case t)
                 (field-list (bibtex-field-list
--- 2994,3008 ----
            (message (nth 1 comment))
          (message "No comment available")))))
  
! (defun bibtex-make-field (field &optional move interactive)
    "Make a field named FIELD in current BibTeX entry.
  FIELD is either a string or a list of the form
  \(FIELD-NAME COMMENT-STRING INIT ALTERNATIVE-FLAG) as in
  `bibtex-entry-field-alist'.
! If MOVE is non-nil, move point past the present field before making
! the new field.  If INTERACTIVE is non-nil, move point to the end of
! the new field.  Otherwise move point past the new field.
! MOVE and INTERACTIVE are t when called interactively."
    (interactive
     (list (let ((completion-ignore-case t)
                 (field-list (bibtex-field-list
***************
*** 3023,3034 ****
             (completing-read "BibTeX field name: "
                              (append (car field-list) (cdr field-list))
                              nil nil nil bibtex-field-history))
!        t))
    (unless (consp field)
      (setq field (list field)))
!   (if (or interactive called-by-yank)
        (let (bibtex-help-message)
!         (bibtex-find-text nil t t)
          (if (looking-at "[}\"]")
              (forward-char))))
    (insert ",\n")
--- 3012,3023 ----
             (completing-read "BibTeX field name: "
                              (append (car field-list) (cdr field-list))
                              nil nil nil bibtex-field-history))
!          t t))
    (unless (consp field)
      (setq field (list field)))
!   (if move
        (let (bibtex-help-message)
!         (bibtex-find-text)
          (if (looking-at "[}\"]")
              (forward-char))))
    (insert ",\n")
***************
*** 3042,3054 ****
    (unless bibtex-align-at-equal-sign
      (indent-to-column (+ bibtex-entry-offset
                           bibtex-text-indentation)))
-   (unless called-by-yank (insert (bibtex-field-left-delimiter)))
    (let ((init (nth 2 field)))
!     (cond ((stringp init)
!            (insert init))
!           ((fboundp init)
!            (insert (funcall init)))))
!   (unless called-by-yank (insert (bibtex-field-right-delimiter)))
    (when interactive
      (forward-char -1)
      (bibtex-print-help-message)))
--- 3031,3041 ----
    (unless bibtex-align-at-equal-sign
      (indent-to-column (+ bibtex-entry-offset
                           bibtex-text-indentation)))
    (let ((init (nth 2 field)))
!     (insert (cond ((stringp init) init)
!                   ((fboundp init) (funcall init))
!                   (t (concat (bibtex-field-left-delimiter)
!                              (bibtex-field-right-delimiter))))))
    (when interactive
      (forward-char -1)
      (bibtex-print-help-message)))
***************
*** 3083,3099 ****
             (goto-char (bibtex-end-of-string bounds)))
            ((looking-at "[ address@hidden \t]*preamble[ \t\n]*")
             (goto-char (match-end 0))
!            (cond ((looking-at "(")
!                   (unless (re-search-forward ")[ \t]*\n\n" nil 'move)
!                     (setq err t)))
!                  ((looking-at "{")
!                   (unless (re-search-forward "}[ \t]*\n\n" nil 'move)
!                     (setq err t)))
!                  (t
!                   (setq err t)))
!            (unless err
!              (goto-char (match-beginning 0))
!              (forward-char)))
            (t
             (if (interactive-p)
                 (message "Not on a known BibTeX entry."))
--- 3070,3078 ----
             (goto-char (bibtex-end-of-string bounds)))
            ((looking-at "[ address@hidden \t]*preamble[ \t\n]*")
             (goto-char (match-end 0))
!            (if (looking-at "[({]")
!                (forward-sexp 1)
!              (setq err t)))
            (t
             (if (interactive-p)
                 (message "Not on a known BibTeX entry."))
***************
*** 3103,3116 ****
        (error "Syntactically incorrect BibTeX entry starts here")))
    (point))
  
! (defun bibtex-reposition-window (&optional arg)
    "Make the current BibTeX entry visible.
! Optional argument ARG is exactly as in `recenter'."
!   (interactive "P")
!   (save-excursion
!     (goto-char
!      (/ (+ (bibtex-beginning-of-entry) (bibtex-end-of-entry)) 2))
!     (recenter arg)))
  
  (defun bibtex-mark-entry ()
    "Put mark at beginning, point at end of current BibTeX entry."
--- 3082,3116 ----
        (error "Syntactically incorrect BibTeX entry starts here")))
    (point))
  
! (defun bibtex-goto-line (arg)
!   "Goto line ARG, counting from beginning of (narrowed) buffer."
!   ;; code adapted from `goto-line'
!   (goto-char (point-min))
!   (if (eq selective-display t)
!       (re-search-forward "[\n\C-m]" nil 'end (1- arg))
!     (forward-line (1- arg))))
! 
! (defun bibtex-reposition-window ()
    "Make the current BibTeX entry visible.
! If entry is smaller than `window-body-height', entry is centered in window.
! Otherwise display the beginning of entry."
!   (interactive)
!   (let ((pnt (point))
!         (beg (line-number-at-pos (bibtex-beginning-of-entry)))
!         (end (line-number-at-pos (bibtex-end-of-entry))))
!     (if (> (window-body-height) (- end beg))
!         ;; entry fits in current window
!         (progn
!           (bibtex-goto-line (/ (+ 1 beg end) 2))
!           (recenter)
!           (goto-char pnt))
!       ;; entry too large for current window
!       (bibtex-goto-line beg)
!       (recenter 0)
!       (if (> (1+ (- (line-number-at-pos pnt) beg))
!              (window-body-height))
!           (bibtex-goto-line beg)
!         (goto-char pnt)))))
  
  (defun bibtex-mark-entry ()
    "Put mark at beginning, point at end of current BibTeX entry."
***************
*** 3120,3128 ****
  
  (defun bibtex-count-entries (&optional count-string-entries)
    "Count number of entries in current buffer or region.
! With prefix argument COUNT-STRING-ENTRIES it counts all entries,
! otherwise it counts all except Strings.
! If mark is active it counts entries in region, if not in whole buffer."
    (interactive "P")
    (let ((number 0)
          (bibtex-sort-ignore-string-entries
--- 3120,3128 ----
  
  (defun bibtex-count-entries (&optional count-string-entries)
    "Count number of entries in current buffer or region.
! With prefix argument COUNT-STRING-ENTRIES count all entries,
! otherwise count all entries except @String entries.
! If mark is active count entries in region, if not in whole buffer."
    (interactive "P")
    (let ((number 0)
          (bibtex-sort-ignore-string-entries
***************
*** 3139,3151 ****
               number)))
  
  (defun bibtex-ispell-entry ()
!   "Spell whole BibTeX entry."
    (interactive)
    (ispell-region (save-excursion (bibtex-beginning-of-entry))
                   (save-excursion (bibtex-end-of-entry))))
  
  (defun bibtex-ispell-abstract ()
!   "Spell abstract of BibTeX entry."
    (interactive)
    (let ((bounds (save-excursion
                    (bibtex-beginning-of-entry)
--- 3139,3151 ----
               number)))
  
  (defun bibtex-ispell-entry ()
!   "Check BibTeX entry for spelling errors."
    (interactive)
    (ispell-region (save-excursion (bibtex-beginning-of-entry))
                   (save-excursion (bibtex-end-of-entry))))
  
  (defun bibtex-ispell-abstract ()
!   "Check abstract of BibTeX entry for spelling errors."
    (interactive)
    (let ((bounds (save-excursion
                    (bibtex-beginning-of-entry)
***************
*** 3164,3186 ****
                        (bibtex-end-of-entry))))
  
  (defun bibtex-entry-index ()
!   "Return the index of the BibTeX entry at point.  Move point.
  The index is a list (KEY CROSSREF-KEY ENTRY-NAME) that is used for sorting
! the entries of the BibTeX buffer.  Return nil if no entry found."
    (let ((case-fold-search t))
      (if (re-search-forward bibtex-entry-maybe-empty-head nil t)
          (let ((key (bibtex-key-in-head))
                ;; all entry names should be downcase (for ease of comparison)
                (entry-name (downcase (bibtex-type-in-head))))
            ;; Don't search CROSSREF-KEY if we don't need it.
!           (if (equal bibtex-maintain-sorted-entries 'crossref)
!               (save-excursion
!                 (bibtex-beginning-of-entry)
!                 (let ((bounds (bibtex-search-forward-field
!                                "\\(OPT\\)?crossref" t)))
!                   (list key
!                         (if bounds (bibtex-text-in-field-bounds bounds t))
!                         entry-name)))
              (list key nil entry-name))))))
  
  (defun bibtex-lessp (index1 index2)
--- 3164,3186 ----
                        (bibtex-end-of-entry))))
  
  (defun bibtex-entry-index ()
!   "Return index of BibTeX entry head at or past position of point.
  The index is a list (KEY CROSSREF-KEY ENTRY-NAME) that is used for sorting
! the entries of the BibTeX buffer.  CROSSREF-KEY is nil unless the value
! of `bibtex-maintain-sorted-entries' is `crossref'.  Move point to the end
! of the head of the entry found.  Return nil if no entry found."
    (let ((case-fold-search t))
      (if (re-search-forward bibtex-entry-maybe-empty-head nil t)
          (let ((key (bibtex-key-in-head))
                ;; all entry names should be downcase (for ease of comparison)
                (entry-name (downcase (bibtex-type-in-head))))
            ;; Don't search CROSSREF-KEY if we don't need it.
!           (if (eq bibtex-maintain-sorted-entries 'crossref)
!               (let ((bounds (bibtex-search-forward-field
!                              "\\(OPT\\)?crossref" t)))
!                 (list key
!                       (if bounds (bibtex-text-in-field-bounds bounds t))
!                       entry-name))
              (list key nil entry-name))))))
  
  (defun bibtex-lessp (index1 index2)
***************
*** 3190,3196 ****
  If its value is nil use plain sorting."
    (cond ((not index1) (not index2)) ; indices can be nil
          ((not index2) nil)
!         ((equal bibtex-maintain-sorted-entries 'crossref)
           (if (nth 1 index1)
               (if (nth 1 index2)
                   (or (string-lessp (nth 1 index1) (nth 1 index2))
--- 3190,3196 ----
  If its value is nil use plain sorting."
    (cond ((not index1) (not index2)) ; indices can be nil
          ((not index2) nil)
!         ((eq bibtex-maintain-sorted-entries 'crossref)
           (if (nth 1 index1)
               (if (nth 1 index2)
                   (or (string-lessp (nth 1 index1) (nth 1 index2))
***************
*** 3200,3206 ****
             (if (nth 1 index2)
                 (string-lessp (nth 0 index1) (nth 1 index2))
               (string-lessp (nth 0 index1) (nth 0 index2)))))
!         ((equal bibtex-maintain-sorted-entries 'entry-class)
           (let ((n1 (cdr (or (assoc (nth 2 index1) 
bibtex-sort-entry-class-alist)
                              (assoc 'catch-all bibtex-sort-entry-class-alist)
                              '(nil . 1000))))  ; if there is nothing else
--- 3200,3206 ----
             (if (nth 1 index2)
                 (string-lessp (nth 0 index1) (nth 1 index2))
               (string-lessp (nth 0 index1) (nth 0 index2)))))
!         ((eq bibtex-maintain-sorted-entries 'entry-class)
           (let ((n1 (cdr (or (assoc (nth 2 index1) 
bibtex-sort-entry-class-alist)
                              (assoc 'catch-all bibtex-sort-entry-class-alist)
                              '(nil . 1000))))  ; if there is nothing else
***************
*** 3210,3216 ****
             (or (< n1 n2)
                 (and (= n1 n2)
                      (string-lessp (car index1) (car index2))))))
!         (t ; (equal bibtex-maintain-sorted-entries 'plain)
           (string-lessp (car index1) (car index2)))))
  
  (defun bibtex-sort-buffer ()
--- 3210,3216 ----
             (or (< n1 n2)
                 (and (= n1 n2)
                      (string-lessp (car index1) (car index2))))))
!         (t ; (eq bibtex-maintain-sorted-entries 'plain)
           (string-lessp (car index1) (car index2)))))
  
  (defun bibtex-sort-buffer ()
***************
*** 3218,3224 ****
  The predicate for sorting is defined via `bibtex-maintain-sorted-entries'.
  If its value is nil use plain sorting.  Text outside of BibTeX entries is not
  affected.  If `bibtex-sort-ignore-string-entries' is non-nil, @String entries
! will be ignored."
    (interactive)
    (save-restriction
      (narrow-to-region (bibtex-beginning-of-first-entry)
--- 3218,3224 ----
  The predicate for sorting is defined via `bibtex-maintain-sorted-entries'.
  If its value is nil use plain sorting.  Text outside of BibTeX entries is not
  affected.  If `bibtex-sort-ignore-string-entries' is non-nil, @String entries
! are ignored."
    (interactive)
    (save-restriction
      (narrow-to-region (bibtex-beginning-of-first-entry)
***************
*** 3232,3268 ****
                 nil                         ; ENDKEY function
                 'bibtex-lessp)))            ; PREDICATE
  
- (defun bibtex-find-entry-globally (key)
-   "Move point to the beginning of BibTeX entry named KEY in `bibtex-files'."
-   (interactive
-    (list (let (key-alist)
-            (dolist (buffer (bibtex-files-expand t))
-              (with-current-buffer buffer
-                (setq key-alist (append bibtex-reference-keys key-alist))))
-            (completing-read "Find key: " key-alist
-                             nil nil nil 'bibtex-key-history))))
-   (let ((buffer-list (bibtex-files-expand t))
-         buffer found)
-     (while (and (not found)
-                 (setq buffer (pop buffer-list)))
-       (with-current-buffer buffer
-         (if (cdr (assoc-string key bibtex-reference-keys))
-             (setq found t))))
-     (if found
-         (progn
-         (let ((same-window-buffer-names
-                (cons (buffer-name buffer) same-window-buffer-names)))
-           (pop-to-buffer buffer))
-         (bibtex-find-entry key))
-       (message "Key `%s' not found" key))))
- 
  (defun bibtex-find-crossref (crossref-key &optional pnt split)
    "Move point to the beginning of BibTeX entry CROSSREF-KEY.
! Return position of entry if CROSSREF-KEY is found and nil otherwise.
! If position of current entry is after CROSSREF-KEY an error is signaled.
! Optional arg PNT is the position of the referencing entry.
! If optional arg SPLIT is non-nil, split window so that both the referencing
! and the crossrefed entry are displayed.
  If called interactively, CROSSREF-KEY defaults to crossref key of current
  entry and SPLIT is t."
    (interactive
--- 3232,3247 ----
                 nil                         ; ENDKEY function
                 'bibtex-lessp)))            ; PREDICATE
  
  (defun bibtex-find-crossref (crossref-key &optional pnt split)
    "Move point to the beginning of BibTeX entry CROSSREF-KEY.
! If `bibtex-files' is non-nil, search all these files.
! Otherwise the search is limited to the current buffer.
! Return position of entry if CROSSREF-KEY is found or nil otherwise.
! If CROSSREF-KEY is in the same buffer like current entry but before it
! an error is signaled.  Optional arg PNT is the position of the referencing
! entry. It defaults to position of point.  If optional arg SPLIT is non-nil,
! split window so that both the referencing and the crossrefed entry are
! displayed.
  If called interactively, CROSSREF-KEY defaults to crossref key of current
  entry and SPLIT is t."
    (interactive
***************
*** 3272,3325 ****
              (let ((bounds (bibtex-search-forward-field "crossref" t)))
                (if bounds
                    (bibtex-text-in-field-bounds bounds t))))))
!      (list (bibtex-read-key "Find crossref key: " crossref-key) (point) t)))
!   (let ((pos (save-excursion (bibtex-find-entry crossref-key))))
!     (unless pnt (setq pnt (point)))
      (cond ((not pos)
!            (message "Crossref key `%s' not found" crossref-key))
!           (split
             (goto-char pnt)
!            (select-window (split-window))
             (goto-char pos)
             (beginning-of-line)
!            (set-window-start (selected-window) (point))
!            (if (> pnt pos)
                 (error "The referencing entry must preceed the crossrefed 
entry!")))
!           ((> pnt pos)
!                (error "The referencing entry must preceed the crossrefed 
entry!"))
!           (t (goto-char pos)))
      pos))
  
! (defun bibtex-find-entry (key &optional start)
    "Move point to the beginning of BibTeX entry named KEY.
  Return position of entry if KEY is found or nil if not found.
  Optional arg START is buffer position where the search starts.
  If it is nil, start search at beginning of buffer.
! With prefix arg, the value of START is position of point."
!   (interactive (list (bibtex-read-key "Find key: ")
!                      (if current-prefix-arg (point))))
!   (let* (case-fold-search
!          (pnt (save-excursion
!                 (goto-char (or start (point-min)))
!                 (if (re-search-forward (concat "^[ \t]*\\("
!                                                bibtex-entry-type
!                                                "\\)[ \t]*[({][ \t\n]*\\("
!                                                (regexp-quote key)
!                                                "\\)[ \t\n]*[,=]")
!                                        nil t)
!                     (match-beginning 0)))))
!     (cond (pnt
!            (goto-char pnt))
!           ((interactive-p)
!            (message "Key `%s' not found" key)))))
  
  (defun bibtex-prepare-new-entry (index)
    "Prepare a new BibTeX entry with index INDEX.
  INDEX is a list (KEY CROSSREF-KEY ENTRY-NAME).
  Move point where the entry KEY should be placed.
  If `bibtex-maintain-sorted-entries' is non-nil, perform a binary
! search to look for place for KEY.  This will fail if buffer is not in
! sorted order, see \\[bibtex-validate].)
  Return t if preparation was successful or nil if entry KEY already exists."
    (let ((key (nth 0 index))
          key-exist)
--- 3251,3335 ----
              (let ((bounds (bibtex-search-forward-field "crossref" t)))
                (if bounds
                    (bibtex-text-in-field-bounds bounds t))))))
!      (list (bibtex-read-key "Find crossref key: " crossref-key t)
!            (point) t)))
!   (let (buffer pos eqb)
!     (save-excursion
!       (setq pos (bibtex-find-entry crossref-key t)
!             buffer (current-buffer)))
!     (setq eqb (eq buffer (current-buffer)))
      (cond ((not pos)
!            (if split (message "Crossref key `%s' not found" crossref-key)))
!           (split ; called (quasi) interactively
!            (unless pnt (setq pnt (point)))
             (goto-char pnt)
!            (if eqb (select-window (split-window))
!              (pop-to-buffer buffer))
             (goto-char pos)
+            (bibtex-reposition-window)
             (beginning-of-line)
!            (if (and eqb (> pnt pos))
                 (error "The referencing entry must preceed the crossrefed 
entry!")))
!           ;; `bibtex-find-crossref' is called noninteractively during
!           ;; clean-up of an entry.  Then it is not possible to check
!           ;; whether the current entry and the crossrefed entry have
!           ;; the correct sorting order.
!           (eqb (goto-char pos))
!           (t (set-buffer buffer) (goto-char pos)))
      pos))
  
! (defun bibtex-find-entry (key &optional global start display)
    "Move point to the beginning of BibTeX entry named KEY.
  Return position of entry if KEY is found or nil if not found.
+ With prefix arg GLOBAL non-nil, search KEY in `bibtex-files'.
+ Otherwise the search is limited to the current buffer.
  Optional arg START is buffer position where the search starts.
  If it is nil, start search at beginning of buffer.
! If DISPLAY is non-nil, display the buffer containing KEY.
! Otherwise, use `set-buffer'.  DISPLAY is t when called interactively."
!   (interactive (list (bibtex-read-key "Find key: " nil current-prefix-arg)
!                      current-prefix-arg nil t))
!   (if (and global bibtex-files)
!       (let ((buffer-list (bibtex-files-expand t))
!             buffer found)
!         (while (and (not found)
!                     (setq buffer (pop buffer-list)))
!           (with-current-buffer buffer
!             (if (cdr (assoc-string key bibtex-reference-keys))
!                 ;; `bibtex-find-entry' moves point if key found
!                 (setq found (bibtex-find-entry key)))))
!         (cond ((and found display)
!                (let ((same-window-buffer-names
!                       (cons (buffer-name buffer) same-window-buffer-names)))
!                  (pop-to-buffer buffer)
!                  (bibtex-reposition-window)))
!               (found (set-buffer buffer))
!               (display (message "Key `%s' not found" key)))
!         found)
! 
!     (let* (case-fold-search
!            (pnt (save-excursion
!                   (goto-char (or start (point-min)))
!                   (if (re-search-forward (concat "^[ \t]*\\("
!                                                  bibtex-entry-type
!                                                  "\\)[ \t]*[({][ \t\n]*\\("
!                                                  (regexp-quote key)
!                                                  "\\)[ \t\n]*[,=]")
!                                          nil t)
!                       (match-beginning 0)))))
!       (cond (pnt
!              (goto-char pnt)
!              (if display (bibtex-reposition-window)))
!             (display (message "Key `%s' not found" key)))
!       pnt)))
  
  (defun bibtex-prepare-new-entry (index)
    "Prepare a new BibTeX entry with index INDEX.
  INDEX is a list (KEY CROSSREF-KEY ENTRY-NAME).
  Move point where the entry KEY should be placed.
  If `bibtex-maintain-sorted-entries' is non-nil, perform a binary
! search to look for place for KEY.  This requires that buffer is sorted,
! see \\[bibtex-validate].)
  Return t if preparation was successful or nil if entry KEY already exists."
    (let ((key (nth 0 index))
          key-exist)
***************
*** 3437,3447 ****
  
            ;; Check for duplicate keys in `bibtex-files'.
            (bibtex-parse-keys)
!           (dolist (buffer (bibtex-files-expand))
!             (dolist (key (with-current-buffer buffer
!                            ;; We don't want to be fooled by outdated
!                            ;; bibtex-reference-keys.
!                            (bibtex-parse-keys) bibtex-reference-keys))
                (when (and (cdr key)
                           (cdr (assoc-string (car key) bibtex-reference-keys)))
                  (bibtex-find-entry (car key))
--- 3447,3455 ----
  
            ;; Check for duplicate keys in `bibtex-files'.
            (bibtex-parse-keys)
!           ;; We don't want to be fooled by outdated `bibtex-reference-keys'.
!           (dolist (buffer (bibtex-files-expand nil t))
!             (dolist (key (with-current-buffer buffer bibtex-reference-keys))
                (when (and (cdr key)
                           (cdr (assoc-string (car key) bibtex-reference-keys)))
                  (bibtex-find-entry (car key))
***************
*** 3540,3546 ****
  
  (defun bibtex-validate-globally (&optional strings)
    "Check for duplicate keys in `bibtex-files'.
! With prefix arg STRINGS, check for duplicate strings, too.
  Return t if test was successful, nil otherwise."
    (interactive "P")
    (let ((buffer-list (bibtex-files-expand t))
--- 3548,3554 ----
  
  (defun bibtex-validate-globally (&optional strings)
    "Check for duplicate keys in `bibtex-files'.
! With optional prefix arg STRINGS, check for duplicate strings, too.
  Return t if test was successful, nil otherwise."
    (interactive "P")
    (let ((buffer-list (bibtex-files-expand t))
***************
*** 3595,3602 ****
        (message "No duplicate keys.")
        t)))
  
! (defun bibtex-next-field (arg)
!   "Find end of text of next BibTeX field; with ARG, to its beginning."
    (interactive "P")
    (bibtex-inside-field)
    (let ((start (point)))
--- 3603,3611 ----
        (message "No duplicate keys.")
        t)))
  
! (defun bibtex-next-field (begin)
!   "Move point to end of text of next BibTeX field.
! With prefix BEGIN non-nil, move point to its beginning."
    (interactive "P")
    (bibtex-inside-field)
    (let ((start (point)))
***************
*** 3608,3643 ****
         (goto-char start)
         (end-of-line)
         (forward-char))))
!   (bibtex-find-text arg t))
  
! (defun bibtex-find-text (arg &optional as-if-interactive no-error)
!   "Go to end of text of current field; with ARG, go to beginning."
!   (interactive "P\np")
!   (bibtex-inside-field)
!   (let ((bounds (bibtex-enclosing-field as-if-interactive)))
!     (if bounds
!         (progn (if arg
!                    (progn (goto-char (bibtex-start-of-text-in-field bounds))
!                           (if (looking-at "[{\"]")
!                               (forward-char)))
!                  (goto-char (bibtex-end-of-text-in-field bounds))
!                  (if (or (= (preceding-char) ?})
!                          (= (preceding-char) ?\"))
!                      (forward-char -1)))
!                (if bibtex-help-message
!                    (bibtex-print-help-message)))
!       (beginning-of-line)
!       (cond ((setq bounds (bibtex-parse-string))
!              (goto-char (if arg
!                             (bibtex-start-of-text-in-string bounds)
!                           (bibtex-end-of-text-in-string bounds))))
!             ((looking-at bibtex-entry-maybe-empty-head)
!              (goto-char (if arg
!                             (match-beginning bibtex-key-in-head)
!                           (match-end 0))))
!             (t
!              (unless no-error
!                (error "Not on BibTeX field")))))))
  
  (defun bibtex-remove-OPT-or-ALT ()
    "Remove the string starting optional/alternative fields.
--- 3617,3656 ----
         (goto-char start)
         (end-of-line)
         (forward-char))))
!   (bibtex-find-text begin))
  
! (defun bibtex-find-text (&optional begin noerror)
!   "Move point to end of text of current BibTeX field.
! With optional prefix BEGIN non-nil, move point to its beginning.
! Unless NOERROR is non-nil, an error is signaled if point is not
! on a BibTeX field."
!   (interactive "P")
!   (let* ((pnt (point))
!          (_ (bibtex-inside-field))
!          (bounds (bibtex-enclosing-field t)))
!     (beginning-of-line)
!     (cond (bounds
!            (if begin
!                (progn (goto-char (bibtex-start-of-text-in-field bounds))
!                       (if (looking-at "[{\"]")
!                           (forward-char)))
!              (goto-char (bibtex-end-of-text-in-field bounds))
!              (if (or (= (preceding-char) ?})
!                      (= (preceding-char) ?\"))
!                  (forward-char -1)))
!            (if bibtex-help-message
!                (bibtex-print-help-message)))
!           ((setq bounds (bibtex-parse-string))
!            (goto-char (if begin
!                           (1+ (bibtex-start-of-text-in-string bounds))
!                         (1- (bibtex-end-of-text-in-string bounds)))))
!           ((looking-at bibtex-entry-maybe-empty-head)
!            (goto-char (if begin
!                           (match-beginning bibtex-key-in-head)
!                         (match-end 0))))
!           (t
!            (goto-char pnt)
!            (unless noerror (error "Not on BibTeX field"))))))
  
  (defun bibtex-remove-OPT-or-ALT ()
    "Remove the string starting optional/alternative fields.
***************
*** 3690,3696 ****
             (beg (bibtex-start-of-field bounds)))
        (goto-char end)
        (skip-chars-forward " \t\n,")
!       (push (list 'field (bibtex-name-in-field bounds)
                    (bibtex-text-in-field-bounds bounds))
              bibtex-field-kill-ring)
        (if (> (length bibtex-field-kill-ring) bibtex-field-kill-ring-max)
--- 3703,3709 ----
             (beg (bibtex-start-of-field bounds)))
        (goto-char end)
        (skip-chars-forward " \t\n,")
!       (push (list (bibtex-name-in-field bounds) nil
                    (bibtex-text-in-field-bounds bounds))
              bibtex-field-kill-ring)
        (if (> (length bibtex-field-kill-ring) bibtex-field-kill-ring-max)
***************
*** 3703,3716 ****
    (setq bibtex-last-kill-command 'field))
  
  (defun bibtex-copy-field-as-kill ()
!   "Copy the field at point to the kill ring."
    (interactive)
    (bibtex-kill-field t))
  
  (defun bibtex-kill-entry (&optional copy-only)
    "Kill the entire enclosing BibTeX entry.
! With prefix arg COPY-ONLY the current entry to
! `bibtex-entry-kill-ring', but do not actually kill it."
    (interactive "P")
    (save-excursion
      (let* ((case-fold-search t)
--- 3716,3729 ----
    (setq bibtex-last-kill-command 'field))
  
  (defun bibtex-copy-field-as-kill ()
!   "Copy the BibTeX field at point to the kill ring."
    (interactive)
    (bibtex-kill-field t))
  
  (defun bibtex-kill-entry (&optional copy-only)
    "Kill the entire enclosing BibTeX entry.
! With prefix arg COPY-ONLY, copy the current entry to `bibtex-entry-kill-ring',
! but do not actually kill it."
    (interactive "P")
    (save-excursion
      (let* ((case-fold-search t)
***************
*** 3720,3726 ****
                              bibtex-entry-maybe-empty-head nil 'move)
                             (goto-char (match-beginning 0)))
                         (point))))
!       (push (list 'entry (buffer-substring-no-properties beg end))
              bibtex-entry-kill-ring)
        (if (> (length bibtex-entry-kill-ring) bibtex-entry-kill-ring-max)
            (setcdr (nthcdr (1- bibtex-entry-kill-ring-max)
--- 3733,3739 ----
                              bibtex-entry-maybe-empty-head nil 'move)
                             (goto-char (match-beginning 0)))
                         (point))))
!       (push (buffer-substring-no-properties beg end)
              bibtex-entry-kill-ring)
        (if (> (length bibtex-entry-kill-ring) bibtex-entry-kill-ring-max)
            (setcdr (nthcdr (1- bibtex-entry-kill-ring-max)
***************
*** 3742,3757 ****
  With argument N, reinsert the Nth most recently killed BibTeX item.
  See also the command \\[bibtex-yank-pop]]."
    (interactive "*p")
!   (bibtex-insert-current-kill (1- n))
    (setq this-command 'bibtex-yank))
  
  (defun bibtex-yank-pop (n)
!   "Replace just-yanked killed BibTeX item with a different.
  This command is allowed only immediately after a `bibtex-yank' or a
! `bibtex-yank-pop'.
! At such a time, the region contains a reinserted previously killed
! BibTeX item.  `bibtex-yank-pop' deletes that item and inserts in its
! place a different killed BibTeX item.
  
  With no argument, the previous kill is inserted.
  With argument N, insert the Nth previous kill.
--- 3755,3769 ----
  With argument N, reinsert the Nth most recently killed BibTeX item.
  See also the command \\[bibtex-yank-pop]]."
    (interactive "*p")
!   (bibtex-insert-kill (1- n))
    (setq this-command 'bibtex-yank))
  
  (defun bibtex-yank-pop (n)
!   "Replace just-yanked killed BibTeX item with a different item.
  This command is allowed only immediately after a `bibtex-yank' or a
! `bibtex-yank-pop'.  At such a time, the region contains a reinserted
! previously killed BibTeX item.  `bibtex-yank-pop' deletes that item
! and inserts in its place a different killed BibTeX item.
  
  With no argument, the previous kill is inserted.
  With argument N, insert the Nth previous kill.
***************
*** 3765,3771 ****
    (setq this-command 'bibtex-yank)
    (let ((inhibit-read-only t))
      (delete-region (point) (mark t))
!     (bibtex-insert-current-kill n)))
  
  (defun bibtex-empty-field ()
    "Delete the text part of the current field, replace with empty text."
--- 3777,3783 ----
    (setq this-command 'bibtex-yank)
    (let ((inhibit-read-only t))
      (delete-region (point) (mark t))
!     (bibtex-insert-kill n)))
  
  (defun bibtex-empty-field ()
    "Delete the text part of the current field, replace with empty text."
***************
*** 3797,3803 ****
  Check that no required fields are empty and formats entry dependent
  on the value of `bibtex-entry-format'.
  If the reference key of the entry is empty or a prefix argument is given,
! calculate a new reference key.  (Note: this will only work if fields in entry
  begin on separate lines prior to calling `bibtex-clean-entry' or if
  'realign is contained in `bibtex-entry-format'.)
  Don't call `bibtex-clean-entry' on @Preamble entries.
--- 3809,3815 ----
  Check that no required fields are empty and formats entry dependent
  on the value of `bibtex-entry-format'.
  If the reference key of the entry is empty or a prefix argument is given,
! calculate a new reference key.  (Note: this works only if fields in entry
  begin on separate lines prior to calling `bibtex-clean-entry' or if
  'realign is contained in `bibtex-entry-format'.)
  Don't call `bibtex-clean-entry' on @Preamble entries.
***************
*** 3807,3823 ****
    ;; is called by bibtex-reformat
    (interactive "P")
    (let ((case-fold-search t)
!         entry-type key)
!     (bibtex-beginning-of-entry)
!     (save-excursion
!       (when (re-search-forward bibtex-entry-maybe-empty-head nil t)
!         (setq entry-type (bibtex-type-in-head))
!         (setq key (bibtex-key-in-head))))
      ;; formatting
      (cond ((bibtex-string= entry-type "preamble")
             ;; (bibtex-format-preamble)
             (error "No clean up of @Preamble entries"))
!           ((bibtex-string= entry-type "string"))
            ;; (bibtex-format-string)
            (t (bibtex-format-entry)))
      ;; set key
--- 3819,3834 ----
    ;; is called by bibtex-reformat
    (interactive "P")
    (let ((case-fold-search t)
!         (start (bibtex-beginning-of-entry))
!         (_ (looking-at bibtex-entry-maybe-empty-head))
!         (entry-type (bibtex-type-in-head))
!         (key (bibtex-key-in-head)))
      ;; formatting
      (cond ((bibtex-string= entry-type "preamble")
             ;; (bibtex-format-preamble)
             (error "No clean up of @Preamble entries"))
!           ((bibtex-string= entry-type "string")
!            (setq entry-type 'string))
            ;; (bibtex-format-string)
            (t (bibtex-format-entry)))
      ;; set key
***************
*** 3825,3864 ****
        (setq key (bibtex-generate-autokey))
        ;; Sometimes bibtex-generate-autokey returns an empty string
        (if (or bibtex-autokey-edit-before-use (string= "" key))
!           (setq key (bibtex-read-key "Key to use: " key)))
!       (re-search-forward bibtex-entry-maybe-empty-head)
!       (if (match-beginning bibtex-key-in-head)
!           (delete-region (match-beginning bibtex-key-in-head)
!                          (match-end bibtex-key-in-head)))
!       (insert key))
  
      (unless called-by-reformat
!       (let* ((start (bibtex-beginning-of-entry))
!              (end (progn (bibtex-end-of-entry)
!                          (if (re-search-forward
!                               bibtex-entry-maybe-empty-head nil 'move)
!                              (goto-char (match-beginning 0)))
!                          (point)))
               (entry (buffer-substring start end))
               ;; include the crossref key in index
               (index (let ((bibtex-maintain-sorted-entries 'crossref))
!                       (goto-char start)
!                       (bibtex-entry-index)))
               error)
          ;; sorting
          (if (and bibtex-maintain-sorted-entries
                   (not (and bibtex-sort-ignore-string-entries
!                            (bibtex-string= entry-type "string"))))
              (progn
                (delete-region start end)
!               (setq error (not (bibtex-prepare-new-entry index)))
!               (insert entry)
!               (forward-char -1)
!               (bibtex-beginning-of-entry) ; moves backward
!               (re-search-forward bibtex-entry-head))
            (bibtex-find-entry key)
            (setq error (or (/= (point) start)
!                           (bibtex-find-entry key end))))
          (if error
              (error "New inserted entry yields duplicate key"))
          (dolist (buffer (bibtex-files-expand))
--- 3836,3877 ----
        (setq key (bibtex-generate-autokey))
        ;; Sometimes bibtex-generate-autokey returns an empty string
        (if (or bibtex-autokey-edit-before-use (string= "" key))
!           (setq key (if (eq entry-type 'string)
!                         (bibtex-read-string-key key)
!                       (bibtex-read-key "Key to use: " key))))
!       (save-excursion
!         (re-search-forward (if (eq entry-type 'string)
!                                bibtex-string-maybe-empty-head
!                              bibtex-entry-maybe-empty-head))
!         (if (match-beginning bibtex-key-in-head)
!             (delete-region (match-beginning bibtex-key-in-head)
!                            (match-end bibtex-key-in-head)))
!         (insert key)))
  
      (unless called-by-reformat
!       (let* ((end (save-excursion
!                     (bibtex-end-of-entry)
!                     (if (re-search-forward
!                          bibtex-entry-maybe-empty-head nil 'move)
!                         (goto-char (match-beginning 0)))
!                     (point)))
               (entry (buffer-substring start end))
               ;; include the crossref key in index
               (index (let ((bibtex-maintain-sorted-entries 'crossref))
!                       (bibtex-entry-index))) ; moves point to end of head
               error)
          ;; sorting
          (if (and bibtex-maintain-sorted-entries
                   (not (and bibtex-sort-ignore-string-entries
!                            (eq entry-type 'string))))
              (progn
                (delete-region start end)
!               (setq error (not (bibtex-prepare-new-entry index))
!                     start (point)) ; update start
!               (save-excursion (insert entry)))
            (bibtex-find-entry key)
            (setq error (or (/= (point) start)
!                           (bibtex-find-entry key nil end))))
          (if error
              (error "New inserted entry yields duplicate key"))
          (dolist (buffer (bibtex-files-expand))
***************
*** 3867,3876 ****
                  (error "Duplicate key in %s" (buffer-file-name)))))
  
          ;; Only update the list of keys if it has been built already.
!         (cond ((bibtex-string= entry-type "string")
                 (if (and (listp bibtex-strings)
                          (not (assoc key bibtex-strings)))
!                    (push (list key) bibtex-strings)))
                ;; We have a normal entry.
                ((listp bibtex-reference-keys)
                 (cond ((not (assoc key bibtex-reference-keys))
--- 3880,3891 ----
                  (error "Duplicate key in %s" (buffer-file-name)))))
  
          ;; Only update the list of keys if it has been built already.
!         (cond ((eq entry-type 'string)
                 (if (and (listp bibtex-strings)
                          (not (assoc key bibtex-strings)))
!                    (push (cons key (bibtex-text-in-string
!                                     (save-excursion (bibtex-parse-string)) t))
!                            bibtex-strings)))
                ;; We have a normal entry.
                ((listp bibtex-reference-keys)
                 (cond ((not (assoc key bibtex-reference-keys))
***************
*** 4041,4049 ****
      (goto-char pnt)))
  
  (defun bibtex-convert-alien (&optional read-options)
!   "Convert an alien BibTeX buffer to be fully usable by BibTeX mode.
  If a file does not conform with all standards used by BibTeX mode,
! some of the high-level features of BibTeX mode will not be available.
  This function tries to convert current buffer to conform with these standards.
  With prefix argument READ-OPTIONS non-nil, read options for reformatting
  entries from minibuffer."
--- 4056,4064 ----
      (goto-char pnt)))
  
  (defun bibtex-convert-alien (&optional read-options)
!   "Make an alien BibTeX buffer fully usable by BibTeX mode.
  If a file does not conform with all standards used by BibTeX mode,
! some of the high-level features of BibTeX mode are not available.
  This function tries to convert current buffer to conform with these standards.
  With prefix argument READ-OPTIONS non-nil, read options for reformatting
  entries from minibuffer."
***************
*** 4080,4088 ****
                 (<= pnt (bibtex-end-of-text-in-field bounds)))
            (setq name (bibtex-name-in-field bounds t)
                  compl (cond ((bibtex-string= name "crossref")
!                              'key)
                              ((bibtex-string= name "month")
                               bibtex-predefined-month-strings)
                              (t (if (listp bibtex-strings)
                                     bibtex-strings
                                   ;; so that bibtex-complete-string-cleanup
--- 4095,4106 ----
                 (<= pnt (bibtex-end-of-text-in-field bounds)))
            (setq name (bibtex-name-in-field bounds t)
                  compl (cond ((bibtex-string= name "crossref")
!                              ;; point is in crossref field
!                              'crossref-key)
                              ((bibtex-string= name "month")
+                              ;; point is in month field
                               bibtex-predefined-month-strings)
+                             ;; point is in other field
                              (t (if (listp bibtex-strings)
                                     bibtex-strings
                                   ;; so that bibtex-complete-string-cleanup
***************
*** 4090,4128 ****
                                   (bibtex-parse-strings
                                    (bibtex-string-files-init))))))
          (bibtex-beginning-of-entry)
!         (if (and (re-search-forward bibtex-entry-maybe-empty-head nil t)
!                  ;; point is inside a key
!                  (or (and (match-beginning bibtex-key-in-head)
!                           (>= pnt (match-beginning bibtex-key-in-head))
!                           (<= pnt (match-end bibtex-key-in-head)))
!                      ;; or point is on empty key
!                      (and (not (match-beginning bibtex-key-in-head))
!                           (= pnt (match-end 0)))))
!             (setq compl 'key))))
! 
!     (cond ((equal compl 'key)
!            ;; key completion
!            (setq choose-completion-string-functions
!                  (lambda (choice buffer mini-p base-size)
!                    (let ((choose-completion-string-functions nil))
!                      (choose-completion-string choice buffer base-size))
!                    (bibtex-complete-key-cleanup choice)
!                    ;; return t (required by 
choose-completion-string-functions)
!                    t))
!            (bibtex-complete-key-cleanup (bibtex-complete-internal
!                                          bibtex-reference-keys)))
  
            (compl
             ;; string completion
!            (setq choose-completion-string-functions
!                  `(lambda (choice buffer mini-p base-size)
!                     (let ((choose-completion-string-functions nil))
!                       (choose-completion-string choice buffer base-size))
!                     (bibtex-complete-string-cleanup choice ',compl)
!                     ;; return t (required by 
choose-completion-string-functions)
!                     t))
!            (bibtex-complete-string-cleanup (bibtex-complete-internal compl)
!                                            compl))
  
            (t (error "Point outside key or BibTeX field")))))
  
--- 4108,4167 ----
                                   (bibtex-parse-strings
                                    (bibtex-string-files-init))))))
          (bibtex-beginning-of-entry)
!         (cond ((and (looking-at bibtex-string-maybe-empty-head)
!                     ;; point is inside a string key
!                     (or (and (match-beginning bibtex-key-in-head)
!                              (>= pnt (match-beginning bibtex-key-in-head))
!                              (<= pnt (match-end bibtex-key-in-head)))
!                         ;; or point is on empty string key
!                         (and (not (match-beginning bibtex-key-in-head))
!                              (= pnt (match-end 0)))))
!                (setq compl 'string))
!               ((and (looking-at bibtex-entry-maybe-empty-head)
!                     ;; point is inside a key
!                     (or (and (match-beginning bibtex-key-in-head)
!                              (>= pnt (match-beginning bibtex-key-in-head))
!                              (<= pnt (match-end bibtex-key-in-head)))
!                         ;; or point is on empty key
!                         (and (not (match-beginning bibtex-key-in-head))
!                              (= pnt (match-end 0)))))
!                (setq compl 'key)))))
! 
!     (cond ((eq compl 'key)
!            ;; key completion: no cleanup needed
!            (let (completion-ignore-case)
!              (bibtex-complete-internal (bibtex-global-key-alist))))
! 
!           ((eq compl 'crossref-key)
!            ;; crossref key completion
!            (let (completion-ignore-case)
!              (setq choose-completion-string-functions
!                    (lambda (choice buffer mini-p base-size)
!                      (let ((choose-completion-string-functions nil))
!                        (choose-completion-string choice buffer base-size))
!                      (bibtex-complete-crossref-cleanup choice)
!                      ;; return t (needed by 
choose-completion-string-functions)
!                      t))
!              (bibtex-complete-crossref-cleanup (bibtex-complete-internal
!                                                 (bibtex-global-key-alist)))))
! 
!           ((eq compl 'string)
!            ;; string key completion: no cleanup needed
!            (let ((completion-ignore-case t))
!              (bibtex-complete-internal bibtex-strings)))
  
            (compl
             ;; string completion
!            (let ((completion-ignore-case t))
!              (setq choose-completion-string-functions
!                    `(lambda (choice buffer mini-p base-size)
!                       (let ((choose-completion-string-functions nil))
!                         (choose-completion-string choice buffer base-size))
!                       (bibtex-complete-string-cleanup choice ',compl)
!                       ;; return t (needed by 
choose-completion-string-functions)
!                       t))
!              (bibtex-complete-string-cleanup (bibtex-complete-internal compl)
!                                              compl)))
  
            (t (error "Point outside key or BibTeX field")))))
  
***************
*** 4193,4200 ****
  
  (defun bibtex-String (&optional key)
    "Insert a new BibTeX @String entry with key KEY."
!   (interactive (list (completing-read "String key: " bibtex-strings
!                                       nil nil nil 'bibtex-key-history)))
    (let ((bibtex-maintain-sorted-entries
           (unless bibtex-sort-ignore-string-entries
             bibtex-maintain-sorted-entries))
--- 4232,4238 ----
  
  (defun bibtex-String (&optional key)
    "Insert a new BibTeX @String entry with key KEY."
!   (interactive (list (bibtex-read-string-key)))
    (let ((bibtex-maintain-sorted-entries
           (unless bibtex-sort-ignore-string-entries
             bibtex-maintain-sorted-entries))
***************
*** 4242,4255 ****
            ;; Always ignore case,
            (case-fold-search t)
            (lst bibtex-generate-url-list)
-           (delim-regexp "\\`[{\"]\\(.*\\)[}\"]\\'")
            field url scheme)
        (while (setq scheme (pop lst))
          (when (and (setq field (cdr (assoc-string (caar scheme)
                                                  fields-alist t)))
                     ;; Always remove field delimiters
!                    (progn (if (string-match delim-regexp field)
!                               (setq field (match-string 1 field)))
                            (string-match (cdar scheme) field)))
            (setq lst nil)
          (if (null (cdr scheme))
--- 4280,4291 ----
            ;; Always ignore case,
            (case-fold-search t)
            (lst bibtex-generate-url-list)
            field url scheme)
        (while (setq scheme (pop lst))
          (when (and (setq field (cdr (assoc-string (caar scheme)
                                                  fields-alist t)))
                     ;; Always remove field delimiters
!                    (progn (setq field (bibtex-remove-delimiters-string field))
                            (string-match (cdar scheme) field)))
            (setq lst nil)
          (if (null (cdr scheme))
***************
*** 4259,4266 ****
                     (setq url (concat url step)))
                    ((setq field (cdr (assoc-string (car step) fields-alist t)))
                     ;; Always remove field delimiters
!                    (if (string-match delim-regexp field)
!                        (setq field (match-string 1 field)))
                     (if (string-match (nth 1 step) field)
                         (setq field (cond
                                      ((functionp (nth 2 step))
--- 4295,4301 ----
                     (setq url (concat url step)))
                    ((setq field (cdr (assoc-string (car step) fields-alist t)))
                     ;; Always remove field delimiters
!                    (setq field (bibtex-remove-delimiters-string field))
                     (if (string-match (nth 1 step) field)
                         (setq field (cond
                                      ((functionp (nth 2 step))
***************
*** 4268,4274 ****
                                      ((numberp (nth 2 step))
                                       (match-string (nth 2 step) field))
                                      (t
!                                      (replace-match (nth 2 step) nil nil 
field))))
                       ;; If the scheme is set up correctly,
                       ;; we should never reach this point
                       (error "Match failed: %s" field))
--- 4303,4309 ----
                                      ((numberp (nth 2 step))
                                       (match-string (nth 2 step) field))
                                      (t
!                                      (replace-match (nth 2 step) t nil 
field))))
                       ;; If the scheme is set up correctly,
                       ;; we should never reach this point
                       (error "Match failed: %s" field))




reply via email to

[Prev in Thread] Current Thread [Next in Thread]