<div dir="ltr">In my infinite cleverness I think I found a solution which gives both constexpr and non-trivial constructors.<div><br></div><div>Please take a look at <a href="https://reviews.llvm.org/D25389">https://reviews.llvm.org/D25389</a>.</div><div><br></div><div>/Eric</div></div><div class="gmail_extra"><br><div class="gmail_quote">On Fri, Oct 7, 2016 at 8:11 PM, Eric Fiselier <span dir="ltr"><<a href="mailto:eric@efcs.ca" target="_blank">eric@efcs.ca</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><div dir="ltr">On second thought applying (A) might be ill-advised. Most of the pair tests still fail after applying it in constructs like "std::is_copy_constructible_v<<wbr>std::pair<NonCopyable, int&&>>", except now instead of returning the wrong answer the traits cause hard compile errors and template barf.<div><br></div><div>@Ed, David, and Dimitry The FreeBSD std::pair implementation is fundamentally broken, and there's not much I think I can do about it. Is there a timeline for making the ABI change in FreeBSD?</div><span class="HOEnZb"><font color="#888888"><div><br></div><div>/Eric</div></font></span></div><div class="HOEnZb"><div class="h5"><div class="gmail_extra"><br><div class="gmail_quote">On Fri, Oct 7, 2016 at 7:59 PM, Eric Fiselier <span dir="ltr"><<a href="mailto:eric@efcs.ca" target="_blank">eric@efcs.ca</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><div dir="ltr"><span>> <span style="font-size:12.8px">Does anyone know what the problem may be?</span><div><span style="font-size:12.8px"><br></span></div></span><div><span style="font-size:12.8px">FreeBSD ships std::pair with explicitly defined copy and move constructors as opposed to explicitly defaulted ones. Mistakenly these constructors have not been marked constexpr in C++14.</span></div><div><span style="font-size:12.8px">FreeBSD provides these old constructors is because switching to defaulted copy/move constructors is an ABI break because it makes std::pair non-trivial and changes how it's passed to functions according to the Itanium ABI.</span><br></div><div><span style="font-size:12.8px"><br></span></div><div>Fixing this requires either (A) marking the fallback constructors constexpr in C++14, or (B) convincing FreeBSD to take the ABI break.</div><div><br></div><div>The easiest and simplistic fix is (A). However my concern with (A) is that the fallback constructors don't SFINAE away if they are ill-formed. This means that applying constexpr to them could break existing code by causing the eager instantiation of the ill-formed constructors, instantiations that would not occur if the constructors were non-constexpr. For this reason I think fix (B) is more correct, and greatly preferable.</div><div><br></div><div>Since we have plenty of time until the next release I'll go ahead and commit (A) for now, keeping my ear to the ground for breakage.  </div><span><font color="#888888"><div><br></div><div>/Eric</div><div><span style="font-size:12.8px"><br></span></div></font></span></div><div><div><div class="gmail_extra"><br><div class="gmail_quote">On Fri, Oct 7, 2016 at 7:23 PM, Krzysztof Parzyszek via cfe-dev <span dir="ltr"><<a href="mailto:cfe-dev@lists.llvm.org" target="_blank">cfe-dev@lists.llvm.org</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">I'm running this on FreeBSD 11 (stable). It has clang-3.8.0 as the system compiler. LLVM/Clang/et al. compiled without problems, but I'm seeing failures in check-libcxx.  Example below.<br>
<br>
Does anyone know what the problem may be?<br>
<br>
<br>
clang version 4.0.0 (<a href="http://llvm.org/git/clang.git" rel="noreferrer" target="_blank">http://llvm.org/git/clang.git</a> a85c03256cfc0812e268f5e0f1b804<wbr>910e75e673) (<a href="http://llvm.org/git/llvm.git" rel="noreferrer" target="_blank">http://llvm.org/git/llvm.git</a> c95d4ff692323bde64fc8ef45e174b<wbr>19450779af)<br>
Target: x86_64-unknown-freebsd11.0<br>
Thread model: posix<br>
InstalledDir: /w/c/org/bin<br>
 "/w/c/org/bin/clang-4.0" -cc1 -triple x86_64-unknown-freebsd11.0 -emit-obj -mrelax-all -disable-free -main-file-name minmax_init_list_comp.pass.cpp -mrelocation-model static -mthread-model posix -mdisable-fp-elim -masm-verbose -mconstructor-aliases -munwind-tables -target-cpu x86-64 -v -v -dwarf-column-info -debugger-tuning=gdb -coverage-notes-file /w/bld/org/projects/libcxx/tes<wbr>t/std/algorithms/alg.sorting/a<wbr>lg.min.max/Output/minmax_init_<wbr>list_comp.pass.cpp.gcno -nostdinc++ -resource-dir /w/c/org/bin/../lib/clang/4.0.<wbr>0 -include /w/src/<a href="http://llvm.org/projects/libcxx/test/support/nasty_macros.hpp" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/support/nasty_macros.hp<wbr>p</a> -I /w/src/<a href="http://llvm.org/projects/libcxx/include" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include</a> -I /w/src/<a href="http://llvm.org/projects/libcxx/test/support" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/support</a> -D LIBCXX_FILESYSTEM_STATIC_TEST_<wbr>ROOT=/w/src/<a href="http://llvm.org/projects/libcxx/test/std/experimental/filesystem/Inputs/static_test_env" rel="noreferrer" target="_blank">llvm.org/projects/<wbr>libcxx/test/std/experimental/f<wbr>ilesystem/Inputs/static_test_e<wbr>nv</a> -D LIBCXX_FILESYSTEM_DYNAMIC_TEST<wbr>_ROOT=/w/bld/org/projects/libc<wbr>xx/test/filesystem/Output/dyna<wbr>mic_env -D LIBCXX_FILESYSTEM_DYNAMIC_TEST<wbr>_HELPER=/usr/local/bin/python2<wbr>.7 /w/src/<a href="http://llvm.org/projects/libcxx/test/support/filesystem_dynamic_test_helper.py" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/support/filesystem_dyna<wbr>mic_test_helper.py</a> -Werror=thread-safety -std=c++1z -fdeprecated-macro -fdebug-compilation-dir /w/src/<a href="http://llvm.org" rel="noreferrer" target="_blank">llvm.org</a> -ferror-limit 19 -fmessage-length 210 -fobjc-runtime=gnustep -fcxx-exceptions -fexceptions -fdiagnostics-show-option -fcolor-diagnostics -o /w/bld/org/projects/libcxx/tes<wbr>t/std/algorithms/alg.sorting/a<wbr>lg.min.max/Output/minmax_init_<wbr>list_comp.pass.cpp.o -x c++ /w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp</a><br>
clang -cc1 version 4.0.0 based upon LLVM 4.0.0svn default target x86_64-unknown-freebsd11.0<br>
#include "..." search starts here:<br>
#include <...> search starts here:<br>
 /w/src/<a href="http://llvm.org/projects/libcxx/include" rel="noreferrer" target="_blank">llvm.org/projects/libc<wbr>xx/include</a><br>
 /w/src/<a href="http://llvm.org/projects/libcxx/test/support" rel="noreferrer" target="_blank">llvm.org/projects/libc<wbr>xx/test/support</a><br>
 /w/c/org/bin/../lib/clang/4.0<wbr>.0/include<br>
 /usr/include<br>
End of search list.<br>
/w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp:68:19" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp:68:19</a>: error: static_assert expression is not an integral constant expression<br>
    static_assert((std::minmax({1, 2, 3}, std::greater<int>()) == std::pair<int, int>(3, 1)), "");<br>
<br>
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~<wbr>~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~<wbr>~~~~~~~~~~~~~~<br>
/w/src/<a href="http://llvm.org/projects/libcxx/include/algorithm:2823:12" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include/algorithm:2823:12</a>: note: non-constexpr constructor 'pair' cannot be used in a constant expression<br>
    return __result;<br>
           ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp:68:20" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp:68:20</a>: note: in call to 'minmax({&{1, 2, 3}[0], 3}, {{}})'<br>
    static_assert((std::minmax({1, 2, 3}, std::greater<int>()) == std::pair<int, int>(3, 1)), "");<br>
                   ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/include/utility:316:5" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include/utility:316:5</a>: note: declared here<br>
    pair(pair&& __p) _NOEXCEPT_(is_nothrow_move_con<wbr>structible<first_type>::value &&<br>
    ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp:69:19" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp:69:19</a>: error: static_assert expression is not an integral constant expression<br>
    static_assert((std::minmax({1, 3, 2}, std::greater<int>()) == std::pair<int, int>(3, 1)), "");<br>
<br>
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~<wbr>~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~<wbr>~~~~~~~~~~~~~~<br>
/w/src/<a href="http://llvm.org/projects/libcxx/include/algorithm:2823:12" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include/algorithm:2823:12</a>: note: non-constexpr constructor 'pair' cannot be used in a constant expression<br>
    return __result;<br>
           ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp:69:20" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp:69:20</a>: note: in call to 'minmax({&{1, 3, 2}[0], 3}, {{}})'<br>
    static_assert((std::minmax({1, 3, 2}, std::greater<int>()) == std::pair<int, int>(3, 1)), "");<br>
                   ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/include/utility:316:5" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include/utility:316:5</a>: note: declared here<br>
    pair(pair&& __p) _NOEXCEPT_(is_nothrow_move_con<wbr>structible<first_type>::value &&<br>
    ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp:70:19" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp:70:19</a>: error: static_assert expression is not an integral constant expression<br>
    static_assert((std::minmax({2, 1, 3}, std::greater<int>()) == std::pair<int, int>(3, 1)), "");<br>
<br>
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~<wbr>~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~<wbr>~~~~~~~~~~~~~~<br>
/w/src/<a href="http://llvm.org/projects/libcxx/include/algorithm:2823:12" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include/algorithm:2823:12</a>: note: non-constexpr constructor 'pair' cannot be used in a constant expression<br>
    return __result;<br>
           ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp:70:20" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp:70:20</a>: note: in call to 'minmax({&{2, 1, 3}[0], 3}, {{}})'<br>
    static_assert((std::minmax({2, 1, 3}, std::greater<int>()) == std::pair<int, int>(3, 1)), "");<br>
                   ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/include/utility:316:5" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include/utility:316:5</a>: note: declared here<br>
    pair(pair&& __p) _NOEXCEPT_(is_nothrow_move_con<wbr>structible<first_type>::value &&<br>
    ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp:71:19" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp:71:19</a>: error: static_assert expression is not an integral constant expression<br>
    static_assert((std::minmax({2, 3, 1}, std::greater<int>()) == std::pair<int, int>(3, 1)), "");<br>
<br>
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~<wbr>~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~<wbr>~~~~~~~~~~~~~~<br>
/w/src/<a href="http://llvm.org/projects/libcxx/include/algorithm:2823:12" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include/algorithm:2823:12</a>: note: non-constexpr constructor 'pair' cannot be used in a constant expression<br>
    return __result;<br>
           ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp:71:20" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp:71:20</a>: note: in call to 'minmax({&{2, 3, 1}[0], 3}, {{}})'<br>
    static_assert((std::minmax({2, 3, 1}, std::greater<int>()) == std::pair<int, int>(3, 1)), "");<br>
                   ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/include/utility:316:5" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include/utility:316:5</a>: note: declared here<br>
    pair(pair&& __p) _NOEXCEPT_(is_nothrow_move_con<wbr>structible<first_type>::value &&<br>
    ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp:72:19" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp:72:19</a>: error: static_assert expression is not an integral constant expression<br>
    static_assert((std::minmax({3, 1, 2}, std::greater<int>()) == std::pair<int, int>(3, 1)), "");<br>
<br>
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~<wbr>~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~<wbr>~~~~~~~~~~~~~~<br>
/w/src/<a href="http://llvm.org/projects/libcxx/include/algorithm:2823:12" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include/algorithm:2823:12</a>: note: non-constexpr constructor 'pair' cannot be used in a constant expression<br>
    return __result;<br>
           ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp:72:20" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp:72:20</a>: note: in call to 'minmax({&{3, 1, 2}[0], 3}, {{}})'<br>
    static_assert((std::minmax({3, 1, 2}, std::greater<int>()) == std::pair<int, int>(3, 1)), "");<br>
                   ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/include/utility:316:5" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include/utility:316:5</a>: note: declared here<br>
    pair(pair&& __p) _NOEXCEPT_(is_nothrow_move_con<wbr>structible<first_type>::value &&<br>
    ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp:73:19" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp:73:19</a>: error: static_assert expression is not an integral constant expression<br>
    static_assert((std::minmax({3, 2, 1}, std::greater<int>()) == std::pair<int, int>(3, 1)), "");<br>
<br>
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~<wbr>~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~<wbr>~~~~~~~~~~~~~~<br>
/w/src/<a href="http://llvm.org/projects/libcxx/include/algorithm:2823:12" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include/algorithm:2823:12</a>: note: non-constexpr constructor 'pair' cannot be used in a constant expression<br>
    return __result;<br>
           ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/test/std/algorithms/alg.sorting/alg.min.max/minmax_init_list_comp.pass.cpp:73:20" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/test/std/algorithms/alg.sort<wbr>ing/alg.min.max/minmax_init_li<wbr>st_comp.pass.cpp:73:20</a>: note: in call to 'minmax({&{3, 2, 1}[0], 3}, {{}})'<br>
    static_assert((std::minmax({3, 2, 1}, std::greater<int>()) == std::pair<int, int>(3, 1)), "");<br>
                   ^<br>
/w/src/<a href="http://llvm.org/projects/libcxx/include/utility:316:5" rel="noreferrer" target="_blank">llvm.org/projects/libcx<wbr>x/include/utility:316:5</a>: note: declared here<br>
    pair(pair&& __p) _NOEXCEPT_(is_nothrow_move_con<wbr>structible<first_type>::value &&<br>
    ^<br>
6 errors generated.<br>
<br>
<br>
-Krzysztof<br>
<br>
______________________________<wbr>_________________<br>
cfe-dev mailing list<br>
<a href="mailto:cfe-dev@lists.llvm.org" target="_blank">cfe-dev@lists.llvm.org</a><br>
<a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-dev" rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/<wbr>mailman/listinfo/cfe-dev</a><br>
</blockquote></div><br></div>
</div></div></blockquote></div><br></div>
</div></div></blockquote></div><br></div>