home *** CD-ROM | disk | FTP | other *** search
/ InfoMagic Source Code 1993 July / THE_SOURCE_CODE_CD_ROM.iso / languages / elisp / packages / headers / text0000.txt < prev   
Encoding:
Text File  |  1990-07-22  |  38.0 KB  |  1,088 lines

  1. Enclosed is code to automatically create and maintain file headers.  This
  2. code is cleaner and mush more easily customized than any of my previous
  3. header postings.
  4.  
  5. New in this release is a set of customizations that allow headers to be
  6. created and maintained from the command line.  This is good for projects
  7. with some vi die-hards or when headers are being added in mass for the
  8. first time.  Example:
  9.    cd $EMACS/lisp
  10.    headers -make *.el
  11.  
  12. I have found file headers to be very valuable in project development. I
  13. always know who has been where and how many times they were there. Most
  14. often, I also know what they did.  The update count and last modified date
  15. are very useful in determining the proper version of a file to use.  I have
  16. often thought that it would be easier to integrate patches from individuals
  17. to gnu tools such as gcc and g++ if I knew for certain what version of a
  18. particular file they were working from.  If all had headers, I would see
  19. the update count and date in the "diff -c" output and would be able to find
  20. or recreate the file to patch accordingly.
  21.  
  22. In this message are three files:
  23.   header.el  -- Emacs header functions and customization instructions
  24.   headers.1  -- Man page for command line headers useage
  25.   headers    -- Shell script to hide the emacsness of command line headers.
  26.  
  27. ===============================================================
  28. Lynn Slater -- lrs@indetech.com or {sun, ames, pacbell}!indetech!lrs
  29. 42075 Lawrence Place, Fremont Ca 94538
  30. Office (415) 438-2048; Home (415) 796-4149; Fax (415) 438-2034
  31. ===============================================================
  32.  
  33. -*- File: ~/local/header.el
  34. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  35. ;; header.el --- Support for creation and automatic update of file headers
  36. ;; Author          : Lynn Slater
  37. ;; Created On      : Tue Aug  4 17:06:46 1987
  38. ;; Last Modified By: Lynn Slater
  39. ;; Last Modified On: Wed Nov  1 09:02:18 1989
  40. ;; Update Count    : 126
  41. ;; Status          : OK
  42. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  43. ;; Copyright (C) 1988 Lynn Randolph Slater, Jr.
  44. ;; Copyright (C) 1989 Free Software Foundation, Inc.
  45. ;; This file is compatable with GNU Emacs but is not part of the official
  46. ;; distribution (yet).
  47. ;;
  48. ;; This file is distributed in the hope that it will be useful,
  49. ;; but without any warranty.  No author or distributor
  50. ;; accepts responsibility to anyone for the consequences of using it
  51. ;; or for whether it serves any particular purpose or works at all,
  52. ;; unless he says so in writing.
  53. ;;
  54. ;; Everyone is granted permission to copy, modify and redistribute
  55. ;; this file, but only under the conditions described in the
  56. ;; document "GNU Emacs copying permission notice".   An exact copy
  57. ;; of the document is supposed to have been given to you along with
  58. ;; this file so that you can know how you may redistribute it all.
  59. ;; It should be in a file named COPYING.  Among other things, the
  60. ;; copyright notice and this notice must be preserved on all copies.
  61.  
  62. ;; This file adds support for the creation and automatic maintenence of file
  63. ;; headers such as the one above.
  64. ;;  User Commands:
  65. ;;   M-x make-header
  66. ;;   M-x make-revision
  67. ;;   M-x make-divisor
  68. ;;   M-x make-box-comment
  69. ;; Customizer commands
  70. ;;   register-file-header-action
  71. ;; Customizer variables
  72. ;;   header-copyright-notice
  73. ;;   make-header-hooks
  74. ;;
  75. ;; This file is particularly useful with the file-declarations package also
  76. ;;   by Lynn Slater.
  77. ;; Make this file header.el, byte-compile it in your path
  78. ;;
  79. ;; Read the first 20% of this file to learn how to customize.
  80.  
  81. ;; History         
  82. ;; 25-Sep-1989        Lynn Slater    
  83. ;;    Last Modified: Mon Sep 25 15:12:16 1989 #119 (Lynn Slater)
  84. ;;    added -default-mode ahd headerable-file-p
  85. ;; 10-Sep-1989        Lynn Slater    
  86. ;;    Last Modified: Wed Sep  6 17:36:00 1989 #110 (Lynn Slater)
  87. ;;    Seperated out header-mode-line and header-end. Headers are now really
  88. ;;    easy to modify.
  89. ;;    Added instructions for mode-specific headers.
  90. ;; 8-Aug-1989        Lynn Slater    
  91. ;;    Last Modified: Thu Aug  3 08:04:06 1989 #88 (Lynn Slater)
  92. ;;    Changed structure to allow site/user customized headers
  93. ;; 24-Jun-1989        Lynn Slater    
  94. ;;    Last Modified: Thu Jun 22 12:52:24 1989 #84 (Lynn Slater)
  95. ;;    restructured file, made the order of header actions not be significant.
  96. ;; 22-Jun-1989        Lynn Slater    
  97. ;;    Last Modified: Thu Jun 22 11:40:53 1989 #82 (Lynn Slater)
  98. ;;    Made file header actions easier to declare
  99. ;;    Made sccs and rcs support be user settable.
  100. ;;    Added c-style support
  101. ;; 25-Jan-1989        Lynn Slater    
  102. ;;    Last Modified: Wed Jan 25 12:03:23 1989 #78 (Lynn Slater)
  103. ;;    Added make-doc command
  104. ;; 25-Jan-1989        Lynn Slater    
  105. ;;    Last Modified: Tue Sep  6 07:57:22 1988 #77 (Lynn Slater)
  106. ;;    made the make-revision command include the last-modified data
  107. ;; 31-Aug-1988        Lynn Slater    
  108. ;;    Made the make-revision work in most modes
  109. ;;    Added the update-file-name command
  110. ;; 1-Mar-1988        Lynn Slater
  111. ;;   made the headers be as sensitive as possible to the proper
  112. ;;   comment chars.
  113. ;; 1-Mar-1988        Lynn Slater
  114. ;;   Made the mode be declared in each header
  115. ;; 26-Feb-1988        Lynn Slater
  116. ;;   added the make-revision call
  117. (provide 'header)
  118.  
  119. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  120. ;; This file has two major divisions: header creation and automatic header
  121. ;; maintenance.
  122. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  123.  
  124. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  125. ;; User/Site Customizable Variables
  126. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  127. (defvar header-max 2000
  128.   "Is the number of characters at the start of a buffer that will be
  129.    searched for header info to automatically update.")
  130.  
  131. (defvar header-copyright-notice nil
  132.   "A string containing a copyright disclaimer to be inserted into all headers.
  133.    This string needs no leading blanks and may contain any number of lines.
  134.    May be nil.")
  135.  
  136. (defvar make-header-hooks '(
  137.                 header-file-name
  138.                 header-copyright
  139.                 ;;header-sccs
  140.                 header-AFS
  141.                 header-author
  142.                 header-creation-date
  143.                 header-modification-author
  144.                 header-modification-date
  145.                 header-update-count
  146.                 header-status
  147.                 ;; Re-enable the following lines if you wish
  148.                 ;;header-blank
  149.                 ;;header-history
  150.                 ;;header-purpose
  151.                 ;;header-toc
  152.                 )
  153.  
  154.   "A list of functions which will insert the various header elements.
  155.    Each function is started on a new line and is expected to end in a new line.
  156.    Each function may insert any number of lines, but each line, including
  157.    the first, must be started with the value of the header-prefix-string
  158.    variable. (This variable holds the same value as would be returned by
  159.    calling 'header-prefix-string but is faster to access.)
  160.    Each function may set the following dynamically bound values:
  161.      header-prefix-string -- mode specific comment sequence
  162.      return-to        -- character position to which point will be moved
  163.                          after all header functions are processed. Any
  164.                          header function may set this, but only the last
  165.                          set will take effect.
  166.  
  167.    It is reasonable to locally set these hooks according to certain
  168.    modes. For example, a table of contents may only apply to code development
  169.    modes and 'header-shell should only apply to shell scripts. See the
  170.    instructions in header.el to do this.")
  171.  
  172. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  173. ;; Register the automatic actions to take for file headers during a save
  174. ;; See the second part of the file for explinations.
  175. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  176. (progn
  177.   (register-file-header-action "[ \t]Update Count[ \t]*: "  'update-write-count)
  178.   (register-file-header-action "[ \t]Last Modified By[ \t]*: "  'update-last-modifier)
  179.   (register-file-header-action "[ \t]Last Modified On[ \t]*: "  'update-last-modified-date)
  180.   ;;(register-file-header-action "^.* *\\(.*\\) *\\-\\-" 'update-file-name)
  181.   )
  182.  
  183. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  184. ;; Mode specific headers:
  185. ;;  Not all headers should look alike. Suppose that you have a unix script
  186. ;;  mode and want it to have a shell specifier line that all other headers
  187. ;;  do not have. To do this, Place the following lines
  188. ;;     (make-local-variable 'make-header-hooks)
  189. ;;     (setq make-header-hooks (cons 'header-shell 
  190. ;;                                    (default-value 'make-header-hooks)))  
  191. ;;  either in a hook called when the mode is invoked or in the code that
  192. ;;  establishes the mode.
  193. ;;
  194. ;;  Note that the header building blocks are automatically sensitive to the
  195. ;;  different comment characters in different modes.
  196. ;;
  197. ;; Mode specific update actions:
  198. ;;  Suppose something needs to be automatically maintained only in certian
  199. ;;  modes. An example is the .TH macro in man pages.  You can create mode
  200. ;;  specific update actions by placing lines such as the following in the
  201. ;;  mode creation function of in the mode hook.
  202. ;;    (make-local-variable 'file-header-update-alist)
  203. ;;    (register-file-header-action
  204. ;;      "^\.TH[ \t]+[^\" \t]+[ \t]+[^\" \t]+[ \t]+\"\\([^\"]*\\)\"" 
  205. ;;     'update-last-modified-date-macro)
  206. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  207.  
  208. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  209. ;; Define the individual header elements.  THESE ARE THE BUILDING BLOCKS
  210. ;; used to construct a site specific header.  You may add your own
  211. ;; functions either in this file or in your .emacs file.  The variable
  212. ;; make-header-hooks specifies the functions that will actually be called.
  213. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  214. (defun header-blank ()
  215.   "Places a blank line into a file header"
  216.   (insert header-prefix-string  "\n"))
  217.  
  218. (defun header-file-name ()
  219.   "Places the buffer's file name and leaves room for a description."
  220.   (insert header-prefix-string (buffer-name) " -- \n")
  221.   (setq return-to (1- (point))))
  222.  
  223. (defun header-author ()
  224.   "Inserts the current user's name as the module's author."
  225.   (insert header-prefix-string "Author          : " (user-full-name) "\n"))
  226.  
  227. (defun header-creation-date ()
  228.   "Places today's data as the file creation date."
  229.   (insert header-prefix-string "Created On      : "  (current-time-string) "\n"))
  230.  
  231. (defun header-modification-author ()
  232.   "Inserts the current user's name as the one who last modified the module.
  233.    This will be overwritten with each file save if all the
  234.    file-header-actions in the default header.el file are registered."
  235.   (insert header-prefix-string  "Last Modified By: \n"))
  236.  
  237. (defun header-modification-date ()
  238.   "Inserts todays date as the time of last modification.
  239.    This will be overwritten with each file save if all the
  240.    file-header-actions in the default header.el file are registered."
  241.   (insert header-prefix-string  "Last Modified On: \n"))
  242.  
  243. (defun header-update-count ()
  244.   "Inserts a count of the number of times the file has been saved.  This is
  245.   often a more useful measure of 'age' and 'modifications' than dates
  246.   recorded in the file system.  It is a handy code metric that is a
  247.   surprizingly good indication of file complexity and can often help
  248.   indicate which modules have been changed so much that they need a rethink.
  249.   It also assist recovery from source control mixups."  
  250.   (insert header-prefix-string  "Update Count    : 0\n"))
  251.  
  252. (defun header-status ()
  253.   "Inserts a status line that should be manually edited to reflect the
  254.    general condition of the entire module."
  255.   (insert header-prefix-string
  256.       "Status          : Unknown, Use with caution!\n"))
  257.  
  258. (defun header-history ()
  259.   "Inserts HISTORY line into header for later use by make-revision.
  260.    Without this, make history will insert after the header."
  261.   (insert header-prefix-string  "HISTORY\n"))
  262.  
  263. (defun header-purpose ()
  264.   "Inserts a line that starts a section that should describe the purpose of
  265.    the file/module."
  266.   (insert header-prefix-string  "PURPOSE\n"
  267.       header-prefix-string "    |>Description of modules purpose<|\n"))
  268.  
  269. (defun header-toc ()
  270.   "Inserts a line that starts a section that should describe each function
  271.    defined in the module that is significant to external users."
  272.   (insert header-prefix-string  "TABLE OF CONTENTS\n" header-prefix-string "\n"))
  273.  
  274. (defun header-rcs ()
  275.   "Inserts lines to record rcs information."
  276.   (insert header-prefix-string
  277.       "$Locker$\n"    
  278.       header-prefix-string
  279.       "$Log$\n"))
  280.  
  281. (defun header-sccs ()
  282.   "Inserts a line to record sccs information."
  283.   (insert header-prefix-string "SCCS Status     : %W%\t%G%\n"))
  284.  
  285. (defun header-AFS ()
  286.   "Inserts a line to record SHAPE information."
  287.   (insert header-prefix-string "AFSID           : $__Header$\n"))
  288.  
  289. (defun header-copyright ()
  290.   "Inserts the copyright notice stored in the variable header-copyright-notice.
  291.    This value may be nil."
  292.   (if header-copyright-notice
  293.       (let ((start (point)))
  294.     (insert header-copyright-notice)
  295.     (save-restriction
  296.       (narrow-to-region start (point))
  297.       (goto-char (point-min))
  298.       ;; I must now insert the header prefix.  I cannot just do a
  299.       ;; replace string because that would cause too many undo boundries.
  300.       (insert header-prefix-string)
  301.       (while (progn (skip-chars-forward "^\n") (looking-at "\n"))
  302.         (forward-char 1)
  303.         (insert header-prefix-string))
  304.       (goto-char (point-max)))
  305.     (insert "\n"))))
  306.  
  307. (defun header-shell ()
  308.   "Inserts a kernal shell specifier line. Uses the same shell named in
  309.    explicit-shell-file-name, the ESHELL environment variable, the SHELL
  310.     environment variable, or '/bin/sh'. (This is the same shell that the
  311.    shell command uses."
  312.   (insert "#!" (or (and (boundp 'explicit-shell-file-name)
  313.              explicit-shell-file-name)
  314.            (getenv "ESHELL")
  315.            (getenv "SHELL")
  316.            "/bin/sh")
  317.       "\n"))
  318.  
  319. (defun header-mode-line ()
  320.   "Inserts the mode line into the buffer."
  321.   (let* ((mode-declaration
  322.       (concat " -*- Mode: " (true-mode-name)
  323.           (if (assoc 'c-style (buffer-local-variables))
  324.               (concat "; C-Style: " (symbol-name c-style))
  325.             "")
  326.           " -*- "))
  327.      (md-length (length mode-declaration)))
  328.     (insert (cond
  329.          ((and comment-start (= (length comment-start) 1))
  330.           ;; I will presume that the comment start character is
  331.           ;; the filler character.
  332.           (concat comment-start comment-start
  333.               (make-string (/ (- 77 md-length) 2)
  334.                    (aref comment-start 0))
  335.               mode-declaration
  336.               (make-string (/ (- 78 md-length) 2)
  337.                    (aref comment-start 0))
  338.               ))
  339.          (comment-start-p
  340.           ;; I will presume that spaces will fill the gaps
  341.           (concat comment-start
  342.               (make-string (/ (- 79 md-length (length comment-start))
  343.                       2) ?\ )
  344.               mode-declaration))
  345.          (t;; there is no known comment-start. Presume lisp
  346.           (concat ";;"
  347.               (make-string (/ (- 77 md-length) 2) ?\;)
  348.               mode-declaration
  349.               (make-string (/ (- 78 md-length) 2) ?\;))))
  350.         "\n"))
  351.   )
  352.  
  353. (defun header-end-line ()
  354.   "Inserts a trailing divisor line for headers."
  355.   (insert (cond (comment-end-p comment-end)
  356.         ((and comment-start (= (length comment-start) 1))
  357.          (make-string 79 (aref comment-start 0)))
  358.         (comment-start-p comment-start)
  359.         (t       (make-string 79 ?\;)))
  360.       "\n\n"))
  361.  
  362. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  363. ;; System Variables -- Do not modify. Instead, call the functions that modify.
  364. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  365. (defvar file-header-update-alist ()
  366.   "Used by update file header to know what to do in the file. Is a list of
  367.    sets of cons cells where the car is a regexp string and the cdr is the
  368.    fcn to call if the string is found near the start of the file.")  
  369.  
  370. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  371. ;; User function to declare header actions on a save file.
  372. ;;   See examples at the end of this file.
  373. ;; Invoke from site-init.el or in .emacs.
  374. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  375. (defun register-file-header-action (regexp function-to-call)
  376.   "Accepts REGEXP and FUNCTION-TO-CALL. Records 
  377.    FUNCTION-TO-CALL as the appropiate action to take if the REGEXP is
  378.    found in the file header when a file is written.  The function will be
  379.    called with the cursor located just after the matched regexp.
  380.  
  381.    Calling this fcn twice with the same arguments overwrites
  382.    the previous FUNCTION-TO-CALL"
  383.   (let ((ml (assoc regexp file-header-update-alist)))
  384.     (if ml
  385.     (setcdr ml function-to-call);; overwrite old defn
  386.       ;; This entry is new to us. Add to the master alist
  387.       (setq file-header-update-alist
  388.         (cons (cons regexp function-to-call)
  389.           file-header-update-alist)))))
  390.  
  391. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  392. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  393. ;; Header and file division header creation code
  394. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  395. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  396. (defun true-mode-name ()
  397.   "Returns the name of the mode in such a form that the mode may be
  398.   re-established by calling the function named by appending '-name' to
  399.   this string.  This differs from the variable called mode-name in that
  400.   this is guaranteed to work while the values held by the variable may
  401.   have embedded spaces or other junk.
  402.  
  403.   THIS MODE NAME IS GUARANTEED OK TO USE IN THE MODE LINE."
  404.   (let ((major-mode-name (symbol-name major-mode)))
  405.     (capitalize (substring major-mode-name 0
  406.                (or   (string-match "-mode" major-mode-name)
  407.                  (length major-mode-name))))))
  408.  
  409.  
  410. (defun header-prefix-string ()
  411.   "Returns a mode specific prefix string for use in headers. Is sensitive
  412.    to the various language dependent comment coventions."
  413.   (let ((comment-end-p (and comment-end
  414.                 (not (string-equal comment-end "")))))
  415.     (cond
  416.      ((and comment-start (= (length comment-start) 1))
  417.       (concat comment-start comment-start " "))
  418.      ;; Special case, three letter comment starts where the first and
  419.      ;; second letters are the same. (i.e. c++ and ada)
  420.      ((and comment-start (= (length comment-start) 3)
  421.        (equal (aref comment-start 1) (aref comment-start 0)))
  422.       comment-start)
  423.      ;; Other three letter comment starts -> grab the middle character
  424.      ((and comment-start (= (length comment-start) 3))
  425.       (concat " " (list (aref comment-start 1)) " "))
  426.      ;; 
  427.      ((and comment-start (not comment-end-p))
  428.       ;; Note: no comment end implies that the full comment start must be
  429.       ;; used on each line.
  430.       comment-start)
  431.      (t                    ; I have no idea what is a good block 
  432.                     ; start character and will use lisp
  433.                     ; as a default.
  434.       ";; "))
  435.     ))
  436.  
  437. (defun make-header ()
  438.   "Makes a standard file header at the top of the buffer. A header is
  439.    composed of a mode line, a body, and an end line.  The body is
  440.    constructed by calling the functions in make-header-hooks.
  441.    The mode line and end lines start and terminate block comments while the
  442.    body lines just have to continue the comment. "
  443.   (interactive)
  444.   (beginning-of-buffer)       ;; leave the mark at the old location
  445.   ;; Dynamically bound some handy variables
  446.   (let ((return-to nil)       ;;; to be set by make-header-hooks functions
  447.     (header-prefix-string (header-prefix-string)) ;;; cache the result
  448.     (comment-start-p
  449.      (and comment-start (not (string-equal comment-start ""))))
  450.     (comment-end-p (and comment-end (not (string-equal comment-end "")))))
  451.  
  452.     ;; Do the header functions
  453.     (mapcar 'funcall make-header-hooks)
  454.  
  455.     ;; Move to wherever return-to was set
  456.     (if return-to (goto-char return-to))
  457.     ))
  458.  
  459. (defun make-revision ()
  460.   "Inserts a revision marker after the history line.  Makes the history
  461.    line if it does not already exist."
  462.   (interactive)
  463.   (let ((header-prefix-string (header-prefix-string))
  464.     (logical-comment-start
  465.      (if (= (length comment-start) 1)
  466.          (concat comment-start comment-start " ")
  467.        comment-start)))
  468.  
  469.     ;; Look for the History line
  470.     (beginning-of-buffer)         ;;; leave a mark where we were
  471.     (if (re-search-forward (concat "^\\("
  472.                    (regexp-quote (header-prefix-string))
  473.                    "\\|"
  474.                    (if (and comment-start
  475.                         (not (string-equal comment-start "")))
  476.                        (concat
  477.                     "\\|" (regexp-quote comment-start))
  478.                      "")
  479.                    "\\)"
  480.                    " *History")
  481.                header-max t)
  482.     (progn (end-of-line))
  483.       (progn
  484.     ;; We did not find a history line, add one
  485.     (goto-char (point-min))
  486.     ;; find the first line that is not part of the header
  487.     (while (and (< (point) header-max)
  488.             (looking-at
  489.              (concat "[ \t]*\\("
  490.                  (regexp-quote (header-prefix-string))
  491.                  (if (and comment-start
  492.                       (not (string-equal comment-start "")))
  493.                  (concat
  494.                   "\\|" (regexp-quote comment-start))
  495.                    "")
  496.                  (if (and comment-end
  497.                       (not (string-equal comment-end "")))
  498.                  (concat "\\|" (regexp-quote comment-end))
  499.                    "")
  500.                  "\\)")))
  501.       (forward-line 1))
  502.     (insert "\n" logical-comment-start
  503.         "HISTORY ")
  504.     (save-excursion (insert "\n" comment-end))))
  505.  
  506.     ;; We are now on the line with the history marker
  507.     
  508.     (insert "\n"
  509.         header-prefix-string
  510.         (current-d-m-y-string)
  511.         "\t\t"
  512.         (user-full-name)
  513.         ;;"\t|>Ident<|\n"
  514.         "\t\n"
  515.         header-prefix-string
  516.         "   "
  517.         )
  518.     ;; Now, add details about the history of the file before its modification
  519.     (if (save-excursion
  520.       (re-search-backward "Last Modified On[\t]*: \\(.+\\)$" nil t))
  521.     (progn
  522.       (insert "Last Modified: " (buffer-substring (match-beginning 1)
  523.                               (match-end 1)))
  524.       (if (save-excursion
  525.         (re-search-backward "Update Count[ \t]*: \\([0-9]+\\)$" nil t))
  526.           (insert " #" (buffer-substring (match-beginning 1)
  527.                          (match-end 1))))
  528.       (if (save-excursion
  529.         (re-search-backward "Last Modified By[ \t]*: \\(.+\\)$" nil t))
  530.           (insert " (" (buffer-substring (match-beginning 1)
  531.                          (match-end 1))
  532.               ")"))
  533.       (insert "\n" header-prefix-string "   ")))
  534.     ))
  535.  
  536. (defun make-divisor (&optional end-col)
  537.   "A divisor line is the comment start, filler, and the comment end"
  538.   (interactive)
  539.   (insert comment-start)
  540.   (if (= 1 (length comment-start))
  541.       (insert comment-start))
  542.   (insert (make-string (max 2
  543.                 (- (or end-col (- fill-column 2)) (length
  544.                                    comment-end)
  545.                    2 (current-column)))
  546.                        (aref comment-start
  547.                  (if (= 1 (length comment-start)) 0 1))
  548.                ))
  549.   (insert comment-end)
  550.   )
  551.  
  552.  
  553. (defun make-box-comment (&optional end-col)
  554.   "Inserts a box comment that is built using mode specific comment characters."
  555.   (interactive)
  556.   (if (not (= 0 (current-column))) (forward-line 1))
  557.   (insert comment-start)
  558.   (if (= 1 (length comment-start))
  559.       (insert comment-start))
  560.   (if (not (char-equal (preceding-char) ? )) (insert ? )) 
  561.   (insert (make-string (max 2
  562.                 (- (or end-col fill-column ) (length
  563.                                    comment-end)
  564.                    2 (current-column)))
  565.                        (aref comment-start
  566.                  (if (= 1 (length comment-start)) 0 1))
  567.                ))
  568.   (insert "\n" (header-prefix-string) )
  569.   (save-excursion
  570.     (insert "\n" (header-prefix-string)
  571.         (make-string (max 2
  572.                   (- (or end-col fill-column) (length
  573.                                  comment-end)
  574.                  2 (current-column)))
  575.              (aref comment-start
  576.                    (if (= 1 (length comment-start)) 0 1))
  577.              )
  578.         comment-end "\n")))
  579.  
  580. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  581.  
  582. (defun current-d-m-y-string ()
  583.   (let ((str (current-time-string)))
  584.     (concat (if (equal ?\  (aref str 8))
  585.                (substring str 9 10)
  586.                (substring str 8 10))
  587.         "-"
  588.         (substring str 4 7)
  589.         "-"
  590.         (substring str 20 24))))
  591.  
  592.  
  593. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  594. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  595. ;; Automatic Header update code
  596. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  597. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  598. (defun update-file-header ()
  599.   "If the file has been modified, searches the first header-max chars in the
  600.    buffer using the regexps in file-header-update-alist. When a match is
  601.    found, it applies the corresponding function with the point located just
  602.    after the match.  The functions can use (match-beginning) and
  603.    (match-end) calls to find out the strings that causes them to be invoked." 
  604.   (interactive)
  605.   (if (and (> (buffer-size) 100) (buffer-modified-p) (not buffer-read-only))
  606.       (save-excursion
  607.     (save-restriction ;; only search the header-max number of characters
  608.       (narrow-to-region 1 (min header-max (- (buffer-size) 1)))
  609.       (let ((patterns file-header-update-alist))
  610.         ;; do not record this call as a command in the command history
  611.         (setq last-command nil)
  612.         (while patterns
  613.           (goto-char (point-min))
  614.           (if (re-search-forward (car (car patterns)) nil t)
  615.           (progn
  616.             ;; position the cursor at the end of the match
  617.             (goto-char (match-end 0))
  618.             ;;(message "do            (funcall (cdr (car patterns)))))
  619.           (setq patterns (cdr patterns))
  620.           )
  621.         )))))
  622.  
  623. ;; Place the header update function as a write file action
  624. (if (not (memq 'update-file-header write-file-hooks))
  625.     (setq write-file-hooks (cons 'update-file-header write-file-hooks)))
  626.  
  627. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  628. ;; Now, define the individual file header actions.  These are the building
  629. ;; blocks of automatic header maintenance.
  630. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  631. (defun delete-and-forget-line ()
  632.   ;; does not place the line in the kill-ring
  633.   (let* ((start (point))
  634.      (stop  (progn (end-of-line) (point)))
  635.      (str   (buffer-substring start stop))
  636.      )
  637.   (delete-region start stop)
  638.   str))
  639.  
  640. (defun update-write-count ()
  641.   (let ((num)
  642.     (str  (delete-and-forget-line)))
  643.     (setq num (car (read-from-string str)))
  644.     (if (not (numberp num))
  645.     (progn
  646.       (insert str)
  647.       (error "invalid number for update count '%s'" str))
  648.       (progn
  649.     ;;(message "New write count=%s" num)
  650.     (insert (format "%s" (+ 1 num)))))
  651.     ))
  652.  
  653. (defun update-last-modifier ()
  654.   (delete-and-forget-line)
  655.   (insert (format "%s" (user-full-name)))
  656.   )
  657.  
  658. (defun update-last-modified-date ()
  659.   (delete-and-forget-line)
  660.   (insert (format "%s" (current-time-string)))
  661.   )
  662.  
  663. (defun update-file-name ()
  664.   (beginning-of-line)
  665.   ;; verify that we are looking at a file name for this mode
  666.   (if (looking-at
  667.        (concat (regexp-quote (header-prefix-string)) " *\\(.*\\) *\\-\\-"))
  668.       (progn
  669.     (goto-char (match-beginning 1))
  670.     (delete-region (match-beginning 1) (match-end 1))
  671.     (insert (file-name-nondirectory (buffer-file-name))" -")
  672.     )))
  673.  
  674.  
  675. ;;(setq file-header-update-alist nil)
  676. ;;(setq file-header-update-alist (cdr file-header-update-alist))
  677.  
  678. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  679. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  680. ;; Stand Alone Headers
  681. ;;
  682. ;; These functions give the ability to invoke headers from the command line.
  683. ;;   This if if yor site has non-productive vi users and you want them to
  684. ;;   be able to use headers as well.
  685. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  686. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  687. (defun headerable-file-p (file)
  688.   (not (if (not (file-exists-p file))
  689.        (message "\"%s\" does not exist!." file)
  690.      (if (file-symlink-p file)
  691.          (message "\"%s\" is a symolic link." file)
  692.        (if (file-directory-p file)
  693.            (message "\"%s\" is a directory." file)
  694.          )))))
  695.  
  696. (defun uniqueify-list (list)
  697.   (let ((rest list))
  698.     (while rest
  699.       (setcdr rest (delq (car rest) (cdr rest)))
  700.       (setq rest (cdr rest)))
  701.     list))
  702.  
  703. ;;(headerable-file-p "AFS")
  704. ;;(headerable-file-p "dbiogen.el")
  705. ;;(headerable-file-p "dbiogen.elc")
  706.  
  707. (defvar header-required-mode nil
  708.   "The mode we will force files to be in, irregareless of file suffix.")
  709.  
  710. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  711. ;; Define a touch-headers command. This depends upon Lynn Slater's
  712. ;; customizations to startup.el to allow command-line-hooks.
  713. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  714. (setq command-line-hooks (cons 'touch-headers command-line-hooks))
  715. (defun touch-headers ()
  716.   (if (or (string= argi "-touch") (string= argi "-touch-headers"))
  717.       (let ((trim-versions-without-asking t)
  718.         (executing-macro "true"));; suppress "Mark Set" messages
  719.     ;; Consume all following arguments until one starts with a "-"
  720.     (while (and command-line-args-left
  721.             (not (char-equal ?- (aref (car command-line-args-left) 0))))
  722.       (if (headerable-file-p (car command-line-args-left))
  723.           (progn
  724.         (find-file (car command-line-args-left))
  725.         (make-revision)
  726.         (write-file nil)
  727.         (kill-buffer (current-buffer))))
  728.       (setq command-line-args-left (cdr command-line-args-left))
  729.       ))))
  730.  
  731. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  732. ;; Define a make-headers command line option.
  733. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  734. (setq command-line-hooks (cons 'make-headers command-line-hooks))
  735. (defun make-headers ()
  736.   (if (or (string= argi "-make-headers") (string= argi "-make"))
  737.       (let ((trim-versions-without-asking t)
  738.         (executing-macro "true"));; suppress "Mark Set" messages
  739.     ;; Consume all following arguments until one starts with a "-"
  740.     (while (and command-line-args-left
  741.             (not (char-equal ?- (aref (car command-line-args-left) 0))))
  742.      
  743.       (if (headerable-file-p (car command-line-args-left))
  744.           (progn
  745.         (find-file (car command-line-args-left))
  746.         (if header-required-mode
  747.             (funcall header-required-mode))
  748.         (make-header)
  749.         (write-file nil)
  750.         (message "\tMode was %s" major-mode)
  751.         (kill-buffer (current-buffer))))
  752.       (setq command-line-args-left (cdr command-line-args-left))
  753.       ))))
  754.  
  755. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  756. ;; Define a -default-mode command line option.
  757. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  758. (setq command-line-hooks (cons 'set-header-mode command-line-hooks))
  759. (defun set-header-mode ()
  760.   (if (or (string= argi "-default-mode")
  761.       (string= argi "-default"))
  762.       (let ((trim-versions-without-asking t)
  763.         (executing-macro "true");; suppress "Mark Set" messages
  764.         (mode (intern (car command-line-args-left))))
  765.     (if (memq mode (mapcar 'cdr auto-mode-alist))
  766.         (progn
  767.           (setq default-major-mode mode)
  768.           (message "Default mode is %s" default-major-mode)
  769.           (setq command-line-args-left (cdr command-line-args-left)))
  770.       (message "Mode \"%s\" is invalid. Try one of %s" mode
  771.            (uniqueify-list (mapcar 'cdr auto-mode-alist)))
  772.       (kill-emacs 1))
  773.     )))
  774.  
  775. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  776. ;; Define a -required-mode command line option.
  777. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  778. (setq command-line-hooks (cons 'set-header-required-mode command-line-hooks))
  779. (defun set-header-required-mode ()
  780.   (if (or (string= argi "-required-mode")
  781.       (string= argi "-mode"))
  782.       (let ((trim-versions-without-asking t)
  783.         (executing-macro "true");; suppress "Mark Set" messages
  784.         (mode (intern (car command-line-args-left))))
  785.     (if (memq mode (mapcar 'cdr auto-mode-alist))
  786.         (progn
  787.           (setq header-required-mode mode)
  788.           (message "Required mode is %s" header-required-mode)
  789.           (setq command-line-args-left (cdr command-line-args-left)))
  790.       (message "Mode \"%s\" is invalid. Try one of %s" mode
  791.            (uniqueify-list (mapcar 'cdr auto-mode-alist)))
  792.       (kill-emacs 1))
  793.     )))
  794.  
  795.  
  796. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  797. ;; Things in the works or still to do.
  798. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  799. ;; effort.el -- allows an "effort" to be resgistered in the mode line much
  800. ;; like the mode is. The effort then determines some header characteristics
  801. ;; such as copyright.  Typical efforts would be 'gdb 'gcc, 'g++, 'emacs, etc.
  802. ;; This would let the copyright (and c-style) be adjusted even within
  803. ;; common modes.
  804. ;;
  805. ;; need ez access to values in the header 
  806. ;; need a headerp fcn
  807. ;;
  808. ;; auto make-revision if current user is not same as last modifier
  809. ;;   this would give a history of who touched what.
  810.  
  811. -*- End File: ~/local/header.el
  812.  
  813. -*- File: ~/local/headers.1
  814. .\"                             -*- Mode: Nroff -*- 
  815. .\" headers.1 -- Man page for headers
  816. .\" 
  817. .\" Copyright (c) 1989, Independence Technologies Inc. (ITI)
  818. .\" All Rights Reserved.
  819. .\" 
  820. .\" This is an unpublished work of ITI which is protected under 
  821. .\" the copyright laws of the United States and a trade secret
  822. .\" of ITI. It may not be used, copied, disclosed or transferred
  823. .\" other than in accordance with the written permission of ITI.
  824. .\" 
  825. .\" Shape           : $__Header$
  826. .\" Author          : Lynn Slater
  827. .\" Created On      : Wed Sep  6 14:55:42 1989
  828. .\" Last Modified By: Lynn Slater
  829. .\" Last Modified On: Mon Sep 25 16:23:12 1989
  830. .\" Update Count    : 21
  831. .\" Status          : Unknown, Use with caution!
  832. .\" 
  833. .\" HISTORY
  834. .\" 25-Sep-1989        Lynn Slater    
  835. .\"    Last Modified: Mon Sep 25 15:28:43 1989 #19 (Lynn Slater)
  836. .\"    Mask mode
  837. .\"    Brought doc up to date. -default-mode,  make-mode
  838. .\" 
  839. .\" 
  840. .TH HEADERS 1 "Mon Sep 25 16:23:11 1989" "ITI/Emacs"
  841. .SH NAME
  842. headers \- Automatic Header Maintenance in conformance to ITI standards
  843. .SH SYNOPSIS
  844. .B headers
  845. [
  846. .B -mode
  847. .IR mode
  848. ] [
  849. .B -default-mode
  850. .IR mode
  851. ] [
  852. .B -make
  853. .IR datafile .\|.\|.
  854. ] [
  855. .B -touch
  856. .IR datafile .\|.\|.
  857. ] [
  858. .B -TOC
  859. .IR datafile .\|.\|.
  860. ] [
  861. .B -SYNOPSIS
  862. .IR datafile .\|.\|.
  863. ]
  864. .LP
  865. .B emacs -batch -l headers
  866. [
  867. .B -mode
  868. .IR mode
  869. ] [
  870. .B -default-mode
  871. .IR mode
  872. ] [
  873. .B -make
  874. .IR datafile .\|.\|.
  875. ] [
  876. .B -touch
  877. .IR datafile .\|.\|.
  878. ] [
  879. .B -TOC
  880. .IR datafile .\|.\|.
  881. ] [
  882. .B -SYNOPSIS
  883. .IR datafile .\|.\|.
  884. ]
  885. .LP
  886. .SH DESCRIPTION
  887. .LP
  888. This processor adds ITI standard headers into 
  889. .I existing
  890. non-directory non-linked files. It can
  891. also insert ITI standard revision markings.
  892. .RE
  893. .LP
  894. .SH OPTIONS
  895. .TP
  896. .B "\-default-mode"
  897. Sets the 
  898. .I default 
  899. editing mode and header style for those files without a
  900. standard suffix.
  901. Normally, the mode is determined by the file suffix. Suffixes map to modes
  902. as described below.
  903. .TP
  904. .B "\-mode"
  905. Sets the 
  906. editing mode and header style for all remaining files processed by the make option, irregardless of
  907. their file suffix or existing file header.
  908. .TP
  909. .B "\-make"
  910. Load or create all the listed data files in either the mode implied by
  911. their suffix or in the default mode. Make and insert a ITI standard header
  912. into the file and save it.
  913.  
  914. .TP
  915. .B "\-touch"
  916. Load or create all the listed data files and add a ITI standard revision
  917. marker. If the file has a header, the mode in the mode line will take
  918. precidence over the default mode or the mode implied by the file suffix. 
  919. Save the file after updating all other present header fields.
  920.  
  921. .TP
  922. .B "-TOC"
  923. Load or create all the listed files and replace the table of contents with
  924. a new one extracted from the function headers. The extraction will only
  925. work if file has existing headers in conformance with ITI coding standards.
  926.  
  927. This option also updates the header information before saving the file.
  928.  
  929. .TP
  930. .B "\-SYNOPSIS"
  931. Load or create all the listed files. Scan each one for standard function
  932. headers. Delete the synopsis section and replace it with the function
  933. declaration (indented following comment marks). If you have done your
  934. function declarations properly, they should be acceptable as a synopsis. 
  935.  
  936. In C++ mode, a function declaration begins just after the function header
  937. and ends with the close paren of the argument list.
  938.  
  939. In C mode, a function declaration begins just after the function header
  940. and ends with the next blank line.  This should work fine if you seperate
  941. the argument declarations from internal variable declarations.
  942.  
  943. Comments are converted to a slightly different syntax when the
  944. function declaration is moved; this prevents nested comments.
  945.  
  946. .TP
  947. .B "Mode and Suffix map"
  948. .RS
  949. .TP15
  950. ada-mode
  951. (.ada .a)
  952. Ada Mode is the major mode for editing Ada code.  
  953. .TP15
  954. awk-mode
  955. (no suffixes)
  956. Set up for editing awk code (a minor variation on C mode).
  957. .TP15
  958. c-mode
  959. (.c .h .y .l .tcl .tcl-script) (but not .cc )
  960. Major mode for editing C code.
  961. .TP15
  962. c++-mode
  963. (.cc .hxx .cxx)
  964. Major mode for editing C++ code.  Very much like editing C code, but
  965. understands more constructs and uses
  966. different comments.
  967. .TP15
  968. emacs-lisp-mode
  969. (.el)
  970. Major mode for editing Lisp code to run in Emacs.
  971. .TP15
  972. fortran-mode
  973. (.f)
  974. Major mode for editing fortran code.
  975. .TP15
  976. Fundamental-mode
  977. (no suffixes)
  978. A generic editing mode
  979. .TP15
  980. LaTeX-mode
  981. (.sty .bbl)
  982. Major mode for editing files of input for TeX or LaTeX.
  983. .TP15
  984. lisp-mode
  985. (.lisp .lsp .ml)
  986. Major mode for editing Lisp code for Lisps other than GNU Emacs Lisp.
  987. .TP15
  988. make-mode
  989. (.mk)
  990. Mode for eciting of make scripts.
  991. .TP15
  992. mask-mode
  993. (.m)
  994. Mode for eciting of mask files.
  995. .TP15
  996. nroff-mode
  997. (no suffixes)
  998. Major mode for editing text intended for nroff to format.
  999. .TP15
  1000. prolog-mode
  1001. (.pl .prolog)
  1002. Major mode for editing Prolog code for Prologs.
  1003. .TP15
  1004. scheme-mode
  1005. (.scm)
  1006. Major mode for editing Scheme code.
  1007. .TP15
  1008. scribe-mode
  1009. (.mss)
  1010. Major mode for editing scribe (a document processor) files.
  1011. .TP15
  1012. script-mode
  1013. (no suffixes)
  1014. Mode for eciting of shell scripts.
  1015. .TP15
  1016. sql-mode
  1017. (.sql .isql)
  1018. Mode for editing sql scripts and sending them to other processes.
  1019. .TP15
  1020. TeX-mode
  1021. (.tex .TeX)
  1022. Major mode for editing files of input for TeX or LaTeX.
  1023. .TP15
  1024. texinfo-mode 
  1025. (.texinfo)
  1026. Major mode for editing texinfo files.
  1027. .TP15
  1028. text-mode
  1029. (.text .bib .article .letter )
  1030. Major mode for editing text intended for humans to read. 
  1031. .RE
  1032. .LP
  1033. The initial default mode is fundemental-mode
  1034. .LP
  1035. .SH FILES
  1036. .SH DIAGNOSTICS
  1037. Hopefully self-explainatory.
  1038. .IP
  1039. .SH EXAMPLES
  1040. .PD 0
  1041. To add some headers to non-headed existing c files
  1042. .nf
  1043.   headers -make *.c
  1044. .fi
  1045.  
  1046. To insert some revison notifications
  1047. .nf
  1048.   headers -touch t1.c t2.h
  1049. .fi
  1050.  
  1051. To start some script mode files
  1052. .nf
  1053.   headers -mode script-mode -make script1 script2
  1054. .fi
  1055.  
  1056. To do all of the above
  1057. .nf
  1058.   headers -make *.c -touch t1.c t2.h \\ 
  1059.     -mode script-mode -make script1 script2
  1060. .fi
  1061.  
  1062. To bring the file and function headers of a set of files up to date. Also
  1063. record last modifier and other useful information.
  1064. .nf
  1065.   headers -TOC *.c -SYNOPSIS *.c
  1066. .fi
  1067.  
  1068. .SH BUGS 
  1069. The synopsis extraction is not very robust and can be confused by
  1070. comment characters in strings or by unusual styles.
  1071.  
  1072. .LP
  1073. .PD
  1074. .SH SEE ALSO
  1075. .BR emacs (1)
  1076. .LP
  1077.  
  1078. -*- End File: ~/local/headers.1
  1079.  
  1080.  
  1081. -*- File: /usr/local/bin/headers
  1082. #!/bin/sh
  1083. emacs -batch -l headers $*
  1084.  
  1085. -*- End File: /usr/local/bin/headers
  1086.  
  1087.  
  1088.