(;-- defun
(and (eq type 'defun)
(looking-at verilog-zero-indent-re))
(if (/= (current-column) 0)
(delete-horizontal-space)))
(;-- declaration
(and (or
(eq type 'defun)
(eq type 'block))
(looking-at verilog-declaration-re))
(verilog-indent-declaration ind))
(;-- Everything else
t
(let ((val (eval (cdr (assoc type verilog-indent-alist)))))
(if (/= (current-column) val)
(progn
(delete-horizontal-space)
(indent-to val)))
))
)
(if (looking-at "[ \t]+$")
(skip-chars-forward " \t"))
indent-str ; Return indent data
)
)
(defun verilog-indent-level ()
"Return the indent-level the current statement has."
(save-excursion
(let (par-pos)
(beginning-of-line)
(setq par-pos (verilog-parenthesis-depth))
(while par-pos
(goto-char par-pos)
(beginning-of-line)
(setq par-pos (verilog-parenthesis-depth)))
(skip-chars-forward " \t")
(current-column))))
(defun verilog-case-indent-level ()
"Return the indent-level the current statement has.
Do not count named blocks or case-statements."
(save-excursion
(skip-chars-forward " \t")
(cond
((looking-at verilog-named-block-re)
(current-column))
((and (not (looking-at verilog-case-re))
(looking-at "^[^:;]+[ \t]*:"))
(verilog-re-search-forward ":" nil t)
(skip-chars-forward " \t")
(current-column))
(t
(current-column)))))
(defun verilog-indent-comment ()
"Indent current line as comment."
(let* ((stcol
(cond
((verilog-in-star-comment-p)
(save-excursion
(re-search-backward "/\\*" nil t)
(1+(current-column))))
(comment-column
comment-column )
(t
(save-excursion
(re-search-backward "//" nil t)
(current-column)))
)
))
(delete-horizontal-space)
(indent-to stcol)
stcol)
)
(defun verilog-more-comment (&optional arg)
"Make more comment lines like the previous "
(let* ((star 0)
(stcol
(cond
((verilog-in-star-comment-p)
(save-excursion
(setq star 1)
(re-search-backward "/\\*" nil t)
(1+(current-column))))
(comment-column
comment-column )
(t
(save-excursion
(re-search-backward "//" nil t)
(current-column)))
)
))
(progn
(indent-to stcol)
(if (and star
(save-excursion
(forward-line -1)
(skip-chars-forward " \t")
(looking-at "\*")
)
)
(insert "* "))
)
)
)
(defun verilog-comment-indent (&optional arg)
"return the column number the line should be indented to."
(cond
((verilog-in-star-comment-p)
(save-excursion
(re-search-backward "/\\*" nil t)
(1+(current-column))))
( comment-column
comment-column )
(t
(save-excursion
(re-search-backward "//" nil t)
(current-column)))
)
)
;;;
(defun verilog-pretty-declarations ()
"Line up declarations arround point"
(interactive)
(save-excursion
(if (progn
(verilog-beg-of-statement-1)
(looking-at verilog-declaration-re))
(let* ((m1 (make-marker))
(e) (r)
(here (point))
(start
(progn
(verilog-beg-of-statement-1)
(while (looking-at verilog-declaration-re)
(beginning-of-line)
(setq e (point))
(verilog-backward-syntactic-ws)
(backward-char)
(verilog-beg-of-statement-1)) ;Ack, need to grok `define
e))
(end
(progn
(goto-char here)
(verilog-end-of-statement)
(setq e (point)) ;Might be on last line
(verilog-forward-syntactic-ws)
(while (looking-at verilog-declaration-re)
(beginning-of-line)
(verilog-end-of-statement)
(setq e (point))
(verilog-forward-syntactic-ws)
)
e))
(edpos (set-marker (make-marker) end))
(ind)
(base-ind
(progn
(goto-char start)
(verilog-do-indent (verilog-calculate-indent))
(verilog-forward-ws&directives)
(current-column)
))
)
(goto-char end)
(goto-char start)
(if (> (- end start) 100)
(message "Lining up declarations..(please stand by)"))
;; Get the begining of line indent first
(while (progn (setq e (marker-position edpos))
(< (point) e))
(delete-horizontal-space)
(indent-to base-ind)
(forward-line))
;; Now find biggest prefix
(setq ind (verilog-get-lineup-indent start edpos))
;; Now indent each line.
(goto-char start)
(while (progn (setq e (marker-position edpos))
(setq r (- e (point)))
(> r 0))
(setq e (point))
(message "%d" r)
(cond
((looking-at verilog-declaration-re-1)
(let ((p (match-end 0)))
(set-marker m1 p)
(if (verilog-re-search-forward "[[#`]" p 'move)
(progn
(forward-char -1)
(just-one-space)
(goto-char (marker-position m1))
(just-one-space)
(indent-to ind)
)
(progn
(just-one-space)
(indent-to ind))
)
))
((verilog-continued-line-1 start)
(goto-char e)
(delete-horizontal-space)
(indent-to ind))
(t ; Must be comment or white space
(goto-char e)
(verilog-forward-ws&directives)
(forward-line -1)
)
)
(forward-line 1)
)
(message "")
)
)
)
)
(defun verilog-indent-declaration (baseind)
"Indent current lines as declaration, lining up the variable names
based on previous declaration's indentation."
(interactive)
(let ((pos (point-marker))
(lim (save-excursion
(verilog-re-search-backward
"\\(\\<begin\\>\\)\\|\\(\\<module\\>\\)" nil 'move)
(point)))
(ind)
(val)
(m1 (make-marker))
)
;; Use previous declaration (in this module) as template.
(if (verilog-re-search-backward verilog-declaration-re-1 lim t)
(progn
(goto-char (match-end 0))
(skip-chars-forward " \t")
(setq ind (current-column))
(goto-char pos)
(setq val (+ baseind (eval (cdr (assoc 'declaration verilog-indent-alist)))))
(if (/= (current-column) val)
(progn
(delete-horizontal-space)
(indent-to val)))
(if (looking-at verilog-declaration-re-2)
(let ((p (match-end 0)))
(set-marker m1 p)
(if (verilog-re-search-forward "[[#`]" p 'move)
(progn
(forward-char -1)
(just-one-space)
(goto-char (marker-position m1))
(just-one-space)
(indent-to ind)
)
(if (/= p ind)
(progn
(just-one-space)
(indent-to ind))
)
)
)
)
)
(let ((val (+ baseind (eval (cdr (assoc 'declaration verilog-indent-alist))))))
(if (/= val (current-column))
(progn
(delete-horizontal-space)
(indent-to val))))
)
(goto-char pos)
)
)
; "Return the indent level that will line up several lines within the region
;from b to e nicely. The lineup string is str."
(defun verilog-get-lineup-indent (b edpos)
(save-excursion
(let ((ind 0) e)
(goto-char b)
;; Get rightmost position
(while (progn (setq e (marker-position edpos))
(< (point) e))
(if (verilog-re-search-forward verilog-declaration-re-1 e 'move)
(progn
(goto-char (match-end 0))
(verilog-backward-syntactic-ws)
(if (> (current-column) ind)
(setq ind (current-column)))
(goto-char (match-end 0)))))
(if (> ind 0)
(1+ ind)
;; No lineup-string found
(goto-char b)
(end-of-line)
(skip-chars-backward " \t")
(1+ (current-column))))))
;; A useful mode debugging aide
(defun verilog-comment-depth (type val)
""
(save-excursion
(let
((b (prog2
(beginning-of-line)
(point-marker)
(end-of-line)))
(e (point-marker)))
(if (re-search-backward " /\\* \[#-\]# \[a-zA-Z\]+ \[0-9\]+ ## \\*/" b t)
(progn
(replace-match " /* -# ## */")
(end-of-line))
(progn
(end-of-line)
(insert " /* ## ## */"))))
(backward-char 6)
(insert
(format "%s %d" type val))
)
)
;;;
;;;
;;; Completion
;;;
(defvar verilog-str nil)
(defvar verilog-all nil)
(defvar verilog-pred nil)
(defvar verilog-buffer-to-use nil)
(defvar verilog-flag nil)
(defvar verilog-toggle-completions nil
"*Non-nil means \\<verilog-mode-map>\\[verilog-complete-word] should try all
possible completions one by one.
Repeated use of \\[verilog-complete-word] will show you all of them.
Normally, when there is more than one possible completion,
it displays a list of all possible completions.")
(defvar verilog-type-keywords
'("buf" "bufif0" "bufif1" "cmos"
"defparam" "inout" "input"
"integer" "nand" "nmos" "nor" "not"
"notif0" "notif1" "or" "output"
"parameter"
"pmos" "pull0" "pull1" "pullup"
"rcmos" "real" "realtime" "reg" "rnmos"
"rpmos" "rtran"
"rtranif0" "rtranif1" "time" "tran"
"tranif0" "tranif1" "tri" "tri0" "tri1"
"triand" "trior" "trireg" "wand"
"wire" "wor" "xnor" "xor" )
"*Keywords for types used when completing a word in a declaration or parmlist.
\(eg. integer, real, char.) The types defined within the Verilog program
will be completed runtime, and should not be added to this list.")
(defvar verilog-defun-keywords
'("begin" "function" "task" "initial"
"always" "assign" "posedge" "negedge"
"endmodule")
"*Keywords to complete when standing at first word of a line in declarative scope.
\(eg. initial, always, begin, assign.)
The procedures and variables defined within the Verilog program
will be completed runtime and should not be added to this list.")
(defvar verilog-block-keywords
'("begin" "fork" "join" "case"
"end" "if" "else" "for" "while"
"repeat")
"*Keywords to complete when standing at first word of a line in behavioral scope.
\(eg. begin, if, then, else, for, fork.)
The procedures and variables defined within the Verilog program
will be completed runtime and should not be added to this list.")
(defvar verilog-tf-keywords
'("begin" "fork" "join" "case"
"end" "endtask" "endfunction" "if"
"else" "for" "while" "repeat")
"*Keywords to complete when standing at first word of a line in a task or function
scope.
\(eg. begin, if, then, else, for, fork.)
The procedures and variables defined within the Verilog program
will be completed runtime and should not be added to this list.")
(defvar verilog-case-keywords
'("begin" "fork" "join" "case"
"end" "endcase" "if" "else" "for"
"repeat")
"*Keywords to complete when standing at first word of a line in behavioral scope.
\(eg. begin, if, then, else, for, fork.)
The procedures and variables defined within the Verilog program
will be completed runtime and should not be added to this list.")
(defvar verilog-separator-keywords
'("else" "then" "begin")
"*Keywords to complete when NOT standing at the first word of a statement.
\(eg. else, then.)
Variables and function names defined within the
Verilog program are completed runtime and should not be added to this list.")
(defun verilog-string-diff (str1 str2)
"Return index of first letter where STR1 and STR2 differs."
(catch 'done
(let ((diff 0))
(while t
(if (or (> (1+ diff) (length str1))
(> (1+ diff) (length str2)))
(throw 'done diff))
(or (equal (aref str1 diff) (aref str2 diff))
(throw 'done diff))
(setq diff (1+ diff))))))
;; Calculate all possible completions for functions if argument is `function',
;; completions for procedures if argument is `procedure' or both functions and
;; procedures otherwise.
(defun verilog-func-completion (type)
;; Build regular expression for module/task/function names
(if (string= verilog-str "")
(setq verilog-str "[a-zA-Z_]"))
(let ((verilog-str (concat (cond
((eq type 'module) "\\<\\(module\\)\\s +")
((eq type 'tf) "\\<\\(task\\|function\\)\\s +")
(t "\\<\\(task\\|function\\|module\\)\\s +"))
"\\<\\(" verilog-str "[a-zA-Z0-9_.]*\\)\\>"))
match)
(if (not (looking-at verilog-defun-re))
(verilog-re-search-backward verilog-defun-re nil t))
(forward-char 1)
;; Search through all reachable functions
(goto-char (point-min))
(while (verilog-re-search-forward verilog-str (point-max) t)
(progn (setq match (buffer-substring (match-beginning 2)
(match-end 2)))
(if (or (null verilog-pred)
(funcall verilog-pred match))
(setq verilog-all (cons match verilog-all)))))
(if (match-beginning 0)
(goto-char (match-beginning 0)))))
(defun verilog-get-completion-decl ()
;; Macro for searching through current declaration (var, type or const)
;; for matches of `str' and adding the occurence tp `all'
(let ((end (save-excursion (verilog-declaration-end)
(point)))
match)
;; Traverse lines
(while (< (point) end)
(if (verilog-re-search-forward verilog-declaration-re-1 (verilog-get-end-of-line)
t)
;; Traverse current line
(while (and (verilog-re-search-forward
(concat "\\((\\|\\<\\(var\\|type\\|const\\)\\>\\)\\|"
verilog-symbol-re)
(verilog-get-beg-of-line) t)
(not (match-end 1)))
(setq match (buffer-substring (match-beginning 0) (match-end 0)))
(if (string-match (concat "\\<" verilog-str) match)
(if (or (null verilog-pred)
(funcall verilog-pred match))
(setq verilog-all (cons match verilog-all))))))
(if (verilog-re-search-forward "\\<record\\>"
(verilog-get-end-of-line) t)
(verilog-declaration-end)
(forward-line 1)))))
(defun verilog-type-completion ()
"Calculate all possible completions for types."
(let ((start (point))
goon)
;; Search for all reachable type declarations
(while (or (verilog-beg-of-defun)
(setq goon (not goon)))
(save-excursion
(if (and (< start (prog1 (save-excursion (verilog-end-of-defun)
(point))
(forward-char 1)))
(verilog-re-search-forward
"\\<type\\>\\|\\<\\(begin\\|function\\|procedure\\)\\>"
start t)
(not (match-end 1)))
;; Check current type declaration
(verilog-get-completion-decl))))))
(defun verilog-var-completion ()
"Calculate all possible completions for variables (or constants)."
nil)
; Not done yet; in 1.99 perhaps
; (let ((start (point))
; goon twice)
; ;; Search for all reachable var declarations
; (while (or (verilog-beg-of-defun)
; (setq goon (not goon)))
; (save-excursion
; (if (> start (prog1 (save-excursion (verilog-end-of-defun)
; (point))))
; () ; Declarations not reacable
; (cond ((and (verilog-re-search-forward verilog-declaration-re start t)
; ;; Check var/const declarations
; (verilog-get-completion-decl)))))))))
(defun verilog-keyword-completion (keyword-list)
"Give list of all possible completions of keywords in KEYWORD-LIST."
(mapcar '(lambda (s)
(if (string-match (concat "\\<" verilog-str) s)
(if (or (null verilog-pred)
(funcall verilog-pred s))
(setq verilog-all (cons s verilog-all)))))
keyword-list))
;; Function passed to completing-read, try-completion or
;; all-completions to get completion on STR. If predicate is non-nil,
;; it must be a function to be called for every match to check if this
;; should really be a match. If flag is t, the function returns a list
;; of all possible completions. If it is nil it returns a string, the
;; longest possible completion, or t if STR is an exact match. If flag
;; is 'lambda, the function returns t if STR is an exact match, nil
;; otherwise.
(defun verilog-completion (verilog-str verilog-pred verilog-flag)
(save-excursion
(let ((verilog-all nil))
;; Set buffer to use for searching labels. This should be set
;; within functins which use verilog-completions
(set-buffer verilog-buffer-to-use)
;; Determine what should be completed
(let ((state (car (verilog-calculate-indent))))
(cond ((eq state 'defun)
(save-excursion (verilog-var-completion))
(verilog-func-completion 'module)
(verilog-keyword-completion verilog-defun-keywords))
((eq state 'block)
(save-excursion (verilog-var-completion))
(verilog-func-completion 'tf)
(verilog-keyword-completion verilog-block-keywords))
((eq state 'case)
(save-excursion (verilog-var-completion))
(verilog-func-completion 'tf)
(verilog-keyword-completion verilog-case-keywords))
((eq state 'tf)
(save-excursion (verilog-var-completion))
(verilog-func-completion 'tf)
(verilog-keyword-completion verilog-tf-keywords))
(t;--Anywhere else
(save-excursion (verilog-var-completion))
(verilog-func-completion 'both)
(verilog-keyword-completion verilog-separator-keywords))))
;; Now we have built a list of all matches. Give response to caller
(verilog-completion-response))))
(defun verilog-completion-response ()
(cond ((or (equal verilog-flag 'lambda) (null verilog-flag))
;; This was not called by all-completions
(if (null verilog-all)
;; Return nil if there was no matching label
nil
;; Get longest string common in the labels
(let* ((elm (cdr verilog-all))
(match (car verilog-all))
(min (length match))
tmp)
(if (string= match verilog-str)
;; Return t if first match was an exact match
(setq match t)
(while (not (null elm))
;; Find longest common string
(if (< (setq tmp (verilog-string-diff match (car elm))) min)
(progn
(setq min tmp)
(setq match (substring match 0 min))))
;; Terminate with match=t if this is an exact match
(if (string= (car elm) verilog-str)
(progn
(setq match t)
(setq elm nil))
(setq elm (cdr elm)))))
;; If this is a test just for exact match, return nil ot t
(if (and (equal verilog-flag 'lambda) (not (equal match 't)))
nil
match))))
;; If flag is t, this was called by all-completions. Return
;; list of all possible completions
(verilog-flag
verilog-all)))
(defvar verilog-last-word-numb 0)
(defvar verilog-last-word-shown nil)
(defvar verilog-last-completions nil)
(defun verilog-complete-word ()
"Complete word at current point.
\(See also `verilog-toggle-completions', `verilog-type-keywords',
`verilog-start-keywords' and `verilog-separator-keywords'.)"
(interactive)
(let* ((b (save-excursion (skip-chars-backward "a-zA-Z0-9_") (point)))
(e (save-excursion (skip-chars-forward "a-zA-Z0-9_") (point)))
(verilog-str (buffer-substring b e))
;; The following variable is used in verilog-completion
(verilog-buffer-to-use (current-buffer))
(allcomp (if (and verilog-toggle-completions
(string= verilog-last-word-shown verilog-str))
verilog-last-completions
(all-completions verilog-str 'verilog-completion)))
(match (if verilog-toggle-completions
"" (try-completion
verilog-str (mapcar '(lambda (elm)
(cons elm 0)) allcomp)))))
;; Delete old string
(delete-region b e)
;; Toggle-completions inserts whole labels
(if verilog-toggle-completions
(progn
;; Update entry number in list
(setq verilog-last-completions allcomp
verilog-last-word-numb
(if (>= verilog-last-word-numb (1- (length allcomp)))
0
(1+ verilog-last-word-numb)))
(setq verilog-last-word-shown (elt allcomp verilog-last-word-numb))
;; Display next match or same string if no match was found
(if (not (null allcomp))
(insert "" verilog-last-word-shown)
(insert "" verilog-str)
(message "(No match)")))
;; The other form of completion does not necessarly do that.
;; Insert match if found, or the original string if no match
(if (or (null match) (equal match 't))
(progn (insert "" verilog-str)
(message "(No match)"))
(insert "" match))
;; Give message about current status of completion
(cond ((equal match 't)
(if (not (null (cdr allcomp)))
(message "(Complete but not unique)")
(message "(Sole completion)")))
;; Display buffer if the current completion didn't help
;; on completing the label.
((and (not (null (cdr allcomp))) (= (length verilog-str)
(length match)))
(with-output-to-temp-buffer "*Completions*"
(display-completion-list allcomp))
;; Wait for a keypress. Then delete *Completion* window
(momentary-string-display "" (point))
(delete-window (get-buffer-window (get-buffer "*Completions*")))
)))))
(defun verilog-show-completions ()
"Show all possible completions at current point."
(interactive)
(let* ((b (save-excursion (skip-chars-backward "a-zA-Z0-9_") (point)))
(e (save-excursion (skip-chars-forward "a-zA-Z0-9_") (point)))
(verilog-str (buffer-substring b e))
;; The following variable is used in verilog-completion
(verilog-buffer-to-use (current-buffer))
(allcomp (if (and verilog-toggle-completions
(string= verilog-last-word-shown verilog-str))
verilog-last-completions
(all-completions verilog-str 'verilog-completion))))
;; Show possible completions in a temporary buffer.
(with-output-to-temp-buffer "*Completions*"
(display-completion-list allcomp))
;; Wait for a keypress. Then delete *Completion* window
(momentary-string-display "" (point))
(delete-window (get-buffer-window (get-buffer "*Completions*")))))
(defun verilog-get-default-symbol ()
"Return symbol around current point as a string."
(save-excursion
(buffer-substring (progn
(skip-chars-backward " \t")
(skip-chars-backward "a-zA-Z0-9_")
(point))
(progn
(skip-chars-forward "a-zA-Z0-9_")
(point)))))
(defun verilog-build-defun-re (str &optional arg)
"Return function/task/module starting with STR as regular expression.
With optional second arg non-nil, STR is the complete name of the instruction."
(if arg
(concat "^\\(function\\|task\\|module\\)[ \t]+\\(" str
"\\)\\>")
(concat "^\\(function\\|task\\|module\\)[ \t]+\\(" str
"[a-zA-Z0-9_]*\\)\\>")))
;; Function passed to completing-read, try-completion or
;; all-completions to get completion on any function name. If
;; predicate is non-nil, it must be a function to be called for every
;; match to check if this should really be a match. If flag is t, the
;; function returns a list of all possible completions. If it is nil
;; it returns a string, the longest possible completion, or t if STR
;; is an exact match. If flag is 'lambda, the function returns t if
;; STR is an exact match, nil otherwise.
(defun verilog-comp-defun (verilog-str verilog-pred verilog-flag)
(save-excursion
(let ((verilog-all nil)
match)
;; Set buffer to use for searching labels. This should be set
;; within functins which use verilog-completions
(set-buffer verilog-buffer-to-use)
(let ((verilog-str verilog-str))
;; Build regular expression for functions
(if (string= verilog-str "")
(setq verilog-str (verilog-build-defun-re "[a-zA-Z_]"))
(setq verilog-str (verilog-build-defun-re verilog-str)))
(goto-char (point-min))
;; Build a list of all possible completions
(while (verilog-re-search-forward verilog-str nil t)
(setq match (buffer-substring (match-beginning 2) (match-end 2)))
(if (or (null verilog-pred)
(funcall verilog-pred match))
(setq verilog-all (cons match verilog-all)))))
;; Now we have built a list of all matches. Give response to caller
(verilog-completion-response))))
(defun verilog-goto-defun ()
"Move to specified Verilog module/task/function.
The default is a name found in the buffer around point.
If search fails, other files are checked based on verilog-library-directories."
(interactive)
(let* ((default (verilog-get-default-symbol))
;; The following variable is used in verilog-comp-function
(verilog-buffer-to-use (current-buffer))
(label (if (not (string= default ""))
;; Do completion with default
(completing-read (concat "Label: (default " default ") ")
'verilog-comp-defun nil nil "")
;; There is no default value. Complete without it
(completing-read "Label: "
'verilog-comp-defun nil nil "")))
pt)
;; If there was no response on prompt, use default value
(if (string= label "")
(setq label default))
;; Goto right place in buffer if label is not an empty string
(or (string= label "")
(progn
(save-excursion
(goto-char (point-min))
(setq pt (re-search-forward (verilog-build-defun-re label t) nil t)))
(when pt
(goto-char pt)
(beginning-of-line))
pt)
(verilog-goto-defun-file label)
)))
;; Eliminate compile warning
(eval-when-compile
(if (not (boundp 'occur-pos-list))
(defvar occur-pos-list nil "Backward compatibility occur positions.")))
(defun verilog-showscopes ()
"list all scopes in this module"
(interactive)
(let (
(buffer (current-buffer))
(linenum 1)
(nlines 0)
(first 1)
(prevpos (point-min))
(final-context-start (make-marker))
(regexp "\\(module\\s-+\\w+\\s-*(\\)\\|\\(\\w+\\s-+\\w+\\s-*(\\)")
)
(with-output-to-temp-buffer "*Occur*"
(save-excursion
(message (format "Searching for %s ..." regexp))
;; Find next match, but give up if prev match was at end of buffer.
(while (and (not (= prevpos (point-max)))
(verilog-re-search-forward regexp nil t))
(goto-char (match-beginning 0))
(beginning-of-line)
(save-match-data
(setq linenum (+ linenum (count-lines prevpos (point)))))
(setq prevpos (point))
(goto-char (match-end 0))
(let* ((start (save-excursion
(goto-char (match-beginning 0))
(forward-line (if (< nlines 0) nlines (- nlines)))
(point)))
(end (save-excursion
(goto-char (match-end 0))
(if (> nlines 0)
(forward-line (1+ nlines))
(forward-line 1))
(point)))
(tag (format "%3d" linenum))
(empty (make-string (length tag) ?\ ))
tem)
(save-excursion
(setq tem (make-marker))
(set-marker tem (point))
(set-buffer standard-output)
(setq occur-pos-list (cons tem occur-pos-list))
(or first (zerop nlines)
(insert "--------\n"))
(setq first nil)
(insert-buffer-substring buffer start end)
(backward-char (- end start))
(setq tem (if (< nlines 0) (- nlines) nlines))
(while (> tem 0)
(insert empty ?:)
(forward-line 1)
(setq tem (1- tem)))
(let ((this-linenum linenum))
(set-marker final-context-start
(+ (point) (- (match-end 0) (match-beginning 0))))
(while (< (point) final-context-start)
(if (null tag)
(setq tag (format "%3d" this-linenum)))
(insert tag ?:)))))))
(set-buffer-modified-p nil))))
;;;; Added by Subbu Meiyappan for Header
(defun verilog-header ()
"Insert a standard Verilog file header."
(interactive)
(let ((start (point)))
(insert "\
//-----------------------------------------------------------------------------
// Title : <title>
// Project : <project>
//-----------------------------------------------------------------------------
// File : <filename>
// Author : <author>
// Created : <credate>
// Last modified : <moddate>
//-----------------------------------------------------------------------------
// Description :
// <description>
//-----------------------------------------------------------------------------
// Copyright (c) 1998 by <company> This model is the confidential and
// proprietary property of <company> and the possession or use of this
// file requires a written license from <company>.
//------------------------------------------------------------------------------
// Modification history :
// <modhist>
//-----------------------------------------------------------------------------
")
(goto-char start)
(search-forward "<filename>")
(replace-match (buffer-name) t t)
(search-forward "<author>") (replace-match "" t t)
(insert (user-full-name))
(insert " <" (user-login-name) "@" (system-name)
">")
(search-forward "<credate>") (replace-match "" t t)
(insert-date)
(search-forward "<moddate>") (replace-match "" t t)
(insert-date)
(search-forward "<modhist>") (replace-match "" t t)
(insert-date)
(insert " : created")
(goto-char start)
(let (string)
(setq string (read-string "title: "))
(search-forward "<title>")
(replace-match string t t)
(setq string (read-string "project: " verilog-project))
(make-variable-buffer-local 'verilog-project)
(setq verilog-project string)
(search-forward "<project>")
(replace-match string t t)
(setq string (read-string "Company: " verilog-company))
(make-variable-buffer-local 'verilog-company)
(setq verilog-company string)
(search-forward "<company>")
(replace-match string t t)
(search-forward "<company>")
(replace-match string t t)
(search-forward "<company>")
(replace-match string t t)
(search-backward "<description>")
(replace-match "" t t)
)))
;; verilog-header Uses the insert-date function
(defun insert-date ()
"Insert date from the system."
(interactive)
(let ((timpos))
(setq timpos (point))
(if verilog-date-scientific-format
(shell-command "date \"+@%Y/%m/%d\"" t)
(shell-command "date \"+(a)%d.%m.%Y\"" t))
(search-forward "@")
(delete-region timpos (point))
(end-of-line))
(delete-char 1)
)
;;;
;;; Signal list parsing
;;;
(defun verilog-signals-not-in (in-list not-list)
"Return list of signals in IN-LIST that aren't also in NOT-LIST.
Signals must be in standard (base vector) form."
(let (out-list)
(while in-list
(if (not (assoc (car (car in-list)) not-list))
(setq out-list (cons (car in-list) out-list)))
(setq in-list (cdr in-list)))
(nreverse out-list)))
;;;(verilog-signals-not-in '(("A" "") ("B" "")
("DEL" "[2:3]")) '(("DEL" "") ("EXT"
"")))
(defun verilog-signals-memory (in-list)
"Return list of signals in IN-LIST that are memoried (multidimensional)."
(let (out-list)
(while in-list
(if (nth 3 (car in-list))
(setq out-list (cons (car in-list) out-list)))
(setq in-list (cdr in-list)))
out-list))
;;;(verilog-signals-memory '(("A" nil nil "[3:0]"))
'(("B" nil nil nil)))
(defun verilog-signals-combine-bus (in-list)
"Return a list of signals in IN-LIST, with all duplicates removed, and with
busses combined. For example A[2] and A[1] become A[2:1]."
(let ((combo "")
out-list signal highbit lowbit svhighbit svlowbit comment svbusstring bus)
;; Shove signals so duplicated signals will be adjacent
(setq in-list (sort in-list (function (lambda (a b) (string< (car a) (car
b))))))
(while in-list
(setq signal (nth 0 (car in-list))
bus (nth 1 (car in-list))
comment (nth 2 (car in-list)))
(cond ((and bus
(or (and (string-match "\\[\\([0-9]+\\):\\([0-9]+\\)\\]" bus)
(setq highbit (string-to-int (match-string 1 bus))
lowbit (string-to-int (match-string 2 bus))))
(and (string-match "\\[\\([0-9]+\\)\\]" bus)
(setq highbit (string-to-int (match-string 1 bus))
lowbit highbit))))
;; Combine bits in bus