123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061 |
- %YAML 1.2
- ---
- # http://www.sublimetext.com/docs/3/syntax.html
- name: C++ (fmt)
- comment: I don't think anyone uses .hp. .cp tends to be paired with .h. (I could be wrong. :) -- chris
- file_extensions:
- - cpp
- - cc
- - cp
- - cxx
- - c++
- - C
- - h
- - hh
- - hpp
- - hxx
- - h++
- - inl
- - ipp
- first_line_match: '-\*- C\+\+ -\*-'
- scope: source.c++
- variables:
- identifier: \b[[:alpha:]_][[:alnum:]_]*\b # upper and lowercase
- macro_identifier: \b[[:upper:]_][[:upper:][:digit:]_]{2,}\b # only uppercase, at least 3 chars
- path_lookahead: '(?:::\s*)?(?:{{identifier}}\s*::\s*)*(?:template\s+)?{{identifier}}'
- operator_method_name: '\boperator\s*(?:[-+*/%^&|~!=<>]|[-+*/%^&|=!<>]=|<<=?|>>=?|&&|\|\||\+\+|--|,|->\*?|\(\)|\[\]|""\s*{{identifier}})'
- casts: 'const_cast|dynamic_cast|reinterpret_cast|static_cast'
- operator_keywords: 'and|and_eq|bitand|bitor|compl|not|not_eq|or|or_eq|xor|xor_eq|noexcept'
- control_keywords: 'break|case|catch|continue|default|do|else|for|goto|if|_Pragma|return|switch|throw|try|while'
- memory_operators: 'new|delete'
- basic_types: 'asm|__asm__|auto|bool|_Bool|char|_Complex|double|float|_Imaginary|int|long|short|signed|unsigned|void'
- before_tag: 'struct|union|enum\s+class|enum\s+struct|enum|class'
- declspec: '__declspec\(\s*\w+(?:\([^)]+\))?\s*\)'
- storage_classes: 'static|export|extern|friend|explicit|virtual|register|thread_local'
- type_qualifier: 'const|constexpr|mutable|typename|volatile'
- compiler_directive: 'inline|restrict|__restrict__|__restrict'
- visibility_modifiers: 'private|protected|public'
- other_keywords: 'typedef|nullptr|{{visibility_modifiers}}|static_assert|sizeof|using|typeid|alignof|alignas|namespace|template'
- modifiers: '{{storage_classes}}|{{type_qualifier}}|{{compiler_directive}}'
- non_angle_brackets: '(?=<<|<=)'
- regular: '[^(){}&;*^%=<>-]*'
- paren_open: (?:\(
- paren_close: '\))?'
- generic_open: (?:<
- generic_close: '>)?'
- balance_parentheses: '{{regular}}{{paren_open}}{{regular}}{{paren_close}}{{regular}}'
- generic_lookahead: <{{regular}}{{generic_open}}{{regular}}{{generic_open}}{{regular}}{{generic_close}}\s*{{generic_close}}{{balance_parentheses}}>
- data_structures_forward_decl_lookahead: '(\s+{{macro_identifier}})*\s*(:\s*({{path_lookahead}}|{{visibility_modifiers}}|,|\s|<[^;]*>)+)?;'
- non_func_keywords: 'if|for|switch|while|decltype|sizeof|__declspec|__attribute__|typeid|alignof|alignas|static_assert'
- format_spec: |-
- (?x:
- (?:.? [<>=^])? # fill align
- [ +-]? # sign
- \#? # alternate form
- # technically, octal and hexadecimal integers are also supported as 'width', but rarely used
- \d* # width
- ,? # thousands separator
- (?:\.\d+)? # precision
- [bcdeEfFgGnosxX%]? # type
- )
- contexts:
- main:
- - include: preprocessor-global
- - include: global
- #############################################################################
- # Reusable contexts
- #
- # The follow contexts are currently constructed to be reused in the
- # Objetive-C++ syntax. They are specifically constructed to not push into
- # sub-contexts, which ensures that Objective-C++ code isn't accidentally
- # lexed as plain C++.
- #
- # The "unique-*" contexts are additions that C++ makes over C, and thus can
- # be directly reused in Objective-C++ along with contexts from Objective-C
- # and C.
- #############################################################################
- unique-late-expressions:
- # This is highlighted after all of the other control keywords
- # to allow operator overloading to be lexed properly
- - match: \boperator\b
- scope: keyword.control.c++
- unique-modifiers:
- - match: \b({{modifiers}})\b
- scope: storage.modifier.c++
- unique-variables:
- - match: \bthis\b
- scope: variable.language.c++
- # common C++ instance var naming idiom -- fMemberName
- - match: '\b(f|m)[[:upper:]]\w*\b'
- scope: variable.other.readwrite.member.c++
- # common C++ instance var naming idiom -- m_member_name
- - match: '\bm_[[:alnum:]_]+\b'
- scope: variable.other.readwrite.member.c++
- unique-constants:
- - match: \bnullptr\b
- scope: constant.language.c++
- unique-keywords:
- - match: \busing\b
- scope: keyword.control.c++
- - match: \bbreak\b
- scope: keyword.control.flow.break.c++
- - match: \bcontinue\b
- scope: keyword.control.flow.continue.c++
- - match: \bgoto\b
- scope: keyword.control.flow.goto.c++
- - match: \breturn\b
- scope: keyword.control.flow.return.c++
- - match: \bthrow\b
- scope: keyword.control.flow.throw.c++
- - match: \b({{control_keywords}})\b
- scope: keyword.control.c++
- - match: '\bdelete\b(\s*\[\])?|\bnew\b(?!])'
- scope: keyword.control.c++
- - match: \b({{operator_keywords}})\b
- scope: keyword.operator.word.c++
- unique-types:
- - match: \b(char16_t|char32_t|wchar_t|nullptr_t)\b
- scope: storage.type.c++
- - match: \bclass\b
- scope: storage.type.c++
- unique-strings:
- - match: '((?:L|u8|u|U)?R)("([^\(\)\\ ]{0,16})\()'
- captures:
- 1: storage.type.string.c++
- 2: punctuation.definition.string.begin.c++
- push:
- - meta_scope: string.quoted.double.c++
- - match: '\)\3"'
- scope: punctuation.definition.string.end.c++
- pop: true
- - match: '\{\{|\}\}'
- scope: constant.character.escape.c++
- - include: formatting-syntax
- unique-numbers:
- - match: |-
- (?x)
- (?:
- # floats
- (?:
- (?:\b\d(?:[\d']*\d)?\.\d(?:[\d']*\d)?|\B\.\d(?:[\d']*\d)?)(?:[Ee][+-]?\d(?:[\d']*\d)?)?(?:[fFlL]|(?:i[fl]?|h|min|[mun]?s|_\w*))?\b
- |
- (?:\b\d(?:[\d']*\d)?\.)(?:\B|(?:[fFlL]|(?:i[fl]?|h|min|[mun]?s|_\w*))\b|(?:[Ee][+-]?\d(?:[\d']*\d)?)(?:[fFlL]|(?:i[fl]?|h|min|[mun]?s|_\w*))?\b)
- |
- \b\d(?:[\d']*\d)?(?:[Ee][+-]?\d(?:[\d']*\d)?)(?:[fFlL]|(?:i[fl]?|h|min|[mun]?s|_\w*))?\b
- )
- |
- # ints
- \b(?:
- (?:
- # dec
- [1-9](?:[\d']*\d)?
- |
- # oct
- 0(?:[0-7']*[0-7])?
- |
- # hex
- 0[Xx][\da-fA-F](?:[\da-fA-F']*[\da-fA-F])?
- |
- # bin
- 0[Bb][01](?:[01']*[01])?
- )
- # int suffixes
- (?:(?:l{1,2}|L{1,2})[uU]?|[uU](?:l{0,2}|L{0,2})|(?:i[fl]?|h|min|[mun]?s|_\w*))?)\b
- )
- (?!\.) # Number must not be followed by a decimal point
- scope: constant.numeric.c++
- identifiers:
- - match: '{{identifier}}\s*(::)\s*'
- captures:
- 1: punctuation.accessor.c++
- - match: '(?:(::)\s*)?{{identifier}}'
- captures:
- 1: punctuation.accessor.c++
- function-specifiers:
- - match: \b(const|final|noexcept|override)\b
- scope: storage.modifier.c++
- #############################################################################
- # The following are C++-specific contexts that should not be reused. This is
- # because they push into subcontexts and use variables that are C++-specific.
- #############################################################################
- ## Common context layout
- global:
- - match: '(?=\btemplate\b)'
- push:
- - include: template
- - match: (?=\S)
- set: global-modifier
- - include: namespace
- - include: keywords-angle-brackets
- - match: '(?={{path_lookahead}}\s*<)'
- push: global-modifier
- # Take care of comments just before a function definition.
- - match: /\*
- scope: punctuation.definition.comment.c
- push:
- - - match: \s*(?=\w)
- set: global-modifier
- - match: ""
- pop: true
- - - meta_scope: comment.block.c
- - match: \*/
- scope: punctuation.definition.comment.c
- pop: true
- - include: early-expressions
- - match: ^\s*\b(extern)(?=\s+"C(\+\+)?")
- scope: storage.modifier.c++
- push:
- - include: comments
- - include: strings
- - match: '\{'
- scope: punctuation.section.block.begin.c++
- set:
- - meta_scope: meta.extern-c.c++
- - match: '^\s*(#\s*ifdef)\s*__cplusplus\s*'
- scope: meta.preprocessor.c++
- captures:
- 1: keyword.control.import.c++
- set:
- - match: '\}'
- scope: punctuation.section.block.end.c++
- pop: true
- - include: preprocessor-global
- - include: global
- - match: '\}'
- scope: punctuation.section.block.end.c++
- pop: true
- - include: preprocessor-global
- - include: global
- - match: (?=\S)
- set: global-modifier
- - match: ^\s*(?=\w)
- push: global-modifier
- - include: late-expressions
- statements:
- - include: preprocessor-statements
- - include: scope:source.c#label
- - include: expressions
- expressions:
- - include: early-expressions
- - include: late-expressions
- early-expressions:
- - include: early-expressions-before-generic-type
- - include: generic-type
- - include: early-expressions-after-generic-type
- early-expressions-before-generic-type:
- - include: preprocessor-expressions
- - include: comments
- - include: case-default
- - include: typedef
- - include: keywords-angle-brackets
- - include: keywords-parens
- - include: keywords
- - include: numbers
- # Prevent a '<' from getting scoped as the start of another template
- # parameter list, if in reality a less-than-or-equals sign is meant.
- - match: <=
- scope: keyword.operator.comparison.c
- early-expressions-after-generic-type:
- - include: members-arrow
- - include: operators
- - include: members-dot
- - include: strings
- - include: parens
- - include: brackets
- - include: block
- - include: variables
- - include: constants
- - match: ','
- scope: punctuation.separator.c++
- - match: '\)|\}'
- scope: invalid.illegal.stray-bracket-end.c++
- expressions-minus-generic-type:
- - include: early-expressions-before-generic-type
- - include: angle-brackets
- - include: early-expressions-after-generic-type
- - include: late-expressions
- expressions-minus-generic-type-function-call:
- - include: early-expressions-before-generic-type
- - include: angle-brackets
- - include: early-expressions-after-generic-type
- - include: late-expressions-before-function-call
- - include: identifiers
- - match: ';'
- scope: punctuation.terminator.c++
- late-expressions:
- - include: late-expressions-before-function-call
- - include: function-call
- - include: identifiers
- - match: ';'
- scope: punctuation.terminator.c++
- late-expressions-before-function-call:
- - include: unique-late-expressions
- - include: modifiers-parens
- - include: modifiers
- - include: types
- expressions-minus-function-call:
- - include: early-expressions
- - include: late-expressions-before-function-call
- - include: identifiers
- - match: ';'
- scope: punctuation.terminator.c++
- comments:
- - include: scope:source.c#comments
- operators:
- - include: scope:source.c#operators
- modifiers:
- - include: unique-modifiers
- - include: scope:source.c#modifiers
- variables:
- - include: unique-variables
- - include: scope:source.c#variables
- constants:
- - include: unique-constants
- - include: scope:source.c#constants
- keywords:
- - include: unique-keywords
- - include: scope:source.c#keywords
- types:
- - include: unique-types
- - include: types-parens
- - include: scope:source.c#types
- strings:
- - include: unique-strings
- - match: '(L|u8|u|U)?(")'
- captures:
- 1: storage.type.string.c++
- 2: punctuation.definition.string.begin.c++
- push:
- - meta_scope: string.quoted.double.c++
- - match: '"'
- scope: punctuation.definition.string.end.c++
- pop: true
- - include: scope:source.c#string_escaped_char
- - match: |-
- (?x)%
- (\d+\$)? # field (argument #)
- [#0\- +']* # flags
- [,;:_]? # separator character (AltiVec)
- ((-?\d+)|\*(-?\d+\$)?)? # minimum field width
- (\.((-?\d+)|\*(-?\d+\$)?)?)? # precision
- (hh|h|ll|l|j|t|z|q|L|vh|vl|v|hv|hl)? # length modifier
- (\[[^\]]+\]|[am]s|[diouxXDOUeEfFgGaACcSspn%]) # conversion type
- scope: constant.other.placeholder.c++
- - match: '\{\{|\}\}'
- scope: constant.character.escape.c++
- - include: formatting-syntax
- - include: scope:source.c#strings
- formatting-syntax:
- # https://docs.python.org/3.6/library/string.html#formatstrings
- - match: |- # simple form
- (?x)
- (\{)
- (?: [\w.\[\]]+)? # field_name
- ( ! [ars])? # conversion
- ( : (?:{{format_spec}}| # format_spec OR
- [^}%]*%.[^}]*) # any format-like string
- )?
- (\})
- scope: constant.other.placeholder.c++
- captures:
- 1: punctuation.definition.placeholder.begin.c++
- 2: storage.modifier.c++onversion.c++
- 3: constant.other.format-spec.c++
- 4: punctuation.definition.placeholder.end.c++
- - match: \{(?=[^\}"']+\{[^"']*\}) # complex (nested) form
- scope: punctuation.definition.placeholder.begin.c++
- push:
- - meta_scope: constant.other.placeholder.c++
- - match: \}
- scope: punctuation.definition.placeholder.end.c++
- pop: true
- - match: '[\w.\[\]]+'
- - match: '![ars]'
- scope: storage.modifier.conversion.c++
- - match: ':'
- push:
- - meta_scope: meta.format-spec.c++ constant.other.format-spec.c++
- - match: (?=\})
- pop: true
- - include: formatting-syntax
- numbers:
- - include: unique-numbers
- - include: scope:source.c#numbers
- ## C++-specific contexts
- case-default:
- - match: '\b(default|case)\b'
- scope: keyword.control.c++
- push:
- - match: (?=[);,])
- pop: true
- - match: ':'
- scope: punctuation.separator.c++
- pop: true
- - include: expressions
- modifiers-parens:
- - match: '\b(alignas)\b\s*(\()'
- captures:
- 1: storage.modifier.c++
- 2: meta.group.c++ punctuation.section.group.begin.c++
- push:
- - meta_content_scope: meta.group.c++
- - match: '\)'
- scope: meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- - match: \b(__attribute__)\s*(\(\()
- captures:
- 1: storage.modifier.c++
- 2: meta.group.c++ punctuation.section.group.begin.c++
- push :
- - meta_scope: meta.attribute.c++
- - meta_content_scope: meta.group.c++
- - include: parens
- - include: strings
- - match: \)\)
- scope: meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - match: \b(__declspec)(\()
- captures:
- 1: storage.modifier.c++
- 2: meta.group.c++ punctuation.section.group.begin.c++
- push:
- - meta_content_scope: meta.group.c++
- - match: '\)'
- scope: meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - match: '\b(align|allocate|code_seg|deprecated|property|uuid)\b\s*(\()'
- captures:
- 1: storage.modifier.c++
- 2: meta.group.c++ punctuation.section.group.begin.c++
- push:
- - meta_content_scope: meta.group.c++
- - match: '\)'
- scope: meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: numbers
- - include: strings
- - match: \b(get|put)\b
- scope: variable.parameter.c++
- - match: ','
- scope: punctuation.separator.c++
- - match: '='
- scope: keyword.operator.assignment.c++
- - match: '\b(appdomain|deprecated|dllimport|dllexport|jintrinsic|naked|noalias|noinline|noreturn|nothrow|novtable|process|restrict|safebuffers|selectany|thread)\b'
- scope: constant.other.c++
- types-parens:
- - match: '\b(decltype)\b\s*(\()'
- captures:
- 1: storage.type.c++
- 2: meta.group.c++ punctuation.section.group.begin.c++
- push:
- - meta_content_scope: meta.group.c++
- - match: '\)'
- scope: meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- keywords-angle-brackets:
- - match: \b({{casts}})\b\s*
- scope: keyword.operator.word.cast.c++
- push:
- - match: '>'
- scope: punctuation.section.generic.end.c++
- pop: true
- - match: '<'
- scope: punctuation.section.generic.begin.c++
- push:
- - match: '(?=>)'
- pop: true
- - include: expressions-minus-generic-type-function-call
- keywords-parens:
- - match: '\b(alignof|typeid|static_assert|sizeof)\b\s*(\()'
- captures:
- 1: keyword.operator.word.c++
- 2: meta.group.c++ punctuation.section.group.begin.c++
- push:
- - meta_content_scope: meta.group.c++
- - match: '\)'
- scope: meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- namespace:
- - match: '\b(using)\s+(namespace)\s+(?={{path_lookahead}})'
- captures:
- 1: keyword.control.c++
- 2: keyword.control.c++
- push:
- - include: identifiers
- - match: ''
- pop: true
- - match: '\b(namespace)\s+(?=({{path_lookahead}})?(?!\s*[;,]))'
- scope: meta.namespace.c++
- captures:
- 1: keyword.control.c++
- push:
- - meta_content_scope: meta.namespace.c++ entity.name.namespace.c++
- - include: identifiers
- - match: ''
- set:
- - meta_scope: meta.namespace.c++
- - include: comments
- - match: '='
- scope: keyword.operator.alias.c++
- - match: '(?=;)'
- pop: true
- - match: '\}'
- scope: meta.block.c++ punctuation.section.block.end.c++
- pop: true
- - match: '\{'
- scope: punctuation.section.block.begin.c++
- push:
- - meta_scope: meta.block.c++
- - match: '(?=\})'
- pop: true
- - include: preprocessor-global
- - include: global
- - include: expressions
- template-common:
- # Exit the template scope if we hit some basic invalid characters. This
- # helps when a user is in the middle of typing their template types and
- # prevents re-highlighting the whole file until the next > is found.
- - match: (?=[{};])
- pop: true
- - include: expressions
- template:
- - match: \btemplate\b
- scope: storage.type.template.c++
- push:
- - meta_scope: meta.template.c++
- # Explicitly include comments here at the top, in order to NOT match the
- # \S lookahead in the case of comments.
- - include: comments
- - match: <
- scope: punctuation.section.generic.begin.c++
- set:
- - meta_content_scope: meta.template.c++
- - match: '>'
- scope: meta.template.c++ punctuation.section.generic.end.c++
- pop: true
- - match: \.{3}
- scope: keyword.operator.variadic.c++
- - match: \b(typename|{{before_tag}})\b
- scope: storage.type.c++
- - include: template # include template here for nested templates
- - include: template-common
- - match: (?=\S)
- set:
- - meta_content_scope: meta.template.c++
- - match: \b({{before_tag}})\b
- scope: storage.type.c++
- - include: template-common
- generic-type:
- - match: '(?=(?!template){{path_lookahead}}\s*{{generic_lookahead}}\s*\()'
- push:
- - meta_scope: meta.function-call.c++
- - match: \btemplate\b
- scope: storage.type.template.c++
- - match: '(?:(::)\s*)?{{identifier}}\s*(::)\s*'
- captures:
- 1: punctuation.accessor.double-colon.c++
- 2: punctuation.accessor.double-colon.c++
- - match: (?:(::)\s*)?({{identifier}})\s*(<)
- captures:
- 1: punctuation.accessor.double-colon.c++
- 2: variable.function.c++
- 3: punctuation.section.generic.begin.c++
- push:
- - match: '>'
- scope: punctuation.section.generic.end.c++
- pop: true
- - include: expressions-minus-generic-type-function-call
- - match: (?:(::)\s*)?({{identifier}})\s*(\()
- captures:
- 1: punctuation.accessor.double-colon.c++
- 2: variable.function.c++
- 3: punctuation.section.group.begin.c++
- set:
- - meta_scope: meta.function-call.c++
- - meta_content_scope: meta.group.c++
- - match: '\)'
- scope: meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- - include: angle-brackets
- - match: '\('
- scope: meta.group.c++ punctuation.section.group.begin.c++
- set:
- - meta_scope: meta.function-call.c++
- - meta_content_scope: meta.group.c++
- - match: '\)'
- scope: meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- - match: '(?=(?!template){{path_lookahead}}\s*{{generic_lookahead}})'
- push:
- - include: identifiers
- - match: '<'
- scope: punctuation.section.generic.begin.c++
- set:
- - match: '>'
- scope: punctuation.section.generic.end.c++
- pop: true
- - include: expressions-minus-generic-type-function-call
- angle-brackets:
- - match: '<(?!<)'
- scope: punctuation.section.generic.begin.c++
- push:
- - match: '>'
- scope: punctuation.section.generic.end.c++
- pop: true
- - include: expressions-minus-generic-type-function-call
- block:
- - match: '\{'
- scope: punctuation.section.block.begin.c++
- push:
- - meta_scope: meta.block.c++
- - match: (?=^\s*#\s*(elif|else|endif)\b)
- pop: true
- - match: '\}'
- scope: punctuation.section.block.end.c++
- pop: true
- - include: statements
- function-call:
- - match: (?={{path_lookahead}}\s*\()
- push:
- - meta_scope: meta.function-call.c++
- - include: scope:source.c#c99
- - match: '(?:(::)\s*)?{{identifier}}\s*(::)\s*'
- scope: variable.function.c++
- captures:
- 1: punctuation.accessor.c++
- 2: punctuation.accessor.c++
- - match: '(?:(::)\s*)?{{identifier}}'
- scope: variable.function.c++
- captures:
- 1: punctuation.accessor.c++
- - match: '\('
- scope: meta.group.c++ punctuation.section.group.begin.c++
- set:
- - meta_content_scope: meta.function-call.c++ meta.group.c++
- - match: '\)'
- scope: meta.function-call.c++ meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- members-inside-function-call:
- - meta_content_scope: meta.method-call.c++ meta.group.c++
- - match: \)
- scope: meta.method-call.c++ meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- members-after-accessor-junction:
- # After we've seen an accessor (dot or arrow), this context decides what
- # kind of entity we're accessing.
- - include: comments
- - match: \btemplate\b
- scope: meta.method-call.c++ storage.type.template.c++
- # Guaranteed to be a template member function call after we match this
- set:
- - meta_content_scope: meta.method-call.c++
- - include: comments
- - match: '{{identifier}}'
- scope: variable.function.member.c++
- set:
- - meta_content_scope: meta.method-call.c++
- - match: \(
- scope: meta.group.c++ punctuation.section.group.begin.c++
- set: members-inside-function-call
- - include: comments
- - include: angle-brackets
- - match: (?=\S) # safety pop
- pop: true
- - match: (?=\S) # safety pop
- pop: true
- # Operator overloading
- - match: '({{operator_method_name}})\s*(\()'
- captures:
- 0: meta.method-call.c++
- 1: variable.function.member.c++
- 2: meta.group.c++ punctuation.section.group.begin.c++
- set: members-inside-function-call
- # Non-templated member function call
- - match: (~?{{identifier}})\s*(\()
- captures:
- 0: meta.method-call.c++
- 1: variable.function.member.c++
- 2: meta.group.c++ punctuation.section.group.begin.c++
- set: members-inside-function-call
- # Templated member function call
- - match: (~?{{identifier}})\s*(?={{generic_lookahead}})
- captures:
- 1: variable.function.member.c++
- set:
- - meta_scope: meta.method-call.c++
- - match: <
- scope: punctuation.section.generic.begin.c++
- set:
- - meta_content_scope: meta.method-call.c++
- - match: '>'
- scope: punctuation.section.generic.end.c++
- set:
- - meta_content_scope: meta.method-call.c++
- - include: comments
- - match: \(
- scope: punctuation.section.group.begin.c++
- set: members-inside-function-call
- - match: (?=\S) # safety pop
- pop: true
- - include: expressions
- # Explicit base-class access
- - match: ({{identifier}})\s*(::)
- captures:
- 1: variable.other.base-class.c++
- 2: punctuation.accessor.double-colon.c++
- set: members-after-accessor-junction # reset
- # Just a regular member variable
- - match: '{{identifier}}'
- scope: variable.other.readwrite.member.c++
- pop: true
- members-dot:
- - include: scope:source.c#access-illegal
- # No lookahead required because members-dot goes after operators in the
- # early-expressions-after-generic-type context. This means triple dots
- # (i.e. "..." or "variadic") is attempted first.
- - match: \.
- scope: punctuation.accessor.dot.c++
- push: members-after-accessor-junction
- members-arrow:
- # This needs to be before operators in the
- # early-expressions-after-generic-type context because otherwise the "->"
- # from the C language will match.
- - match: ->
- scope: punctuation.accessor.arrow.c++
- push: members-after-accessor-junction
- typedef:
- - match: \btypedef\b
- scope: storage.type.c++
- push:
- - match: ({{identifier}})?\s*(?=;)
- captures:
- 1: entity.name.type.typedef.c++
- pop: true
- - match: \b(struct)\s+({{identifier}})\b
- captures:
- 1: storage.type.c++
- - include: expressions-minus-generic-type
- parens:
- - match: \(
- scope: punctuation.section.group.begin.c++
- push:
- - meta_scope: meta.group.c++
- - match: \)
- scope: punctuation.section.group.end.c++
- pop: true
- - include: expressions
- brackets:
- - match: \[
- scope: punctuation.section.brackets.begin.c++
- push:
- - meta_scope: meta.brackets.c++
- - match: \]
- scope: punctuation.section.brackets.end.c++
- pop: true
- - include: expressions
- function-trailing-return-type:
- - match: '{{non_angle_brackets}}'
- pop: true
- - include: angle-brackets
- - include: types
- - include: modifiers-parens
- - include: modifiers
- - include: identifiers
- - match: \*|&
- scope: keyword.operator.c++
- - include: function-trailing-return-type-parens
- - match: '(?=\S)'
- pop: true
- function-trailing-return-type-parens:
- - match: \(
- scope: punctuation.section.group.begin.c++
- push:
- - meta_scope: meta.group.c++
- - match: \)
- scope: punctuation.section.group.end.c++
- pop: true
- - include: function-trailing-return-type
- ## Detection of function and data structure definitions at the global level
- global-modifier:
- - include: comments
- - include: modifiers-parens
- - include: modifiers
- # Constructors and destructors don't have a type
- - match: '(?={{path_lookahead}}\s*::\s*{{identifier}}\s*(\(|$))'
- set:
- - meta_content_scope: meta.function.c++ entity.name.function.constructor.c++
- - include: identifiers
- - match: '(?=[^\w\s])'
- set: function-definition-params
- - match: '(?={{path_lookahead}}\s*::\s*~{{identifier}}\s*(\(|$))'
- set:
- - meta_content_scope: meta.function.c++ entity.name.function.destructor.c++
- - include: identifiers
- - match: '~{{identifier}}'
- - match: '(?=[^\w\s])'
- set: function-definition-params
- # If we see a path ending in :: before a newline, we don't know if it is
- # a constructor or destructor, or a long return type, so we are just going
- # to treat it like a regular function. Most likely it is a constructor,
- # since it doesn't seem most developers would create such a long typename.
- - match: '(?={{path_lookahead}}\s*::\s*$)'
- set:
- - meta_content_scope: meta.function.c++ entity.name.function.c++
- - include: identifiers
- - match: '~{{identifier}}'
- - match: '(?=[^\w\s])'
- set: function-definition-params
- - include: unique-strings
- - match: '(?=\S)'
- set: global-type
- global-type:
- - include: comments
- - match: \*|&
- scope: keyword.operator.c++
- - match: '(?=\b({{control_keywords}}|{{operator_keywords}}|{{casts}}|{{memory_operators}}|{{other_keywords}}|operator)\b)'
- pop: true
- - match: '(?=\s)'
- set: global-maybe-function
- # If a class/struct/enum followed by a name that is not a macro or declspec
- # then this is likely a return type of a function. This is uncommon.
- - match: |-
- (?x:
- ({{before_tag}})
- \s+
- (?=
- (?![[:upper:][:digit:]_]+\b|__declspec|{{before_tag}})
- {{path_lookahead}}
- (\s+{{identifier}}\s*\(|\s*[*&])
- )
- )
- captures:
- 1: storage.type.c++
- set:
- - include: identifiers
- - match: ''
- set: global-maybe-function
- # The previous match handles return types of struct/enum/etc from a func,
- # there this one exits the context to allow matching an actual struct/class
- - match: '(?=\b({{before_tag}})\b)'
- set: data-structures
- - match: '(?=\b({{casts}})\b\s*<)'
- pop: true
- - match: '{{non_angle_brackets}}'
- pop: true
- - include: angle-brackets
- - include: types
- # Allow a macro call
- - match: '({{identifier}})\s*(\()(?=[^\)]+\))'
- captures:
- 1: variable.function.c++
- 2: meta.group.c++ punctuation.section.group.begin.c++
- push:
- - meta_scope: meta.function-call.c++
- - meta_content_scope: meta.group.c++
- - match: '\)'
- scope: meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- - match: '(?={{path_lookahead}}\s*\()'
- set:
- - include: function-call
- - match: ''
- pop: true
- - include: variables
- - include: constants
- - include: identifiers
- - match: (?=\W)
- pop: true
- global-maybe-function:
- - include: comments
- # Consume pointer info, macros and any type info that was offset by macros
- - match: \*|&
- scope: keyword.operator.c++
- - match: '(?=\b({{control_keywords}}|{{operator_keywords}}|{{casts}}|{{memory_operators}}|{{other_keywords}})\b)'
- pop: true
- - match: '\b({{type_qualifier}})\b'
- scope: storage.modifier.c++
- - match: '{{non_angle_brackets}}'
- pop: true
- - include: angle-brackets
- - include: types
- - include: modifiers-parens
- - include: modifiers
- # All uppercase identifier just before a newline is most likely a macro
- - match: '[[:upper:][:digit:]_]+\s*$'
- # Operator overloading
- - match: '(?=({{path_lookahead}}\s*(?:{{generic_lookahead}})?::\s*)?{{operator_method_name}}\s*(\(|$))'
- set:
- - meta_content_scope: meta.function.c++ entity.name.function.c++
- - include: identifiers
- - match: '(?=\s*(\(|$))'
- set: function-definition-params
- # Identifier that is not the function name - likely a macro or type
- - match: '(?={{path_lookahead}}([ \t]+|[*&])(?!\s*(<|::|\(|$)))'
- push:
- - include: identifiers
- - match: ''
- pop: true
- # Real function definition
- - match: '(?={{path_lookahead}}({{generic_lookahead}}({{path_lookahead}})?)\s*(\(|$))'
- set: [function-definition-params, global-function-identifier-generic]
- - match: '(?={{path_lookahead}}\s*(\(|$))'
- set: [function-definition-params, global-function-identifier]
- - match: '(?={{path_lookahead}}\s*::\s*$)'
- set: [function-definition-params, global-function-identifier]
- - match: '(?=\S)'
- pop: true
- global-function-identifier-generic:
- - include: angle-brackets
- - match: '::'
- scope: punctuation.accessor.c++
- - match: '(?={{identifier}}<.*>\s*\()'
- push:
- - meta_content_scope: entity.name.function.c++
- - include: identifiers
- - match: '(?=<)'
- pop: true
- - match: '(?={{identifier}}\s*\()'
- push:
- - meta_content_scope: entity.name.function.c++
- - include: identifiers
- - match: ''
- pop: true
- - match: '(?=\()'
- pop: true
- global-function-identifier:
- - meta_content_scope: entity.name.function.c++
- - include: identifiers
- - match: '(?=\S)'
- pop: true
- function-definition-params:
- - meta_content_scope: meta.function.c++
- - include: comments
- - match: '(?=\()'
- set:
- - match: \(
- scope: meta.function.parameters.c++ meta.group.c++ punctuation.section.group.begin.c++
- set:
- - meta_content_scope: meta.function.parameters.c++ meta.group.c++
- - match : \)
- scope: punctuation.section.group.end.c++
- set: function-definition-continue
- - match: '\bvoid\b'
- scope: storage.type.c++
- - match: '{{identifier}}(?=\s*(\[|,|\)|=))'
- scope: variable.parameter.c++
- - match: '='
- scope: keyword.operator.assignment.c++
- push:
- - match: '(?=,|\))'
- pop: true
- - include: expressions-minus-generic-type
- - include: scope:source.c#preprocessor-line-continuation
- - include: expressions-minus-generic-type
- - include: scope:source.c#preprocessor-line-continuation
- - match: (?=\S)
- pop: true
- function-definition-continue:
- - meta_content_scope: meta.function.c++
- - include: comments
- - match: '(?=;)'
- pop: true
- - match: '->'
- scope: punctuation.separator.c++
- set: function-definition-trailing-return
- - include: function-specifiers
- - match: '='
- scope: keyword.operator.assignment.c++
- - match: '&'
- scope: keyword.operator.c++
- - match: \b0\b
- scope: constant.numeric.c++
- - match: \b(default|delete)\b
- scope: storage.modifier.c++
- - match: '(?=\{)'
- set: function-definition-body
- - match: '(?=\S)'
- pop: true
- function-definition-trailing-return:
- - include: comments
- - match: '(?=;)'
- pop: true
- - match: '(?=\{)'
- set: function-definition-body
- - include: function-specifiers
- - include: function-trailing-return-type
- function-definition-body:
- - meta_content_scope: meta.function.c++ meta.block.c++
- - match: '\{'
- scope: punctuation.section.block.begin.c++
- set:
- - meta_content_scope: meta.function.c++ meta.block.c++
- - match: '\}'
- scope: meta.function.c++ meta.block.c++ punctuation.section.block.end.c++
- pop: true
- - match: (?=^\s*#\s*(elif|else|endif)\b)
- pop: true
- - match: '(?=({{before_tag}})([^(;]+$|.*\{))'
- push: data-structures
- - include: statements
- ## Data structures including classes, structs, unions and enums
- data-structures:
- - match: '\bclass\b'
- scope: storage.type.c++
- set: data-structures-class-definition
- # Detect variable type definitions using struct/enum/union followed by a tag
- - match: '\b({{before_tag}})(?=\s+{{path_lookahead}}\s+{{path_lookahead}}\s*[=;\[])'
- scope: storage.type.c++
- - match: '\bstruct\b'
- scope: storage.type.c++
- set: data-structures-struct-definition
- - match: '\benum(\s+(class|struct))?\b'
- scope: storage.type.c++
- set: data-structures-enum-definition
- - match: '\bunion\b'
- scope: storage.type.c++
- set: data-structures-union-definition
- - match: '(?=\S)'
- pop: true
- preprocessor-workaround-eat-macro-before-identifier:
- # Handle macros so they aren't matched as the class name
- - match: ({{macro_identifier}})(?=\s+~?{{identifier}})
- captures:
- 1: meta.assumed-macro.c
- data-structures-class-definition:
- - meta_scope: meta.class.c++
- - include: data-structures-definition-common-begin
- - match: '{{identifier}}(?={{data_structures_forward_decl_lookahead}})'
- scope: entity.name.class.forward-decl.c++
- set: data-structures-class-definition-after-identifier
- - match: '{{identifier}}'
- scope: entity.name.class.c++
- set: data-structures-class-definition-after-identifier
- - match: '(?=[:{])'
- set: data-structures-class-definition-after-identifier
- - match: '(?=;)'
- pop: true
- data-structures-class-definition-after-identifier:
- - meta_content_scope: meta.class.c++
- - include: data-structures-definition-common-begin
- # No matching of identifiers since they should all be macros at this point
- - include: data-structures-definition-common-end
- - match: '\{'
- scope: meta.block.c++ punctuation.section.block.begin.c++
- set:
- - meta_content_scope: meta.class.c++ meta.block.c++
- - match: '\}'
- scope: meta.class.c++ meta.block.c++ punctuation.section.block.end.c++
- pop: true
- - include: data-structures-body
- data-structures-struct-definition:
- - meta_scope: meta.struct.c++
- - include: data-structures-definition-common-begin
- - match: '{{identifier}}(?={{data_structures_forward_decl_lookahead}})'
- scope: entity.name.struct.forward-decl.c++
- set: data-structures-struct-definition-after-identifier
- - match: '{{identifier}}'
- scope: entity.name.struct.c++
- set: data-structures-struct-definition-after-identifier
- - match: '(?=[:{])'
- set: data-structures-struct-definition-after-identifier
- - match: '(?=;)'
- pop: true
- data-structures-struct-definition-after-identifier:
- - meta_content_scope: meta.struct.c++
- - include: data-structures-definition-common-begin
- # No matching of identifiers since they should all be macros at this point
- - include: data-structures-definition-common-end
- - match: '\{'
- scope: meta.block.c++ punctuation.section.block.begin.c++
- set:
- - meta_content_scope: meta.struct.c++ meta.block.c++
- - match: '\}'
- scope: meta.struct.c++ meta.block.c++ punctuation.section.block.end.c++
- pop: true
- - include: data-structures-body
- data-structures-enum-definition:
- - meta_scope: meta.enum.c++
- - include: data-structures-definition-common-begin
- - match: '{{identifier}}(?={{data_structures_forward_decl_lookahead}})'
- scope: entity.name.enum.forward-decl.c++
- set: data-structures-enum-definition-after-identifier
- - match: '{{identifier}}'
- scope: entity.name.enum.c++
- set: data-structures-enum-definition-after-identifier
- - match: '(?=[:{])'
- set: data-structures-enum-definition-after-identifier
- - match: '(?=;)'
- pop: true
- data-structures-enum-definition-after-identifier:
- - meta_content_scope: meta.enum.c++
- - include: data-structures-definition-common-begin
- # No matching of identifiers since they should all be macros at this point
- - include: data-structures-definition-common-end
- - match: '\{'
- scope: meta.block.c++ punctuation.section.block.begin.c++
- set:
- - meta_content_scope: meta.enum.c++ meta.block.c++
- # Enums don't support methods so we have a simplified body
- - match: '\}'
- scope: meta.enum.c++ meta.block.c++ punctuation.section.block.end.c++
- pop: true
- - include: statements
- data-structures-union-definition:
- - meta_scope: meta.union.c++
- - include: data-structures-definition-common-begin
- - match: '{{identifier}}(?={{data_structures_forward_decl_lookahead}})'
- scope: entity.name.union.forward-decl.c++
- set: data-structures-union-definition-after-identifier
- - match: '{{identifier}}'
- scope: entity.name.union.c++
- set: data-structures-union-definition-after-identifier
- - match: '(?=[{])'
- set: data-structures-union-definition-after-identifier
- - match: '(?=;)'
- pop: true
- data-structures-union-definition-after-identifier:
- - meta_content_scope: meta.union.c++
- - include: data-structures-definition-common-begin
- # No matching of identifiers since they should all be macros at this point
- # Unions don't support base classes
- - include: angle-brackets
- - match: '\{'
- scope: meta.block.c++ punctuation.section.block.begin.c++
- set:
- - meta_content_scope: meta.union.c++ meta.block.c++
- - match: '\}'
- scope: meta.union.c++ meta.block.c++ punctuation.section.block.end.c++
- pop: true
- - include: data-structures-body
- - match: '(?=;)'
- pop: true
- data-structures-definition-common-begin:
- - include: comments
- - match: '(?=\b(?:{{before_tag}}|{{control_keywords}})\b)'
- pop: true
- - include: preprocessor-other
- - include: modifiers-parens
- - include: modifiers
- - include: preprocessor-workaround-eat-macro-before-identifier
- data-structures-definition-common-end:
- - include: angle-brackets
- - match: \bfinal\b
- scope: storage.modifier.c++
- - match: ':'
- scope: punctuation.separator.c++
- push:
- - include: comments
- - include: preprocessor-other
- - include: modifiers-parens
- - include: modifiers
- - match: '\b(virtual|{{visibility_modifiers}})\b'
- scope: storage.modifier.c++
- - match: (?={{path_lookahead}})
- push:
- - meta_scope: entity.other.inherited-class.c++
- - include: identifiers
- - match: ''
- pop: true
- - include: angle-brackets
- - match: ','
- scope: punctuation.separator.c++
- - match: (?=\{|;)
- pop: true
- - match: '(?=;)'
- pop: true
- data-structures-body:
- - include: preprocessor-data-structures
- - match: '(?=\btemplate\b)'
- push:
- - include: template
- - match: (?=\S)
- set: data-structures-modifier
- - include: typedef
- - match: \b({{visibility_modifiers}})\s*(:)(?!:)
- captures:
- 1: storage.modifier.c++
- 2: punctuation.section.class.c++
- - match: '^\s*(?=(?:~?\w+|::))'
- push: data-structures-modifier
- - include: expressions-minus-generic-type
- data-structures-modifier:
- - match: '\bfriend\b'
- scope: storage.modifier.c++
- push:
- - match: (?=;)
- pop: true
- - match: '\{'
- scope: punctuation.section.block.begin.c++
- set:
- - meta_scope: meta.block.c++
- - match: '\}'
- scope: punctuation.section.block.end.c++
- pop: true
- - include: statements
- - match: '\b({{before_tag}})\b'
- scope: storage.type.c++
- - include: expressions-minus-function-call
- - include: comments
- - include: modifiers-parens
- - include: modifiers
- - match: '\bstatic_assert(?=\s*\()'
- scope: meta.static-assert.c++ keyword.operator.word.c++
- push:
- - match: '\('
- scope: meta.group.c++ punctuation.section.group.begin.c++
- set:
- - meta_content_scope: meta.function-call.c++ meta.group.c++
- - match: '\)'
- scope: meta.function-call.c++ meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- # Destructor
- - match: '(?:{{identifier}}\s*(::)\s*)?~{{identifier}}(?=\s*(\(|$))'
- scope: meta.method.destructor.c++ entity.name.function.destructor.c++
- captures:
- 1: punctuation.accessor.c++
- set: method-definition-params
- # It's a macro, not a constructor if there is no type in the first param
- - match: '({{identifier}})\s*(\()(?=\s*(?!void){{identifier}}\s*[),])'
- captures:
- 1: variable.function.c++
- 2: meta.group.c++ punctuation.section.group.begin.c++
- push:
- - meta_scope: meta.function-call.c++
- - meta_content_scope: meta.group.c++
- - match: '\)'
- scope: meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- # Constructor
- - include: preprocessor-workaround-eat-macro-before-identifier
- - match: '((?!{{before_tag}}|template){{identifier}})(?=\s*\()'
- scope: meta.method.constructor.c++ entity.name.function.constructor.c++
- set: method-definition-params
- # Long form constructor
- - match: '({{identifier}}\s*(::)\s*{{identifier}})(?=\s*\()'
- captures:
- 1: meta.method.constructor.c++ entity.name.function.constructor.c++
- 2: punctuation.accessor.c++
- push: method-definition-params
- - match: '(?=\S)'
- set: data-structures-type
- data-structures-type:
- - include: comments
- - match: \*|&
- scope: keyword.operator.c++
- # Cast methods
- - match: '(operator)\s+({{identifier}})(?=\s*(\(|$))'
- captures:
- 1: keyword.control.c++
- 2: meta.method.c++ entity.name.function.c++
- set: method-definition-params
- - match: '(?=\b({{control_keywords}}|{{operator_keywords}}|{{casts}}|{{memory_operators}}|{{other_keywords}}|operator)\b)'
- pop: true
- - match: '(?=\s)'
- set: data-structures-maybe-method
- # If a class/struct/enum followed by a name that is not a macro or declspec
- # then this is likely a return type of a function. This is uncommon.
- - match: |-
- (?x:
- ({{before_tag}})
- \s+
- (?=
- (?![[:upper:][:digit:]_]+\b|__declspec|{{before_tag}})
- {{path_lookahead}}
- (\s+{{identifier}}\s*\(|\s*[*&])
- )
- )
- captures:
- 1: storage.type.c++
- set:
- - include: identifiers
- - match: ''
- set: data-structures-maybe-method
- # The previous match handles return types of struct/enum/etc from a func,
- # there this one exits the context to allow matching an actual struct/class
- - match: '(?=\b({{before_tag}})\b)'
- set: data-structures
- - match: '(?=\b({{casts}})\b\s*<)'
- pop: true
- - match: '{{non_angle_brackets}}'
- pop: true
- - include: angle-brackets
- - include: types
- - include: variables
- - include: constants
- - include: identifiers
- - match: (?=[&*])
- set: data-structures-maybe-method
- - match: (?=\W)
- pop: true
- data-structures-maybe-method:
- - include: comments
- # Consume pointer info, macros and any type info that was offset by macros
- - match: \*|&
- scope: keyword.operator.c++
- - match: '(?=\b({{control_keywords}}|{{operator_keywords}}|{{casts}}|{{memory_operators}}|{{other_keywords}})\b)'
- pop: true
- - match: '\b({{type_qualifier}})\b'
- scope: storage.modifier.c++
- - match: '{{non_angle_brackets}}'
- pop: true
- - include: angle-brackets
- - include: types
- - include: modifiers-parens
- - include: modifiers
- # Operator overloading
- - match: '{{operator_method_name}}(?=\s*(\(|$))'
- scope: meta.method.c++ entity.name.function.c++
- set: method-definition-params
- # Identifier that is not the function name - likely a macro or type
- - match: '(?={{path_lookahead}}([ \t]+|[*&])(?!\s*(<|::|\()))'
- push:
- - include: identifiers
- - match: ''
- pop: true
- # Real function definition
- - match: '(?={{path_lookahead}}({{generic_lookahead}})\s*(\())'
- set: [method-definition-params, data-structures-function-identifier-generic]
- - match: '(?={{path_lookahead}}\s*(\())'
- set: [method-definition-params, data-structures-function-identifier]
- - match: '(?={{path_lookahead}}\s*::\s*$)'
- set: [method-definition-params, data-structures-function-identifier]
- - match: '(?=\S)'
- pop: true
- data-structures-function-identifier-generic:
- - include: angle-brackets
- - match: '(?={{identifier}})'
- push:
- - meta_content_scope: entity.name.function.c++
- - include: identifiers
- - match: '(?=<)'
- pop: true
- - match: '(?=\()'
- pop: true
- data-structures-function-identifier:
- - meta_content_scope: entity.name.function.c++
- - include: identifiers
- - match: '(?=\S)'
- pop: true
- method-definition-params:
- - meta_content_scope: meta.method.c++
- - include: comments
- - match: '(?=\()'
- set:
- - match: \(
- scope: meta.method.parameters.c++ meta.group.c++ punctuation.section.group.begin.c++
- set:
- - meta_content_scope: meta.method.parameters.c++ meta.group.c++
- - match : \)
- scope: punctuation.section.group.end.c++
- set: method-definition-continue
- - match: '\bvoid\b'
- scope: storage.type.c++
- - match: '{{identifier}}(?=\s*(\[|,|\)|=))'
- scope: variable.parameter.c++
- - match: '='
- scope: keyword.operator.assignment.c++
- push:
- - match: '(?=,|\))'
- pop: true
- - include: expressions-minus-generic-type
- - include: expressions-minus-generic-type
- - match: '(?=\S)'
- pop: true
- method-definition-continue:
- - meta_content_scope: meta.method.c++
- - include: comments
- - match: '(?=;)'
- pop: true
- - match: '->'
- scope: punctuation.separator.c++
- set: method-definition-trailing-return
- - include: function-specifiers
- - match: '='
- scope: keyword.operator.assignment.c++
- - match: '&'
- scope: keyword.operator.c++
- - match: \b0\b
- scope: constant.numeric.c++
- - match: \b(default|delete)\b
- scope: storage.modifier.c++
- - match: '(?=:)'
- set:
- - match: ':'
- scope: punctuation.separator.initializer-list.c++
- set:
- - meta_scope: meta.method.constructor.initializer-list.c++
- - match: '{{identifier}}'
- scope: variable.other.readwrite.member.c++
- push:
- - match: \(
- scope: meta.group.c++ punctuation.section.group.begin.c++
- set:
- - meta_content_scope: meta.group.c++
- - match: \)
- scope: meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- - match: \{
- scope: meta.group.c++ punctuation.section.group.begin.c++
- set:
- - meta_content_scope: meta.group.c++
- - match: \}
- scope: meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- - include: comments
- - match: (?=\{|;)
- set: method-definition-continue
- - include: expressions
- - match: '(?=\{)'
- set: method-definition-body
- - match: '(?=\S)'
- pop: true
- method-definition-trailing-return:
- - include: comments
- - match: '(?=;)'
- pop: true
- - match: '(?=\{)'
- set: method-definition-body
- - include: function-specifiers
- - include: function-trailing-return-type
- method-definition-body:
- - meta_content_scope: meta.method.c++ meta.block.c++
- - match: '\{'
- scope: punctuation.section.block.begin.c++
- set:
- - meta_content_scope: meta.method.c++ meta.block.c++
- - match: '\}'
- scope: meta.method.c++ meta.block.c++ punctuation.section.block.end.c++
- pop: true
- - match: (?=^\s*#\s*(elif|else|endif)\b)
- pop: true
- - match: '(?=({{before_tag}})([^(;]+$|.*\{))'
- push: data-structures
- - include: statements
- ## Preprocessor for data-structures
- preprocessor-data-structures:
- - include: preprocessor-rule-enabled-data-structures
- - include: preprocessor-rule-disabled-data-structures
- - include: preprocessor-practical-workarounds
- preprocessor-rule-disabled-data-structures:
- - match: ^\s*((#if)\s+(0))\b
- captures:
- 1: meta.preprocessor.c++
- 2: keyword.control.import.c++
- 3: constant.numeric.preprocessor.c++
- push:
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- pop: true
- - match: ^\s*(#\s*else)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.else.c++
- push:
- - match: (?=^\s*#\s*endif\b)
- pop: true
- - include: negated-block
- - include: data-structures-body
- - match: ""
- push:
- - meta_scope: comment.block.preprocessor.if-branch.c++
- - match: (?=^\s*#\s*(else|endif)\b)
- pop: true
- - include: scope:source.c#preprocessor-disabled
- preprocessor-rule-enabled-data-structures:
- - match: ^\s*((#if)\s+(0*1))\b
- captures:
- 1: meta.preprocessor.c++
- 2: keyword.control.import.c++
- 3: constant.numeric.preprocessor.c++
- push:
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- pop: true
- - match: ^\s*(#\s*else)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.else.c++
- push:
- - meta_content_scope: comment.block.preprocessor.else-branch.c++
- - match: (?=^\s*#\s*endif\b)
- pop: true
- - include: scope:source.c#preprocessor-disabled
- - match: ""
- push:
- - match: (?=^\s*#\s*(else|endif)\b)
- pop: true
- - include: negated-block
- - include: data-structures-body
- ## Preprocessor for global
- preprocessor-global:
- - include: preprocessor-rule-enabled-global
- - include: preprocessor-rule-disabled-global
- - include: preprocessor-rule-other-global
- preprocessor-statements:
- - include: preprocessor-rule-enabled-statements
- - include: preprocessor-rule-disabled-statements
- - include: preprocessor-rule-other-statements
- preprocessor-expressions:
- - include: scope:source.c#incomplete-inc
- - include: preprocessor-macro-define
- - include: scope:source.c#pragma-mark
- - include: preprocessor-other
- preprocessor-rule-disabled-global:
- - match: ^\s*((#if)\s+(0))\b
- captures:
- 1: meta.preprocessor.c++
- 2: keyword.control.import.c++
- 3: constant.numeric.preprocessor.c++
- push:
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- pop: true
- - match: ^\s*(#\s*else)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.else.c++
- push:
- - match: (?=^\s*#\s*endif\b)
- pop: true
- - include: preprocessor-global
- - include: negated-block
- - include: global
- - match: ""
- push:
- - meta_scope: comment.block.preprocessor.if-branch.c++
- - match: (?=^\s*#\s*(else|endif)\b)
- pop: true
- - include: scope:source.c#preprocessor-disabled
- preprocessor-rule-enabled-global:
- - match: ^\s*((#if)\s+(0*1))\b
- captures:
- 1: meta.preprocessor.c++
- 2: keyword.control.import.c++
- 3: constant.numeric.preprocessor.c++
- push:
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- pop: true
- - match: ^\s*(#\s*else)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.else.c++
- push:
- - meta_content_scope: comment.block.preprocessor.else-branch.c++
- - match: (?=^\s*#\s*endif\b)
- pop: true
- - include: scope:source.c#preprocessor-disabled
- - match: ""
- push:
- - match: (?=^\s*#\s*(else|endif)\b)
- pop: true
- - include: preprocessor-global
- - include: negated-block
- - include: global
- preprocessor-rule-other-global:
- - match: ^\s*(#\s*(?:if|ifdef|ifndef))\b
- captures:
- 1: keyword.control.import.c++
- push:
- - meta_scope: meta.preprocessor.c++
- - include: scope:source.c#preprocessor-line-continuation
- - include: scope:source.c#preprocessor-comments
- - match: \bdefined\b
- scope: keyword.control.c++
- # Enter a new scope where all elif/else branches have their
- # contexts popped by a subsequent elif/else/endif. This ensures that
- # preprocessor branches don't push multiple meta.block scopes on
- # the stack, thus messing up the "global" context's detection of
- # functions.
- - match: $\n
- set: preprocessor-if-branch-global
- # These gymnastics here ensure that we are properly handling scope even
- # when the preprocessor is used to create different scope beginnings, such
- # as a different if/while condition
- preprocessor-if-branch-global:
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- pop: true
- - match: (?=^\s*#\s*(elif|else)\b)
- push: preprocessor-elif-else-branch-global
- - match: \{
- scope: punctuation.section.block.begin.c++
- set: preprocessor-block-if-branch-global
- - include: preprocessor-global
- - include: negated-block
- - include: global
- preprocessor-block-if-branch-global:
- - meta_scope: meta.block.c++
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- set: preprocessor-block-finish-global
- - match: (?=^\s*#\s*(elif|else)\b)
- push: preprocessor-elif-else-branch-global
- - match: \}
- scope: punctuation.section.block.end.c++
- set: preprocessor-if-branch-global
- - include: statements
- preprocessor-block-finish-global:
- - meta_scope: meta.block.c++
- - match: ^\s*(#\s*(?:if|ifdef|ifndef))\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- set: preprocessor-block-finish-if-branch-global
- - match: \}
- scope: punctuation.section.block.end.c++
- pop: true
- - include: statements
- preprocessor-block-finish-if-branch-global:
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: keyword.control.import.c++
- pop: true
- - match: \}
- scope: punctuation.section.block.end.c++
- set: preprocessor-if-branch-global
- - include: statements
- preprocessor-elif-else-branch-global:
- - match: (?=^\s*#\s*(endif)\b)
- pop: true
- - include: preprocessor-global
- - include: negated-block
- - include: global
- ## Preprocessor for statements
- preprocessor-rule-disabled-statements:
- - match: ^\s*((#if)\s+(0))\b
- captures:
- 1: meta.preprocessor.c++
- 2: keyword.control.import.c++
- 3: constant.numeric.preprocessor.c++
- push:
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- pop: true
- - match: ^\s*(#\s*else)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.else.c++
- push:
- - match: (?=^\s*#\s*endif\b)
- pop: true
- - include: negated-block
- - include: statements
- - match: ""
- push:
- - meta_scope: comment.block.preprocessor.if-branch.c++
- - match: (?=^\s*#\s*(else|endif)\b)
- pop: true
- - include: scope:source.c#preprocessor-disabled
- preprocessor-rule-enabled-statements:
- - match: ^\s*((#if)\s+(0*1))\b
- captures:
- 1: meta.preprocessor.c++
- 2: keyword.control.import.c++
- 3: constant.numeric.preprocessor.c++
- push:
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- pop: true
- - match: ^\s*(#\s*else)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.else.c++
- push:
- - meta_content_scope: comment.block.preprocessor.else-branch.c++
- - match: (?=^\s*#\s*endif\b)
- pop: true
- - include: scope:source.c#preprocessor-disabled
- - match: ""
- push:
- - match: (?=^\s*#\s*(else|endif)\b)
- pop: true
- - include: negated-block
- - include: statements
- preprocessor-rule-other-statements:
- - match: ^\s*(#\s*(?:if|ifdef|ifndef))\b
- captures:
- 1: keyword.control.import.c++
- push:
- - meta_scope: meta.preprocessor.c++
- - include: scope:source.c#preprocessor-line-continuation
- - include: scope:source.c#preprocessor-comments
- - match: \bdefined\b
- scope: keyword.control.c++
- # Enter a new scope where all elif/else branches have their
- # contexts popped by a subsequent elif/else/endif. This ensures that
- # preprocessor branches don't push multiple meta.block scopes on
- # the stack, thus messing up the "global" context's detection of
- # functions.
- - match: $\n
- set: preprocessor-if-branch-statements
- # These gymnastics here ensure that we are properly handling scope even
- # when the preprocessor is used to create different scope beginnings, such
- # as a different if/while condition
- preprocessor-if-branch-statements:
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- pop: true
- - match: (?=^\s*#\s*(elif|else)\b)
- push: preprocessor-elif-else-branch-statements
- - match: \{
- scope: punctuation.section.block.begin.c++
- set: preprocessor-block-if-branch-statements
- - match: (?=(?!{{non_func_keywords}}){{path_lookahead}}\s*\()
- set: preprocessor-if-branch-function-call
- - include: negated-block
- - include: statements
- preprocessor-if-branch-function-call:
- - meta_content_scope: meta.function-call.c++
- - include: scope:source.c#c99
- - match: '(?:(::)\s*)?{{identifier}}\s*(::)\s*'
- scope: variable.function.c++
- captures:
- 1: punctuation.accessor.c++
- 2: punctuation.accessor.c++
- - match: '(?:(::)\s*)?{{identifier}}'
- scope: variable.function.c++
- captures:
- 1: punctuation.accessor.c++
- - match: '\('
- scope: meta.group.c++ punctuation.section.group.begin.c++
- set: preprocessor-if-branch-function-call-arguments
- preprocessor-if-branch-function-call-arguments:
- - meta_content_scope: meta.function-call.c++ meta.group.c++
- - match : \)
- scope: meta.function-call.c++ meta.group.c++ punctuation.section.group.end.c++
- set: preprocessor-if-branch-statements
- - match: ^\s*(#\s*(?:elif|else))\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- set: preprocessor-if-branch-statements
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- set: preprocessor-if-branch-function-call-arguments-finish
- - include: expressions
- preprocessor-if-branch-function-call-arguments-finish:
- - meta_content_scope: meta.function-call.c++ meta.group.c++
- - match: \)
- scope: meta.function-call.c++ meta.group.c++ punctuation.section.group.end.c++
- pop: true
- - include: expressions
- preprocessor-block-if-branch-statements:
- - meta_scope: meta.block.c++
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- set: preprocessor-block-finish-statements
- - match: (?=^\s*#\s*(elif|else)\b)
- push: preprocessor-elif-else-branch-statements
- - match: \}
- scope: punctuation.section.block.end.c++
- set: preprocessor-if-branch-statements
- - include: statements
- preprocessor-block-finish-statements:
- - meta_scope: meta.block.c++
- - match: ^\s*(#\s*(?:if|ifdef|ifndef))\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- set: preprocessor-block-finish-if-branch-statements
- - match: \}
- scope: punctuation.section.block.end.c++
- pop: true
- - include: statements
- preprocessor-block-finish-if-branch-statements:
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: keyword.control.import.c++
- pop: true
- - match: \}
- scope: meta.block.c++ punctuation.section.block.end.c++
- set: preprocessor-if-branch-statements
- - include: statements
- preprocessor-elif-else-branch-statements:
- - match: (?=^\s*#\s*endif\b)
- pop: true
- - include: negated-block
- - include: statements
- ## Preprocessor other
- negated-block:
- - match: '\}'
- scope: punctuation.section.block.end.c++
- push:
- - match: '\{'
- scope: punctuation.section.block.begin.c++
- pop: true
- - match: (?=^\s*#\s*(elif|else|endif)\b)
- pop: true
- - include: statements
- preprocessor-macro-define:
- - match: ^\s*(\#\s*define)\b
- captures:
- 1: meta.preprocessor.macro.c++ keyword.control.import.define.c++
- push:
- - meta_content_scope: meta.preprocessor.macro.c++
- - include: scope:source.c#preprocessor-line-continuation
- - include: scope:source.c#preprocessor-line-ending
- - include: scope:source.c#preprocessor-comments
- - match: '({{identifier}})(?=\()'
- scope: entity.name.function.preprocessor.c++
- set:
- - match: '\('
- scope: punctuation.section.group.begin.c++
- set: preprocessor-macro-params
- - match: '{{identifier}}'
- scope: entity.name.constant.preprocessor.c++
- set: preprocessor-macro-definition
- preprocessor-macro-params:
- - meta_scope: meta.preprocessor.macro.parameters.c++ meta.group.c++
- - match: '{{identifier}}'
- scope: variable.parameter.c++
- - match: \)
- scope: punctuation.section.group.end.c++
- set: preprocessor-macro-definition
- - match: ','
- scope: punctuation.separator.c++
- push:
- - match: '{{identifier}}'
- scope: variable.parameter.c++
- pop: true
- - include: scope:source.c#preprocessor-line-continuation
- - include: scope:source.c#preprocessor-comments
- - match: '\.\.\.'
- scope: keyword.operator.variadic.c++
- - match: '(?=\))'
- pop: true
- - match: (/\*).*(\*/)
- scope: comment.block.c++
- captures:
- 1: punctuation.definition.comment.c++
- 2: punctuation.definition.comment.c++
- - match: '\S+'
- scope: invalid.illegal.unexpected-character.c++
- - include: scope:source.c#preprocessor-line-continuation
- - include: scope:source.c#preprocessor-comments
- - match: '\.\.\.'
- scope: keyword.operator.variadic.c++
- - match: (/\*).*(\*/)
- scope: comment.block.c++
- captures:
- 1: punctuation.definition.comment.c++
- 2: punctuation.definition.comment.c++
- - match: $\n
- scope: invalid.illegal.unexpected-end-of-line.c++
- preprocessor-macro-definition:
- - meta_content_scope: meta.preprocessor.macro.c++
- - include: scope:source.c#preprocessor-line-continuation
- - include: scope:source.c#preprocessor-line-ending
- - include: scope:source.c#preprocessor-comments
- # Don't define blocks in define statements
- - match: '\{'
- scope: punctuation.section.block.begin.c++
- - match: '\}'
- scope: punctuation.section.block.end.c++
- - include: expressions
- preprocessor-practical-workarounds:
- - include: preprocessor-convention-ignore-uppercase-ident-lines
- - include: scope:source.c#preprocessor-convention-ignore-uppercase-calls-without-semicolon
- preprocessor-convention-ignore-uppercase-ident-lines:
- - match: ^(\s*{{macro_identifier}})+\s*$
- scope: meta.assumed-macro.c++
- push:
- # It's possible that we are dealing with a function return type on its own line, and the
- # name of the function is on the subsequent line.
- - match: '(?={{path_lookahead}}({{generic_lookahead}}({{path_lookahead}})?)\s*\()'
- set: [function-definition-params, global-function-identifier-generic]
- - match: '(?={{path_lookahead}}\s*\()'
- set: [function-definition-params, global-function-identifier]
- - match: ^
- pop: true
- preprocessor-other:
- - match: ^\s*(#\s*(?:if|ifdef|ifndef|elif|else|line|pragma|undef))\b
- captures:
- 1: keyword.control.import.c++
- push:
- - meta_scope: meta.preprocessor.c++
- - include: scope:source.c#preprocessor-line-continuation
- - include: scope:source.c#preprocessor-line-ending
- - include: scope:source.c#preprocessor-comments
- - match: \bdefined\b
- scope: keyword.control.c++
- - match: ^\s*(#\s*endif)\b
- captures:
- 1: meta.preprocessor.c++ keyword.control.import.c++
- - match: ^\s*(#\s*(?:error|warning))\b
- captures:
- 1: keyword.control.import.error.c++
- push:
- - meta_scope: meta.preprocessor.diagnostic.c++
- - include: scope:source.c#preprocessor-line-continuation
- - include: scope:source.c#preprocessor-line-ending
- - include: scope:source.c#preprocessor-comments
- - include: strings
- - match: '\S+'
- scope: string.unquoted.c++
- - match: ^\s*(#\s*(?:include|include_next|import))\b
- captures:
- 1: keyword.control.import.include.c++
- push:
- - meta_scope: meta.preprocessor.include.c++
- - include: scope:source.c#preprocessor-line-continuation
- - include: scope:source.c#preprocessor-line-ending
- - include: scope:source.c#preprocessor-comments
- - match: '"'
- scope: punctuation.definition.string.begin.c++
- push:
- - meta_scope: string.quoted.double.include.c++
- - match: '"'
- scope: punctuation.definition.string.end.c++
- pop: true
- - match: <
- scope: punctuation.definition.string.begin.c++
- push:
- - meta_scope: string.quoted.other.lt-gt.include.c++
- - match: '>'
- scope: punctuation.definition.string.end.c++
- pop: true
- - include: preprocessor-practical-workarounds
|