From: Reid Kleckner Date: Fri, 20 Mar 2015 00:31:07 +0000 (+0000) Subject: C++14: Disable sized deallocation by default due to ABI breakage X-Git-Tag: llvmorg-3.7.0-rc1~8756 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=7ffc3fbb2f448e5c23da7ebe2af71fe29f92fa04;p=platform%2Fupstream%2Fllvm.git C++14: Disable sized deallocation by default due to ABI breakage There are no widely deployed standard libraries providing sized deallocation functions, so we have to punt and ask the user if they want us to use sized deallocation. In the future, when such libraries are deployed, we can teach the driver to detect them and enable this feature. N3536 claimed that a weak thunk from sized to unsized deallocation could be emitted to avoid breaking backwards compatibility with standard libraries not providing sized deallocation. However, this approach and other variations don't work in practice. With the weak function approach, the thunk has to have default visibility in order to ensure that it is overridden by other DSOs providing sized deallocation. Weak, default visibility symbols are particularly expensive on MachO, so John McCall was considering disabling this feature by default on Darwin. It also changes behavior ELF linking behavior, causing certain otherwise unreferenced object files from an archive to be pulled into the link. Our second approach was to use an extern_weak function declaration and do an inline conditional branch at the deletion call site. This doesn't work because extern_weak only works on MachO if you have some archive providing the default value of the extern_weak symbol. Arranging to provide such an archive has the same challenges as providing the symbol in the standard library. Not to mention that extern_weak doesn't really work on COFF. Reviewers: rsmith, rjmccall Differential Revision: http://reviews.llvm.org/D8467 llvm-svn: 232788 --- diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst index 5727a35..90655d4 100644 --- a/clang/docs/ReleaseNotes.rst +++ b/clang/docs/ReleaseNotes.rst @@ -62,6 +62,11 @@ about them. The improvements since the 3.5 release include: New Compiler Flags ------------------ +The sized deallocation feature of C++14 is now controlled by the +``-fsized-deallocation`` flag. This feature relies on library support that +isn't yet widely deployed, so the user must supply an extra flag to get the +extra functionality. + The option .... diff --git a/clang/include/clang/AST/Decl.h b/clang/include/clang/AST/Decl.h index 5380339..009335d 100644 --- a/clang/include/clang/AST/Decl.h +++ b/clang/include/clang/AST/Decl.h @@ -1861,11 +1861,6 @@ public: /// allocation function. [...] bool isReplaceableGlobalAllocationFunction() const; - /// \brief Determine whether this function is a sized global deallocation - /// function in C++1y. If so, find and return the corresponding unsized - /// deallocation function. - FunctionDecl *getCorrespondingUnsizedGlobalDeallocationFunction() const; - /// Compute the language linkage. LanguageLinkage getLanguageLinkage() const; diff --git a/clang/include/clang/Basic/LangOptions.def b/clang/include/clang/Basic/LangOptions.def index 21de1e3..f9c372c 100644 --- a/clang/include/clang/Basic/LangOptions.def +++ b/clang/include/clang/Basic/LangOptions.def @@ -165,7 +165,6 @@ LANGOPT(CUDAAllowHostCallsFromHostDevice, 1, 0, "Allow host device functions to LANGOPT(AssumeSaneOperatorNew , 1, 1, "implicit __attribute__((malloc)) for C++'s new operators") LANGOPT(SizedDeallocation , 1, 0, "enable sized deallocation functions") -LANGOPT(DefineSizedDeallocation , 1, 0, "generate weak definitions of sized delete") BENIGN_LANGOPT(ElideConstructors , 1, 1, "C++ copy constructor elision") BENIGN_LANGOPT(DumpRecordLayouts , 1, 0, "dumping the layout of IRgen'd records") BENIGN_LANGOPT(DumpRecordLayoutsSimple , 1, 0, "dumping the layout of IRgen'd records in a simple form") diff --git a/clang/include/clang/Driver/CC1Options.td b/clang/include/clang/Driver/CC1Options.td index 11e6942..6b785b45 100644 --- a/clang/include/clang/Driver/CC1Options.td +++ b/clang/include/clang/Driver/CC1Options.td @@ -518,12 +518,6 @@ def fdeprecated_macro : Flag<["-"], "fdeprecated-macro">, HelpText<"Defines the __DEPRECATED macro">; def fno_deprecated_macro : Flag<["-"], "fno-deprecated-macro">, HelpText<"Undefines the __DEPRECATED macro">; -def fsized_deallocation : Flag<["-"], "fsized-deallocation">, - HelpText<"Enable C++14 sized global deallocation functions">; -def fno_sized_deallocation: Flag<["-"], "fno-sized-deallocation">, - HelpText<"Disable sized deallocation functions">; -def fdefine_sized_deallocation: Flag<["-"], "fdefine-sized-deallocation">, - HelpText<"Allow compiler-generated definition of sized deallocation functions">; def fobjc_subscripting_legacy_runtime : Flag<["-"], "fobjc-subscripting-legacy-runtime">, HelpText<"Allow Objective-C array and dictionary subscripting in legacy runtime">; def vtordisp_mode_EQ : Joined<["-"], "vtordisp-mode=">, diff --git a/clang/include/clang/Driver/Options.td b/clang/include/clang/Driver/Options.td index 20b1c43..5a37a64 100644 --- a/clang/include/clang/Driver/Options.td +++ b/clang/include/clang/Driver/Options.td @@ -830,6 +830,9 @@ def fapplication_extension : Flag<["-"], "fapplication-extension">, HelpText<"Restrict code to those available for App Extensions">; def fno_application_extension : Flag<["-"], "fno-application-extension">, Group; +def fsized_deallocation : Flag<["-"], "fsized-deallocation">, Flags<[CC1Option]>, + HelpText<"Enable C++14 sized global deallocation functions">, Group; +def fno_sized_deallocation: Flag<["-"], "fno-sized-deallocation">, Group; def fobjc_gc_only : Flag<["-"], "fobjc-gc-only">, Group, Flags<[CC1Option]>, HelpText<"Use GC exclusively for Objective-C related memory management">; diff --git a/clang/lib/AST/Decl.cpp b/clang/lib/AST/Decl.cpp index e700cf8..3498772 100644 --- a/clang/lib/AST/Decl.cpp +++ b/clang/lib/AST/Decl.cpp @@ -2513,39 +2513,6 @@ bool FunctionDecl::isReplaceableGlobalAllocationFunction() const { return RD && isNamed(RD, "nothrow_t") && RD->isInStdNamespace(); } -FunctionDecl * -FunctionDecl::getCorrespondingUnsizedGlobalDeallocationFunction() const { - ASTContext &Ctx = getASTContext(); - if (!Ctx.getLangOpts().SizedDeallocation) - return nullptr; - - if (getDeclName().getNameKind() != DeclarationName::CXXOperatorName) - return nullptr; - if (getDeclName().getCXXOverloadedOperator() != OO_Delete && - getDeclName().getCXXOverloadedOperator() != OO_Array_Delete) - return nullptr; - if (isa(getDeclContext())) - return nullptr; - - if (!getDeclContext()->getRedeclContext()->isTranslationUnit()) - return nullptr; - - if (getNumParams() != 2 || isVariadic() || - !Ctx.hasSameType(getType()->castAs()->getParamType(1), - Ctx.getSizeType())) - return nullptr; - - // This is a sized deallocation function. Find the corresponding unsized - // deallocation function. - lookup_result R = getDeclContext()->lookup(getDeclName()); - for (lookup_result::iterator RI = R.begin(), RE = R.end(); RI != RE; - ++RI) - if (FunctionDecl *FD = dyn_cast(*RI)) - if (FD->getNumParams() == 1 && !FD->isVariadic()) - return FD; - return nullptr; -} - LanguageLinkage FunctionDecl::getLanguageLinkage() const { return getDeclLanguageLinkage(*this); } diff --git a/clang/lib/CodeGen/CodeGenFunction.cpp b/clang/lib/CodeGen/CodeGenFunction.cpp index dabec15..9e80f0a 100644 --- a/clang/lib/CodeGen/CodeGenFunction.cpp +++ b/clang/lib/CodeGen/CodeGenFunction.cpp @@ -802,20 +802,6 @@ static void TryMarkNoThrow(llvm::Function *F) { F->setDoesNotThrow(); } -static void EmitSizedDeallocationFunction(CodeGenFunction &CGF, - const FunctionDecl *UnsizedDealloc) { - // This is a weak discardable definition of the sized deallocation function. - CGF.CurFn->setLinkage(llvm::Function::LinkOnceAnyLinkage); - if (CGF.CGM.supportsCOMDAT()) - CGF.CurFn->setComdat( - CGF.CGM.getModule().getOrInsertComdat(CGF.CurFn->getName())); - - // Call the unsized deallocation function and forward the first argument - // unchanged. - llvm::Constant *Unsized = CGF.CGM.GetAddrOfFunction(UnsizedDealloc); - CGF.Builder.CreateCall(Unsized, &*CGF.CurFn->arg_begin()); -} - void CodeGenFunction::GenerateCode(GlobalDecl GD, llvm::Function *Fn, const CGFunctionInfo &FnInfo) { const FunctionDecl *FD = cast(GD.getDecl()); @@ -891,14 +877,6 @@ void CodeGenFunction::GenerateCode(GlobalDecl GD, llvm::Function *Fn, emitImplicitAssignmentOperatorBody(Args); } else if (Stmt *Body = FD->getBody()) { EmitFunctionBody(Args, Body); - } else if (FunctionDecl *UnsizedDealloc = - FD->getCorrespondingUnsizedGlobalDeallocationFunction()) { - // Global sized deallocation functions get an implicit weak definition if - // they don't have an explicit definition, if allowed. - assert(getLangOpts().DefineSizedDeallocation && - "Can't emit unallowed definition."); - EmitSizedDeallocationFunction(*this, UnsizedDealloc); - } else llvm_unreachable("no definition for emitted function"); diff --git a/clang/lib/CodeGen/CodeGenModule.cpp b/clang/lib/CodeGen/CodeGenModule.cpp index d1da069..f4ae684 100644 --- a/clang/lib/CodeGen/CodeGenModule.cpp +++ b/clang/lib/CodeGen/CodeGenModule.cpp @@ -1620,16 +1620,6 @@ CodeGenModule::GetOrCreateLLVMFunction(StringRef MangledName, // don't need it anymore). addDeferredDeclToEmit(F, DDI->second); DeferredDecls.erase(DDI); - - // Otherwise, if this is a sized deallocation function, emit a weak - // definition for it at the end of the translation unit (if allowed), - // unless the sized deallocation function is aliased. - } else if (D && - cast(D) - ->getCorrespondingUnsizedGlobalDeallocationFunction() && - getLangOpts().DefineSizedDeallocation && - !D->hasAttr()) { - addDeferredDeclToEmit(F, GD); // Otherwise, there are cases we have to worry about where we're // using a declaration for which we must emit a definition but where diff --git a/clang/lib/Driver/Tools.cpp b/clang/lib/Driver/Tools.cpp index 4ec8cae..94c71ac 100644 --- a/clang/lib/Driver/Tools.cpp +++ b/clang/lib/Driver/Tools.cpp @@ -4250,6 +4250,12 @@ void Clang::ConstructJob(Compilation &C, const JobAction &JA, options::OPT_fno_assume_sane_operator_new)) CmdArgs.push_back("-fno-assume-sane-operator-new"); + // -fsized-deallocation is off by default, as it is an ABI-breaking change for + // most platforms. + if (Args.hasFlag(options::OPT_fsized_deallocation, + options::OPT_fno_sized_deallocation, false)) + CmdArgs.push_back("-fsized-deallocation"); + // -fconstant-cfstrings is default, and may be subject to argument translation // on Darwin. if (!Args.hasFlag(options::OPT_fconstant_cfstrings, diff --git a/clang/lib/Frontend/CompilerInvocation.cpp b/clang/lib/Frontend/CompilerInvocation.cpp index b9869fd..42de57e 100644 --- a/clang/lib/Frontend/CompilerInvocation.cpp +++ b/clang/lib/Frontend/CompilerInvocation.cpp @@ -1262,9 +1262,6 @@ void CompilerInvocation::setLangDefaults(LangOptions &Opts, InputKind IK, Opts.CXXOperatorNames = Opts.CPlusPlus; Opts.DollarIdents = !Opts.AsmPreprocessor; - - // C++14 onwards has sized global deallocation functions. - Opts.SizedDeallocation = Opts.CPlusPlus14; } /// Attempt to parse a visibility value out of the given argument. @@ -1543,10 +1540,7 @@ static void ParseLangArgs(LangOptions &Opts, ArgList &Args, InputKind IK, Opts.NoBuiltin = Args.hasArg(OPT_fno_builtin) || Opts.Freestanding; Opts.NoMathBuiltin = Args.hasArg(OPT_fno_math_builtin); Opts.AssumeSaneOperatorNew = !Args.hasArg(OPT_fno_assume_sane_operator_new); - Opts.SizedDeallocation |= Args.hasArg(OPT_fsized_deallocation); - Opts.SizedDeallocation &= !Args.hasArg(OPT_fno_sized_deallocation); - Opts.DefineSizedDeallocation = Opts.SizedDeallocation && - Args.hasArg(OPT_fdefine_sized_deallocation); + Opts.SizedDeallocation = Args.hasArg(OPT_fsized_deallocation); Opts.HeinousExtensions = Args.hasArg(OPT_fheinous_gnu_extensions); Opts.AccessControl = !Args.hasArg(OPT_fno_access_control); Opts.ElideConstructors = !Args.hasArg(OPT_fno_elide_constructors); diff --git a/clang/lib/Sema/SemaExprCXX.cpp b/clang/lib/Sema/SemaExprCXX.cpp index 97ee7bd..bdd92c0 100644 --- a/clang/lib/Sema/SemaExprCXX.cpp +++ b/clang/lib/Sema/SemaExprCXX.cpp @@ -2168,15 +2168,6 @@ void Sema::DeclareGlobalAllocationFunction(DeclarationName Name, } } } - - // If the function is sized operator delete and has not already been - // declared, and weak definitions have been disabled, do not declare - // it implicitly. Instead, let deallocation function lookup pick up - // unsized delete. - // FIXME: We should remove this guard once backward compatibility is - // no longer an issue - if (NumParams == 2 && !getLangOpts().DefineSizedDeallocation) - return; FunctionProtoType::ExtProtoInfo EPI; diff --git a/clang/test/CXX/drs/dr412.cpp b/clang/test/CXX/drs/dr412.cpp index 39cdd61..27bc7e5 100644 --- a/clang/test/CXX/drs/dr412.cpp +++ b/clang/test/CXX/drs/dr412.cpp @@ -15,7 +15,7 @@ inline void* operator new(size_t) BAD_ALLOC; // expected-error {{cannot be decla inline void* operator new[](size_t) BAD_ALLOC; // expected-error {{cannot be declared 'inline'}} inline void operator delete(void*) NOEXCEPT; // expected-error {{cannot be declared 'inline'}} inline void operator delete[](void*) NOEXCEPT; // expected-error {{cannot be declared 'inline'}} -#if __cplusplus >= 201402L +#ifdef __cpp_sized_deallocation inline void operator delete(void*, size_t) NOEXCEPT; // expected-error {{cannot be declared 'inline'}} inline void operator delete[](void*, size_t) NOEXCEPT; // expected-error {{cannot be declared 'inline'}} #endif diff --git a/clang/test/CodeGenCXX/cxx1y-sized-deallocation.cpp b/clang/test/CodeGenCXX/cxx1y-sized-deallocation.cpp index 1d021a7..78cc713 100644 --- a/clang/test/CodeGenCXX/cxx1y-sized-deallocation.cpp +++ b/clang/test/CodeGenCXX/cxx1y-sized-deallocation.cpp @@ -1,22 +1,18 @@ -// RUN: %clang_cc1 -std=c++1y %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s --check-prefix=CHECK-UNSIZED -// RUN: %clang_cc1 -std=c++1y %s -emit-llvm -triple x86_64-linux-gnu -o - -DINLIB | FileCheck %s --check-prefix=CHECK --check-prefix=CHECKUND -// RUN: %clang_cc1 -std=c++1y %s -emit-llvm -triple x86_64-linux-gnu -fdefine-sized-deallocation -o - | FileCheck %s --check-prefix=CHECK --check-prefix=CHECKDEF -// RUN: %clang_cc1 -std=c++11 -fsized-deallocation %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s --check-prefix=CHECK-UNSIZED -// RUN: %clang_cc1 -std=c++11 -fsized-deallocation %s -emit-llvm -triple x86_64-linux-gnu -o - -DINLIB | FileCheck %s --check-prefix=CHECK --check-prefix=CHECKUND -// RUN: %clang_cc1 -std=c++11 -fsized-deallocation -fdefine-sized-deallocation %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s --check-prefix=CHECK --check-prefix=CHECKDEF +// Check that delete exprs call the sized deallocation function if +// -fsized-deallocation is passed in both C++11 and C++14. +// RUN: %clang_cc1 -std=c++11 -fsized-deallocation %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s +// RUN: %clang_cc1 -std=c++14 -fsized-deallocation %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s + +// Check that we don't used sized deallocation without -fsized-deallocation and +// C++14. // RUN: %clang_cc1 -std=c++11 %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s --check-prefix=CHECK-UNSIZED -// RUN: %clang_cc1 -std=c++1y %s -emit-llvm -triple x86_64-linux-gnu -fno-sized-deallocation -o - | FileCheck %s --check-prefix=CHECK-UNSIZED +// RUN: %clang_cc1 -std=c++14 %s -emit-llvm -triple x86_64-linux-gnu -o - | FileCheck %s --check-prefix=CHECK-UNSIZED // CHECK-UNSIZED-NOT: _ZdlPvm // CHECK-UNSIZED-NOT: _ZdaPvm typedef decltype(sizeof(0)) size_t; -#ifdef INLIB -void operator delete(void *, size_t) noexcept; -void operator delete[](void *, size_t) noexcept; -#endif - typedef int A; struct B { int n; }; struct C { ~C() {} }; @@ -60,9 +56,7 @@ D::D() {} // CHECK: call void @_ZdlPvm(i8* %{{[^ ]*}}, i64 4) // CHECK: call void @_ZdaPv(i8* %{{[^ ]*}}) -// CHECKDEF-LABEL: define linkonce void @_ZdlPvm(i8*, i64) #{{[0-9]+}} comdat -// CHECKDEF: call void @_ZdlPv(i8* %0) -// CHECKUND-LABEL: declare void @_ZdlPvm(i8* +// CHECK-LABEL: declare void @_ZdlPvm(i8* // CHECK-LABEL: define weak_odr void @_Z3delI1BEvv() // CHECK: call void @_ZdlPvm(i8* %{{[^ ]*}}, i64 4) @@ -82,9 +76,7 @@ D::D() {} // CHECK: add i64 %{{[^ ]*}}, 8 // CHECK: call void @_ZdaPvm(i8* %{{[^ ]*}}, i64 %{{[^ ]*}}) -// CHECKDEF-LABEL: define linkonce void @_ZdaPvm(i8*, i64) #{{[0-9]+}} comdat -// CHECKDEF: call void @_ZdaPv(i8* %0) -// CHECKUND-LABEL: declare void @_ZdaPvm(i8* +// CHECK-LABEL: declare void @_ZdaPvm(i8* // CHECK-LABEL: define weak_odr void @_Z3delI1DEvv() // CHECK: call void @_ZdlPvm(i8* %{{[^ ]*}}, i64 8) diff --git a/clang/test/CodeGenCXX/implicit-allocation-functions.cpp b/clang/test/CodeGenCXX/implicit-allocation-functions.cpp deleted file mode 100644 index d4e9841..0000000 --- a/clang/test/CodeGenCXX/implicit-allocation-functions.cpp +++ /dev/null @@ -1,69 +0,0 @@ -// RUN: %clang_cc1 -emit-llvm -triple x86_64-unknown-unknown -o - -std=c++11 %s 2>&1 | FileCheck %s -check-prefix=CHECKDEF -check-prefix=CHECK11 -// RUN: %clang_cc1 -emit-llvm -triple x86_64-unknown-unknown -o - -std=c++11 -fvisibility hidden %s 2>&1 | FileCheck %s -check-prefix=CHECKHID -check-prefix=CHECK11 -// RUN: %clang_cc1 -emit-llvm -triple x86_64-unknown-unknown -o - -std=c++14 -DINLIB -fno-sized-deallocation %s 2>&1 | FileCheck %s -check-prefix=CHECKDEF -check-prefix=CHECK11 -// RUN: %clang_cc1 -emit-llvm -triple x86_64-unknown-unknown -o - -std=c++14 -DINLIB %s 2>&1 | FileCheck %s -check-prefix=CHECKDEF -check-prefix=CHECK14 -check-prefix=CHECK14UND -// RUN: %clang_cc1 -emit-llvm -triple x86_64-unknown-unknown -o - -std=c++14 -DINLIB -fvisibility hidden %s 2>&1 | FileCheck %s -check-prefix=CHECKHID -check-prefix=CHECK14 -check-prefix=CHECK14UND -// RUN: %clang_cc1 -emit-llvm -triple x86_64-unknown-unknown -o - -std=c++14 -DINLIB -fdefine-sized-deallocation %s 2>&1 | FileCheck %s -check-prefix=CHECKDEF -check-prefix=CHECK14 -check-prefix=CHECK14DEFCOMDAT -// RUN: %clang_cc1 -emit-llvm -triple x86_64-unknown-unknown -o - -std=c++14 -DINLIB -fdefine-sized-deallocation -fvisibility hidden %s 2>&1 | FileCheck %s -check-prefix=CHECKHID -check-prefix=CHECK14 -check-prefix=CHECK14DEFCOMDAT -// RUN: %clang_cc1 -emit-llvm -triple x86_64-apple-macosx -o - -std=c++14 -DINLIB -fdefine-sized-deallocation %s | FileCheck %s -check-prefix=CHECKDEF -check-prefix=CHECK14 -check-prefix=CHECK14DEFNOCOMDAT - -// PR22419: Implicit sized deallocation functions always have default visibility. -// Generalized to all implicit allocation functions. - -#ifdef INLIB -typedef decltype(sizeof(0)) size_t; -void operator delete(void *, size_t) noexcept; -void operator delete[](void *, size_t) noexcept; -#endif - -// CHECK14-DAG: %struct.A = type { i8 } -struct A { }; - -// CHECKDEF-DAG: define void @_Z3fooP1A(%struct.A* %is) -// CHECKHID-DAG: define hidden void @_Z3fooP1A(%struct.A* %is) -void foo(A* is) { - - // CHECK11-DAG: call noalias i8* @_Znwm(i64 1) - // CHECK14-DAG: call noalias i8* @_Znwm(i64 1) - is = new A(); - - // CHECK11-DAG: call void @_ZdlPv(i8* %{{.+}}) - // CHECK14-DAG: call void @_ZdlPvm(i8* %{{.+}}, i64 1) - delete is; -} - -// CHECK11-DAG: declare noalias i8* @_Znwm(i64) -// CHECK11-DAG: declare void @_ZdlPv(i8*) - -// CHECK14-DAG: declare noalias i8* @_Znwm(i64) -// CHECK14UND-DAG: declare void @_ZdlPvm(i8*, i64) -// CHECK14DEFCOMDAT-DAG: define linkonce void @_ZdlPvm(i8*, i64) #{{[0-9]+}} comdat { -// CHECK14DEFCOMDAT-DAG: declare void @_ZdlPv(i8*) -// CHECK14DEFNOCOMDAT-DAG: define linkonce void @_ZdlPvm(i8*, i64) #{{[0-9]+}} { -// CHECK14DEFNOCOMDAT-DAG: declare void @_ZdlPv(i8*) - -// CHECK14-DAG: %struct.B = type { i8 } -struct B { ~B() { }}; - -// CHECKDEF-DAG: define void @_Z1fP1B(%struct.B* %p) -// CHECKHID-DAG: define hidden void @_Z1fP1B(%struct.B* %p) -void f(B *p) { - - // CHECK11-DAG: call noalias i8* @_Znam(i64 13) - // CHECK14-DAG: call noalias i8* @_Znam(i64 13) - p = new B[5]; - - // CHECK11-DAG: call void @_ZdaPv(i8* %{{.+}}) - // CHECK14-DAG: call void @_ZdaPvm(i8* %{{.+}}, i64 %{{.+}}) - delete[] p; -} - -// CHECK11-DAG: declare noalias i8* @_Znam(i64) -// CHECK11-DAG: declare void @_ZdaPv(i8*) - -// CHECK14-DAG: declare noalias i8* @_Znam(i64) -// CHECK14UND-DAG: declare void @_ZdaPvm(i8*, i64) -// CHECK14DEF-DAG: define linkonce void @_ZdaPvm(i8*, i64) #{{[0-9]+}} comdat { -// CHECK14DEF-DAG: declare void @_ZdaPv(i8*) -// CHECK14DEFNOCOMDAT-DAG: define linkonce void @_ZdaPvm(i8*, i64) #{{[0-9]+}} { -// CHECK14DEFNOCOMDAT-DAG: declare void @_ZdaPv(i8*) diff --git a/clang/test/CodeGenCXX/pr21754.cpp b/clang/test/CodeGenCXX/pr21754.cpp deleted file mode 100644 index 65ee765..0000000 --- a/clang/test/CodeGenCXX/pr21754.cpp +++ /dev/null @@ -1,11 +0,0 @@ -// RUN: %clang -cc1 -emit-llvm -triple x86_64-unknown-unknown -std=c++1y -o - %s 2>&1 | FileCheck %s -// RUN: %clang -cc1 -emit-llvm -triple x86_64-unknown-unknown -std=c++1y -fdefine-sized-deallocation -o - %s 2>&1 | FileCheck %s -// RUN: %clang -cc1 -emit-llvm -triple x86_64-unknown-unknown -std=c++1y -fno-sized-deallocation -o - %s 2>&1 | FileCheck %s -// RUN: %clang -cc1 -emit-llvm -triple x86_64-unknown-unknown -std=c++11 -fsized-deallocation -o - %s 2>&1 | FileCheck %s -// RUN: %clang -cc1 -emit-llvm -triple x86_64-unknown-unknown -std=c++11 -fsized-deallocation -fdefine-sized-deallocation -o - %s 2>&1 | FileCheck %s -// RUN: %clang -cc1 -emit-llvm -triple x86_64-unknown-unknown -std=c++11 -o - %s 2>&1 | FileCheck %s - -void operator delete(void*, unsigned long) throw() __attribute__((alias("foo"))); -extern "C" void foo(void*, unsigned long) {} - -// CHECK-DAG: @_ZdlPvm = alias void (i8*, i64)* @foo diff --git a/clang/test/Lexer/cxx-features.cpp b/clang/test/Lexer/cxx-features.cpp index 670a105..d06090e 100644 --- a/clang/test/Lexer/cxx-features.cpp +++ b/clang/test/Lexer/cxx-features.cpp @@ -1,6 +1,6 @@ // RUN: %clang_cc1 -std=c++98 -verify %s // RUN: %clang_cc1 -std=c++11 -verify %s -// RUN: %clang_cc1 -std=c++1y -verify %s +// RUN: %clang_cc1 -std=c++1y -fsized-deallocation -verify %s // expected-no-diagnostics diff --git a/clang/www/cxx_status.html b/clang/www/cxx_status.html index 4c767d1..5b53cba 100644 --- a/clang/www/cxx_status.html +++ b/clang/www/cxx_status.html @@ -504,14 +504,14 @@ Clang version in which each feature became available.

Clang 3.4 (6) +

-(6): In Clang SVN, using sized deallocation in C++14 mode requires linking either -libc++ 3.7 or later, or libstdc++ 5 or later. Alternatively, you can use the --Xclang -fdefine-sized-deallocation compiler option to enable the implementation from -Clang 3.4 through Clang 3.6, where weak definitions of sized deallocation functions are implicitly -generated (by the compiler). You can also use the -Xclang -fno-sized-deallocation option -to disable sized deallocation. Note that both of these flags are temporary provisions and may go away -soon. +(6): In Clang 3.7 and later, sized deallocation is only enabled +if the user passes the -fsized-deallocation flag. The user must +supply definitions of the sized deallocation functions, either by providing them +explicitly or by using a C++ standard library that does. libstdc++ +added these functions in version 5.0, and libc++ added them in +version 3.7.