2 " Language: shell (sh) Korn shell (ksh) bash (sh)
3 " Maintainer: Dr. Charles E. Campbell, Jr. <NdrOchipS@PcampbellAfamily.Mbiz>
4 " Previous Maintainer: Lennart Schultz <Lennart.Schultz@ecmwf.int>
5 " Last Change: Jul 01, 2008
7 " URL: http://mysite.verizon.net/astronaut/vim/index.html#vimlinks_syntax
8 " For options and settings, please use: :help ft-sh-syntax
9 " This file includes many ideas from Éric Brunet (eric.brunet@ens.fr)
11 " For version 5.x: Clear all syntax items {{{1
12 " For version 6.x: Quit when a syntax file was already loaded
15 elseif exists("b:current_syntax")
19 " handling /bin/sh with is_kornshell/is_sh {{{1
20 " b:is_sh is set when "#! /bin/sh" is found;
21 " However, it often is just a masquerade by bash (typically Linux)
22 " or kornshell (typically workstations with Posix "sh").
23 " So, when the user sets "is_bash" or "is_kornshell",
24 " a b:is_sh is converted into b:is_bash/b:is_kornshell,
26 if !exists("b:is_kornshell") && !exists("b:is_bash")
27 if exists("g:is_posix") && !exists("g:is_kornshell")
28 let g:is_kornshell= g:is_posix
30 if exists("g:is_kornshell")
35 elseif exists("g:is_bash")
45 " adjust iskeyword for shell characters
46 "setlocal isk=@,48-57,_,192-255,#,.,/
48 " set up default g:sh_fold_enabled {{{1
49 if !exists("g:sh_fold_enabled")
50 let g:sh_fold_enabled= 0
51 elseif g:sh_fold_enabled != 0 && !has("folding")
52 let g:sh_fold_enabled= 0
53 echomsg "Ignoring g:sh_fold_enabled=".g:sh_fold_enabled."; need to re-compile vim for +fold support"
55 if !exists("s:sh_fold_functions")
56 let s:sh_fold_functions = 1
58 if !exists("s:sh_fold_heredoc")
59 let s:sh_fold_heredoc = 2
61 if !exists("s:sh_fold_ifdofor")
62 let s:sh_fold_ifdofor = 4
64 if g:sh_fold_enabled && &fdm == "manual"
68 " sh syntax is case sensitive {{{1
71 " Clusters: contains=@... clusters {{{1
72 "==================================
73 syn cluster shErrorList contains=shDoError,shIfError,shInError,shCaseError,shEsacError,shCurlyError,shParenError,shTestError
74 if exists("b:is_kornshell")
75 syn cluster ErrorList add=shDTestError
77 syn cluster shArithParenList contains=shArithmetic,shDeref,shDerefSimple,shEscape,shNumber,shOperator,shPosnParm,shExSingleQuote,shSingleQuote,shDoubleQuote,shStatement,shVariable,shAlias,shTest,shCtrlSeq,shSpecial,shParen
78 syn cluster shArithList contains=@shArithParenList,shParenError
79 syn cluster shCaseEsacList contains=shCaseStart,shCase,shCaseBar,shCaseIn,shComment,shDeref,shDerefSimple,shCaseCommandSub,shCaseExSingleQuote,shCaseSingleQuote,shCaseDoubleQuote,shCtrlSeq,@shErrorList,shStringSpecial
80 syn cluster shCaseList contains=@shCommandSubList,shCaseEsac,shColon,shCommandSub,shCommandSub,shComment,shDo,shEcho,shExpr,shFor,shHereDoc,shIf,shRedir,shSetList,shSource,shStatement,shVariable,shCtrlSeq
81 syn cluster shColonList contains=@shCaseList
82 syn cluster shCommandSubList contains=shArithmetic,shDeref,shDerefSimple,shEscape,shNumber,shOperator,shPosnParm,shExSingleQuote,shSingleQuote,shDoubleQuote,shStatement,shVariable,shSubSh,shAlias,shTest,shCtrlSeq,shSpecial
83 syn cluster shCurlyList contains=shNumber,shComma,shDeref,shDerefSimple,shDerefSpecial
84 syn cluster shDblQuoteList contains=shCommandSub,shDeref,shDerefSimple,shPosnParm,shExSingleQuote,shCtrlSeq,shSpecial
85 syn cluster shDerefList contains=shDeref,shDerefSimple,shDerefVar,shDerefSpecial,shDerefWordError,shDerefPPS
86 syn cluster shDerefVarList contains=shDerefOp,shDerefVarArray,shDerefOpError
87 syn cluster shEchoList contains=shArithmetic,shCommandSub,shDeref,shDerefSimple,shExpr,shExSingleQuote,shSingleQuote,shDoubleQuote,shCtrlSeq,shEchoQuote
88 syn cluster shExprList1 contains=shCharClass,shNumber,shOperator,shExSingleQuote,shSingleQuote,shDoubleQuote,shExpr,shDblBrace,shDeref,shDerefSimple,shCtrlSeq
89 syn cluster shExprList2 contains=@shExprList1,@shCaseList,shTest
90 syn cluster shFunctionList contains=@shCommandSubList,shCaseEsac,shColon,shCommandSub,shCommandSub,shComment,shDo,shEcho,shExpr,shFor,shHereDoc,shIf,shRedir,shSetList,shSource,shStatement,shVariable,shOperator,shCtrlSeq
91 if exists("b:is_kornshell") || exists("b:is_bash")
92 syn cluster shFunctionList add=shRepeat
93 syn cluster shFunctionList add=shDblBrace,shDblParen
95 syn cluster shHereBeginList contains=@shCommandSubList
96 syn cluster shHereList contains=shBeginHere,shHerePayload
97 syn cluster shHereListDQ contains=shBeginHere,@shDblQuoteList,shHerePayload
98 syn cluster shIdList contains=shCommandSub,shWrapLineOperator,shSetOption,shDeref,shDerefSimple,shRedir,shExSingleQuote,shSingleQuote,shDoubleQuote,shExpr,shCtrlSeq,shStringSpecial
99 syn cluster shLoopList contains=@shCaseList,shTestOpr,shExpr,shDblBrace,shConditional,shCaseEsac,shTest,@shErrorList,shSet
100 syn cluster shSubShList contains=@shCaseList,shOperator
101 syn cluster shTestList contains=shCharClass,shComment,shCommandSub,shDeref,shDerefSimple,shDoubleQuote,shExpr,shExpr,shNumber,shOperator,shExSingleQuote,shSingleQuote,shTestOpr,shTest,shCtrlSeq
106 " This one is needed INSIDE a CommandSub, so that `echo bla` be correct
107 syn region shEcho matchgroup=shStatement start="\<echo\>" skip="\\$" matchgroup=shOperator end="$" matchgroup=NONE end="[<>;&|()]"me=e-1 end="\d[<>]"me=e-2 end="#"me=e-1 contains=@shEchoList skipwhite nextgroup=shQuickComment
108 syn region shEcho matchgroup=shStatement start="\<print\>" skip="\\$" matchgroup=shOperator end="$" matchgroup=NONE end="[<>;&|()]"me=e-1 end="\d[<>]"me=e-2 end="#"me=e-1 contains=@shEchoList skipwhite nextgroup=shQuickComment
109 syn match shEchoQuote contained '\%(\\\\\)*\\["`']'
111 " This must be after the strings, so that ... \" will be correct
112 syn region shEmbeddedEcho contained matchgroup=shStatement start="\<print\>" skip="\\$" matchgroup=shOperator end="$" matchgroup=NONE end="[<>;&|`)]"me=e-1 end="\d[<>]"me=e-2 end="#"me=e-1 contains=shNumber,shExSingleQuote,shSingleQuote,shDeref,shDerefSimple,shSpecialVar,shOperator,shDoubleQuote,shCharClass,shCtrlSeq
116 if exists("b:is_kornshell") || exists("b:is_bash")
117 syn match shStatement "\<alias\>"
118 syn region shAlias matchgroup=shStatement start="\<alias\>\s\+\(\w\+\)\@=" skip="\\$" end="\>\|`"
119 syn region shAlias matchgroup=shStatement start="\<alias\>\s\+\(\w\+=\)\@=" skip="\\$" end="="
124 syn match shDoError "\<done\>"
125 syn match shIfError "\<fi\>"
126 syn match shInError "\<in\>"
127 syn match shCaseError ";;"
128 syn match shEsacError "\<esac\>"
129 syn match shCurlyError "}"
130 syn match shParenError ")"
131 if exists("b:is_kornshell")
132 syn match shDTestError "]]"
134 syn match shTestError "]"
137 " ====================
138 syn match shOption "\s\zs[-+][a-zA-Z0-9]\+\>"
139 syn match shOption "\s\zs--[^ \t$`'"|]\+"
141 " File Redirection Highlighted As Operators: {{{1
142 "===========================================
143 syn match shRedir "\d\=>\(&[-0-9]\)\="
144 syn match shRedir "\d\=>>-\="
145 syn match shRedir "\d\=<\(&[-0-9]\)\="
146 syn match shRedir "\d<<-\="
150 syn match shOperator "<<\|>>" contained
151 syn match shOperator "[!&;|]" contained
152 syn match shOperator "\[[[^:]\|\]]" contained
153 syn match shOperator "!\==" skipwhite nextgroup=shPattern
154 syn match shPattern "\<\S\+\())\)\@=" contained contains=shExSingleQuote,shSingleQuote,shDoubleQuote,shDeref
158 syn region shExpr transparent matchgroup=shExprRegion start="{" end="}" contains=@shExprList2
159 syn region shSubSh transparent matchgroup=shSubShRegion start="(" end=")" contains=@shSubShList
163 "syn region shExpr transparent matchgroup=shRange start="\[" skip=+\\\\\|\\$+ end="\]" contains=@shTestList
164 syn region shExpr matchgroup=shRange start="\[" skip=+\\\\\|\\$+ end="\]" contains=@shTestList
165 syn region shTest transparent matchgroup=shStatement start="\<test\>" skip=+\\\\\|\\$+ matchgroup=NONE end="[;&|]"me=e-1 end="$" contains=@shExprList1
166 syn match shTestOpr contained "<=\|>=\|!=\|==\|-.\>\|-\(nt\|ot\|ef\|eq\|ne\|lt\|le\|gt\|ge\)\>\|[!<>]"
167 syn match shTestOpr contained '=' skipwhite nextgroup=shTestDoubleQuote,shTestSingleQuote,shTestPattern
168 syn match shTestPattern contained '\w\+'
169 syn match shTestDoubleQuote contained '"[^"]*"'
170 syn match shTestSingleQuote contained '\\.'
171 syn match shTestSingleQuote contained "'[^']*'"
172 if exists("b:is_kornshell") || exists("b:is_bash")
173 syn region shDblBrace matchgroup=Delimiter start="\[\[" skip=+\\\\\|\\$+ end="\]\]" contains=@shTestList
174 syn region shDblParen matchgroup=Delimiter start="((" skip=+\\\\\|\\$+ end="))" contains=@shTestList
177 " Character Class In Range: {{{1
178 " =========================
179 syn match shCharClass contained "\[:\(backspace\|escape\|return\|xdigit\|alnum\|alpha\|blank\|cntrl\|digit\|graph\|lower\|print\|punct\|space\|upper\|tab\):\]"
181 " Loops: do, if, while, until {{{1
183 if (g:sh_fold_enabled % (s:sh_fold_ifdofor * 2))/s:sh_fold_ifdofor
184 syn region shDo fold transparent matchgroup=shConditional start="\<do\>" matchgroup=shConditional end="\<done\>" contains=@shLoopList
185 syn region shIf fold transparent matchgroup=shConditional start="\<if\_s" matchgroup=shConditional end="\<;\_s*then\>" end="\<fi\>" contains=@shLoopList,shDblBrace,shDblParen,shFunctionKey
186 syn region shFor fold matchgroup=shLoop start="\<for\_s" end="\<in\_s" end="\<do\>"me=e-2 contains=@shLoopList,shDblParen skipwhite nextgroup=shCurlyIn
188 syn region shDo transparent matchgroup=shConditional start="\<do\>" matchgroup=shConditional end="\<done\>" contains=@shLoopList
189 syn region shIf transparent matchgroup=shConditional start="\<if\_s" matchgroup=shConditional end="\<;\_s*then\>" end="\<fi\>" contains=@shLoopList,shDblBrace,shDblParen,shFunctionKey
190 syn region shFor matchgroup=shLoop start="\<for\_s" end="\<in\>" end="\<do\>"me=e-2 contains=@shLoopList,shDblParen skipwhite nextgroup=shCurlyIn
192 if exists("b:is_kornshell") || exists("b:is_bash")
193 syn cluster shCaseList add=shRepeat
194 syn cluster shFunctionList add=shRepeat
195 syn region shRepeat matchgroup=shLoop start="\<while\_s" end="\<in\_s" end="\<do\>"me=e-2 contains=@shLoopList,shDblParen,shDblBrace
196 syn region shRepeat matchgroup=shLoop start="\<until\_s" end="\<in\_s" end="\<do\>"me=e-2 contains=@shLoopList,shDblParen,shDblBrace
197 syn region shCaseEsac matchgroup=shConditional start="\<select\s" matchgroup=shConditional end="\<in\>" end="\<do\>" contains=@shLoopList
199 syn region shRepeat matchgroup=shLoop start="\<while\_s" end="\<do\>"me=e-2 contains=@shLoopList
200 syn region shRepeat matchgroup=shLoop start="\<until\_s" end="\<do\>"me=e-2 contains=@shLoopList
202 syn region shCurlyIn contained matchgroup=Delimiter start="{" end="}" contains=@shCurlyList
203 syn match shComma contained ","
205 " Case: case...esac {{{1
207 syn match shCaseBar contained skipwhite "\(^\|[^\\]\)\(\\\\\)*\zs|" nextgroup=shCase,shCaseStart,shCaseBar,shComment,shCaseExSingleQuote,shCaseSingleQuote,shCaseDoubleQuote
208 syn match shCaseStart contained skipwhite skipnl "(" nextgroup=shCase,shCaseBar
209 syn region shCase contained skipwhite skipnl matchgroup=shSnglCase start="\%(\\.\|[^#$()'" \t]\)\{-}\zs)" end=";;" end="esac"me=s-1 contains=@shCaseList nextgroup=shCaseStart,shCase,shComment
210 if (g:sh_fold_enabled % (s:sh_fold_ifdofor * 2))/s:sh_fold_ifdofor
211 syn region shCaseEsac fold matchgroup=shConditional start="\<case\>" end="\<esac\>" contains=@shCaseEsacList
213 syn region shCaseEsac matchgroup=shConditional start="\<case\>" end="\<esac\>" contains=@shCaseEsacList
215 syn keyword shCaseIn contained skipwhite skipnl in nextgroup=shCase,shCaseStart,shCaseBar,shComment,shCaseExSingleQuote,shCaseSingleQuote,shCaseDoubleQuote
216 if exists("b:is_bash")
217 syn region shCaseExSingleQuote matchgroup=shOperator start=+\$'+ skip=+\\\\\|\\.+ end=+'+ contains=shStringSpecial,shSpecial skipwhite skipnl nextgroup=shCaseBar contained
219 syn region shCaseExSingleQuote matchgroup=Error start=+\$'+ skip=+\\\\\|\\.+ end=+'+ contains=shStringSpecial skipwhite skipnl nextgroup=shCaseBar contained
221 syn region shCaseSingleQuote matchgroup=shOperator start=+'+ end=+'+ contains=shStringSpecial skipwhite skipnl nextgroup=shCaseBar contained
222 syn region shCaseDoubleQuote matchgroup=shOperator start=+"+ skip=+\\\\\|\\.+ end=+"+ contains=@shDblQuoteList,shStringSpecial skipwhite skipnl nextgroup=shCaseBar contained
223 syn region shCaseCommandSub start=+`+ skip=+\\\\\|\\.+ end=+`+ contains=@shCommandSubList skipwhite skipnl nextgroup=shCaseBar contained
227 syn match shWrapLineOperator "\\$"
228 syn region shCommandSub start="`" skip="\\\\\|\\." end="`" contains=@shCommandSubList
229 syn match shEscape contained '\\.'
231 " $() and $(()): {{{1
232 " $(..) is not supported by sh (Bourne shell). However, apparently
233 " some systems (HP?) have as their /bin/sh a (link to) Korn shell
234 " (ie. Posix compliant shell). /bin/ksh should work for those
235 " systems too, however, so the following syntax will flag $(..) as
236 " an Error under /bin/sh. By consensus of vimdev'ers!
237 if exists("b:is_kornshell") || exists("b:is_bash")
238 syn region shCommandSub matchgroup=shCmdSubRegion start="\$(" skip='\\\\\|\\.' end=")" contains=@shCommandSubList
239 syn region shArithmetic matchgroup=shArithRegion start="\$((" skip='\\\\\|\\.' end="))" contains=@shArithList
240 syn match shSkipInitWS contained "^\s\+"
242 syn region shCommandSub matchgroup=Error start="\$(" end=")" contains=@shCommandSubList
245 if exists("b:is_bash")
246 syn cluster shCommandSubList add=bashSpecialVariables,bashStatement
247 syn cluster shCaseList add=bashAdminStatement,bashStatement
248 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
249 syn keyword bashStatement chmod clear complete du egrep expr fgrep find gnufind gnugrep grep install less ls mkdir mv rm rmdir rpm sed sleep sort strip tail touch
250 syn keyword bashAdminStatement daemon killall killproc nice reload restart start status stop
253 if exists("b:is_kornshell")
254 syn cluster shCommandSubList add=kshSpecialVariables,kshStatement
255 syn cluster shCaseList add=kshStatement
256 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
257 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
260 syn match shSource "^\.\s"
261 syn match shSource "\s\.\s"
262 syn region shColon start="^\s*:" end="$\|" end="#"me=e-1 contains=@shColonList
264 " String And Character Constants: {{{1
265 "================================
266 syn match shNumber "-\=\<\d\+\>#\="
267 syn match shCtrlSeq "\\\d\d\d\|\\[abcfnrtv0]" contained
268 if exists("b:is_bash")
269 syn match shSpecial "\\\o\o\o\|\\x\x\x\|\\c.\|\\[abefnrtv]" contained
271 if exists("b:is_bash")
272 syn region shExSingleQuote matchgroup=shOperator start=+\$'+ skip=+\\\\\|\\.+ end=+'+ contains=shStringSpecial,shSpecial
274 syn region shExSingleQuote matchGroup=Error start=+\$'+ skip=+\\\\\|\\.+ end=+'+ contains=shStringSpecial
276 syn region shSingleQuote matchgroup=shOperator start=+'+ end=+'+ contains=shStringSpecial,@Spell
277 syn region shDoubleQuote matchgroup=shOperator start=+"+ skip=+\\"+ end=+"+ contains=@shDblQuoteList,shStringSpecial,@Spell
278 syn match shStringSpecial "[^[:print:]]" contained
279 syn match shStringSpecial "\%(\\\\\)*\\[\\"'`$()#]"
280 syn match shSpecial "[^\\]\zs\%(\\\\\)*\\[\\"'`$()#]"
281 syn match shSpecial "^\%(\\\\\)*\\[\\"'`$()#]"
285 syn cluster shCommentGroup contains=shTodo,@Spell
286 syn keyword shTodo contained COMBAK FIXME TODO XXX
287 syn match shComment "^\s*\zs#.*$" contains=@shCommentGroup
288 syn match shComment "\s\zs#.*$" contains=@shCommentGroup
289 syn match shQuickComment contained "#.*$"
291 " Here Documents: {{{1
292 " =========================================
294 syn region shHereDoc matchgroup=shRedir start="<<\s*\**END[a-zA-Z_0-9]*\**" matchgroup=shRedir end="^END[a-zA-Z_0-9]*$" contains=@shDblQuoteList
295 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
296 syn region shHereDoc matchgroup=shRedir start="<<\s*\**EOF\**" matchgroup=shRedir end="^EOF$" contains=@shDblQuoteList
297 syn region shHereDoc matchgroup=shRedir start="<<-\s*\**EOF\**" matchgroup=shRedir end="^\s*EOF$" contains=@shDblQuoteList
298 syn region shHereDoc matchgroup=shRedir start="<<\s*\**\.\**" matchgroup=shRedir end="^\.$" contains=@shDblQuoteList
299 syn region shHereDoc matchgroup=shRedir start="<<-\s*\**\.\**" matchgroup=shRedir end="^\s*\.$" contains=@shDblQuoteList
301 elseif (g:sh_fold_enabled % (s:sh_fold_heredoc * 2))/s:sh_fold_heredoc
302 syn region shHereDoc matchgroup=shRedir fold start="<<\s*\z(\S*\)" matchgroup=shRedir end="^\z1\s*$" contains=@shDblQuoteList
303 syn region shHereDoc matchgroup=shRedir fold start="<<\s*\"\z(\S*\)\"" matchgroup=shRedir end="^\z1\s*$"
304 syn region shHereDoc matchgroup=shRedir fold start="<<\s*'\z(\S*\)'" matchgroup=shRedir end="^\z1\s*$"
305 syn region shHereDoc matchgroup=shRedir fold start="<<-\s*\z(\S*\)" matchgroup=shRedir end="^\s*\z1\s*$" contains=@shDblQuoteList
306 syn region shHereDoc matchgroup=shRedir fold start="<<-\s*\"\z(\S*\)\"" matchgroup=shRedir end="^\s*\z1\s*$"
307 syn region shHereDoc matchgroup=shRedir fold start="<<-\s*'\z(\S*\)'" matchgroup=shRedir end="^\s*\z1\s*$"
308 syn region shHereDoc matchgroup=shRedir fold start="<<\s*\\\_$\_s*\z(\S*\)" matchgroup=shRedir end="^\z1\s*$"
309 syn region shHereDoc matchgroup=shRedir fold start="<<\s*\\\_$\_s*\"\z(\S*\)\"" matchgroup=shRedir end="^\z1\s*$"
310 syn region shHereDoc matchgroup=shRedir fold start="<<-\s*\\\_$\_s*'\z(\S*\)'" matchgroup=shRedir end="^\s*\z1\s*$"
311 syn region shHereDoc matchgroup=shRedir fold start="<<-\s*\\\_$\_s*\z(\S*\)" matchgroup=shRedir end="^\s*\z1\s*$"
312 syn region shHereDoc matchgroup=shRedir fold start="<<-\s*\\\_$\_s*\"\z(\S*\)\"" matchgroup=shRedir end="^\s*\z1\s*$"
313 syn region shHereDoc matchgroup=shRedir fold start="<<\s*\\\_$\_s*'\z(\S*\)'" matchgroup=shRedir end="^\z1\s*$"
314 syn region shHereDoc matchgroup=shRedir fold start="<<\\\z(\S*\)" matchgroup=shRedir end="^\z1\s*$"
317 syn region shHereDoc matchgroup=shRedir start="<<\s*\\\=\z(\S*\)" matchgroup=shRedir end="^\z1\s*$" contains=@shDblQuoteList
318 syn region shHereDoc matchgroup=shRedir start="<<\s*\"\z(\S*\)\"" matchgroup=shRedir end="^\z1\s*$"
319 syn region shHereDoc matchgroup=shRedir start="<<-\s*\z(\S*\)" matchgroup=shRedir end="^\s*\z1\s*$" contains=@shDblQuoteList
320 syn region shHereDoc matchgroup=shRedir start="<<-\s*'\z(\S*\)'" matchgroup=shRedir end="^\s*\z1\s*$"
321 syn region shHereDoc matchgroup=shRedir start="<<\s*'\z(\S*\)'" matchgroup=shRedir end="^\z1\s*$"
322 syn region shHereDoc matchgroup=shRedir start="<<-\s*\"\z(\S*\)\"" matchgroup=shRedir end="^\s*\z1\s*$"
323 syn region shHereDoc matchgroup=shRedir start="<<\s*\\\_$\_s*\z(\S*\)" matchgroup=shRedir end="^\z1\s*$"
324 syn region shHereDoc matchgroup=shRedir start="<<-\s*\\\_$\_s*\z(\S*\)" matchgroup=shRedir end="^\s*\z1\s*$"
325 syn region shHereDoc matchgroup=shRedir start="<<-\s*\\\_$\_s*'\z(\S*\)'" matchgroup=shRedir end="^\s*\z1\s*$"
326 syn region shHereDoc matchgroup=shRedir start="<<\s*\\\_$\_s*'\z(\S*\)'" matchgroup=shRedir end="^\z1\s*$"
327 syn region shHereDoc matchgroup=shRedir start="<<\s*\\\_$\_s*\"\z(\S*\)\"" matchgroup=shRedir end="^\z1\s*$"
328 syn region shHereDoc matchgroup=shRedir start="<<-\s*\\\_$\_s*\"\z(\S*\)\"" matchgroup=shRedir end="^\s*\z1\s*$"
329 syn region shHereDoc matchgroup=shRedir start="<<\\\z(\S*\)" matchgroup=shRedir end="^\z1\s*$"
334 if exists("b:is_bash")
335 syn match shRedir "<<<"
340 syn match shSetOption "\s\zs[-+][a-zA-Z0-9]\+\>" contained
341 syn match shVariable "\<\([bwglsav]:\)\=[a-zA-Z0-9.!@_%+,]*\ze=" nextgroup=shSetIdentifier
342 syn match shSetIdentifier "=" contained nextgroup=shPattern,shDeref,shDerefSimple,shDoubleQuote,shSingleQuote,shExSingleQuote
343 if exists("b:is_bash")
344 syn region shSetList oneline matchgroup=shSet start="\<\(declare\|typeset\|local\|export\|unset\)\>\ze[^/]" end="$" matchgroup=shOperator end="\ze[}|);&]" matchgroup=NONE end="\ze#\|=" contains=@shIdList
345 syn region shSetList oneline matchgroup=shSet start="\<set\>\ze[^/]" end="\ze[;|)]\|$" matchgroup=shOperator end="\ze[}|);&]" matchgroup=NONE end="\ze[#=]" contains=@shIdList
346 elseif exists("b:is_kornshell")
347 syn region shSetList oneline matchgroup=shSet start="\<\(typeset\|export\|unset\)\>\ze[^/]" end="$" matchgroup=shOperator end="\ze[}|);&]" matchgroup=NONE end="\ze[#=]" contains=@shIdList
348 syn region shSetList oneline matchgroup=shSet start="\<set\>\ze[^/]" end="$" matchgroup=shOperator end="\ze[}|);&]" matchgroup=NONE end="\ze[#=]" contains=@shIdList
350 syn region shSetList oneline matchgroup=shSet start="\<\(set\|export\|unset\)\>\ze[^/]" end="$" matchgroup=shOperator end="\ze[}|);&]" matchgroup=NONE end="\ze[#=]" contains=@shIdList
354 if !exists("g:is_posix")
355 syn keyword shFunctionKey function skipwhite skipnl nextgroup=shFunctionTwo
358 if exists("b:is_bash")
359 if (g:sh_fold_enabled % (s:sh_fold_functions * 2))/s:sh_fold_functions
360 syn region shFunctionOne fold matchgroup=shFunction start="^\s*\h[-a-zA-Z_0-9]*\s*()\_s*{" end="}" contains=@shFunctionList skipwhite skipnl nextgroup=shFunctionStart,shQuickComment
361 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
363 syn region shFunctionOne matchgroup=shFunction start="^\s*\h[-a-zA-Z_0-9]*\s*()\_s*{" end="}" contains=@shFunctionList
364 syn region shFunctionTwo matchgroup=shFunction start="\h[-a-zA-Z_0-9]*\s*\%(()\)\=\_s*{" end="}" contains=shFunctionKey,@shFunctionList contained
367 if (g:sh_fold_enabled % (s:sh_fold_functions * 2))/s:sh_fold_functions
368 syn region shFunctionOne fold matchgroup=shFunction start="^\s*\h\w*\s*()\_s*{" end="}" contains=@shFunctionList skipwhite skipnl nextgroup=shFunctionStart,shQuickComment
369 syn region shFunctionTwo fold matchgroup=shFunction start="\h\w*\s*\%(()\)\=\_s*{" end="}" contains=shFunctionKey,@shFunctionList contained skipwhite skipnl nextgroup=shFunctionStart,shQuickComment
371 syn region shFunctionOne matchgroup=shFunction start="^\s*\h\w*\s*()\_s*{" end="}" contains=@shFunctionList
372 syn region shFunctionTwo matchgroup=shFunction start="\h\w*\s*\%(()\)\=\_s*{" end="}" contains=shFunctionKey,@shFunctionList contained
376 " Parameter Dereferencing: {{{1
377 " ========================
378 syn match shDerefSimple "\$\%(\h\w*\|\d\)"
379 syn region shDeref matchgroup=PreProc start="\${" end="}" contains=@shDerefList,shDerefVarArray
380 syn match shDerefWordError "[^}$[]" contained
381 syn match shDerefSimple "\$[-#*@!?]"
382 syn match shDerefSimple "\$\$"
383 if exists("b:is_bash") || exists("b:is_kornshell")
384 syn region shDeref matchgroup=PreProc start="\${##\=" end="}" contains=@shDerefList
385 syn region shDeref matchgroup=PreProc start="\${\$\$" end="}" contains=@shDerefList
388 " bash: ${!prefix*} and ${#parameter}: {{{1
389 " ====================================
390 if exists("b:is_bash")
391 syn region shDeref matchgroup=PreProc start="\${!" end="\*\=}" contains=@shDerefList,shDerefOp
392 syn match shDerefVar contained "{\@<=!\w\+" nextgroup=@shDerefVarList
395 syn match shDerefSpecial contained "{\@<=[-*@?0]" nextgroup=shDerefOp,shDerefOpError
396 syn match shDerefSpecial contained "\({[#!]\)\@<=[[:alnum:]*@_]\+" nextgroup=@shDerefVarList,shDerefOp
397 syn match shDerefVar contained "{\@<=\w\+" nextgroup=@shDerefVarList
399 " sh ksh bash : ${var[... ]...} array reference: {{{1
400 syn region shDerefVarArray contained matchgroup=shDeref start="\[" end="]" contains=@shCommandSubList nextgroup=shDerefOp,shDerefOpError
402 " Special ${parameter OPERATOR word} handling: {{{1
403 " sh ksh bash : ${parameter:-word} word is default value
404 " sh ksh bash : ${parameter:=word} assign word as default value
405 " sh ksh bash : ${parameter:?word} display word if parameter is null
406 " sh ksh bash : ${parameter:+word} use word if parameter is not null, otherwise nothing
407 " ksh bash : ${parameter#pattern} remove small left pattern
408 " ksh bash : ${parameter##pattern} remove large left pattern
409 " ksh bash : ${parameter%pattern} remove small right pattern
410 " ksh bash : ${parameter%%pattern} remove large right pattern
411 syn cluster shDerefPatternList contains=shDerefPattern,shDerefString
412 syn match shDerefOpError contained ":[[:punct:]]"
413 syn match shDerefOp contained ":\=[-=?]" nextgroup=@shDerefPatternList
414 syn match shDerefOp contained ":\=+" nextgroup=@shDerefPatternList
415 if exists("b:is_bash") || exists("b:is_kornshell")
416 syn match shDerefOp contained "#\{1,2}" nextgroup=@shDerefPatternList
417 syn match shDerefOp contained "%\{1,2}" nextgroup=@shDerefPatternList
418 syn match shDerefPattern contained "[^{}]\+" contains=shDeref,shDerefSimple,shDerefPattern,shDerefString,shCommandSub,shDerefEscape nextgroup=shDerefPattern
419 syn region shDerefPattern contained start="{" end="}" contains=shDeref,shDerefSimple,shDerefString,shCommandSub nextgroup=shDerefPattern
420 syn match shDerefEscape contained '\%(\\\\\)*\\.'
422 syn region shDerefString contained matchgroup=shOperator start=+\%(\\\)\@<!'+ end=+'+ contains=shStringSpecial
423 syn region shDerefString contained matchgroup=shOperator start=+\%(\\\)\@<!"+ skip=+\\"+ end=+"+ contains=@shDblQuoteList,shStringSpecial
424 syn match shDerefString contained "\\["']" nextgroup=shDerefPattern
426 if exists("b:is_bash")
427 " bash : ${parameter:offset}
428 " bash : ${parameter:offset:length}
429 syn region shDerefOp contained start=":[$[:alnum:]_]"me=e-1 end=":"me=e-1 end="}"me=e-1 contains=@shCommandSubList nextgroup=shDerefPOL
430 syn match shDerefPOL contained ":[^}]\+" contains=@shCommandSubList
432 " bash : ${parameter//pattern/string}
433 " bash : ${parameter//pattern}
434 syn match shDerefPPS contained '/\{1,2}' nextgroup=shDerefPPSleft
435 syn region shDerefPPSleft contained start='.' skip=@\%(\\\)\/@ matchgroup=shDerefOp end='/' end='\ze}' nextgroup=shDerefPPSright contains=@shCommandSubList
436 syn region shDerefPPSright contained start='.' end='\ze}' contains=@shCommandSubList
439 " Arithmetic Parenthesized Expressions: {{{1
440 syn region shParen matchgroup=shArithRegion start='(\ze[^(]' end=')' contains=@shArithParenList
442 " Useful sh Keywords: {{{1
443 " ===================
444 syn keyword shStatement break cd chdir continue eval exec exit kill newgrp pwd read readonly return shift test trap ulimit umask wait
445 syn keyword shConditional contained elif else then
446 syn keyword shCondError elif else then
448 " Useful ksh Keywords: {{{1
449 " ====================
450 if exists("b:is_kornshell") || exists("b:is_bash")
451 syn keyword shStatement autoload bg false fc fg functions getopts hash history integer jobs let nohup print printf r stop suspend times true type unalias whence
452 if exists("g:is_posix")
453 syn keyword shStatement command
455 syn keyword shStatement time
458 " Useful bash Keywords: {{{1
459 " =====================
460 if exists("b:is_bash")
461 syn keyword shStatement bind builtin dirs disown enable help local logout popd pushd shopt source
463 syn keyword shStatement login newgrp
467 " Synchronization: {{{1
469 if !exists("sh_minlines")
470 let sh_minlines = 200
472 if !exists("sh_maxlines")
473 let sh_maxlines = 2 * sh_minlines
475 exec "syn sync minlines=" . sh_minlines . " maxlines=" . sh_maxlines
476 syn sync match shCaseEsacSync grouphere shCaseEsac "\<case\>"
477 syn sync match shCaseEsacSync groupthere shCaseEsac "\<esac\>"
478 syn sync match shDoSync grouphere shDo "\<do\>"
479 syn sync match shDoSync groupthere shDo "\<done\>"
480 syn sync match shForSync grouphere shFor "\<for\>"
481 syn sync match shForSync groupthere shFor "\<in\>"
482 syn sync match shIfSync grouphere shIf "\<if\>"
483 syn sync match shIfSync groupthere shIf "\<fi\>"
484 syn sync match shUntilSync grouphere shRepeat "\<until\>"
485 syn sync match shWhileSync grouphere shRepeat "\<while\>"
487 " Default Highlighting: {{{1
488 " =====================
489 hi def link shArithRegion shShellVariables
490 hi def link shBeginHere shRedir
491 hi def link shCaseBar shConditional
492 hi def link shCaseCommandSub shCommandSub
493 hi def link shCaseDoubleQuote shDoubleQuote
494 hi def link shCaseIn shConditional
495 hi def link shCaseSingleQuote shSingleQuote
496 hi def link shCaseStart shConditional
497 hi def link shCmdSubRegion shShellVariables
498 hi def link shColon shStatement
499 hi def link shDerefOp shOperator
500 hi def link shDerefPOL shDerefOp
501 hi def link shDerefPPS shDerefOp
502 hi def link shDeref shShellVariables
503 hi def link shDerefSimple shDeref
504 hi def link shDerefSpecial shDeref
505 hi def link shDerefString shDoubleQuote
506 hi def link shDerefVar shDeref
507 hi def link shDoubleQuote shString
508 hi def link shEcho shString
509 hi def link shEchoQuote shString
510 hi def link shEmbeddedEcho shString
511 hi def link shEscape shCommandSub
512 hi def link shExSingleQuote shSingleQuote
513 hi def link shFunction Function
514 hi def link shHereDoc shString
515 hi def link shHerePayload shHereDoc
516 hi def link shLoop shStatement
517 hi def link shOption shCommandSub
518 hi def link shPattern shString
519 hi def link shParen shArithmetic
520 hi def link shPosnParm shShellVariables
521 hi def link shQuickComment shComment
522 hi def link shRange shOperator
523 hi def link shRedir shOperator
524 hi def link shSetOption shOption
525 hi def link shSingleQuote shString
526 hi def link shSource shOperator
527 hi def link shStringSpecial shSpecial
528 hi def link shSubShRegion shOperator
529 hi def link shTestOpr shConditional
530 hi def link shTestPattern shString
531 hi def link shTestDoubleQuote shString
532 hi def link shTestSingleQuote shString
533 hi def link shVariable shSetList
534 hi def link shWrapLineOperator shOperator
536 if exists("b:is_bash")
537 hi def link bashAdminStatement shStatement
538 hi def link bashSpecialVariables shShellVariables
539 hi def link bashStatement shStatement
540 hi def link shFunctionParen Delimiter
541 hi def link shFunctionDelim Delimiter
543 if exists("b:is_kornshell")
544 hi def link kshSpecialVariables shShellVariables
545 hi def link kshStatement shStatement
546 hi def link shFunctionParen Delimiter
549 hi def link shCaseError Error
550 hi def link shCondError Error
551 hi def link shCurlyError Error
552 hi def link shDerefError Error
553 hi def link shDerefOpError Error
554 hi def link shDerefWordError Error
555 hi def link shDoError Error
556 hi def link shEsacError Error
557 hi def link shIfError Error
558 hi def link shInError Error
559 hi def link shParenError Error
560 hi def link shTestError Error
561 if exists("b:is_kornshell")
562 hi def link shDTestError Error
565 hi def link shArithmetic Special
566 hi def link shCharClass Identifier
567 hi def link shSnglCase Statement
568 hi def link shCommandSub Special
569 hi def link shComment Comment
570 hi def link shConditional Conditional
571 hi def link shCtrlSeq Special
572 hi def link shExprRegion Delimiter
573 hi def link shFunctionKey Function
574 hi def link shFunctionName Function
575 hi def link shNumber Number
576 hi def link shOperator Operator
577 hi def link shRepeat Repeat
578 hi def link shSet Statement
579 hi def link shSetList Identifier
580 hi def link shShellVariables PreProc
581 hi def link shSpecial Special
582 hi def link shStatement Statement
583 hi def link shString String
584 hi def link shTodo Todo
585 hi def link shAlias Identifier
587 " Set Current Syntax: {{{1
588 " ===================
589 if exists("b:is_bash")
590 let b:current_syntax = "bash"
591 elseif exists("b:is_kornshell")
592 let b:current_syntax = "ksh"
594 let b:current_syntax = "sh"
597 " vim: ts=16 fdm=marker