Skip to content

[Clang] question about template argument deduction #107111

@rherilier

Description

@rherilier

Hello,

While writing some code for the libsigc++ project, I faced a case with template code which needed to use #if/else/endif to make it build with gcc, clang and msvc.

I sadly fail to write a testcase without having libsigc++ as a dependency:

/**
 * to build:
 * * g++ -std=c++17 main.cpp `pkg-config sigc++-3.0 --cflags --libs`
 * * clang++ -std=c++17 main.cpp `pkg-config sigc++-3.0 --cflags --libs`
 */
#include <sigc++/sigc++.h>
#include <cstdio>

template<typename T_return, typename T_obj, typename T_obj2, typename... T_arg>
inline sigc::connection
connect1(sigc::signal<T_return(T_arg...)>& signal, T_obj& obj, T_return (T_obj2::*fun)(T_arg...))
{
  printf("connect1<..., T_obj, T_obj2, T_arg...>\n");
  return signal.connect(sigc::mem_fun<T_return, T_obj, T_obj2, T_arg...>(obj, fun));
}

template<typename T_return, typename T_obj, typename... T_arg>
inline sigc::connection
connect2(sigc::signal<T_return(T_arg...)>& signal, T_obj& obj, T_return (T_obj::*fun)(T_arg...))
{
  printf("connect2<..., T_obj, T_arg...>\n");
  return signal.connect(sigc::mem_fun<T_return, T_obj, T_obj, T_arg...>(obj, fun));
}

struct foo
{
  void fun(int i) { printf("foo::fun(int %d)\n", i); }
  void fun(double d) { printf("foo::fun(double %f)\n", d); }
};

int main()
{
  sigc::signal<void(int)> s;
  foo f;

  connect1(s, f, &foo::fun); // build on gcc and msvc but not clang
  connect2(s, f, &foo::fun); // build on gcc and clang but not msvc

  s.emit(42);

  return 0;
}

and the error log is:

main.cpp:36:3: error: no matching function for call to 'connect1'
  connect1(s, f, &foo::fun); // build on gcc and msvc but not clang
  ^~~~~~~~
main.cpp:11:1: note: candidate template ignored: couldn't infer template argument 'T_obj2'
connect1(sigc::signal<T_return(T_arg...)>& signal, T_obj& obj, T_return (T_obj2::*fun)(T_arg...))
^
1 error generated.

Used GCC's versions are 13.3.0 and 14.2.0 while clang's versions are 16.0.6, 17.0.6, 18.1.8, and 19.1.0.

As gcc and msvc success to compile connect1(s, &foo::fun), could it be a limit in clang's template arguments deduction algorithm?

Thanks in advance

Metadata

Metadata

Assignees

No one assigned

    Labels

    clang:frontendLanguage frontend issues, e.g. anything involving "Sema"questionA question, not bug report. Check out https://llvm.org/docs/GettingInvolved.html instead!

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions