xref: /llvm-project/libc/docs/dev/implementation_standard.rst (revision 665efe896746b1dd138773e6e4d300ec97de27c2)
1Convention for implementing entrypoints
2=======================================
3
4LLVM-libc entrypoints are defined in the entrypoints document. In this document,
5we explain how the entrypoints are implemented. The source layout document
6explains that, within the high level ``src`` directory, there exists one
7directory for every public header file provided by LLVM-libc. The
8implementations of entrypoints live in the directory for the header they belong
9to. Some entrypoints are platform specific, and so their implementations are in
10a subdirectory with the name of the platform (e.g. ``stdio/linux/remove.cpp``).
11
12Implementation of entrypoints can span multiple ``.cpp`` and ``.h`` files, but
13there will be at least one header file with name of the form
14``<entrypoint name>.h`` for every entrypoint. This header file is called the
15implementation header file. For the ``isalpha`` function, the path to the
16implementation header file is ``src/ctype/isalpha.h``.
17
18Implementation Header File Structure
19------------------------------------
20
21We will use the ``isalpha`` function from the public ``ctype.h`` header file as an
22example. The ``isalpha`` function will be declared in an internal header file
23``src/ctype/isalpha.h`` as follows::
24
25    // --- isalpha.h --- //
26    #ifndef LLVM_LIBC_SRC_CTYPE_ISALPHA_H
27    #define LLVM_LIBC_SRC_CTYPE_ISALPHA_H
28
29    namespace LIBC_NAMESPACE_DECL {
30
31    int isalpha(int c);
32
33    } // namespace LIBC_NAMESPACE_DECL
34
35    #endif LLVM_LIBC_SRC_CTYPE_ISALPHA_H
36
37Notice that the ``isalpha`` function declaration is nested inside the namespace
38``LIBC_NAMESPACE_DECL``. All implementation constructs in LLVM-libc are declared
39within the namespace ``LIBC_NAMESPACE_DECL``.
40
41``.cpp`` File Structure
42-----------------------
43
44The main ``.cpp`` file is named ``<entrypoint name>.cpp`` and is usually in the
45same folder as the header. It contains the signature of the entrypoint function,
46which must be defined with the ``LLVM_LIBC_FUNCTION`` macro. For example, the
47``isalpha`` function from ``ctype.h`` is defined as follows, in the file
48``src/ctype/isalpha.cpp``::
49
50    // --- isalpha.cpp --- //
51
52    namespace LIBC_NAMESPACE_DECL {
53
54    LLVM_LIBC_FUNCTION(int, isalpha, (int c)) {
55      // ... implementation goes here.
56    }
57
58    } // namespace LIBC_NAMESPACE_DECL
59
60Notice the use of the macro ``LLVM_LIBC_FUNCTION``. This macro helps us define
61a C alias symbol for the C++ implementation. For example, for a library build,
62the macro is defined as follows::
63
64    #define LLVM_LIBC_FUNCTION(type, name, arglist)
65        LLVM_LIBC_FUNCTION_IMPL(type, name, arglist)
66    #define LLVM_LIBC_FUNCTION_IMPL(type, name, arglist)
67        LLVM_LIBC_FUNCTION_ATTR decltype(LIBC_NAMESPACE::name)
68            __##name##_impl__ __asm__(#name);
69        decltype(LIBC_NAMESPACE::name) name [[gnu::alias(#name)]];
70        type __##name##_impl__ arglist
71
72The LLVM_LIBC_FUNCTION_ATTR macro is normally defined to nothing, but can be
73defined by vendors who want to set their own attributes.
74