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

Constexpr template member function call is not taken as a constant expression #129986

Closed
WorldRobertProject opened this issue Mar 6, 2025 · 3 comments
Labels
clang:frontend Language frontend issues, e.g. anything involving "Sema" confirmed Verified by a second party constexpr Anything related to constant evaluation question A question, not bug report. Check out https://llvm.org/docs/GettingInvolved.html instead! rejects-valid

Comments

@WorldRobertProject
Copy link

WorldRobertProject commented Mar 6, 2025

    class X
    {
    public:
        constexpr X()
        {
            Foo(1);
        }
    
        template <typename T>
        constexpr void Foo(T value)
        {
        }
    };
    
    constexpr X x;

The above code produces the following compilation error:

    error: constexpr variable 'x' must be initialized by a constant expression
    | constexpr X x;
    |             ^
    note: undefined function 'Foo<int>' cannot be used in a constant expression
    |         Foo(1);
    |         ^
    note: in call to 'X()'
    | constexpr X x;
    |             ^
    note: declared here
    |     constexpr void Foo(T value)
    |                    ^

When Foo is a global function, no error occurs.

clang version: 18.1.8 (Red Hat, Inc. 18.1.8-3.el9)

@dtcxzyw dtcxzyw added clang:frontend Language frontend issues, e.g. anything involving "Sema" rejects-valid constexpr Anything related to constant evaluation confirmed Verified by a second party and removed new issue labels Mar 6, 2025
@llvmbot
Copy link
Member

llvmbot commented Mar 6, 2025

@llvm/issue-subscribers-clang-frontend

Author: Robert (WorldRobertProject)

class X { public: constexpr X() { Foo(1); }
    template &lt;typename T&gt;
    constexpr void Foo(T value)
    {
    }
};

constexpr X x;

The above code produces the following compilation error:

error: constexpr variable 'x' must be initialized by a constant expression
| constexpr X x;
|             ^
note: undefined function 'Foo&lt;int&gt;' cannot be used in a constant expression
|         Foo(1);
|         ^
note: in call to 'X()'
| constexpr X x;
|             ^
note: declared here
|     constexpr void Foo(T value)
|                    ^

When Foo is a global function, no error occurs.

clang version: 18.1.8 (Red Hat, Inc. 18.1.8-3.el9)

@tbaederr
Copy link
Contributor

tbaederr commented Mar 6, 2025

This is probably #73232

@WorldRobertProject
Copy link
Author

Thank you so much, @tbaederr!

I understand that this is a problem with the language specification itself
regarding the timing of template instantiation.

The following code is successfully compiled.

class X
{
public:
    constexpr X();

    template <typename T>
    constexpr void Foo(T value)
    {
    }
};

constexpr X::X()
{
    Foo(1);
}

constexpr X x;

I'm thinking of writing codes like this to avoid this problem.

@EugeneZelenko EugeneZelenko added the question A question, not bug report. Check out https://llvm.org/docs/GettingInvolved.html instead! label Mar 6, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
clang:frontend Language frontend issues, e.g. anything involving "Sema" confirmed Verified by a second party constexpr Anything related to constant evaluation question A question, not bug report. Check out https://llvm.org/docs/GettingInvolved.html instead! rejects-valid
Projects
None yet
Development

No branches or pull requests

5 participants