Hans, can we get this onto the Clang 4 release branch (along with the documentation added in r292558 and fixed in r292559)? This will allow us to avoid libc++ carrying a version test for Clang, and allow it to cleanly finish off its implementation of P0426.
On 19 January 2017 at 16:45, Richard Smith via cfe-commits < cfe-commits@lists.llvm.org> wrote: > Author: rsmith > Date: Thu Jan 19 18:45:35 2017 > New Revision: 292555 > > URL: http://llvm.org/viewvc/llvm-project?rev=292555&view=rev > Log: > P0426: Make the library implementation of constexpr char_traits a little > easier > by providing a memchr builtin that returns char* instead of void*. > > Also add a __has_feature flag to indicate the presence of constexpr forms > of > the relevant <string> functions. > > Modified: > cfe/trunk/include/clang/Basic/Builtins.def > cfe/trunk/lib/AST/ExprConstant.cpp > cfe/trunk/lib/CodeGen/CGBuiltin.cpp > cfe/trunk/lib/Lex/PPMacroExpansion.cpp > cfe/trunk/test/CodeGenCXX/builtins.cpp > cfe/trunk/test/Lexer/has_feature_cxx0x.cpp > cfe/trunk/test/SemaCXX/constexpr-string.cpp > > Modified: cfe/trunk/include/clang/Basic/Builtins.def > URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/ > clang/Basic/Builtins.def?rev=292555&r1=292554&r2=292555&view=diff > ============================================================ > ================== > --- cfe/trunk/include/clang/Basic/Builtins.def (original) > +++ cfe/trunk/include/clang/Basic/Builtins.def Thu Jan 19 18:45:35 2017 > @@ -1339,6 +1339,7 @@ BUILTIN(__builtin_smulll_overflow, "bSLL > BUILTIN(__builtin_addressof, "v*v&", "nct") > BUILTIN(__builtin_operator_new, "v*z", "c") > BUILTIN(__builtin_operator_delete, "vv*", "n") > +BUILTIN(__builtin_char_memchr, "c*cC*iz", "n") > > // Safestack builtins > BUILTIN(__builtin___get_unsafe_stack_start, "v*", "Fn") > > Modified: cfe/trunk/lib/AST/ExprConstant.cpp > URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ > ExprConstant.cpp?rev=292555&r1=292554&r2=292555&view=diff > ============================================================ > ================== > --- cfe/trunk/lib/AST/ExprConstant.cpp (original) > +++ cfe/trunk/lib/AST/ExprConstant.cpp Thu Jan 19 18:45:35 2017 > @@ -5683,6 +5683,7 @@ bool PointerExprEvaluator::VisitBuiltinC > case Builtin::BI__builtin_strchr: > case Builtin::BI__builtin_wcschr: > case Builtin::BI__builtin_memchr: > + case Builtin::BI__builtin_char_memchr: > case Builtin::BI__builtin_wmemchr: { > if (!Visit(E->getArg(0))) > return false; > @@ -5720,6 +5721,7 @@ bool PointerExprEvaluator::VisitBuiltinC > // Fall through. > case Builtin::BImemchr: > case Builtin::BI__builtin_memchr: > + case Builtin::BI__builtin_char_memchr: > // memchr compares by converting both sides to unsigned char. > That's also > // correct for strchr if we get this far (to cope with plain char > being > // unsigned in the strchr case). > > Modified: cfe/trunk/lib/CodeGen/CGBuiltin.cpp > URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/ > CGBuiltin.cpp?rev=292555&r1=292554&r2=292555&view=diff > ============================================================ > ================== > --- cfe/trunk/lib/CodeGen/CGBuiltin.cpp (original) > +++ cfe/trunk/lib/CodeGen/CGBuiltin.cpp Thu Jan 19 18:45:35 2017 > @@ -1189,6 +1189,10 @@ RValue CodeGenFunction::EmitBuiltinExpr( > return RValue::get(Dest.getPointer()); > } > > + case Builtin::BI__builtin_char_memchr: > + BuiltinID = Builtin::BI__builtin_memchr; > + break; > + > case Builtin::BI__builtin___memcpy_chk: { > // fold __builtin_memcpy_chk(x, y, cst1, cst2) to memcpy iff > cst1<=cst2. > llvm::APSInt Size, DstSize; > > Modified: cfe/trunk/lib/Lex/PPMacroExpansion.cpp > URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Lex/ > PPMacroExpansion.cpp?rev=292555&r1=292554&r2=292555&view=diff > ============================================================ > ================== > --- cfe/trunk/lib/Lex/PPMacroExpansion.cpp (original) > +++ cfe/trunk/lib/Lex/PPMacroExpansion.cpp Thu Jan 19 18:45:35 2017 > @@ -1183,6 +1183,7 @@ static bool HasFeature(const Preprocesso > .Case("cxx_attributes", LangOpts.CPlusPlus11) > .Case("cxx_auto_type", LangOpts.CPlusPlus11) > .Case("cxx_constexpr", LangOpts.CPlusPlus11) > + .Case("cxx_constexpr_string_builtins", LangOpts.CPlusPlus11) > .Case("cxx_decltype", LangOpts.CPlusPlus11) > .Case("cxx_decltype_incomplete_return_types", LangOpts.CPlusPlus11) > .Case("cxx_default_function_template_args", LangOpts.CPlusPlus11) > > Modified: cfe/trunk/test/CodeGenCXX/builtins.cpp > URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/ > CodeGenCXX/builtins.cpp?rev=292555&r1=292554&r2=292555&view=diff > ============================================================ > ================== > --- cfe/trunk/test/CodeGenCXX/builtins.cpp (original) > +++ cfe/trunk/test/CodeGenCXX/builtins.cpp Thu Jan 19 18:45:35 2017 > @@ -26,3 +26,7 @@ int x = __builtin_abs(-2); > long y = __builtin_abs(-2l); > // CHECK: [[Y:%.+]] = call i64 @_Z13__builtin_absl(i64 -2) > // CHECK: store i64 [[Y]], i64* @y, align 8 > + > +extern const char char_memchr_arg[32]; > +char *memchr_result = __builtin_char_memchr(char_memchr_arg, 123, 32); > +// CHECK: call i8* @memchr(i8* getelementptr inbounds ([32 x i8], [32 x > i8]* @char_memchr_arg, i32 0, i32 0), i32 123, i64 32) > > Modified: cfe/trunk/test/Lexer/has_feature_cxx0x.cpp > URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Lexer/ > has_feature_cxx0x.cpp?rev=292555&r1=292554&r2=292555&view=diff > ============================================================ > ================== > --- cfe/trunk/test/Lexer/has_feature_cxx0x.cpp (original) > +++ cfe/trunk/test/Lexer/has_feature_cxx0x.cpp Thu Jan 19 18:45:35 2017 > @@ -301,6 +301,17 @@ int no_constexpr(); > // CHECK-11: has_constexpr > // CHECK-NO-11: no_constexpr > > +#if __has_feature(cxx_constexpr_string_builtins) > +int has_constexpr_string_builtins(); > +#else > +int no_constexpr_string_builtins(); > +#endif > + > +// CHECK-1Z: has_constexpr_string_builtins > +// CHECK-14: has_constexpr_string_builtins > +// CHECK-11: has_constexpr_string_builtins > +// CHECK-NO-11: no_constexpr_string_builtins > + > #if __has_feature(cxx_generalized_initializers) > int has_generalized_initializers(); > #else > > Modified: cfe/trunk/test/SemaCXX/constexpr-string.cpp > URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/ > SemaCXX/constexpr-string.cpp?rev=292555&r1=292554&r2=292555&view=diff > ============================================================ > ================== > --- cfe/trunk/test/SemaCXX/constexpr-string.cpp (original) > +++ cfe/trunk/test/SemaCXX/constexpr-string.cpp Thu Jan 19 18:45:35 2017 > @@ -166,6 +166,27 @@ namespace StrchrEtc { > static_assert(__builtin_memchr(nullptr, 'x', 3) == nullptr); // > expected-error {{not an integral constant}} expected-note {{dereferenced > null}} > static_assert(__builtin_memchr(nullptr, 'x', 0) == nullptr); // FIXME: > Should we reject this? > > + static_assert(__builtin_char_memchr(kStr, 'a', 0) == nullptr); > + static_assert(__builtin_char_memchr(kStr, 'a', 1) == kStr); > + static_assert(__builtin_char_memchr(kStr, '\0', 5) == nullptr); > + static_assert(__builtin_char_memchr(kStr, '\0', 6) == kStr + 5); > + static_assert(__builtin_char_memchr(kStr, '\xff', 8) == kStr + 4); > + static_assert(__builtin_char_memchr(kStr, '\xff' + 256, 8) == kStr + > 4); > + static_assert(__builtin_char_memchr(kStr, '\xff' - 256, 8) == kStr + > 4); > + static_assert(__builtin_char_memchr(kFoo, 'x', 3) == nullptr); > + static_assert(__builtin_char_memchr(kFoo, 'x', 4) == nullptr); // > expected-error {{not an integral constant}} expected-note {{dereferenced > one-past-the-end}} > + static_assert(__builtin_char_memchr(nullptr, 'x', 3) == nullptr); // > expected-error {{not an integral constant}} expected-note {{dereferenced > null}} > + static_assert(__builtin_char_memchr(nullptr, 'x', 0) == nullptr); // > FIXME: Should we reject this? > + > + static_assert(*__builtin_char_memchr(kStr, '\xff', 8) == '\xff'); > + constexpr bool char_memchr_mutable() { > + char buffer[] = "mutable"; > + *__builtin_char_memchr(buffer, 't', 8) = 'r'; > + *__builtin_char_memchr(buffer, 'm', 8) = 'd'; > + return __builtin_strcmp(buffer, "durable") == 0; > + } > + static_assert(char_memchr_mutable()); > + > constexpr bool a = !strchr("hello", 'h'); // expected-error {{constant > expression}} expected-note {{non-constexpr function 'strchr' cannot be used > in a constant expression}} > constexpr bool b = !memchr("hello", 'h', 3); // expected-error > {{constant expression}} expected-note {{non-constexpr function 'memchr' > cannot be used in a constant expression}} > } > > > _______________________________________________ > cfe-commits mailing list > cfe-commits@lists.llvm.org > http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits >
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits