Clang warning: use of this statement in a constexpr ... is a C++14 extension [-Wc++14-extensions] (ext_constexpr_body_invalid_stmt)

From emmtrix Wiki
Jump to navigation Jump to search
Text
error: use of this statement in a constexpr
function
constructor
is a C++14 extension

Type Warning
Category Semantic Issue
Internal Id ext_constexpr_body_invalid_stmt
Active by Default Yes
Flags -Wno-c++14-extensions (9 elements)
-Wno-c++1y-extensions (9 elements)
Internal Message use of this statement in a constexpr %select{function|constructor}0 is a C++14 extension
Regular Expression (?:warning|error|fatal error)\: use of this statement in a constexpr (?:function|constructor) is a C\+\+14 extension \[(?:\-Werror,)?\-Wc\+\+14\-extensions[^\]]*\]
First Commit 2013-04-22 d9f663b510c4 C++1y constexpr extensions, round 1: Allow most forms of declaration and

Description

The warning is issued by the Clang compiler when a constexpr function or constructor contains a statement or feature that is only permissible as a constexpr in the C++14 standard, but the code is being compiled with a standard version earlier than C++14. In such cases, using these statements or features as part of a constexpr function or constructor is an extension to the capabilities of constexpr in C++11 and will trigger this warning if such extensions are not explicitly allowed via compiler flags. This warning informs the user about the use of C++14 extensions within a constexpr context when compiling for a C++11 (or earlier) standard, which could potentially lead to portability issues if the code is intended to be C++11 compliant. The compiler flags -Wc++14-extensions and -Wc++1y-extensions are related to this warning, allowing users to control the emission of warnings related to the use of C++14 extensions.  
AI Generated

Example

In the following example, a constexpr function named f is defined to demonstrate how conditional statements within a constexpr function trigger a Clang warning when compiled under the C++11 standard. The function f takes a boolean parameter b and returns an integer value based on a simple if-else condition. The use of conditional statements and multiple return statements in a constexpr function or constructor is a feature introduced in C++14. Thus, attempting to compile this code as C++11 results in warnings indicating the use of C++14 extensions, specifically pointing out the use of an if statement and multiple return paths within a constexpr function. These warnings are meant to inform about potential portability issues or the use of newer language features when targeting an older C++ standard version.  
AI Generated


Flags -xc++ -std=c++11

[Try out in Compiler Explorer]

Source
#include <iostream>

constexpr int f(bool b) {
  // if statement
  if (b)
    return 10;
  else
    return 20;
}

int main() {
  std::cout << f(true) << std::endl;
  return 0;
}
Compiler Output
<source>:5:3: warning: use of this statement in a constexpr function is a C++14 extension [-Wc++14-extensions]
<source>:8:5: warning: multiple return statements in constexpr function is a C++14 extension [-Wc++14-extensions]
<source>:6:5: note: previous return statement is here


Clang Internals (17.0.6)

Git Commit Message

C++1y constexpr extensions, round 1: Allow most forms of declaration and
statement in constexpr functions. Everything which doesn't require variable
mutation is also allowed as an extension in C++11. 'void' becomes a literal
type to support constexpr functions which return 'void'.

llvm-svn: 180022

Used in Clang Sources

This section lists all occurrences of the diagnostic within the Clang's codebase. For each occurrence, an auto-extracted snipped from the source code is listed including key elements like control structures, functions, or classes. It should illustrate the conditions under which the diagnostic is activated.

clang/lib/Sema/SemaDeclCXX.cpp (line 2300)

/// Check the body for the given constexpr function declaration only contains
/// the permitted types of statement. C++11 [dcl.constexpr]p3,p4.
///
/// \return true if the body is OK, false if we have found or diagnosed a
/// problem.
static bool CheckConstexprFunctionBody(Sema &SemaRef, const FunctionDecl *Dcl, Stmt *Body, Sema::CheckConstexprKind Kind) {
  // ...
  if (Kind == Sema::CheckConstexprKind::CheckValid) {
  // ...
  } else if (Cxx2bLoc.isValid()) {
  // ...
  } else if (Cxx2aLoc.isValid()) {
  // ...
  } else if (Cxx1yLoc.isValid()) {
    SemaRef.Diag(Cxx1yLoc, SemaRef.getLangOpts().CPlusPlus14 ? diag::warn_cxx11_compat_constexpr_body_invalid_stmt : diag::ext_constexpr_body_invalid_stmt) << isa<CXXConstructorDecl>(Dcl);

Triggered in Clang Tests

This section lists all internal Clang test cases that trigger the diagnostic.

clang/test/CXX/dcl.dcl/dcl.spec/dcl.constexpr/p4.cpp

  • clang/test/CXX/dcl.dcl/dcl.spec/dcl.constexpr/p4.cpp:57:11: error: use of this statement in a constexpr constructor is a C++14 extension [-Werror,-Wc++14-extensions]
  • clang/test/CXX/dcl.dcl/dcl.spec/dcl.constexpr/p4.cpp:106:5: error: use of this statement in a constexpr constructor is a C++14 extension [-Werror,-Wc++14-extensions]
  • clang/test/CXX/dcl.dcl/dcl.spec/dcl.constexpr/p4.cpp:130:5: error: use of this statement in a constexpr constructor is a C++14 extension [-Werror,-Wc++14-extensions]