Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

defaulted destructor makes defaulted copy constructor non-constexpr #37491

Closed
mclow opened this issue Jul 12, 2018 · 4 comments
Closed

defaulted destructor makes defaulted copy constructor non-constexpr #37491

mclow opened this issue Jul 12, 2018 · 4 comments
Labels
bugzilla Issues migrated from bugzilla c++ clang:diagnostics New/improved warning or error message in Clang, but not in clang-tidy or static analyzer clang:frontend Language frontend issues, e.g. anything involving "Sema" constexpr Anything related to constant evaluation

Comments

@mclow
Copy link
Contributor

mclow commented Jul 12, 2018

Bugzilla Link 38143
Version trunk
OS All
CC @DougGregor,@marehr,@zygoloid

Extended Description

Consider this code:

class span {
public:
    using pointer                = const int *;

    constexpr span() : __data{nullptr} {}

    constexpr span           (const span&) noexcept = default;
    constexpr span& operator=(const span&) noexcept = default;
    ~span() noexcept = default;

    constexpr pointer data()    const noexcept { return __data; }

private:
    pointer __data;
};

When compiled with a recent clang [clang version 7.0.0 (trunk 336548)], (-std=c++2a) it gives an error:

junk.cpp:8:5: error: defaulted definition of copy assignment operator is not
      constexpr
    constexpr span& operator=(const span&) noexcept = default;
    ^

However, if I switch the order of the two lines to:
    ~span() noexcept = default;
    constexpr span& operator=(const span&) noexcept = default;

then it compiles w/o error.

However, I believe that it should compile w/o error in both cases.

@marehr
Copy link

marehr commented Apr 30, 2019

duplicate of #26063 ?

@llvmbot
Copy link
Member

llvmbot commented Nov 21, 2021

Still persists in Clang 13 with constexpr constructors.

This issue doesn't appear in GCC 11.2 and Clang 13 with -std=c++17, but it only appears when the flag -std=c++20 is given.

Below is the sample code:

struct Foo {
  constexpr Foo(const Foo&) noexcept = default;
  constexpr Foo(Foo&&) noexcept = default;

  constexpr auto operator=(const Foo&) noexcept -> Foo& = default;
  constexpr auto operator=(Foo&&) noexcept -> Foo& = default;
};

with the following errors:

<source>:5:3: error: defaulted definition of copy assignment operator is not constexpr
  constexpr auto operator=(const Foo&) noexcept -> Foo& = default;
  ^
<source>:6:3: error: defaulted definition of move assignment operator is not constexpr
  constexpr auto operator=(Foo&&) noexcept -> Foo& = default;
  ^
2 errors generated.
Compiler returned: 1

Live demo: https://godbolt.org/z/6Mz6K3PMf

As shown above, the warning states that both assignment operators are not constexpr even though they are already declared constexpr, which is contradictory.

@llvmbot llvmbot transferred this issue from llvm/llvm-bugzilla-archive Dec 10, 2021
@Endilll Endilll added the clang:to-be-triaged Should not be used for new issues label Jul 20, 2024
@frederick-vs-ja
Copy link
Contributor

frederick-vs-ja commented Feb 21, 2025

The original issue was a duplicate.

Still persists in Clang 13 with constexpr constructors.

No. Lack of the constexpr default constructor was critical before C++23, see N4868 [basic.type]/10.5.2 and P2448R2.

Clang was correct on rejecting constexpr on Foo::operator=, but the diagnostic message was wrong. #85145 fixed the diagnostic message in Clang 19.

Now Clang says

error: defaulted definition of copy assignment operator cannot be marked constexpr before C++23

Godbolt link

@frederick-vs-ja frederick-vs-ja added clang:frontend Language frontend issues, e.g. anything involving "Sema" clang:diagnostics New/improved warning or error message in Clang, but not in clang-tidy or static analyzer constexpr Anything related to constant evaluation and removed clang:to-be-triaged Should not be used for new issues labels Feb 21, 2025
@llvmbot
Copy link
Member

llvmbot commented Feb 21, 2025

@llvm/issue-subscribers-clang-frontend

Author: Marshall Clow (mclow)

| | | | --- | --- | | Bugzilla Link | [38143](https://llvm.org/bz38143) | | Version | trunk | | OS | All | | CC | @DougGregor,@marehr,@zygoloid |

Extended Description

Consider this code:

class span {
public:
    using pointer                = const int *;

    constexpr span() : __data{nullptr} {}

    constexpr span           (const span&amp;) noexcept = default;
    constexpr span&amp; operator=(const span&amp;) noexcept = default;
    ~span() noexcept = default;

    constexpr pointer data()    const noexcept { return __data; }

private:
    pointer __data;
};

When compiled with a recent clang [clang version 7.0.0 (trunk 336548)], (-std=c++2a) it gives an error:

junk.cpp:8:5: error: defaulted definition of copy assignment operator is not
      constexpr
    constexpr span&amp; operator=(const span&amp;) noexcept = default;
    ^

However, if I switch the order of the two lines to:
    ~span() noexcept = default;
    constexpr span&amp; operator=(const span&amp;) noexcept = default;

then it compiles w/o error.

However, I believe that it should compile w/o error in both cases.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bugzilla Issues migrated from bugzilla c++ clang:diagnostics New/improved warning or error message in Clang, but not in clang-tidy or static analyzer clang:frontend Language frontend issues, e.g. anything involving "Sema" constexpr Anything related to constant evaluation
Projects
None yet
Development

No branches or pull requests

5 participants