host info updates
[distro-setup] / .vim / syntax / sh.vim
1 " modified to remove obnoxious overhighliting
2 " Vim syntax file
3 " Language: shell (sh) Korn shell (ksh) bash (sh)
4 " Maintainer: Dr. Charles E. Campbell, Jr. <NdrOchipS@PcampbellAfamily.Mbiz>
5 " Previous Maintainer: Lennart Schultz <Lennart.Schultz@ecmwf.int>
6 " Last Change: Sep 17, 2008
7 " Version: 104
8 " URL: http://mysite.verizon.net/astronaut/vim/index.html#vimlinks_syntax
9 " For options and settings, please use: :help ft-sh-syntax
10 " This file includes many ideas from Éric Brunet (eric.brunet@ens.fr)
11
12 " For version 5.x: Clear all syntax items {{{1
13 " For version 6.x: Quit when a syntax file was already loaded
14 if version < 600
15 syntax clear
16 elseif exists("b:current_syntax")
17 finish
18 endif
19
20 " handling /bin/sh with is_kornshell/is_sh {{{1
21 " b:is_sh is set when "#! /bin/sh" is found;
22 " However, it often is just a masquerade by bash (typically Linux)
23 " or kornshell (typically workstations with Posix "sh").
24 " So, when the user sets "is_bash" or "is_kornshell",
25 " a b:is_sh is converted into b:is_bash/b:is_kornshell,
26 " respectively.
27 if !exists("b:is_kornshell") && !exists("b:is_bash")
28 if exists("g:is_posix") && !exists("g:is_kornshell")
29 let g:is_kornshell= g:is_posix
30 endif
31 if exists("g:is_kornshell")
32 let b:is_kornshell= 1
33 if exists("b:is_sh")
34 unlet b:is_sh
35 endif
36 elseif exists("g:is_bash")
37 let b:is_bash= 1
38 if exists("b:is_sh")
39 unlet b:is_sh
40 endif
41 else
42 let b:is_sh= 1
43 endif
44 endif
45
46 " set up default g:sh_fold_enabled {{{1
47 if !exists("g:sh_fold_enabled")
48 let g:sh_fold_enabled= 0
49 elseif g:sh_fold_enabled != 0 && !has("folding")
50 let g:sh_fold_enabled= 0
51 echomsg "Ignoring g:sh_fold_enabled=".g:sh_fold_enabled."; need to re-compile vim for +fold support"
52 endif
53 if !exists("s:sh_fold_functions")
54 let s:sh_fold_functions = 1
55 endif
56 if !exists("s:sh_fold_heredoc")
57 let s:sh_fold_heredoc = 2
58 endif
59 if !exists("s:sh_fold_ifdofor")
60 let s:sh_fold_ifdofor = 4
61 endif
62 if g:sh_fold_enabled && &fdm == "manual"
63 set fdm=syntax
64 endif
65
66 " sh syntax is case sensitive {{{1
67 syn case match
68
69 " Clusters: contains=@... clusters {{{1
70 "==================================
71 syn cluster shErrorList contains=shDoError,shIfError,shInError,shCaseError,shEsacError,shCurlyError,shParenError,shTestError
72 if exists("b:is_kornshell")
73 syn cluster ErrorList add=shDTestError
74 endif
75 syn cluster shArithParenList contains=shArithmetic,shDeref,shDerefSimple,shEcho,shEscape,shNumber,shOperator,shPosnParm,shExSingleQuote,shRedir,shSingleQuote,shDoubleQuote,shStatement,shVariable,shAlias,shTest,shCtrlSeq,shSpecial,shParen
76 syn cluster shArithList contains=@shArithParenList,shParenError
77 syn cluster shCaseEsacList contains=shCaseStart,shCase,shCaseBar,shCaseIn,shComment,shDeref,shDerefSimple,shCaseCommandSub,shCaseExSingleQuote,shCaseSingleQuote,shCaseDoubleQuote,shCtrlSeq,@shErrorList,shStringSpecial
78 syn cluster shCaseList contains=@shCommandSubList,shCaseEsac,shColon,shCommandSub,shCommandSub,shComment,shDo,shEcho,shExpr,shFor,shHereDoc,shIf,shRedir,shSetList,shSource,shStatement,shVariable,shCtrlSeq
79 syn cluster shColonList contains=@shCaseList
80 syn cluster shCommandSubList contains=shArithmetic,shDeref,shDerefSimple,shEscape,shNumber,shOperator,shPosnParm,shExSingleQuote,shSingleQuote,shDoubleQuote,shStatement,shVariable,shSubSh,shAlias,shTest,shCtrlSeq,shSpecial
81 syn cluster shCurlyList contains=shNumber,shComma,shDeref,shDerefSimple,shDerefSpecial
82 syn cluster shDblQuoteList contains=shCommandSub,shDeref,shDerefSimple,shPosnParm,shExSingleQuote,shCtrlSeq,shSpecial
83 syn cluster shDerefList contains=shDeref,shDerefSimple,shDerefVar,shDerefSpecial,shDerefWordError,shDerefPPS
84 syn cluster shDerefVarList contains=shDerefOp,shDerefVarArray
85 syn cluster shEchoList contains=shArithmetic,shCommandSub,shDeref,shDerefSimple,shExpr,shExSingleQuote,shSingleQuote,shDoubleQuote,shCtrlSeq,shEchoQuote
86 syn cluster shExprList1 contains=shCharClass,shNumber,shOperator,shExSingleQuote,shSingleQuote,shDoubleQuote,shExpr,shDblBrace,shDeref,shDerefSimple,shCtrlSeq
87 syn cluster shExprList2 contains=@shExprList1,@shCaseList,shTest
88 syn cluster shFunctionList contains=@shCommandSubList,shCaseEsac,shColon,shCommandSub,shCommandSub,shComment,shDo,shEcho,shExpr,shFor,shHereDoc,shIf,shRedir,shSetList,shSource,shStatement,shVariable,shOperator,shCtrlSeq
89 if exists("b:is_kornshell") || exists("b:is_bash")
90 syn cluster shFunctionList add=shRepeat
91 syn cluster shFunctionList add=shDblBrace,shDblParen
92 endif
93 syn cluster shHereBeginList contains=@shCommandSubList
94 syn cluster shHereList contains=shBeginHere,shHerePayload
95 syn cluster shHereListDQ contains=shBeginHere,@shDblQuoteList,shHerePayload
96 syn cluster shIdList contains=shCommandSub,shWrapLineOperator,shSetOption,shDeref,shDerefSimple,shRedir,shExSingleQuote,shSingleQuote,shDoubleQuote,shExpr,shCtrlSeq,shStringSpecial
97 syn cluster shLoopList contains=@shCaseList,shTestOpr,shExpr,shDblBrace,shConditional,shCaseEsac,shTest,@shErrorList,shSet
98 syn cluster shSubShList contains=@shCaseList,shOperator
99 syn cluster shTestList contains=shCharClass,shComment,shCommandSub,shDeref,shDerefSimple,shDoubleQuote,shExpr,shExpr,shNumber,shOperator,shExSingleQuote,shSingleQuote,shTestOpr,shTest,shCtrlSeq
100
101
102 " Alias: {{{1
103 " =====
104 if exists("b:is_kornshell") || exists("b:is_bash")
105 syn match shStatement "\<alias\>"
106 syn region shAlias matchgroup=shStatement start="\<alias\>\s\+\(\w\+\)\@=" skip="\\$" end="\>\|`"
107 syn region shAlias matchgroup=shStatement start="\<alias\>\s\+\(\w\+=\)\@=" skip="\\$" end="="
108 endif
109
110 " Error Codes: {{{1
111 " ============
112 syn match shDoError "\<done\>"
113 syn match shIfError "\<fi\>"
114 syn match shInError "\<in\>"
115 syn match shCaseError ";;"
116 syn match shEsacError "\<esac\>"
117 syn match shCurlyError "}"
118 syn match shParenError ")"
119 if exists("b:is_kornshell")
120 syn match shDTestError "]]"
121 endif
122 syn match shTestError "]"
123
124 " Options: {{{1
125 " ====================
126 syn match shOption "\s\zs[-+][a-zA-Z0-9]\+\>"
127 syn match shOption "\s\zs--[^ \t$`'"|]\+"
128
129 " File Redirection Highlighted As Operators: {{{1
130 "===========================================
131 syn match shRedir "\d\=>\(&[-0-9]\)\="
132 syn match shRedir "\d\=>>-\="
133 syn match shRedir "\d\=<\(&[-0-9]\)\="
134 syn match shRedir "\d<<-\="
135
136 " Operators: {{{1
137 " ==========
138 syn match shOperator "<<\|>>" contained
139 syn match shOperator "[!&;|]" contained
140 syn match shOperator "\[[[^:]\|\]]" contained
141 syn match shOperator "!\==" skipwhite nextgroup=shPattern
142 syn match shPattern "\<\S\+\())\)\@=" contained contains=shExSingleQuote,shSingleQuote,shDoubleQuote,shDeref
143
144 " Subshells: {{{1
145 " ==========
146 syn region shExpr transparent matchgroup=shExprRegion start="{" end="}" contains=@shExprList2
147 syn region shSubSh transparent matchgroup=shSubShRegion start="(" end=")" contains=@shSubShList
148
149 " Tests: {{{1
150 "=======
151 "syn region shExpr transparent matchgroup=shRange start="\[" skip=+\\\\\|\\$+ end="\]" contains=@shTestList
152 syn region shExpr matchgroup=shRange start="\[" skip=+\\\\\|\\$+ end="\]" contains=@shTestList
153 syn region shTest transparent matchgroup=shStatement start="\<test\>" skip=+\\\\\|\\$+ matchgroup=NONE end="[;&|]"me=e-1 end="$" contains=@shExprList1
154 syn match shTestOpr contained "<=\|>=\|!=\|==\|-.\>\|-\(nt\|ot\|ef\|eq\|ne\|lt\|le\|gt\|ge\)\>\|[!<>]"
155 syn match shTestOpr contained '=' skipwhite nextgroup=shTestDoubleQuote,shTestSingleQuote,shTestPattern
156 syn match shTestPattern contained '\w\+'
157 syn match shTestDoubleQuote contained '"[^"]*"'
158 syn match shTestSingleQuote contained '\\.'
159 syn match shTestSingleQuote contained "'[^']*'"
160 if exists("b:is_kornshell") || exists("b:is_bash")
161 syn region shDblBrace matchgroup=Delimiter start="\[\[" skip=+\\\\\|\\$+ end="\]\]" contains=@shTestList
162 syn region shDblParen matchgroup=Delimiter start="((" skip=+\\\\\|\\$+ end="))" contains=@shTestList
163 endif
164
165 " Character Class In Range: {{{1
166 " =========================
167 syn match shCharClass contained "\[:\(backspace\|escape\|return\|xdigit\|alnum\|alpha\|blank\|cntrl\|digit\|graph\|lower\|print\|punct\|space\|upper\|tab\):\]"
168
169 " Loops: do, if, while, until {{{1
170 " ======
171 if (g:sh_fold_enabled % (s:sh_fold_ifdofor * 2))/s:sh_fold_ifdofor
172 syn region shDo fold transparent matchgroup=shConditional start="\<do\>" matchgroup=shConditional end="\<done\>" contains=@shLoopList
173 syn region shIf fold transparent matchgroup=shConditional start="\<if\_s" matchgroup=shConditional end="\<;\_s*then\>" end="\<fi\>" contains=@shLoopList,shDblBrace,shDblParen,shFunctionKey
174 syn region shFor fold matchgroup=shLoop start="\<for\_s" end="\<in\_s" end="\<do\>"me=e-2 contains=@shLoopList,shDblParen skipwhite nextgroup=shCurlyIn
175 else
176 syn region shDo transparent matchgroup=shConditional start="\<do\>" matchgroup=shConditional end="\<done\>" contains=@shLoopList
177 syn region shIf transparent matchgroup=shConditional start="\<if\_s" matchgroup=shConditional end="\<;\_s*then\>" end="\<fi\>" contains=@shLoopList,shDblBrace,shDblParen,shFunctionKey
178 syn region shFor matchgroup=shLoop start="\<for\_s" end="\<in\>" end="\<do\>"me=e-2 contains=@shLoopList,shDblParen skipwhite nextgroup=shCurlyIn
179 endif
180 if exists("b:is_kornshell") || exists("b:is_bash")
181 syn cluster shCaseList add=shRepeat
182 syn cluster shFunctionList add=shRepeat
183 syn region shRepeat matchgroup=shLoop start="\<while\_s" end="\<in\_s" end="\<do\>"me=e-2 contains=@shLoopList,shDblParen,shDblBrace
184 syn region shRepeat matchgroup=shLoop start="\<until\_s" end="\<in\_s" end="\<do\>"me=e-2 contains=@shLoopList,shDblParen,shDblBrace
185 syn region shCaseEsac matchgroup=shConditional start="\<select\s" matchgroup=shConditional end="\<in\>" end="\<do\>" contains=@shLoopList
186 else
187 syn region shRepeat matchgroup=shLoop start="\<while\_s" end="\<do\>"me=e-2 contains=@shLoopList
188 syn region shRepeat matchgroup=shLoop start="\<until\_s" end="\<do\>"me=e-2 contains=@shLoopList
189 endif
190 syn region shCurlyIn contained matchgroup=Delimiter start="{" end="}" contains=@shCurlyList
191 syn match shComma contained ","
192
193 " Case: case...esac {{{1
194 " ====
195 syn match shCaseBar contained skipwhite "\(^\|[^\\]\)\(\\\\\)*\zs|" nextgroup=shCase,shCaseStart,shCaseBar,shComment,shCaseExSingleQuote,shCaseSingleQuote,shCaseDoubleQuote
196 syn match shCaseStart contained skipwhite skipnl "(" nextgroup=shCase,shCaseBar
197 syn region shCase contained skipwhite skipnl matchgroup=shSnglCase start="\%(\\.\|[^#$()'" \t]\)\{-}\zs)" end=";;" end="esac"me=s-1 contains=@shCaseList nextgroup=shCaseStart,shCase,shComment
198 if (g:sh_fold_enabled % (s:sh_fold_ifdofor * 2))/s:sh_fold_ifdofor
199 syn region shCaseEsac fold matchgroup=shConditional start="\<case\>" end="\<esac\>" contains=@shCaseEsacList
200 else
201 syn region shCaseEsac matchgroup=shConditional start="\<case\>" end="\<esac\>" contains=@shCaseEsacList
202 endif
203 syn keyword shCaseIn contained skipwhite skipnl in nextgroup=shCase,shCaseStart,shCaseBar,shComment,shCaseExSingleQuote,shCaseSingleQuote,shCaseDoubleQuote
204 if exists("b:is_bash")
205 syn region shCaseExSingleQuote matchgroup=shOperator start=+\$'+ skip=+\\\\\|\\.+ end=+'+ contains=shStringSpecial,shSpecial skipwhite skipnl nextgroup=shCaseBar contained
206 else
207 syn region shCaseExSingleQuote matchgroup=Error start=+\$'+ skip=+\\\\\|\\.+ end=+'+ contains=shStringSpecial skipwhite skipnl nextgroup=shCaseBar contained
208 endif
209 syn region shCaseSingleQuote matchgroup=shOperator start=+'+ end=+'+ contains=shStringSpecial skipwhite skipnl nextgroup=shCaseBar contained
210 syn region shCaseDoubleQuote matchgroup=shOperator start=+"+ skip=+\\\\\|\\.+ end=+"+ contains=@shDblQuoteList,shStringSpecial skipwhite skipnl nextgroup=shCaseBar contained
211 syn region shCaseCommandSub start=+`+ skip=+\\\\\|\\.+ end=+`+ contains=@shCommandSubList skipwhite skipnl nextgroup=shCaseBar contained
212
213 " Misc: {{{1
214 "======
215 syn match shWrapLineOperator "\\$"
216 syn region shCommandSub start="`" skip="\\\\\|\\." end="`" contains=@shCommandSubList
217 syn match shEscape contained '\\.'
218
219 " $() and $(()): {{{1
220 " $(..) is not supported by sh (Bourne shell). However, apparently
221 " some systems (HP?) have as their /bin/sh a (link to) Korn shell
222 " (ie. Posix compliant shell). /bin/ksh should work for those
223 " systems too, however, so the following syntax will flag $(..) as
224 " an Error under /bin/sh. By consensus of vimdev'ers!
225 if exists("b:is_kornshell") || exists("b:is_bash")
226 syn region shCommandSub matchgroup=shCmdSubRegion start="\$(" skip='\\\\\|\\.' end=")" contains=@shCommandSubList
227 syn region shArithmetic matchgroup=shArithRegion start="\$((" skip='\\\\\|\\.' end="))" contains=@shArithList
228 syn match shSkipInitWS contained "^\s\+"
229 else
230 syn region shCommandSub matchgroup=Error start="\$(" end=")" contains=@shCommandSubList
231 endif
232
233 if exists("b:is_bash")
234 syn cluster shCommandSubList add=bashSpecialVariables,bashStatement
235 syn cluster shCaseList add=bashAdminStatement,bashStatement
236 syn keyword bashSpecialVariables contained BASH BASH_ENV BASH_VERSINFO BASH_VERSION CDPATH DIRSTACK EUID FCEDIT FIGNORE GLOBIGNORE GROUPS HISTCMD HISTCONTROL HISTFILE HISTFILESIZE HISTIGNORE HISTSIZE HOME HOSTFILE HOSTNAME HOSTTYPE IFS IGNOREEOF INPUTRC LANG LC_ALL LC_COLLATE LC_MESSAGES LINENO MACHTYPE MAIL MAILCHECK MAILPATH OLDPWD OPTARG OPTERR OPTIND OSTYPE PATH PIPESTATUS PPID PROMPT_COMMAND PS1 PS2 PS3 PS4 PWD RANDOM REPLY SECONDS SHELLOPTS SHLVL TIMEFORMAT TIMEOUT UID auto_resume histchars
237 endif
238
239 if exists("b:is_kornshell")
240 syn cluster shCommandSubList add=kshSpecialVariables,kshStatement
241 syn cluster shCaseList add=kshStatement
242 syn keyword kshSpecialVariables contained CDPATH COLUMNS EDITOR ENV ERRNO FCEDIT FPATH HISTFILE HISTSIZE HOME IFS LINENO LINES MAIL MAILCHECK MAILPATH OLDPWD OPTARG OPTIND PATH PPID PS1 PS2 PS3 PS4 PWD RANDOM REPLY SECONDS SHELL TMOUT VISUAL
243 syn keyword kshStatement cat chmod clear cp du egrep expr fgrep find grep install killall less ls mkdir mv nice printenv rm rmdir sed sort strip stty tail touch tput
244 endif
245
246 syn match shSource "^\.\s"
247 syn match shSource "\s\.\s"
248 syn region shColon start="^\s*:" end="$\|" end="#"me=e-1 contains=@shColonList
249
250 " String And Character Constants: {{{1
251 "================================
252 syn match shNumber "-\=\<\d\+\>#\="
253 syn match shCtrlSeq "\\\d\d\d\|\\[abcfnrtv0]" contained
254 if exists("b:is_bash")
255 syn match shSpecial "\\\o\o\o\|\\x\x\x\|\\c.\|\\[abefnrtv]" contained
256 endif
257 if exists("b:is_bash")
258 syn region shExSingleQuote matchgroup=shOperator start=+\$'+ skip=+\\\\\|\\.+ end=+'+ contains=shStringSpecial,shSpecial
259 else
260 syn region shExSingleQuote matchGroup=Error start=+\$'+ skip=+\\\\\|\\.+ end=+'+ contains=shStringSpecial
261 endif
262 syn region shSingleQuote matchgroup=shOperator start=+'+ end=+'+ contains=shStringSpecial,@Spell
263 syn region shDoubleQuote matchgroup=shOperator start=+"+ skip=+\\"+ end=+"+ contains=@shDblQuoteList,shStringSpecial,@Spell
264 syn match shStringSpecial "[^[:print:] \t]" contained
265 syn match shStringSpecial "\%(\\\\\)*\\[\\"'`$()#]"
266 syn match shSpecial "[^\\]\zs\%(\\\\\)*\\[\\"'`$()#]"
267 syn match shSpecial "^\%(\\\\\)*\\[\\"'`$()#]"
268
269 " Comments: {{{1
270 "==========
271 syn cluster shCommentGroup contains=shTodo,@Spell
272 syn keyword shTodo contained COMBAK FIXME TODO XXX
273 syn match shComment "^\s*\zs#.*$" contains=@shCommentGroup
274 syn match shComment "\s\zs#.*$" contains=@shCommentGroup
275 syn match shQuickComment contained "#.*$"
276
277 " Here Documents: {{{1
278 " =========================================
279 if version < 600
280 syn region shHereDoc matchgroup=shRedir start="<<\s*\**END[a-zA-Z_0-9]*\**" matchgroup=shRedir end="^END[a-zA-Z_0-9]*$" contains=@shDblQuoteList
281 syn region shHereDoc matchgroup=shRedir start="<<-\s*\**END[a-zA-Z_0-9]*\**" matchgroup=shRedir end="^\s*END[a-zA-Z_0-9]*$" contains=@shDblQuoteList
282 syn region shHereDoc matchgroup=shRedir start="<<\s*\**EOF\**" matchgroup=shRedir end="^EOF$" contains=@shDblQuoteList
283 syn region shHereDoc matchgroup=shRedir start="<<-\s*\**EOF\**" matchgroup=shRedir end="^\s*EOF$" contains=@shDblQuoteList
284 syn region shHereDoc matchgroup=shRedir start="<<\s*\**\.\**" matchgroup=shRedir end="^\.$" contains=@shDblQuoteList
285 syn region shHereDoc matchgroup=shRedir start="<<-\s*\**\.\**" matchgroup=shRedir end="^\s*\.$" contains=@shDblQuoteList
286
287 elseif (g:sh_fold_enabled % (s:sh_fold_heredoc * 2))/s:sh_fold_heredoc
288 syn region shHereDoc matchgroup=shRedir fold start="<<\s*\z(\S*\)" matchgroup=shRedir end="^\z1\s*$" contains=@shDblQuoteList
289 syn region shHereDoc matchgroup=shRedir fold start="<<\s*\"\z(\S*\)\"" matchgroup=shRedir end="^\z1\s*$"
290 syn region shHereDoc matchgroup=shRedir fold start="<<\s*'\z(\S*\)'" matchgroup=shRedir end="^\z1\s*$"
291 syn region shHereDoc matchgroup=shRedir fold start="<<-\s*\z(\S*\)" matchgroup=shRedir end="^\s*\z1\s*$" contains=@shDblQuoteList
292 syn region shHereDoc matchgroup=shRedir fold start="<<-\s*\"\z(\S*\)\"" matchgroup=shRedir end="^\s*\z1\s*$"
293 syn region shHereDoc matchgroup=shRedir fold start="<<-\s*'\z(\S*\)'" matchgroup=shRedir end="^\s*\z1\s*$"
294 syn region shHereDoc matchgroup=shRedir fold start="<<\s*\\\_$\_s*\z(\S*\)" matchgroup=shRedir end="^\z1\s*$"
295 syn region shHereDoc matchgroup=shRedir fold start="<<\s*\\\_$\_s*\"\z(\S*\)\"" matchgroup=shRedir end="^\z1\s*$"
296 syn region shHereDoc matchgroup=shRedir fold start="<<-\s*\\\_$\_s*'\z(\S*\)'" matchgroup=shRedir end="^\s*\z1\s*$"
297 syn region shHereDoc matchgroup=shRedir fold start="<<-\s*\\\_$\_s*\z(\S*\)" matchgroup=shRedir end="^\s*\z1\s*$"
298 syn region shHereDoc matchgroup=shRedir fold start="<<-\s*\\\_$\_s*\"\z(\S*\)\"" matchgroup=shRedir end="^\s*\z1\s*$"
299 syn region shHereDoc matchgroup=shRedir fold start="<<\s*\\\_$\_s*'\z(\S*\)'" matchgroup=shRedir end="^\z1\s*$"
300 syn region shHereDoc matchgroup=shRedir fold start="<<\\\z(\S*\)" matchgroup=shRedir end="^\z1\s*$"
301
302 else
303 syn region shHereDoc matchgroup=shRedir start="<<\s*\\\=\z(\S*\)" matchgroup=shRedir end="^\z1\s*$" contains=@shDblQuoteList
304 syn region shHereDoc matchgroup=shRedir start="<<\s*\"\z(\S*\)\"" matchgroup=shRedir end="^\z1\s*$"
305 syn region shHereDoc matchgroup=shRedir start="<<-\s*\z(\S*\)" matchgroup=shRedir end="^\s*\z1\s*$" contains=@shDblQuoteList
306 syn region shHereDoc matchgroup=shRedir start="<<-\s*'\z(\S*\)'" matchgroup=shRedir end="^\s*\z1\s*$"
307 syn region shHereDoc matchgroup=shRedir start="<<\s*'\z(\S*\)'" matchgroup=shRedir end="^\z1\s*$"
308 syn region shHereDoc matchgroup=shRedir start="<<-\s*\"\z(\S*\)\"" matchgroup=shRedir end="^\s*\z1\s*$"
309 syn region shHereDoc matchgroup=shRedir start="<<\s*\\\_$\_s*\z(\S*\)" matchgroup=shRedir end="^\z1\s*$"
310 syn region shHereDoc matchgroup=shRedir start="<<-\s*\\\_$\_s*\z(\S*\)" matchgroup=shRedir end="^\s*\z1\s*$"
311 syn region shHereDoc matchgroup=shRedir start="<<-\s*\\\_$\_s*'\z(\S*\)'" matchgroup=shRedir end="^\s*\z1\s*$"
312 syn region shHereDoc matchgroup=shRedir start="<<\s*\\\_$\_s*'\z(\S*\)'" matchgroup=shRedir end="^\z1\s*$"
313 syn region shHereDoc matchgroup=shRedir start="<<\s*\\\_$\_s*\"\z(\S*\)\"" matchgroup=shRedir end="^\z1\s*$"
314 syn region shHereDoc matchgroup=shRedir start="<<-\s*\\\_$\_s*\"\z(\S*\)\"" matchgroup=shRedir end="^\s*\z1\s*$"
315 syn region shHereDoc matchgroup=shRedir start="<<\\\z(\S*\)" matchgroup=shRedir end="^\z1\s*$"
316 endif
317
318 " Here Strings: {{{1
319 " =============
320 if exists("b:is_bash")
321 syn match shRedir "<<<"
322 endif
323
324 " Identifiers: {{{1
325 "=============
326 syn match shSetOption "\s\zs[-+][a-zA-Z0-9]\+\>" contained
327 syn match shVariable "\<\([bwglsav]:\)\=[a-zA-Z0-9.!@_%+,]*\ze=" nextgroup=shSetIdentifier
328 syn match shSetIdentifier "=" contained nextgroup=shPattern,shDeref,shDerefSimple,shDoubleQuote,shSingleQuote,shExSingleQuote
329
330 " Functions: {{{1
331 if !exists("g:is_posix")
332 syn keyword shFunctionKey function skipwhite skipnl nextgroup=shFunctionTwo
333 endif
334
335 if exists("b:is_bash")
336 if (g:sh_fold_enabled % (s:sh_fold_functions * 2))/s:sh_fold_functions
337 syn region shFunctionOne fold matchgroup=shFunction start="^\s*\h[-a-zA-Z_0-9]*\s*()\_s*{" end="}" contains=@shFunctionList skipwhite skipnl nextgroup=shFunctionStart,shQuickComment
338 syn region shFunctionTwo fold matchgroup=shFunction start="\h[-a-zA-Z_0-9]*\s*\%(()\)\=\_s*{" end="}" contains=shFunctionKey,@shFunctionList contained skipwhite skipnl nextgroup=shFunctionStart,shQuickComment
339 else
340 syn region shFunctionOne matchgroup=shFunction start="^\s*\h[-a-zA-Z_0-9]*\s*()\_s*{" end="}" contains=@shFunctionList
341 syn region shFunctionTwo matchgroup=shFunction start="\h[-a-zA-Z_0-9]*\s*\%(()\)\=\_s*{" end="}" contains=shFunctionKey,@shFunctionList contained
342 endif
343 else
344 if (g:sh_fold_enabled % (s:sh_fold_functions * 2))/s:sh_fold_functions
345 syn region shFunctionOne fold matchgroup=shFunction start="^\s*\h\w*\s*()\_s*{" end="}" contains=@shFunctionList skipwhite skipnl nextgroup=shFunctionStart,shQuickComment
346 syn region shFunctionTwo fold matchgroup=shFunction start="\h\w*\s*\%(()\)\=\_s*{" end="}" contains=shFunctionKey,@shFunctionList contained skipwhite skipnl nextgroup=shFunctionStart,shQuickComment
347 else
348 syn region shFunctionOne matchgroup=shFunction start="^\s*\h\w*\s*()\_s*{" end="}" contains=@shFunctionList
349 syn region shFunctionTwo matchgroup=shFunction start="\h\w*\s*\%(()\)\=\_s*{" end="}" contains=shFunctionKey,@shFunctionList contained
350 endif
351 endif
352
353 " Parameter Dereferencing: {{{1
354 " ========================
355 syn match shDerefSimple "\$\%(\h\w*\|\d\)"
356 syn region shDeref matchgroup=PreProc start="\${" end="}" contains=@shDerefList,shDerefVarArray
357 syn match shDerefSimple "\$[-#*@!?]"
358 syn match shDerefSimple "\$\$"
359 if exists("b:is_bash") || exists("b:is_kornshell")
360 syn region shDeref matchgroup=PreProc start="\${##\=" end="}" contains=@shDerefList
361 syn region shDeref matchgroup=PreProc start="\${\$\$" end="}" contains=@shDerefList
362 endif
363
364 " bash: ${!prefix*} and ${#parameter}: {{{1
365 " ====================================
366 if exists("b:is_bash")
367 syn region shDeref matchgroup=PreProc start="\${!" end="\*\=}" contains=@shDerefList,shDerefOp
368 syn match shDerefVar contained "{\@<=!\w\+" nextgroup=@shDerefVarList
369 endif
370
371 syn match shDerefSpecial contained "{\@<=[-*@?0]" nextgroup=shDerefOp
372 syn match shDerefSpecial contained "\({[#!]\)\@<=[[:alnum:]*@_]\+" nextgroup=@shDerefVarList,shDerefOp
373 syn match shDerefVar contained "{\@<=\w\+" nextgroup=@shDerefVarList
374
375 " sh ksh bash : ${var[... ]...} array reference: {{{1
376 syn region shDerefVarArray contained matchgroup=shDeref start="\[" end="]" contains=@shCommandSubList nextgroup=shDerefOp
377
378 " Special ${parameter OPERATOR word} handling: {{{1
379 " sh ksh bash : ${parameter:-word} word is default value
380 " sh ksh bash : ${parameter:=word} assign word as default value
381 " sh ksh bash : ${parameter:?word} display word if parameter is null
382 " sh ksh bash : ${parameter:+word} use word if parameter is not null, otherwise nothing
383 " ksh bash : ${parameter#pattern} remove small left pattern
384 " ksh bash : ${parameter##pattern} remove large left pattern
385 " ksh bash : ${parameter%pattern} remove small right pattern
386 " ksh bash : ${parameter%%pattern} remove large right pattern
387 syn cluster shDerefPatternList contains=shDerefPattern,shDerefString
388 syn match shDerefOp contained ":\=[-=?]" nextgroup=@shDerefPatternList
389 syn match shDerefOp contained ":\=+" nextgroup=@shDerefPatternList
390 if exists("b:is_bash") || exists("b:is_kornshell")
391 syn match shDerefOp contained "#\{1,2}" nextgroup=@shDerefPatternList
392 syn match shDerefOp contained "%\{1,2}" nextgroup=@shDerefPatternList
393 syn match shDerefPattern contained "[^{}]\+" contains=shDeref,shDerefSimple,shDerefPattern,shDerefString,shCommandSub,shDerefEscape nextgroup=shDerefPattern
394 syn region shDerefPattern contained start="{" end="}" contains=shDeref,shDerefSimple,shDerefString,shCommandSub nextgroup=shDerefPattern
395 syn match shDerefEscape contained '\%(\\\\\)*\\.'
396 endif
397 syn region shDerefString contained matchgroup=shOperator start=+\%(\\\)\@<!'+ end=+'+ contains=shStringSpecial
398 syn region shDerefString contained matchgroup=shOperator start=+\%(\\\)\@<!"+ skip=+\\"+ end=+"+ contains=@shDblQuoteList,shStringSpecial
399 syn match shDerefString contained "\\["']" nextgroup=shDerefPattern
400
401 if exists("b:is_bash")
402 " bash : ${parameter:offset}
403 " bash : ${parameter:offset:length}
404 syn region shDerefOp contained start=":[$[:alnum:]_]"me=e-1 end=":"me=e-1 end="}"me=e-1 contains=@shCommandSubList nextgroup=shDerefPOL
405 syn match shDerefPOL contained ":[^}]\+" contains=@shCommandSubList
406
407 " bash : ${parameter//pattern/string}
408 " bash : ${parameter//pattern}
409 syn match shDerefPPS contained '/\{1,2}' nextgroup=shDerefPPSleft
410 syn region shDerefPPSleft contained start='.' skip=@\%(\\\)\/@ matchgroup=shDerefOp end='/' end='\ze}' nextgroup=shDerefPPSright contains=@shCommandSubList
411 syn region shDerefPPSright contained start='.' end='\ze}' contains=@shCommandSubList
412 endif
413
414 " Arithmetic Parenthesized Expressions: {{{1
415 syn region shParen matchgroup=shArithRegion start='(\ze[^(]' end=')' contains=@shArithParenList
416
417 " Useful sh Keywords: {{{1
418 " ===================
419 syn keyword shConditional contained elif else then
420 syn keyword shCondError elif else then
421
422 " Useful ksh Keywords: {{{1
423 " ====================
424 if exists("g:is_posix")
425 syn keyword shStatement command
426 else
427 syn keyword shStatement time
428 endif
429
430 " Useful bash Keywords: {{{1
431 " =====================
432
433 " Synchronization: {{{1
434 " ================
435 if !exists("sh_minlines")
436 let sh_minlines = 200
437 endif
438 if !exists("sh_maxlines")
439 let sh_maxlines = 2 * sh_minlines
440 endif
441 exec "syn sync minlines=" . sh_minlines . " maxlines=" . sh_maxlines
442 syn sync match shCaseEsacSync grouphere shCaseEsac "\<case\>"
443 syn sync match shCaseEsacSync groupthere shCaseEsac "\<esac\>"
444 syn sync match shDoSync grouphere shDo "\<do\>"
445 syn sync match shDoSync groupthere shDo "\<done\>"
446 syn sync match shForSync grouphere shFor "\<for\>"
447 syn sync match shForSync groupthere shFor "\<in\>"
448 syn sync match shIfSync grouphere shIf "\<if\>"
449 syn sync match shIfSync groupthere shIf "\<fi\>"
450 syn sync match shUntilSync grouphere shRepeat "\<until\>"
451 syn sync match shWhileSync grouphere shRepeat "\<while\>"
452
453 " Default Highlighting: {{{1
454 " =====================
455 hi def link shArithRegion shShellVariables
456 hi def link shBeginHere shRedir
457 hi def link shCaseBar shConditional
458 hi def link shCaseCommandSub shCommandSub
459 hi def link shCaseDoubleQuote shDoubleQuote
460 hi def link shCaseIn shConditional
461 hi def link shCaseSingleQuote shSingleQuote
462 hi def link shCaseStart shConditional
463 hi def link shCmdSubRegion shShellVariables
464 hi def link shColon shStatement
465 hi def link shDerefOp shOperator
466 hi def link shDerefPOL shDerefOp
467 hi def link shDerefPPS shDerefOp
468 hi def link shDeref shShellVariables
469 hi def link shDerefSimple shDeref
470 hi def link shDerefSpecial shDeref
471 hi def link shDerefString shDoubleQuote
472 hi def link shDerefVar shDeref
473 hi def link shDoubleQuote shString
474 hi def link shEcho shString
475 hi def link shEchoQuote shString
476 hi def link shEmbeddedEcho shString
477 hi def link shEscape shCommandSub
478 hi def link shExSingleQuote shSingleQuote
479 hi def link shFunction Function
480 hi def link shHereDoc shString
481 hi def link shHerePayload shHereDoc
482 hi def link shLoop shStatement
483 hi def link shOption shCommandSub
484 hi def link shPattern shString
485 hi def link shParen shArithmetic
486 hi def link shPosnParm shShellVariables
487 hi def link shQuickComment shComment
488 hi def link shRange shOperator
489 hi def link shRedir shOperator
490 hi def link shSetOption shOption
491 hi def link shSingleQuote shString
492 hi def link shSource shOperator
493 hi def link shStringSpecial shSpecial
494 hi def link shSubShRegion shOperator
495 hi def link shTestOpr shConditional
496 hi def link shTestPattern shString
497 hi def link shTestDoubleQuote shString
498 hi def link shTestSingleQuote shString
499 hi def link shVariable shSetList
500 hi def link shWrapLineOperator shOperator
501
502 if exists("b:is_bash")
503 hi def link bashAdminStatement shStatement
504 hi def link bashSpecialVariables shShellVariables
505 hi def link bashStatement shStatement
506 hi def link shFunctionParen Delimiter
507 hi def link shFunctionDelim Delimiter
508 endif
509 if exists("b:is_kornshell")
510 hi def link kshSpecialVariables shShellVariables
511 hi def link kshStatement shStatement
512 hi def link shFunctionParen Delimiter
513 endif
514
515 hi def link shCaseError Error
516 hi def link shCondError Error
517 hi def link shCurlyError Error
518 hi def link shDerefError Error
519 hi def link shDerefWordError Error
520 hi def link shDoError Error
521 hi def link shEsacError Error
522 hi def link shIfError Error
523 hi def link shInError Error
524 hi def link shParenError Error
525 hi def link shTestError Error
526 if exists("b:is_kornshell")
527 hi def link shDTestError Error
528 endif
529
530 hi def link shArithmetic Special
531 hi def link shCharClass Identifier
532 hi def link shSnglCase Statement
533 hi def link shCommandSub Special
534 hi def link shComment Comment
535 hi def link shConditional Conditional
536 hi def link shCtrlSeq Special
537 hi def link shExprRegion Delimiter
538 hi def link shFunctionKey Function
539 hi def link shFunctionName Function
540 hi def link shNumber Number
541 hi def link shOperator Operator
542 hi def link shRepeat Repeat
543 hi def link shSet Statement
544 hi def link shSetList Identifier
545 hi def link shShellVariables PreProc
546 hi def link shSpecial Special
547 hi def link shStatement Statement
548 hi def link shString String
549 hi def link shTodo Todo
550 hi def link shAlias Identifier
551
552 " Set Current Syntax: {{{1
553 " ===================
554 if exists("b:is_bash")
555 let b:current_syntax = "bash"
556 elseif exists("b:is_kornshell")
557 let b:current_syntax = "ksh"
558 else
559 let b:current_syntax = "sh"
560 endif
561
562 " vim: ts=16 fdm=marker