vim-jp / vim-cpp

c or cpp syntax files
147 stars 44 forks source link

Highlight C++11+ attribute specifications #57

Open willeccles opened 3 years ago

willeccles commented 3 years ago

I have for the time being implemented this in my own local copy (in ~/.vim/syntax). I am not an expert at vim syntax files, so I have one minor problem which is that if you have [noreturn], the noreturn will be highlighted (and some other weird edge cases), but I'm not able to fix this myself, so I've simply attached attached my diff so far:

diff --git a/usr/local/share/nvim/runtime/syntax/cpp.vim b/home/cactus/.vim/syntax/cpp.vim
index ed38913..92fd735 100644
--- a/usr/local/share/nvim/runtime/syntax/cpp.vim
+++ b/home/cactus/.vim/syntax/cpp.vim
@@ -47,6 +47,8 @@ if !exists("cpp_no_cpp11")
   syn region cppRawString  matchgroup=cppRawStringDelimiter start=+\%(u8\|[uLU]\)\=R"\z([[:alnum:]_{}[\]#<>%:;.?*\+\-/\^&|~!=,"']\{,16}\)(+ end=+)\z1"+ contains=@Spell
   syn match cppCast        "\<\(const\|static\|dynamic\)_pointer_cast\s*<"me=e-1
   syn match cppCast        "\<\(const\|static\|dynamic\)_pointer_cast\s*$"
+  syn region cppAttrSpec   matchgroup=cppAttributeDelimiter start=+\[\[+ end=+\]\]+ contains=TOP
+  syn keyword cppAttribute noreturn carries_dependency contained containedin=cppAttrSpec
 endif

 " C++ 14 extensions
@@ -56,6 +58,7 @@ if !exists("cpp_no_cpp14")
   syn match cppNumber      display "\<[1-9]\('\=\d\+\)*\(u\=l\{0,2}\|ll\=u\)\>" contains=cFloat
   syn match cppNumber      display "\<0x\x\('\=\x\+\)*\(u\=l\{0,2}\|ll\=u\)\>"
   syn case match
+  syn keyword cppAttribute deprecated contained containedin=cppAttrSpec
 endif

 " C++ 20 extensions
@@ -65,12 +68,14 @@ if !exists("cpp_no_cpp20")
   syn keyword cppStructure concept
   syn keyword cppType      char8_t
   syn keyword cppModule        import module export
+  syn keyword cppAttribute likely unlikely no_unique_address contained containedin=cppAttrSpec
 endif

 " C++ 17 extensions
 if !exists("cpp_no_cpp17")
   syn match cppCast        "\<reinterpret_pointer_cast\s*<"me=e-1
   syn match cppCast        "\<reinterpret_pointer_cast\s*$"
+  syn keyword cppAttribute fallthrough nodiscard maybe_unused contained containedin=cppAttrSpec
 endif

 " The minimum and maximum operators in GNU C++
@@ -90,6 +95,8 @@ hi def link cppBoolean        Boolean
 hi def link cppConstant        Constant
 hi def link cppRawStringDelimiter  Delimiter
 hi def link cppRawString       String
+hi def link cppAttributeDelimiter  StorageClass
+hi def link cppAttribute   StorageClass
 hi def link cppNumber      Number
 hi def link cppModule      Include

I have made an effort to not highlight attributes outside of valid contexts (e.g. likely is not highlighted unless it's inside an attribute specifier), but it seems to have some unfortunate side effects. At the moment, this is the resulting highlighting in a few cases: image

willeccles commented 3 years ago

Other thoughts: some of these issues could be avoided by simply doing a brute force highlighting of everything inside the [[]] to make it all the same color, but I didn't like that solution.

dkearns commented 3 years ago

G'day,

Just some quick thoughts...

I'm not really familiar with the C syntax file but if that doesn't get you started I can take a deeper look.

Regards, Doug