//==--- AttrDocs.td - Attribute documentation ----------------------------===//
//
//                     The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===---------------------------------------------------------------------===//

// To test that the documentation builds cleanly, you must run clang-tblgen to
// convert the .td file into a .rst file, and then run sphinx to convert the
// .rst file into an HTML file. After completing testing, you should revert the
// generated .rst file so that the modified version does not get checked in to
// version control.
//
// To run clang-tblgen to generate the .rst file:
// clang-tblgen -gen-attr-docs -I <root>/llvm/tools/clang/include
//   <root>/llvm/tools/clang/include/clang/Basic/Attr.td -o
//   <root>/llvm/tools/clang/docs/AttributeReference.rst
//
// To run sphinx to generate the .html files (note that sphinx-build must be
// available on the PATH):
// Windows (from within the clang\docs directory):
//   make.bat html
// Non-Windows (from within the clang\docs directory):
//   make -f Makefile.sphinx html

def GlobalDocumentation {
  code Intro =[{..
  -------------------------------------------------------------------
  NOTE: This file is automatically generated by running clang-tblgen
  -gen-attr-docs. Do not edit this file by hand!!
  -------------------------------------------------------------------

===================
Attributes in Clang
===================
.. contents::
   :local:

.. |br| raw:: html

  <br/>

Introduction
============

This page lists the attributes currently supported by Clang.
}];
}

def SectionDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``section`` attribute allows you to specify a specific section a
global variable or function should be in after translation.
  }];
  let Heading = "section, __declspec(allocate)";
}

def InitSegDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The attribute applied by ``pragma init_seg()`` controls the section into
which global initialization function pointers are emitted.  It is only
available with ``-fms-extensions``.  Typically, this function pointer is
emitted into ``.CRT$XCU`` on Windows.  The user can change the order of
initialization by using a different section name with the same
``.CRT$XC`` prefix and a suffix that sorts lexicographically before or
after the standard ``.CRT$XCU`` sections.  See the init_seg_
documentation on MSDN for more information.

.. _init_seg: http://msdn.microsoft.com/en-us/library/7977wcck(v=vs.110).aspx
  }];
}

def TLSModelDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``tls_model`` attribute allows you to specify which thread-local storage
model to use. It accepts the following strings:

* global-dynamic
* local-dynamic
* initial-exec
* local-exec

TLS models are mutually exclusive.
  }];
}

def DLLExportDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``__declspec(dllexport)`` attribute declares a variable, function, or
Objective-C interface to be exported from the module.  It is available under the
``-fdeclspec`` flag for compatibility with various compilers.  The primary use
is for COFF object files which explicitly specify what interfaces are available
for external use.  See the dllexport_ documentation on MSDN for more
information.

.. _dllexport: https://msdn.microsoft.com/en-us/library/3y1sfaz2.aspx
  }];
}

def DLLImportDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``__declspec(dllimport)`` attribute declares a variable, function, or
Objective-C interface to be imported from an external module.  It is available
under the ``-fdeclspec`` flag for compatibility with various compilers.  The
primary use is for COFF object files which explicitly specify what interfaces
are imported from external modules.  See the dllimport_ documentation on MSDN
for more information.

.. _dllimport: https://msdn.microsoft.com/en-us/library/3y1sfaz2.aspx
  }];
}

def ThreadDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``__declspec(thread)`` attribute declares a variable with thread local
storage.  It is available under the ``-fms-extensions`` flag for MSVC
compatibility.  See the documentation for `__declspec(thread)`_ on MSDN.

.. _`__declspec(thread)`: http://msdn.microsoft.com/en-us/library/9w1sdazb.aspx

In Clang, ``__declspec(thread)`` is generally equivalent in functionality to the
GNU ``__thread`` keyword.  The variable must not have a destructor and must have
a constant initializer, if any.  The attribute only applies to variables
declared with static storage duration, such as globals, class static data
members, and static locals.
  }];
}

def NoEscapeDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
``noescape`` placed on a function parameter of a pointer type is used to inform
the compiler that the pointer cannot escape: that is, no reference to the object
the pointer points to that is derived from the parameter value will survive
after the function returns. Users are responsible for making sure parameters
annotated with ``noescape`` do not actuallly escape.

For example:

.. code-block:: c

  int *gp;

  void nonescapingFunc(__attribute__((noescape)) int *p) {
    *p += 100; // OK.
  }

  void escapingFunc(__attribute__((noescape)) int *p) {
    gp = p; // Not OK.
  }

Additionally, when the parameter is a `block pointer
<https://clang.llvm.org/docs/BlockLanguageSpec.html>`, the same restriction
applies to copies of the block. For example:

.. code-block:: c

  typedef void (^BlockTy)();
  BlockTy g0, g1;

  void nonescapingFunc(__attribute__((noescape)) BlockTy block) {
    block(); // OK.
  }

  void escapingFunc(__attribute__((noescape)) BlockTy block) {
    g0 = block; // Not OK.
    g1 = Block_copy(block); // Not OK either.
  }

  }];
}

def CarriesDependencyDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``carries_dependency`` attribute specifies dependency propagation into and
out of functions.

When specified on a function or Objective-C method, the ``carries_dependency``
attribute means that the return value carries a dependency out of the function,
so that the implementation need not constrain ordering upon return from that
function. Implementations of the function and its caller may choose to preserve
dependencies instead of emitting memory ordering instructions such as fences.

Note, this attribute does not change the meaning of the program, but may result
in generation of more efficient code.
  }];
}

def CPUSpecificCPUDispatchDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``cpu_specific`` and ``cpu_dispatch`` attributes are used to define and
resolve multiversioned functions. This form of multiversioning provides a
mechanism for declaring versions across translation units and manually
specifying the resolved function list. A specified CPU defines a set of minimum
features that are required for the function to be called. The result of this is
that future processors execute the most restrictive version of the function the
new processor can execute.

Function versions are defined with ``cpu_specific``, which takes one or more CPU
names as a parameter. For example:

.. code-block:: c

  // Declares and defines the ivybridge version of single_cpu.
  __attribute__((cpu_specific(ivybridge)))
  void single_cpu(void){}

  // Declares and defines the atom version of single_cpu.
  __attribute__((cpu_specific(atom)))
  void single_cpu(void){}

  // Declares and defines both the ivybridge and atom version of multi_cpu.
  __attribute__((cpu_specific(ivybridge, atom)))
  void multi_cpu(void){}

A dispatching (or resolving) function can be declared anywhere in a project's
source code with ``cpu_dispatch``. This attribute takes one or more CPU names
as a parameter (like ``cpu_specific``). Functions marked with ``cpu_dispatch``
are not expected to be defined, only declared. If such a marked function has a
definition, any side effects of the function are ignored; trivial function
bodies are permissible for ICC compatibility.

.. code-block:: c

  // Creates a resolver for single_cpu above.
  __attribute__((cpu_dispatch(ivybridge, atom)))
  void single_cpu(void){}

  // Creates a resolver for multi_cpu, but adds a 3rd version defined in another
  // translation unit.
  __attribute__((cpu_dispatch(ivybridge, atom, sandybridge)))
  void multi_cpu(void){}

Note that it is possible to have a resolving function that dispatches based on
more or fewer options than are present in the program. Specifying fewer will
result in the omitted options not being considered during resolution. Specifying
a version for resolution that isn't defined in the program will result in a
linking failure.

It is also possible to specify a CPU name of ``generic`` which will be resolved
if the executing processor doesn't satisfy the features required in the CPU
name. The behavior of a program executing on a processor that doesn't satisfy
any option of a multiversioned function is undefined.
  }];
}

def C11NoReturnDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
A function declared as ``_Noreturn`` shall not return to its caller. The
compiler will generate a diagnostic for a function declared as ``_Noreturn``
that appears to be capable of returning to its caller.
  }];
}

def CXX11NoReturnDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
A function declared as ``[[noreturn]]`` shall not return to its caller. The
compiler will generate a diagnostic for a function declared as ``[[noreturn]]``
that appears to be capable of returning to its caller.
  }];
}

def AssertCapabilityDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "assert_capability, assert_shared_capability";
  let Content = [{
Marks a function that dynamically tests whether a capability is held, and halts
the program if it is not held.
  }];
}

def AcquireCapabilityDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "acquire_capability, acquire_shared_capability";
  let Content = [{
Marks a function as acquiring a capability.
  }];
}

def TryAcquireCapabilityDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "try_acquire_capability, try_acquire_shared_capability";
  let Content = [{
Marks a function that attempts to acquire a capability. This function may fail to
actually acquire the capability; they accept a Boolean value determining
whether acquiring the capability means success (true), or failing to acquire
the capability means success (false).
  }];
}

def ReleaseCapabilityDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "release_capability, release_shared_capability";
  let Content = [{
Marks a function as releasing a capability.
  }];
}

def AssumeAlignedDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Use ``__attribute__((assume_aligned(<alignment>[,<offset>]))`` on a function
declaration to specify that the return value of the function (which must be a
pointer type) has the specified offset, in bytes, from an address with the
specified alignment. The offset is taken to be zero if omitted.

.. code-block:: c++

  // The returned pointer value has 32-byte alignment.
  void *a() __attribute__((assume_aligned (32)));

  // The returned pointer value is 4 bytes greater than an address having
  // 32-byte alignment.
  void *b() __attribute__((assume_aligned (32, 4)));

Note that this attribute provides information to the compiler regarding a
condition that the code already ensures is true. It does not cause the compiler
to enforce the provided alignment assumption.
  }];
}

def AllocSizeDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``alloc_size`` attribute can be placed on functions that return pointers in
order to hint to the compiler how many bytes of memory will be available at the
returned pointer. ``alloc_size`` takes one or two arguments.

- ``alloc_size(N)`` implies that argument number N equals the number of
  available bytes at the returned pointer.
- ``alloc_size(N, M)`` implies that the product of argument number N and
  argument number M equals the number of available bytes at the returned
  pointer.

Argument numbers are 1-based.

An example of how to use ``alloc_size``

.. code-block:: c

  void *my_malloc(int a) __attribute__((alloc_size(1)));
  void *my_calloc(int a, int b) __attribute__((alloc_size(1, 2)));

  int main() {
    void *const p = my_malloc(100);
    assert(__builtin_object_size(p, 0) == 100);
    void *const a = my_calloc(20, 5);
    assert(__builtin_object_size(a, 0) == 100);
  }

.. Note:: This attribute works differently in clang than it does in GCC.
  Specifically, clang will only trace ``const`` pointers (as above); we give up
  on pointers that are not marked as ``const``. In the vast majority of cases,
  this is unimportant, because LLVM has support for the ``alloc_size``
  attribute. However, this may cause mildly unintuitive behavior when used with
  other attributes, such as ``enable_if``.
  }];
}

def CodeSegDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``__declspec(code_seg)`` attribute enables the placement of code into separate
named segments that can be paged or locked in memory individually. This attribute
is used to control the placement of instantiated templates and compiler-generated
code. See the documentation for `__declspec(code_seg)`_ on MSDN.

.. _`__declspec(code_seg)`: http://msdn.microsoft.com/en-us/library/dn636922.aspx
  }];
}

def AllocAlignDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Use ``__attribute__((alloc_align(<alignment>))`` on a function
declaration to specify that the return value of the function (which must be a
pointer type) is at least as aligned as the value of the indicated parameter. The
parameter is given by its index in the list of formal parameters; the first
parameter has index 1 unless the function is a C++ non-static member function,
in which case the first parameter has index 2 to account for the implicit ``this``
parameter.

.. code-block:: c++

  // The returned pointer has the alignment specified by the first parameter.
  void *a(size_t align) __attribute__((alloc_align(1)));

  // The returned pointer has the alignment specified by the second parameter.
  void *b(void *v, size_t align) __attribute__((alloc_align(2)));

  // The returned pointer has the alignment specified by the second visible
  // parameter, however it must be adjusted for the implicit 'this' parameter.
  void *Foo::b(void *v, size_t align) __attribute__((alloc_align(3)));

Note that this attribute merely informs the compiler that a function always
returns a sufficiently aligned pointer. It does not cause the compiler to
emit code to enforce that alignment.  The behavior is undefined if the returned
poitner is not sufficiently aligned.
  }];
}

def EnableIfDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
.. Note:: Some features of this attribute are experimental. The meaning of
  multiple enable_if attributes on a single declaration is subject to change in
  a future version of clang. Also, the ABI is not standardized and the name
  mangling may change in future versions. To avoid that, use asm labels.

The ``enable_if`` attribute can be placed on function declarations to control
which overload is selected based on the values of the function's arguments.
When combined with the ``overloadable`` attribute, this feature is also
available in C.

.. code-block:: c++

  int isdigit(int c);
  int isdigit(int c) __attribute__((enable_if(c <= -1 || c > 255, "chosen when 'c' is out of range"))) __attribute__((unavailable("'c' must have the value of an unsigned char or EOF")));

  void foo(char c) {
    isdigit(c);
    isdigit(10);
    isdigit(-10);  // results in a compile-time error.
  }

The enable_if attribute takes two arguments, the first is an expression written
in terms of the function parameters, the second is a string explaining why this
overload candidate could not be selected to be displayed in diagnostics. The
expression is part of the function signature for the purposes of determining
whether it is a redeclaration (following the rules used when determining
whether a C++ template specialization is ODR-equivalent), but is not part of
the type.

The enable_if expression is evaluated as if it were the body of a
bool-returning constexpr function declared with the arguments of the function
it is being applied to, then called with the parameters at the call site. If the
result is false or could not be determined through constant expression
evaluation, then this overload will not be chosen and the provided string may
be used in a diagnostic if the compile fails as a result.

Because the enable_if expression is an unevaluated context, there are no global
state changes, nor the ability to pass information from the enable_if
expression to the function body. For example, suppose we want calls to
strnlen(strbuf, maxlen) to resolve to strnlen_chk(strbuf, maxlen, size of
strbuf) only if the size of strbuf can be determined:

.. code-block:: c++

  __attribute__((always_inline))
  static inline size_t strnlen(const char *s, size_t maxlen)
    __attribute__((overloadable))
    __attribute__((enable_if(__builtin_object_size(s, 0) != -1))),
                             "chosen when the buffer size is known but 'maxlen' is not")))
  {
    return strnlen_chk(s, maxlen, __builtin_object_size(s, 0));
  }

Multiple enable_if attributes may be applied to a single declaration. In this
case, the enable_if expressions are evaluated from left to right in the
following manner. First, the candidates whose enable_if expressions evaluate to
false or cannot be evaluated are discarded. If the remaining candidates do not
share ODR-equivalent enable_if expressions, the overload resolution is
ambiguous. Otherwise, enable_if overload resolution continues with the next
enable_if attribute on the candidates that have not been discarded and have
remaining enable_if attributes. In this way, we pick the most specific
overload out of a number of viable overloads using enable_if.

.. code-block:: c++

  void f() __attribute__((enable_if(true, "")));  // #1
  void f() __attribute__((enable_if(true, ""))) __attribute__((enable_if(true, "")));  // #2

  void g(int i, int j) __attribute__((enable_if(i, "")));  // #1
  void g(int i, int j) __attribute__((enable_if(j, ""))) __attribute__((enable_if(true)));  // #2

In this example, a call to f() is always resolved to #2, as the first enable_if
expression is ODR-equivalent for both declarations, but #1 does not have another
enable_if expression to continue evaluating, so the next round of evaluation has
only a single candidate. In a call to g(1, 1), the call is ambiguous even though
#2 has more enable_if attributes, because the first enable_if expressions are
not ODR-equivalent.

Query for this feature with ``__has_attribute(enable_if)``.

Note that functions with one or more ``enable_if`` attributes may not have
their address taken, unless all of the conditions specified by said
``enable_if`` are constants that evaluate to ``true``. For example:

.. code-block:: c

  const int TrueConstant = 1;
  const int FalseConstant = 0;
  int f(int a) __attribute__((enable_if(a > 0, "")));
  int g(int a) __attribute__((enable_if(a == 0 || a != 0, "")));
  int h(int a) __attribute__((enable_if(1, "")));
  int i(int a) __attribute__((enable_if(TrueConstant, "")));
  int j(int a) __attribute__((enable_if(FalseConstant, "")));

  void fn() {
    int (*ptr)(int);
    ptr = &f; // error: 'a > 0' is not always true
    ptr = &g; // error: 'a == 0 || a != 0' is not a truthy constant
    ptr = &h; // OK: 1 is a truthy constant
    ptr = &i; // OK: 'TrueConstant' is a truthy constant
    ptr = &j; // error: 'FalseConstant' is a constant, but not truthy
  }

Because ``enable_if`` evaluation happens during overload resolution,
``enable_if`` may give unintuitive results when used with templates, depending
on when overloads are resolved. In the example below, clang will emit a
diagnostic about no viable overloads for ``foo`` in ``bar``, but not in ``baz``:

.. code-block:: c++

  double foo(int i) __attribute__((enable_if(i > 0, "")));
  void *foo(int i) __attribute__((enable_if(i <= 0, "")));
  template <int I>
  auto bar() { return foo(I); }

  template <typename T>
  auto baz() { return foo(T::number); }

  struct WithNumber { constexpr static int number = 1; };
  void callThem() {
    bar<sizeof(WithNumber)>();
    baz<WithNumber>();
  }

This is because, in ``bar``, ``foo`` is resolved prior to template
instantiation, so the value for ``I`` isn't known (thus, both ``enable_if``
conditions for ``foo`` fail). However, in ``baz``, ``foo`` is resolved during
template instantiation, so the value for ``T::number`` is known.
  }];
}

def DiagnoseIfDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``diagnose_if`` attribute can be placed on function declarations to emit
warnings or errors at compile-time if calls to the attributed function meet
certain user-defined criteria. For example:

.. code-block:: c

  int abs(int a)
    __attribute__((diagnose_if(a >= 0, "Redundant abs call", "warning")));
  int must_abs(int a)
    __attribute__((diagnose_if(a >= 0, "Redundant abs call", "error")));

  int val = abs(1); // warning: Redundant abs call
  int val2 = must_abs(1); // error: Redundant abs call
  int val3 = abs(val);
  int val4 = must_abs(val); // Because run-time checks are not emitted for
                            // diagnose_if attributes, this executes without
                            // issue.


``diagnose_if`` is closely related to ``enable_if``, with a few key differences:

* Overload resolution is not aware of ``diagnose_if`` attributes: they're
  considered only after we select the best candidate from a given candidate set.
* Function declarations that differ only in their ``diagnose_if`` attributes are
  considered to be redeclarations of the same function (not overloads).
* If the condition provided to ``diagnose_if`` cannot be evaluated, no
  diagnostic will be emitted.

Otherwise, ``diagnose_if`` is essentially the logical negation of ``enable_if``.

As a result of bullet number two, ``diagnose_if`` attributes will stack on the
same function. For example:

.. code-block:: c

  int foo() __attribute__((diagnose_if(1, "diag1", "warning")));
  int foo() __attribute__((diagnose_if(1, "diag2", "warning")));

  int bar = foo(); // warning: diag1
                   // warning: diag2
  int (*fooptr)(void) = foo; // warning: diag1
                             // warning: diag2

  constexpr int supportsAPILevel(int N) { return N < 5; }
  int baz(int a)
    __attribute__((diagnose_if(!supportsAPILevel(10),
                               "Upgrade to API level 10 to use baz", "error")));
  int baz(int a)
    __attribute__((diagnose_if(!a, "0 is not recommended.", "warning")));

  int (*bazptr)(int) = baz; // error: Upgrade to API level 10 to use baz
  int v = baz(0); // error: Upgrade to API level 10 to use baz

Query for this feature with ``__has_attribute(diagnose_if)``.
  }];
}

def PassObjectSizeDocs : Documentation {
  let Category = DocCatVariable; // Technically it's a parameter doc, but eh.
  let Content = [{
.. Note:: The mangling of functions with parameters that are annotated with
  ``pass_object_size`` is subject to change. You can get around this by
  using ``__asm__("foo")`` to explicitly name your functions, thus preserving
  your ABI; also, non-overloadable C functions with ``pass_object_size`` are
  not mangled.

The ``pass_object_size(Type)`` attribute can be placed on function parameters to
instruct clang to call ``__builtin_object_size(param, Type)`` at each callsite
of said function, and implicitly pass the result of this call in as an invisible
argument of type ``size_t`` directly after the parameter annotated with
``pass_object_size``. Clang will also replace any calls to
``__builtin_object_size(param, Type)`` in the function by said implicit
parameter.

Example usage:

.. code-block:: c

  int bzero1(char *const p __attribute__((pass_object_size(0))))
      __attribute__((noinline)) {
    int i = 0;
    for (/**/; i < (int)__builtin_object_size(p, 0); ++i) {
      p[i] = 0;
    }
    return i;
  }

  int main() {
    char chars[100];
    int n = bzero1(&chars[0]);
    assert(n == sizeof(chars));
    return 0;
  }

If successfully evaluating ``__builtin_object_size(param, Type)`` at the
callsite is not possible, then the "failed" value is passed in. So, using the
definition of ``bzero1`` from above, the following code would exit cleanly:

.. code-block:: c

  int main2(int argc, char *argv[]) {
    int n = bzero1(argv);
    assert(n == -1);
    return 0;
  }

``pass_object_size`` plays a part in overload resolution. If two overload
candidates are otherwise equally good, then the overload with one or more
parameters with ``pass_object_size`` is preferred. This implies that the choice
between two identical overloads both with ``pass_object_size`` on one or more
parameters will always be ambiguous; for this reason, having two such overloads
is illegal. For example:

.. code-block:: c++

  #define PS(N) __attribute__((pass_object_size(N)))
  // OK
  void Foo(char *a, char *b); // Overload A
  // OK -- overload A has no parameters with pass_object_size.
  void Foo(char *a PS(0), char *b PS(0)); // Overload B
  // Error -- Same signature (sans pass_object_size) as overload B, and both
  // overloads have one or more parameters with the pass_object_size attribute.
  void Foo(void *a PS(0), void *b);

  // OK
  void Bar(void *a PS(0)); // Overload C
  // OK
  void Bar(char *c PS(1)); // Overload D

  void main() {
    char known[10], *unknown;
    Foo(unknown, unknown); // Calls overload B
    Foo(known, unknown); // Calls overload B
    Foo(unknown, known); // Calls overload B
    Foo(known, known); // Calls overload B

    Bar(known); // Calls overload D
    Bar(unknown); // Calls overload D
  }

Currently, ``pass_object_size`` is a bit restricted in terms of its usage:

* Only one use of ``pass_object_size`` is allowed per parameter.

* It is an error to take the address of a function with ``pass_object_size`` on
  any of its parameters. If you wish to do this, you can create an overload
  without ``pass_object_size`` on any parameters.

* It is an error to apply the ``pass_object_size`` attribute to parameters that
  are not pointers. Additionally, any parameter that ``pass_object_size`` is
  applied to must be marked ``const`` at its function's definition.
  }];
}

def OverloadableDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Clang provides support for C++ function overloading in C.  Function overloading
in C is introduced using the ``overloadable`` attribute.  For example, one
might provide several overloaded versions of a ``tgsin`` function that invokes
the appropriate standard function computing the sine of a value with ``float``,
``double``, or ``long double`` precision:

.. code-block:: c

  #include <math.h>
  float __attribute__((overloadable)) tgsin(float x) { return sinf(x); }
  double __attribute__((overloadable)) tgsin(double x) { return sin(x); }
  long double __attribute__((overloadable)) tgsin(long double x) { return sinl(x); }

Given these declarations, one can call ``tgsin`` with a ``float`` value to
receive a ``float`` result, with a ``double`` to receive a ``double`` result,
etc.  Function overloading in C follows the rules of C++ function overloading
to pick the best overload given the call arguments, with a few C-specific
semantics:

* Conversion from ``float`` or ``double`` to ``long double`` is ranked as a
  floating-point promotion (per C99) rather than as a floating-point conversion
  (as in C++).

* A conversion from a pointer of type ``T*`` to a pointer of type ``U*`` is
  considered a pointer conversion (with conversion rank) if ``T`` and ``U`` are
  compatible types.

* A conversion from type ``T`` to a value of type ``U`` is permitted if ``T``
  and ``U`` are compatible types.  This conversion is given "conversion" rank.

* If no viable candidates are otherwise available, we allow a conversion from a
  pointer of type ``T*`` to a pointer of type ``U*``, where ``T`` and ``U`` are
  incompatible. This conversion is ranked below all other types of conversions.
  Please note: ``U`` lacking qualifiers that are present on ``T`` is sufficient
  for ``T`` and ``U`` to be incompatible.

The declaration of ``overloadable`` functions is restricted to function
declarations and definitions.  If a function is marked with the ``overloadable``
attribute, then all declarations and definitions of functions with that name,
except for at most one (see the note below about unmarked overloads), must have
the ``overloadable`` attribute.  In addition, redeclarations of a function with
the ``overloadable`` attribute must have the ``overloadable`` attribute, and
redeclarations of a function without the ``overloadable`` attribute must *not*
have the ``overloadable`` attribute. e.g.,

.. code-block:: c

  int f(int) __attribute__((overloadable));
  float f(float); // error: declaration of "f" must have the "overloadable" attribute
  int f(int); // error: redeclaration of "f" must have the "overloadable" attribute

  int g(int) __attribute__((overloadable));
  int g(int) { } // error: redeclaration of "g" must also have the "overloadable" attribute

  int h(int);
  int h(int) __attribute__((overloadable)); // error: declaration of "h" must not
                                            // have the "overloadable" attribute

Functions marked ``overloadable`` must have prototypes.  Therefore, the
following code is ill-formed:

.. code-block:: c

  int h() __attribute__((overloadable)); // error: h does not have a prototype

However, ``overloadable`` functions are allowed to use a ellipsis even if there
are no named parameters (as is permitted in C++).  This feature is particularly
useful when combined with the ``unavailable`` attribute:

.. code-block:: c++

  void honeypot(...) __attribute__((overloadable, unavailable)); // calling me is an error

Functions declared with the ``overloadable`` attribute have their names mangled
according to the same rules as C++ function names.  For example, the three
``tgsin`` functions in our motivating example get the mangled names
``_Z5tgsinf``, ``_Z5tgsind``, and ``_Z5tgsine``, respectively.  There are two
caveats to this use of name mangling:

* Future versions of Clang may change the name mangling of functions overloaded
  in C, so you should not depend on an specific mangling.  To be completely
  safe, we strongly urge the use of ``static inline`` with ``overloadable``
  functions.

* The ``overloadable`` attribute has almost no meaning when used in C++,
  because names will already be mangled and functions are already overloadable.
  However, when an ``overloadable`` function occurs within an ``extern "C"``
  linkage specification, it's name *will* be mangled in the same way as it
  would in C.

For the purpose of backwards compatibility, at most one function with the same
name as other ``overloadable`` functions may omit the ``overloadable``
attribute. In this case, the function without the ``overloadable`` attribute
will not have its name mangled.

For example:

.. code-block:: c

  // Notes with mangled names assume Itanium mangling.
  int f(int);
  int f(double) __attribute__((overloadable));
  void foo() {
    f(5); // Emits a call to f (not _Z1fi, as it would with an overload that
          // was marked with overloadable).
    f(1.0); // Emits a call to _Z1fd.
  }

Support for unmarked overloads is not present in some versions of clang. You may
query for it using ``__has_extension(overloadable_unmarked)``.

Query for this attribute with ``__has_attribute(overloadable)``.
  }];
}

def ObjCMethodFamilyDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Many methods in Objective-C have conventional meanings determined by their
selectors. It is sometimes useful to be able to mark a method as having a
particular conventional meaning despite not having the right selector, or as
not having the conventional meaning that its selector would suggest. For these
use cases, we provide an attribute to specifically describe the "method family"
that a method belongs to.

**Usage**: ``__attribute__((objc_method_family(X)))``, where ``X`` is one of
``none``, ``alloc``, ``copy``, ``init``, ``mutableCopy``, or ``new``.  This
attribute can only be placed at the end of a method declaration:

.. code-block:: objc

  - (NSString *)initMyStringValue __attribute__((objc_method_family(none)));

Users who do not wish to change the conventional meaning of a method, and who
merely want to document its non-standard retain and release semantics, should
use the retaining behavior attributes (``ns_returns_retained``,
``ns_returns_not_retained``, etc).

Query for this feature with ``__has_attribute(objc_method_family)``.
  }];
}

def RetainBehaviorDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The behavior of a function with respect to reference counting for Foundation
(Objective-C), CoreFoundation (C) and OSObject (C++) is determined by a naming
convention (e.g. functions starting with "get" are assumed to return at
``+0``).

It can be overriden using a family of the following attributes.  In
Objective-C, the annotation ``__attribute__((ns_returns_retained))`` applied to
a function communicates that the object is returned at ``+1``, and the caller
is responsible for freeing it.
Similiarly, the annotation ``__attribute__((ns_returns_not_retained))``
specifies that the object is returned at ``+0`` and the ownership remains with
the callee.
The annotation ``__attribute__((ns_consumes_self))`` specifies that
the Objective-C method call consumes the reference to ``self``, e.g. by
attaching it to a supplied parameter.
Additionally, parameters can have an annotation
``__attribute__((ns_consumed))``, which specifies that passing an owned object
as that parameter effectively transfers the ownership, and the caller is no
longer responsible for it.
These attributes affect code generation when interacting with ARC code, and
they are used by the Clang Static Analyzer.

In C programs using CoreFoundation, a similar set of attributes:
``__attribute__((cf_returns_not_retained))``,
``__attribute__((cf_returns_retained))`` and ``__attribute__((cf_consumed))``
have the same respective semantics when applied to CoreFoundation objects.
These attributes affect code generation when interacting with ARC code, and
they are used by the Clang Static Analyzer.

Finally, in C++ interacting with XNU kernel (objects inheriting from OSObject),
the same attribute family is present:
``__attribute__((os_returns_not_retained))``,
``__attribute__((os_returns_retained))`` and ``__attribute__((os_consumed))``,
with the same respective semantics.
Similar to ``__attribute__((ns_consumes_self))``,
``__attribute__((os_consumes_this))`` specifies that the method call consumes
the reference to "this" (e.g., when attaching it to a different object supplied
as a parameter).
Out parameters (parameters the function is meant to write into,
either via pointers-to-pointers or references-to-pointers)
may be annotated with ``__attribute__((os_returns_retained))``
or ``__attribute__((os_returns_not_retained))`` which specifies that the object
written into the out parameter should (or respectively should not) be released
after use.
Since often out parameters may or may not be written depending on the exit
code of the function,
annotations ``__attribute__((os_returns_retained_on_zero))``
and ``__attribute__((os_returns_retained_on_non_zero))`` specify that
an out parameter at ``+1`` is written if and only if the function returns a zero
(respectively non-zero) error code.
Observe that return-code-dependent out parameter annotations are only
available for retained out parameters, as non-retained object do not have to be
released by the callee.
These attributes are only used by the Clang Static Analyzer.

The family of attributes ``X_returns_X_retained`` can be added to functions,
C++ methods, and Objective-C methods and properties.
Attributes ``X_consumed`` can be added to parameters of methods, functions,
and Objective-C methods.
  }];
}



def NoDebugDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``nodebug`` attribute allows you to suppress debugging information for a
function or method, or for a variable that is not a parameter or a non-static
data member.
  }];
}

def NoDuplicateDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``noduplicate`` attribute can be placed on function declarations to control
whether function calls to this function can be duplicated or not as a result of
optimizations. This is required for the implementation of functions with
certain special requirements, like the OpenCL "barrier" function, that might
need to be run concurrently by all the threads that are executing in lockstep
on the hardware. For example this attribute applied on the function
"nodupfunc" in the code below avoids that:

.. code-block:: c

  void nodupfunc() __attribute__((noduplicate));
  // Setting it as a C++11 attribute is also valid
  // void nodupfunc() [[clang::noduplicate]];
  void foo();
  void bar();

  nodupfunc();
  if (a > n) {
    foo();
  } else {
    bar();
  }

gets possibly modified by some optimizations into code similar to this:

.. code-block:: c

  if (a > n) {
    nodupfunc();
    foo();
  } else {
    nodupfunc();
    bar();
  }

where the call to "nodupfunc" is duplicated and sunk into the two branches
of the condition.
  }];
}

def ConvergentDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``convergent`` attribute can be placed on a function declaration. It is
translated into the LLVM ``convergent`` attribute, which indicates that the call
instructions of a function with this attribute cannot be made control-dependent
on any additional values.

In languages designed for SPMD/SIMT programming model, e.g. OpenCL or CUDA,
the call instructions of a function with this attribute must be executed by
all work items or threads in a work group or sub group.

This attribute is different from ``noduplicate`` because it allows duplicating
function calls if it can be proved that the duplicated function calls are
not made control-dependent on any additional values, e.g., unrolling a loop
executed by all work items.

Sample usage:
.. code-block:: c

  void convfunc(void) __attribute__((convergent));
  // Setting it as a C++11 attribute is also valid in a C++ program.
  // void convfunc(void) [[clang::convergent]];

  }];
}

def NoSplitStackDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``no_split_stack`` attribute disables the emission of the split stack
preamble for a particular function. It has no effect if ``-fsplit-stack``
is not specified.
  }];
}

def ObjCRequiresSuperDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Some Objective-C classes allow a subclass to override a particular method in a
parent class but expect that the overriding method also calls the overridden
method in the parent class. For these cases, we provide an attribute to
designate that a method requires a "call to ``super``" in the overriding
method in the subclass.

**Usage**: ``__attribute__((objc_requires_super))``.  This attribute can only
be placed at the end of a method declaration:

.. code-block:: objc

  - (void)foo __attribute__((objc_requires_super));

This attribute can only be applied the method declarations within a class, and
not a protocol.  Currently this attribute does not enforce any placement of
where the call occurs in the overriding method (such as in the case of
``-dealloc`` where the call must appear at the end).  It checks only that it
exists.

Note that on both OS X and iOS that the Foundation framework provides a
convenience macro ``NS_REQUIRES_SUPER`` that provides syntactic sugar for this
attribute:

.. code-block:: objc

  - (void)foo NS_REQUIRES_SUPER;

This macro is conditionally defined depending on the compiler's support for
this attribute.  If the compiler does not support the attribute the macro
expands to nothing.

Operationally, when a method has this annotation the compiler will warn if the
implementation of an override in a subclass does not call super.  For example:

.. code-block:: objc

   warning: method possibly missing a [super AnnotMeth] call
   - (void) AnnotMeth{};
                      ^
  }];
}

def ObjCRuntimeNameDocs : Documentation {
    let Category = DocCatFunction;
    let Content = [{
By default, the Objective-C interface or protocol identifier is used
in the metadata name for that object. The `objc_runtime_name`
attribute allows annotated interfaces or protocols to use the
specified string argument in the object's metadata name instead of the
default name.

**Usage**: ``__attribute__((objc_runtime_name("MyLocalName")))``.  This attribute
can only be placed before an @protocol or @interface declaration:

.. code-block:: objc

  __attribute__((objc_runtime_name("MyLocalName")))
  @interface Message
  @end

    }];
}

def ObjCRuntimeVisibleDocs : Documentation {
    let Category = DocCatFunction;
    let Content = [{
This attribute specifies that the Objective-C class to which it applies is visible to the Objective-C runtime but not to the linker. Classes annotated with this attribute cannot be subclassed and cannot have categories defined for them.
    }];
}

def ObjCBoxableDocs : Documentation {
    let Category = DocCatFunction;
    let Content = [{
Structs and unions marked with the ``objc_boxable`` attribute can be used
with the Objective-C boxed expression syntax, ``@(...)``.

**Usage**: ``__attribute__((objc_boxable))``. This attribute
can only be placed on a declaration of a trivially-copyable struct or union:

.. code-block:: objc

  struct __attribute__((objc_boxable)) some_struct {
    int i;
  };
  union __attribute__((objc_boxable)) some_union {
    int i;
    float f;
  };
  typedef struct __attribute__((objc_boxable)) _some_struct some_struct;

  // ...

  some_struct ss;
  NSValue *boxed = @(ss);

    }];
}

def AvailabilityDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``availability`` attribute can be placed on declarations to describe the
lifecycle of that declaration relative to operating system versions.  Consider
the function declaration for a hypothetical function ``f``:

.. code-block:: c++

  void f(void) __attribute__((availability(macos,introduced=10.4,deprecated=10.6,obsoleted=10.7)));

The availability attribute states that ``f`` was introduced in macOS 10.4,
deprecated in macOS 10.6, and obsoleted in macOS 10.7.  This information
is used by Clang to determine when it is safe to use ``f``: for example, if
Clang is instructed to compile code for macOS 10.5, a call to ``f()``
succeeds.  If Clang is instructed to compile code for macOS 10.6, the call
succeeds but Clang emits a warning specifying that the function is deprecated.
Finally, if Clang is instructed to compile code for macOS 10.7, the call
fails because ``f()`` is no longer available.

The availability attribute is a comma-separated list starting with the
platform name and then including clauses specifying important milestones in the
declaration's lifetime (in any order) along with additional information.  Those
clauses can be:

introduced=\ *version*
  The first version in which this declaration was introduced.

deprecated=\ *version*
  The first version in which this declaration was deprecated, meaning that
  users should migrate away from this API.

obsoleted=\ *version*
  The first version in which this declaration was obsoleted, meaning that it
  was removed completely and can no longer be used.

unavailable
  This declaration is never available on this platform.

message=\ *string-literal*
  Additional message text that Clang will provide when emitting a warning or
  error about use of a deprecated or obsoleted declaration.  Useful to direct
  users to replacement APIs.

replacement=\ *string-literal*
  Additional message text that Clang will use to provide Fix-It when emitting
  a warning about use of a deprecated declaration. The Fix-It will replace
  the deprecated declaration with the new declaration specified.

Multiple availability attributes can be placed on a declaration, which may
correspond to different platforms.  Only the availability attribute with the
platform corresponding to the target platform will be used; any others will be
ignored.  If no availability attribute specifies availability for the current
target platform, the availability attributes are ignored.  Supported platforms
are:

``ios``
  Apple's iOS operating system.  The minimum deployment target is specified by
  the ``-mios-version-min=*version*`` or ``-miphoneos-version-min=*version*``
  command-line arguments.

``macos``
  Apple's macOS operating system.  The minimum deployment target is
  specified by the ``-mmacosx-version-min=*version*`` command-line argument.
  ``macosx`` is supported for backward-compatibility reasons, but it is
  deprecated.

``tvos``
  Apple's tvOS operating system.  The minimum deployment target is specified by
  the ``-mtvos-version-min=*version*`` command-line argument.

``watchos``
  Apple's watchOS operating system.  The minimum deployment target is specified by
  the ``-mwatchos-version-min=*version*`` command-line argument.

A declaration can typically be used even when deploying back to a platform
version prior to when the declaration was introduced.  When this happens, the
declaration is `weakly linked
<https://developer.apple.com/library/mac/#documentation/MacOSX/Conceptual/BPFrameworks/Concepts/WeakLinking.html>`_,
as if the ``weak_import`` attribute were added to the declaration.  A
weakly-linked declaration may or may not be present a run-time, and a program
can determine whether the declaration is present by checking whether the
address of that declaration is non-NULL.

The flag ``strict`` disallows using API when deploying back to a
platform version prior to when the declaration was introduced.  An
attempt to use such API before its introduction causes a hard error.
Weakly-linking is almost always a better API choice, since it allows
users to query availability at runtime.

If there are multiple declarations of the same entity, the availability
attributes must either match on a per-platform basis or later
declarations must not have availability attributes for that
platform. For example:

.. code-block:: c

  void g(void) __attribute__((availability(macos,introduced=10.4)));
  void g(void) __attribute__((availability(macos,introduced=10.4))); // okay, matches
  void g(void) __attribute__((availability(ios,introduced=4.0))); // okay, adds a new platform
  void g(void); // okay, inherits both macos and ios availability from above.
  void g(void) __attribute__((availability(macos,introduced=10.5))); // error: mismatch

When one method overrides another, the overriding method can be more widely available than the overridden method, e.g.,:

.. code-block:: objc

  @interface A
  - (id)method __attribute__((availability(macos,introduced=10.4)));
  - (id)method2 __attribute__((availability(macos,introduced=10.4)));
  @end

  @interface B : A
  - (id)method __attribute__((availability(macos,introduced=10.3))); // okay: method moved into base class later
  - (id)method __attribute__((availability(macos,introduced=10.5))); // error: this method was available via the base class in 10.4
  @end

Starting with the macOS 10.12 SDK, the ``API_AVAILABLE`` macro from
``<os/availability.h>`` can simplify the spelling:

.. code-block:: objc

  @interface A
  - (id)method API_AVAILABLE(macos(10.11)));
  - (id)otherMethod API_AVAILABLE(macos(10.11), ios(11.0));
  @end

Also see the documentation for `@available
<http://clang.llvm.org/docs/LanguageExtensions.html#objective-c-available>`_
  }];
}

def ExternalSourceSymbolDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``external_source_symbol`` attribute specifies that a declaration originates
from an external source and describes the nature of that source.

The fact that Clang is capable of recognizing declarations that were defined
externally can be used to provide better tooling support for mixed-language
projects or projects that rely on auto-generated code. For instance, an IDE that
uses Clang and that supports mixed-language projects can use this attribute to
provide a correct 'jump-to-definition' feature. For a concrete example,
consider a protocol that's defined in a Swift file:

.. code-block:: swift

  @objc public protocol SwiftProtocol {
    func method()
  }

This protocol can be used from Objective-C code by including a header file that
was generated by the Swift compiler. The declarations in that header can use
the ``external_source_symbol`` attribute to make Clang aware of the fact
that ``SwiftProtocol`` actually originates from a Swift module:

.. code-block:: objc

  __attribute__((external_source_symbol(language="Swift",defined_in="module")))
  @protocol SwiftProtocol
  @required
  - (void) method;
  @end

Consequently, when 'jump-to-definition' is performed at a location that
references ``SwiftProtocol``, the IDE can jump to the original definition in
the Swift source file rather than jumping to the Objective-C declaration in the
auto-generated header file.

The ``external_source_symbol`` attribute is a comma-separated list that includes
clauses that describe the origin and the nature of the particular declaration.
Those clauses can be:

language=\ *string-literal*
  The name of the source language in which this declaration was defined.

defined_in=\ *string-literal*
  The name of the source container in which the declaration was defined. The
  exact definition of source container is language-specific, e.g. Swift's
  source containers are modules, so ``defined_in`` should specify the Swift
  module name.

generated_declaration
  This declaration was automatically generated by some tool.

The clauses can be specified in any order. The clauses that are listed above are
all optional, but the attribute has to have at least one clause.
  }];
}

def RequireConstantInitDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
This attribute specifies that the variable to which it is attached is intended
to have a `constant initializer <http://en.cppreference.com/w/cpp/language/constant_initialization>`_
according to the rules of [basic.start.static]. The variable is required to
have static or thread storage duration. If the initialization of the variable
is not a constant initializer an error will be produced. This attribute may
only be used in C++.

Note that in C++03 strict constant expression checking is not done. Instead
the attribute reports if Clang can emit the variable as a constant, even if it's
not technically a 'constant initializer'. This behavior is non-portable.

Static storage duration variables with constant initializers avoid hard-to-find
bugs caused by the indeterminate order of dynamic initialization. They can also
be safely used during dynamic initialization across translation units.

This attribute acts as a compile time assertion that the requirements
for constant initialization have been met. Since these requirements change
between dialects and have subtle pitfalls it's important to fail fast instead
of silently falling back on dynamic initialization.

.. code-block:: c++

  // -std=c++14
  #define SAFE_STATIC [[clang::require_constant_initialization]]
  struct T {
    constexpr T(int) {}
    ~T(); // non-trivial
  };
  SAFE_STATIC T x = {42}; // Initialization OK. Doesn't check destructor.
  SAFE_STATIC T y = 42; // error: variable does not have a constant initializer
  // copy initialization is not a constant expression on a non-literal type.
  }];
}

def WarnMaybeUnusedDocs : Documentation {
  let Category = DocCatVariable;
  let Heading = "maybe_unused, unused";
  let Content = [{
When passing the ``-Wunused`` flag to Clang, entities that are unused by the
program may be diagnosed. The ``[[maybe_unused]]`` (or
``__attribute__((unused))``) attribute can be used to silence such diagnostics
when the entity cannot be removed. For instance, a local variable may exist
solely for use in an ``assert()`` statement, which makes the local variable
unused when ``NDEBUG`` is defined.

The attribute may be applied to the declaration of a class, a typedef, a
variable, a function or method, a function parameter, an enumeration, an
enumerator, a non-static data member, or a label.

.. code-block: c++
  #include <cassert>

  [[maybe_unused]] void f([[maybe_unused]] bool thing1,
                          [[maybe_unused]] bool thing2) {
    [[maybe_unused]] bool b = thing1 && thing2;
    assert(b);
  }
  }];
}

def WarnUnusedResultsDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "nodiscard, warn_unused_result";
  let Content  = [{
Clang supports the ability to diagnose when the results of a function call
expression are discarded under suspicious circumstances. A diagnostic is
generated when a function or its return type is marked with ``[[nodiscard]]``
(or ``__attribute__((warn_unused_result))``) and the function call appears as a
potentially-evaluated discarded-value expression that is not explicitly cast to
`void`.

.. code-block: c++
  struct [[nodiscard]] error_info { /*...*/ };
  error_info enable_missile_safety_mode();

  void launch_missiles();
  void test_missiles() {
    enable_missile_safety_mode(); // diagnoses
    launch_missiles();
  }
  error_info &foo();
  void f() { foo(); } // Does not diagnose, error_info is a reference.
  }];
}

def FallthroughDocs : Documentation {
  let Category = DocCatStmt;
  let Heading = "fallthrough";
  let Content = [{
The ``fallthrough`` (or ``clang::fallthrough``) attribute is used
to annotate intentional fall-through
between switch labels.  It can only be applied to a null statement placed at a
point of execution between any statement and the next switch label.  It is
common to mark these places with a specific comment, but this attribute is
meant to replace comments with a more strict annotation, which can be checked
by the compiler.  This attribute doesn't change semantics of the code and can
be used wherever an intended fall-through occurs.  It is designed to mimic
control-flow statements like ``break;``, so it can be placed in most places
where ``break;`` can, but only if there are no statements on the execution path
between it and the next switch label.

By default, Clang does not warn on unannotated fallthrough from one ``switch``
case to another. Diagnostics on fallthrough without a corresponding annotation
can be enabled with the ``-Wimplicit-fallthrough`` argument.

Here is an example:

.. code-block:: c++

  // compile with -Wimplicit-fallthrough
  switch (n) {
  case 22:
  case 33:  // no warning: no statements between case labels
    f();
  case 44:  // warning: unannotated fall-through
    g();
    [[clang::fallthrough]];
  case 55:  // no warning
    if (x) {
      h();
      break;
    }
    else {
      i();
      [[clang::fallthrough]];
    }
  case 66:  // no warning
    p();
    [[clang::fallthrough]]; // warning: fallthrough annotation does not
                            //          directly precede case label
    q();
  case 77:  // warning: unannotated fall-through
    r();
  }
  }];
}

def ARMInterruptDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "interrupt (ARM)";
  let Content = [{
Clang supports the GNU style ``__attribute__((interrupt("TYPE")))`` attribute on
ARM targets. This attribute may be attached to a function definition and
instructs the backend to generate appropriate function entry/exit code so that
it can be used directly as an interrupt service routine.

The parameter passed to the interrupt attribute is optional, but if
provided it must be a string literal with one of the following values: "IRQ",
"FIQ", "SWI", "ABORT", "UNDEF".

The semantics are as follows:

- If the function is AAPCS, Clang instructs the backend to realign the stack to
  8 bytes on entry. This is a general requirement of the AAPCS at public
  interfaces, but may not hold when an exception is taken. Doing this allows
  other AAPCS functions to be called.
- If the CPU is M-class this is all that needs to be done since the architecture
  itself is designed in such a way that functions obeying the normal AAPCS ABI
  constraints are valid exception handlers.
- If the CPU is not M-class, the prologue and epilogue are modified to save all
  non-banked registers that are used, so that upon return the user-mode state
  will not be corrupted. Note that to avoid unnecessary overhead, only
  general-purpose (integer) registers are saved in this way. If VFP operations
  are needed, that state must be saved manually.

  Specifically, interrupt kinds other than "FIQ" will save all core registers
  except "lr" and "sp". "FIQ" interrupts will save r0-r7.
- If the CPU is not M-class, the return instruction is changed to one of the
  canonical sequences permitted by the architecture for exception return. Where
  possible the function itself will make the necessary "lr" adjustments so that
  the "preferred return address" is selected.

  Unfortunately the compiler is unable to make this guarantee for an "UNDEF"
  handler, where the offset from "lr" to the preferred return address depends on
  the execution state of the code which generated the exception. In this case
  a sequence equivalent to "movs pc, lr" will be used.
  }];
}

def MipsInterruptDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "interrupt (MIPS)";
  let Content = [{
Clang supports the GNU style ``__attribute__((interrupt("ARGUMENT")))`` attribute on
MIPS targets. This attribute may be attached to a function definition and instructs
the backend to generate appropriate function entry/exit code so that it can be used
directly as an interrupt service routine.

By default, the compiler will produce a function prologue and epilogue suitable for
an interrupt service routine that handles an External Interrupt Controller (eic)
generated interrupt. This behaviour can be explicitly requested with the "eic"
argument.

Otherwise, for use with vectored interrupt mode, the argument passed should be
of the form "vector=LEVEL" where LEVEL is one of the following values:
"sw0", "sw1", "hw0", "hw1", "hw2", "hw3", "hw4", "hw5". The compiler will
then set the interrupt mask to the corresponding level which will mask all
interrupts up to and including the argument.

The semantics are as follows:

- The prologue is modified so that the Exception Program Counter (EPC) and
  Status coprocessor registers are saved to the stack. The interrupt mask is
  set so that the function can only be interrupted by a higher priority
  interrupt. The epilogue will restore the previous values of EPC and Status.

- The prologue and epilogue are modified to save and restore all non-kernel
  registers as necessary.

- The FPU is disabled in the prologue, as the floating pointer registers are not
  spilled to the stack.

- The function return sequence is changed to use an exception return instruction.

- The parameter sets the interrupt mask for the function corresponding to the
  interrupt level specified. If no mask is specified the interrupt mask
  defaults to "eic".
  }];
}

def MicroMipsDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Clang supports the GNU style ``__attribute__((micromips))`` and
``__attribute__((nomicromips))`` attributes on MIPS targets. These attributes
may be attached to a function definition and instructs the backend to generate
or not to generate microMIPS code for that function.

These attributes override the `-mmicromips` and `-mno-micromips` options
on the command line.
  }];
}

def MipsLongCallStyleDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "long_call, far";
  let Content = [{
Clang supports the ``__attribute__((long_call))``, ``__attribute__((far))``,
and ``__attribute__((near))`` attributes on MIPS targets. These attributes may
only be added to function declarations and change the code generated
by the compiler when directly calling the function. The ``near`` attribute
allows calls to the function to be made using the ``jal`` instruction, which
requires the function to be located in the same naturally aligned 256MB
segment as the caller.  The ``long_call`` and ``far`` attributes are synonyms
and require the use of a different call sequence that works regardless
of the distance between the functions.

These attributes have no effect for position-independent code.

These attributes take priority over command line switches such
as ``-mlong-calls`` and ``-mno-long-calls``.
  }];
}

def MipsShortCallStyleDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "short_call, near";
  let Content = [{
Clang supports the ``__attribute__((long_call))``, ``__attribute__((far))``,
``__attribute__((short__call))``, and ``__attribute__((near))`` attributes
on MIPS targets. These attributes may only be added to function declarations
and change the code generated by the compiler when directly calling
the function. The ``short_call`` and ``near`` attributes are synonyms and
allow calls to the function to be made using the ``jal`` instruction, which
requires the function to be located in the same naturally aligned 256MB segment
as the caller.  The ``long_call`` and ``far`` attributes are synonyms and
require the use of a different call sequence that works regardless
of the distance between the functions.

These attributes have no effect for position-independent code.

These attributes take priority over command line switches such
as ``-mlong-calls`` and ``-mno-long-calls``.
  }];
}

def RISCVInterruptDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "interrupt (RISCV)";
  let Content = [{
Clang supports the GNU style ``__attribute__((interrupt))`` attribute on RISCV
targets. This attribute may be attached to a function definition and instructs
the backend to generate appropriate function entry/exit code so that it can be
used directly as an interrupt service routine.

Permissible values for this parameter are ``user``, ``supervisor``,
and ``machine``. If there is no parameter, then it defaults to machine.

Repeated interrupt attribute on the same declaration will cause a warning
to be emitted. In case of repeated declarations, the last one prevails.

Refer to:
https://gcc.gnu.org/onlinedocs/gcc/RISC-V-Function-Attributes.html
https://riscv.org/specifications/privileged-isa/
The RISC-V Instruction Set Manual Volume II: Privileged Architecture
Version 1.10.
  }];
}

def AVRInterruptDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "interrupt (AVR)";
  let Content = [{
Clang supports the GNU style ``__attribute__((interrupt))`` attribute on
AVR targets. This attribute may be attached to a function definition and instructs
the backend to generate appropriate function entry/exit code so that it can be used
directly as an interrupt service routine.

On the AVR, the hardware globally disables interrupts when an interrupt is executed.
The first instruction of an interrupt handler declared with this attribute is a SEI
instruction to re-enable interrupts. See also the signal attribute that
does not insert a SEI instruction.
  }];
}

def AVRSignalDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Clang supports the GNU style ``__attribute__((signal))`` attribute on
AVR targets. This attribute may be attached to a function definition and instructs
the backend to generate appropriate function entry/exit code so that it can be used
directly as an interrupt service routine.

Interrupt handler functions defined with the signal attribute do not re-enable interrupts.
}];
}

def TargetDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Clang supports the GNU style ``__attribute__((target("OPTIONS")))`` attribute.
This attribute may be attached to a function definition and instructs
the backend to use different code generation options than were passed on the
command line.

The current set of options correspond to the existing "subtarget features" for
the target with or without a "-mno-" in front corresponding to the absence
of the feature, as well as ``arch="CPU"`` which will change the default "CPU"
for the function.

Example "subtarget features" from the x86 backend include: "mmx", "sse", "sse4.2",
"avx", "xop" and largely correspond to the machine specific options handled by
the front end.

Additionally, this attribute supports function multiversioning for ELF based
x86/x86-64 targets, which can be used to create multiple implementations of the
same function that will be resolved at runtime based on the priority of their
``target`` attribute strings. A function is considered a multiversioned function
if either two declarations of the function have different ``target`` attribute
strings, or if it has a ``target`` attribute string of ``default``.  For
example:

  .. code-block:: c++

    __attribute__((target("arch=atom")))
    void foo() {} // will be called on 'atom' processors.
    __attribute__((target("default")))
    void foo() {} // will be called on any other processors.

All multiversioned functions must contain a ``default`` (fallback)
implementation, otherwise usages of the function are considered invalid.
Additionally, a function may not become multiversioned after its first use.
}];
}

def MinVectorWidthDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Clang supports the ``__attribute__((min_vector_width(width)))`` attribute. This
attribute may be attached to a function and informs the backend that this
function desires vectors of at least this width to be generated. Target-specific
maximum vector widths still apply. This means even if you ask for something
larger than the target supports, you will only get what the target supports.
This attribute is meant to be a hint to control target heuristics that may
generate narrower vectors than what the target hardware supports.

This is currently used by the X86 target to allow some CPUs that support 512-bit
vectors to be limited to using 256-bit vectors to avoid frequency penalties.
This is currently enabled with the ``-prefer-vector-width=256`` command line
option. The ``min_vector_width`` attribute can be used to prevent the backend
from trying to split vector operations to match the ``prefer-vector-width``. All
X86 vector intrinsics from x86intrin.h already set this attribute. Additionally,
use of any of the X86-specific vector builtins will implicitly set this
attribute on the calling function. The intent is that explicitly writing vector
code using the X86 intrinsics will prevent ``prefer-vector-width`` from
affecting the code.
}];
}

def DocCatAMDGPUAttributes : DocumentationCategory<"AMD GPU Attributes">;

def AMDGPUFlatWorkGroupSizeDocs : Documentation {
  let Category = DocCatAMDGPUAttributes;
  let Content = [{
The flat work-group size is the number of work-items in the work-group size
specified when the kernel is dispatched. It is the product of the sizes of the
x, y, and z dimension of the work-group.

Clang supports the
``__attribute__((amdgpu_flat_work_group_size(<min>, <max>)))`` attribute for the
AMDGPU target. This attribute may be attached to a kernel function definition
and is an optimization hint.

``<min>`` parameter specifies the minimum flat work-group size, and ``<max>``
parameter specifies the maximum flat work-group size (must be greater than
``<min>``) to which all dispatches of the kernel will conform. Passing ``0, 0``
as ``<min>, <max>`` implies the default behavior (``128, 256``).

If specified, the AMDGPU target backend might be able to produce better machine
code for barriers and perform scratch promotion by estimating available group
segment size.

An error will be given if:
  - Specified values violate subtarget specifications;
  - Specified values are not compatible with values provided through other
    attributes.
  }];
}

def AMDGPUWavesPerEUDocs : Documentation {
  let Category = DocCatAMDGPUAttributes;
  let Content = [{
A compute unit (CU) is responsible for executing the wavefronts of a work-group.
It is composed of one or more execution units (EU), which are responsible for
executing the wavefronts. An EU can have enough resources to maintain the state
of more than one executing wavefront. This allows an EU to hide latency by
switching between wavefronts in a similar way to symmetric multithreading on a
CPU. In order to allow the state for multiple wavefronts to fit on an EU, the
resources used by a single wavefront have to be limited. For example, the number
of SGPRs and VGPRs. Limiting such resources can allow greater latency hiding,
but can result in having to spill some register state to memory.

Clang supports the ``__attribute__((amdgpu_waves_per_eu(<min>[, <max>])))``
attribute for the AMDGPU target. This attribute may be attached to a kernel
function definition and is an optimization hint.

``<min>`` parameter specifies the requested minimum number of waves per EU, and
*optional* ``<max>`` parameter specifies the requested maximum number of waves
per EU (must be greater than ``<min>`` if specified). If ``<max>`` is omitted,
then there is no restriction on the maximum number of waves per EU other than
the one dictated by the hardware for which the kernel is compiled. Passing
``0, 0`` as ``<min>, <max>`` implies the default behavior (no limits).

If specified, this attribute allows an advanced developer to tune the number of
wavefronts that are capable of fitting within the resources of an EU. The AMDGPU
target backend can use this information to limit resources, such as number of
SGPRs, number of VGPRs, size of available group and private memory segments, in
such a way that guarantees that at least ``<min>`` wavefronts and at most
``<max>`` wavefronts are able to fit within the resources of an EU. Requesting
more wavefronts can hide memory latency but limits available registers which
can result in spilling. Requesting fewer wavefronts can help reduce cache
thrashing, but can reduce memory latency hiding.

This attribute controls the machine code generated by the AMDGPU target backend
to ensure it is capable of meeting the requested values. However, when the
kernel is executed, there may be other reasons that prevent meeting the request,
for example, there may be wavefronts from other kernels executing on the EU.

An error will be given if:
  - Specified values violate subtarget specifications;
  - Specified values are not compatible with values provided through other
    attributes;
  - The AMDGPU target backend is unable to create machine code that can meet the
    request.
  }];
}

def AMDGPUNumSGPRNumVGPRDocs : Documentation {
  let Category = DocCatAMDGPUAttributes;
  let Content = [{
Clang supports the ``__attribute__((amdgpu_num_sgpr(<num_sgpr>)))`` and
``__attribute__((amdgpu_num_vgpr(<num_vgpr>)))`` attributes for the AMDGPU
target. These attributes may be attached to a kernel function definition and are
an optimization hint.

If these attributes are specified, then the AMDGPU target backend will attempt
to limit the number of SGPRs and/or VGPRs used to the specified value(s). The
number of used SGPRs and/or VGPRs may further be rounded up to satisfy the
allocation requirements or constraints of the subtarget. Passing ``0`` as
``num_sgpr`` and/or ``num_vgpr`` implies the default behavior (no limits).

These attributes can be used to test the AMDGPU target backend. It is
recommended that the ``amdgpu_waves_per_eu`` attribute be used to control
resources such as SGPRs and VGPRs since it is aware of the limits for different
subtargets.

An error will be given if:
  - Specified values violate subtarget specifications;
  - Specified values are not compatible with values provided through other
    attributes;
  - The AMDGPU target backend is unable to create machine code that can meet the
    request.
  }];
}

def DocCatCallingConvs : DocumentationCategory<"Calling Conventions"> {
  let Content = [{
Clang supports several different calling conventions, depending on the target
platform and architecture. The calling convention used for a function determines
how parameters are passed, how results are returned to the caller, and other
low-level details of calling a function.
  }];
}

def PcsDocs : Documentation {
  let Category = DocCatCallingConvs;
  let Content = [{
On ARM targets, this attribute can be used to select calling conventions
similar to ``stdcall`` on x86. Valid parameter values are "aapcs" and
"aapcs-vfp".
  }];
}

def AArch64VectorPcsDocs : Documentation {
  let Category = DocCatCallingConvs;
  let Content = [{
On AArch64 targets, this attribute changes the calling convention of a
function to preserve additional floating-point and Advanced SIMD registers
relative to the default calling convention used for AArch64.

This means it is more efficient to call such functions from code that performs
extensive floating-point and vector calculations, because fewer live SIMD and FP
registers need to be saved. This property makes it well-suited for e.g.
floating-point or vector math library functions, which are typically leaf
functions that require a small number of registers.

However, using this attribute also means that it is more expensive to call
a function that adheres to the default calling convention from within such
a function. Therefore, it is recommended that this attribute is only used
for leaf functions.

For more information, see the documentation for `aarch64_vector_pcs`_ on
the Arm Developer website.

.. _`aarch64_vector_pcs`: https://developer.arm.com/products/software-development-tools/hpc/arm-compiler-for-hpc/vector-function-abi
  }];
}

def RegparmDocs : Documentation {
  let Category = DocCatCallingConvs;
  let Content = [{
On 32-bit x86 targets, the regparm attribute causes the compiler to pass
the first three integer parameters in EAX, EDX, and ECX instead of on the
stack. This attribute has no effect on variadic functions, and all parameters
are passed via the stack as normal.
  }];
}

def SysVABIDocs : Documentation {
  let Category = DocCatCallingConvs;
  let Content = [{
On Windows x86_64 targets, this attribute changes the calling convention of a
function to match the default convention used on Sys V targets such as Linux,
Mac, and BSD. This attribute has no effect on other targets.
  }];
}

def MSABIDocs : Documentation {
  let Category = DocCatCallingConvs;
  let Content = [{
On non-Windows x86_64 targets, this attribute changes the calling convention of
a function to match the default convention used on Windows x86_64. This
attribute has no effect on Windows targets or non-x86_64 targets.
  }];
}

def StdCallDocs : Documentation {
  let Category = DocCatCallingConvs;
  let Content = [{
On 32-bit x86 targets, this attribute changes the calling convention of a
function to clear parameters off of the stack on return. This convention does
not support variadic calls or unprototyped functions in C, and has no effect on
x86_64 targets. This calling convention is used widely by the Windows API and
COM applications.  See the documentation for `__stdcall`_ on MSDN.

.. _`__stdcall`: http://msdn.microsoft.com/en-us/library/zxk0tw93.aspx
  }];
}

def FastCallDocs : Documentation {
  let Category = DocCatCallingConvs;
  let Content = [{
On 32-bit x86 targets, this attribute changes the calling convention of a
function to use ECX and EDX as register parameters and clear parameters off of
the stack on return. This convention does not support variadic calls or
unprototyped functions in C, and has no effect on x86_64 targets. This calling
convention is supported primarily for compatibility with existing code. Users
seeking register parameters should use the ``regparm`` attribute, which does
not require callee-cleanup.  See the documentation for `__fastcall`_ on MSDN.

.. _`__fastcall`: http://msdn.microsoft.com/en-us/library/6xa169sk.aspx
  }];
}

def RegCallDocs : Documentation {
  let Category = DocCatCallingConvs;
  let Content = [{
On x86 targets, this attribute changes the calling convention to
`__regcall`_ convention. This convention aims to pass as many arguments
as possible in registers. It also tries to utilize registers for the
return value whenever it is possible.

.. _`__regcall`: https://software.intel.com/en-us/node/693069
  }];
}

def ThisCallDocs : Documentation {
  let Category = DocCatCallingConvs;
  let Content = [{
On 32-bit x86 targets, this attribute changes the calling convention of a
function to use ECX for the first parameter (typically the implicit ``this``
parameter of C++ methods) and clear parameters off of the stack on return. This
convention does not support variadic calls or unprototyped functions in C, and
has no effect on x86_64 targets. See the documentation for `__thiscall`_ on
MSDN.

.. _`__thiscall`: http://msdn.microsoft.com/en-us/library/ek8tkfbw.aspx
  }];
}

def VectorCallDocs : Documentation {
  let Category = DocCatCallingConvs;
  let Content = [{
On 32-bit x86 *and* x86_64 targets, this attribute changes the calling
convention of a function to pass vector parameters in SSE registers.

On 32-bit x86 targets, this calling convention is similar to ``__fastcall``.
The first two integer parameters are passed in ECX and EDX. Subsequent integer
parameters are passed in memory, and callee clears the stack.  On x86_64
targets, the callee does *not* clear the stack, and integer parameters are
passed in RCX, RDX, R8, and R9 as is done for the default Windows x64 calling
convention.

On both 32-bit x86 and x86_64 targets, vector and floating point arguments are
passed in XMM0-XMM5. Homogeneous vector aggregates of up to four elements are
passed in sequential SSE registers if enough are available. If AVX is enabled,
256 bit vectors are passed in YMM0-YMM5. Any vector or aggregate type that
cannot be passed in registers for any reason is passed by reference, which
allows the caller to align the parameter memory.

See the documentation for `__vectorcall`_ on MSDN for more details.

.. _`__vectorcall`: http://msdn.microsoft.com/en-us/library/dn375768.aspx
  }];
}

def DocCatConsumed : DocumentationCategory<"Consumed Annotation Checking"> {
  let Content = [{
Clang supports additional attributes for checking basic resource management
properties, specifically for unique objects that have a single owning reference.
The following attributes are currently supported, although **the implementation
for these annotations is currently in development and are subject to change.**
  }];
}

def SetTypestateDocs : Documentation {
  let Category = DocCatConsumed;
  let Content = [{
Annotate methods that transition an object into a new state with
``__attribute__((set_typestate(new_state)))``.  The new state must be
unconsumed, consumed, or unknown.
  }];
}

def CallableWhenDocs : Documentation {
  let Category = DocCatConsumed;
  let Content = [{
Use ``__attribute__((callable_when(...)))`` to indicate what states a method
may be called in.  Valid states are unconsumed, consumed, or unknown.  Each
argument to this attribute must be a quoted string.  E.g.:

``__attribute__((callable_when("unconsumed", "unknown")))``
  }];
}

def TestTypestateDocs : Documentation {
  let Category = DocCatConsumed;
  let Content = [{
Use ``__attribute__((test_typestate(tested_state)))`` to indicate that a method
returns true if the object is in the specified state..
  }];
}

def ParamTypestateDocs : Documentation {
  let Category = DocCatConsumed;
  let Content = [{
This attribute specifies expectations about function parameters.  Calls to an
function with annotated parameters will issue a warning if the corresponding
argument isn't in the expected state.  The attribute is also used to set the
initial state of the parameter when analyzing the function's body.
  }];
}

def ReturnTypestateDocs : Documentation {
  let Category = DocCatConsumed;
  let Content = [{
The ``return_typestate`` attribute can be applied to functions or parameters.
When applied to a function the attribute specifies the state of the returned
value.  The function's body is checked to ensure that it always returns a value
in the specified state.  On the caller side, values returned by the annotated
function are initialized to the given state.

When applied to a function parameter it modifies the state of an argument after
a call to the function returns.  The function's body is checked to ensure that
the parameter is in the expected state before returning.
  }];
}

def ConsumableDocs : Documentation {
  let Category = DocCatConsumed;
  let Content = [{
Each ``class`` that uses any of the typestate annotations must first be marked
using the ``consumable`` attribute.  Failure to do so will result in a warning.

This attribute accepts a single parameter that must be one of the following:
``unknown``, ``consumed``, or ``unconsumed``.
  }];
}

def NoSanitizeDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Use the ``no_sanitize`` attribute on a function or a global variable
declaration to specify that a particular instrumentation or set of
instrumentations should not be applied. The attribute takes a list of
string literals, which have the same meaning as values accepted by the
``-fno-sanitize=`` flag. For example,
``__attribute__((no_sanitize("address", "thread")))`` specifies that
AddressSanitizer and ThreadSanitizer should not be applied to the
function or variable.

See :ref:`Controlling Code Generation <controlling-code-generation>` for a
full list of supported sanitizer flags.
  }];
}

def NoSanitizeAddressDocs : Documentation {
  let Category = DocCatFunction;
  // This function has multiple distinct spellings, and so it requires a custom
  // heading to be specified. The most common spelling is sufficient.
  let Heading = "no_sanitize_address, no_address_safety_analysis";
  let Content = [{
.. _langext-address_sanitizer:

Use ``__attribute__((no_sanitize_address))`` on a function or a global
variable declaration to specify that address safety instrumentation
(e.g. AddressSanitizer) should not be applied.
  }];
}

def NoSanitizeThreadDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "no_sanitize_thread";
  let Content = [{
.. _langext-thread_sanitizer:

Use ``__attribute__((no_sanitize_thread))`` on a function declaration to
specify that checks for data races on plain (non-atomic) memory accesses should
not be inserted by ThreadSanitizer. The function is still instrumented by the
tool to avoid false positives and provide meaningful stack traces.
  }];
}

def NoSanitizeMemoryDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "no_sanitize_memory";
  let Content = [{
.. _langext-memory_sanitizer:

Use ``__attribute__((no_sanitize_memory))`` on a function declaration to
specify that checks for uninitialized memory should not be inserted
(e.g. by MemorySanitizer). The function may still be instrumented by the tool
to avoid false positives in other places.
  }];
}

def DocCatTypeSafety : DocumentationCategory<"Type Safety Checking"> {
  let Content = [{
Clang supports additional attributes to enable checking type safety properties
that can't be enforced by the C type system. To see warnings produced by these
checks, ensure that -Wtype-safety is enabled. Use cases include:

* MPI library implementations, where these attributes enable checking that
  the buffer type matches the passed ``MPI_Datatype``;
* for HDF5 library there is a similar use case to MPI;
* checking types of variadic functions' arguments for functions like
  ``fcntl()`` and ``ioctl()``.

You can detect support for these attributes with ``__has_attribute()``.  For
example:

.. code-block:: c++

  #if defined(__has_attribute)
  #  if __has_attribute(argument_with_type_tag) && \
        __has_attribute(pointer_with_type_tag) && \
        __has_attribute(type_tag_for_datatype)
  #    define ATTR_MPI_PWT(buffer_idx, type_idx) __attribute__((pointer_with_type_tag(mpi,buffer_idx,type_idx)))
  /* ... other macros ...  */
  #  endif
  #endif

  #if !defined(ATTR_MPI_PWT)
  # define ATTR_MPI_PWT(buffer_idx, type_idx)
  #endif

  int MPI_Send(void *buf, int count, MPI_Datatype datatype /*, other args omitted */)
      ATTR_MPI_PWT(1,3);
  }];
}

def ArgumentWithTypeTagDocs : Documentation {
  let Category = DocCatTypeSafety;
  let Heading = "argument_with_type_tag";
  let Content = [{
Use ``__attribute__((argument_with_type_tag(arg_kind, arg_idx,
type_tag_idx)))`` on a function declaration to specify that the function
accepts a type tag that determines the type of some other argument.

This attribute is primarily useful for checking arguments of variadic functions
(``pointer_with_type_tag`` can be used in most non-variadic cases).

In the attribute prototype above:
  * ``arg_kind`` is an identifier that should be used when annotating all
    applicable type tags.
  * ``arg_idx`` provides the position of a function argument. The expected type of
    this function argument will be determined by the function argument specified
    by ``type_tag_idx``. In the code example below, "3" means that the type of the
    function's third argument will be determined by ``type_tag_idx``.
  * ``type_tag_idx`` provides the position of a function argument. This function
    argument will be a type tag. The type tag will determine the expected type of
    the argument specified by ``arg_idx``. In the code example below, "2" means
    that the type tag associated with the function's second argument should agree
    with the type of the argument specified by ``arg_idx``.

For example:

.. code-block:: c++

  int fcntl(int fd, int cmd, ...)
      __attribute__(( argument_with_type_tag(fcntl,3,2) ));
  // The function's second argument will be a type tag; this type tag will
  // determine the expected type of the function's third argument.
  }];
}

def PointerWithTypeTagDocs : Documentation {
  let Category = DocCatTypeSafety;
  let Heading = "pointer_with_type_tag";
  let Content = [{
Use ``__attribute__((pointer_with_type_tag(ptr_kind, ptr_idx, type_tag_idx)))``
on a function declaration to specify that the function accepts a type tag that
determines the pointee type of some other pointer argument.

In the attribute prototype above:
  * ``ptr_kind`` is an identifier that should be used when annotating all
    applicable type tags.
  * ``ptr_idx`` provides the position of a function argument; this function
    argument will have a pointer type. The expected pointee type of this pointer
    type will be determined by the function argument specified by
    ``type_tag_idx``. In the code example below, "1" means that the pointee type
    of the function's first argument will be determined by ``type_tag_idx``.
  * ``type_tag_idx`` provides the position of a function argument; this function
    argument will be a type tag. The type tag will determine the expected pointee
    type of the pointer argument specified by ``ptr_idx``. In the code example
    below, "3" means that the type tag associated with the function's third
    argument should agree with the pointee type of the pointer argument specified
    by ``ptr_idx``.

For example:

.. code-block:: c++

  typedef int MPI_Datatype;
  int MPI_Send(void *buf, int count, MPI_Datatype datatype /*, other args omitted */)
      __attribute__(( pointer_with_type_tag(mpi,1,3) ));
  // The function's 3rd argument will be a type tag; this type tag will
  // determine the expected pointee type of the function's 1st argument.
  }];
}

def TypeTagForDatatypeDocs : Documentation {
  let Category = DocCatTypeSafety;
  let Content = [{
When declaring a variable, use
``__attribute__((type_tag_for_datatype(kind, type)))`` to create a type tag that
is tied to the ``type`` argument given to the attribute.

In the attribute prototype above:
  * ``kind`` is an identifier that should be used when annotating all applicable
    type tags.
  * ``type`` indicates the name of the type.

Clang supports annotating type tags of two forms.

  * **Type tag that is a reference to a declared identifier.**
    Use ``__attribute__((type_tag_for_datatype(kind, type)))`` when declaring that
    identifier:

    .. code-block:: c++

      typedef int MPI_Datatype;
      extern struct mpi_datatype mpi_datatype_int
          __attribute__(( type_tag_for_datatype(mpi,int) ));
      #define MPI_INT ((MPI_Datatype) &mpi_datatype_int)
      // &mpi_datatype_int is a type tag. It is tied to type "int".

  * **Type tag that is an integral literal.**
    Declare a ``static const`` variable with an initializer value and attach
    ``__attribute__((type_tag_for_datatype(kind, type)))`` on that declaration:

    .. code-block:: c++

      typedef int MPI_Datatype;
      static const MPI_Datatype mpi_datatype_int
          __attribute__(( type_tag_for_datatype(mpi,int) )) = 42;
      #define MPI_INT ((MPI_Datatype) 42)
      // The number 42 is a type tag. It is tied to type "int".


The ``type_tag_for_datatype`` attribute also accepts an optional third argument
that determines how the type of the function argument specified by either
``arg_idx`` or ``ptr_idx`` is compared against the type associated with the type
tag. (Recall that for the ``argument_with_type_tag`` attribute, the type of the
function argument specified by ``arg_idx`` is compared against the type
associated with the type tag. Also recall that for the ``pointer_with_type_tag``
attribute, the pointee type of the function argument specified by ``ptr_idx`` is
compared against the type associated with the type tag.) There are two supported
values for this optional third argument:

  * ``layout_compatible`` will cause types to be compared according to
    layout-compatibility rules (In C++11 [class.mem] p 17, 18, see the
    layout-compatibility rules for two standard-layout struct types and for two
    standard-layout union types). This is useful when creating a type tag
    associated with a struct or union type. For example:

    .. code-block:: c++

      /* In mpi.h */
      typedef int MPI_Datatype;
      struct internal_mpi_double_int { double d; int i; };
      extern struct mpi_datatype mpi_datatype_double_int
          __attribute__(( type_tag_for_datatype(mpi,
                          struct internal_mpi_double_int, layout_compatible) ));

      #define MPI_DOUBLE_INT ((MPI_Datatype) &mpi_datatype_double_int)

      int MPI_Send(void *buf, int count, MPI_Datatype datatype, ...)
          __attribute__(( pointer_with_type_tag(mpi,1,3) ));

      /* In user code */
      struct my_pair { double a; int b; };
      struct my_pair *buffer;
      MPI_Send(buffer, 1, MPI_DOUBLE_INT /*, ...  */); // no warning because the
                                                       // layout of my_pair is
                                                       // compatible with that of
                                                       // internal_mpi_double_int

      struct my_int_pair { int a; int b; }
      struct my_int_pair *buffer2;
      MPI_Send(buffer2, 1, MPI_DOUBLE_INT /*, ...  */); // warning because the
                                                        // layout of my_int_pair
                                                        // does not match that of
                                                        // internal_mpi_double_int

  * ``must_be_null`` specifies that the function argument specified by either
    ``arg_idx`` (for the ``argument_with_type_tag`` attribute) or ``ptr_idx`` (for
    the ``pointer_with_type_tag`` attribute) should be a null pointer constant.
    The second argument to the ``type_tag_for_datatype`` attribute is ignored. For
    example:

    .. code-block:: c++

      /* In mpi.h */
      typedef int MPI_Datatype;
      extern struct mpi_datatype mpi_datatype_null
          __attribute__(( type_tag_for_datatype(mpi, void, must_be_null) ));

      #define MPI_DATATYPE_NULL ((MPI_Datatype) &mpi_datatype_null)
      int MPI_Send(void *buf, int count, MPI_Datatype datatype, ...)
          __attribute__(( pointer_with_type_tag(mpi,1,3) ));

      /* In user code */
      struct my_pair { double a; int b; };
      struct my_pair *buffer;
      MPI_Send(buffer, 1, MPI_DATATYPE_NULL /*, ...  */); // warning: MPI_DATATYPE_NULL
                                                          // was specified but buffer
                                                          // is not a null pointer
  }];
}

def FlattenDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``flatten`` attribute causes calls within the attributed function to
be inlined unless it is impossible to do so, for example if the body of the
callee is unavailable or if the callee has the ``noinline`` attribute.
  }];
}

def FormatDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{

Clang supports the ``format`` attribute, which indicates that the function
accepts a ``printf`` or ``scanf``-like format string and corresponding
arguments or a ``va_list`` that contains these arguments.

Please see `GCC documentation about format attribute
<http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html>`_ to find details
about attribute syntax.

Clang implements two kinds of checks with this attribute.

#. Clang checks that the function with the ``format`` attribute is called with
   a format string that uses format specifiers that are allowed, and that
   arguments match the format string.  This is the ``-Wformat`` warning, it is
   on by default.

#. Clang checks that the format string argument is a literal string.  This is
   the ``-Wformat-nonliteral`` warning, it is off by default.

   Clang implements this mostly the same way as GCC, but there is a difference
   for functions that accept a ``va_list`` argument (for example, ``vprintf``).
   GCC does not emit ``-Wformat-nonliteral`` warning for calls to such
   functions.  Clang does not warn if the format string comes from a function
   parameter, where the function is annotated with a compatible attribute,
   otherwise it warns.  For example:

   .. code-block:: c

     __attribute__((__format__ (__scanf__, 1, 3)))
     void foo(const char* s, char *buf, ...) {
       va_list ap;
       va_start(ap, buf);

       vprintf(s, ap); // warning: format string is not a string literal
     }

   In this case we warn because ``s`` contains a format string for a
   ``scanf``-like function, but it is passed to a ``printf``-like function.

   If the attribute is removed, clang still warns, because the format string is
   not a string literal.

   Another example:

   .. code-block:: c

     __attribute__((__format__ (__printf__, 1, 3)))
     void foo(const char* s, char *buf, ...) {
       va_list ap;
       va_start(ap, buf);

       vprintf(s, ap); // warning
     }

   In this case Clang does not warn because the format string ``s`` and
   the corresponding arguments are annotated.  If the arguments are
   incorrect, the caller of ``foo`` will receive a warning.
  }];
}

def AlignValueDocs : Documentation {
  let Category = DocCatType;
  let Content = [{
The align_value attribute can be added to the typedef of a pointer type or the
declaration of a variable of pointer or reference type. It specifies that the
pointer will point to, or the reference will bind to, only objects with at
least the provided alignment. This alignment value must be some positive power
of 2.

   .. code-block:: c

     typedef double * aligned_double_ptr __attribute__((align_value(64)));
     void foo(double & x  __attribute__((align_value(128)),
              aligned_double_ptr y) { ... }

If the pointer value does not have the specified alignment at runtime, the
behavior of the program is undefined.
  }];
}

def FlagEnumDocs : Documentation {
  let Category = DocCatType;
  let Content = [{
This attribute can be added to an enumerator to signal to the compiler that it
is intended to be used as a flag type. This will cause the compiler to assume
that the range of the type includes all of the values that you can get by
manipulating bits of the enumerator when issuing warnings.
  }];
}

def EnumExtensibilityDocs : Documentation {
  let Category = DocCatType;
  let Content = [{
Attribute ``enum_extensibility`` is used to distinguish between enum definitions
that are extensible and those that are not. The attribute can take either
``closed`` or ``open`` as an argument. ``closed`` indicates a variable of the
enum type takes a value that corresponds to one of the enumerators listed in the
enum definition or, when the enum is annotated with ``flag_enum``, a value that
can be constructed using values corresponding to the enumerators. ``open``
indicates a variable of the enum type can take any values allowed by the
standard and instructs clang to be more lenient when issuing warnings.

.. code-block:: c

  enum __attribute__((enum_extensibility(closed))) ClosedEnum {
    A0, A1
  };

  enum __attribute__((enum_extensibility(open))) OpenEnum {
    B0, B1
  };

  enum __attribute__((enum_extensibility(closed),flag_enum)) ClosedFlagEnum {
    C0 = 1 << 0, C1 = 1 << 1
  };

  enum __attribute__((enum_extensibility(open),flag_enum)) OpenFlagEnum {
    D0 = 1 << 0, D1 = 1 << 1
  };

  void foo1() {
    enum ClosedEnum ce;
    enum OpenEnum oe;
    enum ClosedFlagEnum cfe;
    enum OpenFlagEnum ofe;

    ce = A1;           // no warnings
    ce = 100;          // warning issued
    oe = B1;           // no warnings
    oe = 100;          // no warnings
    cfe = C0 | C1;     // no warnings
    cfe = C0 | C1 | 4; // warning issued
    ofe = D0 | D1;     // no warnings
    ofe = D0 | D1 | 4; // no warnings
  }

  }];
}

def EmptyBasesDocs : Documentation {
  let Category = DocCatType;
  let Content = [{
The empty_bases attribute permits the compiler to utilize the
empty-base-optimization more frequently.
This attribute only applies to struct, class, and union types.
It is only supported when using the Microsoft C++ ABI.
  }];
}

def LayoutVersionDocs : Documentation {
  let Category = DocCatType;
  let Content = [{
The layout_version attribute requests that the compiler utilize the class
layout rules of a particular compiler version.
This attribute only applies to struct, class, and union types.
It is only supported when using the Microsoft C++ ABI.
  }];
}

def LifetimeBoundDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``lifetimebound`` attribute indicates that a resource owned by
a function parameter or implicit object parameter
is retained by the return value of the annotated function
(or, for a parameter of a constructor, in the value of the constructed object).
It is only supported in C++.

This attribute provides an experimental implementation of the facility
described in the C++ committee paper [http://wg21.link/p0936r0](P0936R0),
and is subject to change as the design of the corresponding functionality
changes.
  }];
}

def TrivialABIDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``trivial_abi`` attribute can be applied to a C++ class, struct, or union.
It instructs the compiler to pass and return the type using the C ABI for the
underlying type when the type would otherwise be considered non-trivial for the
purpose of calls.
A class annotated with `trivial_abi` can have non-trivial destructors or copy/move constructors without automatically becoming non-trivial for the purposes of calls. For example:

  .. code-block:: c++

    // A is trivial for the purposes of calls because `trivial_abi` makes the
    // user-provided special functions trivial.
    struct __attribute__((trivial_abi)) A {
      ~A();
      A(const A &);
      A(A &&);
      int x;
    };

    // B's destructor and copy/move constructor are considered trivial for the
    // purpose of calls because A is trivial.
    struct B {
      A a;
    };

If a type is trivial for the purposes of calls, has a non-trivial destructor,
and is passed as an argument by value, the convention is that the callee will
destroy the object before returning.

Attribute ``trivial_abi`` has no effect in the following cases:

- The class directly declares a virtual base or virtual methods.
- The class has a base class that is non-trivial for the purposes of calls.
- The class has a non-static data member whose type is non-trivial for the purposes of calls, which includes:

  - classes that are non-trivial for the purposes of calls
  - __weak-qualified types in Objective-C++
  - arrays of any of the above
  }];
}

def MSInheritanceDocs : Documentation {
  let Category = DocCatType;
  let Heading = "__single_inhertiance, __multiple_inheritance, __virtual_inheritance";
  let Content = [{
This collection of keywords is enabled under ``-fms-extensions`` and controls
the pointer-to-member representation used on ``*-*-win32`` targets.

The ``*-*-win32`` targets utilize a pointer-to-member representation which
varies in size and alignment depending on the definition of the underlying
class.

However, this is problematic when a forward declaration is only available and
no definition has been made yet.  In such cases, Clang is forced to utilize the
most general representation that is available to it.

These keywords make it possible to use a pointer-to-member representation other
than the most general one regardless of whether or not the definition will ever
be present in the current translation unit.

This family of keywords belong between the ``class-key`` and ``class-name``:

.. code-block:: c++

  struct __single_inheritance S;
  int S::*i;
  struct S {};

This keyword can be applied to class templates but only has an effect when used
on full specializations:

.. code-block:: c++

  template <typename T, typename U> struct __single_inheritance A; // warning: inheritance model ignored on primary template
  template <typename T> struct __multiple_inheritance A<T, T>; // warning: inheritance model ignored on partial specialization
  template <> struct __single_inheritance A<int, float>;

Note that choosing an inheritance model less general than strictly necessary is
an error:

.. code-block:: c++

  struct __multiple_inheritance S; // error: inheritance model does not match definition
  int S::*i;
  struct S {};
}];
}

def MSNoVTableDocs : Documentation {
  let Category = DocCatType;
  let Content = [{
This attribute can be added to a class declaration or definition to signal to
the compiler that constructors and destructors will not reference the virtual
function table. It is only supported when using the Microsoft C++ ABI.
  }];
}

def OptnoneDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``optnone`` attribute suppresses essentially all optimizations
on a function or method, regardless of the optimization level applied to
the compilation unit as a whole.  This is particularly useful when you
need to debug a particular function, but it is infeasible to build the
entire application without optimization.  Avoiding optimization on the
specified function can improve the quality of the debugging information
for that function.

This attribute is incompatible with the ``always_inline`` and ``minsize``
attributes.
  }];
}

def LoopHintDocs : Documentation {
  let Category = DocCatStmt;
  let Heading = "#pragma clang loop";
  let Content = [{
The ``#pragma clang loop`` directive allows loop optimization hints to be
specified for the subsequent loop. The directive allows pipelining to be
disabled, or vectorization, interleaving, and unrolling to be enabled or disabled.
Vector width, interleave count, unrolling count, and the initiation interval
for pipelining can be explicitly specified. See `language extensions
<http://clang.llvm.org/docs/LanguageExtensions.html#extensions-for-loop-hint-optimizations>`_
for details.
  }];
}

def UnrollHintDocs : Documentation {
  let Category = DocCatStmt;
  let Heading = "#pragma unroll, #pragma nounroll";
  let Content = [{
Loop unrolling optimization hints can be specified with ``#pragma unroll`` and
``#pragma nounroll``. The pragma is placed immediately before a for, while,
do-while, or c++11 range-based for loop.

Specifying ``#pragma unroll`` without a parameter directs the loop unroller to
attempt to fully unroll the loop if the trip count is known at compile time and
attempt to partially unroll the loop if the trip count is not known at compile
time:

.. code-block:: c++

  #pragma unroll
  for (...) {
    ...
  }

Specifying the optional parameter, ``#pragma unroll _value_``, directs the
unroller to unroll the loop ``_value_`` times.  The parameter may optionally be
enclosed in parentheses:

.. code-block:: c++

  #pragma unroll 16
  for (...) {
    ...
  }

  #pragma unroll(16)
  for (...) {
    ...
  }

Specifying ``#pragma nounroll`` indicates that the loop should not be unrolled:

.. code-block:: c++

  #pragma nounroll
  for (...) {
    ...
  }

``#pragma unroll`` and ``#pragma unroll _value_`` have identical semantics to
``#pragma clang loop unroll(full)`` and
``#pragma clang loop unroll_count(_value_)`` respectively. ``#pragma nounroll``
is equivalent to ``#pragma clang loop unroll(disable)``.  See
`language extensions
<http://clang.llvm.org/docs/LanguageExtensions.html#extensions-for-loop-hint-optimizations>`_
for further details including limitations of the unroll hints.
  }];
}

def PipelineHintDocs : Documentation {
  let Category = DocCatStmt;
  let Heading = "#pragma clang loop pipeline, #pragma clang loop pipeline_initiation_interval";
  let Content = [{
    Software Pipelining optimization is a technique used to optimize loops by
  utilizing instruction-level parallelism. It reorders loop instructions to
  overlap iterations. As a result, the next iteration starts before the previous
  iteration has finished. The module scheduling technique creates a schedule for
  one iteration such that when repeating at regular intervals, no inter-iteration
  dependencies are violated. This constant interval(in cycles) between the start
  of iterations is called the initiation interval. i.e. The initiation interval
  is the number of cycles between two iterations of an unoptimized loop in the
  newly created schedule. A new, optimized loop is created such that a single iteration
  of the loop executes in the same number of cycles as the initiation interval.
    For further details see <https://llvm.org/pubs/2005-06-17-LattnerMSThesis-book.pdf>.

  ``#pragma clang loop pipeline and #pragma loop pipeline_initiation_interval``
  could be used as hints for the software pipelining optimization. The pragma is
  placed immediately before a for, while, do-while, or a C++11 range-based for
  loop.

  Using ``#pragma clang loop pipeline(disable)`` avoids the software pipelining
  optimization. The disable state can only be specified:

  .. code-block:: c++

  #pragma clang loop pipeline(disable)
  for (...) {
    ...
  }

  Using ``#pragma loop pipeline_initiation_interval`` instructs
  the software pipeliner to try the specified initiation interval.
  If a schedule was found then the resulting loop iteration would have
  the specified cycle count. If a schedule was not found then loop
  remains unchanged. The initiation interval must be a positive number
  greater than zero:

  .. code-block:: c++

  #pragma loop pipeline_initiation_interval(10)
  for (...) {
    ...
  }

  }];
}



def OpenCLUnrollHintDocs : Documentation {
  let Category = DocCatStmt;
  let Content = [{
The opencl_unroll_hint attribute qualifier can be used to specify that a loop
(for, while and do loops) can be unrolled. This attribute qualifier can be
used to specify full unrolling or partial unrolling by a specified amount.
This is a compiler hint and the compiler may ignore this directive. See
`OpenCL v2.0 <https://www.khronos.org/registry/cl/specs/opencl-2.0.pdf>`_
s6.11.5 for details.
  }];
}

def OpenCLIntelReqdSubGroupSizeDocs : Documentation {
  let Category = DocCatStmt;
  let Content = [{
The optional attribute intel_reqd_sub_group_size can be used to indicate that
the kernel must be compiled and executed with the specified subgroup size. When
this attribute is present, get_max_sub_group_size() is guaranteed to return the
specified integer value. This is important for the correctness of many subgroup
algorithms, and in some cases may be used by the compiler to generate more optimal
code. See `cl_intel_required_subgroup_size
<https://www.khronos.org/registry/OpenCL/extensions/intel/cl_intel_required_subgroup_size.txt>`
for details.
  }];
}

def OpenCLAccessDocs : Documentation {
  let Category = DocCatStmt;
  let Heading = "__read_only, __write_only, __read_write (read_only, write_only, read_write)";
  let Content = [{
The access qualifiers must be used with image object arguments or pipe arguments
to declare if they are being read or written by a kernel or function.

The read_only/__read_only, write_only/__write_only and read_write/__read_write
names are reserved for use as access qualifiers and shall not be used otherwise.

.. code-block:: c

  kernel void
  foo (read_only image2d_t imageA,
       write_only image2d_t imageB) {
    ...
  }

In the above example imageA is a read-only 2D image object, and imageB is a
write-only 2D image object.

The read_write (or __read_write) qualifier can not be used with pipe.

More details can be found in the OpenCL C language Spec v2.0, Section 6.6.
    }];
}

def DocOpenCLAddressSpaces : DocumentationCategory<"OpenCL Address Spaces"> {
  let Content = [{
The address space qualifier may be used to specify the region of memory that is
used to allocate the object. OpenCL supports the following address spaces:
__generic(generic), __global(global), __local(local), __private(private),
__constant(constant).

  .. code-block:: c

    __constant int c = ...;

    __generic int* foo(global int* g) {
      __local int* l;
      private int p;
      ...
      return l;
    }

More details can be found in the OpenCL C language Spec v2.0, Section 6.5.
  }];
}

def OpenCLAddressSpaceGenericDocs : Documentation {
  let Category = DocOpenCLAddressSpaces;
  let Content = [{
The generic address space attribute is only available with OpenCL v2.0 and later.
It can be used with pointer types. Variables in global and local scope and
function parameters in non-kernel functions can have the generic address space
type attribute. It is intended to be a placeholder for any other address space
except for '__constant' in OpenCL code which can be used with multiple address
spaces.
  }];
}

def OpenCLAddressSpaceConstantDocs : Documentation {
  let Category = DocOpenCLAddressSpaces;
  let Content = [{
The constant address space attribute signals that an object is located in
a constant (non-modifiable) memory region. It is available to all work items.
Any type can be annotated with the constant address space attribute. Objects
with the constant address space qualifier can be declared in any scope and must
have an initializer.
  }];
}

def OpenCLAddressSpaceGlobalDocs : Documentation {
  let Category = DocOpenCLAddressSpaces;
  let Content = [{
The global address space attribute specifies that an object is allocated in
global memory, which is accessible by all work items. The content stored in this
memory area persists between kernel executions. Pointer types to the global
address space are allowed as function parameters or local variables. Starting
with OpenCL v2.0, the global address space can be used with global (program
scope) variables and static local variable as well.
  }];
}

def OpenCLAddressSpaceLocalDocs : Documentation {
  let Category = DocOpenCLAddressSpaces;
  let Content = [{
The local address space specifies that an object is allocated in the local (work
group) memory area, which is accessible to all work items in the same work
group. The content stored in this memory region is not accessible after
the kernel execution ends. In a kernel function scope, any variable can be in
the local address space. In other scopes, only pointer types to the local address
space are allowed. Local address space variables cannot have an initializer.
  }];
}

def OpenCLAddressSpacePrivateDocs : Documentation {
  let Category = DocOpenCLAddressSpaces;
  let Content = [{
The private address space specifies that an object is allocated in the private
(work item) memory. Other work items cannot access the same memory area and its
content is destroyed after work item execution ends. Local variables can be
declared in the private address space. Function arguments are always in the
private address space. Kernel function arguments of a pointer or an array type
cannot point to the private address space.
  }];
}

def OpenCLNoSVMDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
OpenCL 2.0 supports the optional ``__attribute__((nosvm))`` qualifier for
pointer variable. It informs the compiler that the pointer does not refer
to a shared virtual memory region. See OpenCL v2.0 s6.7.2 for details.

Since it is not widely used and has been removed from OpenCL 2.1, it is ignored
by Clang.
  }];
}
def NullabilityDocs : DocumentationCategory<"Nullability Attributes"> {
  let Content = [{
Whether a particular pointer may be "null" is an important concern when working with pointers in the C family of languages. The various nullability attributes indicate whether a particular pointer can be null or not, which makes APIs more expressive and can help static analysis tools identify bugs involving null pointers. Clang supports several kinds of nullability attributes: the ``nonnull`` and ``returns_nonnull`` attributes indicate which function or method parameters and result types can never be null, while nullability type qualifiers indicate which pointer types can be null (``_Nullable``) or cannot be null (``_Nonnull``).

The nullability (type) qualifiers express whether a value of a given pointer type can be null (the ``_Nullable`` qualifier), doesn't have a defined meaning for null (the ``_Nonnull`` qualifier), or for which the purpose of null is unclear (the ``_Null_unspecified`` qualifier). Because nullability qualifiers are expressed within the type system, they are more general than the ``nonnull`` and ``returns_nonnull`` attributes, allowing one to express (for example) a nullable pointer to an array of nonnull pointers. Nullability qualifiers are written to the right of the pointer to which they apply. For example:

  .. code-block:: c

    // No meaningful result when 'ptr' is null (here, it happens to be undefined behavior).
    int fetch(int * _Nonnull ptr) { return *ptr; }

    // 'ptr' may be null.
    int fetch_or_zero(int * _Nullable ptr) {
      return ptr ? *ptr : 0;
    }

    // A nullable pointer to non-null pointers to const characters.
    const char *join_strings(const char * _Nonnull * _Nullable strings, unsigned n);

In Objective-C, there is an alternate spelling for the nullability qualifiers that can be used in Objective-C methods and properties using context-sensitive, non-underscored keywords. For example:

  .. code-block:: objective-c

    @interface NSView : NSResponder
      - (nullable NSView *)ancestorSharedWithView:(nonnull NSView *)aView;
      @property (assign, nullable) NSView *superview;
      @property (readonly, nonnull) NSArray *subviews;
    @end
  }];
}

def TypeNonNullDocs : Documentation {
  let Category = NullabilityDocs;
  let Content = [{
The ``_Nonnull`` nullability qualifier indicates that null is not a meaningful value for a value of the ``_Nonnull`` pointer type. For example, given a declaration such as:

  .. code-block:: c

    int fetch(int * _Nonnull ptr);

a caller of ``fetch`` should not provide a null value, and the compiler will produce a warning if it sees a literal null value passed to ``fetch``. Note that, unlike the declaration attribute ``nonnull``, the presence of ``_Nonnull`` does not imply that passing null is undefined behavior: ``fetch`` is free to consider null undefined behavior or (perhaps for backward-compatibility reasons) defensively handle null.
  }];
}

def TypeNullableDocs : Documentation {
  let Category = NullabilityDocs;
  let Content = [{
The ``_Nullable`` nullability qualifier indicates that a value of the ``_Nullable`` pointer type can be null. For example, given:

  .. code-block:: c

    int fetch_or_zero(int * _Nullable ptr);

a caller of ``fetch_or_zero`` can provide null.
  }];
}

def TypeNullUnspecifiedDocs : Documentation {
  let Category = NullabilityDocs;
  let Content = [{
The ``_Null_unspecified`` nullability qualifier indicates that neither the ``_Nonnull`` nor ``_Nullable`` qualifiers make sense for a particular pointer type. It is used primarily to indicate that the role of null with specific pointers in a nullability-annotated header is unclear, e.g., due to overly-complex implementations or historical factors with a long-lived API.
  }];
}

def NonNullDocs : Documentation {
  let Category = NullabilityDocs;
  let Content = [{
The ``nonnull`` attribute indicates that some function parameters must not be null, and can be used in several different ways. It's original usage (`from GCC <https://gcc.gnu.org/onlinedocs/gcc/Common-Function-Attributes.html#Common-Function-Attributes>`_) is as a function (or Objective-C method) attribute that specifies which parameters of the function are nonnull in a comma-separated list. For example:

  .. code-block:: c

    extern void * my_memcpy (void *dest, const void *src, size_t len)
                    __attribute__((nonnull (1, 2)));

Here, the ``nonnull`` attribute indicates that parameters 1 and 2
cannot have a null value. Omitting the parenthesized list of parameter indices means that all parameters of pointer type cannot be null:

  .. code-block:: c

    extern void * my_memcpy (void *dest, const void *src, size_t len)
                    __attribute__((nonnull));

Clang also allows the ``nonnull`` attribute to be placed directly on a function (or Objective-C method) parameter, eliminating the need to specify the parameter index ahead of type. For example:

  .. code-block:: c

    extern void * my_memcpy (void *dest __attribute__((nonnull)),
                             const void *src __attribute__((nonnull)), size_t len);

Note that the ``nonnull`` attribute indicates that passing null to a non-null parameter is undefined behavior, which the optimizer may take advantage of to, e.g., remove null checks. The ``_Nonnull`` type qualifier indicates that a pointer cannot be null in a more general manner (because it is part of the type system) and does not imply undefined behavior, making it more widely applicable.
  }];
}

def ReturnsNonNullDocs : Documentation {
  let Category = NullabilityDocs;
  let Content = [{
The ``returns_nonnull`` attribute indicates that a particular function (or Objective-C method) always returns a non-null pointer. For example, a particular system ``malloc`` might be defined to terminate a process when memory is not available rather than returning a null pointer:

  .. code-block:: c

    extern void * malloc (size_t size) __attribute__((returns_nonnull));

The ``returns_nonnull`` attribute implies that returning a null pointer is undefined behavior, which the optimizer may take advantage of. The ``_Nonnull`` type qualifier indicates that a pointer cannot be null in a more general manner (because it is part of the type system) and does not imply undefined behavior, making it more widely applicable
}];
}

def NoAliasDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``noalias`` attribute indicates that the only memory accesses inside
function are loads and stores from objects pointed to by its pointer-typed
arguments, with arbitrary offsets.
  }];
}

def OMPDeclareSimdDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "#pragma omp declare simd";
  let Content = [{
The `declare simd` construct can be applied to a function to enable the creation
of one or more versions that can process multiple arguments using SIMD
instructions from a single invocation in a SIMD loop. The `declare simd`
directive is a declarative directive. There may be multiple `declare simd`
directives for a function. The use of a `declare simd` construct on a function
enables the creation of SIMD versions of the associated function that can be
used to process multiple arguments from a single invocation from a SIMD loop
concurrently.
The syntax of the `declare simd` construct is as follows:

  .. code-block:: none

    #pragma omp declare simd [clause[[,] clause] ...] new-line
    [#pragma omp declare simd [clause[[,] clause] ...] new-line]
    [...]
    function definition or declaration

where clause is one of the following:

  .. code-block:: none

    simdlen(length)
    linear(argument-list[:constant-linear-step])
    aligned(argument-list[:alignment])
    uniform(argument-list)
    inbranch
    notinbranch

  }];
}

def OMPDeclareTargetDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "#pragma omp declare target";
  let Content = [{
The `declare target` directive specifies that variables and functions are mapped
to a device for OpenMP offload mechanism.

The syntax of the declare target directive is as follows:

  .. code-block:: c

    #pragma omp declare target new-line
    declarations-definition-seq
    #pragma omp end declare target new-line
  }];
}

def NoStackProtectorDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Clang supports the ``__attribute__((no_stack_protector))`` attribute which disables
the stack protector on the specified function. This attribute is useful for
selectively disabling the stack protector on some functions when building with
``-fstack-protector`` compiler option.

For example, it disables the stack protector for the function ``foo`` but function
``bar`` will still be built with the stack protector with the ``-fstack-protector``
option.

.. code-block:: c

    int __attribute__((no_stack_protector))
    foo (int x); // stack protection will be disabled for foo.

    int bar(int y); // bar can be built with the stack protector.

    }];
}

def NotTailCalledDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``not_tail_called`` attribute prevents tail-call optimization on statically bound calls. It has no effect on indirect calls. Virtual functions, objective-c methods, and functions marked as ``always_inline`` cannot be marked as ``not_tail_called``.

For example, it prevents tail-call optimization in the following case:

  .. code-block:: c

    int __attribute__((not_tail_called)) foo1(int);

    int foo2(int a) {
      return foo1(a); // No tail-call optimization on direct calls.
    }

However, it doesn't prevent tail-call optimization in this case:

  .. code-block:: c

    int __attribute__((not_tail_called)) foo1(int);

    int foo2(int a) {
      int (*fn)(int) = &foo1;

      // not_tail_called has no effect on an indirect call even if the call can be
      // resolved at compile time.
      return (*fn)(a);
    }

Marking virtual functions as ``not_tail_called`` is an error:

  .. code-block:: c++

    class Base {
    public:
      // not_tail_called on a virtual function is an error.
      [[clang::not_tail_called]] virtual int foo1();

      virtual int foo2();

      // Non-virtual functions can be marked ``not_tail_called``.
      [[clang::not_tail_called]] int foo3();
    };

    class Derived1 : public Base {
    public:
      int foo1() override;

      // not_tail_called on a virtual function is an error.
      [[clang::not_tail_called]] int foo2() override;
    };
  }];
}

def NoThrowDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Clang supports the GNU style ``__attribute__((nothrow))`` and Microsoft style
``__declspec(nothrow)`` attribute as an equivalent of `noexcept` on function
declarations. This attribute informs the compiler that the annotated function
does not throw an exception. This prevents exception-unwinding. This attribute
is particularly useful on functions in the C Standard Library that are
guaranteed to not throw an exception.
    }];
}

def InternalLinkageDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``internal_linkage`` attribute changes the linkage type of the declaration to internal.
This is similar to C-style ``static``, but can be used on classes and class methods. When applied to a class definition,
this attribute affects all methods and static data members of that class.
This can be used to contain the ABI of a C++ library by excluding unwanted class methods from the export tables.
  }];
}

def ExcludeFromExplicitInstantiationDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``exclude_from_explicit_instantiation`` attribute opts-out a member of a
class template from being part of explicit template instantiations of that
class template. This means that an explicit instantiation will not instantiate
members of the class template marked with the attribute, but also that code
where an extern template declaration of the enclosing class template is visible
will not take for granted that an external instantiation of the class template
would provide those members (which would otherwise be a link error, since the
explicit instantiation won't provide those members). For example, let's say we
don't want the ``data()`` method to be part of libc++'s ABI. To make sure it
is not exported from the dylib, we give it hidden visibility:

  .. code-block:: c++

    // in <string>
    template <class CharT>
    class basic_string {
    public:
      __attribute__((__visibility__("hidden")))
      const value_type* data() const noexcept { ... }
    };

    template class basic_string<char>;

Since an explicit template instantiation declaration for ``basic_string<char>``
is provided, the compiler is free to assume that ``basic_string<char>::data()``
will be provided by another translation unit, and it is free to produce an
external call to this function. However, since ``data()`` has hidden visibility
and the explicit template instantiation is provided in a shared library (as
opposed to simply another translation unit), ``basic_string<char>::data()``
won't be found and a link error will ensue. This happens because the compiler
assumes that ``basic_string<char>::data()`` is part of the explicit template
instantiation declaration, when it really isn't. To tell the compiler that
``data()`` is not part of the explicit template instantiation declaration, the
``exclude_from_explicit_instantiation`` attribute can be used:

  .. code-block:: c++

    // in <string>
    template <class CharT>
    class basic_string {
    public:
      __attribute__((__visibility__("hidden")))
      __attribute__((exclude_from_explicit_instantiation))
      const value_type* data() const noexcept { ... }
    };

    template class basic_string<char>;

Now, the compiler won't assume that ``basic_string<char>::data()`` is provided
externally despite there being an explicit template instantiation declaration:
the compiler will implicitly instantiate ``basic_string<char>::data()`` in the
TUs where it is used.

This attribute can be used on static and non-static member functions of class
templates, static data members of class templates and member classes of class
templates.
  }];
}

def DisableTailCallsDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``disable_tail_calls`` attribute instructs the backend to not perform tail call optimization inside the marked function.

For example:

  .. code-block:: c

    int callee(int);

    int foo(int a) __attribute__((disable_tail_calls)) {
      return callee(a); // This call is not tail-call optimized.
    }

Marking virtual functions as ``disable_tail_calls`` is legal.

  .. code-block:: c++

    int callee(int);

    class Base {
    public:
      [[clang::disable_tail_calls]] virtual int foo1() {
        return callee(); // This call is not tail-call optimized.
      }
    };

    class Derived1 : public Base {
    public:
      int foo1() override {
        return callee(); // This call is tail-call optimized.
      }
    };

  }];
}

def AnyX86NoCallerSavedRegistersDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Use this attribute to indicate that the specified function has no
caller-saved registers. That is, all registers are callee-saved except for
registers used for passing parameters to the function or returning parameters
from the function.
The compiler saves and restores any modified registers that were not used for
passing or returning arguments to the function.

The user can call functions specified with the 'no_caller_saved_registers'
attribute from an interrupt handler without saving and restoring all
call-clobbered registers.

Note that 'no_caller_saved_registers' attribute is not a calling convention.
In fact, it only overrides the decision of which registers should be saved by
the caller, but not how the parameters are passed from the caller to the callee.

For example:

  .. code-block:: c

    __attribute__ ((no_caller_saved_registers, fastcall))
    void f (int arg1, int arg2) {
      ...
    }

  In this case parameters 'arg1' and 'arg2' will be passed in registers.
  In this case, on 32-bit x86 targets, the function 'f' will use ECX and EDX as
  register parameters. However, it will not assume any scratch registers and
  should save and restore any modified registers except for ECX and EDX.
  }];
}

def X86ForceAlignArgPointerDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
Use this attribute to force stack alignment.

Legacy x86 code uses 4-byte stack alignment. Newer aligned SSE instructions
(like 'movaps') that work with the stack require operands to be 16-byte aligned.
This attribute realigns the stack in the function prologue to make sure the
stack can be used with SSE instructions.

Note that the x86_64 ABI forces 16-byte stack alignment at the call site.
Because of this, 'force_align_arg_pointer' is not needed on x86_64, except in
rare cases where the caller does not align the stack properly (e.g. flow
jumps from i386 arch code).

  .. code-block:: c

    __attribute__ ((force_align_arg_pointer))
    void f () {
      ...
    }

  }];
}

def AnyX86NoCfCheckDocs : Documentation{
  let Category = DocCatFunction;
  let Content = [{
Jump Oriented Programming attacks rely on tampering with addresses used by
indirect call / jmp, e.g. redirect control-flow to non-programmer
intended bytes in the binary.
X86 Supports Indirect Branch Tracking (IBT) as part of Control-Flow
Enforcement Technology (CET). IBT instruments ENDBR instructions used to
specify valid targets of indirect call / jmp.
The ``nocf_check`` attribute has two roles:
1. Appertains to a function - do not add ENDBR instruction at the beginning of
the function.
2. Appertains to a function pointer - do not track the target function of this
pointer (by adding nocf_check prefix to the indirect-call instruction).
}];
}

def SwiftCallDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``swiftcall`` attribute indicates that a function should be called
using the Swift calling convention for a function or function pointer.

The lowering for the Swift calling convention, as described by the Swift
ABI documentation, occurs in multiple phases.  The first, "high-level"
phase breaks down the formal parameters and results into innately direct
and indirect components, adds implicit paraameters for the generic
signature, and assigns the context and error ABI treatments to parameters
where applicable.  The second phase breaks down the direct parameters
and results from the first phase and assigns them to registers or the
stack.  The ``swiftcall`` convention only handles this second phase of
lowering; the C function type must accurately reflect the results
of the first phase, as follows:

- Results classified as indirect by high-level lowering should be
  represented as parameters with the ``swift_indirect_result`` attribute.

- Results classified as direct by high-level lowering should be represented
  as follows:

  - First, remove any empty direct results.

  - If there are no direct results, the C result type should be ``void``.

  - If there is one direct result, the C result type should be a type with
    the exact layout of that result type.

  - If there are a multiple direct results, the C result type should be
    a struct type with the exact layout of a tuple of those results.

- Parameters classified as indirect by high-level lowering should be
  represented as parameters of pointer type.

- Parameters classified as direct by high-level lowering should be
  omitted if they are empty types; otherwise, they should be represented
  as a parameter type with a layout exactly matching the layout of the
  Swift parameter type.

- The context parameter, if present, should be represented as a trailing
  parameter with the ``swift_context`` attribute.

- The error result parameter, if present, should be represented as a
  trailing parameter (always following a context parameter) with the
  ``swift_error_result`` attribute.

``swiftcall`` does not support variadic arguments or unprototyped functions.

The parameter ABI treatment attributes are aspects of the function type.
A function type which which applies an ABI treatment attribute to a
parameter is a different type from an otherwise-identical function type
that does not.  A single parameter may not have multiple ABI treatment
attributes.

Support for this feature is target-dependent, although it should be
supported on every target that Swift supports.  Query for this support
with ``__has_attribute(swiftcall)``.  This implies support for the
``swift_context``, ``swift_error_result``, and ``swift_indirect_result``
attributes.
  }];
}

def SwiftContextDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``swift_context`` attribute marks a parameter of a ``swiftcall``
function as having the special context-parameter ABI treatment.

This treatment generally passes the context value in a special register
which is normally callee-preserved.

A ``swift_context`` parameter must either be the last parameter or must be
followed by a ``swift_error_result`` parameter (which itself must always be
the last parameter).

A context parameter must have pointer or reference type.
  }];
}

def SwiftErrorResultDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``swift_error_result`` attribute marks a parameter of a ``swiftcall``
function as having the special error-result ABI treatment.

This treatment generally passes the underlying error value in and out of
the function through a special register which is normally callee-preserved.
This is modeled in C by pretending that the register is addressable memory:

- The caller appears to pass the address of a variable of pointer type.
  The current value of this variable is copied into the register before
  the call; if the call returns normally, the value is copied back into the
  variable.

- The callee appears to receive the address of a variable.  This address
  is actually a hidden location in its own stack, initialized with the
  value of the register upon entry.  When the function returns normally,
  the value in that hidden location is written back to the register.

A ``swift_error_result`` parameter must be the last parameter, and it must be
preceded by a ``swift_context`` parameter.

A ``swift_error_result`` parameter must have type ``T**`` or ``T*&`` for some
type T.  Note that no qualifiers are permitted on the intermediate level.

It is undefined behavior if the caller does not pass a pointer or
reference to a valid object.

The standard convention is that the error value itself (that is, the
value stored in the apparent argument) will be null upon function entry,
but this is not enforced by the ABI.
  }];
}

def SwiftIndirectResultDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``swift_indirect_result`` attribute marks a parameter of a ``swiftcall``
function as having the special indirect-result ABI treatment.

This treatment gives the parameter the target's normal indirect-result
ABI treatment, which may involve passing it differently from an ordinary
parameter.  However, only the first indirect result will receive this
treatment.  Furthermore, low-level lowering may decide that a direct result
must be returned indirectly; if so, this will take priority over the
``swift_indirect_result`` parameters.

A ``swift_indirect_result`` parameter must either be the first parameter or
follow another ``swift_indirect_result`` parameter.

A ``swift_indirect_result`` parameter must have type ``T*`` or ``T&`` for
some object type ``T``.  If ``T`` is a complete type at the point of
definition of a function, it is undefined behavior if the argument
value does not point to storage of adequate size and alignment for a
value of type ``T``.

Making indirect results explicit in the signature allows C functions to
directly construct objects into them without relying on language
optimizations like C++'s named return value optimization (NRVO).
  }];
}

def SuppressDocs : Documentation {
  let Category = DocCatStmt;
  let Content = [{
The ``[[gsl::suppress]]`` attribute suppresses specific
clang-tidy diagnostics for rules of the `C++ Core Guidelines`_ in a portable
way. The attribute can be attached to declarations, statements, and at
namespace scope.

.. code-block:: c++

  [[gsl::suppress("Rh-public")]]
  void f_() {
    int *p;
    [[gsl::suppress("type")]] {
      p = reinterpret_cast<int*>(7);
    }
  }
  namespace N {
    [[clang::suppress("type", "bounds")]];
    ...
  }

.. _`C++ Core Guidelines`: https://github.com/isocpp/CppCoreGuidelines/blob/master/CppCoreGuidelines.md#inforce-enforcement
  }];
}

def AbiTagsDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``abi_tag`` attribute can be applied to a function, variable, class or
inline namespace declaration to modify the mangled name of the entity. It gives
the ability to distinguish between different versions of the same entity but
with different ABI versions supported. For example, a newer version of a class
could have a different set of data members and thus have a different size. Using
the ``abi_tag`` attribute, it is possible to have different mangled names for
a global variable of the class type. Therefore, the old code could keep using
the old manged name and the new code will use the new mangled name with tags.
  }];
}

def PreserveMostDocs : Documentation {
  let Category = DocCatCallingConvs;
  let Content = [{
On X86-64 and AArch64 targets, this attribute changes the calling convention of
a function. The ``preserve_most`` calling convention attempts to make the code
in the caller as unintrusive as possible. This convention behaves identically
to the ``C`` calling convention on how arguments and return values are passed,
but it uses a different set of caller/callee-saved registers. This alleviates
the burden of saving and recovering a large register set before and after the
call in the caller. If the arguments are passed in callee-saved registers,
then they will be preserved by the callee across the call. This doesn't
apply for values returned in callee-saved registers.

- On X86-64 the callee preserves all general purpose registers, except for
  R11. R11 can be used as a scratch register. Floating-point registers
  (XMMs/YMMs) are not preserved and need to be saved by the caller.

The idea behind this convention is to support calls to runtime functions
that have a hot path and a cold path. The hot path is usually a small piece
of code that doesn't use many registers. The cold path might need to call out to
another function and therefore only needs to preserve the caller-saved
registers, which haven't already been saved by the caller. The
`preserve_most` calling convention is very similar to the ``cold`` calling
convention in terms of caller/callee-saved registers, but they are used for
different types of function calls. ``coldcc`` is for function calls that are
rarely executed, whereas `preserve_most` function calls are intended to be
on the hot path and definitely executed a lot. Furthermore ``preserve_most``
doesn't prevent the inliner from inlining the function call.

This calling convention will be used by a future version of the Objective-C
runtime and should therefore still be considered experimental at this time.
Although this convention was created to optimize certain runtime calls to
the Objective-C runtime, it is not limited to this runtime and might be used
by other runtimes in the future too. The current implementation only
supports X86-64 and AArch64, but the intention is to support more architectures
in the future.
  }];
}

def PreserveAllDocs : Documentation {
  let Category = DocCatCallingConvs;
  let Content = [{
On X86-64 and AArch64 targets, this attribute changes the calling convention of
a function. The ``preserve_all`` calling convention attempts to make the code
in the caller even less intrusive than the ``preserve_most`` calling convention.
This calling convention also behaves identical to the ``C`` calling convention
on how arguments and return values are passed, but it uses a different set of
caller/callee-saved registers. This removes the burden of saving and
recovering a large register set before and after the call in the caller. If
the arguments are passed in callee-saved registers, then they will be
preserved by the callee across the call. This doesn't apply for values
returned in callee-saved registers.

- On X86-64 the callee preserves all general purpose registers, except for
  R11. R11 can be used as a scratch register. Furthermore it also preserves
  all floating-point registers (XMMs/YMMs).

The idea behind this convention is to support calls to runtime functions
that don't need to call out to any other functions.

This calling convention, like the ``preserve_most`` calling convention, will be
used by a future version of the Objective-C runtime and should be considered
experimental at this time.
  }];
}

def DeprecatedDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``deprecated`` attribute can be applied to a function, a variable, or a
type. This is useful when identifying functions, variables, or types that are
expected to be removed in a future version of a program.

Consider the function declaration for a hypothetical function ``f``:

.. code-block:: c++

  void f(void) __attribute__((deprecated("message", "replacement")));

When spelled as `__attribute__((deprecated))`, the deprecated attribute can have
two optional string arguments. The first one is the message to display when
emitting the warning; the second one enables the compiler to provide a Fix-It
to replace the deprecated name with a new name. Otherwise, when spelled as
`[[gnu::deprecated]] or [[deprecated]]`, the attribute can have one optional
string argument which is the message to display when emitting the warning.
  }];
}

def IFuncDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
``__attribute__((ifunc("resolver")))`` is used to mark that the address of a declaration should be resolved at runtime by calling a resolver function.

The symbol name of the resolver function is given in quotes.  A function with this name (after mangling) must be defined in the current translation unit; it may be ``static``.  The resolver function should return a pointer.

The ``ifunc`` attribute may only be used on a function declaration.  A function declaration with an ``ifunc`` attribute is considered to be a definition of the declared entity.  The entity must not have weak linkage; for example, in C++, it cannot be applied to a declaration if a definition at that location would be considered inline.

Not all targets support this attribute. ELF target support depends on both the linker and runtime linker, and is available in at least lld 4.0 and later, binutils 2.20.1 and later, glibc v2.11.1 and later, and FreeBSD 9.1 and later. Non-ELF targets currently do not support this attribute.
  }];
}

def LTOVisibilityDocs : Documentation {
  let Category = DocCatType;
  let Content = [{
See :doc:`LTOVisibility`.
  }];
}

def RenderScriptKernelAttributeDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
``__attribute__((kernel))`` is used to mark a ``kernel`` function in
RenderScript.

In RenderScript, ``kernel`` functions are used to express data-parallel
computations.  The RenderScript runtime efficiently parallelizes ``kernel``
functions to run on computational resources such as multi-core CPUs and GPUs.
See the RenderScript_ documentation for more information.

.. _RenderScript: https://developer.android.com/guide/topics/renderscript/compute.html
  }];
}

def XRayDocs : Documentation {
  let Category = DocCatFunction;
  let Heading = "xray_always_instrument, xray_never_instrument, xray_log_args";
  let Content = [{
``__attribute__((xray_always_instrument))`` or ``[[clang::xray_always_instrument]]`` is used to mark member functions (in C++), methods (in Objective C), and free functions (in C, C++, and Objective C) to be instrumented with XRay. This will cause the function to always have space at the beginning and exit points to allow for runtime patching.

Conversely, ``__attribute__((xray_never_instrument))`` or ``[[clang::xray_never_instrument]]`` will inhibit the insertion of these instrumentation points.

If a function has neither of these attributes, they become subject to the XRay heuristics used to determine whether a function should be instrumented or otherwise.

``__attribute__((xray_log_args(N)))`` or ``[[clang::xray_log_args(N)]]`` is used to preserve N function arguments for the logging function.  Currently, only N==1 is supported.
  }];
}

def TransparentUnionDocs : Documentation {
  let Category = DocCatType;
  let Content = [{
This attribute can be applied to a union to change the behaviour of calls to
functions that have an argument with a transparent union type. The compiler
behaviour is changed in the following manner:

- A value whose type is any member of the transparent union can be passed as an
  argument without the need to cast that value.

- The argument is passed to the function using the calling convention of the
  first member of the transparent union. Consequently, all the members of the
  transparent union should have the same calling convention as its first member.

Transparent unions are not supported in C++.
  }];
}

def ObjCSubclassingRestrictedDocs : Documentation {
  let Category = DocCatType;
  let Content = [{
This attribute can be added to an Objective-C ``@interface`` declaration to
ensure that this class cannot be subclassed.
  }];
}


def SelectAnyDocs : Documentation {
  let Category = DocCatType;
  let Content = [{
This attribute appertains to a global symbol, causing it to have a weak
definition (
`linkonce <https://llvm.org/docs/LangRef.html#linkage-types>`_
), allowing the linker to select any definition.

For more information see
`gcc documentation <https://gcc.gnu.org/onlinedocs/gcc-7.2.0/gcc/Microsoft-Windows-Variable-Attributes.html>`_
or `msvc documentation <https://docs.microsoft.com/pl-pl/cpp/cpp/selectany>`_.
}];
}

def ArtificialDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``artificial`` attribute can be applied to an inline function. If such a
function is inlined, the attribute indicates that debuggers should associate
the resulting instructions with the call site, rather than with the
corresponding line within the inlined callee.
  }];
}

def NoDerefDocs : Documentation {
  let Category = DocCatType;
  let Content = [{
The ``noderef`` attribute causes clang to diagnose dereferences of annotated pointer types.
This is ideally used with pointers that point to special memory which cannot be read
from or written to, but allowing for the pointer to be used in pointer arithmetic.
The following are examples of valid expressions where dereferences are diagnosed:

.. code-block:: c

  int __attribute__((noderef)) *p;
  int x = *p;  // warning

  int __attribute__((noderef)) **p2;
  x = **p2;  // warning

  int * __attribute__((noderef)) *p3;
  p = *p3;  // warning

  struct S {
    int a;
  };
  struct S __attribute__((noderef)) *s;
  x = s->a;    // warning
  x = (*s).a;  // warning

Not all dereferences may diagnose a warning if the value directed by the pointer may not be
accessed. The following are examples of valid expressions where may not be diagnosed:

.. code-block:: c

  int *q;
  int __attribute__((noderef)) *p;
  q = &*p;
  q = *&p;

  struct S {
    int a;
  };
  struct S __attribute__((noderef)) *s;
  p = &s->a;
  p = &(*s).a;

``noderef`` is currently only supported for pointers and arrays and not usable for
references or Objective-C object pointers.

.. code-block: c++

  int x = 2;
  int __attribute__((noderef)) &y = x;  // warning: 'noderef' can only be used on an array or pointer type

.. code-block: objc

  id __attribute__((noderef)) obj = [NSObject new]; // warning: 'noderef' can only be used on an array or pointer type
}];
}

def ReinitializesDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``reinitializes`` attribute can be applied to a non-static, non-const C++
member function to indicate that this member function reinitializes the entire
object to a known state, independent of the previous state of the object.

This attribute can be interpreted by static analyzers that warn about uses of an
object that has been left in an indeterminate state by a move operation. If a
member function marked with the ``reinitializes`` attribute is called on a
moved-from object, the analyzer can conclude that the object is no longer in an
indeterminate state.

A typical example where this attribute would be used is on functions that clear
a container class:

.. code-block:: c++

  template <class T>
  class Container {
  public:
    ...
    [[clang::reinitializes]] void Clear();
    ...
  };
  }];
}

def AlwaysDestroyDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``always_destroy`` attribute specifies that a variable with static or thread
storage duration should have its exit-time destructor run. This attribute is the
default unless clang was invoked with -fno-c++-static-destructors.
  }];
}

def NoDestroyDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``no_destroy`` attribute specifies that a variable with static or thread
storage duration shouldn't have its exit-time destructor run. Annotating every
static and thread duration variable with this attribute is equivalent to
invoking clang with -fno-c++-static-destructors.
  }];
}

def UninitializedDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The command-line parameter ``-ftrivial-auto-var-init=*`` can be used to
initialize trivial automatic stack variables. By default, trivial automatic
stack variables are uninitialized. This attribute is used to override the
command-line parameter, forcing variables to remain uninitialized. It has no
semantic meaning in that using uninitialized values is undefined behavior,
it rather documents the programmer's intent.
  }];
}

def GnuInlineDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
The ``gnu_inline`` changes the meaning of ``extern inline`` to use GNU inline
semantics, meaning:

* If any declaration that is declared ``inline`` is not declared ``extern``,
then the ``inline`` keyword is just a hint. In particular, an out-of-line
definition is still emitted for a function with external linkage, even if all
call sites are inlined, unlike in C99 and C++ inline semantics.

* If all declarations that are declared ``inline`` are also declared
``extern``, then the function body is present only for inlining and no
out-of-line version is emitted.

Some important consequences: ``static inline`` emits an out-of-line
version if needed, a plain ``inline`` definition emits an out-of-line version
always, and an ``extern inline`` definition (in a header) followed by a
(non-``extern``) ``inline`` declaration in a source file emits an out-of-line
version of the function in that source file but provides the function body for
inlining to all includers of the header.

Either ``__GNUC_GNU_INLINE__`` (GNU inline semantics) or
``__GNUC_STDC_INLINE__`` (C99 semantics) will be defined (they are mutually
exclusive). If ``__GNUC_STDC_INLINE__`` is defined, then the ``gnu_inline``
function attribute can be used to get GNU inline semantics on a per function
basis. If ``__GNUC_GNU_INLINE__`` is defined, then the translation unit is
already being compiled with GNU inline semantics as the implied default. It is
unspecified which macro is defined in a C++ compilation.

GNU inline semantics are the default behavior with ``-std=gnu89``,
``-std=c89``, ``-std=c94``, or ``-fgnu89-inline``.
  }];
}

def SpeculativeLoadHardeningDocs : Documentation {
  let Category = DocCatFunction;
  let Content = [{
  This attribute can be applied to a function declaration in order to indicate
  that `Speculative Load Hardening <https://llvm.org/docs/SpeculativeLoadHardening.html>`_
  should be enabled for the function body. This can also be applied to a method
  in Objective C.

  Speculative Load Hardening is a best-effort mitigation against
  information leak attacks that make use of control flow
  miss-speculation - specifically miss-speculation of whether a branch
  is taken or not. Typically vulnerabilities enabling such attacks are
  classified as "Spectre variant #1". Notably, this does not attempt to
  mitigate against miss-speculation of branch target, classified as
  "Spectre variant #2" vulnerabilities.

  When inlining, the attribute is sticky. Inlining a function that
  carries this attribute will cause the caller to gain the
  attribute. This is intended to provide a maximally conservative model
  where the code in a function annotated with this attribute will always
  (even after inlining) end up hardened.
  }];
}

def ObjCExternallyRetainedDocs : Documentation {
  let Category = DocCatVariable;
  let Content = [{
The ``objc_externally_retained`` attribute can be applied to strong local
variables, functions, methods, or blocks to opt into
`externally-retained semantics
<https://clang.llvm.org/docs/AutomaticReferenceCounting.html#externally-retained-variables>`_.

When applied to the definition of a function, method, or block, every parameter
of the function with implicit strong retainable object pointer type is
considered externally-retained, and becomes ``const``. By explicitly annotating
a parameter with ``__strong``, you can opt back into the default
non-externally-retained behaviour for that parameter. For instance,
``first_param`` is externally-retained below, but not ``second_param``:

.. code-block:: objc

  __attribute__((objc_externally_retained))
  void f(NSArray *first_param, __strong NSArray *second_param) {
    // ...
  }

Likewise, when applied to a strong local variable, that variable becomes
``const`` and is considered externally-retained.

When compiled without ``-fobjc-arc``, this attribute is ignored.
}]; }
