egorzhdan created this revision. egorzhdan added a reviewer: gchatelet. Herald added a project: All. egorzhdan requested review of this revision. Herald added a project: clang. Herald added a subscriber: cfe-commits.
This change teaches the Sema logic for `__builtin_memcpy_inline` to implicitly convert arrays passed as arguments to pointers, similarly to regular `memcpy`. This code will no longer cause a compiler crash: void f(char *p) { char s[1] = {0}; __builtin_memcpy_inline(p, s, 1); } rdar://88147527 Repository: rG LLVM Github Monorepo https://reviews.llvm.org/D121475 Files: clang/lib/Sema/SemaChecking.cpp clang/test/Sema/builtins-memcpy-inline.cpp Index: clang/test/Sema/builtins-memcpy-inline.cpp =================================================================== --- clang/test/Sema/builtins-memcpy-inline.cpp +++ clang/test/Sema/builtins-memcpy-inline.cpp @@ -36,3 +36,9 @@ // we do not try to evaluate size in non intantiated templates. __builtin_memcpy_inline(dst, src, size); } + +void test_memcpy_inline_implicit_conversion(void *ptr) { + char a[5]; + __builtin_memcpy_inline(ptr, a, 5); + __builtin_memcpy_inline(a, ptr, 5); +} Index: clang/lib/Sema/SemaChecking.cpp =================================================================== --- clang/lib/Sema/SemaChecking.cpp +++ clang/lib/Sema/SemaChecking.cpp @@ -1943,6 +1943,17 @@ case Builtin::BI__builtin_nontemporal_store: return SemaBuiltinNontemporalOverloaded(TheCallResult); case Builtin::BI__builtin_memcpy_inline: { + auto ArgArrayConversion = [&](unsigned Arg) { + ExprResult ArgExpr = + DefaultFunctionArrayLvalueConversion(TheCall->getArg(Arg)); + if (ArgExpr.isInvalid()) + return true; + TheCall->setArg(Arg, ArgExpr.get()); + return false; + }; + + if (ArgArrayConversion(0) || ArgArrayConversion(1)) + return true; clang::Expr *SizeOp = TheCall->getArg(2); // We warn about copying to or from `nullptr` pointers when `size` is // greater than 0. When `size` is value dependent we cannot evaluate its
Index: clang/test/Sema/builtins-memcpy-inline.cpp =================================================================== --- clang/test/Sema/builtins-memcpy-inline.cpp +++ clang/test/Sema/builtins-memcpy-inline.cpp @@ -36,3 +36,9 @@ // we do not try to evaluate size in non intantiated templates. __builtin_memcpy_inline(dst, src, size); } + +void test_memcpy_inline_implicit_conversion(void *ptr) { + char a[5]; + __builtin_memcpy_inline(ptr, a, 5); + __builtin_memcpy_inline(a, ptr, 5); +} Index: clang/lib/Sema/SemaChecking.cpp =================================================================== --- clang/lib/Sema/SemaChecking.cpp +++ clang/lib/Sema/SemaChecking.cpp @@ -1943,6 +1943,17 @@ case Builtin::BI__builtin_nontemporal_store: return SemaBuiltinNontemporalOverloaded(TheCallResult); case Builtin::BI__builtin_memcpy_inline: { + auto ArgArrayConversion = [&](unsigned Arg) { + ExprResult ArgExpr = + DefaultFunctionArrayLvalueConversion(TheCall->getArg(Arg)); + if (ArgExpr.isInvalid()) + return true; + TheCall->setArg(Arg, ArgExpr.get()); + return false; + }; + + if (ArgArrayConversion(0) || ArgArrayConversion(1)) + return true; clang::Expr *SizeOp = TheCall->getArg(2); // We warn about copying to or from `nullptr` pointers when `size` is // greater than 0. When `size` is value dependent we cannot evaluate its
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits