1" Language: Verilog HDL 2" Maintainer: Chih-Tsun Huang <[email protected]> 3" Last Change: 2011 Dec 10 by Thilo Six 4" URL: http://larc.ee.nthu.edu.tw/~cthuang/vim/indent/verilog.vim 5" 6" Credits: 7" Suggestions for improvement, bug reports by 8" Leo Butlero <[email protected]> 9" 10" Buffer Variables: 11" b:verilog_indent_modules : indenting after the declaration 12" of module blocks 13" b:verilog_indent_width : indenting width 14" b:verilog_indent_verbose : verbose to each indenting 15" 16 17" Only load this indent file when no other was loaded. 18if exists("b:did_indent") 19 finish 20endif 21let b:did_indent = 1 22 23setlocal indentexpr=GetVerilogIndent() 24setlocal indentkeys=!^F,o,O,0),=begin,=end,=join,=endcase 25setlocal indentkeys+==endmodule,=endfunction,=endtask,=endspecify 26setlocal indentkeys+==`else,=`endif 27 28" Only define the function once. 29if exists("*GetVerilogIndent") 30 finish 31endif 32 33let s:cpo_save = &cpo 34set cpo&vim 35 36function GetVerilogIndent() 37 38 if exists('b:verilog_indent_width') 39 let offset = b:verilog_indent_width 40 else 41 let offset = &sw 42 endif 43 if exists('b:verilog_indent_modules') 44 let indent_modules = offset 45 else 46 let indent_modules = 0 47 endif 48 49 " Find a non-blank line above the current line. 50 let lnum = prevnonblank(v:lnum - 1) 51 52 " At the start of the file use zero indent. 53 if lnum == 0 54 return 0 55 endif 56 57 let lnum2 = prevnonblank(lnum - 1) 58 let curr_line = getline(v:lnum) 59 let last_line = getline(lnum) 60 let last_line2 = getline(lnum2) 61 let ind = indent(lnum) 62 let ind2 = indent(lnum - 1) 63 let offset_comment1 = 1 64 " Define the condition of an open statement 65 " Exclude the match of //, /* or */ 66 let vlog_openstat = '\(\<or\>\|\([*/]\)\@<![*(,{><+-/%^&|!=?:]\([*/]\)\@!\)' 67 " Define the condition when the statement ends with a one-line comment 68 let vlog_comment = '\(//.*\|/\*.*\*/\s*\)' 69 if exists('b:verilog_indent_verbose') 70 let vverb_str = 'INDENT VERBOSE:' 71 let vverb = 1 72 else 73 let vverb = 0 74 endif 75 76 " Indent accoding to last line 77 " End of multiple-line comment 78 if last_line =~ '\*/\s*$' && last_line !~ '/\*.\{-}\*/' 79 let ind = ind - offset_comment1 80 if vverb 81 echo vverb_str "De-indent after a multiple-line comment." 82 endif 83 84 " Indent after if/else/for/case/always/initial/specify/fork blocks 85 elseif last_line =~ '`\@<!\<\(if\|else\)\>' || 86 \ last_line =~ '^\s*\<\(for\|case\%[[zx]]\)\>' || 87 \ last_line =~ '^\s*\<\(always\|initial\)\>' || 88 \ last_line =~ '^\s*\<\(specify\|fork\)\>' 89 if last_line !~ '\(;\|\<end\>\)\s*' . vlog_comment . '*$' || 90 \ last_line =~ '\(//\|/\*\).*\(;\|\<end\>\)\s*' . vlog_comment . '*$' 91 let ind = ind + offset 92 if vverb | echo vverb_str "Indent after a block statement." | endif 93 endif 94 " Indent after function/task blocks 95 elseif last_line =~ '^\s*\<\(function\|task\)\>' 96 if last_line !~ '\<end\>\s*' . vlog_comment . '*$' || 97 \ last_line =~ '\(//\|/\*\).*\(;\|\<end\>\)\s*' . vlog_comment . '*$' 98 let ind = ind + offset 99 if vverb 100 echo vverb_str "Indent after function/task block statement." 101 endif 102 endif 103 104 " Indent after module/function/task/specify/fork blocks 105 elseif last_line =~ '^\s*\<module\>' 106 let ind = ind + indent_modules 107 if vverb && indent_modules 108 echo vverb_str "Indent after module statement." 109 endif 110 if last_line =~ '[(,]\s*' . vlog_comment . '*$' && 111 \ last_line !~ '\(//\|/\*\).*[(,]\s*' . vlog_comment . '*$' 112 let ind = ind + offset 113 if vverb 114 echo vverb_str "Indent after a multiple-line module statement." 115 endif 116 endif 117 118 " Indent after a 'begin' statement 119 elseif last_line =~ '\(\<begin\>\)\(\s*:\s*\w\+\)*' . vlog_comment . '*$' && 120 \ last_line !~ '\(//\|/\*\).*\(\<begin\>\)' && 121 \ ( last_line2 !~ vlog_openstat . '\s*' . vlog_comment . '*$' || 122 \ last_line2 =~ '^\s*[^=!]\+\s*:\s*' . vlog_comment . '*$' ) 123 let ind = ind + offset 124 if vverb | echo vverb_str "Indent after begin statement." | endif 125 126 " De-indent for the end of one-line block 127 elseif ( last_line !~ '\<begin\>' || 128 \ last_line =~ '\(//\|/\*\).*\<begin\>' ) && 129 \ last_line2 =~ '\<\(`\@<!if\|`\@<!else\|for\|always\|initial\)\>.*' . 130 \ vlog_comment . '*$' && 131 \ last_line2 !~ 132 \ '\(//\|/\*\).*\<\(`\@<!if\|`\@<!else\|for\|always\|initial\)\>' && 133 \ last_line2 !~ vlog_openstat . '\s*' . vlog_comment . '*$' && 134 \ ( last_line2 !~ '\<begin\>' || 135 \ last_line2 =~ '\(//\|/\*\).*\<begin\>' ) 136 let ind = ind - offset 137 if vverb 138 echo vverb_str "De-indent after the end of one-line statement." 139 endif 140 141 " Multiple-line statement (including case statement) 142 " Open statement 143 " Ident the first open line 144 elseif last_line =~ vlog_openstat . '\s*' . vlog_comment . '*$' && 145 \ last_line !~ '\(//\|/\*\).*' . vlog_openstat . '\s*$' && 146 \ last_line2 !~ vlog_openstat . '\s*' . vlog_comment . '*$' 147 let ind = ind + offset 148 if vverb | echo vverb_str "Indent after an open statement." | endif 149 150 " Close statement 151 " De-indent for an optional close parenthesis and a semicolon, and only 152 " if there exists precedent non-whitespace char 153 elseif last_line =~ ')*\s*;\s*' . vlog_comment . '*$' && 154 \ last_line !~ '^\s*)*\s*;\s*' . vlog_comment . '*$' && 155 \ last_line !~ '\(//\|/\*\).*\S)*\s*;\s*' . vlog_comment . '*$' && 156 \ ( last_line2 =~ vlog_openstat . '\s*' . vlog_comment . '*$' && 157 \ last_line2 !~ ';\s*//.*$') && 158 \ last_line2 !~ '^\s*' . vlog_comment . '$' 159 let ind = ind - offset 160 if vverb | echo vverb_str "De-indent after a close statement." | endif 161 162 " `ifdef and `else 163 elseif last_line =~ '^\s*`\<\(ifdef\|else\)\>' 164 let ind = ind + offset 165 if vverb 166 echo vverb_str "Indent after a `ifdef or `else statement." 167 endif 168 169 endif 170 171 " Re-indent current line 172 173 " De-indent on the end of the block 174 " join/end/endcase/endfunction/endtask/endspecify 175 if curr_line =~ '^\s*\<\(join\|end\|endcase\)\>' || 176 \ curr_line =~ '^\s*\<\(endfunction\|endtask\|endspecify\)\>' 177 let ind = ind - offset 178 if vverb | echo vverb_str "De-indent the end of a block." | endif 179 elseif curr_line =~ '^\s*\<endmodule\>' 180 let ind = ind - indent_modules 181 if vverb && indent_modules 182 echo vverb_str "De-indent the end of a module." 183 endif 184 185 " De-indent on a stand-alone 'begin' 186 elseif curr_line =~ '^\s*\<begin\>' 187 if last_line !~ '^\s*\<\(function\|task\|specify\|module\)\>' && 188 \ last_line !~ '^\s*\()*\s*;\|)\+\)\s*' . vlog_comment . '*$' && 189 \ ( last_line =~ 190 \ '\<\(`\@<!if\|`\@<!else\|for\|case\%[[zx]]\|always\|initial\)\>' || 191 \ last_line =~ ')\s*' . vlog_comment . '*$' || 192 \ last_line =~ vlog_openstat . '\s*' . vlog_comment . '*$' ) 193 let ind = ind - offset 194 if vverb 195 echo vverb_str "De-indent a stand alone begin statement." 196 endif 197 endif 198 199 " De-indent after the end of multiple-line statement 200 elseif curr_line =~ '^\s*)' && 201 \ ( last_line =~ vlog_openstat . '\s*' . vlog_comment . '*$' || 202 \ last_line !~ vlog_openstat . '\s*' . vlog_comment . '*$' && 203 \ last_line2 =~ vlog_openstat . '\s*' . vlog_comment . '*$' ) 204 let ind = ind - offset 205 if vverb 206 echo vverb_str "De-indent the end of a multiple statement." 207 endif 208 209 " De-indent `else and `endif 210 elseif curr_line =~ '^\s*`\<\(else\|endif\)\>' 211 let ind = ind - offset 212 if vverb | echo vverb_str "De-indent `else and `endif statement." | endif 213 214 endif 215 216 " Return the indention 217 return ind 218endfunction 219 220let &cpo = s:cpo_save 221unlet s:cpo_save 222 223" vim:sw=2 224