[IR] string vs tablegen'd attributes (and boilerplate)

Hi all,
I’ve added a few attributes now to IR, and I’ve noticed that we can either use simple strings or define attributes in llvm/include/llvm/IR/Attributes.td, though doing so seemed to require much more boilerplate as I needed to additionally modify:

  • llvm/include/llvm/AsmParser/LLToken.h
  • llvm/include/llvm/Bitcode/LLVMBitCodes.h
  • llvm/include/llvm/IR/Attributes.td
  • llvm/lib/AsmParser/LLLexer.cpp
  • llvm/lib/Bitcode/Reader/BitcodeReader.cpp
  • llvm/lib/Bitcode/Writer/BitcodeWriter.cpp
  • llvm/lib/Transforms/Utils/CodeExtractor.cpp
  • llvm/test/Bitcode/attributes.ll
  • llvm/include/llvm/IR/Attributes.td

Are there formal (explicit) recommendations documented anywhere on which are preferred and what the tradeoffs are?

String attributes are also (or at least used to be?) called “target-specific attributes”. I believe they are intended primarily as an extension mechanism for arbitrary target attributes that do not need to be pre-declared.

At least for cases where an attribute carries semantics relevant to the middle-end optimizer, I’d expect it to be implemented as an enum attribute. If it’s only relevant to one target, then it should likely be a string attribute.