Vendor import of clang trunk r351319 (just before the release_80 branch
point): https://llvm.org/svn/llvm-project/cfe/trunk@351319
This commit is contained in:
parent
c7e70c433e
commit
676fbe8105
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/vendor/clang/dist/; revision=343173 svn path=/vendor/clang/clang-trunk-r351319/; revision=343174; tag=vendor/clang/clang-trunk-r351319
6
.gitignore
vendored
6
.gitignore
vendored
@ -24,6 +24,7 @@
|
||||
#==============================================================================#
|
||||
cscope.files
|
||||
cscope.out
|
||||
/tags
|
||||
|
||||
#==============================================================================#
|
||||
# Directories to ignore (do not add trailing '/'s, they skip symlinks).
|
||||
@ -35,3 +36,8 @@ docs/_build
|
||||
docs/analyzer/_build
|
||||
# debug info testsuite
|
||||
test/debuginfo-tests
|
||||
|
||||
# VS2017 and VSCode config files.
|
||||
.vscode
|
||||
.vs
|
||||
|
||||
|
169
CMakeLists.txt
169
CMakeLists.txt
@ -1,5 +1,9 @@
|
||||
cmake_minimum_required(VERSION 3.4.3)
|
||||
|
||||
if(POLICY CMP0075)
|
||||
cmake_policy(SET CMP0075 NEW)
|
||||
endif()
|
||||
|
||||
# If we are not building as a part of LLVM, build Clang as an
|
||||
# standalone project, using LLVM as an external library:
|
||||
if( CMAKE_SOURCE_DIR STREQUAL CMAKE_CURRENT_SOURCE_DIR )
|
||||
@ -7,9 +11,14 @@ if( CMAKE_SOURCE_DIR STREQUAL CMAKE_CURRENT_SOURCE_DIR )
|
||||
|
||||
# Rely on llvm-config.
|
||||
set(CONFIG_OUTPUT)
|
||||
find_program(LLVM_CONFIG "llvm-config")
|
||||
if(LLVM_CONFIG)
|
||||
set (LLVM_CONFIG_FOUND 1)
|
||||
message(STATUS "Found LLVM_CONFIG as ${LLVM_CONFIG}")
|
||||
message(DEPRECATION "Using llvm-config to detect the LLVM installation is \
|
||||
deprecated. The installed cmake files should be used \
|
||||
instead. CMake should be able to detect your LLVM install \
|
||||
automatically, but you can also use LLVM_DIR to specify \
|
||||
the path containing LLVMConfig.cmake.")
|
||||
set(CONFIG_COMMAND ${LLVM_CONFIG}
|
||||
"--assertion-mode"
|
||||
"--bindir"
|
||||
@ -32,17 +41,20 @@ if( CMAKE_SOURCE_DIR STREQUAL CMAKE_CURRENT_SOURCE_DIR )
|
||||
message(STATUS "${CONFIG_COMMAND_STR}")
|
||||
message(FATAL_ERROR "llvm-config failed with status ${HAD_ERROR}")
|
||||
endif()
|
||||
else()
|
||||
message(FATAL_ERROR "llvm-config not found -- ${LLVM_CONFIG}")
|
||||
|
||||
list(GET CONFIG_OUTPUT 0 ENABLE_ASSERTIONS)
|
||||
list(GET CONFIG_OUTPUT 1 TOOLS_BINARY_DIR)
|
||||
list(GET CONFIG_OUTPUT 2 LIBRARY_DIR)
|
||||
list(GET CONFIG_OUTPUT 3 INCLUDE_DIR)
|
||||
list(GET CONFIG_OUTPUT 4 LLVM_OBJ_ROOT)
|
||||
list(GET CONFIG_OUTPUT 5 MAIN_SRC_DIR)
|
||||
list(GET CONFIG_OUTPUT 6 LLVM_CONFIG_CMAKE_PATH)
|
||||
|
||||
# Normalize LLVM_CMAKE_PATH. --cmakedir might contain backslashes.
|
||||
# CMake assumes slashes as PATH.
|
||||
file(TO_CMAKE_PATH ${LLVM_CONFIG_CMAKE_PATH} LLVM_CMAKE_PATH)
|
||||
endif()
|
||||
|
||||
list(GET CONFIG_OUTPUT 0 ENABLE_ASSERTIONS)
|
||||
list(GET CONFIG_OUTPUT 1 TOOLS_BINARY_DIR)
|
||||
list(GET CONFIG_OUTPUT 2 LIBRARY_DIR)
|
||||
list(GET CONFIG_OUTPUT 3 INCLUDE_DIR)
|
||||
list(GET CONFIG_OUTPUT 4 LLVM_OBJ_ROOT)
|
||||
list(GET CONFIG_OUTPUT 5 MAIN_SRC_DIR)
|
||||
list(GET CONFIG_OUTPUT 6 LLVM_CONFIG_CMAKE_PATH)
|
||||
|
||||
if(NOT MSVC_IDE)
|
||||
set(LLVM_ENABLE_ASSERTIONS ${ENABLE_ASSERTIONS}
|
||||
@ -51,27 +63,29 @@ if( CMAKE_SOURCE_DIR STREQUAL CMAKE_CURRENT_SOURCE_DIR )
|
||||
mark_as_advanced(LLVM_ENABLE_ASSERTIONS)
|
||||
endif()
|
||||
|
||||
find_package(LLVM REQUIRED HINTS "${LLVM_CMAKE_PATH}")
|
||||
list(APPEND CMAKE_MODULE_PATH ${LLVM_DIR})
|
||||
|
||||
# We can't check LLVM_CONFIG here, because find_package(LLVM ...) also sets
|
||||
# LLVM_CONFIG.
|
||||
if (NOT LLVM_CONFIG_FOUND)
|
||||
# Pull values from LLVMConfig.cmake. We can drop this once the llvm-config
|
||||
# path is removed.
|
||||
set(TOOLS_BINARY_DIR ${LLVM_TOOLS_BINARY_DIR})
|
||||
set(LIBRARY_DIR ${LLVM_LIBRARY_DIR})
|
||||
set(INCLUDE_DIR ${LLVM_INCLUDE_DIR})
|
||||
set(LLVM_OBJ_DIR ${LLVM_BINARY_DIR})
|
||||
endif()
|
||||
|
||||
set(LLVM_TOOLS_BINARY_DIR ${TOOLS_BINARY_DIR} CACHE PATH "Path to llvm/bin")
|
||||
set(LLVM_LIBRARY_DIR ${LIBRARY_DIR} CACHE PATH "Path to llvm/lib")
|
||||
set(LLVM_MAIN_INCLUDE_DIR ${INCLUDE_DIR} CACHE PATH "Path to llvm/include")
|
||||
set(LLVM_BINARY_DIR ${LLVM_OBJ_ROOT} CACHE PATH "Path to LLVM build tree")
|
||||
set(LLVM_MAIN_SRC_DIR ${MAIN_SRC_DIR} CACHE PATH "Path to LLVM source tree")
|
||||
|
||||
# Normalize LLVM_CMAKE_PATH. --cmakedir might contain backslashes.
|
||||
# CMake assumes slashes as PATH.
|
||||
file(TO_CMAKE_PATH ${LLVM_CONFIG_CMAKE_PATH} LLVM_CMAKE_PATH)
|
||||
|
||||
find_program(LLVM_TABLEGEN_EXE "llvm-tblgen" ${LLVM_TOOLS_BINARY_DIR}
|
||||
NO_DEFAULT_PATH)
|
||||
|
||||
set(LLVMCONFIG_FILE "${LLVM_CMAKE_PATH}/LLVMConfig.cmake")
|
||||
if(EXISTS ${LLVMCONFIG_FILE})
|
||||
list(APPEND CMAKE_MODULE_PATH "${LLVM_CMAKE_PATH}")
|
||||
include(${LLVMCONFIG_FILE})
|
||||
else()
|
||||
message(FATAL_ERROR "Not found: ${LLVMCONFIG_FILE}")
|
||||
endif()
|
||||
|
||||
# They are used as destination of target generators.
|
||||
set(LLVM_RUNTIME_OUTPUT_INTDIR ${CMAKE_BINARY_DIR}/${CMAKE_CFG_INTDIR}/bin)
|
||||
set(LLVM_LIBRARY_OUTPUT_INTDIR ${CMAKE_BINARY_DIR}/${CMAKE_CFG_INTDIR}/lib${LLVM_LIBDIR_SUFFIX})
|
||||
@ -89,6 +103,7 @@ if( CMAKE_SOURCE_DIR STREQUAL CMAKE_CURRENT_SOURCE_DIR )
|
||||
option(LLVM_FORCE_USE_OLD_HOST_TOOLCHAIN
|
||||
"Set to ON to force using an old, unsupported host toolchain." OFF)
|
||||
option(CLANG_ENABLE_BOOTSTRAP "Generate the clang bootstrap target" OFF)
|
||||
option(LLVM_ENABLE_LIBXML2 "Use libxml2 if available." ON)
|
||||
|
||||
include(AddLLVM)
|
||||
include(TableGen)
|
||||
@ -184,13 +199,15 @@ endif()
|
||||
# we can include cmake files from this directory.
|
||||
list(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/cmake/modules")
|
||||
|
||||
# Don't look for libxml if we're using MSan, since uninstrumented third party
|
||||
# code may call MSan interceptors like strlen, leading to false positives.
|
||||
if(NOT LLVM_USE_SANITIZER MATCHES "Memory.*")
|
||||
set (LIBXML2_FOUND 0)
|
||||
find_package(LibXml2 2.5.3 QUIET)
|
||||
if (LIBXML2_FOUND)
|
||||
set(CLANG_HAVE_LIBXML 1)
|
||||
if(LLVM_ENABLE_LIBXML2)
|
||||
# Don't look for libxml if we're using MSan, since uninstrumented third party
|
||||
# code may call MSan interceptors like strlen, leading to false positives.
|
||||
if(NOT LLVM_USE_SANITIZER MATCHES "Memory.*")
|
||||
set (LIBXML2_FOUND 0)
|
||||
find_package(LibXml2 2.5.3 QUIET)
|
||||
if (LIBXML2_FOUND)
|
||||
set(CLANG_HAVE_LIBXML 1)
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
@ -279,6 +296,9 @@ endif()
|
||||
set(CLANG_VENDOR_UTI "org.llvm.clang" CACHE STRING
|
||||
"Vendor-specific uti.")
|
||||
|
||||
set(CLANG_PYTHON_BINDINGS_VERSIONS "" CACHE STRING
|
||||
"Python versions to install libclang python bindings for")
|
||||
|
||||
# The libdir suffix must exactly match whatever LLVM's configuration used.
|
||||
set(CLANG_LIBDIR_SUFFIX "${LLVM_LIBDIR_SUFFIX}")
|
||||
|
||||
@ -286,25 +306,13 @@ set(CLANG_SOURCE_DIR ${CMAKE_CURRENT_SOURCE_DIR})
|
||||
set(CLANG_BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR})
|
||||
|
||||
if( CMAKE_SOURCE_DIR STREQUAL CMAKE_BINARY_DIR AND NOT MSVC_IDE )
|
||||
message(FATAL_ERROR "In-source builds are not allowed. CMake would overwrite "
|
||||
"the makefiles distributed with LLVM. Please create a directory and run cmake "
|
||||
message(FATAL_ERROR "In-source builds are not allowed. "
|
||||
"Please create a directory and run cmake "
|
||||
"from there, passing the path to this source directory as the last argument. "
|
||||
"This process created the file `CMakeCache.txt' and the directory "
|
||||
"`CMakeFiles'. Please delete them.")
|
||||
endif()
|
||||
|
||||
if( NOT CMAKE_SOURCE_DIR STREQUAL CMAKE_BINARY_DIR )
|
||||
file(GLOB_RECURSE
|
||||
tablegenned_files_on_include_dir
|
||||
"${CLANG_SOURCE_DIR}/include/clang/*.inc")
|
||||
if( tablegenned_files_on_include_dir )
|
||||
message(FATAL_ERROR "Apparently there is a previous in-source build, "
|
||||
"probably as the result of running `configure' and `make' on "
|
||||
"${CLANG_SOURCE_DIR}. This may cause problems. The suspicious files are:\n"
|
||||
"${tablegenned_files_on_include_dir}\nPlease clean the source directory.")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
# If CLANG_VERSION_* is specified, use it, if not use LLVM_VERSION_*.
|
||||
if(NOT DEFINED CLANG_VERSION_MAJOR)
|
||||
set(CLANG_VERSION_MAJOR ${LLVM_VERSION_MAJOR})
|
||||
@ -403,24 +411,37 @@ option(CLANG_BUILD_TOOLS
|
||||
option(CLANG_ENABLE_ARCMT "Build ARCMT." ON)
|
||||
option(CLANG_ENABLE_STATIC_ANALYZER "Build static analyzer." ON)
|
||||
|
||||
option(CLANG_ANALYZER_BUILD_Z3
|
||||
"Build the static analyzer with the Z3 constraint manager." OFF)
|
||||
set(CLANG_ANALYZER_Z3_INSTALL_DIR "" CACHE STRING "Install directory of the Z3 solver.")
|
||||
|
||||
find_package(Z3 4.7.1)
|
||||
|
||||
if (CLANG_ANALYZER_Z3_INSTALL_DIR)
|
||||
if (NOT Z3_FOUND)
|
||||
message(FATAL_ERROR "Z3 4.7.1 has not been found in CLANG_ANALYZER_Z3_INSTALL_DIR: ${CLANG_ANALYZER_Z3_INSTALL_DIR}.")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
set(CLANG_ANALYZER_ENABLE_Z3_SOLVER_DEFAULT "${Z3_FOUND}")
|
||||
|
||||
option(CLANG_ANALYZER_ENABLE_Z3_SOLVER
|
||||
"Enable Support for the Z3 constraint solver in the Clang Static Analyzer."
|
||||
${CLANG_ANALYZER_ENABLE_Z3_SOLVER_DEFAULT}
|
||||
)
|
||||
|
||||
if (CLANG_ANALYZER_ENABLE_Z3_SOLVER)
|
||||
if (NOT Z3_FOUND)
|
||||
message(FATAL_ERROR "CLANG_ANALYZER_ENABLE_Z3_SOLVER cannot be enabled when Z3 is not available.")
|
||||
endif()
|
||||
|
||||
set(CLANG_ANALYZER_WITH_Z3 1)
|
||||
endif()
|
||||
|
||||
option(CLANG_ENABLE_PROTO_FUZZER "Build Clang protobuf fuzzer." OFF)
|
||||
|
||||
if(NOT CLANG_ENABLE_STATIC_ANALYZER AND (CLANG_ENABLE_ARCMT OR CLANG_ANALYZER_BUILD_Z3))
|
||||
if(NOT CLANG_ENABLE_STATIC_ANALYZER AND (CLANG_ENABLE_ARCMT OR CLANG_ANALYZER_ENABLE_Z3_SOLVER))
|
||||
message(FATAL_ERROR "Cannot disable static analyzer while enabling ARCMT or Z3")
|
||||
endif()
|
||||
|
||||
if(CLANG_ANALYZER_BUILD_Z3)
|
||||
find_package(Z3 4.5)
|
||||
if(Z3_FOUND)
|
||||
set(CLANG_ANALYZER_WITH_Z3 1)
|
||||
else()
|
||||
message(FATAL_ERROR "Cannot find Z3 header file or shared library")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(CLANG_ENABLE_ARCMT)
|
||||
set(CLANG_ENABLE_OBJC_REWRITER ON)
|
||||
endif()
|
||||
@ -494,6 +515,7 @@ if( CLANG_INCLUDE_TESTS )
|
||||
)
|
||||
endif()
|
||||
add_subdirectory(test)
|
||||
add_subdirectory(bindings/python/tests)
|
||||
|
||||
if(CLANG_BUILT_STANDALONE)
|
||||
# Add a global check rule now that all subdirectories have been traversed
|
||||
@ -502,11 +524,13 @@ if( CLANG_INCLUDE_TESTS )
|
||||
get_property(LLVM_LIT_PARAMS GLOBAL PROPERTY LLVM_LIT_PARAMS)
|
||||
get_property(LLVM_LIT_DEPENDS GLOBAL PROPERTY LLVM_LIT_DEPENDS)
|
||||
get_property(LLVM_LIT_EXTRA_ARGS GLOBAL PROPERTY LLVM_LIT_EXTRA_ARGS)
|
||||
get_property(LLVM_ADDITIONAL_TEST_TARGETS
|
||||
GLOBAL PROPERTY LLVM_ADDITIONAL_TEST_TARGETS)
|
||||
add_lit_target(check-all
|
||||
"Running all regression tests"
|
||||
${LLVM_LIT_TESTSUITES}
|
||||
PARAMS ${LLVM_LIT_PARAMS}
|
||||
DEPENDS ${LLVM_LIT_DEPENDS}
|
||||
DEPENDS ${LLVM_LIT_DEPENDS} ${LLVM_ADDITIONAL_TEST_TARGETS}
|
||||
ARGS ${LLVM_LIT_EXTRA_ARGS}
|
||||
)
|
||||
endif()
|
||||
@ -578,8 +602,8 @@ if (CLANG_ENABLE_BOOTSTRAP)
|
||||
if(NOT BOOTSTRAP_LLVM_ENABLE_LLD AND LLVM_BINUTILS_INCDIR)
|
||||
add_dependencies(clang-bootstrap-deps LLVMgold)
|
||||
endif()
|
||||
set(LTO_AR -DCMAKE_AR=${LLVM_RUNTIME_OUTPUT_INTDIR}/llvm-ar)
|
||||
set(LTO_RANLIB -DCMAKE_RANLIB=${LLVM_RUNTIME_OUTPUT_INTDIR}/llvm-ranlib)
|
||||
set(${CLANG_STAGE}_AR -DCMAKE_AR=${LLVM_RUNTIME_OUTPUT_INTDIR}/llvm-ar)
|
||||
set(${CLANG_STAGE}_RANLIB -DCMAKE_RANLIB=${LLVM_RUNTIME_OUTPUT_INTDIR}/llvm-ranlib)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
@ -645,6 +669,26 @@ if (CLANG_ENABLE_BOOTSTRAP)
|
||||
-DCMAKE_ASM_COMPILER=${LLVM_RUNTIME_OUTPUT_INTDIR}/${C_COMPILER}
|
||||
-DCMAKE_ASM_COMPILER_ID=Clang)
|
||||
|
||||
if(BOOTSTRAP_CMAKE_SYSTEM_NAME)
|
||||
set(${CLANG_STAGE}_CONFIG -DLLVM_CONFIG_PATH=${LLVM_RUNTIME_OUTPUT_INTDIR}/llvm-config)
|
||||
set(${CLANG_STAGE}_TABLEGEN
|
||||
-DLLVM_TABLEGEN=${LLVM_RUNTIME_OUTPUT_INTDIR}/llvm-tblgen
|
||||
-DCLANG_TABLEGEN=${LLVM_RUNTIME_OUTPUT_INTDIR}/clang-tblgen)
|
||||
if(BOOTSTRAP_CMAKE_SYSTEM_NAME STREQUAL "Linux")
|
||||
if(BOOTSTRAP_LLVM_ENABLE_LLD)
|
||||
set(${CLANG_STAGE}_LINKER -DCMAKE_LINKER=${LLVM_RUNTIME_OUTPUT_INTDIR}/ld.lld)
|
||||
endif()
|
||||
if(NOT BOOTSTRAP_LLVM_ENABLE_LTO)
|
||||
add_dependencies(clang-bootstrap-deps llvm-ar llvm-ranlib)
|
||||
set(${CLANG_STAGE}_AR -DCMAKE_AR=${LLVM_RUNTIME_OUTPUT_INTDIR}/llvm-ar)
|
||||
set(${CLANG_STAGE}_RANLIB -DCMAKE_RANLIB=${LLVM_RUNTIME_OUTPUT_INTDIR}/llvm-ranlib)
|
||||
endif()
|
||||
add_dependencies(clang-bootstrap-deps llvm-objcopy llvm-strip)
|
||||
set(${CLANG_STAGE}_OBJCOPY -DCMAKE_OBJCOPY=${LLVM_RUNTIME_OUTPUT_INTDIR}/llvm-objcopy)
|
||||
set(${CLANG_STAGE}_STRIP -DCMAKE_STRIP=${LLVM_RUNTIME_OUTPUT_INTDIR}/llvm-strip)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(BOOTSTRAP_LLVM_BUILD_INSTRUMENTED)
|
||||
add_dependencies(clang-bootstrap-deps llvm-profdata)
|
||||
set(PGO_OPT -DLLVM_PROFDATA=${LLVM_RUNTIME_OUTPUT_INTDIR}/llvm-profdata)
|
||||
@ -713,7 +757,14 @@ if (CLANG_ENABLE_BOOTSTRAP)
|
||||
${PASSTHROUGH_VARIABLES}
|
||||
-DCLANG_STAGE=${NEXT_CLANG_STAGE}
|
||||
${COMPILER_OPTIONS}
|
||||
${LTO_LIBRARY} ${LTO_AR} ${LTO_RANLIB} ${verbose} ${PGO_OPT}
|
||||
${${CLANG_STAGE}_CONFIG}
|
||||
${${CLANG_STAGE}_TABLEGEN}
|
||||
${LTO_LIBRARY} ${verbose} ${PGO_OPT}
|
||||
${${CLANG_STAGE}_LINKER}
|
||||
${${CLANG_STAGE}_AR}
|
||||
${${CLANG_STAGE}_RANLIB}
|
||||
${${CLANG_STAGE}_OBJCOPY}
|
||||
${${CLANG_STAGE}_STRIP}
|
||||
INSTALL_COMMAND ""
|
||||
STEP_TARGETS configure build
|
||||
USES_TERMINAL_CONFIGURE 1
|
||||
|
@ -49,6 +49,10 @@ N: John McCall
|
||||
E: rjmccall@apple.com
|
||||
D: Clang LLVM IR generation
|
||||
|
||||
N: Brad Smith
|
||||
E: brad@comstyle.com
|
||||
D: OpenBSD driver
|
||||
|
||||
N: Richard Smith
|
||||
E: richard@metafoo.co.uk
|
||||
D: All parts of Clang not covered by someone else
|
||||
|
@ -4,7 +4,7 @@ LLVM Release License
|
||||
University of Illinois/NCSA
|
||||
Open Source License
|
||||
|
||||
Copyright (c) 2007-2018 University of Illinois at Urbana-Champaign.
|
||||
Copyright (c) 2007-2019 University of Illinois at Urbana-Champaign.
|
||||
All rights reserved.
|
||||
|
||||
Developed by:
|
||||
|
@ -8,13 +8,6 @@ To time GCC preprocessing speed without output, use:
|
||||
"time gcc -MM file"
|
||||
This is similar to -Eonly.
|
||||
|
||||
//===---------------------------------------------------------------------===//
|
||||
|
||||
Creating and using a PTH file for performance measurement (use a release build).
|
||||
|
||||
$ clang -ccc-pch-is-pth -x objective-c-header INPUTS/Cocoa_h.m -o /tmp/tokencache
|
||||
$ clang -cc1 -token-cache /tmp/tokencache INPUTS/Cocoa_h.m
|
||||
|
||||
//===---------------------------------------------------------------------===//
|
||||
|
||||
C++ Template Instantiation benchmark:
|
||||
|
@ -4,12 +4,12 @@
|
||||
|
||||
This directory implements Python bindings for Clang.
|
||||
|
||||
You may need to alter LD_LIBRARY_PATH so that the Clang library can be
|
||||
You may need to set CLANG_LIBRARY_PATH so that the Clang library can be
|
||||
found. The unit tests are designed to be run with any standard test
|
||||
runner. For example:
|
||||
--
|
||||
$ env PYTHONPATH=$(echo ~/llvm/tools/clang/bindings/python/) \
|
||||
LD_LIBRARY_PATH=$(llvm-config --libdir) \
|
||||
CLANG_LIBRARY_PATH=$(llvm-config --libdir) \
|
||||
python -m unittest discover -v
|
||||
tests.cindex.test_index.test_create ... ok
|
||||
...
|
||||
|
@ -44,6 +44,7 @@
|
||||
Most object information is exposed using properties, when the underlying API
|
||||
call is efficient.
|
||||
"""
|
||||
from __future__ import absolute_import, division, print_function
|
||||
|
||||
# TODO
|
||||
# ====
|
||||
@ -63,10 +64,10 @@
|
||||
# o implement additional SourceLocation, SourceRange, and File methods.
|
||||
|
||||
from ctypes import *
|
||||
import collections
|
||||
|
||||
import clang.enumerations
|
||||
|
||||
import os
|
||||
import sys
|
||||
if sys.version_info[0] == 3:
|
||||
# Python 3 strings are unicode, translate them to/from utf8 for C-interop.
|
||||
@ -108,8 +109,6 @@ def b(x):
|
||||
return x
|
||||
return x.encode('utf8')
|
||||
|
||||
xrange = range
|
||||
|
||||
elif sys.version_info[0] == 2:
|
||||
# Python 2 strings are utf8 byte strings, no translation is needed for
|
||||
# C-interop.
|
||||
@ -123,6 +122,22 @@ def _to_python_string(x, *args):
|
||||
def b(x):
|
||||
return x
|
||||
|
||||
# Importing ABC-s directly from collections is deprecated since Python 3.7,
|
||||
# will stop working in Python 3.8.
|
||||
# See: https://docs.python.org/dev/whatsnew/3.7.html#id3
|
||||
if sys.version_info[:2] >= (3, 7):
|
||||
from collections import abc as collections_abc
|
||||
else:
|
||||
import collections as collections_abc
|
||||
|
||||
# We only support PathLike objects on Python version with os.fspath present
|
||||
# to be consistent with the Python standard library. On older Python versions
|
||||
# we only support strings and we have dummy fspath to just pass them through.
|
||||
try:
|
||||
fspath = os.fspath
|
||||
except AttributeError:
|
||||
def fspath(x):
|
||||
return x
|
||||
|
||||
# ctypes doesn't implicitly convert c_void_p to the appropriate wrapper
|
||||
# object. This is a problem, because it means that from_parameter will see an
|
||||
@ -391,7 +406,7 @@ def spelling(self):
|
||||
|
||||
@property
|
||||
def ranges(self):
|
||||
class RangeIterator:
|
||||
class RangeIterator(object):
|
||||
def __init__(self, diag):
|
||||
self.diag = diag
|
||||
|
||||
@ -407,7 +422,7 @@ def __getitem__(self, key):
|
||||
|
||||
@property
|
||||
def fixits(self):
|
||||
class FixItIterator:
|
||||
class FixItIterator(object):
|
||||
def __init__(self, diag):
|
||||
self.diag = diag
|
||||
|
||||
@ -427,7 +442,7 @@ def __getitem__(self, key):
|
||||
|
||||
@property
|
||||
def children(self):
|
||||
class ChildDiagnosticsIterator:
|
||||
class ChildDiagnosticsIterator(object):
|
||||
def __init__(self, diag):
|
||||
self.diag_set = conf.lib.clang_getChildDiagnostics(diag)
|
||||
|
||||
@ -547,7 +562,7 @@ def get_tokens(tu, extent):
|
||||
|
||||
token_group = TokenGroup(tu, tokens_memory, tokens_count)
|
||||
|
||||
for i in xrange(0, count):
|
||||
for i in range(0, count):
|
||||
token = Token()
|
||||
token.int_data = tokens_array[i].int_data
|
||||
token.ptr_data = tokens_array[i].ptr_data
|
||||
@ -2173,7 +2188,7 @@ def argument_types(self):
|
||||
The returned object is iterable and indexable. Each item in the
|
||||
container is a Type instance.
|
||||
"""
|
||||
class ArgumentsIterator(collections.Sequence):
|
||||
class ArgumentsIterator(collections_abc.Sequence):
|
||||
def __init__(self, parent):
|
||||
self.parent = parent
|
||||
self.length = None
|
||||
@ -2254,6 +2269,12 @@ def from_result(res, fn, args):
|
||||
|
||||
return res
|
||||
|
||||
def get_num_template_arguments(self):
|
||||
return conf.lib.clang_Type_getNumTemplateArguments(self)
|
||||
|
||||
def get_template_argument_type(self, num):
|
||||
return conf.lib.clang_Type_getTemplateArgumentAsType(self, num)
|
||||
|
||||
def get_canonical(self):
|
||||
"""
|
||||
Return the canonical type for a Type.
|
||||
@ -2460,8 +2481,8 @@ class _CXUnsavedFile(Structure):
|
||||
# 20: CompletionChunk.Kind("VerticalSpace")
|
||||
}
|
||||
|
||||
class CompletionChunk:
|
||||
class Kind:
|
||||
class CompletionChunk(object):
|
||||
class Kind(object):
|
||||
def __init__(self, name):
|
||||
self.name = name
|
||||
|
||||
@ -2548,7 +2569,7 @@ def isKindResultType(self):
|
||||
20: CompletionChunk.Kind("VerticalSpace")}
|
||||
|
||||
class CompletionString(ClangObject):
|
||||
class Availability:
|
||||
class Availability(object):
|
||||
def __init__(self, name):
|
||||
self.name = name
|
||||
|
||||
@ -2641,7 +2662,7 @@ def results(self):
|
||||
|
||||
@property
|
||||
def diagnostics(self):
|
||||
class DiagnosticsItr:
|
||||
class DiagnosticsItr(object):
|
||||
def __init__(self, ccr):
|
||||
self.ccr= ccr
|
||||
|
||||
@ -2746,11 +2767,11 @@ def from_source(cls, filename, args=None, unsaved_files=None, options=0,
|
||||
etc. e.g. ["-Wall", "-I/path/to/include"].
|
||||
|
||||
In-memory file content can be provided via unsaved_files. This is an
|
||||
iterable of 2-tuples. The first element is the str filename. The
|
||||
second element defines the content. Content can be provided as str
|
||||
source code or as file objects (anything with a read() method). If
|
||||
a file object is being used, content will be read until EOF and the
|
||||
read cursor will not be reset to its original position.
|
||||
iterable of 2-tuples. The first element is the filename (str or
|
||||
PathLike). The second element defines the content. Content can be
|
||||
provided as str source code or as file objects (anything with a read()
|
||||
method). If a file object is being used, content will be read until EOF
|
||||
and the read cursor will not be reset to its original position.
|
||||
|
||||
options is a bitwise or of TranslationUnit.PARSE_XXX flags which will
|
||||
control parsing behavior.
|
||||
@ -2795,11 +2816,13 @@ def from_source(cls, filename, args=None, unsaved_files=None, options=0,
|
||||
if hasattr(contents, "read"):
|
||||
contents = contents.read()
|
||||
|
||||
unsaved_array[i].name = b(name)
|
||||
unsaved_array[i].name = b(fspath(name))
|
||||
unsaved_array[i].contents = b(contents)
|
||||
unsaved_array[i].length = len(contents)
|
||||
|
||||
ptr = conf.lib.clang_parseTranslationUnit(index, filename, args_array,
|
||||
ptr = conf.lib.clang_parseTranslationUnit(index,
|
||||
fspath(filename) if filename is not None else None,
|
||||
args_array,
|
||||
len(args), unsaved_array,
|
||||
len(unsaved_files), options)
|
||||
|
||||
@ -2820,11 +2843,13 @@ def from_ast_file(cls, filename, index=None):
|
||||
|
||||
index is optional and is the Index instance to use. If not provided,
|
||||
a default Index will be created.
|
||||
|
||||
filename can be str or PathLike.
|
||||
"""
|
||||
if index is None:
|
||||
index = Index.create()
|
||||
|
||||
ptr = conf.lib.clang_createTranslationUnit(index, filename)
|
||||
ptr = conf.lib.clang_createTranslationUnit(index, fspath(filename))
|
||||
if not ptr:
|
||||
raise TranslationUnitLoadError(filename)
|
||||
|
||||
@ -2939,7 +2964,7 @@ def diagnostics(self):
|
||||
"""
|
||||
Return an iterable (and indexable) object containing the diagnostics.
|
||||
"""
|
||||
class DiagIterator:
|
||||
class DiagIterator(object):
|
||||
def __init__(self, tu):
|
||||
self.tu = tu
|
||||
|
||||
@ -2977,7 +3002,7 @@ def reparse(self, unsaved_files=None, options=0):
|
||||
print(value)
|
||||
if not isinstance(value, str):
|
||||
raise TypeError('Unexpected unsaved file contents.')
|
||||
unsaved_files_array[i].name = name
|
||||
unsaved_files_array[i].name = fspath(name)
|
||||
unsaved_files_array[i].contents = value
|
||||
unsaved_files_array[i].length = len(value)
|
||||
ptr = conf.lib.clang_reparseTranslationUnit(self, len(unsaved_files),
|
||||
@ -2996,10 +3021,10 @@ def save(self, filename):
|
||||
case, the reason(s) why should be available via
|
||||
TranslationUnit.diagnostics().
|
||||
|
||||
filename -- The path to save the translation unit to.
|
||||
filename -- The path to save the translation unit to (str or PathLike).
|
||||
"""
|
||||
options = conf.lib.clang_defaultSaveOptions(self)
|
||||
result = int(conf.lib.clang_saveTranslationUnit(self, filename,
|
||||
result = int(conf.lib.clang_saveTranslationUnit(self, fspath(filename),
|
||||
options))
|
||||
if result != 0:
|
||||
raise TranslationUnitSaveError(result,
|
||||
@ -3041,10 +3066,10 @@ def codeComplete(self, path, line, column, unsaved_files=None,
|
||||
print(value)
|
||||
if not isinstance(value, str):
|
||||
raise TypeError('Unexpected unsaved file contents.')
|
||||
unsaved_files_array[i].name = b(name)
|
||||
unsaved_files_array[i].name = b(fspath(name))
|
||||
unsaved_files_array[i].contents = b(value)
|
||||
unsaved_files_array[i].length = len(value)
|
||||
ptr = conf.lib.clang_codeCompleteAt(self, path, line, column,
|
||||
ptr = conf.lib.clang_codeCompleteAt(self, fspath(path), line, column,
|
||||
unsaved_files_array, len(unsaved_files), options)
|
||||
if ptr:
|
||||
return CodeCompletionResults(ptr)
|
||||
@ -3072,7 +3097,7 @@ class File(ClangObject):
|
||||
@staticmethod
|
||||
def from_name(translation_unit, file_name):
|
||||
"""Retrieve a file handle within the given translation unit."""
|
||||
return File(conf.lib.clang_getFile(translation_unit, file_name))
|
||||
return File(conf.lib.clang_getFile(translation_unit, fspath(file_name)))
|
||||
|
||||
@property
|
||||
def name(self):
|
||||
@ -3171,7 +3196,7 @@ def arguments(self):
|
||||
Invariant : the first argument is the compiler executable
|
||||
"""
|
||||
length = conf.lib.clang_CompileCommand_getNumArgs(self.cmd)
|
||||
for i in xrange(length):
|
||||
for i in range(length):
|
||||
yield conf.lib.clang_CompileCommand_getArg(self.cmd, i)
|
||||
|
||||
class CompileCommands(object):
|
||||
@ -3223,7 +3248,7 @@ def fromDirectory(buildDir):
|
||||
"""Builds a CompilationDatabase from the database found in buildDir"""
|
||||
errorCode = c_uint()
|
||||
try:
|
||||
cdb = conf.lib.clang_CompilationDatabase_fromDirectory(buildDir,
|
||||
cdb = conf.lib.clang_CompilationDatabase_fromDirectory(fspath(buildDir),
|
||||
byref(errorCode))
|
||||
except CompilationDatabaseError as e:
|
||||
raise CompilationDatabaseError(int(errorCode.value),
|
||||
@ -3236,7 +3261,7 @@ def getCompileCommands(self, filename):
|
||||
build filename. Returns None if filename is not found in the database.
|
||||
"""
|
||||
return conf.lib.clang_CompilationDatabase_getCompileCommands(self,
|
||||
filename)
|
||||
fspath(filename))
|
||||
|
||||
def getAllCompileCommands(self):
|
||||
"""
|
||||
@ -3999,6 +4024,15 @@ def cursor(self):
|
||||
Type,
|
||||
Type.from_result),
|
||||
|
||||
("clang_Type_getNumTemplateArguments",
|
||||
[Type],
|
||||
c_int),
|
||||
|
||||
("clang_Type_getTemplateArgumentAsType",
|
||||
[Type, c_uint],
|
||||
Type,
|
||||
Type.from_result),
|
||||
|
||||
("clang_Type_getOffsetOf",
|
||||
[Type, c_interop_string],
|
||||
c_longlong),
|
||||
@ -4062,7 +4096,7 @@ def register(item):
|
||||
for f in functionList:
|
||||
register(f)
|
||||
|
||||
class Config:
|
||||
class Config(object):
|
||||
library_path = None
|
||||
library_file = None
|
||||
compatibility_check = True
|
||||
@ -4075,7 +4109,7 @@ def set_library_path(path):
|
||||
raise Exception("library path must be set before before using " \
|
||||
"any other functionalities in libclang.")
|
||||
|
||||
Config.library_path = path
|
||||
Config.library_path = fspath(path)
|
||||
|
||||
@staticmethod
|
||||
def set_library_file(filename):
|
||||
@ -4084,7 +4118,7 @@ def set_library_file(filename):
|
||||
raise Exception("library file must be set before before using " \
|
||||
"any other functionalities in libclang.")
|
||||
|
||||
Config.library_file = filename
|
||||
Config.library_file = fspath(filename)
|
||||
|
||||
@staticmethod
|
||||
def set_compatibility_check(check_status):
|
||||
|
@ -79,7 +79,7 @@ def main():
|
||||
if not tu:
|
||||
parser.error("unable to load input")
|
||||
|
||||
pprint(('diags', map(get_diag_info, tu.diagnostics)))
|
||||
pprint(('diags', [get_diag_info(d) for d in tu.diagnostics]))
|
||||
pprint(('nodes', get_info(tu.cursor)))
|
||||
|
||||
if __name__ == '__main__':
|
||||
|
46
bindings/python/tests/CMakeLists.txt
Normal file
46
bindings/python/tests/CMakeLists.txt
Normal file
@ -0,0 +1,46 @@
|
||||
# Test target to run Python test suite from main build.
|
||||
|
||||
add_custom_target(check-clang-python
|
||||
COMMAND ${CMAKE_COMMAND} -E env
|
||||
CLANG_LIBRARY_PATH=$<TARGET_FILE_DIR:libclang>
|
||||
${PYTHON_EXECUTABLE} -m unittest discover
|
||||
DEPENDS libclang
|
||||
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/..)
|
||||
|
||||
set(RUN_PYTHON_TESTS TRUE)
|
||||
set_target_properties(check-clang-python PROPERTIES FOLDER "Clang tests")
|
||||
|
||||
# Tests require libclang.so which is only built with LLVM_ENABLE_PIC=ON
|
||||
if(NOT LLVM_ENABLE_PIC)
|
||||
set(RUN_PYTHON_TESTS FALSE)
|
||||
endif()
|
||||
|
||||
# Do not try to run if libclang was built with ASan because
|
||||
# the sanitizer library will likely be loaded too late to perform
|
||||
# interception and will then fail.
|
||||
# We could use LD_PRELOAD/DYLD_INSERT_LIBRARIES but this isn't
|
||||
# portable so its easier just to not run the tests when building
|
||||
# with ASan.
|
||||
list(FIND LLVM_USE_SANITIZER "Address" LLVM_USE_ASAN_INDEX)
|
||||
if(NOT LLVM_USE_ASAN_INDEX EQUAL -1)
|
||||
set(RUN_PYTHON_TESTS FALSE)
|
||||
endif()
|
||||
|
||||
# Tests fail on Windows, and need someone knowledgeable to fix.
|
||||
# It's not clear whether it's a test or a valid binding problem.
|
||||
if(WIN32)
|
||||
set(RUN_PYTHON_TESTS FALSE)
|
||||
endif()
|
||||
|
||||
# AArch64 and Hexagon have known test failures that need to be
|
||||
# addressed.
|
||||
# SystemZ has broken Python/FFI interface:
|
||||
# https://reviews.llvm.org/D52840#1265716
|
||||
if(${LLVM_NATIVE_ARCH} MATCHES "^(AArch64|Hexagon|SystemZ)$")
|
||||
set(RUN_PYTHON_TESTS FALSE)
|
||||
endif()
|
||||
|
||||
if(RUN_PYTHON_TESTS)
|
||||
set_property(GLOBAL APPEND PROPERTY
|
||||
LLVM_ADDITIONAL_TEST_TARGETS check-clang-python)
|
||||
endif()
|
@ -1,3 +1,7 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import AccessSpecifier
|
||||
from clang.cindex import Cursor
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import CompilationDatabase
|
||||
from clang.cindex import CompilationDatabaseError
|
||||
from clang.cindex import CompileCommands
|
||||
@ -6,6 +11,8 @@
|
||||
import gc
|
||||
import unittest
|
||||
import sys
|
||||
from .util import skip_if_no_fspath
|
||||
from .util import str_to_path
|
||||
|
||||
|
||||
kInputsDir = os.path.join(os.path.dirname(__file__), 'INPUTS')
|
||||
@ -26,17 +33,19 @@ def test_create(self):
|
||||
"""Check we can load a compilation database"""
|
||||
cdb = CompilationDatabase.fromDirectory(kInputsDir)
|
||||
|
||||
def test_lookup_fail(self):
|
||||
"""Check file lookup failure"""
|
||||
cdb = CompilationDatabase.fromDirectory(kInputsDir)
|
||||
self.assertIsNone(cdb.getCompileCommands('file_do_not_exist.cpp'))
|
||||
|
||||
def test_lookup_succeed(self):
|
||||
"""Check we get some results if the file exists in the db"""
|
||||
cdb = CompilationDatabase.fromDirectory(kInputsDir)
|
||||
cmds = cdb.getCompileCommands('/home/john.doe/MyProject/project.cpp')
|
||||
self.assertNotEqual(len(cmds), 0)
|
||||
|
||||
@skip_if_no_fspath
|
||||
def test_lookup_succeed_pathlike(self):
|
||||
"""Same as test_lookup_succeed, but with PathLikes"""
|
||||
cdb = CompilationDatabase.fromDirectory(str_to_path(kInputsDir))
|
||||
cmds = cdb.getCompileCommands(str_to_path('/home/john.doe/MyProject/project.cpp'))
|
||||
self.assertNotEqual(len(cmds), 0)
|
||||
|
||||
def test_all_compilecommand(self):
|
||||
"""Check we get all results from the db"""
|
||||
cdb = CompilationDatabase.fromDirectory(kInputsDir)
|
||||
|
@ -1,6 +1,13 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import TranslationUnit
|
||||
|
||||
import unittest
|
||||
from .util import skip_if_no_fspath
|
||||
from .util import str_to_path
|
||||
|
||||
|
||||
class TestCodeCompletion(unittest.TestCase):
|
||||
@ -38,6 +45,32 @@ def test_code_complete(self):
|
||||
]
|
||||
self.check_completion_results(cr, expected)
|
||||
|
||||
@skip_if_no_fspath
|
||||
def test_code_complete_pathlike(self):
|
||||
files = [(str_to_path('fake.c'), """
|
||||
/// Aaa.
|
||||
int test1;
|
||||
|
||||
/// Bbb.
|
||||
void test2(void);
|
||||
|
||||
void f() {
|
||||
|
||||
}
|
||||
""")]
|
||||
|
||||
tu = TranslationUnit.from_source(str_to_path('fake.c'), ['-std=c99'], unsaved_files=files,
|
||||
options=TranslationUnit.PARSE_INCLUDE_BRIEF_COMMENTS_IN_CODE_COMPLETION)
|
||||
|
||||
cr = tu.codeComplete(str_to_path('fake.c'), 9, 1, unsaved_files=files, include_brief_comments=True)
|
||||
|
||||
expected = [
|
||||
"{'int', ResultType} | {'test1', TypedText} || Priority: 50 || Availability: Available || Brief comment: Aaa.",
|
||||
"{'void', ResultType} | {'test2', TypedText} | {'(', LeftParen} | {')', RightParen} || Priority: 50 || Availability: Available || Brief comment: Bbb.",
|
||||
"{'return', TypedText} || Priority: 40 || Availability: Available || Brief comment: None"
|
||||
]
|
||||
self.check_completion_results(cr, expected)
|
||||
|
||||
def test_code_complete_availability(self):
|
||||
files = [('fake.cpp', """
|
||||
class P {
|
||||
@ -61,11 +94,11 @@ class Q : public P {
|
||||
cr = tu.codeComplete('fake.cpp', 12, 5, unsaved_files=files)
|
||||
|
||||
expected = [
|
||||
"{'const', TypedText} || Priority: 40 || Availability: Available || Brief comment: None",
|
||||
"{'volatile', TypedText} || Priority: 40 || Availability: Available || Brief comment: None",
|
||||
"{'const', TypedText} || Priority: 50 || Availability: Available || Brief comment: None",
|
||||
"{'volatile', TypedText} || Priority: 50 || Availability: Available || Brief comment: None",
|
||||
"{'operator', TypedText} || Priority: 40 || Availability: Available || Brief comment: None",
|
||||
"{'P', TypedText} | {'::', Text} || Priority: 75 || Availability: Available || Brief comment: None",
|
||||
"{'Q', TypedText} | {'::', Text} || Priority: 75 || Availability: Available || Brief comment: None"
|
||||
"{'P', TypedText} || Priority: 50 || Availability: Available || Brief comment: None",
|
||||
"{'Q', TypedText} || Priority: 50 || Availability: Available || Brief comment: None"
|
||||
]
|
||||
self.check_completion_results(cr, expected)
|
||||
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import TranslationUnit
|
||||
from tests.cindex.util import get_cursor
|
||||
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
import ctypes
|
||||
import gc
|
||||
import unittest
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import CursorKind
|
||||
|
||||
import unittest
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import *
|
||||
from .util import get_tu
|
||||
|
||||
@ -46,7 +51,7 @@ def test_diagnostic_fixit(self):
|
||||
self.assertEqual(tu.diagnostics[0].fixits[0].value, '.f0 = ')
|
||||
|
||||
def test_diagnostic_range(self):
|
||||
tu = get_tu('void f() { int i = "a" + 1; }')
|
||||
tu = get_tu('void f() { int i = "a"; }')
|
||||
self.assertEqual(len(tu.diagnostics), 1)
|
||||
self.assertEqual(tu.diagnostics[0].severity, Diagnostic.Warning)
|
||||
self.assertEqual(tu.diagnostics[0].location.line, 1)
|
||||
@ -58,7 +63,7 @@ def test_diagnostic_range(self):
|
||||
self.assertEqual(tu.diagnostics[0].ranges[0].start.line, 1)
|
||||
self.assertEqual(tu.diagnostics[0].ranges[0].start.column, 20)
|
||||
self.assertEqual(tu.diagnostics[0].ranges[0].end.line, 1)
|
||||
self.assertEqual(tu.diagnostics[0].ranges[0].end.column, 27)
|
||||
self.assertEqual(tu.diagnostics[0].ranges[0].end.column, 23)
|
||||
with self.assertRaises(IndexError):
|
||||
tu.diagnostics[0].ranges[1].start.line
|
||||
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
import clang.cindex
|
||||
from clang.cindex import ExceptionSpecificationKind
|
||||
from .util import get_tu
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import Index, File
|
||||
|
||||
import unittest
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import *
|
||||
import os
|
||||
import unittest
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import LinkageKind
|
||||
from clang.cindex import Cursor
|
||||
from clang.cindex import TranslationUnit
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import Cursor
|
||||
from clang.cindex import File
|
||||
from clang.cindex import SourceLocation
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import TLSKind
|
||||
from clang.cindex import Cursor
|
||||
from clang.cindex import TranslationUnit
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import TokenKind
|
||||
|
||||
import unittest
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from clang.cindex import CursorKind
|
||||
from clang.cindex import Index
|
||||
from clang.cindex import SourceLocation
|
||||
|
@ -1,6 +1,12 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
from contextlib import contextmanager
|
||||
import gc
|
||||
import os
|
||||
import sys
|
||||
import tempfile
|
||||
import unittest
|
||||
|
||||
@ -15,6 +21,8 @@
|
||||
from clang.cindex import TranslationUnit
|
||||
from .util import get_cursor
|
||||
from .util import get_tu
|
||||
from .util import skip_if_no_fspath
|
||||
from .util import str_to_path
|
||||
|
||||
|
||||
kInputsDir = os.path.join(os.path.dirname(__file__), 'INPUTS')
|
||||
@ -31,6 +39,17 @@ def save_tu(tu):
|
||||
yield t.name
|
||||
|
||||
|
||||
@contextmanager
|
||||
def save_tu_pathlike(tu):
|
||||
"""Convenience API to save a TranslationUnit to a file.
|
||||
|
||||
Returns the filename it was saved to.
|
||||
"""
|
||||
with tempfile.NamedTemporaryFile() as t:
|
||||
tu.save(str_to_path(t.name))
|
||||
yield t.name
|
||||
|
||||
|
||||
class TestTranslationUnit(unittest.TestCase):
|
||||
def test_spelling(self):
|
||||
path = os.path.join(kInputsDir, 'hello.cpp')
|
||||
@ -75,15 +94,31 @@ def test_unsaved_files(self):
|
||||
self.assertEqual(spellings[-1], 'y')
|
||||
|
||||
def test_unsaved_files_2(self):
|
||||
try:
|
||||
from StringIO import StringIO
|
||||
except:
|
||||
if sys.version_info.major >= 3:
|
||||
from io import StringIO
|
||||
else:
|
||||
from io import BytesIO as StringIO
|
||||
tu = TranslationUnit.from_source('fake.c', unsaved_files = [
|
||||
('fake.c', StringIO('int x;'))])
|
||||
spellings = [c.spelling for c in tu.cursor.get_children()]
|
||||
self.assertEqual(spellings[-1], 'x')
|
||||
|
||||
@skip_if_no_fspath
|
||||
def test_from_source_accepts_pathlike(self):
|
||||
tu = TranslationUnit.from_source(str_to_path('fake.c'), ['-Iincludes'], unsaved_files = [
|
||||
(str_to_path('fake.c'), """
|
||||
#include "fake.h"
|
||||
int x;
|
||||
int SOME_DEFINE;
|
||||
"""),
|
||||
(str_to_path('includes/fake.h'), """
|
||||
#define SOME_DEFINE y
|
||||
""")
|
||||
])
|
||||
spellings = [c.spelling for c in tu.cursor.get_children()]
|
||||
self.assertEqual(spellings[-2], 'x')
|
||||
self.assertEqual(spellings[-1], 'y')
|
||||
|
||||
def assert_normpaths_equal(self, path1, path2):
|
||||
""" Compares two paths for equality after normalizing them with
|
||||
os.path.normpath
|
||||
@ -130,6 +165,16 @@ def test_save(self):
|
||||
self.assertTrue(os.path.exists(path))
|
||||
self.assertGreater(os.path.getsize(path), 0)
|
||||
|
||||
@skip_if_no_fspath
|
||||
def test_save_pathlike(self):
|
||||
"""Ensure TranslationUnit.save() works with PathLike filename."""
|
||||
|
||||
tu = get_tu('int foo();')
|
||||
|
||||
with save_tu_pathlike(tu) as path:
|
||||
self.assertTrue(os.path.exists(path))
|
||||
self.assertGreater(os.path.getsize(path), 0)
|
||||
|
||||
def test_save_translation_errors(self):
|
||||
"""Ensure that saving to an invalid directory raises."""
|
||||
|
||||
@ -162,6 +207,22 @@ def test_load(self):
|
||||
# Just in case there is an open file descriptor somewhere.
|
||||
del tu2
|
||||
|
||||
@skip_if_no_fspath
|
||||
def test_load_pathlike(self):
|
||||
"""Ensure TranslationUnits can be constructed from saved files -
|
||||
PathLike variant."""
|
||||
tu = get_tu('int foo();')
|
||||
self.assertEqual(len(tu.diagnostics), 0)
|
||||
with save_tu(tu) as path:
|
||||
tu2 = TranslationUnit.from_ast_file(filename=str_to_path(path))
|
||||
self.assertEqual(len(tu2.diagnostics), 0)
|
||||
|
||||
foo = get_cursor(tu2, 'foo')
|
||||
self.assertIsNotNone(foo)
|
||||
|
||||
# Just in case there is an open file descriptor somewhere.
|
||||
del tu2
|
||||
|
||||
def test_index_parse(self):
|
||||
path = os.path.join(kInputsDir, 'hello.cpp')
|
||||
index = Index.create()
|
||||
@ -180,6 +241,19 @@ def test_get_file(self):
|
||||
with self.assertRaises(Exception):
|
||||
f = tu.get_file('foobar.cpp')
|
||||
|
||||
@skip_if_no_fspath
|
||||
def test_get_file_pathlike(self):
|
||||
"""Ensure tu.get_file() works appropriately with PathLike filenames."""
|
||||
|
||||
tu = get_tu('int foo();')
|
||||
|
||||
f = tu.get_file(str_to_path('t.c'))
|
||||
self.assertIsInstance(f, File)
|
||||
self.assertEqual(f.name, 't.c')
|
||||
|
||||
with self.assertRaises(Exception):
|
||||
f = tu.get_file(str_to_path('foobar.cpp'))
|
||||
|
||||
def test_get_source_location(self):
|
||||
"""Ensure tu.get_source_location() works."""
|
||||
|
||||
|
@ -1,3 +1,8 @@
|
||||
import os
|
||||
from clang.cindex import Config
|
||||
if 'CLANG_LIBRARY_PATH' in os.environ:
|
||||
Config.set_library_path(os.environ['CLANG_LIBRARY_PATH'])
|
||||
|
||||
import gc
|
||||
import unittest
|
||||
|
||||
@ -436,3 +441,28 @@ def test_addrspace(self):
|
||||
|
||||
self.assertIsNotNone(testInteger, "Could not find testInteger.")
|
||||
self.assertEqual(testInteger.type.get_address_space(), 2)
|
||||
|
||||
def test_template_arguments(self):
|
||||
source = """
|
||||
class Foo {
|
||||
};
|
||||
template <typename T>
|
||||
class Template {
|
||||
};
|
||||
Template<Foo> instance;
|
||||
int bar;
|
||||
"""
|
||||
tu = get_tu(source, lang='cpp')
|
||||
|
||||
# Varible with a template argument.
|
||||
cursor = get_cursor(tu, 'instance')
|
||||
cursor_type = cursor.type
|
||||
self.assertEqual(cursor.kind, CursorKind.VAR_DECL)
|
||||
self.assertEqual(cursor_type.spelling, 'Template<Foo>')
|
||||
self.assertEqual(cursor_type.get_num_template_arguments(), 1)
|
||||
template_type = cursor_type.get_template_argument_type(0)
|
||||
self.assertEqual(template_type.spelling, 'Foo')
|
||||
|
||||
# Variable without a template argument.
|
||||
cursor = get_cursor(tu, 'bar')
|
||||
self.assertEqual(cursor.get_num_template_arguments(), -1)
|
||||
|
@ -1,5 +1,15 @@
|
||||
# This file provides common utility functions for the test suite.
|
||||
|
||||
import os
|
||||
HAS_FSPATH = hasattr(os, 'fspath')
|
||||
|
||||
if HAS_FSPATH:
|
||||
from pathlib import Path as str_to_path
|
||||
else:
|
||||
str_to_path = None
|
||||
|
||||
import unittest
|
||||
|
||||
from clang.cindex import Cursor
|
||||
from clang.cindex import TranslationUnit
|
||||
|
||||
@ -68,8 +78,13 @@ def get_cursors(source, spelling):
|
||||
return cursors
|
||||
|
||||
|
||||
skip_if_no_fspath = unittest.skipUnless(HAS_FSPATH,
|
||||
"Requires file system path protocol / Python 3.6+")
|
||||
|
||||
__all__ = [
|
||||
'get_cursor',
|
||||
'get_cursors',
|
||||
'get_tu',
|
||||
'skip_if_no_fspath',
|
||||
'str_to_path',
|
||||
]
|
||||
|
@ -1,29 +1,33 @@
|
||||
# This file sets up a CMakeCache for the second stage of a Fuchsia toolchain
|
||||
# build.
|
||||
# This file sets up a CMakeCache for the second stage of a Fuchsia toolchain build.
|
||||
|
||||
set(LLVM_TARGETS_TO_BUILD X86;ARM;AArch64 CACHE STRING "")
|
||||
|
||||
set(PACKAGE_VENDOR Fuchsia CACHE STRING "")
|
||||
|
||||
set(LLVM_INCLUDE_EXAMPLES OFF CACHE BOOL "")
|
||||
set(LLVM_INCLUDE_DOCS OFF CACHE BOOL "")
|
||||
set(LLVM_ENABLE_BACKTRACES OFF CACHE BOOL "")
|
||||
if(NOT APPLE)
|
||||
set(LLVM_ENABLE_LLD ON CACHE BOOL "")
|
||||
endif()
|
||||
set(LLVM_ENABLE_LTO ON CACHE BOOL "")
|
||||
set(LLVM_ENABLE_MODULES ON CACHE BOOL "")
|
||||
set(LLVM_ENABLE_PER_TARGET_RUNTIME_DIR ON CACHE BOOL "")
|
||||
set(LLVM_ENABLE_TERMINFO OFF CACHE BOOL "")
|
||||
set(LLVM_ENABLE_ZLIB ON CACHE BOOL "")
|
||||
set(LLVM_EXTERNALIZE_DEBUGINFO ON CACHE BOOL "")
|
||||
set(CLANG_PLUGIN_SUPPORT OFF CACHE BOOL "")
|
||||
set(LLVM_INCLUDE_EXAMPLES OFF CACHE BOOL "")
|
||||
set(LLVM_INCLUDE_DOCS OFF CACHE BOOL "")
|
||||
|
||||
set(LLVM_ENABLE_LTO ON CACHE BOOL "")
|
||||
set(CLANG_DEFAULT_CXX_STDLIB libc++ CACHE STRING "")
|
||||
if(NOT APPLE)
|
||||
set(LLVM_ENABLE_LLD ON CACHE BOOL "")
|
||||
set(CLANG_DEFAULT_LINKER lld CACHE STRING "")
|
||||
set(CLANG_DEFAULT_OBJCOPY llvm-objcopy CACHE STRING "")
|
||||
endif()
|
||||
set(CLANG_DEFAULT_CXX_STDLIB libc++ CACHE STRING "")
|
||||
set(CLANG_DEFAULT_RTLIB compiler-rt CACHE STRING "")
|
||||
set(CLANG_PLUGIN_SUPPORT OFF CACHE BOOL "")
|
||||
|
||||
set(ENABLE_LINKER_BUILD_ID ON CACHE BOOL "")
|
||||
set(ENABLE_X86_RELAX_RELOCATIONS ON CACHE BOOL "")
|
||||
|
||||
set(LLVM_ENABLE_ASSERTIONS ON CACHE BOOL "")
|
||||
set(CMAKE_BUILD_TYPE RelWithDebInfo CACHE STRING "")
|
||||
set(CMAKE_C_FLAGS_RELWITHDEBINFO "-O3 -gline-tables-only -DNDEBUG" CACHE STRING "")
|
||||
set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "-O3 -gline-tables-only -DNDEBUG" CACHE STRING "")
|
||||
@ -31,39 +35,50 @@ set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "-O3 -gline-tables-only -DNDEBUG" CACHE STRIN
|
||||
if(APPLE)
|
||||
list(APPEND BUILTIN_TARGETS "default")
|
||||
list(APPEND RUNTIME_TARGETS "default")
|
||||
elseif(UNIX)
|
||||
foreach(target i386;x86_64;armhf;aarch64)
|
||||
if(LINUX_${target}_SYSROOT)
|
||||
# Set the per-target builtins options.
|
||||
list(APPEND BUILTIN_TARGETS "${target}-linux-gnu")
|
||||
set(BUILTINS_${target}-linux-gnu_CMAKE_SYSTEM_NAME Linux CACHE STRING "")
|
||||
set(BUILTINS_${target}-linux-gnu_CMAKE_BUILD_TYPE Release CACHE STRING "")
|
||||
set(BUILTINS_${target}-linux-gnu_CMAKE_SYSROOT ${LINUX_${target}_SYSROOT} CACHE STRING "")
|
||||
|
||||
# Set the per-target runtimes options.
|
||||
list(APPEND RUNTIME_TARGETS "${target}-linux-gnu")
|
||||
set(RUNTIMES_${target}-linux-gnu_CMAKE_SYSTEM_NAME Linux CACHE STRING "")
|
||||
set(RUNTIMES_${target}-linux-gnu_CMAKE_BUILD_TYPE Release CACHE STRING "")
|
||||
set(RUNTIMES_${target}-linux-gnu_CMAKE_SYSROOT ${LINUX_${target}_SYSROOT} CACHE STRING "")
|
||||
set(RUNTIMES_${target}-linux-gnu_LLVM_ENABLE_ASSERTIONS ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_LIBUNWIND_ENABLE_SHARED OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_LIBUNWIND_USE_COMPILER_RT ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_LIBUNWIND_INSTALL_LIBRARY OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_LIBCXXABI_USE_COMPILER_RT ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_LIBCXXABI_ENABLE_SHARED OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_LIBCXXABI_USE_LLVM_UNWINDER ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_LIBCXXABI_ENABLE_STATIC_UNWINDER ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_LIBCXXABI_INSTALL_LIBRARY OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_LIBCXX_ENABLE_SHARED OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_SANITIZER_CXX_ABI "libc++" CACHE STRING "")
|
||||
set(RUNTIMES_${target}-linux-gnu_SANITIZER_CXX_ABI_INTREE ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-linux-gnu_COMPILER_RT_USE_BUILTINS_LIBRARY ON CACHE BOOL "")
|
||||
endif()
|
||||
endforeach()
|
||||
set(COMPILER_RT_ENABLE_IOS OFF CACHE BOOL "")
|
||||
set(COMPILER_RT_ENABLE_TVOS OFF CACHE BOOL "")
|
||||
set(COMPILER_RT_ENABLE_WATCHOS OFF CACHE BOOL "")
|
||||
endif()
|
||||
|
||||
foreach(target aarch64-linux-gnu;armv7-linux-gnueabihf;i386-linux-gnu;x86_64-linux-gnu)
|
||||
if(LINUX_${target}_SYSROOT)
|
||||
# Set the per-target builtins options.
|
||||
list(APPEND BUILTIN_TARGETS "${target}")
|
||||
set(BUILTINS_${target}_CMAKE_SYSTEM_NAME Linux CACHE STRING "")
|
||||
set(BUILTINS_${target}_CMAKE_BUILD_TYPE Release CACHE STRING "")
|
||||
set(BUILTINS_${target}_CMAKE_SYSROOT ${LINUX_${target}_SYSROOT} CACHE STRING "")
|
||||
set(BUILTINS_${target}_CMAKE_SHARED_LINKER_FLAGS "-fuse-ld=lld" CACHE STRING "")
|
||||
set(BUILTINS_${target}_CMAKE_MODULE_LINKER_FLAGS "-fuse-ld=lld" CACHE STRING "")
|
||||
set(BUILTINS_${target}_CMAKE_EXE_LINKER_FLAG "-fuse-ld=lld" CACHE STRING "")
|
||||
|
||||
# Set the per-target runtimes options.
|
||||
list(APPEND RUNTIME_TARGETS "${target}")
|
||||
set(RUNTIMES_${target}_CMAKE_SYSTEM_NAME Linux CACHE STRING "")
|
||||
set(RUNTIMES_${target}_CMAKE_BUILD_TYPE Release CACHE STRING "")
|
||||
set(RUNTIMES_${target}_CMAKE_SYSROOT ${LINUX_${target}_SYSROOT} CACHE STRING "")
|
||||
set(RUNTIMES_${target}_CMAKE_SHARED_LINKER_FLAGS "-fuse-ld=lld" CACHE STRING "")
|
||||
set(RUNTIMES_${target}_CMAKE_MODULE_LINKER_FLAGS "-fuse-ld=lld" CACHE STRING "")
|
||||
set(RUNTIMES_${target}_CMAKE_EXE_LINKER_FLAGS "-fuse-ld=lld" CACHE STRING "")
|
||||
set(RUNTIMES_${target}_LLVM_ENABLE_ASSERTIONS ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBUNWIND_ENABLE_SHARED OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBUNWIND_USE_COMPILER_RT ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBUNWIND_INSTALL_LIBRARY OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXXABI_USE_COMPILER_RT ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXXABI_ENABLE_SHARED OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXXABI_USE_LLVM_UNWINDER ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXXABI_ENABLE_STATIC_UNWINDER ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXXABI_INSTALL_LIBRARY OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXX_ENABLE_SHARED OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXX_ABI_VERSION 2 CACHE STRING "")
|
||||
set(RUNTIMES_${target}_SANITIZER_CXX_ABI "libc++" CACHE STRING "")
|
||||
set(RUNTIMES_${target}_SANITIZER_CXX_ABI_INTREE ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_COMPILER_RT_USE_BUILTINS_LIBRARY ON CACHE BOOL "")
|
||||
endif()
|
||||
endforeach()
|
||||
|
||||
if(FUCHSIA_SDK)
|
||||
set(FUCHSIA_aarch64_NAME arm64)
|
||||
set(FUCHSIA_x86_64_NAME x64)
|
||||
@ -78,25 +93,25 @@ if(FUCHSIA_SDK)
|
||||
list(APPEND BUILTIN_TARGETS "${target}-fuchsia")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_SYSTEM_NAME Fuchsia CACHE STRING "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_BUILD_TYPE Release CACHE STRING "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_ASM_FLAGS ${FUCHSIA_${target}_COMPILER_FLAGS} CACHE PATH "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_C_FLAGS ${FUCHSIA_${target}_COMPILER_FLAGS} CACHE PATH "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_CXX_FLAGS ${FUCHSIA_${target}_COMPILER_FLAGS} CACHE PATH "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_SHARED_LINKER_FLAGS ${FUCHSIA_${target}_LINKER_FLAGS} CACHE PATH "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_MODULE_LINKER_FLAGS ${FUCHSIA_${target}_LINKER_FLAGS} CACHE PATH "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_EXE_LINKER_FLAGS ${FUCHSIA_${target}_LINKER_FLAGS} CACHE PATH "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_ASM_FLAGS ${FUCHSIA_${target}_COMPILER_FLAGS} CACHE STRING "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_C_FLAGS ${FUCHSIA_${target}_COMPILER_FLAGS} CACHE STRING "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_CXX_FLAGS ${FUCHSIA_${target}_COMPILER_FLAGS} CACHE STRING "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_SHARED_LINKER_FLAGS ${FUCHSIA_${target}_LINKER_FLAGS} CACHE STRING "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_MODULE_LINKER_FLAGS ${FUCHSIA_${target}_LINKER_FLAGS} CACHE STRING "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_EXE_LINKER_FLAGS ${FUCHSIA_${target}_LINKER_FLAGS} CACHE STRING "")
|
||||
set(BUILTINS_${target}-fuchsia_CMAKE_SYSROOT ${FUCHSIA_${target}_SYSROOT} CACHE PATH "")
|
||||
|
||||
# Set the per-target runtimes options.
|
||||
list(APPEND RUNTIME_TARGETS "${target}-fuchsia")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_SYSTEM_NAME Fuchsia CACHE STRING "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_BUILD_TYPE Release CACHE STRING "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_BUILD_WITH_INSTALL_RPATH ON CACHE STRING "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_ASM_FLAGS ${FUCHSIA_${target}_COMPILER_FLAGS} CACHE PATH "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_C_FLAGS ${FUCHSIA_${target}_COMPILER_FLAGS} CACHE PATH "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_CXX_FLAGS ${FUCHSIA_${target}_COMPILER_FLAGS} CACHE PATH "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_SHARED_LINKER_FLAGS ${FUCHSIA_${target}_LINKER_FLAGS} CACHE PATH "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_MODULE_LINKER_FLAGS ${FUCHSIA_${target}_LINKER_FLAGS} CACHE PATH "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_EXE_LINKER_FLAGS ${FUCHSIA_${target}_LINKER_FLAGS} CACHE PATH "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_BUILD_WITH_INSTALL_RPATH ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_ASM_FLAGS ${FUCHSIA_${target}_COMPILER_FLAGS} CACHE STRING "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_C_FLAGS ${FUCHSIA_${target}_COMPILER_FLAGS} CACHE STRING "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_CXX_FLAGS ${FUCHSIA_${target}_COMPILER_FLAGS} CACHE STRING "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_SHARED_LINKER_FLAGS ${FUCHSIA_${target}_LINKER_FLAGS} CACHE STRING "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_MODULE_LINKER_FLAGS ${FUCHSIA_${target}_LINKER_FLAGS} CACHE STRING "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_EXE_LINKER_FLAGS ${FUCHSIA_${target}_LINKER_FLAGS} CACHE STRING "")
|
||||
set(RUNTIMES_${target}-fuchsia_CMAKE_SYSROOT ${FUCHSIA_${target}_SYSROOT} CACHE PATH "")
|
||||
set(RUNTIMES_${target}-fuchsia_LLVM_ENABLE_ASSERTIONS ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-fuchsia_LIBUNWIND_USE_COMPILER_RT ON CACHE BOOL "")
|
||||
@ -109,6 +124,8 @@ if(FUCHSIA_SDK)
|
||||
set(RUNTIMES_${target}-fuchsia_LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-fuchsia_LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-fuchsia_LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-fuchsia_LIBCXX_HERMETIC_STATIC_LIBRARY ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}-fuchsia_LIBCXX_ABI_VERSION 2 CACHE STRING "")
|
||||
endforeach()
|
||||
|
||||
set(LLVM_RUNTIME_SANITIZERS "Address" CACHE STRING "")
|
||||
@ -127,6 +144,7 @@ set(LLVM_TOOLCHAIN_TOOLS
|
||||
llvm-cov
|
||||
llvm-cxxfilt
|
||||
llvm-dwarfdump
|
||||
llvm-dwp
|
||||
llvm-lib
|
||||
llvm-nm
|
||||
llvm-objcopy
|
||||
@ -138,6 +156,7 @@ set(LLVM_TOOLCHAIN_TOOLS
|
||||
llvm-size
|
||||
llvm-strip
|
||||
llvm-symbolizer
|
||||
llvm-xray
|
||||
opt
|
||||
sancov
|
||||
CACHE STRING "")
|
||||
@ -147,6 +166,7 @@ set(LLVM_DISTRIBUTION_COMPONENTS
|
||||
libclang
|
||||
lld
|
||||
LTO
|
||||
clang-apply-replacements
|
||||
clang-format
|
||||
clang-headers
|
||||
clang-include-fixer
|
||||
|
@ -1,30 +1,30 @@
|
||||
# This file sets up a CMakeCache for a Fuchsia toolchain build.
|
||||
|
||||
set(LLVM_TARGETS_TO_BUILD Native CACHE STRING "")
|
||||
set(LLVM_TARGETS_TO_BUILD X86;ARM;AArch64 CACHE STRING "")
|
||||
|
||||
set(PACKAGE_VENDOR Fuchsia CACHE STRING "")
|
||||
|
||||
set(LLVM_INCLUDE_EXAMPLES OFF CACHE BOOL "")
|
||||
set(LLVM_INCLUDE_TESTS OFF CACHE BOOL "")
|
||||
set(LLVM_INCLUDE_DOCS OFF CACHE BOOL "")
|
||||
set(LLVM_ENABLE_BACKTRACES OFF CACHE BOOL "")
|
||||
set(LLVM_ENABLE_PER_TARGET_RUNTIME_DIR ON CACHE BOOL "")
|
||||
set(LLVM_ENABLE_TERMINFO OFF CACHE BOOL "")
|
||||
set(LLVM_ENABLE_ZLIB OFF CACHE BOOL "")
|
||||
set(CLANG_INCLUDE_TESTS OFF CACHE BOOL "")
|
||||
set(LLVM_INCLUDE_EXAMPLES OFF CACHE BOOL "")
|
||||
set(LLVM_INCLUDE_DOCS OFF CACHE BOOL "")
|
||||
|
||||
set(CLANG_DEFAULT_CXX_STDLIB libc++ CACHE STRING "")
|
||||
if(NOT APPLE)
|
||||
set(CLANG_DEFAULT_LINKER lld CACHE STRING "")
|
||||
set(CLANG_DEFAULT_OBJCOPY llvm-objcopy CACHE STRING "")
|
||||
endif()
|
||||
set(CLANG_DEFAULT_RTLIB compiler-rt CACHE STRING "")
|
||||
set(CLANG_PLUGIN_SUPPORT OFF CACHE BOOL "")
|
||||
|
||||
set(ENABLE_LINKER_BUILD_ID ON CACHE BOOL "")
|
||||
set(ENABLE_X86_RELAX_RELOCATIONS ON CACHE BOOL "")
|
||||
|
||||
set(LLVM_ENABLE_ASSERTIONS ON CACHE BOOL "")
|
||||
set(CMAKE_BUILD_TYPE Release CACHE STRING "")
|
||||
|
||||
set(BOOTSTRAP_LLVM_ENABLE_LTO ON CACHE BOOL "")
|
||||
if(NOT APPLE)
|
||||
set(BOOTSTRAP_LLVM_ENABLE_LLD ON CACHE BOOL "")
|
||||
endif()
|
||||
|
||||
set(CLANG_DEFAULT_CXX_STDLIB libc++ CACHE STRING "")
|
||||
set(CLANG_DEFAULT_RTLIB compiler-rt CACHE STRING "")
|
||||
|
||||
if(APPLE)
|
||||
set(COMPILER_RT_ENABLE_IOS OFF CACHE BOOL "")
|
||||
set(COMPILER_RT_ENABLE_TVOS OFF CACHE BOOL "")
|
||||
@ -43,18 +43,57 @@ elseif(UNIX)
|
||||
set(LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
|
||||
endif()
|
||||
|
||||
if(BOOTSTRAP_CMAKE_SYSTEM_NAME)
|
||||
set(target "${BOOTSTRAP_CMAKE_CXX_COMPILER_TARGET}")
|
||||
if(STAGE2_LINUX_${target}_SYSROOT)
|
||||
set(BUILTINS_${target}_CMAKE_SYSTEM_NAME Linux CACHE STRING "")
|
||||
set(BUILTINS_${target}_CMAKE_BUILD_TYPE Release CACHE STRING "")
|
||||
set(BUILTINS_${target}_CMAKE_SYSROOT ${STAGE2_LINUX_${target}_SYSROOT} CACHE STRING "")
|
||||
set(LLVM_BUILTIN_TARGETS "${target}" CACHE STRING "")
|
||||
|
||||
set(RUNTIMES_${target}_CMAKE_SYSTEM_NAME Linux CACHE STRING "")
|
||||
set(RUNTIMES_${target}_CMAKE_BUILD_TYPE Release CACHE STRING "")
|
||||
set(RUNTIMES_${target}_CMAKE_SYSROOT ${STAGE2_LINUX_${target}_SYSROOT} CACHE STRING "")
|
||||
set(RUNTIMES_${target}_LLVM_ENABLE_ASSERTIONS ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBUNWIND_ENABLE_SHARED OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBUNWIND_USE_COMPILER_RT ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBUNWIND_INSTALL_LIBRARY OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXXABI_USE_COMPILER_RT ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXXABI_ENABLE_SHARED OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXXABI_USE_LLVM_UNWINDER ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXXABI_ENABLE_STATIC_UNWINDER ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXXABI_INSTALL_LIBRARY OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXX_ENABLE_SHARED OFF CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_LIBCXX_ABI_VERSION 2 CACHE STRING "")
|
||||
set(RUNTIMES_${target}_SANITIZER_CXX_ABI "libc++" CACHE STRING "")
|
||||
set(RUNTIMES_${target}_SANITIZER_CXX_ABI_INTREE ON CACHE BOOL "")
|
||||
set(RUNTIMES_${target}_COMPILER_RT_USE_BUILTINS_LIBRARY ON CACHE BOOL "")
|
||||
set(LLVM_RUNTIME_TARGETS "${target}" CACHE STRING "")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
set(BOOTSTRAP_LLVM_ENABLE_LTO ON CACHE BOOL "")
|
||||
if(NOT APPLE)
|
||||
set(BOOTSTRAP_LLVM_ENABLE_LLD ON CACHE BOOL "")
|
||||
endif()
|
||||
|
||||
set(CLANG_BOOTSTRAP_TARGETS
|
||||
check-all
|
||||
check-llvm
|
||||
check-clang
|
||||
check-lld
|
||||
llvm-config
|
||||
test-suite
|
||||
test-depends
|
||||
llvm-test-depends
|
||||
clang-test-depends
|
||||
lld-test-depends
|
||||
distribution
|
||||
install-distribution
|
||||
install-distribution-stripped
|
||||
install-distribution-toolchain
|
||||
clang CACHE STRING "")
|
||||
|
||||
get_cmake_property(variableNames VARIABLES)
|
||||
|
@ -131,6 +131,7 @@ macro(add_clang_tool name)
|
||||
endif()
|
||||
|
||||
add_clang_executable(${name} ${ARGN})
|
||||
add_dependencies(${name} clang-headers)
|
||||
|
||||
if (CLANG_BUILD_TOOLS)
|
||||
if(${name} IN_LIST LLVM_DISTRIBUTION_COMPONENTS OR
|
||||
|
@ -1,13 +1,36 @@
|
||||
# Looking for Z3 in CLANG_ANALYZER_Z3_INSTALL_DIR
|
||||
find_path(Z3_INCLUDE_DIR NAMES z3.h
|
||||
NO_DEFAULT_PATH
|
||||
PATHS ${CLANG_ANALYZER_Z3_INSTALL_DIR}/include
|
||||
PATH_SUFFIXES libz3 z3
|
||||
)
|
||||
|
||||
find_library(Z3_LIBRARIES NAMES z3 libz3
|
||||
NO_DEFAULT_PATH
|
||||
PATHS ${CLANG_ANALYZER_Z3_INSTALL_DIR}
|
||||
PATH_SUFFIXES lib bin
|
||||
)
|
||||
|
||||
find_program(Z3_EXECUTABLE z3
|
||||
NO_DEFAULT_PATH
|
||||
PATHS ${CLANG_ANALYZER_Z3_INSTALL_DIR}
|
||||
PATH_SUFFIXES bin
|
||||
)
|
||||
|
||||
# If Z3 has not been found in CLANG_ANALYZER_Z3_INSTALL_DIR look in the default directories
|
||||
find_path(Z3_INCLUDE_DIR NAMES z3.h
|
||||
PATH_SUFFIXES libz3 z3
|
||||
)
|
||||
|
||||
find_library(Z3_LIBRARIES NAMES z3 libz3
|
||||
PATH_SUFFIXES lib bin
|
||||
)
|
||||
|
||||
find_program(Z3_EXECUTABLE z3)
|
||||
find_program(Z3_EXECUTABLE z3
|
||||
PATH_SUFFIXES bin
|
||||
)
|
||||
|
||||
if(Z3_INCLUDE_DIR AND Z3_EXECUTABLE)
|
||||
if(Z3_INCLUDE_DIR AND Z3_LIBRARIES AND Z3_EXECUTABLE)
|
||||
execute_process (COMMAND ${Z3_EXECUTABLE} -version
|
||||
OUTPUT_VARIABLE libz3_version_str
|
||||
ERROR_QUIET
|
||||
|
@ -24,7 +24,7 @@ Typical slowdown introduced by AddressSanitizer is **2x**.
|
||||
How to build
|
||||
============
|
||||
|
||||
Build LLVM/Clang with `CMake <http://llvm.org/docs/CMake.html>`_.
|
||||
Build LLVM/Clang with `CMake <https://llvm.org/docs/CMake.html>`_.
|
||||
|
||||
Usage
|
||||
=====
|
||||
@ -265,7 +265,7 @@ Limitations
|
||||
* On 64-bit platforms AddressSanitizer maps (but not reserves) 16+ Terabytes of
|
||||
virtual address space. This means that tools like ``ulimit`` may not work as
|
||||
usually expected.
|
||||
* Static linking is not supported.
|
||||
* Static linking of executables is not supported.
|
||||
|
||||
Supported Platforms
|
||||
===================
|
||||
@ -278,6 +278,7 @@ AddressSanitizer is supported on:
|
||||
* Android ARM
|
||||
* NetBSD i386/x86\_64
|
||||
* FreeBSD i386/x86\_64 (tested on FreeBSD 11-current)
|
||||
* Windows 8.1+ (i386/x86\_64)
|
||||
|
||||
Ports to various other platforms are in progress.
|
||||
|
||||
@ -288,6 +289,9 @@ AddressSanitizer is fully functional on supported platforms starting from LLVM
|
||||
3.1. The test suite is integrated into CMake build and can be run with ``make
|
||||
check-asan`` command.
|
||||
|
||||
The Windows port is functional and is used by Chrome and Firefox, but it is not
|
||||
as well supported as the other ports.
|
||||
|
||||
More Information
|
||||
================
|
||||
|
||||
|
@ -1734,20 +1734,78 @@ A program is ill-formed if it refers to the ``NSAutoreleasePool`` class.
|
||||
rest of the language. Not draining the pool during an unwind is apparently
|
||||
required by the Objective-C exceptions implementation.
|
||||
|
||||
.. _arc.misc.externally_retained:
|
||||
|
||||
Externally-Retained Variables
|
||||
-----------------------------
|
||||
|
||||
In some situations, variables with strong ownership are considered
|
||||
externally-retained by the implementation. This means that the variable is
|
||||
retained elsewhere, and therefore the implementation can elide retaining and
|
||||
releasing its value. Such a variable is implicitly ``const`` for safety. In
|
||||
contrast with ``__unsafe_unretained``, an externally-retained variable still
|
||||
behaves as a strong variable outside of initialization and destruction. For
|
||||
instance, when an externally-retained variable is captured in a block the value
|
||||
of the variable is retained and released on block capture and destruction. It
|
||||
also affects C++ features such as lambda capture, ``decltype``, and template
|
||||
argument deduction.
|
||||
|
||||
Implicitly, the implementation assumes that the :ref:`self parameter in a
|
||||
non-init method <arc.misc.self>` and the :ref:`variable in a for-in loop
|
||||
<arc.misc.enumeration>` are externally-retained.
|
||||
|
||||
Externally-retained semantics can also be opted into with the
|
||||
``objc_externally_retained`` attribute. This attribute can apply to strong local
|
||||
variables, functions, methods, or blocks:
|
||||
|
||||
.. code-block:: objc
|
||||
|
||||
@class WobbleAmount;
|
||||
|
||||
@interface Widget : NSObject
|
||||
-(void)wobble:(WobbleAmount *)amount;
|
||||
@end
|
||||
|
||||
@implementation Widget
|
||||
|
||||
-(void)wobble:(WobbleAmount *)amount
|
||||
__attribute__((objc_externally_retained)) {
|
||||
// 'amount' and 'alias' aren't retained on entry, nor released on exit.
|
||||
__attribute__((objc_externally_retained)) WobbleAmount *alias = amount;
|
||||
}
|
||||
@end
|
||||
|
||||
Annotating a function with this attribute makes every parameter with strong
|
||||
retainable object pointer type externally-retained, unless the variable was
|
||||
explicitly qualified with ``__strong``. For instance, ``first_param`` is
|
||||
externally-retained (and therefore ``const``) below, but not ``second_param``:
|
||||
|
||||
.. code-block:: objc
|
||||
|
||||
__attribute__((objc_externally_retained))
|
||||
void f(NSArray *first_param, __strong NSArray *second_param) {
|
||||
// ...
|
||||
}
|
||||
|
||||
You can test if your compiler has support for ``objc_externally_retained`` with
|
||||
``__has_attribute``:
|
||||
|
||||
.. code-block:: objc
|
||||
|
||||
#if __has_attribute(objc_externally_retained)
|
||||
// Use externally retained...
|
||||
#endif
|
||||
|
||||
.. _arc.misc.self:
|
||||
|
||||
``self``
|
||||
--------
|
||||
|
||||
The ``self`` parameter variable of an Objective-C method is never actually
|
||||
retained by the implementation. It is undefined behavior, or at least
|
||||
dangerous, to cause an object to be deallocated during a message send to that
|
||||
object.
|
||||
|
||||
To make this safe, for Objective-C instance methods ``self`` is implicitly
|
||||
``const`` unless the method is in the :ref:`init family
|
||||
<arc.family.semantics.init>`. Further, ``self`` is **always** implicitly
|
||||
``const`` within a class method.
|
||||
The ``self`` parameter variable of an non-init Objective-C method is considered
|
||||
:ref:`externally-retained <arc.misc.externally_retained>` by the implementation.
|
||||
It is undefined behavior, or at least dangerous, to cause an object to be
|
||||
deallocated during a message send to that object. In an init method, ``self``
|
||||
follows the :ref:``init family rules <arc.family.semantics.init>``.
|
||||
|
||||
.. admonition:: Rationale
|
||||
|
||||
@ -1758,9 +1816,9 @@ To make this safe, for Objective-C instance methods ``self`` is implicitly
|
||||
without this retain and release. Since it's extremely uncommon to actually
|
||||
do so, even unintentionally, and since there's no natural way for the
|
||||
programmer to remove this retain/release pair otherwise (as there is for
|
||||
other parameters by, say, making the variable ``__unsafe_unretained``), we
|
||||
chose to make this optimizing assumption and shift some amount of risk to the
|
||||
user.
|
||||
other parameters by, say, making the variable ``objc_externally_retained`` or
|
||||
qualifying it with ``__unsafe_unretained``), we chose to make this optimizing
|
||||
assumption and shift some amount of risk to the user.
|
||||
|
||||
.. _arc.misc.enumeration:
|
||||
|
||||
@ -1769,8 +1827,9 @@ Fast enumeration iteration variables
|
||||
|
||||
If a variable is declared in the condition of an Objective-C fast enumeration
|
||||
loop, and the variable has no explicit ownership qualifier, then it is
|
||||
qualified with ``const __strong`` and objects encountered during the
|
||||
enumeration are not actually retained.
|
||||
implicitly :ref:`externally-retained <arc.misc.externally_retained>` so that
|
||||
objects encountered during the enumeration are not actually retained and
|
||||
released.
|
||||
|
||||
.. admonition:: Rationale
|
||||
|
||||
@ -2284,8 +2343,8 @@ block exactly as if it had been sent the ``retain`` message.
|
||||
|
||||
.. _arc.runtime.objc_storeStrong:
|
||||
|
||||
``id objc_storeStrong(id *object, id value);``
|
||||
----------------------------------------------
|
||||
``void objc_storeStrong(id *object, id value);``
|
||||
------------------------------------------------
|
||||
|
||||
*Precondition:* ``object`` is a valid pointer to a ``__strong`` object which is
|
||||
adequately aligned for a pointer. ``value`` is null or a pointer to a valid
|
||||
|
@ -1 +1 @@
|
||||
*NOTE* This document has moved to http://clang.llvm.org/docs/Block-ABI-Apple.html.
|
||||
*NOTE* This document has moved to https://clang.llvm.org/docs/Block-ABI-Apple.html.
|
||||
|
@ -36,7 +36,7 @@ Treat source input files as Objective-C inputs
|
||||
|
||||
Treat source input files as Objective-C++ inputs
|
||||
|
||||
.. option:: -Qn
|
||||
.. option:: -Qn, -fno-ident
|
||||
|
||||
Do not emit metadata containing compiler name and version
|
||||
|
||||
@ -44,7 +44,7 @@ Do not emit metadata containing compiler name and version
|
||||
|
||||
Don't emit warning for unused driver arguments
|
||||
|
||||
.. option:: -Qy
|
||||
.. option:: -Qy, -fident
|
||||
|
||||
Emit metadata containing compiler name and version
|
||||
|
||||
@ -158,7 +158,7 @@ Compile CUDA code for host only. Has no effect on non-CUDA compilations.
|
||||
|
||||
.. option:: --cuda-include-ptx=<arg>, --no-cuda-include-ptx=<arg>
|
||||
|
||||
Include PTX for the follwing GPU architecture (e.g. sm\_35) or 'all'. May be specified more than once.
|
||||
Include PTX for the following GPU architecture (e.g. sm\_35) or 'all'. May be specified more than once.
|
||||
|
||||
.. option:: --cuda-noopt-device-debug, --no-cuda-noopt-device-debug
|
||||
|
||||
@ -214,9 +214,13 @@ Flush denormal floating point values to zero in CUDA device mode.
|
||||
|
||||
Generate relocatable device code, also known as separate compilation mode.
|
||||
|
||||
.. option:: -fcuda-short-ptr, -fno-cuda-short-ptr
|
||||
|
||||
Use 32-bit pointers for accessing const/local/shared address spaces.
|
||||
|
||||
.. option:: -ffixed-r19
|
||||
|
||||
Reserve the r19 register (Hexagon only)
|
||||
Reserve register r19 (Hexagon only)
|
||||
|
||||
.. option:: -fheinous-gnu-extensions
|
||||
|
||||
@ -260,6 +264,10 @@ Display available options
|
||||
|
||||
Display help for hidden options
|
||||
|
||||
.. option:: --hip-link
|
||||
|
||||
Link clang-offload-bundler bundles for HIP
|
||||
|
||||
.. option:: -image\_base <arg>
|
||||
|
||||
.. option:: -index-header-map
|
||||
@ -452,6 +460,10 @@ Use pipes between commands, when possible
|
||||
|
||||
.. option:: --print-diagnostic-categories
|
||||
|
||||
.. option:: -print-effective-triple, --print-effective-triple
|
||||
|
||||
Print the effective target triple
|
||||
|
||||
.. option:: -print-file-name=<file>, --print-file-name=<file>, --print-file-name <arg>
|
||||
|
||||
Print the full library path of <file>
|
||||
@ -480,6 +492,10 @@ Print the resource directory pathname
|
||||
|
||||
Print the paths used for finding libraries and programs
|
||||
|
||||
.. option:: -print-target-triple, --print-target-triple
|
||||
|
||||
Print the normalized target triple
|
||||
|
||||
.. option:: -private\_bundle
|
||||
|
||||
.. option:: -pthread, -no-pthread
|
||||
@ -558,6 +574,8 @@ Serialize compiler diagnostics to a file
|
||||
|
||||
.. option:: -shared-libsan, -shared-libasan
|
||||
|
||||
Dynamically link the sanitizer runtime
|
||||
|
||||
.. option:: -single\_module
|
||||
|
||||
.. option:: -specs=<arg>, --specs=<arg>
|
||||
@ -568,6 +586,8 @@ Serialize compiler diagnostics to a file
|
||||
|
||||
.. option:: -static-libsan
|
||||
|
||||
Statically link the sanitizer runtime
|
||||
|
||||
.. option:: -static-libstdc++
|
||||
|
||||
.. option:: -std-default=<arg>
|
||||
@ -712,6 +732,12 @@ Attempt to match the ABI of Clang <version>
|
||||
|
||||
Treat each comma separated argument in <arg> as a documentation comment block command
|
||||
|
||||
.. option:: -fcomplete-member-pointers, -fno-complete-member-pointers
|
||||
|
||||
Require member pointer base types to be complete if they would be significant under the Microsoft ABI
|
||||
|
||||
.. option:: -fcrash-diagnostics-dir=<arg>
|
||||
|
||||
.. option:: -fdeclspec, -fno-declspec
|
||||
|
||||
Allow \_\_declspec as a keyword
|
||||
@ -746,7 +772,7 @@ Enables an experimental new pass manager in LLVM.
|
||||
|
||||
.. option:: -ffine-grained-bitfield-accesses, -fno-fine-grained-bitfield-accesses
|
||||
|
||||
Use separate accesses for bitfields with legal widths and alignments.
|
||||
Use separate accesses for consecutive bitfield runs with legal widths and alignments.
|
||||
|
||||
.. option:: -finline-functions, -fno-inline-functions
|
||||
|
||||
@ -766,6 +792,16 @@ Don't use blacklist file for sanitizers
|
||||
|
||||
.. option:: -fparse-all-comments
|
||||
|
||||
.. option:: -frecord-command-line, -frecord-gcc-switches, -fno-record-command-line, -fno-record-gcc-switches
|
||||
|
||||
Generate a section named ".GCC.command.line" containing the clang driver
|
||||
command-line. After linking, the section may contain multiple command lines,
|
||||
which will be individually terminated by null bytes. Separate arguments within
|
||||
a command line are combined with spaces; spaces and backslashes within an
|
||||
argument are escaped with backslashes. This format differs from the format of
|
||||
the equivalent section produced by GCC with the -frecord-gcc-switches flag.
|
||||
This option is currently only supported on ELF targets.
|
||||
|
||||
.. option:: -fsanitize-address-field-padding=<arg>
|
||||
|
||||
Level of field padding for AddressSanitizer
|
||||
@ -774,9 +810,15 @@ Level of field padding for AddressSanitizer
|
||||
|
||||
Enable linker dead stripping of globals in AddressSanitizer
|
||||
|
||||
.. option:: -fsanitize-address-poison-class-member-array-new-cookie, -fno-sanitize-address-poison-class-member-array-new-cookie
|
||||
.. option:: -fsanitize-address-use-odr-indicator, -fno-sanitize-address-use-odr-indicator
|
||||
|
||||
Enable poisoning array cookies when using class member operator new\[\] in AddressSanitizer
|
||||
Enable ODR indicator globals to avoid false ODR violation reports in partially sanitized programs at the cost of an increase in binary size
|
||||
|
||||
.. option:: -fsanitize-address-poison-custom-array-cookie, -fno-sanitize-address-poison-custom-array-cookie
|
||||
|
||||
Enable "poisoning" array cookies when allocating arrays with a custom operator new\[\] in Address Sanitizer, preventing accesses to the cookies from user code. An array cookie is a small implementation-defined header added to certain array allocations to record metadata such as the length of the array. Accesses to array cookies from user code are technically allowed by the standard but are more likely to be the result of an out-of-bounds array access.
|
||||
|
||||
An operator new\[\] is "custom" if it is not one of the allocation functions provided by the C++ standard library. Array cookies from non-custom allocation functions are always poisoned.
|
||||
|
||||
.. option:: -fsanitize-address-use-after-scope, -fno-sanitize-address-use-after-scope
|
||||
|
||||
@ -854,6 +896,10 @@ Strip (or keep only, if negative) a given number of path components when emittin
|
||||
|
||||
Turn on runtime checks for various forms of undefined or suspicious behavior. See user manual for available checks
|
||||
|
||||
.. option:: -moutline, -mno-outline
|
||||
|
||||
Enable function outlining (AArch64 only)
|
||||
|
||||
.. option:: --param <arg>, --param=<arg>
|
||||
|
||||
.. option:: -std=<arg>, --std=<arg>, --std <arg>
|
||||
@ -1151,6 +1197,10 @@ Target-independent compilation options
|
||||
|
||||
.. option:: -faccess-control, -fno-access-control
|
||||
|
||||
.. option:: -faddrsig, -fno-addrsig
|
||||
|
||||
Emit an address-significance table
|
||||
|
||||
.. option:: -falign-functions, -fno-align-functions
|
||||
|
||||
.. program:: clang1
|
||||
@ -1223,12 +1273,20 @@ Accept non-standard constructs supported by the Borland compiler
|
||||
|
||||
Load the clang builtins module map file.
|
||||
|
||||
.. option:: -fc++-static-destructors, -fno-c++-static-destructors
|
||||
|
||||
Enable C++ static destructor registration (the default)
|
||||
|
||||
.. option:: -fcaret-diagnostics, -fno-caret-diagnostics
|
||||
|
||||
.. option:: -fcf-protection=<arg>, -fcf-protection (equivalent to -fcf-protection=full)
|
||||
|
||||
Instrument control-flow architecture protection. Options: return, branch, full, none.
|
||||
|
||||
.. option:: -fchar8\_t, -fno-char8\_t
|
||||
|
||||
Enable C++ builtin type char8\_t
|
||||
|
||||
.. option:: -fclasspath=<arg>, --CLASSPATH <arg>, --CLASSPATH=<arg>, --classpath <arg>, --classpath=<arg>
|
||||
|
||||
.. option:: -fcolor-diagnostics, -fno-color-diagnostics
|
||||
@ -1293,6 +1351,10 @@ Place debug types in their own section (ELF Only)
|
||||
|
||||
Parse templated function definitions at the end of the translation unit
|
||||
|
||||
.. option:: -fdelete-null-pointer-checks, -fno-delete-null-pointer-checks
|
||||
|
||||
Treat usage of null pointers as undefined behavior.
|
||||
|
||||
.. option:: -fdenormal-fp-math=<arg>
|
||||
|
||||
.. option:: -fdiagnostics-absolute-paths
|
||||
@ -1325,6 +1387,10 @@ Print option name with mappable diagnostics
|
||||
|
||||
Print a template comparison tree for differing templates
|
||||
|
||||
.. option:: -fdigraphs, -fno-digraphs
|
||||
|
||||
Enable alternative token representations '<:', ':>', '<%', '%>', '%:', '%:%:' (default)
|
||||
|
||||
.. option:: -fdollars-in-identifiers, -fno-dollars-in-identifiers
|
||||
|
||||
Allow '$' in identifiers
|
||||
@ -1375,8 +1441,16 @@ Allow aggressive, lossy floating-point optimizations
|
||||
|
||||
.. option:: -ffinite-math-only, -fno-finite-math-only
|
||||
|
||||
.. option:: -ffixed-point, -fno-fixed-point
|
||||
|
||||
Enable fixed point types
|
||||
|
||||
.. option:: -ffor-scope, -fno-for-scope
|
||||
|
||||
.. option:: -fforce-emit-vtables, -fno-force-emit-vtables
|
||||
|
||||
Emits more virtual tables to improve devirtualization
|
||||
|
||||
.. option:: -fforce-enable-int128, -fno-force-enable-int128
|
||||
|
||||
Enable support for int128\_t type
|
||||
@ -1439,6 +1513,10 @@ Enable the integrated assembler
|
||||
|
||||
.. option:: -fjump-tables, -fno-jump-tables
|
||||
|
||||
.. option:: -fkeep-static-consts
|
||||
|
||||
Keep static const variables even if unused
|
||||
|
||||
.. option:: -flax-vector-conversions, -fno-lax-vector-conversions
|
||||
|
||||
.. option:: -flimited-precision=<arg>
|
||||
@ -1543,14 +1621,6 @@ Specifies the largest alignment guaranteed by '::operator new(size\_t)'
|
||||
|
||||
Disable implicit builtin knowledge of a specific function
|
||||
|
||||
.. option:: -fdelete-null-pointer-checks, -fno-delete-null-pointer-checks
|
||||
|
||||
When enabled, treat null pointer dereference, creation of a reference to null,
|
||||
or passing a null pointer to a function parameter annotated with the "nonnull"
|
||||
attribute as undefined behavior. (And, thus the optimizer may assume that any
|
||||
pointer used in such a way must not have been null and optimize away the
|
||||
branches accordingly.) On by default.
|
||||
|
||||
.. option:: -fno-elide-type
|
||||
|
||||
Do not elide types when printing diagnostics
|
||||
@ -1834,6 +1904,10 @@ Emit full debug info for all types used by the program
|
||||
|
||||
Enable optimizations based on the strict definition of an enum's value range
|
||||
|
||||
.. option:: -fstrict-float-cast-overflow, -fno-strict-float-cast-overflow
|
||||
|
||||
Assume that overflowing float-to-int casts are undefined (default)
|
||||
|
||||
.. option:: -fstrict-overflow, -fno-strict-overflow
|
||||
|
||||
.. option:: -fstrict-return, -fno-strict-return
|
||||
@ -1942,12 +2016,6 @@ Set the default symbol visibility for all global declarations
|
||||
|
||||
Enables whole-program vtable optimization. Requires -flto
|
||||
|
||||
.. option:: -fforce-emit-vtables, -fno-force-emit-vtables
|
||||
|
||||
In order to improve devirtualization, forces emitting of vtables even in
|
||||
modules where it isn't necessary. It causes more inline virtual functions
|
||||
to be emitted.
|
||||
|
||||
.. option:: -fwrapv, -fno-wrapv
|
||||
|
||||
Treat signed integer overflow as two's complement
|
||||
@ -2078,12 +2146,6 @@ Put objects of at most <size> bytes into small data section (MIPS / Hexagon)
|
||||
|
||||
.. option:: -mabi=<arg>
|
||||
|
||||
.. option:: -mabicalls, -mno-abicalls
|
||||
|
||||
Enable SVR4-style position-independent code (Mips only)
|
||||
|
||||
.. option:: -mabs=<arg>
|
||||
|
||||
.. option:: -malign-double
|
||||
|
||||
Align doubles to two words in structs (x86 only)
|
||||
@ -2096,54 +2158,32 @@ Align doubles to two words in structs (x86 only)
|
||||
|
||||
Link stack frames through backchain on System Z
|
||||
|
||||
.. option:: -mcheck-zero-division, -mno-check-zero-division
|
||||
|
||||
.. option:: -mcmodel=<arg>
|
||||
|
||||
.. option:: -mcompact-branches=<arg>
|
||||
|
||||
.. option:: -mconsole<arg>
|
||||
|
||||
.. option:: -mcpu=<arg>, -mv4 (equivalent to -mcpu=hexagonv4), -mv5 (equivalent to -mcpu=hexagonv5), -mv55 (equivalent to -mcpu=hexagonv55), -mv60 (equivalent to -mcpu=hexagonv60), -mv62 (equivalent to -mcpu=hexagonv62), -mv65 (equivalent to -mcpu=hexagonv65)
|
||||
.. option:: -mcpu=<arg>, -mv5 (equivalent to -mcpu=hexagonv5), -mv55 (equivalent to -mcpu=hexagonv55), -mv60 (equivalent to -mcpu=hexagonv60), -mv62 (equivalent to -mcpu=hexagonv62), -mv65 (equivalent to -mcpu=hexagonv65)
|
||||
|
||||
.. option:: -mcrc, -mno-crc
|
||||
|
||||
Allow use of CRC instructions (ARM/Mips only)
|
||||
|
||||
.. option:: -mdefault-build-attributes<arg>, -mno-default-build-attributes<arg>
|
||||
|
||||
.. option:: -mdll<arg>
|
||||
|
||||
.. option:: -mdouble-float
|
||||
|
||||
.. option:: -mdsp, -mno-dsp
|
||||
|
||||
.. option:: -mdspr2, -mno-dspr2
|
||||
|
||||
.. option:: -mdynamic-no-pic<arg>
|
||||
|
||||
.. option:: -meabi <arg>
|
||||
|
||||
Set EABI type, e.g. 4, 5 or gnu (default depends on triple)
|
||||
|
||||
.. option:: -membedded-data, -mno-embedded-data
|
||||
|
||||
Place constants in the .rodata section instead of the .sdata section even if they meet the -G <size> threshold (MIPS)
|
||||
|
||||
.. option:: -mextern-sdata, -mno-extern-sdata
|
||||
|
||||
Assume that externally defined data is in the small data if it meets the -G <size> threshold (MIPS)
|
||||
|
||||
.. option:: -mfentry
|
||||
|
||||
Insert calls to fentry at function entry (x86 only)
|
||||
|
||||
.. option:: -mfloat-abi=<arg>
|
||||
|
||||
.. option:: -mfp32
|
||||
|
||||
Use 32-bit floating point registers (MIPS only)
|
||||
|
||||
.. option:: -mfp64
|
||||
|
||||
Use 64-bit floating point registers (MIPS only)
|
||||
|
||||
.. option:: -mfpmath=<arg>
|
||||
|
||||
.. option:: -mfpu=<arg>
|
||||
@ -2152,10 +2192,6 @@ Use 64-bit floating point registers (MIPS only)
|
||||
|
||||
Enable merging of globals
|
||||
|
||||
.. option:: -mgpopt, -mno-gpopt
|
||||
|
||||
Use GP relative accesses for symbols known to be in a small data section (MIPS)
|
||||
|
||||
.. option:: -mhard-float
|
||||
|
||||
.. option:: -mhwdiv=<arg>, --mhwdiv <arg>, --mhwdiv=<arg>
|
||||
@ -2172,22 +2208,10 @@ Use Intel MCU ABI
|
||||
|
||||
(integrated-as) Emit an object file which can be used with an incremental linker
|
||||
|
||||
.. option:: -mindirect-jump=<arg>
|
||||
|
||||
Change indirect jump instructions to inhibit speculation
|
||||
|
||||
.. option:: -miphoneos-version-min=<arg>, -mios-version-min=<arg>
|
||||
|
||||
.. option:: -mips16
|
||||
|
||||
.. option:: -mkernel
|
||||
|
||||
.. option:: -mldc1-sdc1, -mno-ldc1-sdc1
|
||||
|
||||
.. option:: -mlocal-sdata, -mno-local-sdata
|
||||
|
||||
Extend the -G behaviour to object local data (MIPS)
|
||||
|
||||
.. option:: -mlong-calls, -mno-long-calls
|
||||
|
||||
Generate branches with extended addressability, usually via indirect jumps.
|
||||
@ -2196,30 +2220,12 @@ Generate branches with extended addressability, usually via indirect jumps.
|
||||
|
||||
Set Mac OS X deployment target
|
||||
|
||||
.. option:: -mmadd4, -mno-madd4
|
||||
|
||||
Enable the generation of 4-operand madd.s, madd.d and related instructions.
|
||||
|
||||
.. option:: -mmcu=<arg>
|
||||
|
||||
.. option:: -mmicromips, -mno-micromips
|
||||
|
||||
.. option:: -mms-bitfields, -mno-ms-bitfields
|
||||
|
||||
Set the default structure layout to be compatible with the Microsoft compiler standard
|
||||
|
||||
.. option:: -mmsa, -mno-msa
|
||||
|
||||
Enable MSA ASE (MIPS only)
|
||||
|
||||
.. option:: -mmt, -mno-mt
|
||||
|
||||
Enable MT ASE (MIPS only)
|
||||
|
||||
.. option:: -mnan=<arg>
|
||||
|
||||
.. option:: -mno-mips16
|
||||
|
||||
.. option:: -momit-leaf-frame-pointer, -mno-omit-leaf-frame-pointer
|
||||
|
||||
Omit frame pointer setup for leaf functions
|
||||
@ -2252,11 +2258,15 @@ Enable hexagon-qdsp6 backward compatibility
|
||||
|
||||
(integrated-as) Relax all machine instructions
|
||||
|
||||
.. option:: -mretpoline, -mno-retpoline
|
||||
|
||||
.. option:: -mrtd, -mno-rtd
|
||||
|
||||
Make StdCall calling convention the default
|
||||
|
||||
.. option:: -msingle-float
|
||||
.. option:: -msign-return-address=<arg>
|
||||
|
||||
Select return address signing scope
|
||||
|
||||
.. option:: -msoft-float, -mno-soft-float
|
||||
|
||||
@ -2302,10 +2312,36 @@ The thread model to use, e.g. posix, single (posix by default)
|
||||
|
||||
.. option:: -mx32
|
||||
|
||||
.. option:: -mxgot, -mno-xgot
|
||||
|
||||
AARCH64
|
||||
-------
|
||||
.. option:: -ffixed-x1
|
||||
|
||||
Reserve the x1 register (AArch64 only)
|
||||
|
||||
.. option:: -ffixed-x2
|
||||
|
||||
Reserve the x2 register (AArch64 only)
|
||||
|
||||
.. option:: -ffixed-x3
|
||||
|
||||
Reserve the x3 register (AArch64 only)
|
||||
|
||||
.. option:: -ffixed-x4
|
||||
|
||||
Reserve the x4 register (AArch64 only)
|
||||
|
||||
.. option:: -ffixed-x5
|
||||
|
||||
Reserve the x5 register (AArch64 only)
|
||||
|
||||
.. option:: -ffixed-x6
|
||||
|
||||
Reserve the x6 register (AArch64 only)
|
||||
|
||||
.. option:: -ffixed-x7
|
||||
|
||||
Reserve the x7 register (AArch64 only)
|
||||
|
||||
.. option:: -ffixed-x18
|
||||
|
||||
Reserve the x18 register (AArch64 only)
|
||||
@ -2314,6 +2350,42 @@ Reserve the x18 register (AArch64 only)
|
||||
|
||||
Reserve the x20 register (AArch64 only)
|
||||
|
||||
.. option:: -fcall-saved-x8
|
||||
|
||||
Make the x8 register call-saved (AArch64 only)
|
||||
|
||||
.. option:: -fcall-saved-x9
|
||||
|
||||
Make the x9 register call-saved (AArch64 only)
|
||||
|
||||
.. option:: -fcall-saved-x10
|
||||
|
||||
Make the x10 register call-saved (AArch64 only)
|
||||
|
||||
.. option:: -fcall-saved-x11
|
||||
|
||||
Make the x11 register call-saved (AArch64 only)
|
||||
|
||||
.. option:: -fcall-saved-x12
|
||||
|
||||
Make the x12 register call-saved (AArch64 only)
|
||||
|
||||
.. option:: -fcall-saved-x13
|
||||
|
||||
Make the x13 register call-saved (AArch64 only)
|
||||
|
||||
.. option:: -fcall-saved-x14
|
||||
|
||||
Make the x14 register call-saved (AArch64 only)
|
||||
|
||||
.. option:: -fcall-saved-x15
|
||||
|
||||
Make the x15 register call-saved (AArch64 only)
|
||||
|
||||
.. option:: -fcall-saved-x18
|
||||
|
||||
Make the x18 register call-saved (AArch64 only)
|
||||
|
||||
.. option:: -mfix-cortex-a53-835769, -mno-fix-cortex-a53-835769
|
||||
|
||||
Workaround Cortex-A53 erratum 835769 (AArch64 only)
|
||||
@ -2334,10 +2406,6 @@ ARM
|
||||
|
||||
Reserve the r9 register (ARM only)
|
||||
|
||||
.. option:: -mcrc
|
||||
|
||||
Allow use of CRC instructions (ARM only)
|
||||
|
||||
.. option:: -mexecute-only, -mno-execute-only, -mpure-code
|
||||
|
||||
Disallow generation of data access to code sections (ARM only)
|
||||
@ -2370,6 +2438,18 @@ Hexagon
|
||||
-------
|
||||
.. option:: -mieee-rnd-near
|
||||
|
||||
.. option:: -mmemops, -mno-memops
|
||||
|
||||
Enable generation of memop instructions
|
||||
|
||||
.. option:: -mnvj, -mno-nvj
|
||||
|
||||
Enable generation of new-value jumps
|
||||
|
||||
.. option:: -mnvs, -mno-nvs
|
||||
|
||||
Enable generation of new-value stores
|
||||
|
||||
.. option:: -mpackets, -mno-packets
|
||||
|
||||
Enable generation of instruction packets
|
||||
@ -2390,6 +2470,82 @@ Set Hexagon Vector Length
|
||||
|
||||
Enable Hexagon Vector eXtensions
|
||||
|
||||
MIPS
|
||||
----
|
||||
.. option:: -mabicalls, -mno-abicalls
|
||||
|
||||
Enable SVR4-style position-independent code (Mips only)
|
||||
|
||||
.. option:: -mabs=<arg>
|
||||
|
||||
.. option:: -mcheck-zero-division, -mno-check-zero-division
|
||||
|
||||
.. option:: -mcompact-branches=<arg>
|
||||
|
||||
.. option:: -mdouble-float
|
||||
|
||||
.. option:: -mdsp, -mno-dsp
|
||||
|
||||
.. option:: -mdspr2, -mno-dspr2
|
||||
|
||||
.. option:: -membedded-data, -mno-embedded-data
|
||||
|
||||
Place constants in the .rodata section instead of the .sdata section even if they meet the -G <size> threshold (MIPS)
|
||||
|
||||
.. option:: -mextern-sdata, -mno-extern-sdata
|
||||
|
||||
Assume that externally defined data is in the small data if it meets the -G <size> threshold (MIPS)
|
||||
|
||||
.. option:: -mfp32
|
||||
|
||||
Use 32-bit floating point registers (MIPS only)
|
||||
|
||||
.. option:: -mfp64
|
||||
|
||||
Use 64-bit floating point registers (MIPS only)
|
||||
|
||||
.. option:: -mginv, -mno-ginv
|
||||
|
||||
.. option:: -mgpopt, -mno-gpopt
|
||||
|
||||
Use GP relative accesses for symbols known to be in a small data section (MIPS)
|
||||
|
||||
.. option:: -mindirect-jump=<arg>
|
||||
|
||||
Change indirect jump instructions to inhibit speculation
|
||||
|
||||
.. option:: -mips16
|
||||
|
||||
.. option:: -mldc1-sdc1, -mno-ldc1-sdc1
|
||||
|
||||
.. option:: -mlocal-sdata, -mno-local-sdata
|
||||
|
||||
Extend the -G behaviour to object local data (MIPS)
|
||||
|
||||
.. option:: -mmadd4, -mno-madd4
|
||||
|
||||
Enable the generation of 4-operand madd.s, madd.d and related instructions.
|
||||
|
||||
.. option:: -mmicromips, -mno-micromips
|
||||
|
||||
.. option:: -mmsa, -mno-msa
|
||||
|
||||
Enable MSA ASE (MIPS only)
|
||||
|
||||
.. option:: -mmt, -mno-mt
|
||||
|
||||
Enable MT ASE (MIPS only)
|
||||
|
||||
.. option:: -mnan=<arg>
|
||||
|
||||
.. option:: -mno-mips16
|
||||
|
||||
.. option:: -msingle-float
|
||||
|
||||
.. option:: -mvirt, -mno-virt
|
||||
|
||||
.. option:: -mxgot, -mno-xgot
|
||||
|
||||
PowerPC
|
||||
-------
|
||||
.. option:: -maltivec, -mno-altivec
|
||||
@ -2504,6 +2660,8 @@ X86
|
||||
|
||||
.. option:: -mgfni, -mno-gfni
|
||||
|
||||
.. option:: -minvpcid, -mno-invpcid
|
||||
|
||||
.. option:: -mlwp, -mno-lwp
|
||||
|
||||
.. option:: -mlzcnt, -mno-lzcnt
|
||||
@ -2512,16 +2670,18 @@ X86
|
||||
|
||||
.. option:: -mmovbe, -mno-movbe
|
||||
|
||||
.. option:: -mmovdiri, -mno-movdiri
|
||||
|
||||
.. option:: -mmovdir64b, -mno-movdir64b
|
||||
|
||||
.. option:: -mmovdiri, -mno-movdiri
|
||||
|
||||
.. option:: -mmpx, -mno-mpx
|
||||
|
||||
.. option:: -mmwaitx, -mno-mwaitx
|
||||
|
||||
.. option:: -mpclmul, -mno-pclmul
|
||||
|
||||
.. option:: -mpconfig, -mno-pconfig
|
||||
|
||||
.. option:: -mpku, -mno-pku
|
||||
|
||||
.. option:: -mpopcnt, -mno-popcnt
|
||||
@ -2530,14 +2690,14 @@ X86
|
||||
|
||||
.. option:: -mprfchw, -mno-prfchw
|
||||
|
||||
.. option:: -mptwrite, -mno-ptwrite
|
||||
|
||||
.. option:: -mrdpid, -mno-rdpid
|
||||
|
||||
.. option:: -mrdrnd, -mno-rdrnd
|
||||
|
||||
.. option:: -mrdseed, -mno-rdseed
|
||||
|
||||
.. option:: -mretpoline, -mno-retpoline
|
||||
|
||||
.. option:: -mretpoline-external-thunk, -mno-retpoline-external-thunk
|
||||
|
||||
.. option:: -mrtm, -mno-rtm
|
||||
@ -2588,6 +2748,12 @@ X86
|
||||
|
||||
.. option:: -mxsaves, -mno-xsaves
|
||||
|
||||
RISCV
|
||||
-----
|
||||
.. option:: -mrelax, -mno-relax
|
||||
|
||||
Enable linker relaxation
|
||||
|
||||
Optimization level
|
||||
~~~~~~~~~~~~~~~~~~
|
||||
|
||||
@ -2671,9 +2837,11 @@ Debug information flags
|
||||
|
||||
Embed source text in DWARF debug sections
|
||||
|
||||
.. option:: -ggnu-pubnames
|
||||
.. option:: -ggnu-pubnames, -gno-gnu-pubnames
|
||||
|
||||
.. option:: -grecord-gcc-switches, -gno-record-gcc-switches
|
||||
.. option:: -gpubnames, -gno-pubnames
|
||||
|
||||
.. option:: -grecord-command-line, -grecord-gcc-switches, -gno-record-command-line, -gno-record-gcc-switches
|
||||
|
||||
.. option:: -gsplit-dwarf
|
||||
|
||||
@ -2886,6 +3054,14 @@ Pass <arg> to the linker
|
||||
|
||||
.. option:: -filelist <arg>
|
||||
|
||||
.. option:: --hip-device-lib-path=<arg>
|
||||
|
||||
HIP device library path
|
||||
|
||||
.. option:: --hip-device-lib=<arg>
|
||||
|
||||
HIP device library
|
||||
|
||||
.. option:: -l<arg>
|
||||
|
||||
.. option:: -r
|
||||
|
@ -169,7 +169,7 @@ Visual Studio Integration
|
||||
=========================
|
||||
|
||||
Download the latest Visual Studio extension from the `alpha build site
|
||||
<http://llvm.org/builds/>`_. The default key-binding is Ctrl-R,Ctrl-F.
|
||||
<https://llvm.org/builds/>`_. The default key-binding is Ctrl-R,Ctrl-F.
|
||||
|
||||
|
||||
Script for patch reformatting
|
||||
@ -200,6 +200,12 @@ So to reformat all the lines in the latest :program:`git` commit, just do:
|
||||
|
||||
git diff -U0 --no-color HEAD^ | clang-format-diff.py -i -p1
|
||||
|
||||
With Mercurial/:program:`hg`:
|
||||
|
||||
.. code-block:: console
|
||||
|
||||
hg diff -U0 --color=never | clang-format-diff.py -i -p1
|
||||
|
||||
In an SVN client, you can do:
|
||||
|
||||
.. code-block:: console
|
||||
|
@ -108,7 +108,7 @@ Configuring Style in Code
|
||||
|
||||
When using ``clang::format::reformat(...)`` functions, the format is specified
|
||||
by supplying the `clang::format::FormatStyle
|
||||
<http://clang.llvm.org/doxygen/structclang_1_1format_1_1FormatStyle.html>`_
|
||||
<https://clang.llvm.org/doxygen/structclang_1_1format_1_1FormatStyle.html>`_
|
||||
structure.
|
||||
|
||||
|
||||
@ -131,7 +131,7 @@ the configuration (without a prefix: ``Auto``).
|
||||
|
||||
* ``LLVM``
|
||||
A style complying with the `LLVM coding standards
|
||||
<http://llvm.org/docs/CodingStandards.html>`_
|
||||
<https://llvm.org/docs/CodingStandards.html>`_
|
||||
* ``Google``
|
||||
A style complying with `Google's C++ style guide
|
||||
<http://google-styleguide.googlecode.com/svn/trunk/cppguide.xml>`_
|
||||
@ -908,20 +908,17 @@ the configuration (without a prefix: ``Auto``).
|
||||
|
||||
try {
|
||||
foo();
|
||||
} catch () {
|
||||
}
|
||||
catch () {
|
||||
}
|
||||
void foo() { bar(); }
|
||||
class foo
|
||||
{
|
||||
class foo {
|
||||
};
|
||||
if (foo()) {
|
||||
} else {
|
||||
}
|
||||
enum X : int
|
||||
{
|
||||
A,
|
||||
B
|
||||
};
|
||||
else {
|
||||
}
|
||||
enum X : int { A, B };
|
||||
|
||||
* ``BS_Allman`` (in configuration: ``Allman``)
|
||||
Always break before braces.
|
||||
@ -1134,21 +1131,17 @@ the configuration (without a prefix: ``Auto``).
|
||||
.. code-block:: c++
|
||||
|
||||
true:
|
||||
FitsOnOneLine::Constructor()
|
||||
: aaaaaaaaaaaaa(aaaaaaaaaaaaaa), aaaaaaaaaaaaa(aaaaaaaaaaaaaa) {}
|
||||
|
||||
DoesntFit::Constructor()
|
||||
: aaaaaaaaaaaaa(aaaaaaaaaaaaaa),
|
||||
aaaaaaaaaaaaa(aaaaaaaaaaaaaa),
|
||||
aaaaaaaaaaaaa(aaaaaaaaaaaaaa) {}
|
||||
SomeClass::Constructor()
|
||||
: aaaaaaaa(aaaaaaaa), aaaaaaaa(aaaaaaaa), aaaaaaaa(aaaaaaaaaaaaaaaaaaaaaaaaa) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
false:
|
||||
FitsOnOneLine::Constructor()
|
||||
: aaaaaaaaaaaaa(aaaaaaaaaaaaaa), aaaaaaaaaaaaa(aaaaaaaaaaaaaa) {}
|
||||
|
||||
DoesntFit::Constructor()
|
||||
: aaaaaaaaaaaaa(aaaaaaaaaaaaaa), aaaaaaaaaaaaa(aaaaaaaaaaaaaa),
|
||||
aaaaaaaaaaaaa(aaaaaaaaaaaaaa) {}
|
||||
SomeClass::Constructor()
|
||||
: aaaaaaaa(aaaaaaaa), aaaaaaaa(aaaaaaaa),
|
||||
aaaaaaaa(aaaaaaaaaaaaaaaaaaaaaaaaa) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
**ConstructorInitializerIndentWidth** (``unsigned``)
|
||||
The number of characters to use for indentation of constructor
|
||||
@ -1297,7 +1290,7 @@ the configuration (without a prefix: ``Auto``).
|
||||
If none of the regular expressions match, INT_MAX is assigned as
|
||||
category. The main header for a source file automatically gets category 0.
|
||||
so that it is generally kept at the beginning of the ``#includes``
|
||||
(http://llvm.org/docs/CodingStandards.html#include-style). However, you
|
||||
(https://llvm.org/docs/CodingStandards.html#include-style). However, you
|
||||
can also assign negative priorities if you have certain headers that
|
||||
always need to be first.
|
||||
|
||||
@ -1402,6 +1395,39 @@ the configuration (without a prefix: ``Auto``).
|
||||
LoooooooooooooooooooooooooooooooooooooooongReturnType
|
||||
LoooooooooooooooooooooooooooooooongFunctionDeclaration();
|
||||
|
||||
**JavaImportGroups** (``std::vector<std::string>``)
|
||||
A vector of prefixes ordered by the desired groups for Java imports.
|
||||
|
||||
Each group is separated by a newline. Static imports will also follow the
|
||||
same grouping convention above all non-static imports. One group's prefix
|
||||
can be a subset of another - the longest prefix is always matched. Within
|
||||
a group, the imports are ordered lexicographically.
|
||||
|
||||
In the .clang-format configuration file, this can be configured like
|
||||
in the following yaml example. This will result in imports being
|
||||
formatted as in the Java example below.
|
||||
|
||||
.. code-block:: yaml
|
||||
|
||||
JavaImportGroups: ['com.example', 'com', 'org']
|
||||
|
||||
|
||||
.. code-block:: java
|
||||
|
||||
import static com.example.function1;
|
||||
|
||||
import static com.test.function2;
|
||||
|
||||
import static org.example.function3;
|
||||
|
||||
import com.example.ClassA;
|
||||
import com.example.Test;
|
||||
import com.example.a.ClassB;
|
||||
|
||||
import com.test.ClassC;
|
||||
|
||||
import org.example.ClassD;
|
||||
|
||||
**JavaScriptQuotes** (``JavaScriptQuoteStyle``)
|
||||
The JavaScriptQuoteStyle to use for JavaScript strings.
|
||||
|
||||
@ -1979,6 +2005,16 @@ the configuration (without a prefix: ``Auto``).
|
||||
|
||||
|
||||
|
||||
**StatementMacros** (``std::vector<std::string>``)
|
||||
A vector of macros that should be interpreted as complete
|
||||
statements.
|
||||
|
||||
Typical macros are expressions, and require a semi-colon to be
|
||||
added; sometimes this is not the case, and this allows to make
|
||||
clang-format aware of such cases.
|
||||
|
||||
For example: Q_UNUSED
|
||||
|
||||
**TabWidth** (``unsigned``)
|
||||
The number of columns used for tab stops.
|
||||
|
||||
|
@ -69,7 +69,7 @@ Putting it all together
|
||||
Let's look at an example plugin that prints top-level function names. This
|
||||
example is checked into the clang repository; please take a look at
|
||||
the `latest version of PrintFunctionNames.cpp
|
||||
<http://llvm.org/viewvc/llvm-project/cfe/trunk/examples/PrintFunctionNames/PrintFunctionNames.cpp?view=markup>`_.
|
||||
<https://llvm.org/viewvc/llvm-project/cfe/trunk/examples/PrintFunctionNames/PrintFunctionNames.cpp?view=markup>`_.
|
||||
|
||||
Running the plugin
|
||||
==================
|
||||
@ -110,7 +110,7 @@ source tree:
|
||||
-plugin -Xclang print-fns
|
||||
|
||||
Also see the print-function-name plugin example's
|
||||
`README <http://llvm.org/viewvc/llvm-project/cfe/trunk/examples/PrintFunctionNames/README.txt?view=markup>`_
|
||||
`README <https://llvm.org/viewvc/llvm-project/cfe/trunk/examples/PrintFunctionNames/README.txt?view=markup>`_
|
||||
|
||||
|
||||
Using the clang command line
|
||||
|
@ -19,12 +19,12 @@ LLVM/Clang checkout:
|
||||
- With Subversion:
|
||||
|
||||
- ``cd llvm/tools/clang/tools``
|
||||
- ``svn co http://llvm.org/svn/llvm-project/clang-tools-extra/trunk extra``
|
||||
- ``svn co https://llvm.org/svn/llvm-project/clang-tools-extra/trunk extra``
|
||||
|
||||
- Or with Git:
|
||||
|
||||
- ``cd llvm/tools/clang/tools``
|
||||
- ``git clone http://llvm.org/git/clang-tools-extra.git extra``
|
||||
- ``git clone https://llvm.org/git/clang-tools-extra.git extra``
|
||||
|
||||
This document describes a high-level overview of the organization of
|
||||
Clang Tools within the project as well as giving an introduction to some
|
||||
@ -105,7 +105,7 @@ provide its own user-focused documentation.
|
||||
``clang-tidy``
|
||||
--------------
|
||||
|
||||
`clang-tidy <http://clang.llvm.org/extra/clang-tidy/>`_ is a clang-based C++
|
||||
`clang-tidy <https://clang.llvm.org/extra/clang-tidy/>`_ is a clang-based C++
|
||||
linter tool. It provides an extensible framework for building compiler-based
|
||||
static analyses detecting and fixing bug-prone patterns, performance,
|
||||
portability and maintainability issues.
|
||||
|
@ -60,7 +60,7 @@ Linker
|
||||
|
||||
The Clang Static Analyzer is a tool that scans source code to try to find bugs
|
||||
through code analysis. This tool uses many parts of Clang and is built into
|
||||
the same driver. Please see <http://clang-analyzer.llvm.org> for more details
|
||||
the same driver. Please see <https://clang-analyzer.llvm.org> for more details
|
||||
on how to use the static analyzer.
|
||||
|
||||
OPTIONS
|
||||
@ -361,7 +361,7 @@ Code Generation Options
|
||||
:option:`-Oz` Like :option:`-Os` (and thus :option:`-O2`), but reduces code
|
||||
size further.
|
||||
|
||||
:option:`-Og` Like :option:`-O1`. In future versions, this option might
|
||||
:option:`-Og` Like :option:`-O1`. In future versions, this option might
|
||||
disable different optimizations in order to improve debuggability.
|
||||
|
||||
:option:`-O` Equivalent to :option:`-O2`.
|
||||
@ -625,7 +625,7 @@ ENVIRONMENT
|
||||
BUGS
|
||||
----
|
||||
|
||||
To report bugs, please visit <http://llvm.org/bugs/>. Most bug reports should
|
||||
To report bugs, please visit <https://bugs.llvm.org/>. Most bug reports should
|
||||
include preprocessed source files (use the :option:`-E` option) and the full
|
||||
output of the compiler, along with information to reproduce.
|
||||
|
||||
@ -633,4 +633,3 @@ SEE ALSO
|
||||
--------
|
||||
|
||||
:manpage:`as(1)`, :manpage:`ld(1)`
|
||||
|
||||
|
@ -45,7 +45,7 @@ Experimental support for :ref:`cross-DSO control flow integrity
|
||||
<cfi-cross-dso>` exists that does not require classes to have hidden LTO
|
||||
visibility. This cross-DSO support has unstable ABI at this time.
|
||||
|
||||
.. _gold plugin: http://llvm.org/docs/GoldPlugin.html
|
||||
.. _gold plugin: https://llvm.org/docs/GoldPlugin.html
|
||||
|
||||
.. _cfi-schemes:
|
||||
|
||||
|
@ -93,8 +93,8 @@ the bit vectors for the whole program. It currently does this using LLVM's
|
||||
`type metadata`_ mechanism together with link-time optimization.
|
||||
|
||||
.. _address point: http://itanium-cxx-abi.github.io/cxx-abi/abi.html#vtable-general
|
||||
.. _type metadata: http://llvm.org/docs/TypeMetadata.html
|
||||
.. _ByteArrayBuilder: http://llvm.org/docs/doxygen/html/structllvm_1_1ByteArrayBuilder.html
|
||||
.. _type metadata: https://llvm.org/docs/TypeMetadata.html
|
||||
.. _ByteArrayBuilder: https://llvm.org/docs/doxygen/html/structllvm_1_1ByteArrayBuilder.html
|
||||
|
||||
Optimizations
|
||||
-------------
|
||||
@ -196,7 +196,7 @@ those sub-hierarchies need to be (see "Stripping Leading/Trailing Zeros in Bit
|
||||
Vectors" above). The `GlobalLayoutBuilder`_ class is responsible for laying
|
||||
out the globals efficiently to minimize the sizes of the underlying bitsets.
|
||||
|
||||
.. _GlobalLayoutBuilder: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/Transforms/IPO/LowerTypeTests.h?view=markup
|
||||
.. _GlobalLayoutBuilder: https://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/Transforms/IPO/LowerTypeTests.h?view=markup
|
||||
|
||||
Alignment
|
||||
~~~~~~~~~
|
||||
@ -274,6 +274,154 @@ If the bit vector is all ones, the bit vector check is redundant; we simply
|
||||
need to check that the address is in range and well aligned. This is more
|
||||
likely to occur if the virtual tables are padded.
|
||||
|
||||
Forward-Edge CFI for Virtual Calls by Interleaving Virtual Tables
|
||||
-----------------------------------------------------------------
|
||||
|
||||
Dimitar et. al. proposed a novel approach that interleaves virtual tables in [1]_.
|
||||
This approach is more efficient in terms of space because padding and bit vectors are no longer needed.
|
||||
At the same time, it is also more efficient in terms of performance because in the interleaved layout
|
||||
address points of the virtual tables are consecutive, thus the validity check of a virtual
|
||||
vtable pointer is always a range check.
|
||||
|
||||
At a high level, the interleaving scheme consists of three steps: 1) split virtual table groups into
|
||||
separate virtual tables, 2) order virtual tables by a pre-order traversal of the class hierarchy
|
||||
and 3) interleave virtual tables.
|
||||
|
||||
The interleaving scheme implemented in LLVM is inspired by [1]_ but has its own
|
||||
enhancements (more in `Interleave virtual tables`_).
|
||||
|
||||
.. [1] `Protecting C++ Dynamic Dispatch Through VTable Interleaving <https://cseweb.ucsd.edu/~lerner/papers/ivtbl-ndss16.pdf>`_. Dimitar Bounov, Rami Gökhan Kıcı, Sorin Lerner.
|
||||
|
||||
Split virtual table groups into separate virtual tables
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
|
||||
The Itanium C++ ABI glues multiple individual virtual tables for a class into a combined virtual table (virtual table group).
|
||||
The interleaving scheme, however, can only work with individual virtual tables so it must split the combined virtual tables first.
|
||||
In comparison, the old scheme does not require the splitting but it is more efficient when the combined virtual tables have been split.
|
||||
The `GlobalSplit`_ pass is responsible for splitting combined virtual tables into individual ones.
|
||||
|
||||
.. _GlobalSplit: https://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/IPO/GlobalSplit.cpp?view=markup
|
||||
|
||||
Order virtual tables by a pre-order traversal of the class hierarchy
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
|
||||
This step is common to both the old scheme described above and the interleaving scheme.
|
||||
For the interleaving scheme, since the combined virtual tables have been split in the previous step,
|
||||
this step ensures that for any class all the compatible virtual tables will appear consecutively.
|
||||
For the old scheme, the same property may not hold since it may work on combined virtual tables.
|
||||
|
||||
For example, consider the following four C++ classes:
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
struct A {
|
||||
virtual void f1();
|
||||
};
|
||||
|
||||
struct B : A {
|
||||
virtual void f1();
|
||||
virtual void f2();
|
||||
};
|
||||
|
||||
struct C : A {
|
||||
virtual void f1();
|
||||
virtual void f3();
|
||||
};
|
||||
|
||||
struct D : B {
|
||||
virtual void f1();
|
||||
virtual void f2();
|
||||
};
|
||||
|
||||
This step will arrange the virtual tables for A, B, C, and D in the order of *vtable-of-A, vtable-of-B, vtable-of-D, vtable-of-C*.
|
||||
|
||||
Interleave virtual tables
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
|
||||
This step is where the interleaving scheme deviates from the old scheme. Instead of laying out
|
||||
whole virtual tables in the previously computed order, the interleaving scheme lays out table
|
||||
entries of the virtual tables strategically to ensure the following properties:
|
||||
|
||||
(1) offset-to-top and RTTI fields layout property
|
||||
|
||||
The Itanium C++ ABI specifies that offset-to-top and RTTI fields appear at the offsets behind the
|
||||
address point. Note that libraries like libcxxabi do assume this property.
|
||||
|
||||
(2) virtual function entry layout property
|
||||
|
||||
For each virtual function the distance between an virtual table entry for this function and the corresponding
|
||||
address point is always the same. This property ensures that dynamic dispatch still works with the interleaving layout.
|
||||
|
||||
Note that the interleaving scheme in the CFI implementation guarantees both properties above whereas the original scheme proposed
|
||||
in [1]_ only guarantees the second property.
|
||||
|
||||
To illustrate how the interleaving algorithm works, let us continue with the running example.
|
||||
The algorithm first separates all the virtual table entries into two work lists. To do so,
|
||||
it starts by allocating two work lists, one initialized with all the offset-to-top entries of virtual tables in the order
|
||||
computed in the last step, one initialized with all the RTTI entries in the same order.
|
||||
|
||||
.. csv-table:: Work list 1 Layout
|
||||
:header: 0, 1, 2, 3
|
||||
|
||||
A::offset-to-top, B::offset-to-top, D::offset-to-top, C::offset-to-top
|
||||
|
||||
|
||||
.. csv-table:: Work list 2 layout
|
||||
:header: 0, 1, 2, 3,
|
||||
|
||||
&A::rtti, &B::rtti, &D::rtti, &C::rtti
|
||||
|
||||
Then for each virtual function the algorithm goes through all the virtual tables in the previously computed order
|
||||
to collect all the related entries into a virtual function list.
|
||||
After this step, there are the following virtual function lists:
|
||||
|
||||
.. csv-table:: f1 list
|
||||
:header: 0, 1, 2, 3
|
||||
|
||||
&A::f1, &B::f1, &D::f1, &C::f1
|
||||
|
||||
|
||||
.. csv-table:: f2 list
|
||||
:header: 0, 1
|
||||
|
||||
&B::f2, &D::f2
|
||||
|
||||
|
||||
.. csv-table:: f3 list
|
||||
:header: 0
|
||||
|
||||
&C::f3
|
||||
|
||||
Next, the algorithm picks the longest remaining virtual function list and appends the whole list to the shortest work list
|
||||
until no function lists are left, and pads the shorter work list so that they are of the same length.
|
||||
In the example, f1 list will be first added to work list 1, then f2 list will be added
|
||||
to work list 2, and finally f3 list will be added to the work list 2. Since work list 1 now has one more entry than
|
||||
work list 2, a padding entry is added to the latter. After this step, the two work lists look like:
|
||||
|
||||
.. csv-table:: Work list 1 Layout
|
||||
:header: 0, 1, 2, 3, 4, 5, 6, 7
|
||||
|
||||
A::offset-to-top, B::offset-to-top, D::offset-to-top, C::offset-to-top, &A::f1, &B::f1, &D::f1, &C::f1
|
||||
|
||||
|
||||
.. csv-table:: Work list 2 layout
|
||||
:header: 0, 1, 2, 3, 4, 5, 6, 7
|
||||
|
||||
&A::rtti, &B::rtti, &D::rtti, &C::rtti, &B::f2, &D::f2, &C::f3, padding
|
||||
|
||||
Finally, the algorithm merges the two work lists into the interleaved layout by alternatingly
|
||||
moving the head of each list to the final layout. After this step, the final interleaved layout looks like:
|
||||
|
||||
.. csv-table:: Interleaved layout
|
||||
:header: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15
|
||||
|
||||
A::offset-to-top, &A::rtti, B::offset-to-top, &B::rtti, D::offset-to-top, &D::rtti, C::offset-to-top, &C::rtti, &A::f1, &B::f2, &B::f1, &D::f2, &D::f1, &C::f3, &C::f1, padding
|
||||
|
||||
In the above interleaved layout, each virtual table's offset-to-top and RTTI are always adjacent, which shows that the layout has the first property.
|
||||
For the second property, let us look at f2 as an example. In the interleaved layout,
|
||||
there are two entries for f2: B::f2 and D::f2. The distance between &B::f2
|
||||
and its address point D::offset-to-top (the entry immediately after &B::rtti) is 5 entry-length, so is the distance between &D::f2 and C::offset-to-top (the entry immediately after &D::rtti).
|
||||
|
||||
Forward-Edge CFI for Indirect Function Calls
|
||||
============================================
|
||||
|
||||
|
@ -15,7 +15,7 @@ build system or Makefiles, nor choosing the right CMake options, etc.
|
||||
Also, it does not cover all the possible options, nor does it contain
|
||||
specific examples for specific architectures. For a concrete example, the
|
||||
`instructions for cross-compiling LLVM itself
|
||||
<http://llvm.org/docs/HowToCrossCompileLLVM.html>`_ may be of interest.
|
||||
<https://llvm.org/docs/HowToCrossCompileLLVM.html>`_ may be of interest.
|
||||
|
||||
After reading this document, you should be familiar with the main issues
|
||||
related to cross-compilation, and what main compiler options Clang provides
|
||||
|
@ -7885,6 +7885,10 @@ This diagnostic is enabled by default.
|
||||
| |+---------------------+|
|
||||
+-----------------------------------------------------------------------------------------------+-----------------------+
|
||||
|
||||
-Woverride-init
|
||||
---------------
|
||||
Synonym for `-Winitializer-overrides`_.
|
||||
|
||||
|
||||
-Woverride-module
|
||||
-----------------
|
||||
@ -8637,9 +8641,9 @@ Also controls `-Wpragma-pack-suspicious-include`_.
|
||||
|
||||
**Diagnostic text:**
|
||||
|
||||
+---------------------------------------------------------------------------------------------------------------+
|
||||
|:warning:`warning:` |nbsp| :diagtext:`the current #pragma pack aligment value is modified in the included file`|
|
||||
+---------------------------------------------------------------------------------------------------------------+
|
||||
+----------------------------------------------------------------------------------------------------------------+
|
||||
|:warning:`warning:` |nbsp| :diagtext:`the current #pragma pack alignment value is modified in the included file`|
|
||||
+----------------------------------------------------------------------------------------------------------------+
|
||||
|
||||
+---------------------------------------------------------------------------------------------+
|
||||
|:warning:`warning:` |nbsp| :diagtext:`unterminated '#pragma pack (push, ...)' at end of file`|
|
||||
|
@ -47,21 +47,21 @@ All memory accesses are prefixed with an inline instruction sequence that
|
||||
verifies the tags. Currently, the following sequence is used:
|
||||
|
||||
|
||||
.. code-block:: asm
|
||||
.. code-block:: none
|
||||
|
||||
// int foo(int *a) { return *a; }
|
||||
// clang -O2 --target=aarch64-linux -fsanitize=hwaddress -c load.c
|
||||
foo:
|
||||
0: 08 00 00 90 adrp x8, 0 <__hwasan_shadow>
|
||||
4: 08 01 40 f9 ldr x8, [x8] // shadow base (to be resolved by the loader)
|
||||
8: 09 dc 44 d3 ubfx x9, x0, #4, #52 // shadow offset
|
||||
c: 28 69 68 38 ldrb w8, [x9, x8] // load shadow tag
|
||||
10: 09 fc 78 d3 lsr x9, x0, #56 // extract address tag
|
||||
14: 3f 01 08 6b cmp w9, w8 // compare tags
|
||||
18: 61 00 00 54 b.ne 24 // jump on mismatch
|
||||
1c: 00 00 40 b9 ldr w0, [x0] // original load
|
||||
4: 08 01 40 f9 ldr x8, [x8] // shadow base (to be resolved by the loader)
|
||||
8: 09 dc 44 d3 ubfx x9, x0, #4, #52 // shadow offset
|
||||
c: 28 69 68 38 ldrb w8, [x9, x8] // load shadow tag
|
||||
10: 09 fc 78 d3 lsr x9, x0, #56 // extract address tag
|
||||
14: 3f 01 08 6b cmp w9, w8 // compare tags
|
||||
18: 61 00 00 54 b.ne 24 // jump on mismatch
|
||||
1c: 00 00 40 b9 ldr w0, [x0] // original load
|
||||
20: c0 03 5f d6 ret
|
||||
24: 40 20 21 d4 brk #0x902 // trap
|
||||
24: 40 20 21 d4 brk #0x902 // trap
|
||||
|
||||
Alternatively, memory accesses are prefixed with a function call.
|
||||
|
||||
|
@ -19,7 +19,7 @@ LLVM Support Library
|
||||
====================
|
||||
|
||||
The LLVM ``libSupport`` library provides many underlying libraries and
|
||||
`data-structures <http://llvm.org/docs/ProgrammersManual.html>`_, including
|
||||
`data-structures <https://llvm.org/docs/ProgrammersManual.html>`_, including
|
||||
command line option processing, various containers and a system abstraction
|
||||
layer, which is used for file system access.
|
||||
|
||||
@ -559,13 +559,9 @@ The clang Driver and library are documented :doc:`here <DriverInternals>`.
|
||||
Precompiled Headers
|
||||
===================
|
||||
|
||||
Clang supports two implementations of precompiled headers. The default
|
||||
implementation, precompiled headers (:doc:`PCH <PCHInternals>`) uses a
|
||||
Clang supports precompiled headers (:doc:`PCH <PCHInternals>`), which uses a
|
||||
serialized representation of Clang's internal data structures, encoded with the
|
||||
`LLVM bitstream format <http://llvm.org/docs/BitCodeFormat.html>`_.
|
||||
Pretokenized headers (:doc:`PTH <PTHInternals>`), on the other hand, contain a
|
||||
serialized representation of the tokens encountered when preprocessing a header
|
||||
(and anything that header includes).
|
||||
`LLVM bitstream format <https://llvm.org/docs/BitCodeFormat.html>`_.
|
||||
|
||||
The Frontend Library
|
||||
====================
|
||||
@ -1690,7 +1686,7 @@ semantic checking for some attributes, etc.
|
||||
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
The first step to adding a new attribute to Clang is to add its definition to
|
||||
`include/clang/Basic/Attr.td
|
||||
<http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/Attr.td?view=markup>`_.
|
||||
<https://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/Attr.td?view=markup>`_.
|
||||
This tablegen definition must derive from the ``Attr`` (tablegen, not
|
||||
semantic) type, or one of its derivatives. Most attributes will derive from the
|
||||
``InheritableAttr`` type, which specifies that the attribute can be inherited by
|
||||
@ -1752,10 +1748,10 @@ the ``SubjectList``. The diagnostics generated for subject list violations are
|
||||
either ``diag::warn_attribute_wrong_decl_type`` or
|
||||
``diag::err_attribute_wrong_decl_type``, and the parameter enumeration is found
|
||||
in `include/clang/Sema/ParsedAttr.h
|
||||
<http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Sema/ParsedAttr.h?view=markup>`_
|
||||
<https://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Sema/ParsedAttr.h?view=markup>`_
|
||||
If a previously unused Decl node is added to the ``SubjectList``, the logic used
|
||||
to automatically determine the diagnostic parameter in `utils/TableGen/ClangAttrEmitter.cpp
|
||||
<http://llvm.org/viewvc/llvm-project/cfe/trunk/utils/TableGen/ClangAttrEmitter.cpp?view=markup>`_
|
||||
<https://llvm.org/viewvc/llvm-project/cfe/trunk/utils/TableGen/ClangAttrEmitter.cpp?view=markup>`_
|
||||
may need to be updated.
|
||||
|
||||
By default, all subjects in the SubjectList must either be a Decl node defined
|
||||
@ -1777,7 +1773,7 @@ All attributes must have some form of documentation associated with them.
|
||||
Documentation is table generated on the public web server by a server-side
|
||||
process that runs daily. Generally, the documentation for an attribute is a
|
||||
stand-alone definition in `include/clang/Basic/AttrDocs.td
|
||||
<http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/AttdDocs.td?view=markup>`_
|
||||
<https://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/AttdDocs.td?view=markup>`_
|
||||
that is named after the attribute being documented.
|
||||
|
||||
If the attribute is not for public consumption, or is an implicitly-created
|
||||
@ -1828,7 +1824,7 @@ All arguments have a name and a flag that specifies whether the argument is
|
||||
optional. The associated C++ type of the argument is determined by the argument
|
||||
definition type. If the existing argument types are insufficient, new types can
|
||||
be created, but it requires modifying `utils/TableGen/ClangAttrEmitter.cpp
|
||||
<http://llvm.org/viewvc/llvm-project/cfe/trunk/utils/TableGen/ClangAttrEmitter.cpp?view=markup>`_
|
||||
<https://llvm.org/viewvc/llvm-project/cfe/trunk/utils/TableGen/ClangAttrEmitter.cpp?view=markup>`_
|
||||
to properly support the type.
|
||||
|
||||
Other Properties
|
||||
@ -1840,7 +1836,7 @@ document, however a few deserve mention.
|
||||
If the parsed form of the attribute is more complex, or differs from the
|
||||
semantic form, the ``HasCustomParsing`` bit can be set to ``1`` for the class,
|
||||
and the parsing code in `Parser::ParseGNUAttributeArgs()
|
||||
<http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Parse/ParseDecl.cpp?view=markup>`_
|
||||
<https://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Parse/ParseDecl.cpp?view=markup>`_
|
||||
can be updated for the special case. Note that this only applies to arguments
|
||||
with a GNU spelling -- attributes with a __declspec spelling currently ignore
|
||||
this flag and are handled by ``Parser::ParseMicrosoftDeclSpec``.
|
||||
@ -1903,7 +1899,7 @@ semantic attribute class object, with ``public`` access.
|
||||
Boilerplate
|
||||
^^^^^^^^^^^
|
||||
All semantic processing of declaration attributes happens in `lib/Sema/SemaDeclAttr.cpp
|
||||
<http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclAttr.cpp?view=markup>`_,
|
||||
<https://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclAttr.cpp?view=markup>`_,
|
||||
and generally starts in the ``ProcessDeclAttribute()`` function. If the
|
||||
attribute is a "simple" attribute -- meaning that it requires no custom semantic
|
||||
processing aside from what is automatically provided, add a call to
|
||||
@ -1919,11 +1915,11 @@ correct minimum number of arguments are passed, etc.
|
||||
|
||||
If the attribute adds additional warnings, define a ``DiagGroup`` in
|
||||
`include/clang/Basic/DiagnosticGroups.td
|
||||
<http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/DiagnosticGroups.td?view=markup>`_
|
||||
<https://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/DiagnosticGroups.td?view=markup>`_
|
||||
named after the attribute's ``Spelling`` with "_"s replaced by "-"s. If there
|
||||
is only a single diagnostic, it is permissible to use ``InGroup<DiagGroup<"your-attribute">>``
|
||||
directly in `DiagnosticSemaKinds.td
|
||||
<http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td?view=markup>`_
|
||||
<https://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td?view=markup>`_
|
||||
|
||||
All semantic diagnostics generated for your attribute, including automatically-
|
||||
generated ones (such as subjects and argument counts), should have a
|
||||
@ -2075,7 +2071,7 @@ are similar.
|
||||
exception-handling directly.
|
||||
* Testing is extremely important in IR generation. Use ``clang -cc1
|
||||
-emit-llvm`` and `FileCheck
|
||||
<http://llvm.org/docs/CommandGuide/FileCheck.html>`_ to verify that you're
|
||||
<https://llvm.org/docs/CommandGuide/FileCheck.html>`_ to verify that you're
|
||||
generating the right IR.
|
||||
|
||||
#. Teach template instantiation how to cope with your AST node, which requires
|
||||
|
@ -11,7 +11,7 @@ matchers.
|
||||
|
||||
<center><iframe width="560" height="315" src="http://www.youtube.com/embed/VqCkCDFLSsc?vq=hd720" frameborder="0" allowfullscreen></iframe></center>
|
||||
|
||||
`Slides <http://llvm.org/devmtg/2013-04/klimek-slides.pdf>`_
|
||||
`Slides <https://llvm.org/devmtg/2013-04/klimek-slides.pdf>`_
|
||||
|
||||
Introduction
|
||||
============
|
||||
@ -23,7 +23,7 @@ constants are available in an unreduced form in the AST. This makes
|
||||
Clang's AST a good fit for refactoring tools.
|
||||
|
||||
Documentation for all Clang AST nodes is available via the generated
|
||||
`Doxygen <http://clang.llvm.org/doxygen>`_. The doxygen online
|
||||
`Doxygen <https://clang.llvm.org/doxygen>`_. The doxygen online
|
||||
documentation is also indexed by your favorite search engine, which will
|
||||
make a search for clang and the AST node's class name usually turn up
|
||||
the doxygen of the class you're looking for (for example, search for:
|
||||
@ -67,26 +67,26 @@ Let's look at a simple example AST:
|
||||
|
||||
The toplevel declaration in
|
||||
a translation unit is always the `translation unit
|
||||
declaration <http://clang.llvm.org/doxygen/classclang_1_1TranslationUnitDecl.html>`_.
|
||||
declaration <https://clang.llvm.org/doxygen/classclang_1_1TranslationUnitDecl.html>`_.
|
||||
In this example, our first user written declaration is the `function
|
||||
declaration <http://clang.llvm.org/doxygen/classclang_1_1FunctionDecl.html>`_
|
||||
declaration <https://clang.llvm.org/doxygen/classclang_1_1FunctionDecl.html>`_
|
||||
of "``f``". The body of "``f``" is a `compound
|
||||
statement <http://clang.llvm.org/doxygen/classclang_1_1CompoundStmt.html>`_,
|
||||
statement <https://clang.llvm.org/doxygen/classclang_1_1CompoundStmt.html>`_,
|
||||
whose child nodes are a `declaration
|
||||
statement <http://clang.llvm.org/doxygen/classclang_1_1DeclStmt.html>`_
|
||||
statement <https://clang.llvm.org/doxygen/classclang_1_1DeclStmt.html>`_
|
||||
that declares our result variable, and the `return
|
||||
statement <http://clang.llvm.org/doxygen/classclang_1_1ReturnStmt.html>`_.
|
||||
statement <https://clang.llvm.org/doxygen/classclang_1_1ReturnStmt.html>`_.
|
||||
|
||||
AST Context
|
||||
===========
|
||||
|
||||
All information about the AST for a translation unit is bundled up in
|
||||
the class
|
||||
`ASTContext <http://clang.llvm.org/doxygen/classclang_1_1ASTContext.html>`_.
|
||||
`ASTContext <https://clang.llvm.org/doxygen/classclang_1_1ASTContext.html>`_.
|
||||
It allows traversal of the whole translation unit starting from
|
||||
`getTranslationUnitDecl <http://clang.llvm.org/doxygen/classclang_1_1ASTContext.html#abd909fb01ef10cfd0244832a67b1dd64>`_,
|
||||
`getTranslationUnitDecl <https://clang.llvm.org/doxygen/classclang_1_1ASTContext.html#abd909fb01ef10cfd0244832a67b1dd64>`_,
|
||||
or to access Clang's `table of
|
||||
identifiers <http://clang.llvm.org/doxygen/classclang_1_1ASTContext.html#a4f95adb9958e22fbe55212ae6482feb4>`_
|
||||
identifiers <https://clang.llvm.org/doxygen/classclang_1_1ASTContext.html#a4f95adb9958e22fbe55212ae6482feb4>`_
|
||||
for the parsed translation unit.
|
||||
|
||||
AST Nodes
|
||||
@ -95,32 +95,32 @@ AST Nodes
|
||||
Clang's AST nodes are modeled on a class hierarchy that does not have a
|
||||
common ancestor. Instead, there are multiple larger hierarchies for
|
||||
basic node types like
|
||||
`Decl <http://clang.llvm.org/doxygen/classclang_1_1Decl.html>`_ and
|
||||
`Stmt <http://clang.llvm.org/doxygen/classclang_1_1Stmt.html>`_. Many
|
||||
`Decl <https://clang.llvm.org/doxygen/classclang_1_1Decl.html>`_ and
|
||||
`Stmt <https://clang.llvm.org/doxygen/classclang_1_1Stmt.html>`_. Many
|
||||
important AST nodes derive from
|
||||
`Type <http://clang.llvm.org/doxygen/classclang_1_1Type.html>`_,
|
||||
`Decl <http://clang.llvm.org/doxygen/classclang_1_1Decl.html>`_,
|
||||
`DeclContext <http://clang.llvm.org/doxygen/classclang_1_1DeclContext.html>`_
|
||||
or `Stmt <http://clang.llvm.org/doxygen/classclang_1_1Stmt.html>`_, with
|
||||
`Type <https://clang.llvm.org/doxygen/classclang_1_1Type.html>`_,
|
||||
`Decl <https://clang.llvm.org/doxygen/classclang_1_1Decl.html>`_,
|
||||
`DeclContext <https://clang.llvm.org/doxygen/classclang_1_1DeclContext.html>`_
|
||||
or `Stmt <https://clang.llvm.org/doxygen/classclang_1_1Stmt.html>`_, with
|
||||
some classes deriving from both Decl and DeclContext.
|
||||
|
||||
There are also a multitude of nodes in the AST that are not part of a
|
||||
larger hierarchy, and are only reachable from specific other nodes, like
|
||||
`CXXBaseSpecifier <http://clang.llvm.org/doxygen/classclang_1_1CXXBaseSpecifier.html>`_.
|
||||
`CXXBaseSpecifier <https://clang.llvm.org/doxygen/classclang_1_1CXXBaseSpecifier.html>`_.
|
||||
|
||||
Thus, to traverse the full AST, one starts from the
|
||||
`TranslationUnitDecl <http://clang.llvm.org/doxygen/classclang_1_1TranslationUnitDecl.html>`_
|
||||
`TranslationUnitDecl <https://clang.llvm.org/doxygen/classclang_1_1TranslationUnitDecl.html>`_
|
||||
and then recursively traverses everything that can be reached from that
|
||||
node - this information has to be encoded for each specific node type.
|
||||
This algorithm is encoded in the
|
||||
`RecursiveASTVisitor <http://clang.llvm.org/doxygen/classclang_1_1RecursiveASTVisitor.html>`_.
|
||||
`RecursiveASTVisitor <https://clang.llvm.org/doxygen/classclang_1_1RecursiveASTVisitor.html>`_.
|
||||
See the `RecursiveASTVisitor
|
||||
tutorial <http://clang.llvm.org/docs/RAVFrontendAction.html>`_.
|
||||
tutorial <https://clang.llvm.org/docs/RAVFrontendAction.html>`_.
|
||||
|
||||
The two most basic nodes in the Clang AST are statements
|
||||
(`Stmt <http://clang.llvm.org/doxygen/classclang_1_1Stmt.html>`_) and
|
||||
(`Stmt <https://clang.llvm.org/doxygen/classclang_1_1Stmt.html>`_) and
|
||||
declarations
|
||||
(`Decl <http://clang.llvm.org/doxygen/classclang_1_1Decl.html>`_). Note
|
||||
(`Decl <https://clang.llvm.org/doxygen/classclang_1_1Decl.html>`_). Note
|
||||
that expressions
|
||||
(`Expr <http://clang.llvm.org/doxygen/classclang_1_1Expr.html>`_) are
|
||||
(`Expr <https://clang.llvm.org/doxygen/classclang_1_1Expr.html>`_) are
|
||||
also statements in Clang's AST.
|
||||
|
@ -112,18 +112,22 @@ of ``cxx_rvalue_references``.
|
||||
``__has_cpp_attribute``
|
||||
-----------------------
|
||||
|
||||
This function-like macro takes a single argument that is the name of a
|
||||
C++11-style attribute. The argument can either be a single identifier, or a
|
||||
scoped identifier. If the attribute is supported, a nonzero value is returned.
|
||||
If the attribute is a standards-based attribute, this macro returns a nonzero
|
||||
value based on the year and month in which the attribute was voted into the
|
||||
working draft. If the attribute is not supported by the current compliation
|
||||
target, this macro evaluates to 0. It can be used like this:
|
||||
This function-like macro is available in C++2a by default, and is provided as an
|
||||
extension in earlier language standards. It takes a single argument that is the
|
||||
name of a double-square-bracket-style attribute. The argument can either be a
|
||||
single identifier or a scoped identifier. If the attribute is supported, a
|
||||
nonzero value is returned. If the attribute is a standards-based attribute, this
|
||||
macro returns a nonzero value based on the year and month in which the attribute
|
||||
was voted into the working draft. See `WG21 SD-6
|
||||
<https://isocpp.org/std/standing-documents/sd-6-sg10-feature-test-recommendations>`_
|
||||
for the list of values returned for standards-based attributes. If the attribute
|
||||
is not supported by the current compliation target, this macro evaluates to 0.
|
||||
It can be used like this:
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
#ifndef __has_cpp_attribute // Optional of course.
|
||||
#define __has_cpp_attribute(x) 0 // Compatibility with non-clang compilers.
|
||||
#ifndef __has_cpp_attribute // For backwards compatibility
|
||||
#define __has_cpp_attribute(x) 0
|
||||
#endif
|
||||
|
||||
...
|
||||
@ -134,10 +138,11 @@ target, this macro evaluates to 0. It can be used like this:
|
||||
#endif
|
||||
...
|
||||
|
||||
The attribute identifier (but not scope) can also be specified with a preceding
|
||||
and following ``__`` (double underscore) to avoid interference from a macro with
|
||||
the same name. For instance, ``gnu::__const__`` can be used instead of
|
||||
``gnu::const``.
|
||||
The attribute scope tokens ``clang`` and ``_Clang`` are interchangeable, as are
|
||||
the attribute scope tokens ``gnu`` and ``__gnu__``. Attribute tokens in either
|
||||
of these namespaces can be specified with a preceding and following ``__``
|
||||
(double underscore) to avoid interference from a macro with the same name. For
|
||||
instance, ``gnu::__const__`` can be used instead of ``gnu::const``.
|
||||
|
||||
``__has_c_attribute``
|
||||
---------------------
|
||||
@ -162,11 +167,11 @@ current compilation target, this macro evaluates to 0. It can be used like this:
|
||||
#endif
|
||||
...
|
||||
|
||||
The attribute identifier (but not scope) can also be specified with a preceding
|
||||
and following ``__`` (double underscore) to avoid interference from a macro with
|
||||
the same name. For instance, ``gnu::__const__`` can be used instead of
|
||||
``gnu::const``.
|
||||
|
||||
The attribute scope tokens ``clang`` and ``_Clang`` are interchangeable, as are
|
||||
the attribute scope tokens ``gnu`` and ``__gnu__``. Attribute tokens in either
|
||||
of these namespaces can be specified with a preceding and following ``__``
|
||||
(double underscore) to avoid interference from a macro with the same name. For
|
||||
instance, ``gnu::__const__`` can be used instead of ``gnu::const``.
|
||||
|
||||
``__has_attribute``
|
||||
-------------------
|
||||
@ -590,7 +595,7 @@ which does not provide them. The features which can be tested are listed here.
|
||||
Since Clang 3.4, the C++ SD-6 feature test macros are also supported.
|
||||
These are macros with names of the form ``__cpp_<feature_name>``, and are
|
||||
intended to be a portable way to query the supported features of the compiler.
|
||||
See `the C++ status page <http://clang.llvm.org/cxx_status.html#ts>`_ for
|
||||
See `the C++ status page <https://clang.llvm.org/cxx_status.html#ts>`_ for
|
||||
information on the version of SD-6 supported by each Clang release, and the
|
||||
macros provided by that revision of the recommendations.
|
||||
|
||||
@ -1013,7 +1018,7 @@ Modules
|
||||
Use ``__has_feature(modules)`` to determine if Modules have been enabled.
|
||||
For example, compiling code with ``-fmodules`` enables the use of Modules.
|
||||
|
||||
More information could be found `here <http://clang.llvm.org/docs/Modules.html>`_.
|
||||
More information could be found `here <https://clang.llvm.org/docs/Modules.html>`_.
|
||||
|
||||
Checks for Type Trait Primitives
|
||||
================================
|
||||
@ -1353,7 +1358,7 @@ In Objective-C, functions and methods are generally assumed to follow the
|
||||
conventions for ownership of object arguments and
|
||||
return values. However, there are exceptions, and so Clang provides attributes
|
||||
to allow these exceptions to be documented. This are used by ARC and the
|
||||
`static analyzer <http://clang-analyzer.llvm.org>`_ Some exceptions may be
|
||||
`static analyzer <https://clang-analyzer.llvm.org>`_ Some exceptions may be
|
||||
better described using the ``objc_method_family`` attribute instead.
|
||||
|
||||
**Usage**: The ``ns_returns_retained``, ``ns_returns_not_retained``,
|
||||
@ -1390,7 +1395,7 @@ method; it specifies that the method expects its ``self`` parameter to have a
|
||||
- (void) baz:(id) __attribute__((ns_consumed)) x;
|
||||
|
||||
Further examples of these attributes are available in the static analyzer's `list of annotations for analysis
|
||||
<http://clang-analyzer.llvm.org/annotations.html#cocoa_mem>`_.
|
||||
<https://clang-analyzer.llvm.org/annotations.html#cocoa_mem>`_.
|
||||
|
||||
Query for these features with ``__has_attribute(ns_consumed)``,
|
||||
``__has_attribute(ns_returns_retained)``, etc.
|
||||
@ -1411,7 +1416,7 @@ Objective-C methods. If such a check was missed, the program would compile
|
||||
fine, run fine on newer systems, but crash on older systems.
|
||||
|
||||
As of LLVM 5.0, ``-Wunguarded-availability`` uses the `availability attributes
|
||||
<http://clang.llvm.org/docs/AttributeReference.html#availability>`_ together
|
||||
<https://clang.llvm.org/docs/AttributeReference.html#availability>`_ together
|
||||
with the new ``@available()`` keyword to assist with this issue.
|
||||
When a method that's introduced in the OS newer than the target OS is called, a
|
||||
-Wunguarded-availability warning is emitted if that call is not guarded:
|
||||
@ -1454,7 +1459,7 @@ More than one platform can be listed in ``@available()``:
|
||||
|
||||
If the caller of ``my_fun()`` already checks that ``my_fun()`` is only called
|
||||
on 10.12, then add an `availability attribute
|
||||
<http://clang.llvm.org/docs/AttributeReference.html#availability>`_ to it,
|
||||
<https://clang.llvm.org/docs/AttributeReference.html#availability>`_ to it,
|
||||
which will also suppress the warning and require that calls to my_fun() are
|
||||
checked:
|
||||
|
||||
@ -1739,6 +1744,70 @@ The '``__builtin_bitreverse``' family of builtins is used to reverse
|
||||
the bitpattern of an integer value; for example ``0b10110110`` becomes
|
||||
``0b01101101``.
|
||||
|
||||
``__builtin_rotateleft``
|
||||
------------------------
|
||||
|
||||
* ``__builtin_rotateleft8``
|
||||
* ``__builtin_rotateleft16``
|
||||
* ``__builtin_rotateleft32``
|
||||
* ``__builtin_rotateleft64``
|
||||
|
||||
**Syntax**:
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
__builtin_rotateleft32(x, y)
|
||||
|
||||
**Examples**:
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
uint8_t rot_x = __builtin_rotateleft8(x, y);
|
||||
uint16_t rot_x = __builtin_rotateleft16(x, y);
|
||||
uint32_t rot_x = __builtin_rotateleft32(x, y);
|
||||
uint64_t rot_x = __builtin_rotateleft64(x, y);
|
||||
|
||||
**Description**:
|
||||
|
||||
The '``__builtin_rotateleft``' family of builtins is used to rotate
|
||||
the bits in the first argument by the amount in the second argument.
|
||||
For example, ``0b10000110`` rotated left by 11 becomes ``0b00110100``.
|
||||
The shift value is treated as an unsigned amount modulo the size of
|
||||
the arguments. Both arguments and the result have the bitwidth specified
|
||||
by the name of the builtin.
|
||||
|
||||
``__builtin_rotateright``
|
||||
_------------------------
|
||||
|
||||
* ``__builtin_rotateright8``
|
||||
* ``__builtin_rotateright16``
|
||||
* ``__builtin_rotateright32``
|
||||
* ``__builtin_rotateright64``
|
||||
|
||||
**Syntax**:
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
__builtin_rotateright32(x, y)
|
||||
|
||||
**Examples**:
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
uint8_t rot_x = __builtin_rotateright8(x, y);
|
||||
uint16_t rot_x = __builtin_rotateright16(x, y);
|
||||
uint32_t rot_x = __builtin_rotateright32(x, y);
|
||||
uint64_t rot_x = __builtin_rotateright64(x, y);
|
||||
|
||||
**Description**:
|
||||
|
||||
The '``__builtin_rotateright``' family of builtins is used to rotate
|
||||
the bits in the first argument by the amount in the second argument.
|
||||
For example, ``0b10000110`` rotated right by 3 becomes ``0b11010000``.
|
||||
The shift value is treated as an unsigned amount modulo the size of
|
||||
the arguments. Both arguments and the result have the bitwidth specified
|
||||
by the name of the builtin.
|
||||
|
||||
``__builtin_unreachable``
|
||||
-------------------------
|
||||
|
||||
@ -1977,7 +2046,7 @@ Floating point builtins
|
||||
Returns the platform specific canonical encoding of a floating point
|
||||
number. This canonicalization is useful for implementing certain
|
||||
numeric primitives such as frexp. See `LLVM canonicalize intrinsic
|
||||
<http://llvm.org/docs/LangRef.html#llvm-canonicalize-intrinsic>`_ for
|
||||
<https://llvm.org/docs/LangRef.html#llvm-canonicalize-intrinsic>`_ for
|
||||
more information on the semantics.
|
||||
|
||||
String builtins
|
||||
@ -2191,7 +2260,7 @@ standard library to implement `std::experimental::coroutine_handle` type.
|
||||
|
||||
Other coroutine builtins are either for internal clang use or for use during
|
||||
development of the coroutine feature. See `Coroutines in LLVM
|
||||
<http://llvm.org/docs/Coroutines.html#intrinsics>`_ for
|
||||
<https://llvm.org/docs/Coroutines.html#intrinsics>`_ for
|
||||
more information on their semantics. Note that builtins matching the intrinsics
|
||||
that take token as the first parameter (llvm.coro.begin, llvm.coro.alloc,
|
||||
llvm.coro.free and llvm.coro.suspend) omit the token parameter and fill it to
|
||||
@ -2298,9 +2367,9 @@ Extensions for Static Analysis
|
||||
|
||||
Clang supports additional attributes that are useful for documenting program
|
||||
invariants and rules for static analysis tools, such as the `Clang Static
|
||||
Analyzer <http://clang-analyzer.llvm.org/>`_. These attributes are documented
|
||||
Analyzer <https://clang-analyzer.llvm.org/>`_. These attributes are documented
|
||||
in the analyzer's `list of source-level annotations
|
||||
<http://clang-analyzer.llvm.org/annotations.html>`_.
|
||||
<https://clang-analyzer.llvm.org/annotations.html>`_.
|
||||
|
||||
|
||||
Extensions for Dynamic Analysis
|
||||
@ -2587,17 +2656,19 @@ Specifying an attribute for multiple declarations (#pragma clang attribute)
|
||||
|
||||
The ``#pragma clang attribute`` directive can be used to apply an attribute to
|
||||
multiple declarations. The ``#pragma clang attribute push`` variation of the
|
||||
directive pushes a new attribute to the attribute stack. The declarations that
|
||||
follow the pragma receive the attributes that are on the attribute stack, until
|
||||
the stack is cleared using a ``#pragma clang attribute pop`` directive. Multiple
|
||||
push directives can be nested inside each other.
|
||||
directive pushes a new "scope" of ``#pragma clang attribute`` that attributes
|
||||
can be added to. The ``#pragma clang attribute (...)`` variation adds an
|
||||
attribute to that scope, and the ``#pragma clang attribute pop`` variation pops
|
||||
the scope. You can also use ``#pragma clang attribute push (...)``, which is a
|
||||
shorthand for when you want to add one attribute to a new scope. Multiple push
|
||||
directives can be nested inside each other.
|
||||
|
||||
The attributes that are used in the ``#pragma clang attribute`` directives
|
||||
can be written using the GNU-style syntax:
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
#pragma clang attribute push(__attribute__((annotate("custom"))), apply_to = function)
|
||||
#pragma clang attribute push (__attribute__((annotate("custom"))), apply_to = function)
|
||||
|
||||
void function(); // The function now has the annotate("custom") attribute
|
||||
|
||||
@ -2607,7 +2678,7 @@ The attributes can also be written using the C++11 style syntax:
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
#pragma clang attribute push([[noreturn]], apply_to = function)
|
||||
#pragma clang attribute push ([[noreturn]], apply_to = function)
|
||||
|
||||
void function(); // The function now has the [[noreturn]] attribute
|
||||
|
||||
@ -2617,7 +2688,7 @@ The ``__declspec`` style syntax is also supported:
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
#pragma clang attribute push(__declspec(dllexport), apply_to = function)
|
||||
#pragma clang attribute push (__declspec(dllexport), apply_to = function)
|
||||
|
||||
void function(); // The function now has the __declspec(dllexport) attribute
|
||||
|
||||
@ -2626,6 +2697,38 @@ The ``__declspec`` style syntax is also supported:
|
||||
A single push directive accepts only one attribute regardless of the syntax
|
||||
used.
|
||||
|
||||
Because multiple push directives can be nested, if you're writing a macro that
|
||||
expands to ``_Pragma("clang attribute")`` it's good hygiene (though not
|
||||
required) to add a namespace to your push/pop directives. A pop directive with a
|
||||
namespace will pop the innermost push that has that same namespace. This will
|
||||
ensure that another macro's ``pop`` won't inadvertently pop your attribute. Note
|
||||
that an ``pop`` without a namespace will pop the innermost ``push`` without a
|
||||
namespace. ``push``es with a namespace can only be popped by ``pop`` with the
|
||||
same namespace. For instance:
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
#define ASSUME_NORETURN_BEGIN _Pragma("clang attribute AssumeNoreturn.push ([[noreturn]], apply_to = function)")
|
||||
#define ASSUME_NORETURN_END _Pragma("clang attribute AssumeNoreturn.pop")
|
||||
|
||||
#define ASSUME_UNAVAILABLE_BEGIN _Pragma("clang attribute Unavailable.push (__attribute__((unavailable)), apply_to=function)")
|
||||
#define ASSUME_UNAVAILABLE_END _Pragma("clang attribute Unavailable.pop")
|
||||
|
||||
|
||||
ASSUME_NORETURN_BEGIN
|
||||
ASSUME_UNAVAILABLE_BEGIN
|
||||
void function(); // function has [[noreturn]] and __attribute__((unavailable))
|
||||
ASSUME_NORETURN_END
|
||||
void other_function(); // function has __attribute__((unavailable))
|
||||
ASSUME_UNAVAILABLE_END
|
||||
|
||||
Without the namespaces on the macros, ``other_function`` will be annotated with
|
||||
``[[noreturn]]`` instead of ``__attribute__((unavailable))``. This may seem like
|
||||
a contrived example, but its very possible for this kind of situation to appear
|
||||
in real code if the pragmas are spread out across a large file. You can test if
|
||||
your version of clang supports namespaces on ``#pragma clang attribute`` with
|
||||
``__has_extension(pragma_clang_attribute_namespaces)``.
|
||||
|
||||
Subject Match Rules
|
||||
-------------------
|
||||
|
||||
|
@ -81,7 +81,7 @@ To that end, matchers that match specific AST nodes (so called node matchers)
|
||||
are bindable; for example, ``recordDecl(hasName("MyClass")).bind("id")`` will
|
||||
bind the matched ``recordDecl`` node to the string "``id``", to be later
|
||||
retrieved in the `match callback
|
||||
<http://clang.llvm.org/doxygen/classclang_1_1ast__matchers_1_1MatchFinder_1_1MatchCallback.html>`_.
|
||||
<https://clang.llvm.org/doxygen/classclang_1_1ast__matchers_1_1MatchFinder_1_1MatchCallback.html>`_.
|
||||
|
||||
.. FIXME: Introduce link to ASTMatchersTutorial.html
|
||||
.. FIXME: Introduce link to ASTMatchersCookbook.html
|
||||
@ -116,7 +116,7 @@ corresponding matcher.
|
||||
|
||||
There are multiple matcher definition macros that deal with polymorphic return
|
||||
values and different parameter counts. See `ASTMatchersMacros.h
|
||||
<http://clang.llvm.org/doxygen/ASTMatchersMacros_8h.html>`_.
|
||||
<https://clang.llvm.org/doxygen/ASTMatchersMacros_8h.html>`_.
|
||||
|
||||
.. _astmatchers-writing:
|
||||
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -19,16 +19,16 @@ As Clang is part of the LLVM project, you'll need to download LLVM's
|
||||
source code first. Both Clang and LLVM are maintained as Subversion
|
||||
repositories, but we'll be accessing them through the git mirror. For
|
||||
further information, see the `getting started
|
||||
guide <http://llvm.org/docs/GettingStarted.html>`_.
|
||||
guide <https://llvm.org/docs/GettingStarted.html>`_.
|
||||
|
||||
.. code-block:: console
|
||||
|
||||
mkdir ~/clang-llvm && cd ~/clang-llvm
|
||||
git clone http://llvm.org/git/llvm.git
|
||||
git clone https://llvm.org/git/llvm.git
|
||||
cd llvm/tools
|
||||
git clone http://llvm.org/git/clang.git
|
||||
git clone https://llvm.org/git/clang.git
|
||||
cd clang/tools
|
||||
git clone http://llvm.org/git/clang-tools-extra.git extra
|
||||
git clone https://llvm.org/git/clang-tools-extra.git extra
|
||||
|
||||
Next you need to obtain the CMake build system and Ninja build tool. You
|
||||
may already have CMake installed, but current binary versions of CMake
|
||||
@ -113,6 +113,7 @@ CMakeLists.txt should have the following contents:
|
||||
LoopConvert.cpp
|
||||
)
|
||||
target_link_libraries(loop-convert
|
||||
PRIVATE
|
||||
clangTooling
|
||||
clangBasic
|
||||
clangASTMatchers
|
||||
|
@ -45,7 +45,7 @@ two style guides are hard-coded:
|
||||
.. code-block:: c++
|
||||
|
||||
/// Returns a format style complying with the LLVM coding standards:
|
||||
/// http://llvm.org/docs/CodingStandards.html.
|
||||
/// https://llvm.org/docs/CodingStandards.html.
|
||||
FormatStyle getLLVMStyle();
|
||||
|
||||
/// Returns a format style complying with Google's C++ style guide:
|
||||
|
@ -198,4 +198,4 @@ Linking
|
||||
|
||||
For a list of libraries to link, look at one of the tools' Makefiles (for
|
||||
example `clang-check/Makefile
|
||||
<http://llvm.org/viewvc/llvm-project/cfe/trunk/tools/clang-check/Makefile?view=markup>`_).
|
||||
<https://llvm.org/viewvc/llvm-project/cfe/trunk/tools/clang-check/Makefile?view=markup>`_).
|
||||
|
@ -70,7 +70,7 @@ The status of major ABI-impacting C++ features:
|
||||
.. _#pragma pointers_to_members:
|
||||
http://msdn.microsoft.com/en-us/library/83cch5a6.aspx
|
||||
.. _/vm: http://msdn.microsoft.com/en-us/library/yad46a6z.aspx
|
||||
.. _pointer to a member of a virtual base class: http://llvm.org/PR15713
|
||||
.. _pointer to a member of a virtual base class: https://llvm.org/PR15713
|
||||
|
||||
* Debug info: :good:`Mostly complete`. Clang emits relatively complete CodeView
|
||||
debug information if ``/Z7`` or ``/Zi`` is passed. Microsoft's link.exe will
|
||||
@ -137,7 +137,7 @@ following program, Clang will recover as if the user had written the
|
||||
commented-out code:
|
||||
|
||||
.. _frequently asked question:
|
||||
http://clang.llvm.org/compatibility.html#dep_lookup
|
||||
https://clang.llvm.org/compatibility.html#dep_lookup
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
|
@ -16,7 +16,7 @@ Typical slowdown introduced by MemorySanitizer is **3x**.
|
||||
How to build
|
||||
============
|
||||
|
||||
Build LLVM/Clang with `CMake <http://llvm.org/docs/CMake.html>`_.
|
||||
Build LLVM/Clang with `CMake <https://llvm.org/docs/CMake.html>`_.
|
||||
|
||||
Usage
|
||||
=====
|
||||
|
@ -411,7 +411,7 @@ A *requires-declaration* specifies the requirements that an importing translatio
|
||||
*feature*:
|
||||
``!``:sub:`opt` *identifier*
|
||||
|
||||
The requirements clause allows specific modules or submodules to specify that they are only accessible with certain language dialects or on certain platforms. The feature list is a set of identifiers, defined below. If any of the features is not available in a given translation unit, that translation unit shall not import the module. When building a module for use by a compilation, submodules requiring unavailable features are ignored. The optional ``!`` indicates that a feature is incompatible with the module.
|
||||
The requirements clause allows specific modules or submodules to specify that they are only accessible with certain language dialects, platforms, environments and target specific features. The feature list is a set of identifiers, defined below. If any of the features is not available in a given translation unit, that translation unit shall not import the module. When building a module for use by a compilation, submodules requiring unavailable features are ignored. The optional ``!`` indicates that a feature is incompatible with the module.
|
||||
|
||||
The following features are defined:
|
||||
|
||||
@ -466,6 +466,11 @@ tls
|
||||
*target feature*
|
||||
A specific target feature (e.g., ``sse4``, ``avx``, ``neon``) is available.
|
||||
|
||||
*platform/os*
|
||||
A os/platform variant (e.g. ``freebsd``, ``win32``, ``windows``, ``linux``, ``ios``, ``macos``, ``iossimulator``) is available.
|
||||
|
||||
*environment*
|
||||
A environment variant (e.g. ``gnu``, ``gnueabi``, ``android``, ``msvc``) is available.
|
||||
|
||||
**Example:** The ``std`` module can be extended to also include C++ and C++11 headers using a *requires-declaration*:
|
||||
|
||||
|
@ -66,12 +66,11 @@ Combined directives
|
||||
|
||||
* #pragma omp target teams distribute parallel for [simd]: :good:`Complete`.
|
||||
|
||||
Clang does not support any constructs/updates from upcoming OpenMP 5.0 except
|
||||
Clang does not support any constructs/updates from OpenMP 5.0 except
|
||||
for `reduction`-based clauses in the `task` and `target`-based directives.
|
||||
|
||||
In addition, the LLVM OpenMP runtime `libomp` supports the OpenMP Tools
|
||||
Interface (OMPT) on x86, x86_64, AArch64, and PPC64 on Linux, Windows, and mac OS.
|
||||
ows, and mac OS.
|
||||
|
||||
.. _basic support for Cuda devices:
|
||||
|
||||
@ -109,11 +108,19 @@ are stored in the global memory. In `Cuda` mode local variables are not shared
|
||||
between the threads and it is user responsibility to share the required data
|
||||
between the threads in the parallel regions.
|
||||
|
||||
Collapsed loop nest counter
|
||||
---------------------------
|
||||
|
||||
When using the collapse clause on a loop nest the default behaviour is to
|
||||
automatically extend the representation of the loop counter to 64 bits for
|
||||
the cases where the sizes of the collapsed loops are not known at compile
|
||||
time. To prevent this conservative choice and use at most 32 bits,
|
||||
compile your program with the `-fopenmp-optimistic-collapse`.
|
||||
|
||||
|
||||
Features not supported or with limited support for Cuda devices
|
||||
---------------------------------------------------------------
|
||||
|
||||
- Reductions across the teams are not supported yet.
|
||||
|
||||
- Cancellation constructs are not supported.
|
||||
|
||||
- Doacross loop nest is not supported.
|
||||
|
@ -70,7 +70,7 @@ minimizes both creation time and the time required to initially load the AST
|
||||
file. The AST file itself contains a serialized representation of Clang's
|
||||
abstract syntax trees and supporting data structures, stored using the same
|
||||
compressed bitstream as `LLVM's bitcode file format
|
||||
<http://llvm.org/docs/BitCodeFormat.html>`_.
|
||||
<https://llvm.org/docs/BitCodeFormat.html>`_.
|
||||
|
||||
Clang's AST files are loaded "lazily" from disk. When an AST file is initially
|
||||
loaded, Clang reads only a small amount of data from the AST file to establish
|
||||
@ -134,7 +134,7 @@ only contain the serialized AST.
|
||||
The ``clangast`` section is organized into several different blocks, each of
|
||||
which contains the serialized representation of a part of Clang's internal
|
||||
representation. Each of the blocks corresponds to either a block or a record
|
||||
within `LLVM's bitstream format <http://llvm.org/docs/BitCodeFormat.html>`_.
|
||||
within `LLVM's bitstream format <https://llvm.org/docs/BitCodeFormat.html>`_.
|
||||
The contents of each of these logical blocks are described below.
|
||||
|
||||
.. image:: PCHLayout.png
|
||||
@ -142,7 +142,7 @@ The contents of each of these logical blocks are described below.
|
||||
The ``llvm-objdump`` utility provides a ``-raw-clang-ast`` option to extract the
|
||||
binary contents of the AST section from an object file container.
|
||||
|
||||
The `llvm-bcanalyzer <http://llvm.org/docs/CommandGuide/llvm-bcanalyzer.html>`_
|
||||
The `llvm-bcanalyzer <https://llvm.org/docs/CommandGuide/llvm-bcanalyzer.html>`_
|
||||
utility can be used to examine the actual structure of the bitstream for the AST
|
||||
section. This information can be used both to help understand the structure of
|
||||
the AST section and to isolate areas where the AST representation can still be
|
||||
|
@ -1,163 +0,0 @@
|
||||
==========================
|
||||
Pretokenized Headers (PTH)
|
||||
==========================
|
||||
|
||||
This document first describes the low-level interface for using PTH and
|
||||
then briefly elaborates on its design and implementation. If you are
|
||||
interested in the end-user view, please see the :ref:`User's Manual
|
||||
<usersmanual-precompiled-headers>`.
|
||||
|
||||
Using Pretokenized Headers with ``clang`` (Low-level Interface)
|
||||
===============================================================
|
||||
|
||||
The Clang compiler frontend, ``clang -cc1``, supports three command line
|
||||
options for generating and using PTH files.
|
||||
|
||||
To generate PTH files using ``clang -cc1``, use the option ``-emit-pth``:
|
||||
|
||||
.. code-block:: console
|
||||
|
||||
$ clang -cc1 test.h -emit-pth -o test.h.pth
|
||||
|
||||
This option is transparently used by ``clang`` when generating PTH
|
||||
files. Similarly, PTH files can be used as prefix headers using the
|
||||
``-include-pth`` option:
|
||||
|
||||
.. code-block:: console
|
||||
|
||||
$ clang -cc1 -include-pth test.h.pth test.c -o test.s
|
||||
|
||||
Alternatively, Clang's PTH files can be used as a raw "token-cache" (or
|
||||
"content" cache) of the source included by the original header file.
|
||||
This means that the contents of the PTH file are searched as substitutes
|
||||
for *any* source files that are used by ``clang -cc1`` to process a
|
||||
source file. This is done by specifying the ``-token-cache`` option:
|
||||
|
||||
.. code-block:: console
|
||||
|
||||
$ cat test.h
|
||||
#include <stdio.h>
|
||||
$ clang -cc1 -emit-pth test.h -o test.h.pth
|
||||
$ cat test.c
|
||||
#include "test.h"
|
||||
$ clang -cc1 test.c -o test -token-cache test.h.pth
|
||||
|
||||
In this example the contents of ``stdio.h`` (and the files it includes)
|
||||
will be retrieved from ``test.h.pth``, as the PTH file is being used in
|
||||
this case as a raw cache of the contents of ``test.h``. This is a
|
||||
low-level interface used to both implement the high-level PTH interface
|
||||
as well as to provide alternative means to use PTH-style caching.
|
||||
|
||||
PTH Design and Implementation
|
||||
=============================
|
||||
|
||||
Unlike GCC's precompiled headers, which cache the full ASTs and
|
||||
preprocessor state of a header file, Clang's pretokenized header files
|
||||
mainly cache the raw lexer *tokens* that are needed to segment the
|
||||
stream of characters in a source file into keywords, identifiers, and
|
||||
operators. Consequently, PTH serves to mainly directly speed up the
|
||||
lexing and preprocessing of a source file, while parsing and
|
||||
type-checking must be completely redone every time a PTH file is used.
|
||||
|
||||
Basic Design Tradeoffs
|
||||
----------------------
|
||||
|
||||
In the long term there are plans to provide an alternate PCH
|
||||
implementation for Clang that also caches the work for parsing and type
|
||||
checking the contents of header files. The current implementation of PCH
|
||||
in Clang as pretokenized header files was motivated by the following
|
||||
factors:
|
||||
|
||||
**Language independence**
|
||||
PTH files work with any language that
|
||||
Clang's lexer can handle, including C, Objective-C, and (in the early
|
||||
stages) C++. This means development on language features at the
|
||||
parsing level or above (which is basically almost all interesting
|
||||
pieces) does not require PTH to be modified.
|
||||
|
||||
**Simple design**
|
||||
Relatively speaking, PTH has a simple design and
|
||||
implementation, making it easy to test. Further, because the
|
||||
machinery for PTH resides at the lower-levels of the Clang library
|
||||
stack it is fairly straightforward to profile and optimize.
|
||||
|
||||
Further, compared to GCC's PCH implementation (which is the dominate
|
||||
precompiled header file implementation that Clang can be directly
|
||||
compared against) the PTH design in Clang yields several attractive
|
||||
features:
|
||||
|
||||
**Architecture independence**
|
||||
In contrast to GCC's PCH files (and
|
||||
those of several other compilers), Clang's PTH files are architecture
|
||||
independent, requiring only a single PTH file when building a
|
||||
program for multiple architectures.
|
||||
|
||||
For example, on Mac OS X one may wish to compile a "universal binary"
|
||||
that runs on PowerPC, 32-bit Intel (i386), and 64-bit Intel
|
||||
architectures. In contrast, GCC requires a PCH file for each
|
||||
architecture, as the definitions of types in the AST are
|
||||
architecture-specific. Since a Clang PTH file essentially represents
|
||||
a lexical cache of header files, a single PTH file can be safely used
|
||||
when compiling for multiple architectures. This can also reduce
|
||||
compile times because only a single PTH file needs to be generated
|
||||
during a build instead of several.
|
||||
|
||||
**Reduced memory pressure**
|
||||
Similar to GCC, Clang reads PTH files
|
||||
via the use of memory mapping (i.e., ``mmap``). Clang, however,
|
||||
memory maps PTH files as read-only, meaning that multiple invocations
|
||||
of ``clang -cc1`` can share the same pages in memory from a
|
||||
memory-mapped PTH file. In comparison, GCC also memory maps its PCH
|
||||
files but also modifies those pages in memory, incurring the
|
||||
copy-on-write costs. The read-only nature of PTH can greatly reduce
|
||||
memory pressure for builds involving multiple cores, thus improving
|
||||
overall scalability.
|
||||
|
||||
**Fast generation**
|
||||
PTH files can be generated in a small fraction
|
||||
of the time needed to generate GCC's PCH files. Since PTH/PCH
|
||||
generation is a serial operation that typically blocks progress
|
||||
during a build, faster generation time leads to improved processor
|
||||
utilization with parallel builds on multicore machines.
|
||||
|
||||
Despite these strengths, PTH's simple design suffers some algorithmic
|
||||
handicaps compared to other PCH strategies such as those used by GCC.
|
||||
While PTH can greatly speed up the processing time of a header file, the
|
||||
amount of work required to process a header file is still roughly linear
|
||||
in the size of the header file. In contrast, the amount of work done by
|
||||
GCC to process a precompiled header is (theoretically) constant (the
|
||||
ASTs for the header are literally memory mapped into the compiler). This
|
||||
means that only the pieces of the header file that are referenced by the
|
||||
source file including the header are the only ones the compiler needs to
|
||||
process during actual compilation. While GCC's particular implementation
|
||||
of PCH mitigates some of these algorithmic strengths via the use of
|
||||
copy-on-write pages, the approach itself can fundamentally dominate at
|
||||
an algorithmic level, especially when one considers header files of
|
||||
arbitrary size.
|
||||
|
||||
There is also a PCH implementation for Clang based on the lazy
|
||||
deserialization of ASTs. This approach theoretically has the same
|
||||
constant-time algorithmic advantages just mentioned but also retains some
|
||||
of the strengths of PTH such as reduced memory pressure (ideal for
|
||||
multi-core builds).
|
||||
|
||||
Internal PTH Optimizations
|
||||
--------------------------
|
||||
|
||||
While the main optimization employed by PTH is to reduce lexing time of
|
||||
header files by caching pre-lexed tokens, PTH also employs several other
|
||||
optimizations to speed up the processing of header files:
|
||||
|
||||
- ``stat`` caching: PTH files cache information obtained via calls to
|
||||
``stat`` that ``clang -cc1`` uses to resolve which files are included
|
||||
by ``#include`` directives. This greatly reduces the overhead
|
||||
involved in context-switching to the kernel to resolve included
|
||||
files.
|
||||
|
||||
- Fast skipping of ``#ifdef`` ... ``#endif`` chains: PTH files
|
||||
record the basic structure of nested preprocessor blocks. When the
|
||||
condition of the preprocessor block is false, all of its tokens are
|
||||
immediately skipped instead of requiring them to be handled by
|
||||
Clang's preprocessor.
|
||||
|
||||
|
@ -128,7 +128,7 @@ locations:
|
||||
if (Declaration->getQualifiedNameAsString() == "n::m::C") {
|
||||
// getFullLoc uses the ASTContext's SourceManager to resolve the source
|
||||
// location and break it up into its line and column parts.
|
||||
FullSourceLoc FullLocation = Context->getFullLoc(Declaration->getLocStart());
|
||||
FullSourceLoc FullLocation = Context->getFullLoc(Declaration->getBeginLoc());
|
||||
if (FullLocation.isValid())
|
||||
llvm::outs() << "Found declaration at "
|
||||
<< FullLocation.getSpellingLineNumber() << ":"
|
||||
@ -160,7 +160,7 @@ Now we can combine all of the above into a small example program:
|
||||
|
||||
bool VisitCXXRecordDecl(CXXRecordDecl *Declaration) {
|
||||
if (Declaration->getQualifiedNameAsString() == "n::m::C") {
|
||||
FullSourceLoc FullLocation = Context->getFullLoc(Declaration->getLocStart());
|
||||
FullSourceLoc FullLocation = Context->getFullLoc(Declaration->getBeginLoc());
|
||||
if (FullLocation.isValid())
|
||||
llvm::outs() << "Found declaration at "
|
||||
<< FullLocation.getSpellingLineNumber() << ":"
|
||||
|
@ -1,41 +1,41 @@
|
||||
=======================================
|
||||
Clang 7.0.0 (In-Progress) Release Notes
|
||||
Clang 8.0.0 (In-Progress) Release Notes
|
||||
=======================================
|
||||
|
||||
.. contents::
|
||||
:local:
|
||||
:depth: 2
|
||||
|
||||
Written by the `LLVM Team <http://llvm.org/>`_
|
||||
Written by the `LLVM Team <https://llvm.org/>`_
|
||||
|
||||
.. warning::
|
||||
|
||||
These are in-progress notes for the upcoming Clang 7 release.
|
||||
These are in-progress notes for the upcoming Clang 8 release.
|
||||
Release notes for previous releases can be found on
|
||||
`the Download Page <http://releases.llvm.org/download.html>`_.
|
||||
`the Download Page <https://releases.llvm.org/download.html>`_.
|
||||
|
||||
Introduction
|
||||
============
|
||||
|
||||
This document contains the release notes for the Clang C/C++/Objective-C
|
||||
frontend, part of the LLVM Compiler Infrastructure, release 7.0.0. Here we
|
||||
frontend, part of the LLVM Compiler Infrastructure, release 8.0.0. Here we
|
||||
describe the status of Clang in some detail, including major
|
||||
improvements from the previous release and new feature work. For the
|
||||
general LLVM release notes, see `the LLVM
|
||||
documentation <http://llvm.org/docs/ReleaseNotes.html>`_. All LLVM
|
||||
documentation <https://llvm.org/docs/ReleaseNotes.html>`_. All LLVM
|
||||
releases may be downloaded from the `LLVM releases web
|
||||
site <http://llvm.org/releases/>`_.
|
||||
site <https://llvm.org/releases/>`_.
|
||||
|
||||
For more information about Clang or LLVM, including information about the
|
||||
latest release, please see the `Clang Web Site <http://clang.llvm.org>`_ or the
|
||||
`LLVM Web Site <http://llvm.org>`_.
|
||||
latest release, please see the `Clang Web Site <https://clang.llvm.org>`_ or the
|
||||
`LLVM Web Site <https://llvm.org>`_.
|
||||
|
||||
Note that if you are reading this file from a Subversion checkout or the
|
||||
main Clang web page, this document applies to the *next* release, not
|
||||
the current one. To see the release notes for a specific release, please
|
||||
see the `releases page <http://llvm.org/releases/>`_.
|
||||
see the `releases page <https://llvm.org/releases/>`_.
|
||||
|
||||
What's New in Clang 7.0.0?
|
||||
What's New in Clang 8.0.0?
|
||||
==========================
|
||||
|
||||
Some of the major new features and improvements to Clang are listed
|
||||
@ -46,86 +46,95 @@ sections with improvements to Clang's support for those languages.
|
||||
Major New Features
|
||||
------------------
|
||||
|
||||
- A new Implicit Conversion Sanitizer (``-fsanitize=implicit-conversion``) group
|
||||
was added. Please refer to the :ref:`release-notes-ubsan` section of the
|
||||
release notes for the details.
|
||||
- Clang supports use of a profile remapping file, which permits
|
||||
profile data captured for one version of a program to be applied
|
||||
when building another version where symbols have changed (for
|
||||
example, due to renaming a class or namespace).
|
||||
See the :doc:`UsersManual` for details.
|
||||
|
||||
Improvements to Clang's diagnostics
|
||||
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
- ``-Wc++98-compat-extra-semi`` is a new flag, which was previously inseparable
|
||||
from ``-Wc++98-compat-pedantic``. The latter still controls the new flag.
|
||||
- ``-Wextra-semi-stmt`` is a new diagnostic that diagnoses extra semicolons,
|
||||
much like ``-Wextra-semi``. This new diagnostic diagnoses all *unnecessary*
|
||||
null statements (expression statements without an expression), unless: the
|
||||
semicolon directly follows a macro that was expanded to nothing or if the
|
||||
semicolon is within the macro itself. This applies to macros defined in system
|
||||
headers as well as user-defined macros.
|
||||
|
||||
- ``-Wextra-semi`` now also controls ``-Wc++98-compat-extra-semi``.
|
||||
Please do note that if you pass ``-Wno-c++98-compat-pedantic``, it implies
|
||||
``-Wno-c++98-compat-extra-semi``, so if you want that diagnostic, you need
|
||||
to explicitly re-enable it (e.g. by appending ``-Wextra-semi``).
|
||||
.. code-block:: c++
|
||||
|
||||
#define MACRO(x) int x;
|
||||
#define NULLMACRO(varname)
|
||||
|
||||
void test() {
|
||||
; // <- warning: ';' with no preceding expression is a null statement
|
||||
|
||||
while (true)
|
||||
; // OK, it is needed.
|
||||
|
||||
switch (my_enum) {
|
||||
case E1:
|
||||
// stuff
|
||||
break;
|
||||
case E2:
|
||||
; // OK, it is needed.
|
||||
}
|
||||
|
||||
MACRO(v0;) // Extra semicolon, but within macro, so ignored.
|
||||
|
||||
MACRO(v1); // <- warning: ';' with no preceding expression is a null statement
|
||||
|
||||
NULLMACRO(v2); // ignored, NULLMACRO expanded to nothing.
|
||||
}
|
||||
|
||||
- ``-Wempty-init-stmt`` is a new diagnostic that diagnoses empty init-statements
|
||||
of ``if``, ``switch``, ``range-based for``, unless: the semicolon directly
|
||||
follows a macro that was expanded to nothing or if the semicolon is within the
|
||||
macro itself (both macros from system headers, and normal macros). This
|
||||
diagnostic is in the ``-Wextra-semi-stmt`` group and is enabled in
|
||||
``-Wextra``.
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
void test() {
|
||||
if(; // <- warning: init-statement of 'if' is a null statement
|
||||
true)
|
||||
;
|
||||
|
||||
switch (; // <- warning: init-statement of 'switch' is a null statement
|
||||
x) {
|
||||
...
|
||||
}
|
||||
|
||||
for (; // <- warning: init-statement of 'range-based for' is a null statement
|
||||
int y : S())
|
||||
;
|
||||
}
|
||||
|
||||
- ``-Wself-assign`` and ``-Wself-assign-field`` were extended to diagnose
|
||||
self-assignment operations using overloaded operators (i.e. classes).
|
||||
If you are doing such an assignment intentionally, e.g. in a unit test for
|
||||
a data structure, the first warning can be disabled by passing
|
||||
``-Wno-self-assign-overloaded``, also the warning can be suppressed by adding
|
||||
``*&`` to the right-hand side or casting it to the appropriate reference type.
|
||||
|
||||
Non-comprehensive list of changes in this release
|
||||
-------------------------------------------------
|
||||
|
||||
- Clang binary and libraries have been renamed from 7.0 to 7.
|
||||
For example, the ``clang`` binary will be called ``clang-7``
|
||||
instead of ``clang-7.0``.
|
||||
- The experimental feature Pretokenized Headers (PTH) was removed in its
|
||||
entirely from Clang. The feature did not properly work with about 1/3 of the
|
||||
possible tokens available and was unmaintained.
|
||||
|
||||
- Clang implements a collection of recent fixes to the C++ standard's definition
|
||||
of "standard-layout". In particular, a class is only considered to be
|
||||
standard-layout if all base classes and the first data member (or bit-field)
|
||||
can be laid out at offset zero.
|
||||
|
||||
- Clang's handling of the GCC ``packed`` class attribute in C++ has been fixed
|
||||
to apply only to non-static data members and not to base classes. This fixes
|
||||
an ABI difference between Clang and GCC, but creates an ABI difference between
|
||||
Clang 7 and earlier versions. The old behavior can be restored by setting
|
||||
``-fclang-abi-compat`` to ``6`` or earlier.
|
||||
|
||||
- Clang implements the proposed resolution of LWG issue 2358, along with the
|
||||
`corresponding change to the Itanium C++ ABI
|
||||
<https://github.com/itanium-cxx-abi/cxx-abi/pull/51>`_, which make classes
|
||||
containing only unnamed non-zero-length bit-fields be considered non-empty.
|
||||
This is an ABI break compared to prior Clang releases, but makes Clang
|
||||
generate code that is ABI-compatible with other compilers. The old
|
||||
behavior can be restored by setting ``-fclang-abi-compat`` to ``6`` or
|
||||
lower.
|
||||
|
||||
- An existing tool named ``diagtool`` has been added to the release. As the
|
||||
name suggests, it helps with dealing with diagnostics in ``clang``, such as
|
||||
finding out the warning hierarchy, and which of them are enabled by default
|
||||
or for a particular compiler invocation.
|
||||
|
||||
- By default, Clang emits an address-significance table into
|
||||
every ELF object file when using the integrated assembler.
|
||||
Address-significance tables allow linkers to implement `safe ICF
|
||||
<https://research.google.com/pubs/archive/36912.pdf>`_ without the false
|
||||
positives that can result from other implementation techniques such as
|
||||
relocation scanning. The ``-faddrsig`` and ``-fno-addrsig`` flags can be
|
||||
used to control whether to emit the address-significance table.
|
||||
|
||||
- ...
|
||||
- The internals of libc++ include directory detection on MacOS have changed.
|
||||
Instead of running a search based on the ``-resource-dir`` flag, the search
|
||||
is now based on the path of the compiler in the filesystem. The default
|
||||
behaviour should not change. However, if you override ``-resource-dir``
|
||||
manually and rely on the old behaviour you will need to add appropriate
|
||||
compiler flags for finding the corresponding libc++ include directory.
|
||||
|
||||
New Compiler Flags
|
||||
------------------
|
||||
|
||||
- ``-fstrict-float-cast-overflow`` and ``-fno-strict-float-cast-overflow``.
|
||||
- ``-fprofile-filter-files=[regexes]`` and ``-fprofile-exclude-files=[regexes]``.
|
||||
|
||||
When a floating-point value is not representable in a destination integer
|
||||
type, the code has undefined behavior according to the language standard. By
|
||||
default, Clang will not guarantee any particular result in that case. With the
|
||||
'no-strict' option, Clang attempts to match the overflowing behavior of the
|
||||
target's native float-to-int conversion instructions.
|
||||
|
||||
- ``-fforce-emit-vtables`` and ``-fno-force-emit-vtables``.
|
||||
|
||||
In order to improve devirtualization, forces emitting of vtables even in
|
||||
modules where it isn't necessary. It causes more inline virtual functions
|
||||
to be emitted.
|
||||
Clang has now options to filter or exclude some files when
|
||||
instrumenting for gcov-based profiling.
|
||||
See the :doc:`UsersManual` for details.
|
||||
|
||||
- ...
|
||||
|
||||
@ -140,46 +149,36 @@ future versions of Clang.
|
||||
Modified Compiler Flags
|
||||
-----------------------
|
||||
|
||||
- Before Clang 7, we prepended the `#` character to the `--autocomplete`
|
||||
argument to enable cc1 flags. For example, when the `-cc1` or `-Xclang` flag
|
||||
is in the :program:`clang` invocation, the shell executed
|
||||
`clang --autocomplete=#-<flag to be completed>`. Clang 7 now requires the
|
||||
whole invocation including all flags to be passed to the `--autocomplete` like
|
||||
this: `clang --autocomplete=-cc1,-xc++,-fsyn`.
|
||||
- As of clang 8, `alignof` and `_Alignof` return the ABI alignment of a type,
|
||||
as opposed to the preferred alignment. `__alignof` still returns the
|
||||
preferred alignment. `-fclang-abi-compat=7` (and previous) will make
|
||||
`alignof` and `_Alignof` return preferred alignment again.
|
||||
|
||||
|
||||
New Pragmas in Clang
|
||||
--------------------
|
||||
|
||||
Clang now supports the ...
|
||||
|
||||
- Clang now supports adding multiple `#pragma clang attribute` attributes into
|
||||
a scope of pushed attributes.
|
||||
|
||||
Attribute Changes in Clang
|
||||
--------------------------
|
||||
|
||||
- Clang now supports function multiversioning with attribute 'target' on ELF
|
||||
based x86/x86-64 environments by using indirect functions. This implementation
|
||||
has a few minor limitations over the GCC implementation for the sake of AST
|
||||
sanity, however it is otherwise compatible with existing code using this
|
||||
feature for GCC. Consult the documentation for the target attribute for more
|
||||
information.
|
||||
|
||||
- ...
|
||||
|
||||
Windows Support
|
||||
---------------
|
||||
|
||||
- clang-cl's support for precompiled headers has been much improved:
|
||||
|
||||
- When using a pch file, clang-cl now no longer redundantly emits inline
|
||||
methods that are already stored in the obj that was built together with
|
||||
the pch file (matching cl.exe). This speeds up builds using pch files
|
||||
by around 30%.
|
||||
|
||||
- The /Ycfoo.h and /Yufoo.h flags can now be used without /FIfoo.h when
|
||||
foo.h is instead included by an explicit `#include` directive. This means
|
||||
Visual Studio's default stdafx.h setup now uses precompiled headers with
|
||||
clang-cl.
|
||||
- clang-cl now supports the use of the precompiled header options /Yc and /Yu
|
||||
without the filename argument. When these options are used without the
|
||||
filename, a `#pragma hdrstop` inside the source marks the end of the
|
||||
precompiled code.
|
||||
|
||||
- clang-cl has a new command-line option, ``/Zc:dllexportInlines-``, similar to
|
||||
``-fvisibility-inlines-hidden`` on non-Windows, that makes class-level
|
||||
`dllexport` and `dllimport` attributes not apply to inline member functions.
|
||||
This can significantly reduce compile and link times. See the `User's Manual
|
||||
<UsersManual.html#the-zc-dllexportinlines-option>`_ for more info.
|
||||
- ...
|
||||
|
||||
|
||||
@ -215,41 +214,52 @@ OpenCL C Language Changes in Clang
|
||||
|
||||
...
|
||||
|
||||
ABI Changes in Clang
|
||||
--------------------
|
||||
|
||||
- `_Alignof` and `alignof` now return the ABI alignment of a type, as opposed
|
||||
to the preferred alignment.
|
||||
|
||||
- This is more in keeping with the language of the standards, as well as
|
||||
being compatible with gcc
|
||||
- `__alignof` and `__alignof__` still return the preferred alignment of
|
||||
a type
|
||||
- This shouldn't break any ABI except for things that explicitly ask for
|
||||
`alignas(alignof(T))`.
|
||||
- If you have interfaces that break with this change, you may wish to switch
|
||||
to `alignas(__alignof(T))`, instead of using the `-fclang-abi-compat`
|
||||
switch.
|
||||
|
||||
OpenMP Support in Clang
|
||||
----------------------------------
|
||||
|
||||
- Clang gained basic support for OpenMP 4.5 offloading for NVPTX target.
|
||||
To compile your program for NVPTX target use the following options:
|
||||
`-fopenmp -fopenmp-targets=nvptx64-nvidia-cuda` for 64 bit platforms or
|
||||
`-fopenmp -fopenmp-targets=nvptx-nvidia-cuda` for 32 bit platform.
|
||||
- Support relational-op != (not-equal) as one of the canonical forms of random
|
||||
access iterator.
|
||||
|
||||
- Passing options to the OpenMP device offloading toolchain can be done using
|
||||
the `-Xopenmp-target=<triple> -opt=val` flag. In this way the `-opt=val`
|
||||
option will be forwarded to the respective OpenMP device offloading toolchain
|
||||
described by the triple. For example passing the compute capability to
|
||||
the OpenMP NVPTX offloading toolchain can be done as follows:
|
||||
`-Xopenmp-target=nvptx64-nvidia-cuda -march=sm_60`. For the case when only one
|
||||
target offload toolchain is specified under the `-fopenmp-targets=<triples>`
|
||||
option, then the triple can be skipped: `-Xopenmp-target -march=sm_60`.
|
||||
- Added support for mapping of the lambdas in target regions.
|
||||
|
||||
- Other bugfixes.
|
||||
- Added parsing/sema analysis for OpenMP 5.0 requires directive.
|
||||
|
||||
- Various bugfixes and improvements.
|
||||
|
||||
New features supported for Cuda devices:
|
||||
|
||||
- Added support for the reductions across the teams.
|
||||
|
||||
- Extended number of constructs that can be executed in SPMD mode.
|
||||
|
||||
- Fixed support for lastprivate/reduction variables in SPMD constructs.
|
||||
|
||||
- General performance improvement.
|
||||
|
||||
CUDA Support in Clang
|
||||
---------------------
|
||||
|
||||
- Clang will now try to locate the CUDA installation next to :program:`ptxas`
|
||||
in the `PATH` environment variable. This behavior can be turned off by passing
|
||||
the new flag `--cuda-path-ignore-env`.
|
||||
|
||||
- Clang now supports generating object files with relocatable device code. This
|
||||
feature needs to be enabled with `-fcuda-rdc` and my result in performance
|
||||
penalties compared to whole program compilation. Please note that NVIDIA's
|
||||
:program:`nvcc` must be used for linking.
|
||||
|
||||
Internal API Changes
|
||||
--------------------
|
||||
|
||||
These are major API changes that have happened since the 6.0.0 release of
|
||||
These are major API changes that have happened since the 7.0.0 release of
|
||||
Clang. If upgrading an external codebase that uses Clang as a library,
|
||||
this section should help get you past the largest hurdles of upgrading.
|
||||
|
||||
@ -263,9 +273,6 @@ AST Matchers
|
||||
clang-format
|
||||
------------
|
||||
|
||||
- Clang-format will now support detecting and formatting code snippets in raw
|
||||
string literals. This is configured through the `RawStringFormats` style
|
||||
option.
|
||||
|
||||
- ...
|
||||
|
||||
@ -287,31 +294,75 @@ Static Analyzer
|
||||
Undefined Behavior Sanitizer (UBSan)
|
||||
------------------------------------
|
||||
|
||||
* A new Implicit Conversion Sanitizer (``-fsanitize=implicit-conversion``) group
|
||||
was added.
|
||||
|
||||
Currently, only one type of issues is caught - implicit integer truncation
|
||||
(``-fsanitize=implicit-integer-truncation``), also known as integer demotion.
|
||||
While there is a ``-Wconversion`` diagnostic group that catches this kind of
|
||||
issues, it is both noisy, and does not catch **all** the cases.
|
||||
* The Implicit Conversion Sanitizer (``-fsanitize=implicit-conversion``) group
|
||||
was extended. One more type of issues is caught - implicit integer sign change.
|
||||
(``-fsanitize=implicit-integer-sign-change``).
|
||||
This makes the Implicit Conversion Sanitizer feature-complete,
|
||||
with only missing piece being bitfield handling.
|
||||
While there is a ``-Wsign-conversion`` diagnostic group that catches this kind
|
||||
of issues, it is both noisy, and does not catch **all** the cases.
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
unsigned char store = 0;
|
||||
|
||||
bool consume(unsigned int val);
|
||||
|
||||
void test(unsigned long val) {
|
||||
if (consume(val)) // the value may have been silently truncated.
|
||||
store = store + 768; // before addition, 'store' was promoted to int.
|
||||
(void)consume((unsigned int)val); // OK, the truncation is explicit.
|
||||
void test(int val) {
|
||||
(void)consume(val); // If the value was negative, it is now large positive.
|
||||
(void)consume((unsigned int)val); // OK, the conversion is explicit.
|
||||
}
|
||||
|
||||
Just like other ``-fsanitize=integer`` checks, these issues are **not**
|
||||
Like some other ``-fsanitize=integer`` checks, these issues are **not**
|
||||
undefined behaviour. But they are not *always* intentional, and are somewhat
|
||||
hard to track down. This group is **not** enabled by ``-fsanitize=undefined``,
|
||||
but the ``-fsanitize=implicit-integer-truncation`` check
|
||||
but the ``-fsanitize=implicit-integer-sign-change`` check
|
||||
is enabled by ``-fsanitize=integer``.
|
||||
(as is ``-fsanitize=implicit-integer-truncation`` check)
|
||||
|
||||
* The Implicit Conversion Sanitizer (``-fsanitize=implicit-conversion``) has
|
||||
learned to sanitize compound assignment operators.
|
||||
|
||||
* ``alignment`` check has learned to sanitize the assume_aligned-like attributes:
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
typedef char **__attribute__((align_value(1024))) aligned_char;
|
||||
struct ac_struct {
|
||||
aligned_char a;
|
||||
};
|
||||
char **load_from_ac_struct(struct ac_struct *x) {
|
||||
return x->a; // <- check that loaded 'a' is aligned
|
||||
}
|
||||
|
||||
char **passthrough(__attribute__((align_value(1024))) char **x) {
|
||||
return x; // <- check the pointer passed as function argument
|
||||
}
|
||||
|
||||
char **__attribute__((alloc_align(2)))
|
||||
alloc_align(int size, unsigned long alignment);
|
||||
|
||||
char **caller(int size) {
|
||||
return alloc_align(size, 1024); // <- check returned pointer
|
||||
}
|
||||
|
||||
char **__attribute__((assume_aligned(1024))) get_ptr();
|
||||
|
||||
char **caller2() {
|
||||
return get_ptr(); // <- check returned pointer
|
||||
}
|
||||
|
||||
void *caller3(char **x) {
|
||||
return __builtin_assume_aligned(x, 1024); // <- check returned pointer
|
||||
}
|
||||
|
||||
void *caller4(char **x, unsigned long offset) {
|
||||
return __builtin_assume_aligned(x, 1024, offset); // <- check returned pointer accounting for the offest
|
||||
}
|
||||
|
||||
void process(char *data, int width) {
|
||||
#pragma omp for simd aligned(data : 1024) // <- aligned clause will be checked.
|
||||
for (int x = 0; x < width; x++)
|
||||
data[x] *= data[x];
|
||||
}
|
||||
|
||||
Core Analysis Improvements
|
||||
==========================
|
||||
@ -337,7 +388,7 @@ Additional Information
|
||||
======================
|
||||
|
||||
A wide variety of additional information is available on the `Clang web
|
||||
page <http://clang.llvm.org/>`_. The web page contains versions of the
|
||||
page <https://clang.llvm.org/>`_. The web page contains versions of the
|
||||
API documentation which are up-to-date with the Subversion version of
|
||||
the source code. You can access versions of these documents specific to
|
||||
this release by going into the "``clang/docs/``" directory in the Clang
|
||||
@ -345,4 +396,4 @@ tree.
|
||||
|
||||
If you have any questions or comments about Clang, please feel free to
|
||||
contact us via the `mailing
|
||||
list <http://lists.llvm.org/mailman/listinfo/cfe-dev>`_.
|
||||
list <https://lists.llvm.org/mailman/listinfo/cfe-dev>`_.
|
||||
|
@ -245,7 +245,7 @@ around comparison instructions and switch statements.
|
||||
Similarly, with ``-fsanitize-coverage=trace-div`` the compiler will instrument
|
||||
integer division instructions (to capture the right argument of division)
|
||||
and with ``-fsanitize-coverage=trace-gep`` --
|
||||
the `LLVM GEP instructions <http://llvm.org/docs/GetElementPtr.html>`_
|
||||
the `LLVM GEP instructions <https://llvm.org/docs/GetElementPtr.html>`_
|
||||
(to capture array indices).
|
||||
|
||||
.. code-block:: c++
|
||||
|
@ -156,7 +156,7 @@ line-oriented report, try:
|
||||
The ``llvm-cov`` tool supports specifying a custom demangler, writing out
|
||||
reports in a directory structure, and generating html reports. For the full
|
||||
list of options, please refer to the `command guide
|
||||
<http://llvm.org/docs/CommandGuide/llvm-cov.html>`_.
|
||||
<https://llvm.org/docs/CommandGuide/llvm-cov.html>`_.
|
||||
|
||||
A few final notes:
|
||||
|
||||
|
@ -47,7 +47,7 @@ The 3.9 release of clang includes ThinLTO support. However, ThinLTO
|
||||
is under active development, and new features, improvements and bugfixes
|
||||
are being added for the next release. For the latest ThinLTO support,
|
||||
`build a recent version of clang and LLVM
|
||||
<http://llvm.org/docs/CMake.html>`_.
|
||||
<https://llvm.org/docs/CMake.html>`_.
|
||||
|
||||
Linkers
|
||||
-------
|
||||
@ -59,7 +59,7 @@ ThinLTO is currently supported for the following linkers:
|
||||
- **gold (via the gold-plugin)**:
|
||||
Similar to monolithic LTO, this requires using
|
||||
a `gold linker configured with plugins enabled
|
||||
<http://llvm.org/docs/GoldPlugin.html>`_.
|
||||
<https://llvm.org/docs/GoldPlugin.html>`_.
|
||||
- **ld64**:
|
||||
Starting with `Xcode 8 <https://developer.apple.com/xcode/>`_.
|
||||
- **lld**:
|
||||
@ -99,13 +99,15 @@ With gold, if you see an error during the link of the form:
|
||||
Then either gold was not configured with plugins enabled, or clang
|
||||
was not built with ``-DLLVM_BINUTILS_INCDIR`` set properly. See
|
||||
the instructions for the
|
||||
`LLVM gold plugin <http://llvm.org/docs/GoldPlugin.html#how-to-build-it>`_.
|
||||
`LLVM gold plugin <https://llvm.org/docs/GoldPlugin.html#how-to-build-it>`_.
|
||||
|
||||
Controlling Backend Parallelism
|
||||
-------------------------------
|
||||
.. _parallelism:
|
||||
|
||||
By default, the ThinLTO link step will launch up to
|
||||
By default, the ThinLTO link step will launch as many
|
||||
threads in parallel as there are cores. If the number of
|
||||
cores can't be computed for the architecture, then it will launch
|
||||
``std::thread::hardware_concurrency`` number of threads in parallel.
|
||||
For machines with hyper-threading, this is the total number of
|
||||
virtual cores. For some applications and machine configurations this
|
||||
@ -196,9 +198,9 @@ To bootstrap clang/LLVM with ThinLTO, follow these steps:
|
||||
|
||||
1. The host compiler_ must be a version of clang that supports ThinLTO.
|
||||
#. The host linker_ must support ThinLTO (and in the case of gold, must be
|
||||
`configured with plugins enabled <http://llvm.org/docs/GoldPlugin.html>`_.
|
||||
`configured with plugins enabled <https://llvm.org/docs/GoldPlugin.html>`_.
|
||||
#. Use the following additional `CMake variables
|
||||
<http://llvm.org/docs/CMake.html#options-and-variables>`_
|
||||
<https://llvm.org/docs/CMake.html#options-and-variables>`_
|
||||
when configuring the bootstrap compiler build:
|
||||
|
||||
* ``-DLLVM_ENABLE_LTO=Thin``
|
||||
|
@ -12,7 +12,7 @@ ThreadSanitizer is about **5x-10x**.
|
||||
How to build
|
||||
------------
|
||||
|
||||
Build LLVM/Clang with `CMake <http://llvm.org/docs/CMake.html>`_.
|
||||
Build LLVM/Clang with `CMake <https://llvm.org/docs/CMake.html>`_.
|
||||
|
||||
Supported Platforms
|
||||
-------------------
|
||||
|
@ -100,14 +100,14 @@ currently-supported languages are:
|
||||
|
||||
In each case, GCC will be invoked to compile the input.
|
||||
|
||||
Assember
|
||||
--------
|
||||
Assembler
|
||||
---------
|
||||
|
||||
Clang can either use LLVM's integrated assembler or an external system-specific
|
||||
tool (for instance, the GNU Assembler on GNU OSes) to produce machine code from
|
||||
assembly.
|
||||
By default, Clang uses LLVM's integrated assembler on all targets where it is
|
||||
supported. If you wish to use the system assember instead, use the
|
||||
supported. If you wish to use the system assembler instead, use the
|
||||
``-fno-integrated-as`` option.
|
||||
|
||||
Linker
|
||||
@ -121,7 +121,7 @@ Clang can be configured to use one of several different linkers:
|
||||
* MSVC's link.exe
|
||||
|
||||
Link-time optimization is natively supported by lld, and supported via
|
||||
a `linker plugin <http://llvm.org/docs/GoldPlugin.html>`_ when using gold.
|
||||
a `linker plugin <https://llvm.org/docs/GoldPlugin.html>`_ when using gold.
|
||||
|
||||
The default linker varies between targets, and can be overridden via the
|
||||
``-fuse-ld=<linker name>`` flag.
|
||||
@ -233,7 +233,7 @@ LLVM's unwinder library can be obtained from subversion:
|
||||
|
||||
.. code-block:: console
|
||||
|
||||
llvm-src$ svn co http://llvm.org/svn/llvm-project/libunwind/trunk projects/libunwind
|
||||
llvm-src$ svn co https://llvm.org/svn/llvm-project/libunwind/trunk projects/libunwind
|
||||
|
||||
When checked out into projects/libunwind within an LLVM checkout,
|
||||
it should be automatically picked up by the LLVM build system.
|
||||
|
@ -9,7 +9,7 @@ the different ways to write clang tools, and their pros and cons.
|
||||
LibClang
|
||||
--------
|
||||
|
||||
`LibClang <http://clang.llvm.org/doxygen/group__CINDEX.html>`_ is a stable high
|
||||
`LibClang <https://clang.llvm.org/doxygen/group__CINDEX.html>`_ is a stable high
|
||||
level C interface to clang. When in doubt LibClang is probably the interface
|
||||
you want to use. Consider the other interfaces only when you have a good
|
||||
reason not to use LibClang.
|
||||
|
@ -25,7 +25,7 @@ The checks have small runtime cost and no impact on address space layout or ABI.
|
||||
How to build
|
||||
============
|
||||
|
||||
Build LLVM/Clang with `CMake <http://llvm.org/docs/CMake.html>`_.
|
||||
Build LLVM/Clang with `CMake <https://llvm.org/docs/CMake.html>`_.
|
||||
|
||||
Usage
|
||||
=====
|
||||
@ -72,7 +72,7 @@ Available checks
|
||||
Available checks are:
|
||||
|
||||
- ``-fsanitize=alignment``: Use of a misaligned pointer or creation
|
||||
of a misaligned reference.
|
||||
of a misaligned reference. Also sanitizes assume_aligned-like attributes.
|
||||
- ``-fsanitize=bool``: Load of a ``bool`` value which is neither
|
||||
``true`` nor ``false``.
|
||||
- ``-fsanitize=builtin``: Passing invalid values to compiler builtins.
|
||||
@ -89,10 +89,21 @@ Available checks are:
|
||||
- ``-fsanitize=function``: Indirect call of a function through a
|
||||
function pointer of the wrong type (Darwin/Linux, C++ and x86/x86_64
|
||||
only).
|
||||
- ``-fsanitize=implicit-integer-truncation``: Implicit conversion from
|
||||
- ``-fsanitize=implicit-unsigned-integer-truncation``,
|
||||
``-fsanitize=implicit-signed-integer-truncation``: Implicit conversion from
|
||||
integer of larger bit width to smaller bit width, if that results in data
|
||||
loss. That is, if the demoted value, after casting back to the original
|
||||
width, is not equal to the original value before the downcast.
|
||||
The ``-fsanitize=implicit-unsigned-integer-truncation`` handles conversions
|
||||
between two ``unsigned`` types, while
|
||||
``-fsanitize=implicit-signed-integer-truncation`` handles the rest of the
|
||||
conversions - when either one, or both of the types are signed.
|
||||
Issues caught by these sanitizers are not undefined behavior,
|
||||
but are often unintentional.
|
||||
- ``-fsanitize=implicit-integer-sign-change``: Implicit conversion between
|
||||
integer types, if that changes the sign of the value. That is, if the the
|
||||
original value was negative and the new value is positive (or zero),
|
||||
or the original value was positive, and the new value is negative.
|
||||
Issues caught by this sanitizer are not undefined behavior,
|
||||
but are often unintentional.
|
||||
- ``-fsanitize=integer-divide-by-zero``: Integer division by zero.
|
||||
@ -156,13 +167,24 @@ You can also use the following check groups:
|
||||
``nullability-*`` group of checks.
|
||||
- ``-fsanitize=undefined-trap``: Deprecated alias of
|
||||
``-fsanitize=undefined``.
|
||||
- ``-fsanitize=implicit-integer-truncation``: Catches lossy integral
|
||||
conversions. Enables ``implicit-signed-integer-truncation`` and
|
||||
``implicit-unsigned-integer-truncation``.
|
||||
- ``-fsanitize=implicit-integer-arithmetic-value-change``: Catches implicit
|
||||
conversions that change the arithmetic value of the integer. Enables
|
||||
``implicit-signed-integer-truncation`` and ``implicit-integer-sign-change``.
|
||||
- ``-fsanitize=implicit-conversion``: Checks for suspicious
|
||||
behaviour of implicit conversions. Enables
|
||||
``implicit-unsigned-integer-truncation``,
|
||||
``implicit-signed-integer-truncation`` and
|
||||
``implicit-integer-sign-change``.
|
||||
- ``-fsanitize=integer``: Checks for undefined or suspicious integer
|
||||
behavior (e.g. unsigned integer overflow).
|
||||
Enables ``signed-integer-overflow``, ``unsigned-integer-overflow``,
|
||||
``shift``, ``integer-divide-by-zero``, and ``implicit-integer-truncation``.
|
||||
- ``-fsanitize=implicit-conversion``: Checks for suspicious behaviours of
|
||||
implicit conversions.
|
||||
Currently, only ``-fsanitize=implicit-integer-truncation`` is implemented.
|
||||
``shift``, ``integer-divide-by-zero``,
|
||||
``implicit-unsigned-integer-truncation``,
|
||||
``implicit-signed-integer-truncation`` and
|
||||
``implicit-integer-sign-change``.
|
||||
- ``-fsanitize=nullability``: Enables ``nullability-arg``,
|
||||
``nullability-assign``, and ``nullability-return``. While violating
|
||||
nullability does not have undefined behavior, it is often unintentional,
|
||||
@ -266,7 +288,7 @@ There are several limitations:
|
||||
Supported Platforms
|
||||
===================
|
||||
|
||||
UndefinedBehaviorSanitizer is supported on the following OS:
|
||||
UndefinedBehaviorSanitizer is supported on the following operating systems:
|
||||
|
||||
* Android
|
||||
* Linux
|
||||
@ -274,6 +296,11 @@ UndefinedBehaviorSanitizer is supported on the following OS:
|
||||
* FreeBSD
|
||||
* OpenBSD
|
||||
* OS X 10.6 onwards
|
||||
* Windows
|
||||
|
||||
The runtime library is relatively portable and platform independent. If the OS
|
||||
you need is not listed above, UndefinedBehaviorSanitizer may already work for
|
||||
it, or could be made to work with a minor porting effort.
|
||||
|
||||
Current Status
|
||||
==============
|
||||
@ -296,6 +323,7 @@ Example
|
||||
-------
|
||||
|
||||
For a file called ``/code/library/file.cpp``, here is what would be emitted:
|
||||
|
||||
* Default (No flag, or ``-fsanitize-undefined-strip-path-components=0``): ``/code/library/file.cpp``
|
||||
* ``-fsanitize-undefined-strip-path-components=1``: ``code/library/file.cpp``
|
||||
* ``-fsanitize-undefined-strip-path-components=2``: ``library/file.cpp``
|
||||
|
@ -22,7 +22,7 @@ This document describes important notes about using Clang as a compiler
|
||||
for an end-user, documenting the supported features, command line
|
||||
options, etc. If you are interested in using Clang to build a tool that
|
||||
processes code, please see :doc:`InternalsManual`. If you are interested in the
|
||||
`Clang Static Analyzer <http://clang-analyzer.llvm.org>`_, please see its web
|
||||
`Clang Static Analyzer <https://clang-analyzer.llvm.org>`_, please see its web
|
||||
page.
|
||||
|
||||
Clang is one component in a complete toolchain for C family languages.
|
||||
@ -587,7 +587,7 @@ Options to Control Clang Crash Diagnostics
|
||||
|
||||
As unbelievable as it may sound, Clang does crash from time to time.
|
||||
Generally, this only occurs to those living on the `bleeding
|
||||
edge <http://llvm.org/releases/download.html#svn>`_. Clang goes to great
|
||||
edge <https://llvm.org/releases/download.html#svn>`_. Clang goes to great
|
||||
lengths to assist you in filing a bug report. Specifically, Clang
|
||||
generates preprocessed source file(s) and associated run script(s) upon
|
||||
a crash. These files should be attached to a bug report to ease
|
||||
@ -982,11 +982,11 @@ Controlling Static Analyzer Diagnostics
|
||||
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
While not strictly part of the compiler, the diagnostics from Clang's
|
||||
`static analyzer <http://clang-analyzer.llvm.org>`_ can also be
|
||||
`static analyzer <https://clang-analyzer.llvm.org>`_ can also be
|
||||
influenced by the user via changes to the source code. See the available
|
||||
`annotations <http://clang-analyzer.llvm.org/annotations.html>`_ and the
|
||||
`annotations <https://clang-analyzer.llvm.org/annotations.html>`_ and the
|
||||
analyzer's `FAQ
|
||||
page <http://clang-analyzer.llvm.org/faq.html#exclude_code>`_ for more
|
||||
page <https://clang-analyzer.llvm.org/faq.html#exclude_code>`_ for more
|
||||
information.
|
||||
|
||||
.. _usersmanual-precompiled-headers:
|
||||
@ -1799,6 +1799,127 @@ In these cases, you can use the flag ``-fno-profile-instr-generate`` (or
|
||||
Note that these flags should appear after the corresponding profile
|
||||
flags to have an effect.
|
||||
|
||||
Profile remapping
|
||||
^^^^^^^^^^^^^^^^^
|
||||
|
||||
When the program is compiled after a change that affects many symbol names,
|
||||
pre-existing profile data may no longer match the program. For example:
|
||||
|
||||
* switching from libstdc++ to libc++ will result in the mangled names of all
|
||||
functions taking standard library types to change
|
||||
* renaming a widely-used type in C++ will result in the mangled names of all
|
||||
functions that have parameters involving that type to change
|
||||
* moving from a 32-bit compilation to a 64-bit compilation may change the
|
||||
underlying type of ``size_t`` and similar types, resulting in changes to
|
||||
manglings
|
||||
|
||||
Clang allows use of a profile remapping file to specify that such differences
|
||||
in mangled names should be ignored when matching the profile data against the
|
||||
program.
|
||||
|
||||
.. option:: -fprofile-remapping-file=<file>
|
||||
|
||||
Specifies a file containing profile remapping information, that will be
|
||||
used to match mangled names in the profile data to mangled names in the
|
||||
program.
|
||||
|
||||
The profile remapping file is a text file containing lines of the form
|
||||
|
||||
.. code-block:: text
|
||||
|
||||
fragmentkind fragment1 fragment2
|
||||
|
||||
where ``fragmentkind`` is one of ``name``, ``type``, or ``encoding``,
|
||||
indicating whether the following mangled name fragments are
|
||||
<`name <http://itanium-cxx-abi.github.io/cxx-abi/abi.html#mangle.name>`_>s,
|
||||
<`type <http://itanium-cxx-abi.github.io/cxx-abi/abi.html#mangle.type>`_>s, or
|
||||
<`encoding <http://itanium-cxx-abi.github.io/cxx-abi/abi.html#mangle.encoding>`_>s,
|
||||
respectively.
|
||||
Blank lines and lines starting with ``#`` are ignored.
|
||||
|
||||
For convenience, built-in <substitution>s such as ``St`` and ``Ss``
|
||||
are accepted as <name>s (even though they technically are not <name>s).
|
||||
|
||||
For example, to specify that ``absl::string_view`` and ``std::string_view``
|
||||
should be treated as equivalent when matching profile data, the following
|
||||
remapping file could be used:
|
||||
|
||||
.. code-block:: text
|
||||
|
||||
# absl::string_view is considered equivalent to std::string_view
|
||||
type N4absl11string_viewE St17basic_string_viewIcSt11char_traitsIcEE
|
||||
|
||||
# std:: might be std::__1:: in libc++ or std::__cxx11:: in libstdc++
|
||||
name 3std St3__1
|
||||
name 3std St7__cxx11
|
||||
|
||||
Matching profile data using a profile remapping file is supported on a
|
||||
best-effort basis. For example, information regarding indirect call targets is
|
||||
currently not remapped. For best results, you are encouraged to generate new
|
||||
profile data matching the updated program, or to remap the profile data
|
||||
using the ``llvm-cxxmap`` and ``llvm-profdata merge`` tools.
|
||||
|
||||
.. note::
|
||||
|
||||
Profile data remapping support is currently only implemented for LLVM's
|
||||
new pass manager, which can be enabled with
|
||||
``-fexperimental-new-pass-manager``.
|
||||
|
||||
.. note::
|
||||
|
||||
Profile data remapping is currently only supported for C++ mangled names
|
||||
following the Itanium C++ ABI mangling scheme. This covers all C++ targets
|
||||
supported by Clang other than Windows.
|
||||
|
||||
GCOV-based Profiling
|
||||
--------------------
|
||||
|
||||
GCOV is a test coverage program, it helps to know how often a line of code
|
||||
is executed. When instrumenting the code with ``--coverage`` option, some
|
||||
counters are added for each edge linking basic blocks.
|
||||
|
||||
At compile time, gcno files are generated containing information about
|
||||
blocks and edges between them. At runtime the counters are incremented and at
|
||||
exit the counters are dumped in gcda files.
|
||||
|
||||
The tool ``llvm-cov gcov`` will parse gcno, gcda and source files to generate
|
||||
a report ``.c.gcov``.
|
||||
|
||||
.. option:: -fprofile-filter-files=[regexes]
|
||||
|
||||
Define a list of regexes separated by a semi-colon.
|
||||
If a file name matches any of the regexes then the file is instrumented.
|
||||
|
||||
.. code-block:: console
|
||||
|
||||
$ clang --coverage -fprofile-filter-files=".*\.c$" foo.c
|
||||
|
||||
For example, this will only instrument files finishing with ``.c``, skipping ``.h`` files.
|
||||
|
||||
.. option:: -fprofile-exclude-files=[regexes]
|
||||
|
||||
Define a list of regexes separated by a semi-colon.
|
||||
If a file name doesn't match all the regexes then the file is instrumented.
|
||||
|
||||
.. code-block:: console
|
||||
|
||||
$ clang --coverage -fprofile-exclude-files="^/usr/include/.*$" foo.c
|
||||
|
||||
For example, this will instrument all the files except the ones in ``/usr/include``.
|
||||
|
||||
If both options are used then a file is instrumented if its name matches any
|
||||
of the regexes from ``-fprofile-filter-list`` and doesn't match all the regexes
|
||||
from ``-fprofile-exclude-list``.
|
||||
|
||||
.. code-block:: console
|
||||
|
||||
$ clang --coverage -fprofile-exclude-files="^/usr/include/.*$" \
|
||||
-fprofile-filter-files="^/usr/.*$"
|
||||
|
||||
In that case ``/usr/foo/oof.h`` is instrumented since it matches the filter regex and
|
||||
doesn't match the exclude regex, but ``/usr/include/foo.h`` doesn't since it matches
|
||||
the exclude regex.
|
||||
|
||||
Controlling Debug Information
|
||||
-----------------------------
|
||||
|
||||
@ -2086,7 +2207,7 @@ comment(lib)`` are well supported.
|
||||
clang has a ``-fms-compatibility`` flag that makes clang accept enough
|
||||
invalid C++ to be able to parse most Microsoft headers. For example, it
|
||||
allows `unqualified lookup of dependent base class members
|
||||
<http://clang.llvm.org/compatibility.html#dep_lookup_bases>`_, which is
|
||||
<https://clang.llvm.org/compatibility.html#dep_lookup_bases>`_, which is
|
||||
a common compatibility issue with clang. This flag is enabled by default
|
||||
for Windows targets.
|
||||
|
||||
@ -2711,16 +2832,17 @@ Command Prompt or a regular Command Prompt where the environment has been set
|
||||
up using e.g. `vcvarsall.bat <http://msdn.microsoft.com/en-us/library/f2ccy3wt.aspx>`_.
|
||||
|
||||
clang-cl can also be used from inside Visual Studio by selecting the LLVM
|
||||
Platform Toolset. The toolset is installed by the LLVM installer, which can be
|
||||
downloaded from the `LLVM release <http://releases.llvm.org/download.html>`_ or
|
||||
`snapshot build <http://llvm.org/builds/>`_ web pages. To use the toolset,
|
||||
select a project in Solution Explorer, open its Property Page (Alt+F7), and in
|
||||
the "General" section of "Configuration Properties" change "Platform Toolset"
|
||||
to e.g. LLVM-vs2014.
|
||||
Platform Toolset. The toolset is not part of the installer, but may be installed
|
||||
separately from the
|
||||
`Visual Studio Marketplace <https://marketplace.visualstudio.com/items?itemName=LLVMExtensions.llvm-toolchain>`_.
|
||||
To use the toolset, select a project in Solution Explorer, open its Property
|
||||
Page (Alt+F7), and in the "General" section of "Configuration Properties"
|
||||
change "Platform Toolset" to LLVM. Doing so enables an additional Property
|
||||
Page for selecting the clang-cl executable to use for builds.
|
||||
|
||||
To use the toolset with MSBuild directly, invoke it with e.g.
|
||||
``/p:PlatformToolset=LLVM-vs2014``. This allows trying out the clang-cl
|
||||
toolchain without modifying your project files.
|
||||
``/p:PlatformToolset=LLVM``. This allows trying out the clang-cl toolchain
|
||||
without modifying your project files.
|
||||
|
||||
It's also possible to point MSBuild at clang-cl without changing toolset by
|
||||
passing ``/p:CLToolPath=c:\llvm\bin /p:CLToolExe=clang-cl.exe``.
|
||||
@ -2729,7 +2851,7 @@ When using CMake and the Visual Studio generators, the toolset can be set with t
|
||||
|
||||
::
|
||||
|
||||
cmake -G"Visual Studio 15 2017" -T LLVM-vs2014 ..
|
||||
cmake -G"Visual Studio 15 2017" -T LLVM ..
|
||||
|
||||
When using CMake with the Ninja generator, set the ``CMAKE_C_COMPILER`` and
|
||||
``CMAKE_CXX_COMPILER`` variables to clang-cl:
|
||||
@ -2776,6 +2898,7 @@ Execute ``clang-cl /?`` to see a list of supported options:
|
||||
/arch:<value> Set architecture for code generation
|
||||
/Brepro- Emit an object file which cannot be reproduced over time
|
||||
/Brepro Emit an object file which can be reproduced over time
|
||||
/clang:<arg> Pass <arg> to the clang driver
|
||||
/C Don't discard comments when preprocessing
|
||||
/c Compile only
|
||||
/d1PP Retain macro definitions in /E mode
|
||||
@ -2805,20 +2928,23 @@ Execute ``clang-cl /?`` to see a list of supported options:
|
||||
/GA Assume thread-local variables are defined in the executable
|
||||
/Gd Set __cdecl as a default calling convention
|
||||
/GF- Disable string pooling
|
||||
/GF Enable string pooling (default)
|
||||
/GR- Disable emission of RTTI data
|
||||
/Gregcall Set __regcall as a default calling convention
|
||||
/GR Enable emission of RTTI data
|
||||
/Gr Set __fastcall as a default calling convention
|
||||
/GS- Disable buffer security check
|
||||
/GS Enable buffer security check
|
||||
/Gs<value> Set stack probe size
|
||||
/guard:<value> Enable Control Flow Guard with /guard:cf
|
||||
/GS Enable buffer security check (default)
|
||||
/Gs Use stack probes (default)
|
||||
/Gs<value> Set stack probe size (default 4096)
|
||||
/guard:<value> Enable Control Flow Guard with /guard:cf,
|
||||
or only the table with /guard:cf,nochecks
|
||||
/Gv Set __vectorcall as a default calling convention
|
||||
/Gw- Don't put each data item in its own section
|
||||
/Gw Put each data item in its own section
|
||||
/GX- Disable exception handling
|
||||
/GX Enable exception handling
|
||||
/Gy- Don't put each function in its own section
|
||||
/Gy- Don't put each function in its own section (default)
|
||||
/Gy Put each function in its own section
|
||||
/Gz Set __stdcall as a default calling convention
|
||||
/help Display available options
|
||||
@ -2832,16 +2958,28 @@ Execute ``clang-cl /?`` to see a list of supported options:
|
||||
/MD Use DLL run-time
|
||||
/MTd Use static debug run-time
|
||||
/MT Use static run-time
|
||||
/O0 Disable optimization
|
||||
/O1 Optimize for size (same as /Og /Os /Oy /Ob2 /GF /Gy)
|
||||
/O2 Optimize for speed (same as /Og /Oi /Ot /Oy /Ob2 /GF /Gy)
|
||||
/Ob0 Disable function inlining
|
||||
/Ob1 Only inline functions which are (explicitly or implicitly) marked inline
|
||||
/Ob2 Inline functions as deemed beneficial by the compiler
|
||||
/Od Disable optimization
|
||||
/Og No effect
|
||||
/Oi- Disable use of builtin functions
|
||||
/Oi Enable use of builtin functions
|
||||
/Os Optimize for size
|
||||
/Ot Optimize for speed
|
||||
/O<value> Optimization level
|
||||
/Ox Deprecated (same as /Og /Oi /Ot /Oy /Ob2); use /O2 instead
|
||||
/Oy- Disable frame pointer omission (x86 only, default)
|
||||
/Oy Enable frame pointer omission (x86 only)
|
||||
/O<flags> Set multiple /O flags at once; e.g. '/O2y-' for '/O2 /Oy-'
|
||||
/o <file or directory> Set output file or directory (ends in / or \)
|
||||
/P Preprocess to file
|
||||
/Qvec- Disable the loop vectorization passes
|
||||
/Qvec Enable the loop vectorization passes
|
||||
/showFilenames- Don't print the name of each compiled file (default)
|
||||
/showFilenames Print the name of each compiled file
|
||||
/showIncludes Print info about included files to stderr
|
||||
/source-charset:<value> Source encoding, supports only UTF-8
|
||||
/std:<value> Language standard to compile for
|
||||
@ -2873,6 +3011,8 @@ Execute ``clang-cl /?`` to see a list of supported options:
|
||||
/Yc<filename> Generate a pch file for all code up to and including <filename>
|
||||
/Yu<filename> Load a pch file and use it instead of all code up to and including <filename>
|
||||
/Z7 Enable CodeView debug information in object files
|
||||
/Zc:dllexportInlines- Don't dllexport/dllimport inline member functions of dllexport/import classes
|
||||
/Zc:dllexportInlines dllexport/dllimport inline member functions of dllexport/import classes (default)
|
||||
/Zc:sizedDealloc- Disable C++14 sized global deallocation functions
|
||||
/Zc:sizedDealloc Enable C++14 sized global deallocation functions
|
||||
/Zc:strictStrings Treat string literals as const
|
||||
@ -2924,13 +3064,16 @@ Execute ``clang-cl /?`` to see a list of supported options:
|
||||
-fno-complete-member-pointers
|
||||
Do not require member pointer base types to be complete if they would be significant under the Microsoft ABI
|
||||
-fno-coverage-mapping Disable code coverage analysis
|
||||
-fno-crash-diagnostics Disable auto-generation of preprocessed source files and a script for reproduction during a clang crash
|
||||
-fno-debug-macro Do not emit macro debug information
|
||||
-fno-delayed-template-parsing
|
||||
Disable delayed template parsing
|
||||
-fno-sanitize-address-poison-class-member-array-new-cookie
|
||||
Disable poisoning array cookies when using class member operator new[] in AddressSanitizer
|
||||
-fno-sanitize-address-poison-custom-array-cookie
|
||||
Disable poisoning array cookies when using custom operator new[] in AddressSanitizer
|
||||
-fno-sanitize-address-use-after-scope
|
||||
Disable use-after-scope detection in AddressSanitizer
|
||||
-fno-sanitize-address-use-odr-indicator
|
||||
Disable ODR indicator globals
|
||||
-fno-sanitize-blacklist Don't use blacklist file for sanitizers
|
||||
-fno-sanitize-cfi-cross-dso
|
||||
Disable control flow integrity (CFI) checks for cross-DSO calls.
|
||||
@ -2952,6 +3095,11 @@ Execute ``clang-cl /?`` to see a list of supported options:
|
||||
-fno-sanitize-trap=<value>
|
||||
Disable trapping for specified sanitizers
|
||||
-fno-standalone-debug Limit debug information produced to reduce size of debug binary
|
||||
-fobjc-runtime=<value> Specify the target Objective-C runtime kind and version
|
||||
-fprofile-exclude-files=<value>
|
||||
Instrument only functions from files where names don't match all the regexes separated by a semi-colon
|
||||
-fprofile-filter-files=<value>
|
||||
Instrument only functions from files where names match any regex separated by a semi-colon
|
||||
-fprofile-instr-generate=<file>
|
||||
Generate instrumented code to collect execution counts into <file>
|
||||
(overridden by LLVM_PROFILE_FILE env var)
|
||||
@ -2960,14 +3108,18 @@ Execute ``clang-cl /?`` to see a list of supported options:
|
||||
(overridden by '=' form of option or LLVM_PROFILE_FILE env var)
|
||||
-fprofile-instr-use=<value>
|
||||
Use instrumentation data for profile-guided optimization
|
||||
-fprofile-remapping-file=<file>
|
||||
Use the remappings described in <file> to match the profile data against names in the program
|
||||
-fsanitize-address-field-padding=<value>
|
||||
Level of field padding for AddressSanitizer
|
||||
-fsanitize-address-globals-dead-stripping
|
||||
Enable linker dead stripping of globals in AddressSanitizer
|
||||
-fsanitize-address-poison-class-member-array-new-cookie
|
||||
Enable poisoning array cookies when using class member operator new[] in AddressSanitizer
|
||||
-fsanitize-address-poison-custom-array-cookie
|
||||
Enable poisoning array cookies when using custom operator new[] in AddressSanitizer
|
||||
-fsanitize-address-use-after-scope
|
||||
Enable use-after-scope detection in AddressSanitizer
|
||||
-fsanitize-address-use-odr-indicator
|
||||
Enable ODR indicator globals to avoid false ODR violation reports in partially sanitized programs at the cost of an increase in binary size
|
||||
-fsanitize-blacklist=<value>
|
||||
Path to blacklist file for sanitizers
|
||||
-fsanitize-cfi-cross-dso
|
||||
@ -2976,6 +3128,8 @@ Execute ``clang-cl /?`` to see a list of supported options:
|
||||
Generalize pointers in CFI indirect call type signature checks
|
||||
-fsanitize-coverage=<value>
|
||||
Specify the type of coverage instrumentation for Sanitizers
|
||||
-fsanitize-hwaddress-abi=<value>
|
||||
Select the HWAddressSanitizer ABI to target (interceptor or platform, default interceptor)
|
||||
-fsanitize-memory-track-origins=<value>
|
||||
Enable origins tracking in MemorySanitizer
|
||||
-fsanitize-memory-track-origins
|
||||
@ -2996,9 +3150,12 @@ Execute ``clang-cl /?`` to see a list of supported options:
|
||||
Strip (or keep only, if negative) a given number of path components when emitting check metadata.
|
||||
-fsanitize=<check> Turn on runtime checks for various forms of undefined or suspicious
|
||||
behavior. See user manual for available checks
|
||||
-fsplit-lto-unit Enables splitting of the LTO unit.
|
||||
-fstandalone-debug Emit full debug info for all types used by the program
|
||||
-fwhole-program-vtables Enables whole-program vtable optimization. Requires -flto
|
||||
-gcodeview-ghash Emit type record hashes in a .debug$H section
|
||||
-gcodeview Generate CodeView debug information
|
||||
-gline-directives-only Emit debug line info directives only
|
||||
-gline-tables-only Emit debug line number tables only
|
||||
-miamcu Use Intel MCU ABI
|
||||
-mllvm <value> Additional arguments to forward to LLVM's option processing
|
||||
@ -3011,6 +3168,92 @@ Execute ``clang-cl /?`` to see a list of supported options:
|
||||
-W<warning> Enable the specified warning
|
||||
-Xclang <arg> Pass <arg> to the clang compiler
|
||||
|
||||
The /clang: Option
|
||||
^^^^^^^^^^^^^^^^^^
|
||||
|
||||
When clang-cl is run with a set of ``/clang:<arg>`` options, it will gather all
|
||||
of the ``<arg>`` arguments and process them as if they were passed to the clang
|
||||
driver. This mechanism allows you to pass flags that are not exposed in the
|
||||
clang-cl options or flags that have a different meaning when passed to the clang
|
||||
driver. Regardless of where they appear in the command line, the ``/clang:``
|
||||
arguments are treated as if they were passed at the end of the clang-cl command
|
||||
line.
|
||||
|
||||
The /Zc:dllexportInlines- Option
|
||||
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
This causes the class-level `dllexport` and `dllimport` attributes to not apply
|
||||
to inline member functions, as they otherwise would. For example, in the code
|
||||
below `S::foo()` would normally be defined and exported by the DLL, but when
|
||||
using the ``/Zc:dllexportInlines-`` flag it is not:
|
||||
|
||||
.. code-block:: c
|
||||
|
||||
struct __declspec(dllexport) S {
|
||||
void foo() {}
|
||||
}
|
||||
|
||||
This has the benefit that the compiler doesn't need to emit a definition of
|
||||
`S::foo()` in every translation unit where the declaration is included, as it
|
||||
would otherwise do to ensure there's a definition in the DLL even if it's not
|
||||
used there. If the declaration occurs in a header file that's widely used, this
|
||||
can save significant compilation time and output size. It also reduces the
|
||||
number of functions exported by the DLL similarly to what
|
||||
``-fvisibility-inlines-hidden`` does for shared objects on ELF and Mach-O.
|
||||
Since the function declaration comes with an inline definition, users of the
|
||||
library can use that definition directly instead of importing it from the DLL.
|
||||
|
||||
Note that the Microsoft Visual C++ compiler does not support this option, and
|
||||
if code in a DLL is compiled with ``/Zc:dllexportInlines-``, the code using the
|
||||
DLL must be compiled in the same way so that it doesn't attempt to dllimport
|
||||
the inline member functions. The reverse scenario should generally work though:
|
||||
a DLL compiled without this flag (such as a system library compiled with Visual
|
||||
C++) can be referenced from code compiled using the flag, meaning that the
|
||||
referencing code will use the inline definitions instead of importing them from
|
||||
the DLL.
|
||||
|
||||
Also note that like when using ``-fvisibility-inlines-hidden``, the address of
|
||||
`S::foo()` will be different inside and outside the DLL, breaking the C/C++
|
||||
standard requirement that functions have a unique address.
|
||||
|
||||
The flag does not apply to explicit class template instantiation definitions or
|
||||
declarations, as those are typically used to explicitly provide a single
|
||||
definition in a DLL, (dllexported instantiation definition) or to signal that
|
||||
the definition is available elsewhere (dllimport instantiation declaration). It
|
||||
also doesn't apply to inline members with static local variables, to ensure
|
||||
that the same instance of the variable is used inside and outside the DLL.
|
||||
|
||||
Using this flag can cause problems when inline functions that would otherwise
|
||||
be dllexported refer to internal symbols of a DLL. For example:
|
||||
|
||||
.. code-block:: c
|
||||
|
||||
void internal();
|
||||
|
||||
struct __declspec(dllimport) S {
|
||||
void foo() { internal(); }
|
||||
}
|
||||
|
||||
Normally, references to `S::foo()` would use the definition in the DLL from
|
||||
which it was exported, and which presumably also has the definition of
|
||||
`internal()`. However, when using ``/Zc:dllexportInlines-``, the inline
|
||||
definition of `S::foo()` is used directly, resulting in a link error since
|
||||
`internal()` is not available. Even worse, if there is an inline definition of
|
||||
`internal()` containing a static local variable, we will now refer to a
|
||||
different instance of that variable than in the DLL:
|
||||
|
||||
.. code-block:: c
|
||||
|
||||
inline int internal() { static int x; return x++; }
|
||||
|
||||
struct __declspec(dllimport) S {
|
||||
int foo() { return internal(); }
|
||||
}
|
||||
|
||||
This could lead to very subtle bugs. Using ``-fvisibility-inlines-hidden`` can
|
||||
lead to the same issue. To avoid it in this case, make `S::foo()` or
|
||||
`internal()` non-inline, or mark them `dllimport/dllexport` explicitly.
|
||||
|
||||
The /fallback Option
|
||||
^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
|
@ -30,9 +30,12 @@ using a 'dot' format viewer (such as Graphviz on OS X) instead.
|
||||
- debug.DumpLiveVars: Show the results of live variable analysis for each
|
||||
top-level function being analyzed.
|
||||
|
||||
- debug.DumpLiveStmts: Show the results of live statement analysis for each
|
||||
top-level function being analyzed.
|
||||
|
||||
- debug.ViewExplodedGraph: Show the Exploded Graphs generated for the
|
||||
analysis of different functions in the input translation unit. When there
|
||||
are several functions analyzed, display one graph per function. Beware
|
||||
are several functions analyzed, display one graph per function. Beware
|
||||
that these graphs may grow very large, even for small functions.
|
||||
|
||||
Path Tracking
|
||||
@ -255,6 +258,23 @@ ExprInspection checks
|
||||
clang_analyzer_hashDump(x); // expected-warning{{hashed string for x}}
|
||||
}
|
||||
|
||||
- ``void clang_analyzer_denote(int, const char *);``
|
||||
|
||||
Denotes symbols with strings. A subsequent call to clang_analyzer_express()
|
||||
will expresses another symbol in terms of these string. Useful for testing
|
||||
relationships between different symbols.
|
||||
|
||||
Example usage::
|
||||
|
||||
void foo(int x) {
|
||||
clang_analyzer_denote(x, "$x");
|
||||
clang_analyzer_express(x + 1); // expected-warning{{$x + 1}}
|
||||
}
|
||||
|
||||
- ``void clang_analyzer_express(int);``
|
||||
|
||||
See clang_analyzer_denote().
|
||||
|
||||
Statistics
|
||||
==========
|
||||
|
||||
|
@ -118,7 +118,7 @@ sometimes zero, for static data, or "uninitialized", for stack variables).
|
||||
int manyInts[10];
|
||||
manyInts[1] = 42; // Creates a Direct binding for manyInts[1].
|
||||
print(manyInts[1]); // Retrieves the Direct binding for manyInts[1];
|
||||
print(manyInts[0]); // There is no Direct binding for manyInts[1].
|
||||
print(manyInts[0]); // There is no Direct binding for manyInts[0].
|
||||
// Is there a Default binding for the entire array?
|
||||
// There is not, but it is a stack variable, so we use
|
||||
// "uninitialized" as the default value (and emit a
|
||||
@ -166,6 +166,6 @@ Here's a concrete example:
|
||||
return p2.x; // The binding for FieldRegion 'p2.x' is requested.
|
||||
// There is no Direct binding, so we look for a Default
|
||||
// binding to 'p2' and find the LCV.
|
||||
// Because it's an LCV, we look at our requested region
|
||||
// Because it's a LCV, we look at our requested region
|
||||
// and see that it's the '.x' field. We ask for the value
|
||||
// of 'p.x' within the snapshot, and get back 42.
|
||||
|
13
docs/conf.py
13
docs/conf.py
@ -11,6 +11,7 @@
|
||||
# All configuration values have a default; values that are commented out
|
||||
# serve to show the default.
|
||||
|
||||
from __future__ import absolute_import, division, print_function
|
||||
import sys, os
|
||||
from datetime import date
|
||||
|
||||
@ -49,9 +50,9 @@
|
||||
# built documents.
|
||||
#
|
||||
# The short version.
|
||||
version = '7'
|
||||
version = '8'
|
||||
# The full version, including alpha/beta/rc tags.
|
||||
release = '7'
|
||||
release = '8'
|
||||
|
||||
# The language for content autogenerated by Sphinx. Refer to documentation
|
||||
# for a list of supported languages.
|
||||
@ -233,14 +234,14 @@
|
||||
header = f.readline().rstrip('\n')
|
||||
|
||||
if len(header) != len(title):
|
||||
print >>sys.stderr, (
|
||||
print((
|
||||
"error: invalid header in %r (does not match title)" % (
|
||||
file_subpath,))
|
||||
file_subpath,)), file=sys.stderr)
|
||||
if ' - ' not in title:
|
||||
print >>sys.stderr, (
|
||||
print((
|
||||
("error: invalid title in %r "
|
||||
"(expected '<name> - <description>')") % (
|
||||
file_subpath,))
|
||||
file_subpath,)), file=sys.stderr)
|
||||
|
||||
# Split the name out of the title.
|
||||
name,description = title.split(' - ', 1)
|
||||
|
@ -83,7 +83,6 @@ Design Documents
|
||||
|
||||
InternalsManual
|
||||
DriverInternals
|
||||
PTHInternals
|
||||
PCHInternals
|
||||
ItaniumMangleAbiTags
|
||||
HardwareAssistedAddressSanitizerDesign.rst
|
||||
|
@ -5,7 +5,10 @@
|
||||
|
||||
import collections
|
||||
import re
|
||||
import urllib2
|
||||
try:
|
||||
from urllib.request import urlopen
|
||||
except ImportError:
|
||||
from urllib2 import urlopen
|
||||
|
||||
MATCHERS_FILE = '../../include/clang/ASTMatchers/ASTMatchers.h'
|
||||
|
||||
@ -38,11 +41,11 @@ def esc(text):
|
||||
text = re.sub(r'>', '>', text)
|
||||
def link_if_exists(m):
|
||||
name = m.group(1)
|
||||
url = 'http://clang.llvm.org/doxygen/classclang_1_1%s.html' % name
|
||||
url = 'https://clang.llvm.org/doxygen/classclang_1_1%s.html' % name
|
||||
if url not in doxygen_probes:
|
||||
try:
|
||||
print 'Probing %s...' % url
|
||||
urllib2.urlopen(url)
|
||||
print('Probing %s...' % url)
|
||||
urlopen(url)
|
||||
doxygen_probes[url] = True
|
||||
except:
|
||||
doxygen_probes[url] = False
|
||||
@ -181,9 +184,9 @@ def act_on_decl(declaration, comment, allowed_types):
|
||||
raise Exception('Inconsistent documentation for: %s' % name)
|
||||
for result_type in result_types:
|
||||
add_matcher(result_type, name, 'Matcher<Type>', comment)
|
||||
if loc:
|
||||
add_matcher('%sLoc' % result_type, '%sLoc' % name, 'Matcher<TypeLoc>',
|
||||
comment)
|
||||
# if loc:
|
||||
# add_matcher('%sLoc' % result_type, '%sLoc' % name, 'Matcher<TypeLoc>',
|
||||
# comment)
|
||||
return
|
||||
|
||||
m = re.match(r"""^\s*AST_POLYMORPHIC_MATCHER(_P)?(.?)(?:_OVERLOAD)?\(
|
||||
@ -307,14 +310,14 @@ def act_on_decl(declaration, comment, allowed_types):
|
||||
if not result_types:
|
||||
if not comment:
|
||||
# Only overloads don't have their own doxygen comments; ignore those.
|
||||
print 'Ignoring "%s"' % name
|
||||
print('Ignoring "%s"' % name)
|
||||
else:
|
||||
print 'Cannot determine result type for "%s"' % name
|
||||
print('Cannot determine result type for "%s"' % name)
|
||||
else:
|
||||
for result_type in result_types:
|
||||
add_matcher(result_type, name, args, comment)
|
||||
else:
|
||||
print '*** Unparsable: "' + declaration + '" ***'
|
||||
print('*** Unparsable: "' + declaration + '" ***')
|
||||
|
||||
def sort_table(matcher_type, matcher_map):
|
||||
"""Returns the sorted html table for the given row map."""
|
||||
@ -354,7 +357,7 @@ def sort_table(matcher_type, matcher_map):
|
||||
allowed_types += [m.group(1)]
|
||||
continue
|
||||
if line.strip() and line.lstrip()[0] == '/':
|
||||
comment += re.sub(r'/+\s?', '', line) + '\n'
|
||||
comment += re.sub(r'^/+\s?', '', line) + '\n'
|
||||
else:
|
||||
declaration += ' ' + line
|
||||
if ((not line.strip()) or
|
||||
|
@ -6,7 +6,6 @@
|
||||
import collections
|
||||
import os
|
||||
import re
|
||||
import urllib2
|
||||
|
||||
CLANG_DIR = os.path.join(os.path.dirname(__file__), '../..')
|
||||
FORMAT_STYLE_FILE = os.path.join(CLANG_DIR, 'include/clang/Format/Format.h')
|
||||
@ -32,7 +31,7 @@ def indent(text, columns, indent_first_line=True):
|
||||
return s
|
||||
return indent + s
|
||||
|
||||
class Option:
|
||||
class Option(object):
|
||||
def __init__(self, name, type, comment):
|
||||
self.name = name
|
||||
self.type = type
|
||||
@ -50,7 +49,7 @@ def __str__(self):
|
||||
2)
|
||||
return s
|
||||
|
||||
class NestedStruct:
|
||||
class NestedStruct(object):
|
||||
def __init__(self, name, comment):
|
||||
self.name = name
|
||||
self.comment = comment.strip()
|
||||
@ -59,7 +58,7 @@ def __init__(self, name, comment):
|
||||
def __str__(self):
|
||||
return '\n'.join(map(str, self.values))
|
||||
|
||||
class NestedField:
|
||||
class NestedField(object):
|
||||
def __init__(self, name, comment):
|
||||
self.name = name
|
||||
self.comment = comment.strip()
|
||||
@ -69,7 +68,7 @@ def __str__(self):
|
||||
self.name,
|
||||
doxygen2rst(indent(self.comment, 2, indent_first_line=False)))
|
||||
|
||||
class Enum:
|
||||
class Enum(object):
|
||||
def __init__(self, name, comment):
|
||||
self.name = name
|
||||
self.comment = comment.strip()
|
||||
@ -78,7 +77,7 @@ def __init__(self, name, comment):
|
||||
def __str__(self):
|
||||
return '\n'.join(map(str, self.values))
|
||||
|
||||
class EnumValue:
|
||||
class EnumValue(object):
|
||||
def __init__(self, name, comment):
|
||||
self.name = name
|
||||
self.comment = comment
|
||||
@ -101,7 +100,7 @@ def clean_comment_line(line):
|
||||
return line[4:] + '\n'
|
||||
|
||||
def read_options(header):
|
||||
class State:
|
||||
class State(object):
|
||||
BeforeStruct, Finished, InStruct, InNestedStruct, InNestedFieldComent, \
|
||||
InFieldComment, InEnum, InEnumMemberComment = range(8)
|
||||
state = State.BeforeStruct
|
||||
@ -180,9 +179,9 @@ class State:
|
||||
'std::vector<std::string>',
|
||||
'std::vector<IncludeCategory>',
|
||||
'std::vector<RawStringFormat>']:
|
||||
if enums.has_key(option.type):
|
||||
if option.type in enums:
|
||||
option.enum = enums[option.type]
|
||||
elif nested_structs.has_key(option.type):
|
||||
elif option.type in nested_structs:
|
||||
option.nested_struct = nested_structs[option.type]
|
||||
else:
|
||||
raise Exception('Unknown type: %s' % option.type)
|
||||
|
@ -1,4 +1,4 @@
|
||||
add_llvm_loadable_module(AnnotateFunctions AnnotateFunctions.cpp PLUGIN_TOOL clang)
|
||||
add_llvm_library(AnnotateFunctions MODULE AnnotateFunctions.cpp PLUGIN_TOOL clang)
|
||||
|
||||
if(LLVM_ENABLE_PLUGINS AND (WIN32 OR CYGWIN))
|
||||
target_link_libraries(AnnotateFunctions PRIVATE
|
||||
|
@ -9,7 +9,7 @@ if( NOT MSVC ) # MSVC mangles symbols differently, and
|
||||
endif()
|
||||
endif()
|
||||
|
||||
add_llvm_loadable_module(PrintFunctionNames PrintFunctionNames.cpp PLUGIN_TOOL clang)
|
||||
add_llvm_library(PrintFunctionNames MODULE PrintFunctionNames.cpp PLUGIN_TOOL clang)
|
||||
|
||||
if(LLVM_ENABLE_PLUGINS AND (WIN32 OR CYGWIN))
|
||||
target_link_libraries(PrintFunctionNames PRIVATE
|
||||
|
@ -1,5 +1,5 @@
|
||||
set(LLVM_EXPORTED_SYMBOL_FILE ${CMAKE_CURRENT_SOURCE_DIR}/SampleAnalyzerPlugin.exports)
|
||||
add_llvm_loadable_module(SampleAnalyzerPlugin MainCallChecker.cpp PLUGIN_TOOL clang)
|
||||
add_llvm_library(SampleAnalyzerPlugin MODULE MainCallChecker.cpp PLUGIN_TOOL clang)
|
||||
|
||||
if(LLVM_ENABLE_PLUGINS AND (WIN32 OR CYGWIN))
|
||||
target_link_libraries(SampleAnalyzerPlugin PRIVATE
|
||||
|
@ -1,6 +1,6 @@
|
||||
#include "clang/StaticAnalyzer/Core/Checker.h"
|
||||
#include "clang/StaticAnalyzer/Core/BugReporter/BugType.h"
|
||||
#include "clang/StaticAnalyzer/Core/CheckerRegistry.h"
|
||||
#include "clang/StaticAnalyzer/Frontend/CheckerRegistry.h"
|
||||
#include "clang/StaticAnalyzer/Core/PathSensitive/CheckerContext.h"
|
||||
|
||||
using namespace clang;
|
||||
@ -45,7 +45,9 @@ void MainCallChecker::checkPreStmt(const CallExpr *CE, CheckerContext &C) const
|
||||
// Register plugin!
|
||||
extern "C"
|
||||
void clang_registerCheckers (CheckerRegistry ®istry) {
|
||||
registry.addChecker<MainCallChecker>("example.MainCallChecker", "Disallows calls to functions called main");
|
||||
registry.addChecker<MainCallChecker>(
|
||||
"example.MainCallChecker", "Disallows calls to functions called main",
|
||||
"");
|
||||
}
|
||||
|
||||
extern "C"
|
||||
|
@ -25,6 +25,7 @@ target_link_libraries(clang-interpreter
|
||||
clangCodeGen
|
||||
clangDriver
|
||||
clangFrontend
|
||||
clangSerialization
|
||||
)
|
||||
|
||||
export_executable_symbols(clang-interpreter)
|
||||
|
@ -21,7 +21,7 @@ static void ThrowerAnError(const char* Name) {
|
||||
int main(int argc, const char** argv) {
|
||||
for (int I = 0; I < argc; ++I)
|
||||
printf("arg[%d]='%s'\n", I, argv[I]);
|
||||
|
||||
|
||||
try {
|
||||
ThrowerAnError("In JIT");
|
||||
} catch (const std::exception& E) {
|
||||
|
@ -54,8 +54,8 @@ class SimpleJIT {
|
||||
std::shared_ptr<SymbolResolver> Resolver;
|
||||
std::unique_ptr<TargetMachine> TM;
|
||||
const DataLayout DL;
|
||||
RTDyldObjectLinkingLayer ObjectLayer;
|
||||
IRCompileLayer<decltype(ObjectLayer), SimpleCompiler> CompileLayer;
|
||||
LegacyRTDyldObjectLinkingLayer ObjectLayer;
|
||||
LegacyIRCompileLayer<decltype(ObjectLayer), SimpleCompiler> CompileLayer;
|
||||
|
||||
public:
|
||||
SimpleJIT()
|
||||
@ -75,7 +75,7 @@ class SimpleJIT {
|
||||
TM(EngineBuilder().selectTarget()), DL(TM->createDataLayout()),
|
||||
ObjectLayer(ES,
|
||||
[this](VModuleKey) {
|
||||
return RTDyldObjectLinkingLayer::Resources{
|
||||
return LegacyRTDyldObjectLinkingLayer::Resources{
|
||||
std::make_shared<SectionMemoryManager>(), Resolver};
|
||||
}),
|
||||
CompileLayer(ObjectLayer, SimpleCompiler(*TM)) {
|
||||
@ -164,7 +164,7 @@ int main(int argc, const char **argv) {
|
||||
}
|
||||
|
||||
// Initialize a compiler invocation object from the clang (-cc1) arguments.
|
||||
const driver::ArgStringList &CCArgs = Cmd.getArguments();
|
||||
const llvm::opt::ArgStringList &CCArgs = Cmd.getArguments();
|
||||
std::unique_ptr<CompilerInvocation> CI(new CompilerInvocation);
|
||||
CompilerInvocation::CreateFromArgs(*CI,
|
||||
const_cast<const char **>(CCArgs.data()),
|
||||
|
@ -32,7 +32,7 @@
|
||||
* compatible, thus CINDEX_VERSION_MAJOR is expected to remain stable.
|
||||
*/
|
||||
#define CINDEX_VERSION_MAJOR 0
|
||||
#define CINDEX_VERSION_MINOR 49
|
||||
#define CINDEX_VERSION_MINOR 50
|
||||
|
||||
#define CINDEX_VERSION_ENCODE(major, minor) ( \
|
||||
((major) * 10000) \
|
||||
@ -178,7 +178,6 @@ typedef struct CXVersion {
|
||||
* A negative value indicates that the cursor is not a function declaration.
|
||||
*/
|
||||
enum CXCursor_ExceptionSpecificationKind {
|
||||
|
||||
/**
|
||||
* The cursor has no exception specification.
|
||||
*/
|
||||
@ -1332,7 +1331,17 @@ enum CXTranslationUnit_Flags {
|
||||
*
|
||||
* The function bodies of the main file are not skipped.
|
||||
*/
|
||||
CXTranslationUnit_LimitSkipFunctionBodiesToPreamble = 0x800
|
||||
CXTranslationUnit_LimitSkipFunctionBodiesToPreamble = 0x800,
|
||||
|
||||
/**
|
||||
* Used to indicate that attributed types should be included in CXType.
|
||||
*/
|
||||
CXTranslationUnit_IncludeAttributedTypes = 0x1000,
|
||||
|
||||
/**
|
||||
* Used to indicate that implicit attributes should be visited.
|
||||
*/
|
||||
CXTranslationUnit_VisitImplicitAttributes = 0x2000
|
||||
};
|
||||
|
||||
/**
|
||||
@ -2559,7 +2568,25 @@ enum CXCursorKind {
|
||||
CXCursor_VisibilityAttr = 417,
|
||||
CXCursor_DLLExport = 418,
|
||||
CXCursor_DLLImport = 419,
|
||||
CXCursor_LastAttr = CXCursor_DLLImport,
|
||||
CXCursor_NSReturnsRetained = 420,
|
||||
CXCursor_NSReturnsNotRetained = 421,
|
||||
CXCursor_NSReturnsAutoreleased = 422,
|
||||
CXCursor_NSConsumesSelf = 423,
|
||||
CXCursor_NSConsumed = 424,
|
||||
CXCursor_ObjCException = 425,
|
||||
CXCursor_ObjCNSObject = 426,
|
||||
CXCursor_ObjCIndependentClass = 427,
|
||||
CXCursor_ObjCPreciseLifetime = 428,
|
||||
CXCursor_ObjCReturnsInnerPointer = 429,
|
||||
CXCursor_ObjCRequiresSuper = 430,
|
||||
CXCursor_ObjCRootClass = 431,
|
||||
CXCursor_ObjCSubclassingRestricted = 432,
|
||||
CXCursor_ObjCExplicitProtocolImpl = 433,
|
||||
CXCursor_ObjCDesignatedInitializer = 434,
|
||||
CXCursor_ObjCRuntimeVisible = 435,
|
||||
CXCursor_ObjCBoxable = 436,
|
||||
CXCursor_FlagEnum = 437,
|
||||
CXCursor_LastAttr = CXCursor_FlagEnum,
|
||||
|
||||
/* Preprocessing */
|
||||
CXCursor_PreprocessingDirective = 500,
|
||||
@ -3266,7 +3293,25 @@ enum CXTypeKind {
|
||||
CXType_OCLSampler = 157,
|
||||
CXType_OCLEvent = 158,
|
||||
CXType_OCLQueue = 159,
|
||||
CXType_OCLReserveID = 160
|
||||
CXType_OCLReserveID = 160,
|
||||
|
||||
CXType_ObjCObject = 161,
|
||||
CXType_ObjCTypeParam = 162,
|
||||
CXType_Attributed = 163,
|
||||
|
||||
CXType_OCLIntelSubgroupAVCMcePayload = 164,
|
||||
CXType_OCLIntelSubgroupAVCImePayload = 165,
|
||||
CXType_OCLIntelSubgroupAVCRefPayload = 166,
|
||||
CXType_OCLIntelSubgroupAVCSicPayload = 167,
|
||||
CXType_OCLIntelSubgroupAVCMceResult = 168,
|
||||
CXType_OCLIntelSubgroupAVCImeResult = 169,
|
||||
CXType_OCLIntelSubgroupAVCRefResult = 170,
|
||||
CXType_OCLIntelSubgroupAVCSicResult = 171,
|
||||
CXType_OCLIntelSubgroupAVCImeResultSingleRefStreamout = 172,
|
||||
CXType_OCLIntelSubgroupAVCImeResultDualRefStreamout = 173,
|
||||
CXType_OCLIntelSubgroupAVCImeSingleRefStreamin = 174,
|
||||
|
||||
CXType_OCLIntelSubgroupAVCImeDualRefStreamin = 175
|
||||
};
|
||||
|
||||
/**
|
||||
@ -3291,6 +3336,7 @@ enum CXCallingConv {
|
||||
CXCallingConv_Swift = 13,
|
||||
CXCallingConv_PreserveMost = 14,
|
||||
CXCallingConv_PreserveAll = 15,
|
||||
CXCallingConv_AArch64VectorCall = 16,
|
||||
|
||||
CXCallingConv_Invalid = 100,
|
||||
CXCallingConv_Unexposed = 200
|
||||
@ -3627,6 +3673,43 @@ CINDEX_LINKAGE int clang_getNumArgTypes(CXType T);
|
||||
*/
|
||||
CINDEX_LINKAGE CXType clang_getArgType(CXType T, unsigned i);
|
||||
|
||||
/**
|
||||
* Retrieves the base type of the ObjCObjectType.
|
||||
*
|
||||
* If the type is not an ObjC object, an invalid type is returned.
|
||||
*/
|
||||
CINDEX_LINKAGE CXType clang_Type_getObjCObjectBaseType(CXType T);
|
||||
|
||||
/**
|
||||
* Retrieve the number of protocol references associated with an ObjC object/id.
|
||||
*
|
||||
* If the type is not an ObjC object, 0 is returned.
|
||||
*/
|
||||
CINDEX_LINKAGE unsigned clang_Type_getNumObjCProtocolRefs(CXType T);
|
||||
|
||||
/**
|
||||
* Retrieve the decl for a protocol reference for an ObjC object/id.
|
||||
*
|
||||
* If the type is not an ObjC object or there are not enough protocol
|
||||
* references, an invalid cursor is returned.
|
||||
*/
|
||||
CINDEX_LINKAGE CXCursor clang_Type_getObjCProtocolDecl(CXType T, unsigned i);
|
||||
|
||||
/**
|
||||
* Retreive the number of type arguments associated with an ObjC object.
|
||||
*
|
||||
* If the type is not an ObjC object, 0 is returned.
|
||||
*/
|
||||
CINDEX_LINKAGE unsigned clang_Type_getNumObjCTypeArgs(CXType T);
|
||||
|
||||
/**
|
||||
* Retrieve a type argument associated with an ObjC object.
|
||||
*
|
||||
* If the type is not an ObjC or the index is not valid,
|
||||
* an invalid type is returned.
|
||||
*/
|
||||
CINDEX_LINKAGE CXType clang_Type_getObjCTypeArg(CXType T, unsigned i);
|
||||
|
||||
/**
|
||||
* Return 1 if the CXType is a variadic function type, and 0 otherwise.
|
||||
*/
|
||||
@ -3700,6 +3783,33 @@ CINDEX_LINKAGE CXType clang_Type_getNamedType(CXType T);
|
||||
*/
|
||||
CINDEX_LINKAGE unsigned clang_Type_isTransparentTagTypedef(CXType T);
|
||||
|
||||
enum CXTypeNullabilityKind {
|
||||
/**
|
||||
* Values of this type can never be null.
|
||||
*/
|
||||
CXTypeNullability_NonNull = 0,
|
||||
/**
|
||||
* Values of this type can be null.
|
||||
*/
|
||||
CXTypeNullability_Nullable = 1,
|
||||
/**
|
||||
* Whether values of this type can be null is (explicitly)
|
||||
* unspecified. This captures a (fairly rare) case where we
|
||||
* can't conclude anything about the nullability of the type even
|
||||
* though it has been considered.
|
||||
*/
|
||||
CXTypeNullability_Unspecified = 2,
|
||||
/**
|
||||
* Nullability is not applicable to this type.
|
||||
*/
|
||||
CXTypeNullability_Invalid = 3
|
||||
};
|
||||
|
||||
/**
|
||||
* Retrieve the nullability kind of a pointer type.
|
||||
*/
|
||||
CINDEX_LINKAGE enum CXTypeNullabilityKind clang_Type_getNullability(CXType T);
|
||||
|
||||
/**
|
||||
* List the possible error codes for \c clang_Type_getSizeOf,
|
||||
* \c clang_Type_getAlignOf, \c clang_Type_getOffsetOf and
|
||||
@ -3778,6 +3888,13 @@ CINDEX_LINKAGE long long clang_Type_getSizeOf(CXType T);
|
||||
*/
|
||||
CINDEX_LINKAGE long long clang_Type_getOffsetOf(CXType T, const char *S);
|
||||
|
||||
/**
|
||||
* Return the type that was modified by this attributed type.
|
||||
*
|
||||
* If the type is not an attributed type, an invalid type is returned.
|
||||
*/
|
||||
CINDEX_LINKAGE CXType clang_Type_getModifiedType(CXType T);
|
||||
|
||||
/**
|
||||
* Return the offset of the field represented by the Cursor.
|
||||
*
|
||||
@ -4347,6 +4464,18 @@ typedef enum {
|
||||
CINDEX_LINKAGE unsigned clang_Cursor_getObjCPropertyAttributes(CXCursor C,
|
||||
unsigned reserved);
|
||||
|
||||
/**
|
||||
* Given a cursor that represents a property declaration, return the
|
||||
* name of the method that implements the getter.
|
||||
*/
|
||||
CINDEX_LINKAGE CXString clang_Cursor_getObjCPropertyGetterName(CXCursor C);
|
||||
|
||||
/**
|
||||
* Given a cursor that represents a property declaration, return the
|
||||
* name of the method that implements the setter, if any.
|
||||
*/
|
||||
CINDEX_LINKAGE CXString clang_Cursor_getObjCPropertySetterName(CXCursor C);
|
||||
|
||||
/**
|
||||
* 'Qualifiers' written next to the return and parameter types in
|
||||
* Objective-C method declarations.
|
||||
@ -5491,10 +5620,15 @@ enum CXCompletionContext {
|
||||
*/
|
||||
CXCompletionContext_NaturalLanguage = 1 << 21,
|
||||
|
||||
/**
|
||||
* #include file completions should be included in the results.
|
||||
*/
|
||||
CXCompletionContext_IncludedFile = 1 << 22,
|
||||
|
||||
/**
|
||||
* The current context is unknown, so set all contexts.
|
||||
*/
|
||||
CXCompletionContext_Unknown = ((1 << 22) - 1)
|
||||
CXCompletionContext_Unknown = ((1 << 23) - 1)
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -15,6 +15,7 @@
|
||||
#ifndef LLVM_CLANG_AST_ASTCONTEXT_H
|
||||
#define LLVM_CLANG_AST_ASTCONTEXT_H
|
||||
|
||||
#include "clang/AST/ASTContextAllocate.h"
|
||||
#include "clang/AST/ASTTypeTraits.h"
|
||||
#include "clang/AST/CanonicalType.h"
|
||||
#include "clang/AST/CommentCommandTraits.h"
|
||||
@ -22,6 +23,7 @@
|
||||
#include "clang/AST/Decl.h"
|
||||
#include "clang/AST/DeclBase.h"
|
||||
#include "clang/AST/DeclarationName.h"
|
||||
#include "clang/AST/Expr.h"
|
||||
#include "clang/AST/ExternalASTSource.h"
|
||||
#include "clang/AST/NestedNameSpecifier.h"
|
||||
#include "clang/AST/PrettyPrinter.h"
|
||||
@ -30,6 +32,7 @@
|
||||
#include "clang/AST/TemplateName.h"
|
||||
#include "clang/AST/Type.h"
|
||||
#include "clang/Basic/AddressSpaces.h"
|
||||
#include "clang/Basic/AttrKinds.h"
|
||||
#include "clang/Basic/IdentifierTable.h"
|
||||
#include "clang/Basic/LLVM.h"
|
||||
#include "clang/Basic/LangOptions.h"
|
||||
@ -79,6 +82,7 @@ struct fltSemantics;
|
||||
|
||||
namespace clang {
|
||||
|
||||
class APFixedPoint;
|
||||
class APValue;
|
||||
class ASTMutationListener;
|
||||
class ASTRecordLayout;
|
||||
@ -92,6 +96,7 @@ class CXXMethodDecl;
|
||||
class CXXRecordDecl;
|
||||
class DiagnosticsEngine;
|
||||
class Expr;
|
||||
class FixedPointSemantics;
|
||||
class MangleContext;
|
||||
class MangleNumberingContext;
|
||||
class MaterializeTemporaryExpr;
|
||||
@ -148,6 +153,22 @@ struct TypeInfo {
|
||||
/// Holds long-lived AST nodes (such as types and decls) that can be
|
||||
/// referred to throughout the semantic analysis of a file.
|
||||
class ASTContext : public RefCountedBase<ASTContext> {
|
||||
public:
|
||||
/// Copy initialization expr of a __block variable and a boolean flag that
|
||||
/// indicates whether the expression can throw.
|
||||
struct BlockVarCopyInit {
|
||||
BlockVarCopyInit() = default;
|
||||
BlockVarCopyInit(Expr *CopyExpr, bool CanThrow)
|
||||
: ExprAndFlag(CopyExpr, CanThrow) {}
|
||||
void setExprAndFlag(Expr *CopyExpr, bool CanThrow) {
|
||||
ExprAndFlag.setPointerAndInt(CopyExpr, CanThrow);
|
||||
}
|
||||
Expr *getCopyExpr() const { return ExprAndFlag.getPointer(); }
|
||||
bool canThrow() const { return ExprAndFlag.getInt(); }
|
||||
llvm::PointerIntPair<Expr *, 1, bool> ExprAndFlag;
|
||||
};
|
||||
|
||||
private:
|
||||
friend class NestedNameSpecifier;
|
||||
|
||||
mutable SmallVector<Type *, 0> Types;
|
||||
@ -242,8 +263,8 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
/// interface.
|
||||
llvm::DenseMap<const ObjCMethodDecl*,const ObjCMethodDecl*> ObjCMethodRedecls;
|
||||
|
||||
/// Mapping from __block VarDecls to their copy initialization expr.
|
||||
llvm::DenseMap<const VarDecl*, Expr*> BlockVarCopyInits;
|
||||
/// Mapping from __block VarDecls to BlockVarCopyInit.
|
||||
llvm::DenseMap<const VarDecl *, BlockVarCopyInit> BlockVarCopyInits;
|
||||
|
||||
/// Mapping from class scope functions specialization to their
|
||||
/// template patterns.
|
||||
@ -316,7 +337,7 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
mutable IdentifierInfo *BoolName = nullptr;
|
||||
|
||||
/// The identifier 'NSObject'.
|
||||
IdentifierInfo *NSObjectName = nullptr;
|
||||
mutable IdentifierInfo *NSObjectName = nullptr;
|
||||
|
||||
/// The identifier 'NSCopying'.
|
||||
IdentifierInfo *NSCopyingName = nullptr;
|
||||
@ -549,26 +570,6 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
IntrusiveRefCntPtr<ExternalASTSource> ExternalSource;
|
||||
ASTMutationListener *Listener = nullptr;
|
||||
|
||||
/// Contains parents of a node.
|
||||
using ParentVector = llvm::SmallVector<ast_type_traits::DynTypedNode, 2>;
|
||||
|
||||
/// Maps from a node to its parents. This is used for nodes that have
|
||||
/// pointer identity only, which are more common and we can save space by
|
||||
/// only storing a unique pointer to them.
|
||||
using ParentMapPointers =
|
||||
llvm::DenseMap<const void *,
|
||||
llvm::PointerUnion4<const Decl *, const Stmt *,
|
||||
ast_type_traits::DynTypedNode *,
|
||||
ParentVector *>>;
|
||||
|
||||
/// Parent map for nodes without pointer identity. We store a full
|
||||
/// DynTypedNode for all keys.
|
||||
using ParentMapOtherNodes =
|
||||
llvm::DenseMap<ast_type_traits::DynTypedNode,
|
||||
llvm::PointerUnion4<const Decl *, const Stmt *,
|
||||
ast_type_traits::DynTypedNode *,
|
||||
ParentVector *>>;
|
||||
|
||||
/// Container for either a single DynTypedNode or for an ArrayRef to
|
||||
/// DynTypedNode. For use with ParentMap.
|
||||
class DynTypedNodeList {
|
||||
@ -610,7 +611,17 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
}
|
||||
};
|
||||
|
||||
/// Returns the parents of the given node.
|
||||
// A traversal scope limits the parts of the AST visible to certain analyses.
|
||||
// RecursiveASTVisitor::TraverseAST will only visit reachable nodes, and
|
||||
// getParents() will only observe reachable parent edges.
|
||||
//
|
||||
// The scope is defined by a set of "top-level" declarations.
|
||||
// Initially, it is the entire TU: {getTranslationUnitDecl()}.
|
||||
// Changing the scope clears the parent cache, which is expensive to rebuild.
|
||||
std::vector<Decl *> getTraversalScope() const { return TraversalScope; }
|
||||
void setTraversalScope(const std::vector<Decl *> &);
|
||||
|
||||
/// Returns the parents of the given node (within the traversal scope).
|
||||
///
|
||||
/// Note that this will lazily compute the parents of all nodes
|
||||
/// and store them for later retrieval. Thus, the first call is O(n)
|
||||
@ -977,7 +988,8 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
/// Get the additional modules in which the definition \p Def has
|
||||
/// been merged.
|
||||
ArrayRef<Module*> getModulesWithMergedDefinition(const NamedDecl *Def) {
|
||||
auto MergedIt = MergedDefModules.find(Def);
|
||||
auto MergedIt =
|
||||
MergedDefModules.find(cast<NamedDecl>(Def->getCanonicalDecl()));
|
||||
if (MergedIt == MergedDefModules.end())
|
||||
return None;
|
||||
return MergedIt->second;
|
||||
@ -1041,6 +1053,9 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
CanQualType OCLSamplerTy, OCLEventTy, OCLClkEventTy;
|
||||
CanQualType OCLQueueTy, OCLReserveIDTy;
|
||||
CanQualType OMPArraySectionTy;
|
||||
#define EXT_OPAQUE_TYPE(ExtType, Id, Ext) \
|
||||
CanQualType Id##Ty;
|
||||
#include "clang/Basic/OpenCLExtensionTypes.def"
|
||||
|
||||
// Types for deductions in C++0x [stmt.ranged]'s desugaring. Built on demand.
|
||||
mutable QualType AutoDeductTy; // Deduction against 'auto'.
|
||||
@ -1403,7 +1418,7 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
|
||||
QualType getInjectedClassNameType(CXXRecordDecl *Decl, QualType TST) const;
|
||||
|
||||
QualType getAttributedType(AttributedType::Kind attrKind,
|
||||
QualType getAttributedType(attr::Kind attrKind,
|
||||
QualType modifiedType,
|
||||
QualType equivalentType);
|
||||
|
||||
@ -1656,7 +1671,7 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
}
|
||||
|
||||
/// Retrieve the identifier 'NSObject'.
|
||||
IdentifierInfo *getNSObjectName() {
|
||||
IdentifierInfo *getNSObjectName() const {
|
||||
if (!NSObjectName) {
|
||||
NSObjectName = &Idents.get("NSObject");
|
||||
}
|
||||
@ -1961,6 +1976,9 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
|
||||
unsigned char getFixedPointScale(QualType Ty) const;
|
||||
unsigned char getFixedPointIBits(QualType Ty) const;
|
||||
FixedPointSemantics getFixedPointSemantics(QualType Ty) const;
|
||||
APFixedPoint getFixedPointMax(QualType Ty) const;
|
||||
APFixedPoint getFixedPointMin(QualType Ty) const;
|
||||
|
||||
DeclarationNameInfo getNameForTemplate(TemplateName Name,
|
||||
SourceLocation NameLoc) const;
|
||||
@ -2488,6 +2506,8 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
|
||||
unsigned getTargetAddressSpace(LangAS AS) const;
|
||||
|
||||
LangAS getLangASForBuiltinAddressSpace(unsigned AS) const;
|
||||
|
||||
/// Get target-dependent integer value for null pointer which is used for
|
||||
/// constant folding.
|
||||
uint64_t getTargetNullPointerValue(QualType QT) const;
|
||||
@ -2657,12 +2677,13 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
/// otherwise returns null.
|
||||
const ObjCInterfaceDecl *getObjContainingInterface(const NamedDecl *ND) const;
|
||||
|
||||
/// Set the copy inialization expression of a block var decl.
|
||||
void setBlockVarCopyInits(VarDecl*VD, Expr* Init);
|
||||
/// Set the copy inialization expression of a block var decl. \p CanThrow
|
||||
/// indicates whether the copy expression can throw or not.
|
||||
void setBlockVarCopyInit(const VarDecl* VD, Expr *CopyExpr, bool CanThrow);
|
||||
|
||||
/// Get the copy initialization expression of the VarDecl \p VD, or
|
||||
/// nullptr if none exists.
|
||||
Expr *getBlockVarCopyInits(const VarDecl* VD);
|
||||
BlockVarCopyInit getBlockVarCopyInit(const VarDecl* VD) const;
|
||||
|
||||
/// Allocate an uninitialized TypeSourceInfo.
|
||||
///
|
||||
@ -2718,7 +2739,7 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
/// predicate.
|
||||
void forEachMultiversionedFunctionVersion(
|
||||
const FunctionDecl *FD,
|
||||
llvm::function_ref<void(const FunctionDecl *)> Pred) const;
|
||||
llvm::function_ref<void(FunctionDecl *)> Pred) const;
|
||||
|
||||
const CXXConstructorDecl *
|
||||
getCopyConstructorForExceptionObject(CXXRecordDecl *RD);
|
||||
@ -2894,13 +2915,13 @@ class ASTContext : public RefCountedBase<ASTContext> {
|
||||
// but we include it here so that ASTContext can quickly deallocate them.
|
||||
llvm::PointerIntPair<StoredDeclsMap *, 1> LastSDM;
|
||||
|
||||
std::unique_ptr<ParentMapPointers> PointerParents;
|
||||
std::unique_ptr<ParentMapOtherNodes> OtherParents;
|
||||
std::vector<Decl *> TraversalScope;
|
||||
class ParentMap;
|
||||
std::unique_ptr<ParentMap> Parents;
|
||||
|
||||
std::unique_ptr<VTableContextBase> VTContext;
|
||||
|
||||
void ReleaseDeclContextMaps();
|
||||
void ReleaseParentMapEntries();
|
||||
|
||||
public:
|
||||
enum PragmaSectionFlag : unsigned {
|
||||
@ -2949,8 +2970,8 @@ inline Selector GetUnarySelector(StringRef name, ASTContext &Ctx) {
|
||||
/// This placement form of operator new uses the ASTContext's allocator for
|
||||
/// obtaining memory.
|
||||
///
|
||||
/// IMPORTANT: These are also declared in clang/AST/AttrIterator.h! Any changes
|
||||
/// here need to also be made there.
|
||||
/// IMPORTANT: These are also declared in clang/AST/ASTContextAllocate.h!
|
||||
/// Any changes here need to also be made there.
|
||||
///
|
||||
/// We intentionally avoid using a nothrow specification here so that the calls
|
||||
/// to this operator will not perform a null check on the result -- the
|
||||
@ -2973,7 +2994,7 @@ inline Selector GetUnarySelector(StringRef name, ASTContext &Ctx) {
|
||||
/// allocator supports it).
|
||||
/// @return The allocated memory. Could be nullptr.
|
||||
inline void *operator new(size_t Bytes, const clang::ASTContext &C,
|
||||
size_t Alignment) {
|
||||
size_t Alignment /* = 8 */) {
|
||||
return C.Allocate(Bytes, Alignment);
|
||||
}
|
||||
|
||||
@ -3011,7 +3032,7 @@ inline void operator delete(void *Ptr, const clang::ASTContext &C, size_t) {
|
||||
/// allocator supports it).
|
||||
/// @return The allocated memory. Could be nullptr.
|
||||
inline void *operator new[](size_t Bytes, const clang::ASTContext& C,
|
||||
size_t Alignment = 8) {
|
||||
size_t Alignment /* = 8 */) {
|
||||
return C.Allocate(Bytes, Alignment);
|
||||
}
|
||||
|
||||
|
38
include/clang/AST/ASTContextAllocate.h
Normal file
38
include/clang/AST/ASTContextAllocate.h
Normal file
@ -0,0 +1,38 @@
|
||||
//===- ASTContextAllocate.h - ASTContext allocate functions -----*- C++ -*-===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// This file declares ASTContext allocation functions separate from the main
|
||||
// code in ASTContext.h.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_CLANG_AST_ASTCONTEXTALLOCATE_H
|
||||
#define LLVM_CLANG_AST_ASTCONTEXTALLOCATE_H
|
||||
|
||||
#include <cstddef>
|
||||
|
||||
namespace clang {
|
||||
|
||||
class ASTContext;
|
||||
|
||||
} // namespace clang
|
||||
|
||||
// Defined in ASTContext.h
|
||||
void *operator new(size_t Bytes, const clang::ASTContext &C,
|
||||
size_t Alignment = 8);
|
||||
void *operator new[](size_t Bytes, const clang::ASTContext &C,
|
||||
size_t Alignment = 8);
|
||||
|
||||
// It is good practice to pair new/delete operators. Also, MSVC gives many
|
||||
// warnings if a matching delete overload is not declared, even though the
|
||||
// throw() spec guarantees it will not be implicitly called.
|
||||
void operator delete(void *Ptr, const clang::ASTContext &C, size_t);
|
||||
void operator delete[](void *Ptr, const clang::ASTContext &C, size_t);
|
||||
|
||||
#endif // LLVM_CLANG_AST_ASTCONTEXTALLOCATE_H
|
@ -11,19 +11,9 @@
|
||||
#define LLVM_CLANG_AST_ASTDIAGNOSTIC_H
|
||||
|
||||
#include "clang/Basic/Diagnostic.h"
|
||||
#include "clang/Basic/DiagnosticAST.h"
|
||||
|
||||
namespace clang {
|
||||
namespace diag {
|
||||
enum {
|
||||
#define DIAG(ENUM,FLAGS,DEFAULT_MAPPING,DESC,GROUP,\
|
||||
SFINAE,NOWERROR,SHOWINSYSHEADER,CATEGORY) ENUM,
|
||||
#define ASTSTART
|
||||
#include "clang/Basic/DiagnosticASTKinds.inc"
|
||||
#undef DIAG
|
||||
NUM_BUILTIN_AST_DIAGNOSTICS
|
||||
};
|
||||
} // end namespace diag
|
||||
|
||||
/// DiagnosticsEngine argument formatting function for diagnostics that
|
||||
/// involve AST nodes.
|
||||
///
|
||||
|
97
include/clang/AST/ASTDumperUtils.h
Normal file
97
include/clang/AST/ASTDumperUtils.h
Normal file
@ -0,0 +1,97 @@
|
||||
//===--- ASTDumperUtils.h - Printing of AST nodes -------------------------===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// This file implements AST utilities for traversal down the tree.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_CLANG_AST_ASTDUMPERUTILS_H
|
||||
#define LLVM_CLANG_AST_ASTDUMPERUTILS_H
|
||||
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
|
||||
namespace clang {
|
||||
|
||||
// Colors used for various parts of the AST dump
|
||||
// Do not use bold yellow for any text. It is hard to read on white screens.
|
||||
|
||||
struct TerminalColor {
|
||||
llvm::raw_ostream::Colors Color;
|
||||
bool Bold;
|
||||
};
|
||||
|
||||
// Red - CastColor
|
||||
// Green - TypeColor
|
||||
// Bold Green - DeclKindNameColor, UndeserializedColor
|
||||
// Yellow - AddressColor, LocationColor
|
||||
// Blue - CommentColor, NullColor, IndentColor
|
||||
// Bold Blue - AttrColor
|
||||
// Bold Magenta - StmtColor
|
||||
// Cyan - ValueKindColor, ObjectKindColor
|
||||
// Bold Cyan - ValueColor, DeclNameColor
|
||||
|
||||
// Decl kind names (VarDecl, FunctionDecl, etc)
|
||||
static const TerminalColor DeclKindNameColor = {llvm::raw_ostream::GREEN, true};
|
||||
// Attr names (CleanupAttr, GuardedByAttr, etc)
|
||||
static const TerminalColor AttrColor = {llvm::raw_ostream::BLUE, true};
|
||||
// Statement names (DeclStmt, ImplicitCastExpr, etc)
|
||||
static const TerminalColor StmtColor = {llvm::raw_ostream::MAGENTA, true};
|
||||
// Comment names (FullComment, ParagraphComment, TextComment, etc)
|
||||
static const TerminalColor CommentColor = {llvm::raw_ostream::BLUE, false};
|
||||
|
||||
// Type names (int, float, etc, plus user defined types)
|
||||
static const TerminalColor TypeColor = {llvm::raw_ostream::GREEN, false};
|
||||
|
||||
// Pointer address
|
||||
static const TerminalColor AddressColor = {llvm::raw_ostream::YELLOW, false};
|
||||
// Source locations
|
||||
static const TerminalColor LocationColor = {llvm::raw_ostream::YELLOW, false};
|
||||
|
||||
// lvalue/xvalue
|
||||
static const TerminalColor ValueKindColor = {llvm::raw_ostream::CYAN, false};
|
||||
// bitfield/objcproperty/objcsubscript/vectorcomponent
|
||||
static const TerminalColor ObjectKindColor = {llvm::raw_ostream::CYAN, false};
|
||||
|
||||
// Null statements
|
||||
static const TerminalColor NullColor = {llvm::raw_ostream::BLUE, false};
|
||||
|
||||
// Undeserialized entities
|
||||
static const TerminalColor UndeserializedColor = {llvm::raw_ostream::GREEN,
|
||||
true};
|
||||
|
||||
// CastKind from CastExpr's
|
||||
static const TerminalColor CastColor = {llvm::raw_ostream::RED, false};
|
||||
|
||||
// Value of the statement
|
||||
static const TerminalColor ValueColor = {llvm::raw_ostream::CYAN, true};
|
||||
// Decl names
|
||||
static const TerminalColor DeclNameColor = {llvm::raw_ostream::CYAN, true};
|
||||
|
||||
// Indents ( `, -. | )
|
||||
static const TerminalColor IndentColor = {llvm::raw_ostream::BLUE, false};
|
||||
|
||||
class ColorScope {
|
||||
llvm::raw_ostream &OS;
|
||||
const bool ShowColors;
|
||||
|
||||
public:
|
||||
ColorScope(llvm::raw_ostream &OS, bool ShowColors, TerminalColor Color)
|
||||
: OS(OS), ShowColors(ShowColors) {
|
||||
if (ShowColors)
|
||||
OS.changeColor(Color.Color, Color.Bold);
|
||||
}
|
||||
~ColorScope() {
|
||||
if (ShowColors)
|
||||
OS.resetColor();
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace clang
|
||||
|
||||
#endif // LLVM_CLANG_AST_ASTDUMPERUTILS_H
|
@ -25,12 +25,15 @@
|
||||
#include "clang/Basic/SourceLocation.h"
|
||||
#include "llvm/ADT/DenseMap.h"
|
||||
#include "llvm/ADT/DenseSet.h"
|
||||
#include "llvm/ADT/Optional.h"
|
||||
#include "llvm/ADT/SmallVector.h"
|
||||
#include "llvm/Support/Error.h"
|
||||
#include <utility>
|
||||
|
||||
namespace clang {
|
||||
|
||||
class ASTContext;
|
||||
class ASTImporterLookupTable;
|
||||
class CXXBaseSpecifier;
|
||||
class CXXCtorInitializer;
|
||||
class Decl;
|
||||
@ -43,6 +46,29 @@ class TagDecl;
|
||||
class TypeSourceInfo;
|
||||
class Attr;
|
||||
|
||||
class ImportError : public llvm::ErrorInfo<ImportError> {
|
||||
public:
|
||||
/// \brief Kind of error when importing an AST component.
|
||||
enum ErrorKind {
|
||||
NameConflict, /// Naming ambiguity (likely ODR violation).
|
||||
UnsupportedConstruct, /// Not supported node or case.
|
||||
Unknown /// Other error.
|
||||
};
|
||||
|
||||
ErrorKind Error;
|
||||
|
||||
static char ID;
|
||||
|
||||
ImportError() : Error(Unknown) { }
|
||||
ImportError(const ImportError &Other) : Error(Other.Error) { }
|
||||
ImportError(ErrorKind Error) : Error(Error) { }
|
||||
|
||||
std::string toString() const;
|
||||
|
||||
void log(raw_ostream &OS) const override;
|
||||
std::error_code convertToErrorCode() const override;
|
||||
};
|
||||
|
||||
// \brief Returns with a list of declarations started from the canonical decl
|
||||
// then followed by subsequent decls in the translation unit.
|
||||
// This gives a canonical list for each entry in the redecl chain.
|
||||
@ -55,12 +81,21 @@ class Attr;
|
||||
/// Imports selected nodes from one AST context into another context,
|
||||
/// merging AST nodes where appropriate.
|
||||
class ASTImporter {
|
||||
friend class ASTNodeImporter;
|
||||
public:
|
||||
using NonEquivalentDeclSet = llvm::DenseSet<std::pair<Decl *, Decl *>>;
|
||||
using ImportedCXXBaseSpecifierMap =
|
||||
llvm::DenseMap<const CXXBaseSpecifier *, CXXBaseSpecifier *>;
|
||||
|
||||
private:
|
||||
|
||||
/// Pointer to the import specific lookup table, which may be shared
|
||||
/// amongst several ASTImporter objects.
|
||||
/// This is an externally managed resource (and should exist during the
|
||||
/// lifetime of the ASTImporter object)
|
||||
/// If not set then the original C/C++ lookup is used.
|
||||
ASTImporterLookupTable *LookupTable = nullptr;
|
||||
|
||||
/// The contexts we're importing to and from.
|
||||
ASTContext &ToContext, &FromContext;
|
||||
|
||||
@ -98,9 +133,13 @@ class Attr;
|
||||
/// (which we have already complained about).
|
||||
NonEquivalentDeclSet NonEquivalentDecls;
|
||||
|
||||
using FoundDeclsTy = SmallVector<NamedDecl *, 2>;
|
||||
FoundDeclsTy findDeclsInToCtx(DeclContext *DC, DeclarationName Name);
|
||||
|
||||
void AddToLookupTable(Decl *ToD);
|
||||
|
||||
public:
|
||||
/// Create a new AST importer.
|
||||
///
|
||||
|
||||
/// \param ToContext The context we'll be importing into.
|
||||
///
|
||||
/// \param ToFileManager The file manager we'll be importing into.
|
||||
@ -112,9 +151,14 @@ class Attr;
|
||||
/// \param MinimalImport If true, the importer will attempt to import
|
||||
/// as little as it can, e.g., by importing declarations as forward
|
||||
/// declarations that can be completed at a later point.
|
||||
///
|
||||
/// \param LookupTable The importer specific lookup table which may be
|
||||
/// shared amongst several ASTImporter objects.
|
||||
/// If not set then the original C/C++ lookup is used.
|
||||
ASTImporter(ASTContext &ToContext, FileManager &ToFileManager,
|
||||
ASTContext &FromContext, FileManager &FromFileManager,
|
||||
bool MinimalImport);
|
||||
bool MinimalImport,
|
||||
ASTImporterLookupTable *LookupTable = nullptr);
|
||||
|
||||
virtual ~ASTImporter();
|
||||
|
||||
@ -122,31 +166,60 @@ class Attr;
|
||||
/// to-be-completed forward declarations when possible.
|
||||
bool isMinimalImport() const { return Minimal; }
|
||||
|
||||
/// Import the given type from the "from" context into the "to"
|
||||
/// context.
|
||||
/// \brief Import the given object, returns the result.
|
||||
///
|
||||
/// \returns the equivalent type in the "to" context, or a NULL type if
|
||||
/// an error occurred.
|
||||
/// \param To Import the object into this variable.
|
||||
/// \param From Object to import.
|
||||
/// \return Error information (success or error).
|
||||
template <typename ImportT>
|
||||
LLVM_NODISCARD llvm::Error importInto(ImportT &To, const ImportT &From) {
|
||||
To = Import(From);
|
||||
if (From && !To)
|
||||
return llvm::make_error<ImportError>();
|
||||
return llvm::Error::success();
|
||||
// FIXME: this should be the final code
|
||||
//auto ToOrErr = Import(From);
|
||||
//if (ToOrErr)
|
||||
// To = *ToOrErr;
|
||||
//return ToOrErr.takeError();
|
||||
}
|
||||
|
||||
/// Import the given type from the "from" context into the "to"
|
||||
/// context. A null type is imported as a null type (no error).
|
||||
///
|
||||
/// \returns The equivalent type in the "to" context, or the import error.
|
||||
llvm::Expected<QualType> Import_New(QualType FromT);
|
||||
// FIXME: Remove this version.
|
||||
QualType Import(QualType FromT);
|
||||
|
||||
/// Import the given type source information from the
|
||||
/// "from" context into the "to" context.
|
||||
///
|
||||
/// \returns the equivalent type source information in the "to"
|
||||
/// context, or NULL if an error occurred.
|
||||
/// \returns The equivalent type source information in the "to"
|
||||
/// context, or the import error.
|
||||
llvm::Expected<TypeSourceInfo *> Import_New(TypeSourceInfo *FromTSI);
|
||||
// FIXME: Remove this version.
|
||||
TypeSourceInfo *Import(TypeSourceInfo *FromTSI);
|
||||
|
||||
/// Import the given attribute from the "from" context into the
|
||||
/// "to" context.
|
||||
///
|
||||
/// \returns the equivalent attribute in the "to" context.
|
||||
/// \returns The equivalent attribute in the "to" context, or the import
|
||||
/// error.
|
||||
llvm::Expected<Attr *> Import_New(const Attr *FromAttr);
|
||||
// FIXME: Remove this version.
|
||||
Attr *Import(const Attr *FromAttr);
|
||||
|
||||
/// Import the given declaration from the "from" context into the
|
||||
/// "to" context.
|
||||
///
|
||||
/// \returns the equivalent declaration in the "to" context, or a NULL type
|
||||
/// if an error occurred.
|
||||
/// \returns The equivalent declaration in the "to" context, or the import
|
||||
/// error.
|
||||
llvm::Expected<Decl *> Import_New(Decl *FromD);
|
||||
llvm::Expected<Decl *> Import_New(const Decl *FromD) {
|
||||
return Import_New(const_cast<Decl *>(FromD));
|
||||
}
|
||||
// FIXME: Remove this version.
|
||||
Decl *Import(Decl *FromD);
|
||||
Decl *Import(const Decl *FromD) {
|
||||
return Import(const_cast<Decl *>(FromD));
|
||||
@ -155,104 +228,137 @@ class Attr;
|
||||
/// Return the copy of the given declaration in the "to" context if
|
||||
/// it has already been imported from the "from" context. Otherwise return
|
||||
/// NULL.
|
||||
Decl *GetAlreadyImportedOrNull(Decl *FromD);
|
||||
Decl *GetAlreadyImportedOrNull(const Decl *FromD) const;
|
||||
|
||||
/// Import the given declaration context from the "from"
|
||||
/// AST context into the "to" AST context.
|
||||
///
|
||||
/// \returns the equivalent declaration context in the "to"
|
||||
/// context, or a NULL type if an error occurred.
|
||||
DeclContext *ImportContext(DeclContext *FromDC);
|
||||
/// context, or error value.
|
||||
llvm::Expected<DeclContext *> ImportContext(DeclContext *FromDC);
|
||||
|
||||
/// Import the given expression from the "from" context into the
|
||||
/// "to" context.
|
||||
///
|
||||
/// \returns the equivalent expression in the "to" context, or NULL if
|
||||
/// an error occurred.
|
||||
/// \returns The equivalent expression in the "to" context, or the import
|
||||
/// error.
|
||||
llvm::Expected<Expr *> Import_New(Expr *FromE);
|
||||
// FIXME: Remove this version.
|
||||
Expr *Import(Expr *FromE);
|
||||
|
||||
/// Import the given statement from the "from" context into the
|
||||
/// "to" context.
|
||||
///
|
||||
/// \returns the equivalent statement in the "to" context, or NULL if
|
||||
/// an error occurred.
|
||||
/// \returns The equivalent statement in the "to" context, or the import
|
||||
/// error.
|
||||
llvm::Expected<Stmt *> Import_New(Stmt *FromS);
|
||||
// FIXME: Remove this version.
|
||||
Stmt *Import(Stmt *FromS);
|
||||
|
||||
/// Import the given nested-name-specifier from the "from"
|
||||
/// context into the "to" context.
|
||||
///
|
||||
/// \returns the equivalent nested-name-specifier in the "to"
|
||||
/// context, or NULL if an error occurred.
|
||||
/// \returns The equivalent nested-name-specifier in the "to"
|
||||
/// context, or the import error.
|
||||
llvm::Expected<NestedNameSpecifier *>
|
||||
Import_New(NestedNameSpecifier *FromNNS);
|
||||
// FIXME: Remove this version.
|
||||
NestedNameSpecifier *Import(NestedNameSpecifier *FromNNS);
|
||||
|
||||
/// Import the given nested-name-specifier from the "from"
|
||||
/// Import the given nested-name-specifier-loc from the "from"
|
||||
/// context into the "to" context.
|
||||
///
|
||||
/// \returns the equivalent nested-name-specifier in the "to"
|
||||
/// context.
|
||||
/// \returns The equivalent nested-name-specifier-loc in the "to"
|
||||
/// context, or the import error.
|
||||
llvm::Expected<NestedNameSpecifierLoc>
|
||||
Import_New(NestedNameSpecifierLoc FromNNS);
|
||||
// FIXME: Remove this version.
|
||||
NestedNameSpecifierLoc Import(NestedNameSpecifierLoc FromNNS);
|
||||
|
||||
/// Import the goven template name from the "from" context into the
|
||||
/// "to" context.
|
||||
/// Import the given template name from the "from" context into the
|
||||
/// "to" context, or the import error.
|
||||
llvm::Expected<TemplateName> Import_New(TemplateName From);
|
||||
// FIXME: Remove this version.
|
||||
TemplateName Import(TemplateName From);
|
||||
|
||||
/// Import the given source location from the "from" context into
|
||||
/// the "to" context.
|
||||
///
|
||||
/// \returns the equivalent source location in the "to" context, or an
|
||||
/// invalid source location if an error occurred.
|
||||
/// \returns The equivalent source location in the "to" context, or the
|
||||
/// import error.
|
||||
llvm::Expected<SourceLocation> Import_New(SourceLocation FromLoc);
|
||||
// FIXME: Remove this version.
|
||||
SourceLocation Import(SourceLocation FromLoc);
|
||||
|
||||
/// Import the given source range from the "from" context into
|
||||
/// the "to" context.
|
||||
///
|
||||
/// \returns the equivalent source range in the "to" context, or an
|
||||
/// invalid source location if an error occurred.
|
||||
/// \returns The equivalent source range in the "to" context, or the import
|
||||
/// error.
|
||||
llvm::Expected<SourceRange> Import_New(SourceRange FromRange);
|
||||
// FIXME: Remove this version.
|
||||
SourceRange Import(SourceRange FromRange);
|
||||
|
||||
/// Import the given declaration name from the "from"
|
||||
/// context into the "to" context.
|
||||
///
|
||||
/// \returns the equivalent declaration name in the "to" context,
|
||||
/// or an empty declaration name if an error occurred.
|
||||
/// \returns The equivalent declaration name in the "to" context, or the
|
||||
/// import error.
|
||||
llvm::Expected<DeclarationName> Import_New(DeclarationName FromName);
|
||||
// FIXME: Remove this version.
|
||||
DeclarationName Import(DeclarationName FromName);
|
||||
|
||||
/// Import the given identifier from the "from" context
|
||||
/// into the "to" context.
|
||||
///
|
||||
/// \returns the equivalent identifier in the "to" context.
|
||||
/// \returns The equivalent identifier in the "to" context. Note: It
|
||||
/// returns nullptr only if the FromId was nullptr.
|
||||
IdentifierInfo *Import(const IdentifierInfo *FromId);
|
||||
|
||||
/// Import the given Objective-C selector from the "from"
|
||||
/// context into the "to" context.
|
||||
///
|
||||
/// \returns the equivalent selector in the "to" context.
|
||||
/// \returns The equivalent selector in the "to" context, or the import
|
||||
/// error.
|
||||
llvm::Expected<Selector> Import_New(Selector FromSel);
|
||||
// FIXME: Remove this version.
|
||||
Selector Import(Selector FromSel);
|
||||
|
||||
/// Import the given file ID from the "from" context into the
|
||||
/// "to" context.
|
||||
///
|
||||
/// \returns the equivalent file ID in the source manager of the "to"
|
||||
/// context.
|
||||
/// \returns The equivalent file ID in the source manager of the "to"
|
||||
/// context, or the import error.
|
||||
llvm::Expected<FileID> Import_New(FileID);
|
||||
// FIXME: Remove this version.
|
||||
FileID Import(FileID);
|
||||
|
||||
/// Import the given C++ constructor initializer from the "from"
|
||||
/// context into the "to" context.
|
||||
///
|
||||
/// \returns the equivalent initializer in the "to" context.
|
||||
/// \returns The equivalent initializer in the "to" context, or the import
|
||||
/// error.
|
||||
llvm::Expected<CXXCtorInitializer *>
|
||||
Import_New(CXXCtorInitializer *FromInit);
|
||||
// FIXME: Remove this version.
|
||||
CXXCtorInitializer *Import(CXXCtorInitializer *FromInit);
|
||||
|
||||
/// Import the given CXXBaseSpecifier from the "from" context into
|
||||
/// the "to" context.
|
||||
///
|
||||
/// \returns the equivalent CXXBaseSpecifier in the source manager of the
|
||||
/// "to" context.
|
||||
/// \returns The equivalent CXXBaseSpecifier in the source manager of the
|
||||
/// "to" context, or the import error.
|
||||
llvm::Expected<CXXBaseSpecifier *>
|
||||
Import_New(const CXXBaseSpecifier *FromSpec);
|
||||
// FIXME: Remove this version.
|
||||
CXXBaseSpecifier *Import(const CXXBaseSpecifier *FromSpec);
|
||||
|
||||
/// Import the definition of the given declaration, including all of
|
||||
/// the declarations it contains.
|
||||
///
|
||||
/// This routine is intended to be used
|
||||
LLVM_NODISCARD llvm::Error ImportDefinition_New(Decl *From);
|
||||
|
||||
// FIXME: Compatibility function.
|
||||
// Usages of this should be changed to ImportDefinition_New.
|
||||
void ImportDefinition(Decl *From);
|
||||
|
||||
/// Cope with a name conflict when importing a declaration into the
|
||||
@ -333,6 +439,13 @@ class Attr;
|
||||
/// equivalent.
|
||||
bool IsStructurallyEquivalent(QualType From, QualType To,
|
||||
bool Complain = true);
|
||||
|
||||
/// Determine the index of a field in its parent record.
|
||||
/// F should be a field (or indirect field) declaration.
|
||||
/// \returns The index of the field in its parent context (starting from 0).
|
||||
/// On error `None` is returned (parent context is non-record).
|
||||
static llvm::Optional<unsigned> getFieldIndex(Decl *F);
|
||||
|
||||
};
|
||||
|
||||
} // namespace clang
|
||||
|
75
include/clang/AST/ASTImporterLookupTable.h
Normal file
75
include/clang/AST/ASTImporterLookupTable.h
Normal file
@ -0,0 +1,75 @@
|
||||
//===- ASTImporterLookupTable.h - ASTImporter specific lookup--*- C++ -*---===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// This file defines the ASTImporterLookupTable class which implements a
|
||||
// lookup procedure for the import mechanism.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_CLANG_AST_ASTIMPORTERLOOKUPTABLE_H
|
||||
#define LLVM_CLANG_AST_ASTIMPORTERLOOKUPTABLE_H
|
||||
|
||||
#include "clang/AST/DeclBase.h" // lookup_result
|
||||
#include "clang/AST/DeclarationName.h"
|
||||
#include "llvm/ADT/DenseMap.h"
|
||||
#include "llvm/ADT/SetVector.h"
|
||||
|
||||
namespace clang {
|
||||
|
||||
class ASTContext;
|
||||
class NamedDecl;
|
||||
class DeclContext;
|
||||
|
||||
// There are certain cases when normal C/C++ lookup (localUncachedLookup)
|
||||
// does not find AST nodes. E.g.:
|
||||
// Example 1:
|
||||
// template <class T>
|
||||
// struct X {
|
||||
// friend void foo(); // this is never found in the DC of the TU.
|
||||
// };
|
||||
// Example 2:
|
||||
// // The fwd decl to Foo is not found in the lookupPtr of the DC of the
|
||||
// // translation unit decl.
|
||||
// // Here we could find the node by doing a traverse throught the list of
|
||||
// // the Decls in the DC, but that would not scale.
|
||||
// struct A { struct Foo *p; };
|
||||
// This is a severe problem because the importer decides if it has to create a
|
||||
// new Decl or not based on the lookup results.
|
||||
// To overcome these cases we need an importer specific lookup table which
|
||||
// holds every node and we are not interested in any C/C++ specific visibility
|
||||
// considerations. Simply, we must know if there is an existing Decl in a
|
||||
// given DC. Once we found it then we can handle any visibility related tasks.
|
||||
class ASTImporterLookupTable {
|
||||
|
||||
// We store a list of declarations for each name.
|
||||
// And we collect these lists for each DeclContext.
|
||||
// We could have a flat map with (DeclContext, Name) tuple as key, but a two
|
||||
// level map seems easier to handle.
|
||||
using DeclList = llvm::SmallSetVector<NamedDecl *, 2>;
|
||||
using NameMap = llvm::SmallDenseMap<DeclarationName, DeclList, 4>;
|
||||
using DCMap = llvm::DenseMap<DeclContext *, NameMap>;
|
||||
|
||||
void add(DeclContext *DC, NamedDecl *ND);
|
||||
void remove(DeclContext *DC, NamedDecl *ND);
|
||||
|
||||
DCMap LookupTable;
|
||||
|
||||
public:
|
||||
ASTImporterLookupTable(TranslationUnitDecl &TU);
|
||||
void add(NamedDecl *ND);
|
||||
void remove(NamedDecl *ND);
|
||||
using LookupResult = DeclList;
|
||||
LookupResult lookup(DeclContext *DC, DeclarationName Name) const;
|
||||
void dump(DeclContext *DC) const;
|
||||
void dump() const;
|
||||
};
|
||||
|
||||
} // namespace clang
|
||||
|
||||
#endif // LLVM_CLANG_AST_ASTIMPORTERLOOKUPTABLE_H
|
@ -15,6 +15,7 @@
|
||||
#ifndef LLVM_CLANG_AST_ASTSTRUCTURALEQUIVALENCE_H
|
||||
#define LLVM_CLANG_AST_ASTSTRUCTURALEQUIVALENCE_H
|
||||
|
||||
#include "clang/AST/DeclBase.h"
|
||||
#include "llvm/ADT/DenseMap.h"
|
||||
#include "llvm/ADT/DenseSet.h"
|
||||
#include "llvm/ADT/Optional.h"
|
||||
@ -114,8 +115,19 @@ struct StructuralEquivalenceContext {
|
||||
private:
|
||||
/// Finish checking all of the structural equivalences.
|
||||
///
|
||||
/// \returns true if an error occurred, false otherwise.
|
||||
/// \returns true if the equivalence check failed (non-equivalence detected),
|
||||
/// false if equivalence was detected.
|
||||
bool Finish();
|
||||
|
||||
/// Check for common properties at Finish.
|
||||
/// \returns true if D1 and D2 may be equivalent,
|
||||
/// false if they are for sure not.
|
||||
bool CheckCommonEquivalence(Decl *D1, Decl *D2);
|
||||
|
||||
/// Check for class dependent properties at Finish.
|
||||
/// \returns true if D1 and D2 may be equivalent,
|
||||
/// false if they are for sure not.
|
||||
bool CheckKindSpecificEquivalence(Decl *D1, Decl *D2);
|
||||
};
|
||||
|
||||
} // namespace clang
|
||||
|
@ -18,6 +18,7 @@
|
||||
#ifndef LLVM_CLANG_AST_ASTVECTOR_H
|
||||
#define LLVM_CLANG_AST_ASTVECTOR_H
|
||||
|
||||
#include "clang/AST/ASTContextAllocate.h"
|
||||
#include "llvm/ADT/PointerIntPair.h"
|
||||
#include <algorithm>
|
||||
#include <cassert>
|
||||
|
@ -14,6 +14,7 @@
|
||||
#ifndef LLVM_CLANG_AST_ATTR_H
|
||||
#define LLVM_CLANG_AST_ATTR_H
|
||||
|
||||
#include "clang/AST/ASTContextAllocate.h" // For Attrs.inc
|
||||
#include "clang/AST/AttrIterator.h"
|
||||
#include "clang/AST/Decl.h"
|
||||
#include "clang/AST/Expr.h"
|
||||
@ -113,6 +114,19 @@ class Attr {
|
||||
void printPretty(raw_ostream &OS, const PrintingPolicy &Policy) const;
|
||||
};
|
||||
|
||||
class TypeAttr : public Attr {
|
||||
protected:
|
||||
TypeAttr(attr::Kind AK, SourceRange R, unsigned SpellingListIndex,
|
||||
bool IsLateParsed)
|
||||
: Attr(AK, R, SpellingListIndex, IsLateParsed) {}
|
||||
|
||||
public:
|
||||
static bool classof(const Attr *A) {
|
||||
return A->getKind() >= attr::FirstTypeAttr &&
|
||||
A->getKind() <= attr::LastTypeAttr;
|
||||
}
|
||||
};
|
||||
|
||||
class StmtAttr : public Attr {
|
||||
protected:
|
||||
StmtAttr(attr::Kind AK, SourceRange R, unsigned SpellingListIndex,
|
||||
|
@ -26,25 +26,6 @@ namespace clang {
|
||||
class ASTContext;
|
||||
class Attr;
|
||||
|
||||
} // namespace clang
|
||||
|
||||
// Defined in ASTContext.h
|
||||
void *operator new(size_t Bytes, const clang::ASTContext &C,
|
||||
size_t Alignment = 8);
|
||||
|
||||
// FIXME: Being forced to not have a default argument here due to redeclaration
|
||||
// rules on default arguments sucks
|
||||
void *operator new[](size_t Bytes, const clang::ASTContext &C,
|
||||
size_t Alignment);
|
||||
|
||||
// It is good practice to pair new/delete operators. Also, MSVC gives many
|
||||
// warnings if a matching delete overload is not declared, even though the
|
||||
// throw() spec guarantees it will not be implicitly called.
|
||||
void operator delete(void *Ptr, const clang::ASTContext &C, size_t);
|
||||
void operator delete[](void *Ptr, const clang::ASTContext &C, size_t);
|
||||
|
||||
namespace clang {
|
||||
|
||||
/// AttrVec - A vector of Attr, which is how they are stored on the AST.
|
||||
using AttrVec = SmallVector<Attr *, 4>;
|
||||
|
||||
|
76
include/clang/AST/AttrVisitor.h
Normal file
76
include/clang/AST/AttrVisitor.h
Normal file
@ -0,0 +1,76 @@
|
||||
//===- AttrVisitor.h - Visitor for Attr subclasses --------------*- C++ -*-===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file is distributed under the University of Illinois Open Source
|
||||
// License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// This file defines the AttrVisitor interface.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_CLANG_AST_ATTRVISITOR_H
|
||||
#define LLVM_CLANG_AST_ATTRVISITOR_H
|
||||
|
||||
#include "clang/AST/Attr.h"
|
||||
|
||||
namespace clang {
|
||||
|
||||
namespace attrvisitor {
|
||||
|
||||
/// A simple visitor class that helps create attribute visitors.
|
||||
template <template <typename> class Ptr, typename ImplClass,
|
||||
typename RetTy = void, class... ParamTys>
|
||||
class Base {
|
||||
public:
|
||||
#define PTR(CLASS) typename Ptr<CLASS>::type
|
||||
#define DISPATCH(NAME) \
|
||||
return static_cast<ImplClass *>(this)->Visit##NAME(static_cast<PTR(NAME)>(A))
|
||||
|
||||
RetTy Visit(PTR(Attr) A) {
|
||||
switch (A->getKind()) {
|
||||
|
||||
#define ATTR(NAME) \
|
||||
case attr::NAME: \
|
||||
DISPATCH(NAME##Attr);
|
||||
#include "clang/Basic/AttrList.inc"
|
||||
}
|
||||
llvm_unreachable("Attr that isn't part of AttrList.inc!");
|
||||
}
|
||||
|
||||
// If the implementation chooses not to implement a certain visit
|
||||
// method, fall back to the parent.
|
||||
#define ATTR(NAME) \
|
||||
RetTy Visit##NAME##Attr(PTR(NAME##Attr) A) { DISPATCH(Attr); }
|
||||
#include "clang/Basic/AttrList.inc"
|
||||
|
||||
RetTy VisitAttr(PTR(Attr)) { return RetTy(); }
|
||||
|
||||
#undef PTR
|
||||
#undef DISPATCH
|
||||
};
|
||||
|
||||
} // namespace attrvisitor
|
||||
|
||||
/// A simple visitor class that helps create attribute visitors.
|
||||
///
|
||||
/// This class does not preserve constness of Attr pointers (see
|
||||
/// also ConstAttrVisitor).
|
||||
template <typename ImplClass, typename RetTy = void, typename... ParamTys>
|
||||
class AttrVisitor : public attrvisitor::Base<std::add_pointer, ImplClass, RetTy,
|
||||
ParamTys...> {};
|
||||
|
||||
/// A simple visitor class that helps create attribute visitors.
|
||||
///
|
||||
/// This class preserves constness of Attr pointers (see also
|
||||
/// AttrVisitor).
|
||||
template <typename ImplClass, typename RetTy = void, typename... ParamTys>
|
||||
class ConstAttrVisitor
|
||||
: public attrvisitor::Base<llvm::make_const_ptr, ImplClass, RetTy,
|
||||
ParamTys...> {};
|
||||
|
||||
} // namespace clang
|
||||
|
||||
#endif // LLVM_CLANG_AST_ATTRVISITOR_H
|
@ -15,6 +15,7 @@
|
||||
#define LLVM_CLANG_AST_BASESUBOBJECT_H
|
||||
|
||||
#include "clang/AST/CharUnits.h"
|
||||
#include "clang/AST/DeclCXX.h"
|
||||
#include "llvm/ADT/DenseMapInfo.h"
|
||||
#include "llvm/Support/type_traits.h"
|
||||
#include <cstdint>
|
||||
|
@ -8,10 +8,15 @@ clang_tablegen(AttrImpl.inc -gen-clang-attr-impl
|
||||
SOURCE ../Basic/Attr.td
|
||||
TARGET ClangAttrImpl)
|
||||
|
||||
clang_tablegen(AttrDump.inc -gen-clang-attr-dump
|
||||
clang_tablegen(AttrTextNodeDump.inc -gen-clang-attr-text-node-dump
|
||||
-I ${CMAKE_CURRENT_SOURCE_DIR}/../../
|
||||
SOURCE ../Basic/Attr.td
|
||||
TARGET ClangAttrDump)
|
||||
TARGET ClangAttrTextDump)
|
||||
|
||||
clang_tablegen(AttrNodeTraverse.inc -gen-clang-attr-node-traverse
|
||||
-I ${CMAKE_CURRENT_SOURCE_DIR}/../../
|
||||
SOURCE ../Basic/Attr.td
|
||||
TARGET ClangAttrTraverse)
|
||||
|
||||
clang_tablegen(AttrVisitor.inc -gen-clang-attr-ast-visitor
|
||||
-I ${CMAKE_CURRENT_SOURCE_DIR}/../../
|
||||
|
@ -510,7 +510,7 @@ struct CanProxyAdaptor<FunctionProtoType>
|
||||
}
|
||||
|
||||
LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isVariadic)
|
||||
LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(unsigned, getTypeQuals)
|
||||
LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(Qualifiers, getTypeQuals)
|
||||
|
||||
using param_type_iterator =
|
||||
CanTypeIterator<FunctionProtoType::param_type_iterator>;
|
||||
|
@ -215,13 +215,9 @@ class Comment {
|
||||
|
||||
SourceRange getSourceRange() const LLVM_READONLY { return Range; }
|
||||
|
||||
SourceLocation getLocStart() const LLVM_READONLY {
|
||||
return Range.getBegin();
|
||||
}
|
||||
SourceLocation getBeginLoc() const LLVM_READONLY { return Range.getBegin(); }
|
||||
|
||||
SourceLocation getLocEnd() const LLVM_READONLY {
|
||||
return Range.getEnd();
|
||||
}
|
||||
SourceLocation getEndLoc() const LLVM_READONLY { return Range.getEnd(); }
|
||||
|
||||
SourceLocation getLocation() const LLVM_READONLY { return Loc; }
|
||||
|
||||
@ -351,8 +347,7 @@ class InlineCommandComment : public InlineContentComment {
|
||||
}
|
||||
|
||||
SourceRange getCommandNameRange() const {
|
||||
return SourceRange(getLocStart().getLocWithOffset(-1),
|
||||
getLocEnd());
|
||||
return SourceRange(getBeginLoc().getLocWithOffset(-1), getEndLoc());
|
||||
}
|
||||
|
||||
RenderKind getRenderKind() const {
|
||||
@ -566,9 +561,9 @@ class ParagraphComment : public BlockContentComment {
|
||||
|
||||
ParagraphCommentBits.IsWhitespaceValid = false;
|
||||
|
||||
setSourceRange(SourceRange(Content.front()->getLocStart(),
|
||||
Content.back()->getLocEnd()));
|
||||
setLocation(Content.front()->getLocStart());
|
||||
setSourceRange(SourceRange(Content.front()->getBeginLoc(),
|
||||
Content.back()->getEndLoc()));
|
||||
setLocation(Content.front()->getBeginLoc());
|
||||
}
|
||||
|
||||
static bool classof(const Comment *C) {
|
||||
@ -662,13 +657,13 @@ class BlockCommandComment : public BlockContentComment {
|
||||
}
|
||||
|
||||
SourceLocation getCommandNameBeginLoc() const {
|
||||
return getLocStart().getLocWithOffset(1);
|
||||
return getBeginLoc().getLocWithOffset(1);
|
||||
}
|
||||
|
||||
SourceRange getCommandNameRange(const CommandTraits &Traits) const {
|
||||
StringRef Name = getCommandName(Traits);
|
||||
return SourceRange(getCommandNameBeginLoc(),
|
||||
getLocStart().getLocWithOffset(1 + Name.size()));
|
||||
getBeginLoc().getLocWithOffset(1 + Name.size()));
|
||||
}
|
||||
|
||||
unsigned getNumArgs() const {
|
||||
@ -688,7 +683,7 @@ class BlockCommandComment : public BlockContentComment {
|
||||
if (Args.size() > 0) {
|
||||
SourceLocation NewLocEnd = Args.back().Range.getEnd();
|
||||
if (NewLocEnd.isValid())
|
||||
setSourceRange(SourceRange(getLocStart(), NewLocEnd));
|
||||
setSourceRange(SourceRange(getBeginLoc(), NewLocEnd));
|
||||
}
|
||||
}
|
||||
|
||||
@ -702,9 +697,9 @@ class BlockCommandComment : public BlockContentComment {
|
||||
|
||||
void setParagraph(ParagraphComment *PC) {
|
||||
Paragraph = PC;
|
||||
SourceLocation NewLocEnd = PC->getLocEnd();
|
||||
SourceLocation NewLocEnd = PC->getEndLoc();
|
||||
if (NewLocEnd.isValid())
|
||||
setSourceRange(SourceRange(getLocStart(), NewLocEnd));
|
||||
setSourceRange(SourceRange(getBeginLoc(), NewLocEnd));
|
||||
}
|
||||
|
||||
CommandMarkerKind getCommandMarker() const LLVM_READONLY {
|
||||
@ -978,7 +973,7 @@ class VerbatimLineComment : public BlockCommandComment {
|
||||
}
|
||||
|
||||
SourceRange getTextRange() const {
|
||||
return SourceRange(TextBegin, getLocEnd());
|
||||
return SourceRange(TextBegin, getEndLoc());
|
||||
}
|
||||
};
|
||||
|
||||
@ -1105,9 +1100,9 @@ class FullComment : public Comment {
|
||||
if (Blocks.empty())
|
||||
return;
|
||||
|
||||
setSourceRange(SourceRange(Blocks.front()->getLocStart(),
|
||||
Blocks.back()->getLocEnd()));
|
||||
setLocation(Blocks.front()->getLocStart());
|
||||
setSourceRange(
|
||||
SourceRange(Blocks.front()->getBeginLoc(), Blocks.back()->getEndLoc()));
|
||||
setLocation(Blocks.front()->getBeginLoc());
|
||||
}
|
||||
|
||||
static bool classof(const Comment *C) {
|
||||
|
@ -10,20 +10,7 @@
|
||||
#ifndef LLVM_CLANG_AST_COMMENTDIAGNOSTIC_H
|
||||
#define LLVM_CLANG_AST_COMMENTDIAGNOSTIC_H
|
||||
|
||||
#include "clang/Basic/Diagnostic.h"
|
||||
|
||||
namespace clang {
|
||||
namespace diag {
|
||||
enum {
|
||||
#define DIAG(ENUM,FLAGS,DEFAULT_MAPPING,DESC,GROUP,\
|
||||
SFINAE,NOWERROR,SHOWINSYSHEADER,CATEGORY) ENUM,
|
||||
#define COMMENTSTART
|
||||
#include "clang/Basic/DiagnosticCommentKinds.inc"
|
||||
#undef DIAG
|
||||
NUM_BUILTIN_COMMENT_DIAGNOSTICS
|
||||
};
|
||||
} // end namespace diag
|
||||
} // end namespace clang
|
||||
#include "clang/Basic/DiagnosticComment.h"
|
||||
|
||||
#endif
|
||||
|
||||
|
@ -11,22 +11,21 @@
|
||||
#define LLVM_CLANG_AST_COMMENTVISITOR_H
|
||||
|
||||
#include "clang/AST/Comment.h"
|
||||
#include "llvm/ADT/STLExtras.h"
|
||||
#include "llvm/Support/ErrorHandling.h"
|
||||
|
||||
namespace clang {
|
||||
namespace comments {
|
||||
|
||||
template <typename T> struct make_ptr { using type = T *; };
|
||||
template <typename T> struct make_const_ptr { using type = const T *; };
|
||||
|
||||
template<template <typename> class Ptr, typename ImplClass, typename RetTy=void>
|
||||
template <template <typename> class Ptr, typename ImplClass,
|
||||
typename RetTy = void, class... ParamTys>
|
||||
class CommentVisitorBase {
|
||||
public:
|
||||
#define PTR(CLASS) typename Ptr<CLASS>::type
|
||||
#define DISPATCH(NAME, CLASS) \
|
||||
return static_cast<ImplClass*>(this)->visit ## NAME(static_cast<PTR(CLASS)>(C))
|
||||
#define DISPATCH(NAME, CLASS) \
|
||||
return static_cast<ImplClass *>(this)->visit##NAME( \
|
||||
static_cast<PTR(CLASS)>(C), std::forward<ParamTys>(P)...)
|
||||
|
||||
RetTy visit(PTR(Comment) C) {
|
||||
RetTy visit(PTR(Comment) C, ParamTys... P) {
|
||||
if (!C)
|
||||
return RetTy();
|
||||
|
||||
@ -44,25 +43,26 @@ class CommentVisitorBase {
|
||||
// If the derived class does not implement a certain Visit* method, fall back
|
||||
// on Visit* method for the superclass.
|
||||
#define ABSTRACT_COMMENT(COMMENT) COMMENT
|
||||
#define COMMENT(CLASS, PARENT) \
|
||||
RetTy visit ## CLASS(PTR(CLASS) C) { DISPATCH(PARENT, PARENT); }
|
||||
#define COMMENT(CLASS, PARENT) \
|
||||
RetTy visit##CLASS(PTR(CLASS) C, ParamTys... P) { DISPATCH(PARENT, PARENT); }
|
||||
#include "clang/AST/CommentNodes.inc"
|
||||
#undef ABSTRACT_COMMENT
|
||||
#undef COMMENT
|
||||
|
||||
RetTy visitComment(PTR(Comment) C) { return RetTy(); }
|
||||
RetTy visitComment(PTR(Comment) C, ParamTys... P) { return RetTy(); }
|
||||
|
||||
#undef PTR
|
||||
#undef DISPATCH
|
||||
};
|
||||
|
||||
template<typename ImplClass, typename RetTy=void>
|
||||
class CommentVisitor :
|
||||
public CommentVisitorBase<make_ptr, ImplClass, RetTy> {};
|
||||
template <typename ImplClass, typename RetTy = void, class... ParamTys>
|
||||
class CommentVisitor : public CommentVisitorBase<std::add_pointer, ImplClass,
|
||||
RetTy, ParamTys...> {};
|
||||
|
||||
template<typename ImplClass, typename RetTy=void>
|
||||
class ConstCommentVisitor :
|
||||
public CommentVisitorBase<make_const_ptr, ImplClass, RetTy> {};
|
||||
template <typename ImplClass, typename RetTy = void, class... ParamTys>
|
||||
class ConstCommentVisitor
|
||||
: public CommentVisitorBase<llvm::make_const_ptr, ImplClass, RetTy,
|
||||
ParamTys...> {};
|
||||
|
||||
} // namespace comments
|
||||
} // namespace clang
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user