From 9092c3e0fa01f3139b016d05d267a89e3b07747a Mon Sep 17 00:00:00 2001 From: rdivacky Date: Wed, 14 Oct 2009 18:03:49 +0000 Subject: Update clang to r84119. --- test/Analysis/CFDateGC.m | 8 +- test/Analysis/CheckNSError.m | 4 +- test/Analysis/NSPanel.m | 2 +- test/Analysis/NSString.m | 15 +- test/Analysis/PR2978.m | 1 + test/Analysis/PR3991.m | 1 + test/Analysis/array-struct.c | 6 +- test/Analysis/casts.c | 19 +- test/Analysis/cfref_rdar6080742.c | 18 +- test/Analysis/complex.c | 2 +- test/Analysis/dead-stores.c | 171 +++- test/Analysis/dead-stores.cpp | 19 + test/Analysis/exercise-ps.c | 2 +- test/Analysis/misc-ps-basic-store.m | 14 + test/Analysis/misc-ps-region-store-i386.m | 14 + test/Analysis/misc-ps-region-store-x86_64.m | 14 + test/Analysis/misc-ps-region-store.m | 243 ++++- test/Analysis/misc-ps.m | 410 +++++++- ...il-receiver-undefined-larger-than-voidptr-ret.m | 3 +- test/Analysis/no-outofbounds.c | 12 + test/Analysis/null-deref-ps.c | 39 +- test/Analysis/outofbound.c | 1 + test/Analysis/pr4209.m | 3 +- test/Analysis/rdar-6442306-1.m | 1 + test/Analysis/rdar-6540084.m | 1 + test/Analysis/rdar-6541136-region.c | 7 +- test/Analysis/rdar-6562655.m | 6 +- ...dar-6600344-nil-receiver-undefined-struct-ret.m | 3 +- test/Analysis/rdar-7168531.m | 19 + test/Analysis/region-1.m | 1 + test/Analysis/region-only-test.c | 2 +- test/Analysis/retain-release-gc-only.m | 186 +++- test/Analysis/retain-release-region-store.m | 24 + test/Analysis/retain-release.m | 439 ++++++++- test/Analysis/security-syntax-checks.m | 91 ++ test/Analysis/uninit-vals-ps-region.c | 18 + test/Analysis/uninit-vals-ps.c | 50 +- test/Analysis/uninit-vals.c | 2 +- test/Analysis/unions-region.m | 41 + test/Analysis/unused-ivars.m | 45 +- test/CMakeLists.txt | 73 +- .../basic.lookup.argdep/p2-template-id.cpp | 27 + .../basic/basic.lookup/basic.lookup.argdep/p2.cpp | 73 ++ .../basic/basic.lookup/basic.lookup.argdep/p4.cpp | 42 + .../basic.lookup/basic.lookup.elab/templateid.cpp | 18 + .../basic.lookup.qual/namespace.qual/p2.cpp | 65 ++ .../basic.lookup.qual/namespace.qual/p3.cpp | 41 + .../basic.lookup.qual/namespace.qual/p4.cpp | 25 + .../basic.lookup.qual/namespace.qual/p5.cpp | 35 + .../basic/basic.lookup/basic.lookup.unqual/p3.cpp | 4 +- .../CXX/basic/basic.start/basic.start.main/p2a.cpp | 8 + .../CXX/basic/basic.start/basic.start.main/p2b.cpp | 8 + .../CXX/basic/basic.start/basic.start.main/p2c.cpp | 4 + .../CXX/basic/basic.start/basic.start.main/p2d.cpp | 4 + .../CXX/basic/basic.start/basic.start.main/p2e.cpp | 4 + .../CXX/basic/basic.start/basic.start.main/p2f.cpp | 7 + .../CXX/basic/basic.start/basic.start.main/p2g.cpp | 4 + .../basic/basic.stc/basic.stc.dynamic/p2-nodef.cpp | 7 + test/CXX/basic/basic.stc/basic.stc.dynamic/p2.cpp | 25 + test/CXX/class.derived/class.virtual/p12.cpp | 19 + test/CXX/class/class.friend/p1-ambiguous.cpp | 37 + test/CXX/class/class.friend/p1.cpp | 76 ++ test/CXX/class/class.friend/p2.cpp | 10 + test/CXX/class/class.friend/p6.cpp | 10 + test/CXX/class/class.local/p3.cpp | 2 +- test/CXX/class/class.local/p4.cpp | 2 +- test/CXX/class/class.nest/p1.cpp | 14 + test/CXX/class/class.nested.type/p1.cpp | 4 +- test/CXX/class/class.union/p1.cpp | 105 ++ .../namespace.def/namespace.memdef/p3.cpp | 15 + .../basic.namespace/namespace.udecl/p3-cxx0x.cpp | 20 + .../basic.namespace/namespace.udecl/p5-cxx0x.cpp | 12 + .../basic.namespace/namespace.udecl/p6-cxx0x.cpp | 8 + .../basic.namespace/namespace.udecl/p8-cxx0x.cpp | 15 + test/CXX/dcl.dcl/dcl.spec/dcl.stc/p9.cpp | 4 +- .../dcl.dcl/dcl.spec/dcl.type/dcl.spec.auto/p3.cpp | 10 + .../dcl.dcl/dcl.spec/dcl.type/dcl.spec.auto/p5.cpp | 13 + .../dcl.dcl/dcl.spec/dcl.type/dcl.type.elab/p3.cpp | 60 ++ .../dcl.decl/dcl.meaning/dcl.fct.default/p10.cpp | 16 + .../dcl.decl/dcl.meaning/dcl.fct.default/p2.cpp | 9 + .../dcl.decl/dcl.meaning/dcl.fct.default/p3.cpp | 13 + .../dcl.decl/dcl.meaning/dcl.fct.default/p4.cpp | 55 ++ .../dcl.decl/dcl.meaning/dcl.fct.default/p5.cpp | 18 + .../dcl.decl/dcl.meaning/dcl.fct.default/p6.cpp | 32 + .../dcl.decl/dcl.meaning/dcl.fct.default/p7.cpp | 7 + .../dcl.decl/dcl.meaning/dcl.fct.default/p8.cpp | 4 + test/CXX/dcl.decl/dcl.meaning/dcl.fct/p3.cpp | 3 + test/CXX/dcl.decl/dcl.meaning/dcl.mptr/p3.cpp | 26 + test/CXX/expr/p3.cpp | 15 + test/CXX/expr/p8.cpp | 18 + test/CXX/expr/p9.cpp | 50 + test/CXX/lex/lex.trigraph/p1.cpp | 19 + test/CXX/lex/lex.trigraph/p2.cpp | 3 + test/CXX/lex/lex.trigraph/p3.cpp | 8 + test/CXX/over/over.match/over.match.best/p1.cpp | 16 + test/CXX/over/over.over/p1.cpp | 94 ++ test/CXX/over/over.over/p2.cpp | 10 + test/CXX/over/over.over/p4.cpp | 23 + test/CXX/temp/temp.decls/temp.class.spec/p6.cpp | 20 + .../temp.class.spec/temp.class.order/p2.cpp | 16 + .../temp.class.spec.mfunc/p1-neg.cpp | 25 + .../temp.class.spec/temp.class.spec.mfunc/p1.cpp | 26 + .../temp.decls/temp.class/temp.mem.class/p1.cpp | 27 + .../temp.class/temp.mem.func/p1-retmem.cpp | 28 + .../temp.decls/temp.class/temp.mem.func/p1.cpp | 68 ++ .../temp.decls/temp.class/temp.mem.func/p1inst.cpp | 17 + .../temp.decls/temp.class/temp.mem.func/pr5056.cpp | 17 + .../temp.decls/temp.class/temp.static/p1-inst.cpp | 28 + .../temp/temp.decls/temp.class/temp.static/p1.cpp | 26 + .../temp.decls/temp.fct/temp.func.order/p4.cpp | 23 + .../temp.decls/temp.fct/temp.func.order/p5.cpp | 12 + .../temp.decls/temp.fct/temp.over.link/p4-neg.cpp | 6 +- .../temp/temp.decls/temp.fct/temp.over.link/p6.cpp | 16 + test/CXX/temp/temp.decls/temp.friend/p1.cpp | 56 ++ test/CXX/temp/temp.decls/temp.friend/p3.cpp | 13 + test/CXX/temp/temp.decls/temp.friend/p5.cpp | 11 + test/CXX/temp/temp.decls/temp.mem/p1.cpp | 16 + .../temp/temp.fct.spec/temp.arg.explicit/p3.cpp | 2 +- .../temp.deduct/temp.deduct.call/p3.cpp | 32 +- .../temp.deduct/temp.deduct.conv/p2.cpp | 36 + .../temp.deduct/temp.deduct.conv/p3.cpp | 30 + .../temp.deduct/temp.deduct.conv/p4.cpp | 44 + .../temp.deduct/temp.deduct.funcaddr/p1.cpp | 22 + .../temp.deduct/temp.deduct.partial/p11.cpp | 22 + test/CXX/temp/temp.param/p1.cpp | 3 + test/CXX/temp/temp.res/temp.dep/p3.cpp | 43 + test/CXX/temp/temp.spec/temp.expl.spec/p1.cpp | 99 ++ test/CXX/temp/temp.spec/temp.expl.spec/p10.cpp | 7 + test/CXX/temp/temp.spec/temp.expl.spec/p11.cpp | 8 + test/CXX/temp/temp.spec/temp.expl.spec/p13.cpp | 6 + test/CXX/temp/temp.spec/temp.expl.spec/p14.cpp | 42 + test/CXX/temp/temp.spec/temp.expl.spec/p15.cpp | 22 + test/CXX/temp/temp.spec/temp.expl.spec/p16.cpp | 26 + test/CXX/temp/temp.spec/temp.expl.spec/p17.cpp | 12 + test/CXX/temp/temp.spec/temp.expl.spec/p18.cpp | 20 + test/CXX/temp/temp.spec/temp.expl.spec/p19.cpp | 30 + test/CXX/temp/temp.spec/temp.expl.spec/p2.cpp | 239 +++++ test/CXX/temp/temp.spec/temp.expl.spec/p20.cpp | 14 + test/CXX/temp/temp.spec/temp.expl.spec/p21.cpp | 30 + test/CXX/temp/temp.spec/temp.expl.spec/p3.cpp | 14 + test/CXX/temp/temp.spec/temp.expl.spec/p4.cpp | 59 ++ test/CXX/temp/temp.spec/temp.expl.spec/p5.cpp | 61 ++ test/CXX/temp/temp.spec/temp.expl.spec/p6.cpp | 56 ++ test/CXX/temp/temp.spec/temp.expl.spec/p9.cpp | 14 + test/CodeCompletion/call.cpp | 28 + test/CodeCompletion/enum-switch-case-qualified.cpp | 33 + test/CodeCompletion/enum-switch-case.c | 29 + test/CodeCompletion/enum-switch-case.cpp | 29 + test/CodeCompletion/function-templates.cpp | 15 + test/CodeCompletion/functions.cpp | 9 + test/CodeCompletion/member-access.c | 13 + test/CodeCompletion/member-access.cpp | 43 + test/CodeCompletion/namespace-alias.cpp | 21 + test/CodeCompletion/namespace.cpp | 15 + test/CodeCompletion/nested-name-specifier.cpp | 18 + test/CodeCompletion/operator.cpp | 18 + test/CodeCompletion/ordinary-name.c | 12 + test/CodeCompletion/property.m | 29 + test/CodeCompletion/tag.c | 13 + test/CodeCompletion/tag.cpp | 26 + test/CodeCompletion/templates.cpp | 17 + test/CodeCompletion/truncation.c | 12 + test/CodeCompletion/truncation.c.h | 5 + test/CodeCompletion/using-namespace.cpp | 21 + test/CodeCompletion/using.cpp | 25 + test/CodeGen/2008-07-17-no-emit-on-error.c | 4 +- ...2008-07-22-bitfield-init-after-zero-len-array.c | 5 +- test/CodeGen/2008-07-29-override-alias-decl.c | 2 +- test/CodeGen/2009-01-21-invalid-debug-info.m | 2 +- test/CodeGen/2009-04-23-dbg.c | 2 +- test/CodeGen/2009-06-01-addrofknr.c | 12 +- test/CodeGen/2009-07-31-DbgDeclare.c | 5 + test/CodeGen/2009-08-14-vararray-crash.c | 11 + test/CodeGen/PR3613-static-decl.c | 2 +- test/CodeGen/PR4611-bitfield-layout.c | 6 + test/CodeGen/PR5060-align.c | 13 + test/CodeGen/address-space-compound-literal.c | 5 + test/CodeGen/address-space-field1.c | 39 + test/CodeGen/address-space-field2.c | 50 + test/CodeGen/address-space-field3.c | 46 + test/CodeGen/address-space-field4.c | 61 ++ test/CodeGen/arm-arguments.c | 94 ++ test/CodeGen/arm_asm_clobber.c | 21 + test/CodeGen/array.c | 4 +- test/CodeGen/asm-inout.c | 18 + test/CodeGen/asm.c | 13 +- test/CodeGen/attr-cleanup.c | 2 +- test/CodeGen/attributes.c | 100 +- test/CodeGen/blocks-2.c | 3 +- test/CodeGen/blocks-aligned-byref-variable.c | 19 + test/CodeGen/blocks-seq.c | 20 +- test/CodeGen/boolassign.c | 5 +- test/CodeGen/builtin-attributes.c | 12 + test/CodeGen/builtins-ffs_parity_popcount.c | 4 +- test/CodeGen/builtins-powi.c | 4 +- test/CodeGen/builtins.c | 2 + test/CodeGen/cast-to-union.c | 8 +- test/CodeGen/conditional.c | 21 +- test/CodeGen/const-init.c | 61 +- test/CodeGen/darwin-string-literals.c | 16 +- test/CodeGen/debug-info.c | 6 +- test/CodeGen/designated-initializers.c | 5 +- test/CodeGen/exprs.c | 8 +- test/CodeGen/ext-vector-shuffle.c | 4 +- test/CodeGen/ext-vector.c | 19 +- test/CodeGen/function-attributes.c | 2 +- test/CodeGen/functions.c | 5 +- test/CodeGen/global-decls.c | 2 +- test/CodeGen/global-init.c | 25 +- test/CodeGen/global-with-initialiser.c | 6 +- test/CodeGen/globalinit.c | 2 +- test/CodeGen/init-with-member-expr.c | 2 +- test/CodeGen/inline.c | 16 +- test/CodeGen/inline2.c | 62 ++ test/CodeGen/packed-union.c | 16 + test/CodeGen/parameter-passing.c | 2 +- test/CodeGen/pragma-pack-1.c | 7 + test/CodeGen/pragma-pack-2.c | 23 + test/CodeGen/pragma-pack-3.c | 19 + test/CodeGen/pragma-weak.c | 165 ++++ test/CodeGen/predefined-expr.c | 45 + test/CodeGen/regparm.c | 5 +- test/CodeGen/stack-protector.c | 3 +- test/CodeGen/statements.c | 22 + test/CodeGen/staticinit.c | 6 +- test/CodeGen/stdcall-fastcall.c | 2 +- test/CodeGen/string-init.c | 2 +- test/CodeGen/struct-init.c | 4 +- test/CodeGen/struct-x86-darwin.c | 20 +- test/CodeGen/struct.c | 43 +- test/CodeGen/union-init.c | 28 +- test/CodeGen/union-init2.c | 4 + test/CodeGen/unreachable.c | 37 + test/CodeGen/unwind-attr.c | 1 + test/CodeGen/vector.c | 10 +- test/CodeGen/visibility.c | 2 +- test/CodeGen/volatile.c | 2 +- test/CodeGen/x86.c | 2 +- test/CodeGen/x86_32-arguments.c | 127 ++- test/CodeGen/x86_64-arguments.c | 28 +- test/CodeGenCXX/PR4827-cast.cpp | 5 + test/CodeGenCXX/PR4890-debug-info-dtor.cpp | 6 + test/CodeGenCXX/PR4983-constructor-conversion.cpp | 16 + test/CodeGenCXX/PR5050-constructor-conversion.cpp | 19 + test/CodeGenCXX/PR5093-static-member-function.cpp | 9 + test/CodeGenCXX/anonymous-namespaces.cpp | 22 + .../anonymous-union-member-initializer.cpp | 12 + test/CodeGenCXX/array-pointer-decay.cpp | 7 + test/CodeGenCXX/attr.cpp | 36 + test/CodeGenCXX/cast-conversion.cpp | 33 + test/CodeGenCXX/class-layout.cpp | 5 + test/CodeGenCXX/conditional-expr-lvalue.cpp | 7 + test/CodeGenCXX/constructor-conversion.cpp | 55 ++ test/CodeGenCXX/constructor-default-arg.cpp | 40 + test/CodeGenCXX/constructor-for-array-members.cpp | 44 + test/CodeGenCXX/constructor-init-reference.cpp | 9 + test/CodeGenCXX/constructor-init.cpp | 61 ++ test/CodeGenCXX/constructor-template.cpp | 56 ++ test/CodeGenCXX/conversion-function.cpp | 115 +++ test/CodeGenCXX/convert-to-fptr.cpp | 47 + test/CodeGenCXX/copy-assign-synthesis-1.cpp | 109 +++ test/CodeGenCXX/copy-assign-synthesis.cpp | 79 ++ test/CodeGenCXX/copy-constructor-elim.cpp | 43 + test/CodeGenCXX/copy-constructor-synthesis.cpp | 110 +++ test/CodeGenCXX/decl-ref-init.cpp | 31 + test/CodeGenCXX/default-arg-temps.cpp | 14 +- .../CodeGenCXX/default-constructor-for-members.cpp | 24 + test/CodeGenCXX/default-destructor-synthesis.cpp | 60 ++ test/CodeGenCXX/delete.cpp | 37 + test/CodeGenCXX/derived-to-base.cpp | 16 + test/CodeGenCXX/destructor-calls.cpp | 41 + test/CodeGenCXX/destructors.cpp | 30 + .../devirtualize-virtual-function-calls.cpp | 47 + test/CodeGenCXX/explicit-instantiation.cpp | 13 +- .../function-template-specialization.cpp | 15 +- test/CodeGenCXX/global-init.cpp | 16 + test/CodeGenCXX/mangle-extreme.cpp | 47 + test/CodeGenCXX/mangle-subst-std.cpp | 39 + test/CodeGenCXX/mangle-subst.cpp | 56 ++ test/CodeGenCXX/mangle.cpp | 190 +++- test/CodeGenCXX/member-function-pointers.cpp | 73 ++ test/CodeGenCXX/member-functions.cpp | 2 +- test/CodeGenCXX/member-pointers-zero-init.cpp | 34 + test/CodeGenCXX/namespace-aliases.cpp | 3 + test/CodeGenCXX/nested-base-member-access.cpp | 52 + test/CodeGenCXX/new.cpp | 23 +- test/CodeGenCXX/nullptr.cpp | 7 + test/CodeGenCXX/overload-binop-implicitconvert.cpp | 22 + test/CodeGenCXX/predefined-expr-sizeof.cpp | 30 + test/CodeGenCXX/predefined-expr.cpp | 226 +++++ test/CodeGenCXX/references.cpp | 13 + test/CodeGenCXX/reinterpret-cast.cpp | 12 + test/CodeGenCXX/static-data-member.cpp | 8 + test/CodeGenCXX/static-init.cpp | 13 + test/CodeGenCXX/temp-1.cpp | 83 ++ ...template-anonymous-union-member-initializer.cpp | 10 + test/CodeGenCXX/trivial-constructor-init.cpp | 21 + test/CodeGenCXX/virt.cpp | 1024 ++++++++++++++++++++ test/CodeGenCXX/virtual-base-cast.cpp | 9 + test/CodeGenCXX/virtual-function-calls.cpp | 11 + test/CodeGenCXX/vtable-cast-crash.cpp | 21 + test/CodeGenCXX/x86_64-arguments.cpp | 10 + test/CodeGenObjC/PR4541.m | 19 + test/CodeGenObjC/PR4894-recursive-debug-crash.m | 40 + test/CodeGenObjC/constant-strings.m | 4 +- test/CodeGenObjC/debug-info-linkagename.m | 17 + test/CodeGenObjC/for-in.m | 44 + test/CodeGenObjC/ivar-layout-64-bitfields.m | 40 + test/CodeGenObjC/ivar-layout-no-optimize.m | 18 + test/CodeGenObjC/messages.m | 4 +- test/CodeGenObjC/objc-assign-ivar.m | 53 + test/CodeGenObjC/objc-gc-aggr-assign.m | 46 + test/CodeGenObjC/objc-read-weak-byref.m | 26 + test/CodeGenObjC/objc2-assign-global.m | 83 +- test/CodeGenObjC/objc2-ivar-assign.m | 41 + test/CodeGenObjC/objc2-new-gc-api-strongcast.m | 26 + test/CodeGenObjC/objc2-weak-assign.m | 4 + test/CodeGenObjC/objc2-weak-ivar-debug.m | 15 + test/CodeGenObjC/objc2-write-barrier-2.m | 80 ++ test/CodeGenObjC/objc2-write-barrier-3.m | 47 + test/CodeGenObjC/objc2-write-barrier-4.m | 28 + test/CodeGenObjC/objc2-write-barrier-5.m | 27 + test/CodeGenObjC/objc2-write-barrier.m | 114 +++ test/CodeGenObjC/object-incr-decr-1.m | 19 + test/CodeGenObjC/overloadable.m | 4 +- test/CodeGenObjC/predefined-expr.m | 90 ++ test/CodeGenObjC/property-agrr-getter.m | 23 +- test/CodeGenObjC/property-setter-attr.m | 2 +- test/CodeGenObjC/protocol-in-extended-class.m | 29 + test/CodeGenObjC/protocols-lazy.m | 4 +- test/CodeGenObjC/protocols.m | 50 + test/CodeGenObjC/variadic-sends.m | 41 + test/Coverage/targets.c | 27 +- test/Driver/arm-darwin-builtin.c | 14 + test/Driver/ast.c | 26 + test/Driver/bindings.c | 6 +- test/Driver/clang-translation.c | 8 +- test/Driver/darwin-arm.c | 4 + test/Driver/darwin-as.c | 10 + test/Driver/darwin-cc.c | 1 - test/Driver/darwin-ld.c | 7 +- test/Driver/default-toolchain.c | 6 +- test/Driver/dragonfly.c | 10 +- test/Driver/freebsd.c | 10 +- test/Driver/openbsd.c | 8 +- test/Driver/pth.c | 8 +- test/Driver/qa_override.c | 3 +- test/Driver/redzone.c | 6 +- test/Frontend/ast-codegen.c | 12 + test/Frontend/ast-main.c | 8 + test/Frontend/dependency-gen.c | 2 +- test/Frontend/stdin.c | 2 +- test/Index/c-index-api-test.m | 224 +++++ test/Index/comments.c | 30 +- test/Index/cxx-operator-overload.cpp | 28 + test/Index/find-decls.c | 25 + test/Index/find-defs.c | 18 + test/Index/find-refs.c | 47 + test/Index/foo.h | 8 + test/Index/multiple-redecls.c | 12 + test/Index/objc-decls.m | 16 + test/Index/objc-message.m | 38 + test/Index/objc.h | 11 + test/Index/resolve-loc.c | 39 +- test/Index/t1.c | 31 + test/Index/t1.m | 23 + test/Index/t2.c | 14 + test/Index/t2.m | 16 + test/Lexer/11-27-2007-FloatLiterals.c | 8 +- test/Lexer/comment-escape.c | 2 +- test/Lexer/dollar-idents.c | 2 +- test/Makefile | 32 +- test/Misc/diag-mapping2.c | 5 +- test/PCH/cxx-method.cpp | 7 + test/PCH/libroot/usr/include/reloc.h | 15 + test/PCH/libroot/usr/include/reloc2.h | 15 + test/PCH/method_pool.h | 3 +- test/PCH/objc_exprs.m | 5 +- test/PCH/pr4489.c | 22 +- test/PCH/reloc.c | 14 + test/Parser/CompoundStmtScope.c | 2 +- test/Parser/MicrosoftExtensions.c | 18 +- test/Parser/argument_redef.c | 2 +- test/Parser/bad-control.c | 4 +- test/Parser/cxx-ambig-paren-expr.cpp | 6 +- test/Parser/cxx-friend.cpp | 21 +- test/Parser/cxx-member-initializers.cpp | 10 + test/Parser/cxx-template-decl.cpp | 21 +- test/Parser/cxx-using-declaration.cpp | 92 +- test/Parser/declarators.c | 10 +- test/Parser/implicit-casts.c | 1 + test/Parser/objc-messaging-neg-1.m | 9 +- test/Parser/pointer_promotion.c | 3 +- test/Parser/pragma-weak.c | 2 +- test/Parser/recovery.c | 12 +- test/Parser/statements.c | 14 +- test/Parser/top-level-semi-cxx0x.cpp | 15 + test/Preprocessor/assembler-with-cpp.c | 2 +- test/Preprocessor/macro-multiline.c | 2 +- test/Preprocessor/macro_fn_comma_swallow.c | 2 +- test/Preprocessor/macro_paste_mscomment.c | 4 +- test/Preprocessor/non_fragile_feature.m | 8 + test/Preprocessor/non_fragile_feature1.m | 8 + test/Preprocessor/pushable-diagnostics.c | 17 + test/Rewriter/id-test-3.m | 2 +- test/Rewriter/method-encoding-1.m | 4 +- test/Rewriter/rewrite-foreach-4.m | 2 +- test/Rewriter/rewrite-foreach-5.m | 2 +- test/Sema/address_spaces.c | 16 +- test/Sema/align-arm-apcs.c | 4 + test/Sema/altivec-init.c | 16 + test/Sema/arg-scope-c99.c | 2 +- test/Sema/arg-scope.c | 2 +- test/Sema/array-constraint.c | 2 +- test/Sema/array-init.c | 23 +- test/Sema/attr-decl-after-definition.c | 19 + test/Sema/attr-deprecated.c | 2 +- test/Sema/attr-format_arg.c | 2 + test/Sema/attr-malloc.c | 25 + test/Sema/attr-noreturn.c | 10 +- test/Sema/attr-section.c | 10 + test/Sema/attr-weak.c | 4 +- test/Sema/bitfield-promote-int-16bit.c | 25 + test/Sema/bitfield-promote.c | 34 + test/Sema/bitfield.c | 2 +- test/Sema/block-args.c | 2 +- test/Sema/block-call.c | 52 +- test/Sema/block-literal.c | 82 +- test/Sema/block-misc.c | 39 +- test/Sema/block-printf-attribute-1.c | 17 +- test/Sema/block-return-1.c | 6 + test/Sema/block-return-2.c | 5 + test/Sema/block-return-3.c | 5 + test/Sema/block-return.c | 6 +- test/Sema/block-sentinel-attribute.c | 25 +- test/Sema/builtin-prefetch.c | 2 +- test/Sema/builtin-unary-fp.c | 12 + test/Sema/builtins.c | 32 +- test/Sema/c89-2.c | 6 +- test/Sema/c89.c | 4 +- test/Sema/compare.c | 23 +- test/Sema/complex-int.c | 5 +- test/Sema/conditional.c | 10 +- test/Sema/darwin-align-cast.c | 5 +- test/Sema/decl-type-merging.c | 10 +- test/Sema/enum.c | 2 +- test/Sema/exprs.c | 11 +- test/Sema/floating-point-compare.c | 4 +- test/Sema/format-attr-pr4470.c | 1 + test/Sema/format-attribute-printf0.c | 26 + test/Sema/freemain.c | 9 + test/Sema/function-pointer-sentinel-attribute.c | 23 +- test/Sema/function-sentinel-attr.c | 2 +- test/Sema/function.c | 2 + test/Sema/heinous-extensions-on.c | 13 +- test/Sema/implicit-builtin-redecl.c | 12 + test/Sema/implicit-int.c | 9 +- test/Sema/incomplete-call.c | 4 +- test/Sema/incomplete-decl.c | 5 +- test/Sema/pragma-pack-4.c | 19 + test/Sema/pragma-unused.c | 9 +- test/Sema/predefined-function.c | 17 +- test/Sema/promote-int-16bit.c | 6 + test/Sema/redefinition.c | 4 +- test/Sema/return-noreturn.c | 29 + test/Sema/return.c | 210 +++- test/Sema/shift.c | 38 +- test/Sema/static-init.c | 4 +- test/Sema/struct-decl.c | 20 +- test/Sema/tentative-decls.c | 2 +- test/Sema/transparent-union-pointer.c | 8 +- test/Sema/type-spec-struct-union.c | 2 +- test/Sema/unused-expr.c | 54 +- test/Sema/va_arg_x86_64.c | 9 +- test/Sema/vector-cast.c | 2 +- test/Sema/warn-char-subscripts.c | 64 ++ test/Sema/warn-unused-variables.c | 19 + test/Sema/x86-intrinsics-headers.c | 24 + test/SemaCXX/PR5086-ambig-resolution-enum.cpp | 13 + test/SemaCXX/abstract.cpp | 57 +- test/SemaCXX/access-control-check.cpp | 16 + test/SemaCXX/addr-of-overloaded-function.cpp | 27 + test/SemaCXX/ambig-user-defined-conversions.cpp | 52 + test/SemaCXX/ambiguous-builtin-unary-operator.cpp | 18 + test/SemaCXX/arrow-operator.cpp | 22 + test/SemaCXX/attr-after-definition.cpp | 9 + test/SemaCXX/attr-deprecated.cpp | 66 ++ test/SemaCXX/attr-format.cpp | 8 + test/SemaCXX/auto-cxx0x.cpp | 2 +- test/SemaCXX/builtin-ptrtomember-ambig.cpp | 24 + test/SemaCXX/builtin-ptrtomember-overload-1.cpp | 46 + test/SemaCXX/builtin-ptrtomember-overload.cpp | 18 + test/SemaCXX/c99.cpp | 8 + test/SemaCXX/cast-conversion.cpp | 21 + test/SemaCXX/cast-explicit-ctor.cpp | 6 + test/SemaCXX/class-base-member-init.cpp | 6 +- test/SemaCXX/class-layout.cpp | 49 + test/SemaCXX/class-names.cpp | 4 +- test/SemaCXX/composite-pointer-type.cpp | 8 + test/SemaCXX/conditional-expr.cpp | 6 +- test/SemaCXX/constructor-initializer.cpp | 41 +- test/SemaCXX/constructor.cpp | 26 + test/SemaCXX/conversion-delete-expr.cpp | 109 +++ test/SemaCXX/conversion-function.cpp | 29 + test/SemaCXX/copy-assignment.cpp | 2 +- test/SemaCXX/copy-constructor-error.cpp | 13 + test/SemaCXX/cstyle-cast.cpp | 231 +++++ test/SemaCXX/dcl_ambig_res.cpp | 9 +- test/SemaCXX/dcl_init_aggr.cpp | 6 +- test/SemaCXX/decl-expr-ambiguity.cpp | 4 +- test/SemaCXX/decl-init-ref.cpp | 26 + test/SemaCXX/decltype-crash.cpp | 7 + test/SemaCXX/decltype-this.cpp | 15 + test/SemaCXX/default-argument-temporaries.cpp | 11 + test/SemaCXX/default-assignment-operator.cpp | 28 +- test/SemaCXX/default-constructor-initializers.cpp | 18 +- test/SemaCXX/default2.cpp | 22 +- test/SemaCXX/deleted-function.cpp | 2 +- test/SemaCXX/destructor.cpp | 11 +- test/SemaCXX/direct-initializer.cpp | 14 + test/SemaCXX/empty-class-layout.cpp | 68 ++ test/SemaCXX/enum.cpp | 13 +- test/SemaCXX/exception-spec.cpp | 126 ++- test/SemaCXX/friend-class-nodecl.cpp | 10 + test/SemaCXX/function-overloaded-redecl.cpp | 10 + test/SemaCXX/functional-cast.cpp | 294 +++++- test/SemaCXX/i-c-e-cxx.cpp | 10 + test/SemaCXX/illegal-member-initialization.cpp | 22 + test/SemaCXX/incomplete-call.cpp | 38 + test/SemaCXX/inherit.cpp | 2 +- test/SemaCXX/invalid-member-expr.cpp | 21 + test/SemaCXX/invalid-template-specifier.cpp | 12 + test/SemaCXX/libstdcxx_is_pod_hack.cpp | 7 + test/SemaCXX/linkage-spec.cpp | 8 + test/SemaCXX/member-expr-static.cpp | 18 +- test/SemaCXX/member-name-lookup.cpp | 10 + test/SemaCXX/member-operator-expr.cpp | 29 + test/SemaCXX/member-pointer.cpp | 10 +- test/SemaCXX/missing-members.cpp | 36 + test/SemaCXX/namespace.cpp | 5 +- test/SemaCXX/nested-name-spec.cpp | 23 +- test/SemaCXX/new-delete.cpp | 45 +- test/SemaCXX/overload-value-dep-arg.cpp | 13 + test/SemaCXX/overloaded-builtin-operators.cpp | 36 +- test/SemaCXX/overloaded-operator.cpp | 37 +- test/SemaCXX/primary-base.cpp | 11 + test/SemaCXX/pseudo-destructors.cpp | 40 + test/SemaCXX/qual-id-test.cpp | 140 +++ test/SemaCXX/ref-init-ambiguous.cpp | 28 + test/SemaCXX/references.cpp | 15 + test/SemaCXX/return.cpp | 18 + test/SemaCXX/static-array-member.cpp | 18 + test/SemaCXX/static-cast-complete-type.cpp | 13 + test/SemaCXX/static-cast.cpp | 22 +- test/SemaCXX/static-initializers.cpp | 10 +- test/SemaCXX/type-traits-incomplete.cpp | 7 + test/SemaCXX/type-traits.cpp | 149 ++- test/SemaCXX/unknown-type-name.cpp | 29 + test/SemaCXX/unreachable-catch-clauses.cpp | 14 + test/SemaCXX/using-decl-1.cpp | 11 + test/SemaCXX/using-decl-templates.cpp | 36 + test/SemaCXX/value-dependent-exprs.cpp | 47 + test/SemaCXX/vararg-non-pod.cpp | 14 +- test/SemaCXX/vector-casts.cpp | 40 + test/SemaCXX/warn-assignment-condition.cpp | 65 ++ test/SemaCXX/warn-char-subscripts.cpp | 21 + test/SemaCXX/warn-for-var-in-else.cpp | 1 + test/SemaCXX/warn-reorder-ctor-initialization.cpp | 89 ++ test/SemaCXX/warn-unused-variables.cpp | 6 + test/SemaCXX/wchar_t.cpp | 4 + test/SemaObjC/access-property-getter.m | 1 + test/SemaObjC/attr-malloc.m | 16 + test/SemaObjC/block-explicit-return-type.m | 77 ++ test/SemaObjC/blocks.m | 11 + test/SemaObjC/call-super-2.m | 4 +- test/SemaObjC/category-1.m | 19 + test/SemaObjC/category-method-lookup-2.m | 1 + test/SemaObjC/class-bitfield.m | 6 +- test/SemaObjC/class-getter-using-dotsyntax.m | 39 + test/SemaObjC/class-impl-1.m | 2 +- .../SemaObjC/compatible-protocol-qualified-types.m | 1 + test/SemaObjC/comptypes-1.m | 4 +- test/SemaObjC/comptypes-3.m | 12 +- test/SemaObjC/comptypes-5.m | 4 +- test/SemaObjC/comptypes-7.m | 4 +- test/SemaObjC/comptypes-a.m | 1 + test/SemaObjC/conditional-expr-3.m | 6 +- test/SemaObjC/conditional-expr-4.m | 20 +- test/SemaObjC/conditional-expr-5.m | 27 + test/SemaObjC/conditional-expr.m | 83 +- test/SemaObjC/crash-label.m | 9 + test/SemaObjC/deref-interface.m | 12 + test/SemaObjC/format-arg-attribute.m | 3 +- test/SemaObjC/id-isa-ref.m | 37 + test/SemaObjC/id.m | 2 +- test/SemaObjC/interface-scope-2.m | 2 + test/SemaObjC/invalid-objc-decls-1.m | 8 + test/SemaObjC/message.m | 2 +- test/SemaObjC/method-arg-decay.m | 1 + test/SemaObjC/method-conflict.m | 4 +- test/SemaObjC/method-encoding-2.m | 4 +- test/SemaObjC/method-lookup-2.m | 5 +- test/SemaObjC/method-lookup.m | 1 + test/SemaObjC/method-typecheck-1.m | 11 +- test/SemaObjC/no-warn-unimpl-method.m | 2 +- test/SemaObjC/nonnull.m | 42 + test/SemaObjC/nsobject-attribute.m | 2 +- test/SemaObjC/objc2-merge-gc-attribue-decl.m | 5 +- test/SemaObjC/property-11.m | 1 + test/SemaObjC/property-9-impl-method.m | 3 +- test/SemaObjC/property-error-readonly-assign.m | 23 + test/SemaObjC/property-expression-error.m | 18 + test/SemaObjC/property-method-lookup-impl.m | 4 +- test/SemaObjC/property-missing.m | 2 +- test/SemaObjC/protocol-archane.m | 3 +- test/SemaObjC/protocol-attribute.m | 4 +- test/SemaObjC/protocol-implementation-inherited.m | 2 +- test/SemaObjC/protocol-lookup.m | 1 + .../protocol-qualified-class-unsupported.m | 2 +- test/SemaObjC/rdr-6211479-array-property.m | 3 +- test/SemaObjC/return.m | 6 + test/SemaObjC/selector-1.m | 13 + test/SemaObjC/sizeof-interface.m | 11 + test/SemaObjC/static-ivar-ref-1.m | 3 +- test/SemaObjC/super-cat-prot.m | 4 +- test/SemaObjC/super.m | 1 + test/SemaObjC/synchronized.m | 2 +- test/SemaObjC/undef-superclass-1.m | 7 + test/SemaObjC/unused.m | 33 +- test/SemaObjC/warn-assign-property-nscopying.m | 15 + test/SemaObjC/warn-superclass-method-mismatch.m | 50 + test/SemaObjC/weak-attr-ivar.m | 5 +- test/SemaObjCXX/overload.mm | 1 + test/SemaObjCXX/protocol-lookup.mm | 1 + test/SemaObjCXX/references.mm | 4 +- test/SemaTemplate/ackermann.cpp | 7 +- test/SemaTemplate/ambiguous-ovl-print.cpp | 9 + test/SemaTemplate/canonical-expr-type-0x.cpp | 16 + test/SemaTemplate/canonical-expr-type.cpp | 53 + test/SemaTemplate/class-template-spec.cpp | 34 +- test/SemaTemplate/constructor-template.cpp | 53 + test/SemaTemplate/copy-ctor-assign.cpp | 36 + test/SemaTemplate/current-instantiation.cpp | 73 ++ test/SemaTemplate/default-arguments.cpp | 20 + test/SemaTemplate/default-expr-arguments.cpp | 86 ++ test/SemaTemplate/dependent-base-member-init.cpp | 36 + test/SemaTemplate/dependent-type-identity.cpp | 2 +- test/SemaTemplate/destructor-template.cpp | 12 + test/SemaTemplate/example-dynarray.cpp | 63 +- test/SemaTemplate/explicit-instantiation.cpp | 75 ++ .../explicit-specialization-member.cpp | 11 + test/SemaTemplate/ext-vector-type.cpp | 2 +- test/SemaTemplate/extern-templates.cpp | 66 ++ test/SemaTemplate/friend-template.cpp | 64 ++ test/SemaTemplate/friend.cpp | 14 + test/SemaTemplate/fun-template-def.cpp | 7 +- .../function-template-specialization.cpp | 35 + test/SemaTemplate/implicit-instantiation-1.cpp | 2 +- test/SemaTemplate/injected-class-name.cpp | 10 +- test/SemaTemplate/instantiate-anonymous-union.cpp | 31 + test/SemaTemplate/instantiate-cast.cpp | 8 +- test/SemaTemplate/instantiate-deeply.cpp | 22 + test/SemaTemplate/instantiate-expr-2.cpp | 48 + test/SemaTemplate/instantiate-expr-5.cpp | 4 + test/SemaTemplate/instantiate-friend-class.cpp | 9 + test/SemaTemplate/instantiate-function-1.cpp | 2 +- test/SemaTemplate/instantiate-function-1.mm | 3 + test/SemaTemplate/instantiate-init.cpp | 28 + .../instantiate-member-initializers.cpp | 26 + test/SemaTemplate/instantiate-member-template.cpp | 105 ++ test/SemaTemplate/instantiate-method.cpp | 9 + test/SemaTemplate/instantiate-static-var.cpp | 22 + test/SemaTemplate/instantiate-typedef.cpp | 2 +- test/SemaTemplate/instantiate-using-decl.cpp | 17 + test/SemaTemplate/member-access-expr.cpp | 77 ++ test/SemaTemplate/member-function-template.cpp | 51 + test/SemaTemplate/member-initializers.cpp | 13 + test/SemaTemplate/member-template-access-expr.cpp | 30 + test/SemaTemplate/metafun-apply.cpp | 3 +- test/SemaTemplate/nested-linkage.cpp | 3 + test/SemaTemplate/nested-template.cpp | 89 +- test/SemaTemplate/partial-spec-instantiate.cpp | 20 + test/SemaTemplate/qualified-id.cpp | 9 + test/SemaTemplate/qualified-names-diag.cpp | 2 +- test/SemaTemplate/temp_class_order.cpp | 42 + test/SemaTemplate/temp_class_spec.cpp | 75 +- test/SemaTemplate/temp_class_spec_neg.cpp | 4 +- test/SemaTemplate/temp_func_order.cpp | 95 ++ test/SemaTemplate/typename-specifier-4.cpp | 70 ++ test/SemaTemplate/typename-specifier.cpp | 15 +- .../value-dependent-null-pointer-constant.cpp | 29 + test/TestRunner.sh | 137 +-- test/lit.cfg | 152 +++ test/lit.site.cfg.in | 10 + 694 files changed, 17634 insertions(+), 1407 deletions(-) create mode 100644 test/Analysis/dead-stores.cpp create mode 100644 test/Analysis/misc-ps-region-store-i386.m create mode 100644 test/Analysis/misc-ps-region-store-x86_64.m create mode 100644 test/Analysis/no-outofbounds.c create mode 100644 test/Analysis/rdar-7168531.m create mode 100644 test/Analysis/security-syntax-checks.m create mode 100644 test/Analysis/unions-region.m create mode 100644 test/CXX/basic/basic.lookup/basic.lookup.argdep/p2-template-id.cpp create mode 100644 test/CXX/basic/basic.lookup/basic.lookup.argdep/p2.cpp create mode 100644 test/CXX/basic/basic.lookup/basic.lookup.argdep/p4.cpp create mode 100644 test/CXX/basic/basic.lookup/basic.lookup.elab/templateid.cpp create mode 100644 test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p2.cpp create mode 100644 test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p3.cpp create mode 100644 test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p4.cpp create mode 100644 test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p5.cpp create mode 100644 test/CXX/basic/basic.start/basic.start.main/p2a.cpp create mode 100644 test/CXX/basic/basic.start/basic.start.main/p2b.cpp create mode 100644 test/CXX/basic/basic.start/basic.start.main/p2c.cpp create mode 100644 test/CXX/basic/basic.start/basic.start.main/p2d.cpp create mode 100644 test/CXX/basic/basic.start/basic.start.main/p2e.cpp create mode 100644 test/CXX/basic/basic.start/basic.start.main/p2f.cpp create mode 100644 test/CXX/basic/basic.start/basic.start.main/p2g.cpp create mode 100644 test/CXX/basic/basic.stc/basic.stc.dynamic/p2-nodef.cpp create mode 100644 test/CXX/basic/basic.stc/basic.stc.dynamic/p2.cpp create mode 100644 test/CXX/class.derived/class.virtual/p12.cpp create mode 100644 test/CXX/class/class.friend/p1-ambiguous.cpp create mode 100644 test/CXX/class/class.friend/p1.cpp create mode 100644 test/CXX/class/class.friend/p2.cpp create mode 100644 test/CXX/class/class.friend/p6.cpp create mode 100644 test/CXX/class/class.nest/p1.cpp create mode 100644 test/CXX/class/class.union/p1.cpp create mode 100644 test/CXX/dcl.dcl/basic.namespace/namespace.def/namespace.memdef/p3.cpp create mode 100644 test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p3-cxx0x.cpp create mode 100644 test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p5-cxx0x.cpp create mode 100644 test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p6-cxx0x.cpp create mode 100644 test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p8-cxx0x.cpp create mode 100644 test/CXX/dcl.dcl/dcl.spec/dcl.type/dcl.spec.auto/p3.cpp create mode 100644 test/CXX/dcl.dcl/dcl.spec/dcl.type/dcl.spec.auto/p5.cpp create mode 100644 test/CXX/dcl.dcl/dcl.spec/dcl.type/dcl.type.elab/p3.cpp create mode 100644 test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p10.cpp create mode 100644 test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p2.cpp create mode 100644 test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p3.cpp create mode 100644 test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p4.cpp create mode 100644 test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p5.cpp create mode 100644 test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p6.cpp create mode 100644 test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p7.cpp create mode 100644 test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p8.cpp create mode 100644 test/CXX/dcl.decl/dcl.meaning/dcl.fct/p3.cpp create mode 100644 test/CXX/dcl.decl/dcl.meaning/dcl.mptr/p3.cpp create mode 100644 test/CXX/expr/p3.cpp create mode 100644 test/CXX/expr/p8.cpp create mode 100644 test/CXX/expr/p9.cpp create mode 100644 test/CXX/lex/lex.trigraph/p1.cpp create mode 100644 test/CXX/lex/lex.trigraph/p2.cpp create mode 100644 test/CXX/lex/lex.trigraph/p3.cpp create mode 100644 test/CXX/over/over.match/over.match.best/p1.cpp create mode 100644 test/CXX/over/over.over/p1.cpp create mode 100644 test/CXX/over/over.over/p2.cpp create mode 100644 test/CXX/over/over.over/p4.cpp create mode 100644 test/CXX/temp/temp.decls/temp.class.spec/p6.cpp create mode 100644 test/CXX/temp/temp.decls/temp.class.spec/temp.class.order/p2.cpp create mode 100644 test/CXX/temp/temp.decls/temp.class.spec/temp.class.spec.mfunc/p1-neg.cpp create mode 100644 test/CXX/temp/temp.decls/temp.class.spec/temp.class.spec.mfunc/p1.cpp create mode 100644 test/CXX/temp/temp.decls/temp.class/temp.mem.class/p1.cpp create mode 100644 test/CXX/temp/temp.decls/temp.class/temp.mem.func/p1-retmem.cpp create mode 100644 test/CXX/temp/temp.decls/temp.class/temp.mem.func/p1.cpp create mode 100644 test/CXX/temp/temp.decls/temp.class/temp.mem.func/p1inst.cpp create mode 100644 test/CXX/temp/temp.decls/temp.class/temp.mem.func/pr5056.cpp create mode 100644 test/CXX/temp/temp.decls/temp.class/temp.static/p1-inst.cpp create mode 100644 test/CXX/temp/temp.decls/temp.class/temp.static/p1.cpp create mode 100644 test/CXX/temp/temp.decls/temp.fct/temp.func.order/p4.cpp create mode 100644 test/CXX/temp/temp.decls/temp.fct/temp.func.order/p5.cpp create mode 100644 test/CXX/temp/temp.decls/temp.fct/temp.over.link/p6.cpp create mode 100644 test/CXX/temp/temp.decls/temp.friend/p1.cpp create mode 100644 test/CXX/temp/temp.decls/temp.friend/p3.cpp create mode 100644 test/CXX/temp/temp.decls/temp.friend/p5.cpp create mode 100644 test/CXX/temp/temp.decls/temp.mem/p1.cpp create mode 100644 test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.conv/p2.cpp create mode 100644 test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.conv/p3.cpp create mode 100644 test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.conv/p4.cpp create mode 100644 test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.funcaddr/p1.cpp create mode 100644 test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.partial/p11.cpp create mode 100644 test/CXX/temp/temp.res/temp.dep/p3.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p1.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p10.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p11.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p13.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p14.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p15.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p16.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p17.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p18.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p19.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p2.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p20.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p21.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p3.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p4.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p5.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p6.cpp create mode 100644 test/CXX/temp/temp.spec/temp.expl.spec/p9.cpp create mode 100644 test/CodeCompletion/call.cpp create mode 100644 test/CodeCompletion/enum-switch-case-qualified.cpp create mode 100644 test/CodeCompletion/enum-switch-case.c create mode 100644 test/CodeCompletion/enum-switch-case.cpp create mode 100644 test/CodeCompletion/function-templates.cpp create mode 100644 test/CodeCompletion/functions.cpp create mode 100644 test/CodeCompletion/member-access.c create mode 100644 test/CodeCompletion/member-access.cpp create mode 100644 test/CodeCompletion/namespace-alias.cpp create mode 100644 test/CodeCompletion/namespace.cpp create mode 100644 test/CodeCompletion/nested-name-specifier.cpp create mode 100644 test/CodeCompletion/operator.cpp create mode 100644 test/CodeCompletion/ordinary-name.c create mode 100644 test/CodeCompletion/property.m create mode 100644 test/CodeCompletion/tag.c create mode 100644 test/CodeCompletion/tag.cpp create mode 100644 test/CodeCompletion/templates.cpp create mode 100644 test/CodeCompletion/truncation.c create mode 100644 test/CodeCompletion/truncation.c.h create mode 100644 test/CodeCompletion/using-namespace.cpp create mode 100644 test/CodeCompletion/using.cpp create mode 100644 test/CodeGen/2009-07-31-DbgDeclare.c create mode 100644 test/CodeGen/2009-08-14-vararray-crash.c create mode 100644 test/CodeGen/PR4611-bitfield-layout.c create mode 100644 test/CodeGen/PR5060-align.c create mode 100644 test/CodeGen/address-space-compound-literal.c create mode 100644 test/CodeGen/address-space-field1.c create mode 100644 test/CodeGen/address-space-field2.c create mode 100644 test/CodeGen/address-space-field3.c create mode 100644 test/CodeGen/address-space-field4.c create mode 100644 test/CodeGen/arm-arguments.c create mode 100644 test/CodeGen/arm_asm_clobber.c create mode 100644 test/CodeGen/asm-inout.c create mode 100644 test/CodeGen/blocks-aligned-byref-variable.c create mode 100644 test/CodeGen/builtin-attributes.c create mode 100644 test/CodeGen/inline2.c create mode 100644 test/CodeGen/packed-union.c create mode 100644 test/CodeGen/pragma-pack-1.c create mode 100644 test/CodeGen/pragma-pack-2.c create mode 100644 test/CodeGen/pragma-pack-3.c create mode 100644 test/CodeGen/pragma-weak.c create mode 100644 test/CodeGen/predefined-expr.c create mode 100644 test/CodeGen/union-init2.c create mode 100644 test/CodeGen/unreachable.c create mode 100644 test/CodeGenCXX/PR4827-cast.cpp create mode 100644 test/CodeGenCXX/PR4890-debug-info-dtor.cpp create mode 100644 test/CodeGenCXX/PR4983-constructor-conversion.cpp create mode 100644 test/CodeGenCXX/PR5050-constructor-conversion.cpp create mode 100644 test/CodeGenCXX/PR5093-static-member-function.cpp create mode 100644 test/CodeGenCXX/anonymous-namespaces.cpp create mode 100644 test/CodeGenCXX/anonymous-union-member-initializer.cpp create mode 100644 test/CodeGenCXX/array-pointer-decay.cpp create mode 100644 test/CodeGenCXX/attr.cpp create mode 100644 test/CodeGenCXX/cast-conversion.cpp create mode 100644 test/CodeGenCXX/class-layout.cpp create mode 100644 test/CodeGenCXX/conditional-expr-lvalue.cpp create mode 100644 test/CodeGenCXX/constructor-conversion.cpp create mode 100644 test/CodeGenCXX/constructor-default-arg.cpp create mode 100644 test/CodeGenCXX/constructor-for-array-members.cpp create mode 100644 test/CodeGenCXX/constructor-init-reference.cpp create mode 100644 test/CodeGenCXX/constructor-init.cpp create mode 100644 test/CodeGenCXX/constructor-template.cpp create mode 100644 test/CodeGenCXX/conversion-function.cpp create mode 100644 test/CodeGenCXX/convert-to-fptr.cpp create mode 100644 test/CodeGenCXX/copy-assign-synthesis-1.cpp create mode 100644 test/CodeGenCXX/copy-assign-synthesis.cpp create mode 100644 test/CodeGenCXX/copy-constructor-elim.cpp create mode 100644 test/CodeGenCXX/copy-constructor-synthesis.cpp create mode 100644 test/CodeGenCXX/decl-ref-init.cpp create mode 100644 test/CodeGenCXX/default-constructor-for-members.cpp create mode 100644 test/CodeGenCXX/default-destructor-synthesis.cpp create mode 100644 test/CodeGenCXX/delete.cpp create mode 100644 test/CodeGenCXX/derived-to-base.cpp create mode 100644 test/CodeGenCXX/destructor-calls.cpp create mode 100644 test/CodeGenCXX/destructors.cpp create mode 100644 test/CodeGenCXX/devirtualize-virtual-function-calls.cpp create mode 100644 test/CodeGenCXX/global-init.cpp create mode 100644 test/CodeGenCXX/mangle-extreme.cpp create mode 100644 test/CodeGenCXX/mangle-subst-std.cpp create mode 100644 test/CodeGenCXX/mangle-subst.cpp create mode 100644 test/CodeGenCXX/member-function-pointers.cpp create mode 100644 test/CodeGenCXX/member-pointers-zero-init.cpp create mode 100644 test/CodeGenCXX/namespace-aliases.cpp create mode 100644 test/CodeGenCXX/nested-base-member-access.cpp create mode 100644 test/CodeGenCXX/nullptr.cpp create mode 100644 test/CodeGenCXX/overload-binop-implicitconvert.cpp create mode 100644 test/CodeGenCXX/predefined-expr-sizeof.cpp create mode 100644 test/CodeGenCXX/predefined-expr.cpp create mode 100644 test/CodeGenCXX/reinterpret-cast.cpp create mode 100644 test/CodeGenCXX/static-data-member.cpp create mode 100644 test/CodeGenCXX/static-init.cpp create mode 100644 test/CodeGenCXX/temp-1.cpp create mode 100644 test/CodeGenCXX/template-anonymous-union-member-initializer.cpp create mode 100644 test/CodeGenCXX/trivial-constructor-init.cpp create mode 100644 test/CodeGenCXX/virt.cpp create mode 100644 test/CodeGenCXX/virtual-base-cast.cpp create mode 100644 test/CodeGenCXX/virtual-function-calls.cpp create mode 100644 test/CodeGenCXX/vtable-cast-crash.cpp create mode 100644 test/CodeGenCXX/x86_64-arguments.cpp create mode 100644 test/CodeGenObjC/PR4541.m create mode 100644 test/CodeGenObjC/PR4894-recursive-debug-crash.m create mode 100644 test/CodeGenObjC/debug-info-linkagename.m create mode 100644 test/CodeGenObjC/for-in.m create mode 100644 test/CodeGenObjC/ivar-layout-64-bitfields.m create mode 100644 test/CodeGenObjC/ivar-layout-no-optimize.m create mode 100644 test/CodeGenObjC/objc-assign-ivar.m create mode 100644 test/CodeGenObjC/objc-gc-aggr-assign.m create mode 100644 test/CodeGenObjC/objc-read-weak-byref.m create mode 100644 test/CodeGenObjC/objc2-ivar-assign.m create mode 100644 test/CodeGenObjC/objc2-new-gc-api-strongcast.m create mode 100644 test/CodeGenObjC/objc2-weak-ivar-debug.m create mode 100644 test/CodeGenObjC/objc2-write-barrier-2.m create mode 100644 test/CodeGenObjC/objc2-write-barrier-3.m create mode 100644 test/CodeGenObjC/objc2-write-barrier-4.m create mode 100644 test/CodeGenObjC/objc2-write-barrier-5.m create mode 100644 test/CodeGenObjC/objc2-write-barrier.m create mode 100644 test/CodeGenObjC/object-incr-decr-1.m create mode 100644 test/CodeGenObjC/predefined-expr.m create mode 100644 test/CodeGenObjC/protocol-in-extended-class.m create mode 100644 test/CodeGenObjC/protocols.m create mode 100644 test/CodeGenObjC/variadic-sends.m create mode 100644 test/Driver/arm-darwin-builtin.c create mode 100644 test/Driver/ast.c create mode 100644 test/Driver/darwin-arm.c create mode 100644 test/Driver/darwin-as.c create mode 100644 test/Frontend/ast-codegen.c create mode 100644 test/Frontend/ast-main.c create mode 100644 test/Index/c-index-api-test.m create mode 100644 test/Index/cxx-operator-overload.cpp create mode 100644 test/Index/find-decls.c create mode 100644 test/Index/find-defs.c create mode 100644 test/Index/find-refs.c create mode 100644 test/Index/foo.h create mode 100644 test/Index/multiple-redecls.c create mode 100644 test/Index/objc-decls.m create mode 100644 test/Index/objc-message.m create mode 100644 test/Index/objc.h create mode 100644 test/Index/t1.c create mode 100644 test/Index/t1.m create mode 100644 test/Index/t2.c create mode 100644 test/Index/t2.m create mode 100644 test/PCH/cxx-method.cpp create mode 100644 test/PCH/libroot/usr/include/reloc.h create mode 100644 test/PCH/libroot/usr/include/reloc2.h create mode 100644 test/PCH/reloc.c create mode 100644 test/Parser/cxx-member-initializers.cpp create mode 100644 test/Parser/top-level-semi-cxx0x.cpp create mode 100644 test/Preprocessor/non_fragile_feature.m create mode 100644 test/Preprocessor/non_fragile_feature1.m create mode 100644 test/Preprocessor/pushable-diagnostics.c create mode 100644 test/Sema/align-arm-apcs.c create mode 100644 test/Sema/altivec-init.c create mode 100644 test/Sema/attr-decl-after-definition.c create mode 100644 test/Sema/attr-malloc.c create mode 100644 test/Sema/attr-section.c create mode 100644 test/Sema/bitfield-promote-int-16bit.c create mode 100644 test/Sema/bitfield-promote.c create mode 100644 test/Sema/block-return-1.c create mode 100644 test/Sema/block-return-2.c create mode 100644 test/Sema/block-return-3.c create mode 100644 test/Sema/builtin-unary-fp.c create mode 100644 test/Sema/format-attribute-printf0.c create mode 100644 test/Sema/freemain.c create mode 100644 test/Sema/pragma-pack-4.c create mode 100644 test/Sema/promote-int-16bit.c create mode 100644 test/Sema/return-noreturn.c create mode 100644 test/Sema/warn-char-subscripts.c create mode 100644 test/Sema/warn-unused-variables.c create mode 100644 test/Sema/x86-intrinsics-headers.c create mode 100644 test/SemaCXX/PR5086-ambig-resolution-enum.cpp create mode 100644 test/SemaCXX/access-control-check.cpp create mode 100644 test/SemaCXX/ambig-user-defined-conversions.cpp create mode 100644 test/SemaCXX/ambiguous-builtin-unary-operator.cpp create mode 100644 test/SemaCXX/arrow-operator.cpp create mode 100644 test/SemaCXX/attr-after-definition.cpp create mode 100644 test/SemaCXX/attr-deprecated.cpp create mode 100644 test/SemaCXX/attr-format.cpp create mode 100644 test/SemaCXX/builtin-ptrtomember-ambig.cpp create mode 100644 test/SemaCXX/builtin-ptrtomember-overload-1.cpp create mode 100644 test/SemaCXX/builtin-ptrtomember-overload.cpp create mode 100644 test/SemaCXX/c99.cpp create mode 100644 test/SemaCXX/cast-conversion.cpp create mode 100644 test/SemaCXX/cast-explicit-ctor.cpp create mode 100644 test/SemaCXX/class-layout.cpp create mode 100644 test/SemaCXX/conversion-delete-expr.cpp create mode 100644 test/SemaCXX/copy-constructor-error.cpp create mode 100644 test/SemaCXX/cstyle-cast.cpp create mode 100644 test/SemaCXX/decl-init-ref.cpp create mode 100644 test/SemaCXX/decltype-crash.cpp create mode 100644 test/SemaCXX/decltype-this.cpp create mode 100644 test/SemaCXX/default-argument-temporaries.cpp create mode 100644 test/SemaCXX/empty-class-layout.cpp create mode 100644 test/SemaCXX/friend-class-nodecl.cpp create mode 100644 test/SemaCXX/function-overloaded-redecl.cpp create mode 100644 test/SemaCXX/illegal-member-initialization.cpp create mode 100644 test/SemaCXX/incomplete-call.cpp create mode 100644 test/SemaCXX/invalid-member-expr.cpp create mode 100644 test/SemaCXX/invalid-template-specifier.cpp create mode 100644 test/SemaCXX/libstdcxx_is_pod_hack.cpp create mode 100644 test/SemaCXX/member-operator-expr.cpp create mode 100644 test/SemaCXX/missing-members.cpp create mode 100644 test/SemaCXX/overload-value-dep-arg.cpp create mode 100644 test/SemaCXX/primary-base.cpp create mode 100644 test/SemaCXX/pseudo-destructors.cpp create mode 100644 test/SemaCXX/qual-id-test.cpp create mode 100644 test/SemaCXX/ref-init-ambiguous.cpp create mode 100644 test/SemaCXX/return.cpp create mode 100644 test/SemaCXX/static-array-member.cpp create mode 100644 test/SemaCXX/static-cast-complete-type.cpp create mode 100644 test/SemaCXX/type-traits-incomplete.cpp create mode 100644 test/SemaCXX/unknown-type-name.cpp create mode 100644 test/SemaCXX/unreachable-catch-clauses.cpp create mode 100644 test/SemaCXX/using-decl-templates.cpp create mode 100644 test/SemaCXX/value-dependent-exprs.cpp create mode 100644 test/SemaCXX/vector-casts.cpp create mode 100644 test/SemaCXX/warn-assignment-condition.cpp create mode 100644 test/SemaCXX/warn-char-subscripts.cpp create mode 100644 test/SemaCXX/warn-reorder-ctor-initialization.cpp create mode 100644 test/SemaCXX/warn-unused-variables.cpp create mode 100644 test/SemaObjC/attr-malloc.m create mode 100644 test/SemaObjC/block-explicit-return-type.m create mode 100644 test/SemaObjC/class-getter-using-dotsyntax.m create mode 100644 test/SemaObjC/conditional-expr-5.m create mode 100644 test/SemaObjC/crash-label.m create mode 100644 test/SemaObjC/deref-interface.m create mode 100644 test/SemaObjC/id-isa-ref.m create mode 100644 test/SemaObjC/nonnull.m create mode 100644 test/SemaObjC/property-expression-error.m create mode 100644 test/SemaObjC/return.m create mode 100644 test/SemaObjC/warn-assign-property-nscopying.m create mode 100644 test/SemaObjC/warn-superclass-method-mismatch.m create mode 100644 test/SemaTemplate/ambiguous-ovl-print.cpp create mode 100644 test/SemaTemplate/canonical-expr-type-0x.cpp create mode 100644 test/SemaTemplate/canonical-expr-type.cpp create mode 100644 test/SemaTemplate/constructor-template.cpp create mode 100644 test/SemaTemplate/copy-ctor-assign.cpp create mode 100644 test/SemaTemplate/default-expr-arguments.cpp create mode 100644 test/SemaTemplate/dependent-base-member-init.cpp create mode 100644 test/SemaTemplate/destructor-template.cpp create mode 100644 test/SemaTemplate/explicit-instantiation.cpp create mode 100644 test/SemaTemplate/explicit-specialization-member.cpp create mode 100644 test/SemaTemplate/extern-templates.cpp create mode 100644 test/SemaTemplate/friend-template.cpp create mode 100644 test/SemaTemplate/friend.cpp create mode 100644 test/SemaTemplate/function-template-specialization.cpp create mode 100644 test/SemaTemplate/instantiate-anonymous-union.cpp create mode 100644 test/SemaTemplate/instantiate-deeply.cpp create mode 100644 test/SemaTemplate/instantiate-expr-5.cpp create mode 100644 test/SemaTemplate/instantiate-friend-class.cpp create mode 100644 test/SemaTemplate/instantiate-init.cpp create mode 100644 test/SemaTemplate/instantiate-member-initializers.cpp create mode 100644 test/SemaTemplate/instantiate-member-template.cpp create mode 100644 test/SemaTemplate/instantiate-using-decl.cpp create mode 100644 test/SemaTemplate/member-access-expr.cpp create mode 100644 test/SemaTemplate/member-function-template.cpp create mode 100644 test/SemaTemplate/member-initializers.cpp create mode 100644 test/SemaTemplate/member-template-access-expr.cpp create mode 100644 test/SemaTemplate/nested-linkage.cpp create mode 100644 test/SemaTemplate/partial-spec-instantiate.cpp create mode 100644 test/SemaTemplate/qualified-id.cpp create mode 100644 test/SemaTemplate/temp_class_order.cpp create mode 100644 test/SemaTemplate/temp_func_order.cpp create mode 100644 test/SemaTemplate/typename-specifier-4.cpp create mode 100644 test/SemaTemplate/value-dependent-null-pointer-constant.cpp create mode 100644 test/lit.cfg create mode 100644 test/lit.site.cfg.in (limited to 'test') diff --git a/test/Analysis/CFDateGC.m b/test/Analysis/CFDateGC.m index dfc7366..557e7e8 100644 --- a/test/Analysis/CFDateGC.m +++ b/test/Analysis/CFDateGC.m @@ -1,6 +1,6 @@ -// RUN: clang-cc -analyze -checker-cfref -verify -fobjc-gc -analyzer-constraints=basic %s && -// RUN: clang-cc -analyze -checker-cfref -verify -fobjc-gc -analyzer-constraints=range %s && -// RUN: clang-cc -analyze -checker-cfref -verify -fobjc-gc -disable-free %s && +// RUN: clang-cc -analyze -checker-cfref -analyzer-store=basic -verify -fobjc-gc -analyzer-constraints=basic %s && +// RUN: clang-cc -analyze -checker-cfref -analyzer-store=basic -verify -fobjc-gc -analyzer-constraints=range %s && +// RUN: clang-cc -analyze -checker-cfref -analyzer-store=basic -verify -fobjc-gc -disable-free %s && // RUN: clang-cc -analyze -checker-cfref -analyzer-store=region -analyzer-constraints=basic -verify -fobjc-gc %s && // RUN: clang-cc -analyze -checker-cfref -analyzer-store=region -analyzer-constraints=range -verify -fobjc-gc %s @@ -25,7 +25,7 @@ extern CFDateRef CFDateCreate(CFAllocatorRef allocator, CFAbsoluteTime at); extern CFAbsoluteTime CFDateGetAbsoluteTime(CFDateRef theDate); typedef struct objc_object {} *id; typedef signed char BOOL; -static __inline__ __attribute__((always_inline)) id NSMakeCollectable(CFTypeRef cf) {} +static __inline__ __attribute__((always_inline)) id NSMakeCollectable(CFTypeRef cf) { return 0; } @protocol NSObject - (BOOL)isEqual:(id)object; - (oneway void)release; - (id)retain; diff --git a/test/Analysis/CheckNSError.m b/test/Analysis/CheckNSError.m index 779b865..5f92594 100644 --- a/test/Analysis/CheckNSError.m +++ b/test/Analysis/CheckNSError.m @@ -24,7 +24,7 @@ extern NSString * const NSXMLParserErrorDomain ; @end @implementation A -- (void)myMethodWhichMayFail:(NSError **)error { // expected-warning {{Method accepting NSError** should have a non-void return value to indicate whether or not an error occured.}} +- (void)myMethodWhichMayFail:(NSError **)error { // expected-warning {{Method accepting NSError** should have a non-void return value to indicate whether or not an error occurred}} *error = [NSError errorWithDomain:@"domain" code:1 userInfo:0]; // expected-warning {{Potential null dereference.}} } @@ -37,7 +37,7 @@ extern NSString * const NSXMLParserErrorDomain ; struct __CFError {}; typedef struct __CFError* CFErrorRef; -void foo(CFErrorRef* error) { // expected-warning {{Function accepting CFErrorRef* should have a non-void return value to indicate whether or not an error occured.}} +void foo(CFErrorRef* error) { // expected-warning {{Function accepting CFErrorRef* should have a non-void return value to indicate whether or not an error occurred}} *error = 0; // expected-warning {{Potential null dereference.}} } diff --git a/test/Analysis/NSPanel.m b/test/Analysis/NSPanel.m index c4d4c22..801620a 100644 --- a/test/Analysis/NSPanel.m +++ b/test/Analysis/NSPanel.m @@ -28,7 +28,7 @@ typedef struct _NSZone NSZone; @end typedef float CGFloat; typedef struct _NSPoint {} NSRect; -static __inline__ __attribute__((always_inline)) NSRect NSMakeRect(CGFloat x, CGFloat y, CGFloat w, CGFloat h) {} +static __inline__ __attribute__((always_inline)) NSRect NSMakeRect(CGFloat x, CGFloat y, CGFloat w, CGFloat h) { NSRect r; return r; } typedef struct {} NSFastEnumerationState; @protocol NSFastEnumeration - (NSUInteger)countByEnumeratingWithState:(NSFastEnumerationState *)state objects:(id *)stackbuf count:(NSUInteger)len; diff --git a/test/Analysis/NSString.m b/test/Analysis/NSString.m index b707071..0ba3cda 100644 --- a/test/Analysis/NSString.m +++ b/test/Analysis/NSString.m @@ -1,9 +1,7 @@ // RUN: clang-cc -triple i386-pc-linux-gnu -analyze -checker-cfref -analyzer-store=basic -analyzer-constraints=basic -verify %s && -// RUN: clang-cc -triple i386-pc-linux-gnu -analyze -checker-cfref -analyzer-store=basic -analyzer-constraints=range -verify %s - - -// NOTWORK: clang-cc -triple i386-pc-linux-gnu -analyze -checker-cfref -analyzer-store=region -analyzer-constraints=basic -verify %s && -// NOTWORK: clang-cc -triple i386-pc-linux-gnu -analyze -checker-cfref -analyzer-store=region -analyzer-constraints=range -verify %s +// RUN: clang-cc -triple i386-pc-linux-gnu -analyze -checker-cfref -analyzer-store=basic -analyzer-constraints=range -verify %s && +// RUN: clang-cc -triple i386-pc-linux-gnu -analyze -checker-cfref -analyzer-store=region -analyzer-constraints=basic -verify %s && +// RUN: clang-cc -triple i386-pc-linux-gnu -analyze -checker-cfref -analyzer-store=region -analyzer-constraints=range -verify %s //===----------------------------------------------------------------------===// // The following code is reduced using delta-debugging from @@ -157,6 +155,7 @@ NSString* f11(CFDictionaryRef dict, const char* key) { if (s) { [s release]; } + return 0; } // Test case for passing a tracked object by-reference to a function we @@ -285,6 +284,12 @@ void testOSCompareAndSwap32Barrier() { [old release]; } +int testOSCompareAndSwap32Barrier_id(Class myclass, id xclass) { + if (OSAtomicCompareAndSwap32Barrier(0, (int32_t) myclass, (int32_t*) &xclass)) + return 1; + return 0; +} + void test_objc_atomicCompareAndSwap() { NSString *old = 0; NSString *s = [[NSString alloc] init]; // no-warning diff --git a/test/Analysis/PR2978.m b/test/Analysis/PR2978.m index 7bc90b8..0cb3dea 100644 --- a/test/Analysis/PR2978.m +++ b/test/Analysis/PR2978.m @@ -55,6 +55,7 @@ [self setW:@"newW"]; // This will release '_W', but retain the new value self.O = 0; // no-warning [super dealloc]; + return 0; } @end diff --git a/test/Analysis/PR3991.m b/test/Analysis/PR3991.m index 20d4b5b..bbc1377 100644 --- a/test/Analysis/PR3991.m +++ b/test/Analysis/PR3991.m @@ -43,6 +43,7 @@ typedef struct _NSZone NSZone; - (void)setCurrentPathComponentIndex:(unsigned int)aCurrentPathComponentIndex; - (NSURL *)folderFeedURL; @end @implementation IHGoogleDocsAdapter - (id)initWithUsername:(NSString *)inUsername password:(NSString *)inPassword owner:(NSObject *)owner { + return 0; } //===----------------------------------------------------------------------===// diff --git a/test/Analysis/array-struct.c b/test/Analysis/array-struct.c index da7df4b..d6b6076 100644 --- a/test/Analysis/array-struct.c +++ b/test/Analysis/array-struct.c @@ -1,7 +1,5 @@ // RUN: clang-cc -analyze -checker-cfref -analyzer-store=basic -analyzer-constraints=basic -verify %s && -// RUN: clang-cc -analyze -checker-cfref -analyzer-store=basic -analyzer-constraints=range -verify %s - -// RegionStore now has an infinite recursion with this test case. +// RUN: clang-cc -analyze -checker-cfref -analyzer-store=basic -analyzer-constraints=range -verify %s && // RUN: clang-cc -analyze -checker-cfref -analyzer-store=region -analyzer-constraints=basic -verify %s && // RUN: clang-cc -analyze -checker-cfref -analyzer-store=region -analyzer-constraints=range -verify %s @@ -145,7 +143,7 @@ void f15() { int a[10]; bar(a); if (a[1]) // no-warning - 1; + (void)1; } struct s3 p[1]; diff --git a/test/Analysis/casts.c b/test/Analysis/casts.c index 5e4222b..ae51ffb 100644 --- a/test/Analysis/casts.c +++ b/test/Analysis/casts.c @@ -1,9 +1,16 @@ -// RUN: clang-cc -analyze -checker-cfref -analyzer-store=region --verify %s +// RUN: clang-cc -triple x86_64-apple-darwin9 -analyze -checker-cfref -analyzer-store=region --verify %s // Test if the 'storage' region gets properly initialized after it is cast to // 'struct sockaddr *'. -#include +typedef unsigned char __uint8_t; +typedef unsigned int __uint32_t; +typedef __uint32_t __darwin_socklen_t; +typedef __uint8_t sa_family_t; +typedef __darwin_socklen_t socklen_t; +struct sockaddr { sa_family_t sa_family; }; +struct sockaddr_storage {}; + void f(int sock) { struct sockaddr_storage storage; struct sockaddr* sockaddr = (struct sockaddr*)&storage; @@ -19,14 +26,14 @@ struct s { struct s *value; }; -int f1(struct s **pval) { +void f1(struct s **pval) { int *tbool = ((void*)0); struct s *t = *pval; pval = &(t->value); - tbool = (int *)pval; // Should record the cast-to type here. + tbool = (int *)pval; // use the cast-to type 'int *' to create element region. char c = (unsigned char) *tbool; // Should use cast-to type to create symbol. - if (*tbool == -1) - 3; + if (*tbool == -1) // here load the element region with the correct type 'int' + (void)3; } void f2(const char *str) { diff --git a/test/Analysis/cfref_rdar6080742.c b/test/Analysis/cfref_rdar6080742.c index 5d95761..9bbaf9b 100644 --- a/test/Analysis/cfref_rdar6080742.c +++ b/test/Analysis/cfref_rdar6080742.c @@ -44,15 +44,15 @@ Boolean DebugDisplayOSStatusMsg(OSStatus status, const char *statusStr, #define AssertNoErr(err){ DebugDisplayOSStatusMsg((err), #err, __FILE__, __LINE__); } #define RequireNoErr(err, action){ if( DebugDisplayOSStatusMsg((err), #err, __FILE__, __LINE__) ) { action }} -void DebugStop(const char *format,...); /* Not an abort function. */ +void DebugStop(const char *format,...); /* Not an abort function. */ int main(int argc, char *argv[]) { - CFStringRef cfString; - OSStatus status = noErr; - cfString = CFStringCreateWithCString(0, "hello", kCFStringEncodingUTF8); - RequireAction(cfString != 0, return memFullErr;) //no - warning - printf("cfstring %p\n", cfString); -Exit: - CFRelease(cfString); - return 0; + CFStringRef cfString; + OSStatus status = noErr; + cfString = CFStringCreateWithCString(0, "hello", kCFStringEncodingUTF8); + RequireAction(cfString != 0, return memFullErr;) //no - warning + printf("cfstring %p\n", cfString); + Exit: + CFRelease(cfString); + return 0; } diff --git a/test/Analysis/complex.c b/test/Analysis/complex.c index cef6245..3633b21 100644 --- a/test/Analysis/complex.c +++ b/test/Analysis/complex.c @@ -5,7 +5,7 @@ #include -int f1(int * p) { +void f1(int * p) { // This branch should be infeasible // because __imag__ p is 0. diff --git a/test/Analysis/dead-stores.c b/test/Analysis/dead-stores.c index 6d3b7e6..c4ff7fa 100644 --- a/test/Analysis/dead-stores.c +++ b/test/Analysis/dead-stores.c @@ -57,7 +57,7 @@ int f7(int *p) { int f8(int *p) { extern int *baz(); - if (p = baz()) // expected-warning{{Although the value}} + if ((p = baz())) // expected-warning{{Although the value}} return 1; return 0; } @@ -129,14 +129,15 @@ int f16(int x) { } // Self-assignments should not be flagged as dead stores. -int f17() { +void f17() { int x = 1; x = x; // no-warning } // // The values of dead stores are only "consumed" in an enclosing expression -// what that value is actually used. In other words, don't say "Although the value stored to 'x' is used...". +// what that value is actually used. In other words, don't say "Although the +// value stored to 'x' is used...". int f18() { int x = 0; // no-warning if (1) @@ -171,3 +172,167 @@ void f20(void) { #pragma unused(x) } +void halt() __attribute__((noreturn)); +int f21() { + int x = 4; + + ++x; // expected-warning{{never read}} + if (1) { + halt(); + (void)x; + } + return 1; +} + +int j; +void f22() { + int x = 4; + int y1 = 4; + int y2 = 4; + int y3 = 4; + int y4 = 4; + int y5 = 4; + int y6 = 4; + int y7 = 4; + int y8 = 4; + int y9 = 4; + int y10 = 4; + int y11 = 4; + int y12 = 4; + int y13 = 4; + int y14 = 4; + int y15 = 4; + int y16 = 4; + int y17 = 4; + int y18 = 4; + int y19 = 4; + int y20 = 4; + + ++x; // expected-warning{{never read}} + ++y1; + ++y2; + ++y3; + ++y4; + ++y5; + ++y6; + ++y7; + ++y8; + ++y9; + ++y10; + ++y11; + ++y12; + ++y13; + ++y14; + ++y15; + ++y16; + ++y17; + ++y18; + ++y19; + ++y20; + + switch (j) { + case 1: + if (0) + (void)x; + if (1) { + (void)y1; + return; + } + (void)x; + break; + case 2: + if (0) + (void)x; + else { + (void)y2; + return; + } + (void)x; + break; + case 3: + if (1) { + (void)y3; + return; + } else + (void)x; + (void)x; + break; + case 4: + 0 ? : ((void)y4, ({ return; })); + (void)x; + break; + case 5: + 1 ? : (void)x; + 0 ? (void)x : ((void)y5, ({ return; })); + (void)x; + break; + case 6: + 1 ? ((void)y6, ({ return; })) : (void)x; + (void)x; + break; + case 7: + (void)(0 && x); + (void)y7; + (void)(0 || (y8, ({ return; }), 1)); + (void)x; + break; + case 8: + (void)(1 && (y9, ({ return; }), 1)); + (void)x; + break; + case 9: + (void)(1 || x); + (void)y10; + break; + case 10: + while (0) { + (void)x; + } + (void)y11; + break; + case 11: + while (1) { + (void)y12; + } + (void)x; + break; + case 12: + do { + (void)y13; + } while (0); + (void)y14; + break; + case 13: + do { + (void)y15; + } while (1); + (void)x; + break; + case 14: + for (;;) { + (void)y16; + } + (void)x; + break; + case 15: + for (;1;) { + (void)y17; + } + (void)x; + break; + case 16: + for (;0;) { + (void)x; + } + (void)y18; + break; + case 17: + __builtin_choose_expr(0, (void)x, ((void)y19, ({ return; }))); + (void)x; + break; + case 19: + __builtin_choose_expr(1, ((void)y20, ({ return; })), (void)x); + (void)x; + break; + } +} diff --git a/test/Analysis/dead-stores.cpp b/test/Analysis/dead-stores.cpp new file mode 100644 index 0000000..9ddb797 --- /dev/null +++ b/test/Analysis/dead-stores.cpp @@ -0,0 +1,19 @@ +// RUN: clang-cc -analyze -warn-dead-stores -verify %s && +// RUN: clang-cc -analyze -checker-cfref -analyzer-store=basic -analyzer-constraints=basic -warn-dead-stores -verify %s && +// RUN: clang-cc -analyze -checker-cfref -analyzer-store=basic -analyzer-constraints=range -warn-dead-stores -verify %s && +// RUN: clang-cc -analyze -checker-cfref -analyzer-store=region -analyzer-constraints=basic -warn-dead-stores -verify %s && +// RUN: clang-cc -analyze -checker-cfref -analyzer-store=region -analyzer-constraints=range -warn-dead-stores -verify %s + +int j; +void f1() { + int x = 4; + + ++x; // expected-warning{{never read}} + + switch (j) { + case 1: + throw 1; + (void)x; + break; + } +} diff --git a/test/Analysis/exercise-ps.c b/test/Analysis/exercise-ps.c index c309349..1e31b18 100644 --- a/test/Analysis/exercise-ps.c +++ b/test/Analysis/exercise-ps.c @@ -5,7 +5,7 @@ // (i.e., no assertions or crashes). -static const char * f1(const char *x, char *y) { +static void f1(const char *x, char *y) { while (*x != 0) { *y++ = *x++; } diff --git a/test/Analysis/misc-ps-basic-store.m b/test/Analysis/misc-ps-basic-store.m index 1207f86..c6ae20c 100644 --- a/test/Analysis/misc-ps-basic-store.m +++ b/test/Analysis/misc-ps-basic-store.m @@ -19,3 +19,17 @@ void checkaccess_union() { ).__i))) & 0xff00) >> 8) == 1) ret = 1; } + +// BasicStore handles this case incorrectly because it doesn't reason about +// the value pointed to by 'x' and thus creates different symbolic values +// at the declarations of 'a' and 'b' respectively. See the companion test +// in 'misc-ps-region-store.m'. +void test_trivial_symbolic_comparison_pointer_parameter(int *x) { + int a = *x; + int b = *x; + if (a != b) { + int *p = 0; + *p = 0xDEADBEEF; // expected-warning{{null}} + } +} + diff --git a/test/Analysis/misc-ps-region-store-i386.m b/test/Analysis/misc-ps-region-store-i386.m new file mode 100644 index 0000000..c2c4d5b --- /dev/null +++ b/test/Analysis/misc-ps-region-store-i386.m @@ -0,0 +1,14 @@ +// RUN: clang-cc -triple i386-apple-darwin9 -analyze -checker-cfref --analyzer-store=region --verify -fblocks %s + +// Here is a case where a pointer is treated as integer, invalidated as an +// integer, and then used again as a pointer. This test just makes sure +// we don't crash. +typedef unsigned uintptr_t; +void test_pointer_invalidated_as_int_aux(uintptr_t* ptr); +void test_pointer_invalidated_as_int() { + void *x; + test_pointer_invalidated_as_int_aux((uintptr_t*) &x); + // Here we have a pointer to integer cast. + uintptr_t y = (uintptr_t) x; +} + diff --git a/test/Analysis/misc-ps-region-store-x86_64.m b/test/Analysis/misc-ps-region-store-x86_64.m new file mode 100644 index 0000000..154ffaf --- /dev/null +++ b/test/Analysis/misc-ps-region-store-x86_64.m @@ -0,0 +1,14 @@ +// RUN: clang-cc -triple x86_64-apple-darwin9 -analyze -checker-cfref --analyzer-store=region --verify -fblocks %s + +// Here is a case where a pointer is treated as integer, invalidated as an +// integer, and then used again as a pointer. This test just makes sure +// we don't crash. +typedef unsigned long uintptr_t; +void test_pointer_invalidated_as_int_aux(uintptr_t* ptr); +void test_pointer_invalidated_as_int() { + void *x; + test_pointer_invalidated_as_int_aux((uintptr_t*) &x); + // Here we have a pointer to integer cast. + uintptr_t y = (uintptr_t) x; +} + diff --git a/test/Analysis/misc-ps-region-store.m b/test/Analysis/misc-ps-region-store.m index 8c8815e..e849042 100644 --- a/test/Analysis/misc-ps-region-store.m +++ b/test/Analysis/misc-ps-region-store.m @@ -1,4 +1,5 @@ -// RUN: clang-cc -analyze -checker-cfref --analyzer-store=region --verify -fblocks %s +// RUN: clang-cc -triple i386-apple-darwin9 -analyze -checker-cfref --analyzer-store=region --verify -fblocks %s && +// RUN: clang-cc -triple x86_64-apple-darwin9 -analyze -checker-cfref --analyzer-store=region --verify -fblocks %s typedef struct objc_selector *SEL; typedef signed char BOOL; @@ -31,10 +32,12 @@ extern NSString * const NSConnectionReplyMode; // PR 2948 (testcase; crash on VisitLValue for union types) // http://llvm.org/bugs/show_bug.cgi?id=2948 - void checkaccess_union() { int ret = 0, status; - if (((((__extension__ (((union { // expected-warning {{ Branch condition evaluates to an uninitialized value.}} + // Since RegionStore doesn't handle unions yet, + // this branch condition won't be triggered + // as involving an uninitialized value. + if (((((__extension__ (((union { // no-warning __typeof (status) __in; int __i;} ) { @@ -43,7 +46,6 @@ void checkaccess_union() { ret = 1; } - // Check our handling of fields being invalidated by function calls. struct test2_struct { int x; int y; char* s; }; void test2_helper(struct test2_struct* p); @@ -68,3 +70,236 @@ char test2() { return 'a'; } +// BasicStore handles this case incorrectly because it doesn't reason about +// the value pointed to by 'x' and thus creates different symbolic values +// at the declarations of 'a' and 'b' respectively. RegionStore handles +// it correctly. See the companion test in 'misc-ps-basic-store.m'. +void test_trivial_symbolic_comparison_pointer_parameter(int *x) { + int a = *x; + int b = *x; + if (a != b) { + int *p = 0; + *p = 0xDEADBEEF; // no-warning + } +} + +// This is a modified test from 'misc-ps.m'. Here we have the extra +// NULL dereferences which are pruned out by RegionStore's symbolic reasoning +// of fields. +typedef struct _BStruct { void *grue; } BStruct; +void testB_aux(void *ptr); + +void testB(BStruct *b) { + { + int *__gruep__ = ((int *)&((b)->grue)); + int __gruev__ = *__gruep__; + int __gruev2__ = *__gruep__; + if (__gruev__ != __gruev2__) { + int *p = 0; + *p = 0xDEADBEEF; // no-warning + } + + testB_aux(__gruep__); + } + { + int *__gruep__ = ((int *)&((b)->grue)); + int __gruev__ = *__gruep__; + int __gruev2__ = *__gruep__; + if (__gruev__ != __gruev2__) { + int *p = 0; + *p = 0xDEADBEEF; // no-warning + } + + if (~0 != __gruev__) {} + } +} + +void testB_2(BStruct *b) { + { + int **__gruep__ = ((int **)&((b)->grue)); + int *__gruev__ = *__gruep__; + testB_aux(__gruep__); + } + { + int **__gruep__ = ((int **)&((b)->grue)); + int *__gruev__ = *__gruep__; + if ((int*)~0 != __gruev__) {} + } +} + +// This test case is a reduced case of a caching bug discovered by an +// assertion failure in RegionStoreManager::BindArray. Essentially the +// DeclStmt is evaluated twice, but on the second loop iteration the +// engine caches out. Previously a false transition would cause UnknownVal +// to bind to the variable, firing an assertion failure. This bug was fixed +// in r76262. +void test_declstmt_caching() { +again: + { + const char a[] = "I like to crash"; + goto again; + } +} + +// Reduced test case from . +// Basically a null check is performed on the field value, which is then +// assigned to a variable and then checked again. +struct s_7114618 { int *p; }; +void test_rdar_7114618(struct s_7114618 *s) { + if (s->p) { + int *p = s->p; + if (!p) { + // Infeasible + int *dead = 0; + *dead = 0xDEADBEEF; // no-warning + } + } +} + +// Test pointers increment correctly. +void f() { + int a[2]; + a[1] = 3; + int *p = a; + p++; + if (*p != 3) { + int *q = 0; + *q = 3; // no-warning + } +} + +// +// Bit-fields of a struct should be invalidated when blasting the entire +// struct with an integer constant. +struct test_7185607 { + int x : 10; + int y : 22; +}; +int rdar_test_7185607() { + struct test_7185607 s; // Uninitialized. + *((unsigned *) &s) = 0U; + return s.x; // no-warning +} + +// [RegionStore] compound literal assignment with +// floats not honored +// This test case is mirrored in misc-ps.m, but this case is a negative. +typedef float CGFloat; +typedef struct _NSSize { + CGFloat width; + CGFloat height; +} NSSize; + +CGFloat rdar7242006_negative(CGFloat x) { + NSSize y; + return y.width; // expected-warning{{garbage}} +} + +// - Allow binding of values to symbolic regions. +// This test case shows how RegionStore tracks the value bound to 'x' +// after the assignment. +typedef int* ptr_rdar_7249340; +void rdar_7249340(ptr_rdar_7249340 x) { + *x = 1; + if (*x) + return; + int *p = 0; // This is unreachable. + *p = 0xDEADBEEF; // no-warning +} + +// - This test case tests both value tracking of +// array values and that we handle symbolic values that are casted +// between different integer types. Note the assignment 'n = *a++'; here +// 'n' is and 'int' and '*a' is 'unsigned'. Previously we got a false positive +// at 'x += *b++' (undefined value) because we got a false path. +int rdar_7249327_aux(void); + +void rdar_7249327(unsigned int A[2*32]) { + int B[2*32]; + int *b; + unsigned int *a; + int x = 0; + + int n; + + a = A; + b = B; + + n = *a++; + if (n) + *b++ = rdar_7249327_aux(); + + a = A; + b = B; + + n = *a++; + if (n) + x += *b++; // no-warning +} + +// - Check that 'x' is invalidated because its +// address is passed in as a value to a struct. +struct doodad_6914474 { int *v; }; +extern void prod_6914474(struct doodad_6914474 *d); +int rdar_6914474(void) { + int x; + struct doodad_6914474 d; + d.v = &x; + prod_6914474(&d); + return x; // no-warning +} + +// Test invalidation of a single field. +struct s_test_field_invalidate { + int x; +}; +extern void test_invalidate_field(int *x); +int test_invalidate_field_test() { + struct s_test_field_invalidate y; + test_invalidate_field(&y.x); + return y.x; // no-warning +} +int test_invalidate_field_test_positive() { + struct s_test_field_invalidate y; + return y.x; // expected-warning{{garbage}} +} + +// This test case illustrates how a typeless array of bytes casted to a +// struct should be treated as initialized. RemoveDeadBindings previously +// had a bug that caused 'x' to lose its default symbolic value after the +// assignment to 'p', thus causing 'p->z' to evaluate to "undefined". +struct ArrayWrapper { unsigned char y[16]; }; +struct WrappedStruct { unsigned z; }; + +int test_handle_array_wrapper() { + struct ArrayWrapper x; + test_handle_array_wrapper(&x); + struct WrappedStruct *p = (struct WrappedStruct*) x.y; + return p->z; // no-warning +} + +// [RegionStore] crash when +// handling load: '*((unsigned int *)"????")' +int rdar_7261075(void) { + unsigned int var = 0; + if (var == *((unsigned int *)"????")) + return 1; + return 0; +} + +// false path due to limited pointer +// arithmetic constraints +void rdar_7275774(void *data, unsigned n) { + if (!(data || n == 0)) + return; + + unsigned short *p = (unsigned short*) data; + unsigned short *q = p + (n / 2); + + if (p < q) { + // If we reach here, 'p' cannot be null. If 'p' is null, then 'n' must + // be '0', meaning that this branch is not feasible. + *p = *q; // no-warning + } +} + diff --git a/test/Analysis/misc-ps.m b/test/Analysis/misc-ps.m index ea41b5b..10e5823 100644 --- a/test/Analysis/misc-ps.m +++ b/test/Analysis/misc-ps.m @@ -1,24 +1,43 @@ -// RUN: clang-cc -analyze -checker-cfref --analyzer-store=basic -analyzer-constraints=basic --verify -fblocks %s && +// NOTE: Use '-fobjc-gc' to test the analysis being run twice, and multiple reports are not issued. +// RUN: clang-cc -analyze -checker-cfref --analyzer-store=basic -fobjc-gc -analyzer-constraints=basic --verify -fblocks %s && // RUN: clang-cc -analyze -checker-cfref --analyzer-store=basic -analyzer-constraints=range --verify -fblocks %s && // RUN: clang-cc -analyze -checker-cfref --analyzer-store=region -analyzer-constraints=basic --verify -fblocks %s && // RUN: clang-cc -analyze -checker-cfref --analyzer-store=region -analyzer-constraints=range --verify -fblocks %s +typedef struct objc_ivar *Ivar; typedef struct objc_selector *SEL; typedef signed char BOOL; typedef int NSInteger; typedef unsigned int NSUInteger; typedef struct _NSZone NSZone; -@class NSInvocation, NSMethodSignature, NSCoder, NSString, NSEnumerator; -@protocol NSObject - (BOOL)isEqual:(id)object; @end -@protocol NSCopying - (id)copyWithZone:(NSZone *)zone; @end +@class NSInvocation, NSArray, NSMethodSignature, NSCoder, NSString, NSEnumerator; +@protocol NSObject +- (BOOL)isEqual:(id)object; +- (id)autorelease; +@end +@protocol NSCopying +- (id)copyWithZone:(NSZone *)zone; +@end @protocol NSMutableCopying - (id)mutableCopyWithZone:(NSZone *)zone; @end -@protocol NSCoding - (void)encodeWithCoder:(NSCoder *)aCoder; @end -@interface NSObject {} - (id)init; @end +@protocol NSCoding +- (void)encodeWithCoder:(NSCoder *)aCoder; +@end +@interface NSObject {} +- (id)init; ++ (id)allocWithZone:(NSZone *)zone; +@end extern id NSAllocateObject(Class aClass, NSUInteger extraBytes, NSZone *zone); @interface NSString : NSObject - (NSUInteger)length; + (id)stringWithUTF8String:(const char *)nullTerminatedCString; @end extern NSString * const NSBundleDidLoadNotification; +@interface NSValue : NSObject +- (void)getValue:(void *)value; +@end +@interface NSNumber : NSValue +- (char)charValue; +- (id)initWithBool:(BOOL)value; +@end @interface NSAssertionHandler : NSObject {} + (NSAssertionHandler *)currentHandler; - (void)handleFailureInMethod:(SEL)selector object:(id)object file:(NSString *)fileName lineNumber:(NSInteger)line description:(NSString *)format,...; @@ -144,7 +163,7 @@ void pr3422() { } // PR 3543 (handle empty statement expressions) -int pr_3543(void) { +void pr_3543(void) { ({}); } @@ -295,4 +314,381 @@ void rdar_7027684(int x, int y) { (rdar_7027684_aux() ? rdar_7027684_aux_2() : (void) 0); } +// Test that we handle casts of string literals to arbitrary types. +unsigned const char *string_literal_test1() { + return (const unsigned char*) "hello"; +} + +const float *string_literal_test2() { + return (const float*) "hello"; +} + +// Test that we handle casts *from* incomplete struct types. +extern const struct _FooAssertStruct _cmd; +void test_cast_from_incomplete_struct_aux(volatile const void *x); +void test_cast_from_incomplete_struct() { + test_cast_from_incomplete_struct_aux(&_cmd); +} + +// Test for +// "ValueManager::makeIntVal(uint64_t X, QualType T) should return a 'Loc' +// when 'T' is a pointer" +// +// Previously this case would crash. +void test_rdar_7034511(NSArray *y) { + NSObject *x; + for (x in y) {} + if (x == ((void*) 0)) {} +} + +// Handle casts of function pointers (CodeTextRegions) to arbitrary pointer +// types. This was previously causing a crash in CastRegion. +void handle_funcptr_voidptr_casts() { + void **ptr; + typedef void *PVOID; + typedef void *PCHAR; + typedef long INT_PTR, *PINT_PTR; + typedef INT_PTR (*FARPROC)(); + FARPROC handle_funcptr_voidptr_casts_aux(); + PVOID handle_funcptr_voidptr_casts_aux_2(PVOID volatile *x); + PVOID handle_funcptr_voidptr_casts_aux_3(PCHAR volatile *x); + + ptr = (void**) handle_funcptr_voidptr_casts_aux(); + handle_funcptr_voidptr_casts_aux_2(ptr); + handle_funcptr_voidptr_casts_aux_3(ptr); +} + +// RegionStore::Retrieve previously crashed on this example. This example +// was previously in the test file 'xfail_regionstore_wine_crash.c'. +void testA() { + long x = 0; + char *y = (char *) &x; + if (!*y) + return; +} + +// RegionStoreManager previously crashed on this example. The problem is that +// the value bound to the field of b->grue after the call to testB_aux is +// a symbolic region. The second '*__gruep__' involves performing a load +// from a 'int*' that really is a 'void**'. The loaded location must be +// implicitly converted to an integer that wraps a location. Previosly we would +// get a crash here due to an assertion failure. +typedef struct _BStruct { void *grue; } BStruct; +void testB_aux(void *ptr); +void testB(BStruct *b) { + { + int *__gruep__ = ((int *)&((b)->grue)); + int __gruev__ = *__gruep__; + testB_aux(__gruep__); + } + { + int *__gruep__ = ((int *)&((b)->grue)); + int __gruev__ = *__gruep__; + if (~0 != __gruev__) {} + } +} + +void test_trivial_symbolic_comparison(int *x) { + int test_trivial_symbolic_comparison_aux(); + int a = test_trivial_symbolic_comparison_aux(); + int b = a; + if (a != b) { + int *p = 0; + *p = 0xDEADBEEF; // no-warning + } + + a = a == 1; + b = b == 1; + if (a != b) { + int *p = 0; + *p = 0xDEADBEEF; // no-warning + } +} + +// Test for: +// false positive null dereference due to +// BasicStoreManager not tracking *static* globals +// +// This just tests the proper tracking of symbolic values for globals (both +// static and non-static). +// +static int* x_rdar_7062158; +void rdar_7062158() { + int *current = x_rdar_7062158; + if (current == x_rdar_7062158) + return; + + int *p = 0; + *p = 0xDEADBEEF; // no-warning +} + +int* x_rdar_7062158_2; +void rdar_7062158_2() { + int *current = x_rdar_7062158_2; + if (current == x_rdar_7062158_2) + return; + + int *p = 0; + *p = 0xDEADBEEF; // no-warning +} + +// This test reproduces a case for a crash when analyzing ClamAV using +// RegionStoreManager (the crash doesn't exhibit in BasicStoreManager because +// it isn't doing anything smart about arrays). The problem is that on the +// second line, 'p = &p[i]', p is assigned an ElementRegion whose index +// is a 16-bit integer. On the third line, a new ElementRegion is created +// based on the previous region, but there the region uses a 32-bit integer, +// resulting in a clash of values (an assertion failure at best). We resolve +// this problem by implicitly converting index values to 'int' when the +// ElementRegion is created. +unsigned char test_array_index_bitwidth(const unsigned char *p) { + unsigned short i = 0; + for (i = 0; i < 2; i++) p = &p[i]; + return p[i+1]; +} + +// This case tests that CastRegion handles casts involving BlockPointerTypes. +// It should not crash. +void test_block_cast() { + id test_block_cast_aux(); + (void (^)(void *))test_block_cast_aux(); // expected-warning{{expression result unused}} +} + +// Test comparison of 'id' instance variable to a null void* constant after +// performing an OSAtomicCompareAndSwap32Barrier. +// This previously was a crash in RegionStoreManager. +@interface TestIdNull { + id x; +} +-(int)foo; +@end +@implementation TestIdNull +-(int)foo { + OSAtomicCompareAndSwap32Barrier(0, (signed)2, (signed*)&x); + if (x == (void*) 0) { return 0; } + return 1; +} +@end + +// PR 4594 - This was a crash when handling casts in SimpleSValuator. +void PR4594() { + char *buf[1]; + char **foo = buf; + *foo = "test"; +} + +// Test invalidation logic where an integer is casted to an array with a +// different sign and then invalidated. +void test_invalidate_cast_int() { + void test_invalidate_cast_int_aux(unsigned *i); + signed i; + test_invalidate_cast_int_aux((unsigned*) &i); + if (i < 0) + return; +} + +// Reduced from a crash involving the cast of an Objective-C symbolic region to +// 'char *' +static NSNumber *test_ivar_offset(id self, SEL _cmd, Ivar inIvar) { + return [[[NSNumber allocWithZone:((void*)0)] initWithBool:*(_Bool *)((char *)self + ivar_getOffset(inIvar))] autorelease]; +} + +// Reduced from a crash in StoreManager::CastRegion involving a divide-by-zero. +// This resulted from not properly handling region casts to 'const void*'. +void test_cast_const_voidptr() { + char x[10]; + char *p = &x[1]; + const void* q = p; +} + +// Reduced from a crash when analyzing Wine. This test handles loads from +// function addresses. +typedef long (*FARPROC)(); +FARPROC test_load_func(FARPROC origfun) { + if (!*(unsigned char*) origfun) + return origfun; + return 0; +} + +// Test passing-by-value an initialized struct variable. +struct test_pass_val { + int x; + int y; +}; +void test_pass_val_aux(struct test_pass_val s); +void test_pass_val() { + struct test_pass_val s; + s.x = 1; + s.y = 2; + test_pass_val_aux(s); +} + +// This is a reduced test case of a false positive that previously appeared +// in RegionStoreManager. Previously the array access resulted in dereferencing +// an undefined value. +int test_array_compound(int *q, int *r, int *z) { + int *array[] = { q, r, z }; + int j = 0; + for (unsigned i = 0; i < 3 ; ++i) + if (*array[i]) ++j; // no-warning + return j; +} + +// This test case previously crashed with -analyzer-store=basic because the +// symbolic value stored in 'x' wouldn't be implicitly casted to a signed value +// during the comparison. +int rdar_7124210(unsigned int x) { + enum { SOME_CONSTANT = 123 }; + int compare = ((signed) SOME_CONSTANT) == *((signed *) &x); + return compare ? 0 : 1; // Forces the evaluation of the symbolic constraint. +} + +void pr4781(unsigned long *raw1) { + unsigned long *cook, *raw0; + unsigned long dough[32]; + int i; + cook = dough; + for( i = 0; i < 16; i++, raw1++ ) { + raw0 = raw1++; + *cook = (*raw0 & 0x00fc0000L) << 6; + *cook |= (*raw0 & 0x00000fc0L) << 10; + } +} + +// - 'self' should be treated as being non-null +// upon entry to an objective-c method. +@interface RDar7185647 +- (id)foo; +@end +@implementation RDar7185647 +- (id) foo { + if (self) + return self; + *((int *) 0x0) = 0xDEADBEEF; // no-warning + return self; +} +@end + +// Test reasoning of __builtin_offsetof; +struct test_offsetof_A { + int x; + int y; +}; +struct test_offsetof_B { + int w; + int z; +}; +void test_offsetof_1() { + if (__builtin_offsetof(struct test_offsetof_A, x) == + __builtin_offsetof(struct test_offsetof_B, w)) + return; + int *p = 0; + *p = 0xDEADBEEF; // no-warning +} +void test_offsetof_2() { + if (__builtin_offsetof(struct test_offsetof_A, y) == + __builtin_offsetof(struct test_offsetof_B, z)) + return; + int *p = 0; + *p = 0xDEADBEEF; // no-warning +} +void test_offsetof_3() { + if (__builtin_offsetof(struct test_offsetof_A, y) - + __builtin_offsetof(struct test_offsetof_A, x) + == + __builtin_offsetof(struct test_offsetof_B, z) - + __builtin_offsetof(struct test_offsetof_B, w)) + return; + int *p = 0; + *p = 0xDEADBEEF; // no-warning +} +void test_offsetof_4() { + if (__builtin_offsetof(struct test_offsetof_A, y) == + __builtin_offsetof(struct test_offsetof_B, w)) + return; + int *p = 0; + *p = 0xDEADBEEF; // expected-warning{{Dereference of null pointer}} +} + +// "nil receiver" false positive: make tracking +// of the MemRegion for 'self' path-sensitive +@interface RDar6829164 : NSObject { + double x; int y; +} +- (id) init; +@end + +id rdar_6829164_1(); +double rdar_6829164_2(); + +@implementation RDar6829164 +- (id) init { + if((self = [super init]) != 0) { + id z = rdar_6829164_1(); + y = (z != 0); + if (y) + x = rdar_6829164_2(); + } + return self; +} +@end + +// - Invalidate values passed-by-reference +// to functions when the pointer to the value is passed as an integer. +void test_7242015_aux(unsigned long); +int rdar_7242015() { + int x; + test_7242015_aux((unsigned long) &x); // no-warning + return x; // Previously we return and uninitialized value when + // using RegionStore. +} + +// [RegionStore] compound literal assignment with +// floats not honored +CGFloat rdar7242006(CGFloat x) { + NSSize y = (NSSize){x, 10}; + return y.width; // no-warning +} + +// PR 4988 - This test exhibits a case where a function can be referenced +// when not explicitly used in an "lvalue" context (as far as the analyzer is +// concerned). This previously triggered a crash due to an invalid assertion. +void pr_4988(void) { + pr_4988; // expected-warning{{expression result unused}} +} + +// - A 'signed char' is used as a flag, which is +// implicitly converted to an int. +void *rdar7152418_bar(); +@interface RDar7152418 { + signed char x; +} +-(char)foo; +@end; +@implementation RDar7152418 +-(char)foo { + char *p = 0; + void *result = 0; + if (x) { + result = rdar7152418_bar(); + p = "hello"; + } + if (!result) { + result = rdar7152418_bar(); + if (result && x) + return *p; // no-warning + } + return 1; +} + +// Test constant-folding of symbolic values, automatically handling type +// conversions of the symbol as necessary. Previously this would crash +// once we started eagerly evaluating symbols whose values were constrained +// to a single value. +void test_constant_symbol(signed char x) { + while (1) { + if (x == ((signed char) 0)) {} + } +} + diff --git a/test/Analysis/nil-receiver-undefined-larger-than-voidptr-ret.m b/test/Analysis/nil-receiver-undefined-larger-than-voidptr-ret.m index 9a64b30..87faab6 100644 --- a/test/Analysis/nil-receiver-undefined-larger-than-voidptr-ret.m +++ b/test/Analysis/nil-receiver-undefined-larger-than-voidptr-ret.m @@ -1,4 +1,5 @@ -// RUN: clang-cc -triple i386-apple-darwin9 -analyze -checker-cfref -analyzer-constraints=basic -analyzer-store=basic %s -verify +// RUN: clang-cc -triple i386-apple-darwin9 -analyze -checker-cfref -analyzer-constraints=basic -analyzer-store=basic %s -verify && +// RUN: clang-cc -triple i386-apple-darwin9 -analyze -checker-cfref -analyzer-constraints=basic -analyzer-store=region %s -verify @interface MyClass {} - (void *)voidPtrM; diff --git a/test/Analysis/no-outofbounds.c b/test/Analysis/no-outofbounds.c new file mode 100644 index 0000000..9405280 --- /dev/null +++ b/test/Analysis/no-outofbounds.c @@ -0,0 +1,12 @@ +// RUN: clang-cc -checker-cfref -analyze -analyzer-store=basic -verify %s && +// RUN: clang-cc -checker-cfref -analyze -analyzer-store=region -verify %s + +//===----------------------------------------------------------------------===// +// This file tests cases where we should not flag out-of-bounds warnings. +//===----------------------------------------------------------------------===// + +void f() { + long x = 0; + char *y = (char*) &x; + char c = y[0] + y[1] + y[2]; // no-warning +} diff --git a/test/Analysis/null-deref-ps.c b/test/Analysis/null-deref-ps.c index 6e20741..f37b441 100644 --- a/test/Analysis/null-deref-ps.c +++ b/test/Analysis/null-deref-ps.c @@ -1,10 +1,16 @@ -// RUN: clang-cc -analyze -std=gnu99 -checker-cfref -verify %s -analyzer-constraints=basic -analyzer-store=basic && -// RUN: clang-cc -analyze -std=gnu99 -checker-cfref -verify %s -analyzer-constraints=range -analyzer-store=basic && -// RUN: clang-cc -analyze -std=gnu99 -checker-cfref -analyzer-store=region -analyzer-constraints=range -analyzer-purge-dead=false -verify %s && -// RUN: clang-cc -analyze -std=gnu99 -checker-cfref -analyzer-store=region -analyzer-constraints=range -verify %s +// RUN: clang-cc -triple i386-apple-darwin10 -analyze -std=gnu99 -checker-cfref -verify %s -analyzer-constraints=basic -analyzer-store=basic && +// RUN: clang-cc -triple i386-apple-darwin10 -analyze -std=gnu99 -checker-cfref -verify %s -analyzer-constraints=range -analyzer-store=basic && +// RUN: clang-cc -triple i386-apple-darwin10 -analyze -std=gnu99 -checker-cfref -analyzer-store=region -analyzer-constraints=range -analyzer-purge-dead=false -verify %s && +// RUN: clang-cc -triple i386-apple-darwin10 -analyze -std=gnu99 -checker-cfref -analyzer-store=region -analyzer-constraints=range -verify %s -#include -#include +typedef unsigned uintptr_t; + +extern void __assert_fail (__const char *__assertion, __const char *__file, + unsigned int __line, __const char *__function) + __attribute__ ((__noreturn__)); + +#define assert(expr) \ + ((expr) ? (void)(0) : __assert_fail (#expr, __FILE__, __LINE__, __func__)) void f1(int *p) { if (p) *p = 1; @@ -72,6 +78,7 @@ int f4_b() { else return; // expected-warning {{non-void function 'f4_b' should return a value}} *p += 10; // expected-warning{{Dereference of null pointer}} + return 0; } @@ -102,6 +109,15 @@ int f6c(int *p, int *q) { : bar3(p, 2, q); // no-warning } +void f6d(int *p) { + bar(p, 0); + // At this point, 'p' cannot be null. + if (!p) { + int *q = 0; + *q = 0xDEADBEEF; // no-warning + } +} + int* qux(); int f7(int x) { @@ -160,7 +176,7 @@ int* f7c2(int *x) { } -int f8(int *p, int *q) { +void f8(int *p, int *q) { if (!p) if (p) *p = 1; // no-warning @@ -262,4 +278,13 @@ void f13() { if (((((int) x) << 2) + 1) >> 1) *x = 1; // no-warning } +// PR 4759 - Attribute non-null checking by the analyzer was not correctly +// handling pointer values that were undefined. +void pr4759_aux(int *p) __attribute__((nonnull)); + +void pr4759() { + int *p; + pr4759_aux(p); // expected-warning{{undefined}} +} + diff --git a/test/Analysis/outofbound.c b/test/Analysis/outofbound.c index 527a311..568f143 100644 --- a/test/Analysis/outofbound.c +++ b/test/Analysis/outofbound.c @@ -1,4 +1,5 @@ // RUN: clang-cc -analyze -checker-cfref -analyzer-store=region -verify %s +// XFAIL char f1() { char* s = "abcd"; diff --git a/test/Analysis/pr4209.m b/test/Analysis/pr4209.m index 7d7d8fc..991d0d6 100644 --- a/test/Analysis/pr4209.m +++ b/test/Analysis/pr4209.m @@ -1,4 +1,4 @@ -// RUN: clang-cc -triple i386-apple-darwin9 -analyze -checker-cfref -verify %s && +// RUN: clang-cc -triple i386-apple-darwin9 -analyze -checker-cfref -analyzer-store=basic -verify %s && // RUN: clang-cc -triple i386-apple-darwin9 -analyze -checker-cfref -analyzer-store=region -verify %s // This test case was crashing due to how CFRefCount.cpp resolved the @@ -56,6 +56,7 @@ CMProfileLocation; - (GSEbayCategory *) parent; - (GSEbayCategory*) subcategoryWithID:(int) inID; @end @implementation GBCategoryChooserPanelController + (int) chooseCategoryIDFromCategories:(NSArray*) inCategories searchRequest:(GBSearchRequest*)inRequest parentWindow:(NSWindow*) inParent { + return 0; } - (void) addCategory:(EBayCategoryType*)inCategory toRootTreeCategory:(NSMutableArray*)inRootTreeCategories { GSEbayCategory *category = [rootCategory subcategoryWithID:[[inCategory categoryID] intValue]]; diff --git a/test/Analysis/rdar-6442306-1.m b/test/Analysis/rdar-6442306-1.m index 15d3498..bfda115 100644 --- a/test/Analysis/rdar-6442306-1.m +++ b/test/Analysis/rdar-6442306-1.m @@ -28,4 +28,5 @@ __Beeble_check__Request__SetPortalSize_t(__attribute__((__unused__)) __Request__ } while (0); } + return 0; } diff --git a/test/Analysis/rdar-6540084.m b/test/Analysis/rdar-6540084.m index 18ab038..cfe5220 100644 --- a/test/Analysis/rdar-6540084.m +++ b/test/Analysis/rdar-6540084.m @@ -32,5 +32,6 @@ typedef struct {} TazVersion; } } } + while (1) {} } @end diff --git a/test/Analysis/rdar-6541136-region.c b/test/Analysis/rdar-6541136-region.c index 1e7a2d9..e2779e8 100644 --- a/test/Analysis/rdar-6541136-region.c +++ b/test/Analysis/rdar-6541136-region.c @@ -13,7 +13,10 @@ void foo( void ) struct load_wine *cmd = (void*) &wonky[1]; cmd = cmd; char *p = (void*) &wonky[1]; - *p = 1; + *p = 1; // no-warning kernel_tea_cheese_t *q = &wonky[1]; - kernel_tea_cheese_t r = *q; // expected-warning{{out-of-bound memory position}} + // This test case tests both the RegionStore logic (doesn't crash) and + // the out-of-bounds checking. We don't expect the warning for now since + // out-of-bound checking is temporarily disabled. + kernel_tea_cheese_t r = *q; // eventually-warning{{out-of-bound memory position}} } diff --git a/test/Analysis/rdar-6562655.m b/test/Analysis/rdar-6562655.m index 581d6ea..3c1c281 100644 --- a/test/Analysis/rdar-6562655.m +++ b/test/Analysis/rdar-6562655.m @@ -1,4 +1,5 @@ -// RUN: clang-cc -analyze -checker-cfref -analyzer-constraints=basic -analyzer-store=basic -verify %s +// RUN: clang-cc -analyze -checker-cfref -analyzer-constraints=basic -analyzer-store=basic -verify %s && +// RUN: clang-cc -analyze -checker-cfref -analyzer-constraints=basic -analyzer-store=region -verify %s // // This test case mainly checks that the retain/release checker doesn't crash // on this file. @@ -51,7 +52,7 @@ typedef struct _NSRunArrayItem { @end @implementation Bar static Baz Qux = 0; -- (id)copyWithZone:(NSZone *)zone {} +- (id)copyWithZone:(NSZone *)zone { return 0; } - (void)encodeWithCoder:(NSCoder *)coder {} @end @implementation Bar (BarBotnet) @@ -59,5 +60,6 @@ static Baz Qux = 0; if (!(*(BarAuxiliary **)&self->_support)->auxCFlags.botnetIsSet) { _cFlags.botnet = [self _initialBotnetZorg]; } + while (1) {} } @end diff --git a/test/Analysis/rdar-6600344-nil-receiver-undefined-struct-ret.m b/test/Analysis/rdar-6600344-nil-receiver-undefined-struct-ret.m index 5d1fa37..49ef7c3 100644 --- a/test/Analysis/rdar-6600344-nil-receiver-undefined-struct-ret.m +++ b/test/Analysis/rdar-6600344-nil-receiver-undefined-struct-ret.m @@ -1,4 +1,5 @@ -// RUN: clang-cc -analyze -checker-cfref -analyzer-constraints=basic -analyzer-store=basic %s -verify +// RUN: clang-cc -analyze -checker-cfref -analyzer-constraints=basic -analyzer-store=basic %s -verify && +// RUN: clang-cc -analyze -checker-cfref -analyzer-constraints=basic -analyzer-store=region %s -verify typedef struct Foo { int x; } Bar; diff --git a/test/Analysis/rdar-7168531.m b/test/Analysis/rdar-7168531.m new file mode 100644 index 0000000..bdbd22d --- /dev/null +++ b/test/Analysis/rdar-7168531.m @@ -0,0 +1,19 @@ +// RUN: clang-cc -analyze -checker-cfref -triple i386-apple-darwin10 -analyzer-store=region && +// RUN: clang-cc -analyze -checker-cfref -triple i386-apple-darwin10 -analyzer-store=basic + +// Note that the target triple is important for this test case. It specifies that we use the +// fragile Objective-C ABI. + +@interface Foo { + int x; +} +@end + +@implementation Foo +static Foo* bar(Foo *p) { + if (p->x) + return ++p; // This is only valid for the fragile ABI. + + return p; +} +@end diff --git a/test/Analysis/region-1.m b/test/Analysis/region-1.m index ed172e4..68a375b 100644 --- a/test/Analysis/region-1.m +++ b/test/Analysis/region-1.m @@ -79,6 +79,7 @@ typedef NSUInteger JabaSourceLanguage; Dos_CharacterRangeType = 0, Dos_LineRangeType = 1 } DosTextRangeType; @implementation JabaSCSharedDiagramViewController + (NSImage *)findImageNamed:(NSString *)name { + return 0; } - (void)revealSourceInEditor:(JabasectItem *)sectItem duperGesture:(BOOL)duperGesture { id selectedElement = [sectItem representedObject]; diff --git a/test/Analysis/region-only-test.c b/test/Analysis/region-only-test.c index 64d3fcd..8908adb 100644 --- a/test/Analysis/region-only-test.c +++ b/test/Analysis/region-only-test.c @@ -9,5 +9,5 @@ void foo(int* p) { if (p[0] == 1) x = &a; if (p[0] == 1) - *x; // no-warning + (void)*x; // no-warning } diff --git a/test/Analysis/retain-release-gc-only.m b/test/Analysis/retain-release-gc-only.m index ec33a57..2833b02 100644 --- a/test/Analysis/retain-release-gc-only.m +++ b/test/Analysis/retain-release-gc-only.m @@ -1,16 +1,26 @@ -// RUN: clang-cc -analyze -checker-cfref -verify -fobjc-gc-only %s && +// RUN: clang-cc -analyze -checker-cfref -analyzer-store=basic -verify -fobjc-gc-only %s && // RUN: clang-cc -analyze -checker-cfref -analyzer-store=region -fobjc-gc-only -verify %s //===----------------------------------------------------------------------===// // Header stuff. //===----------------------------------------------------------------------===// -typedef struct objc_class *Class; - typedef unsigned int __darwin_natural_t; -typedef struct {} div_t; -typedef unsigned long UInt32; +typedef unsigned long uintptr_t; +typedef unsigned int uint32_t; +typedef unsigned long long uint64_t; +typedef unsigned int UInt32; typedef signed long CFIndex; +typedef struct { + CFIndex location; + CFIndex length; +} CFRange; +static __inline__ __attribute__((always_inline)) CFRange CFRangeMake(CFIndex loc, CFIndex len) { + CFRange range; + range.location = loc; + range.length = len; + return range; +} typedef const void * CFTypeRef; typedef const struct __CFString * CFStringRef; typedef const struct __CFAllocator * CFAllocatorRef; @@ -26,7 +36,17 @@ typedef struct __CFArray * CFMutableArrayRef; extern CFMutableArrayRef CFArrayCreateMutable(CFAllocatorRef allocator, CFIndex capacity, const CFArrayCallBacks *callBacks); extern const void *CFArrayGetValueAtIndex(CFArrayRef theArray, CFIndex idx); extern void CFArrayAppendValue(CFMutableArrayRef theArray, const void *value); +typedef struct { +} +CFDictionaryKeyCallBacks; +extern const CFDictionaryKeyCallBacks kCFTypeDictionaryKeyCallBacks; +typedef struct { +} +CFDictionaryValueCallBacks; +extern const CFDictionaryValueCallBacks kCFTypeDictionaryValueCallBacks; typedef const struct __CFDictionary * CFDictionaryRef; +typedef struct __CFDictionary * CFMutableDictionaryRef; +extern CFMutableDictionaryRef CFDictionaryCreateMutable(CFAllocatorRef allocator, CFIndex capacity, const CFDictionaryKeyCallBacks *keyCallBacks, const CFDictionaryValueCallBacks *valueCallBacks); typedef UInt32 CFStringEncoding; enum { kCFStringEncodingMacRoman = 0, kCFStringEncodingWindowsLatin1 = 0x0500, kCFStringEncodingISOLatin1 = 0x0201, kCFStringEncodingNextStepLatin = 0x0B01, kCFStringEncodingASCII = 0x0600, kCFStringEncodingUnicode = 0x0100, kCFStringEncodingUTF8 = 0x08000100, kCFStringEncodingNonLossyASCII = 0x0BFF , kCFStringEncodingUTF16 = 0x0100, kCFStringEncodingUTF16BE = 0x10000100, kCFStringEncodingUTF16LE = 0x14000100, kCFStringEncodingUTF32 = 0x0c000100, kCFStringEncodingUTF32BE = 0x18000100, kCFStringEncodingUTF32LE = 0x1c000100 }; @@ -40,44 +60,96 @@ extern CFAbsoluteTime CFDateGetAbsoluteTime(CFDateRef theDate); typedef __darwin_natural_t natural_t; typedef natural_t mach_port_name_t; typedef mach_port_name_t mach_port_t; -typedef struct { -} -CFRunLoopObserverContext; +typedef int kern_return_t; +typedef kern_return_t mach_error_t; +enum { +kCFNumberSInt8Type = 1, kCFNumberSInt16Type = 2, kCFNumberSInt32Type = 3, kCFNumberSInt64Type = 4, kCFNumberFloat32Type = 5, kCFNumberFloat64Type = 6, kCFNumberCharType = 7, kCFNumberShortType = 8, kCFNumberIntType = 9, kCFNumberLongType = 10, kCFNumberLongLongType = 11, kCFNumberFloatType = 12, kCFNumberDoubleType = 13, kCFNumberCFIndexType = 14, kCFNumberNSIntegerType = 15, kCFNumberCGFloatType = 16, kCFNumberMaxType = 16 }; +typedef CFIndex CFNumberType; +typedef const struct __CFNumber * CFNumberRef; +extern CFNumberRef CFNumberCreate(CFAllocatorRef allocator, CFNumberType theType, const void *valuePtr); +typedef const struct __CFAttributedString *CFAttributedStringRef; +typedef struct __CFAttributedString *CFMutableAttributedStringRef; +extern CFAttributedStringRef CFAttributedStringCreate(CFAllocatorRef alloc, CFStringRef str, CFDictionaryRef attributes) ; +extern CFMutableAttributedStringRef CFAttributedStringCreateMutableCopy(CFAllocatorRef alloc, CFIndex maxLength, CFAttributedStringRef aStr) ; +extern void CFAttributedStringSetAttribute(CFMutableAttributedStringRef aStr, CFRange range, CFStringRef attrName, CFTypeRef value) ; typedef signed char BOOL; -typedef unsigned int NSUInteger; +typedef unsigned long NSUInteger; @class NSString, Protocol; extern void NSLog(NSString *format, ...) __attribute__((format(__NSString__, 1, 2))); typedef struct _NSZone NSZone; @class NSInvocation, NSMethodSignature, NSCoder, NSString, NSEnumerator; -@protocol NSObject - (BOOL)isEqual:(id)object; +@protocol NSObject +- (BOOL)isEqual:(id)object; - (id)retain; - (oneway void)release; - (id)autorelease; +- (Class)class; @end @protocol NSCopying - (id)copyWithZone:(NSZone *)zone; @end @protocol NSMutableCopying - (id)mutableCopyWithZone:(NSZone *)zone; @end @protocol NSCoding - (void)encodeWithCoder:(NSCoder *)aCoder; @end @interface NSObject {} -- (Class)class; -+ (id)alloc; + (id)allocWithZone:(NSZone *)zone; -@end typedef float CGFloat; ++ (id)alloc; +- (void)dealloc; +@end +@interface NSObject (NSCoderMethods) +- (id)awakeAfterUsingCoder:(NSCoder *)aDecoder; +@end +extern id NSAllocateObject(Class aClass, NSUInteger extraBytes, NSZone *zone); +typedef struct { +} +NSFastEnumerationState; +@protocol NSFastEnumeration - (NSUInteger)countByEnumeratingWithState:(NSFastEnumerationState *)state objects:(id *)stackbuf count:(NSUInteger)len; +@end @class NSString, NSDictionary; +@interface NSValue : NSObject - (void)getValue:(void *)value; +@end @interface NSNumber : NSValue - (char)charValue; +- (id)initWithInt:(int)value; +@end @class NSString; +@interface NSArray : NSObject - (NSUInteger)count; +@end @interface NSArray (NSArrayCreation) + (id)array; +@end @interface NSAutoreleasePool : NSObject { +} +- (void)drain; +@end extern NSString * const NSBundleDidLoadNotification; +typedef double NSTimeInterval; +@interface NSDate : NSObject - (NSTimeInterval)timeIntervalSinceReferenceDate; +@end typedef unsigned short unichar; @interface NSString : NSObject - (NSUInteger)length; -- (const char *)UTF8String; +- ( const char *)UTF8String; - (id)initWithUTF8String:(const char *)nullTerminatedCString; + (id)stringWithUTF8String:(const char *)nullTerminatedCString; -- (id)init; -- (void)dealloc; -@end extern NSString * const NSCurrentLocaleDidChangeNotification ; -@protocol NSLocking - (void)lock; -@end extern NSString * const NSUndoManagerCheckpointNotification; -typedef enum { -ACL_READ_DATA = (1<<1), ACL_LIST_DIRECTORY = (1<<1), ACL_WRITE_DATA = (1<<2), ACL_ADD_FILE = (1<<2), ACL_EXECUTE = (1<<3), ACL_SEARCH = (1<<3), ACL_DELETE = (1<<4), ACL_APPEND_DATA = (1<<5), ACL_ADD_SUBDIRECTORY = (1<<5), ACL_DELETE_CHILD = (1<<6), ACL_READ_ATTRIBUTES = (1<<7), ACL_WRITE_ATTRIBUTES = (1<<8), ACL_READ_EXTATTRIBUTES = (1<<9), ACL_WRITE_EXTATTRIBUTES = (1<<10), ACL_READ_SECURITY = (1<<11), ACL_WRITE_SECURITY = (1<<12), ACL_CHANGE_OWNER = (1<<13) } -acl_entry_id_t; -typedef int kern_return_t; -typedef kern_return_t mach_error_t; +@end @class NSString, NSURL, NSError; +@interface NSData : NSObject - (NSUInteger)length; ++ (id)dataWithBytesNoCopy:(void *)bytes length:(NSUInteger)length; ++ (id)dataWithBytesNoCopy:(void *)bytes length:(NSUInteger)length freeWhenDone:(BOOL)b; +@end @class NSLocale, NSDate, NSCalendar, NSTimeZone, NSError, NSArray, NSMutableDictionary; +@interface NSDictionary : NSObject - (NSUInteger)count; +@end @interface NSMutableDictionary : NSDictionary - (void)removeObjectForKey:(id)aKey; +- (void)setObject:(id)anObject forKey:(id)aKey; +@end @interface NSMutableDictionary (NSMutableDictionaryCreation) + (id)dictionaryWithCapacity:(NSUInteger)numItems; +@end typedef double CGFloat; +struct CGSize { +}; +typedef struct CGSize CGSize; +struct CGRect { +}; +typedef struct CGRect CGRect; typedef mach_port_t io_object_t; +typedef char io_name_t[128]; +typedef io_object_t io_iterator_t; typedef io_object_t io_service_t; +typedef struct IONotificationPort * IONotificationPortRef; +typedef void (*IOServiceMatchingCallback)( void * refcon, io_iterator_t iterator ); +io_service_t IOServiceGetMatchingService( mach_port_t masterPort, CFDictionaryRef matching ); +kern_return_t IOServiceGetMatchingServices( mach_port_t masterPort, CFDictionaryRef matching, io_iterator_t * existing ); +kern_return_t IOServiceAddNotification( mach_port_t masterPort, const io_name_t notificationType, CFDictionaryRef matching, mach_port_t wakePort, uintptr_t reference, io_iterator_t * notification ) __attribute__((deprecated)); +kern_return_t IOServiceAddMatchingNotification( IONotificationPortRef notifyPort, const io_name_t notificationType, CFDictionaryRef matching, IOServiceMatchingCallback callback, void * refCon, io_iterator_t * notification ); +CFMutableDictionaryRef IOServiceMatching( const char * name ); +CFMutableDictionaryRef IOServiceNameMatching( const char * name ); +CFMutableDictionaryRef IOBSDNameMatching( mach_port_t masterPort, uint32_t options, const char * bsdName ); +CFMutableDictionaryRef IOOpenFirmwarePathMatching( mach_port_t masterPort, uint32_t options, const char * path ); +CFMutableDictionaryRef IORegistryEntryIDMatching( uint64_t entryID ); typedef struct __DASession * DASessionRef; extern DASessionRef DASessionCreate( CFAllocatorRef allocator ); typedef struct __DADisk * DADiskRef; @@ -85,23 +157,62 @@ extern DADiskRef DADiskCreateFromBSDName( CFAllocatorRef allocator, DASessionRef extern DADiskRef DADiskCreateFromIOMedia( CFAllocatorRef allocator, DASessionRef session, io_service_t media ); extern CFDictionaryRef DADiskCopyDescription( DADiskRef disk ); extern DADiskRef DADiskCopyWholeDisk( DADiskRef disk ); +@interface NSTask : NSObject - (id)init; +@end typedef struct CGColorSpace *CGColorSpaceRef; +typedef struct CGImage *CGImageRef; +typedef struct CGLayer *CGLayerRef; @interface NSResponder : NSObject { } -@end @class NSColor, NSFont, NSNotification; -typedef struct __CFlags { +@end @protocol NSAnimatablePropertyContainer - (id)animator; +@end extern NSString *NSAnimationTriggerOrderIn ; +@interface NSView : NSResponder { } -_CFlags; +@end @protocol NSValidatedUserInterfaceItem - (SEL)action; +@end @protocol NSUserInterfaceValidations - (BOOL)validateUserInterfaceItem:(id )anItem; +@end @class NSDate, NSDictionary, NSError, NSException, NSNotification; +@interface NSApplication : NSResponder { +} +@end enum { +NSTerminateCancel = 0, NSTerminateNow = 1, NSTerminateLater = 2 }; +typedef NSUInteger NSApplicationTerminateReply; +@protocol NSApplicationDelegate @optional - (NSApplicationTerminateReply)applicationShouldTerminate:(NSApplication *)sender; +@end @class NSAttributedString, NSEvent, NSFont, NSFormatter, NSImage, NSMenu, NSText, NSView, NSTextView; @interface NSCell : NSObject { } -@end @class NSDate, NSDictionary, NSError, NSException, NSNotification; -@interface NSManagedObjectContext : NSObject { +@end @class NSTextField, NSPanel, NSArray, NSWindow, NSImage, NSButton, NSError; +typedef struct { +} +CVTimeStamp; +@interface CIImage : NSObject { } -@end enum { +typedef int CIFormat; +@end enum { kDAReturnSuccess = 0, kDAReturnError = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x01, kDAReturnBusy = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x02, kDAReturnBadArgument = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x03, kDAReturnExclusiveAccess = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x04, kDAReturnNoResources = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x05, kDAReturnNotFound = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x06, kDAReturnNotMounted = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x07, kDAReturnNotPermitted = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x08, kDAReturnNotPrivileged = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x09, kDAReturnNotReady = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x0A, kDAReturnNotWritable = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x0B, kDAReturnUnsupported = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x0C }; typedef mach_error_t DAReturn; typedef const struct __DADissenter * DADissenterRef; extern DADissenterRef DADissenterCreate( CFAllocatorRef allocator, DAReturn status, CFStringRef string ); - +@interface CIContext: NSObject { +} +- (CGImageRef)createCGImage:(CIImage *)im fromRect:(CGRect)r; +- (CGImageRef)createCGImage:(CIImage *)im fromRect:(CGRect)r format:(CIFormat)f colorSpace:(CGColorSpaceRef)cs; +- (CGLayerRef)createCGLayerWithSize:(CGSize)size info:(CFDictionaryRef)d; +@end extern NSString* const QCRendererEventKey; +@protocol QCCompositionRenderer - (NSDictionary*) attributes; +@end @interface QCRenderer : NSObject { +} +- (id) createSnapshotImageOfType:(NSString*)type; +@end extern NSString* const QCViewDidStartRenderingNotification; +@interface QCView : NSView { +} +- (id) createSnapshotImageOfType:(NSString*)type; +@end enum { +ICEXIFOrientation1 = 1, ICEXIFOrientation2 = 2, ICEXIFOrientation3 = 3, ICEXIFOrientation4 = 4, ICEXIFOrientation5 = 5, ICEXIFOrientation6 = 6, ICEXIFOrientation7 = 7, ICEXIFOrientation8 = 8, }; +@class ICDevice; +@protocol ICDeviceDelegate @required - (void)didRemoveDevice:(ICDevice*)device; +@end extern NSString *const ICScannerStatusWarmingUp; +@class ICScannerDevice; +@protocol ICScannerDeviceDelegate @optional - (void)scannerDeviceDidBecomeAvailable:(ICScannerDevice*)scanner; +@end CFTypeRef CFMakeCollectable(CFTypeRef cf) ; static __inline__ __attribute__((always_inline)) id NSMakeCollectable(CFTypeRef @@ -198,6 +309,19 @@ void f5b() { @end //===----------------------------------------------------------------------===// +// 'ciContext createCGImage:outputImage fromRect:' returns a retained CF object (not GC'ed)//===----------------------------------------------------------------------===// +//===----------------------------------------------------------------------===// + +void rdar_7174400(QCView *view, QCRenderer *renderer, CIContext *context, + NSString *str, CIImage *img, CGRect rect, + CIFormat form, CGColorSpaceRef cs) { + [view createSnapshotImageOfType:str]; // no-warning + [renderer createSnapshotImageOfType:str]; // no-warning + [context createCGImage:img fromRect:rect]; // expected-warning{{leak}} + [context createCGImage:img fromRect:rect format:form colorSpace:cs]; // expected-warning{{leak}} +} + +//===----------------------------------------------------------------------===// // Tests of ownership attributes. //===----------------------------------------------------------------------===// diff --git a/test/Analysis/retain-release-region-store.m b/test/Analysis/retain-release-region-store.m index 66950e2..7a69683 100644 --- a/test/Analysis/retain-release-region-store.m +++ b/test/Analysis/retain-release-region-store.m @@ -1,4 +1,5 @@ // RUN: clang-cc -analyze -checker-cfref -analyzer-store=region -verify %s +// XFAIL //===----------------------------------------------------------------------===// // The following code is reduced using delta-debugging from @@ -115,4 +116,27 @@ CFAbsoluteTime f4() { } @end +//===----------------------------------------------------------------------===// +// - False positive due to not invalidating the +// reference count of a tracked region that was itself invalidated. +//===----------------------------------------------------------------------===// + +typedef struct __rdar_7257223 { CFDateRef x; } RDar7257223; +void rdar_7257223_aux(RDar7257223 *p); + +// THIS CASE CURRENTLY FAILS. +CFDateRef rdar7257223_Create(void) { + RDar7257223 s; + CFAbsoluteTime t = CFAbsoluteTimeGetCurrent(); + s.x = CFDateCreate(0, t); // no-warning + rdar_7257223_aux(&s); + return s.x; +} + +CFDateRef rdar7257223_Create_2(void) { + RDar7257223 s; + CFAbsoluteTime t = CFAbsoluteTimeGetCurrent(); + s.x = CFDateCreate(0, t); // no-warning + return s.x; +} diff --git a/test/Analysis/retain-release.m b/test/Analysis/retain-release.m index da0ae80..7076bb2 100644 --- a/test/Analysis/retain-release.m +++ b/test/Analysis/retain-release.m @@ -1,6 +1,12 @@ -//>>SLICER -// RUN: clang-cc -analyze -checker-cfref -verify %s && -// RUN: clang-cc -analyze -checker-cfref -analyzer-store=region -verify %s +// RUN: clang-cc -triple x86_64-apple-darwin10 -analyze -checker-cfref -analyzer-store=basic -verify %s && +// RUN: clang-cc -triple x86_64-apple-darwin10 -analyze -checker-cfref -analyzer-store=region -verify %s + +#if __has_feature(attribute_ns_returns_retained) +#define NS_RETURNS_RETAINED __attribute__((ns_returns_retained)) +#endif +#if __has_feature(attribute_cf_returns_retained) +#define CF_RETURNS_RETAINED __attribute__((cf_returns_retained)) +#endif //===----------------------------------------------------------------------===// // The following code is reduced using delta-debugging from Mac OS X headers: @@ -21,6 +27,16 @@ typedef unsigned int uint32_t; typedef unsigned long long uint64_t; typedef unsigned int UInt32; typedef signed long CFIndex; +typedef struct { + CFIndex location; + CFIndex length; +} CFRange; +static __inline__ __attribute__((always_inline)) CFRange CFRangeMake(CFIndex loc, CFIndex len) { + CFRange range; + range.location = loc; + range.length = len; + return range; +} typedef const void * CFTypeRef; typedef const struct __CFString * CFStringRef; typedef const struct __CFAllocator * CFAllocatorRef; @@ -36,8 +52,17 @@ typedef struct __CFArray * CFMutableArrayRef; extern CFMutableArrayRef CFArrayCreateMutable(CFAllocatorRef allocator, CFIndex capacity, const CFArrayCallBacks *callBacks); extern const void *CFArrayGetValueAtIndex(CFArrayRef theArray, CFIndex idx); extern void CFArrayAppendValue(CFMutableArrayRef theArray, const void *value); +typedef struct { +} +CFDictionaryKeyCallBacks; +extern const CFDictionaryKeyCallBacks kCFTypeDictionaryKeyCallBacks; +typedef struct { +} +CFDictionaryValueCallBacks; +extern const CFDictionaryValueCallBacks kCFTypeDictionaryValueCallBacks; typedef const struct __CFDictionary * CFDictionaryRef; typedef struct __CFDictionary * CFMutableDictionaryRef; +extern CFMutableDictionaryRef CFDictionaryCreateMutable(CFAllocatorRef allocator, CFIndex capacity, const CFDictionaryKeyCallBacks *keyCallBacks, const CFDictionaryValueCallBacks *valueCallBacks); typedef UInt32 CFStringEncoding; enum { kCFStringEncodingMacRoman = 0, kCFStringEncodingWindowsLatin1 = 0x0500, kCFStringEncodingISOLatin1 = 0x0201, kCFStringEncodingNextStepLatin = 0x0B01, kCFStringEncodingASCII = 0x0600, kCFStringEncodingUnicode = 0x0100, kCFStringEncodingUTF8 = 0x08000100, kCFStringEncodingNonLossyASCII = 0x0BFF , kCFStringEncodingUTF16 = 0x0100, kCFStringEncodingUTF16BE = 0x10000100, kCFStringEncodingUTF16LE = 0x14000100, kCFStringEncodingUTF32 = 0x0c000100, kCFStringEncodingUTF32BE = 0x18000100, kCFStringEncodingUTF32LE = 0x1c000100 }; @@ -53,29 +78,48 @@ typedef natural_t mach_port_name_t; typedef mach_port_name_t mach_port_t; typedef int kern_return_t; typedef kern_return_t mach_error_t; +enum { +kCFNumberSInt8Type = 1, kCFNumberSInt16Type = 2, kCFNumberSInt32Type = 3, kCFNumberSInt64Type = 4, kCFNumberFloat32Type = 5, kCFNumberFloat64Type = 6, kCFNumberCharType = 7, kCFNumberShortType = 8, kCFNumberIntType = 9, kCFNumberLongType = 10, kCFNumberLongLongType = 11, kCFNumberFloatType = 12, kCFNumberDoubleType = 13, kCFNumberCFIndexType = 14, kCFNumberNSIntegerType = 15, kCFNumberCGFloatType = 16, kCFNumberMaxType = 16 }; +typedef CFIndex CFNumberType; +typedef const struct __CFNumber * CFNumberRef; +extern CFNumberRef CFNumberCreate(CFAllocatorRef allocator, CFNumberType theType, const void *valuePtr); +typedef const struct __CFAttributedString *CFAttributedStringRef; +typedef struct __CFAttributedString *CFMutableAttributedStringRef; +extern CFAttributedStringRef CFAttributedStringCreate(CFAllocatorRef alloc, CFStringRef str, CFDictionaryRef attributes) ; +extern CFMutableAttributedStringRef CFAttributedStringCreateMutableCopy(CFAllocatorRef alloc, CFIndex maxLength, CFAttributedStringRef aStr) ; +extern void CFAttributedStringSetAttribute(CFMutableAttributedStringRef aStr, CFRange range, CFStringRef attrName, CFTypeRef value) ; typedef signed char BOOL; typedef unsigned long NSUInteger; @class NSString, Protocol; extern void NSLog(NSString *format, ...) __attribute__((format(__NSString__, 1, 2))); typedef struct _NSZone NSZone; @class NSInvocation, NSMethodSignature, NSCoder, NSString, NSEnumerator; -@protocol NSObject - (BOOL)isEqual:(id)object; +@protocol NSObject +- (BOOL)isEqual:(id)object; - (id)retain; - (oneway void)release; - (id)autorelease; @end @protocol NSCopying - (id)copyWithZone:(NSZone *)zone; @end @protocol NSMutableCopying - (id)mutableCopyWithZone:(NSZone *)zone; @end @protocol NSCoding - (void)encodeWithCoder:(NSCoder *)aCoder; -@end @interface NSObject { -} +@end +@interface NSObject {} + (id)allocWithZone:(NSZone *)zone; + (id)alloc; - (void)dealloc; -@end extern id NSAllocateObject(Class aClass, NSUInteger extraBytes, NSZone *zone); +@end +@interface NSObject (NSCoderMethods) +- (id)awakeAfterUsingCoder:(NSCoder *)aDecoder; +@end +extern id NSAllocateObject(Class aClass, NSUInteger extraBytes, NSZone *zone); typedef struct { } NSFastEnumerationState; @protocol NSFastEnumeration - (NSUInteger)countByEnumeratingWithState:(NSFastEnumerationState *)state objects:(id *)stackbuf count:(NSUInteger)len; +@end @class NSString, NSDictionary; +@interface NSValue : NSObject - (void)getValue:(void *)value; +@end @interface NSNumber : NSValue - (char)charValue; +- (id)initWithInt:(int)value; @end @class NSString; @interface NSArray : NSObject - (NSUInteger)count; @end @interface NSArray (NSArrayCreation) + (id)array; @@ -90,11 +134,11 @@ typedef double NSTimeInterval; - ( const char *)UTF8String; - (id)initWithUTF8String:(const char *)nullTerminatedCString; + (id)stringWithUTF8String:(const char *)nullTerminatedCString; -@end @class NSString, NSData; +@end @class NSString, NSURL, NSError; @interface NSData : NSObject - (NSUInteger)length; + (id)dataWithBytesNoCopy:(void *)bytes length:(NSUInteger)length; + (id)dataWithBytesNoCopy:(void *)bytes length:(NSUInteger)length freeWhenDone:(BOOL)b; -@end @class NSString; +@end @class NSLocale, NSDate, NSCalendar, NSTimeZone, NSError, NSArray, NSMutableDictionary; @interface NSDictionary : NSObject - (NSUInteger)count; @end @interface NSMutableDictionary : NSDictionary - (void)removeObjectForKey:(id)aKey; - (void)setObject:(id)anObject forKey:(id)aKey; @@ -106,9 +150,6 @@ typedef struct CGSize CGSize; struct CGRect { }; typedef struct CGRect CGRect; -@protocol NSLocking - (void)lock; -- (id)init; -@end @class NSURLAuthenticationChallenge; typedef mach_port_t io_object_t; typedef char io_name_t[128]; typedef io_object_t io_iterator_t; @@ -131,37 +172,32 @@ extern DADiskRef DADiskCreateFromBSDName( CFAllocatorRef allocator, DASessionRef extern DADiskRef DADiskCreateFromIOMedia( CFAllocatorRef allocator, DASessionRef session, io_service_t media ); extern CFDictionaryRef DADiskCopyDescription( DADiskRef disk ); extern DADiskRef DADiskCopyWholeDisk( DADiskRef disk ); -typedef struct CGColorSpace *CGColorSpaceRef; +@interface NSTask : NSObject - (id)init; +@end typedef struct CGColorSpace *CGColorSpaceRef; typedef struct CGImage *CGImageRef; - typedef struct CGLayer *CGLayerRef; - @class NSArray, NSError, NSEvent, NSMenu, NSUndoManager, NSWindow; +typedef struct CGLayer *CGLayerRef; @interface NSResponder : NSObject { } @end @protocol NSAnimatablePropertyContainer - (id)animator; @end extern NSString *NSAnimationTriggerOrderIn ; @interface NSView : NSResponder { -struct __VFlags2 { -} -_vFlags2; -} -@end extern NSString * const NSFullScreenModeAllScreens; -@protocol NSChangeSpelling - (void)changeSpelling:(id)sender; -@end @protocol NSIgnoreMisspelledWords - (void)ignoreSpelling:(id)sender; -@end @class NSColor, NSFont, NSNotification; -@interface NSText : NSView { } @end @protocol NSValidatedUserInterfaceItem - (SEL)action; @end @protocol NSUserInterfaceValidations - (BOOL)validateUserInterfaceItem:(id )anItem; -@end @class NSArray, NSError, NSImage, NSView, NSNotificationCenter, NSURL, NSScreen, NSRunningApplication; +@end @class NSDate, NSDictionary, NSError, NSException, NSNotification; @interface NSApplication : NSResponder { } @end enum { NSTerminateCancel = 0, NSTerminateNow = 1, NSTerminateLater = 2 }; typedef NSUInteger NSApplicationTerminateReply; @protocol NSApplicationDelegate @optional - (NSApplicationTerminateReply)applicationShouldTerminate:(NSApplication *)sender; -@end enum { +@end @class NSAttributedString, NSEvent, NSFont, NSFormatter, NSImage, NSMenu, NSText, NSView, NSTextView; +@interface NSCell : NSObject { } -_CFlags; +@end @class NSTextField, NSPanel, NSArray, NSWindow, NSImage, NSButton, NSError; +typedef struct { +} +CVTimeStamp; @interface CIImage : NSObject { } typedef int CIFormat; @@ -175,7 +211,7 @@ extern DADissenterRef DADissenterCreate( CFAllocatorRef allocator, DAReturn stat - (CGImageRef)createCGImage:(CIImage *)im fromRect:(CGRect)r; - (CGImageRef)createCGImage:(CIImage *)im fromRect:(CGRect)r format:(CIFormat)f colorSpace:(CGColorSpaceRef)cs; - (CGLayerRef)createCGLayerWithSize:(CGSize)size info:(CFDictionaryRef)d; -@end @class NSURL; +@end extern NSString* const QCRendererEventKey; @protocol QCCompositionRenderer - (NSDictionary*) attributes; @end @interface QCRenderer : NSObject { } @@ -188,11 +224,34 @@ extern DADissenterRef DADissenterCreate( CFAllocatorRef allocator, DAReturn stat ICEXIFOrientation1 = 1, ICEXIFOrientation2 = 2, ICEXIFOrientation3 = 3, ICEXIFOrientation4 = 4, ICEXIFOrientation5 = 5, ICEXIFOrientation6 = 6, ICEXIFOrientation7 = 7, ICEXIFOrientation8 = 8, }; @class ICDevice; @protocol ICDeviceDelegate @required - (void)didRemoveDevice:(ICDevice*)device; -@end @class ICCameraDevice; +@end extern NSString *const ICScannerStatusWarmingUp; @class ICScannerDevice; @protocol ICScannerDeviceDelegate @optional - (void)scannerDeviceDidBecomeAvailable:(ICScannerDevice*)scanner; @end - + +typedef long unsigned int __darwin_size_t; +typedef __darwin_size_t size_t; +typedef unsigned long CFTypeID; +struct CGPoint { + CGFloat x; + CGFloat y; +}; +typedef struct CGPoint CGPoint; +typedef struct CGGradient *CGGradientRef; +typedef uint32_t CGGradientDrawingOptions; +extern CFTypeID CGGradientGetTypeID(void); +extern CGGradientRef CGGradientCreateWithColorComponents(CGColorSpaceRef + space, const CGFloat components[], const CGFloat locations[], size_t count); +extern CGGradientRef CGGradientCreateWithColors(CGColorSpaceRef space, + CFArrayRef colors, const CGFloat locations[]); +extern CGGradientRef CGGradientRetain(CGGradientRef gradient); +extern void CGGradientRelease(CGGradientRef gradient); +typedef struct CGContext *CGContextRef; +extern void CGContextDrawLinearGradient(CGContextRef context, + CGGradientRef gradient, CGPoint startPoint, CGPoint endPoint, + CGGradientDrawingOptions options); +extern CGColorSpaceRef CGColorSpaceCreateDeviceRGB(void); + //===----------------------------------------------------------------------===// // Test cases. //===----------------------------------------------------------------------===// @@ -371,6 +430,7 @@ CFMutableArrayRef f13_autorelease_d() { [(id) A autorelease]; CFMutableArrayRef B = CFArrayCreateMutable(0, 10, &kCFTypeArrayCallBacks); // expected-warning{{Object sent -autorelease too many times}} CFRelease(B); // no-warning + while (1) {} } @@ -389,6 +449,18 @@ void f15() { CFRelease(*B); // no-warning } +// Test when we pass NULL to CFRetain/CFRelease. +void f16(int x, CFTypeRef p) { + if (p) + return; + + if (x) { + CFRelease(p); // expected-warning{{Null pointer argument in call to CFRelease}} + } + else { + CFRetain(p); // expected-warning{{Null pointer argument in call to CFRetain}} + } +} // Test basic tracking of ivars associated with 'self'. For the retain/release // checker we currently do not want to flag leaks associated with stores @@ -559,7 +631,7 @@ void rdar6704930(unsigned char *s, unsigned int length) { int rdar_6257780_Case1() { NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; NSArray *array = [NSArray array]; - [array release]; // expected-warning{{Incorrect decrement of the reference count of an object is not owned at this point by the caller}} + [array release]; // expected-warning{{Incorrect decrement of the reference count of an object that is not owned at this point by the caller}} [pool drain]; return 0; } @@ -603,7 +675,8 @@ typedef CFTypeRef OtherRef; @end //===----------------------------------------------------------------------===// -// false positive - init method returns an object owned by caller +// false positive - init method returns an object +// owned by caller //===----------------------------------------------------------------------===// @interface RDar6320065 : NSObject { @@ -646,7 +719,21 @@ int RDar6320065_test() { } //===----------------------------------------------------------------------===// -// [NSData dataWithBytesNoCopy] does not return a retained object +// -awakeAfterUsingCoder: returns an owned object +// and claims the receiver +//===----------------------------------------------------------------------===// + +@interface RDar7129086 : NSObject {} @end +@implementation RDar7129086 +- (id)awakeAfterUsingCoder:(NSCoder *)aDecoder { + [self release]; // no-warning + return [NSString alloc]; // no-warning +} +@end + +//===----------------------------------------------------------------------===// +// [NSData dataWithBytesNoCopy] does not return a +// retained object //===----------------------------------------------------------------------===// @interface RDar6859457 : NSObject {} @@ -750,7 +837,7 @@ void IOServiceNameMatching_wrapper(const char * name) { IOServiceNameMatching(name); // expected-warning{{leak}} } -__attribute__((cf_returns_retained)) CFDictionaryRef CreateDict(); +CF_RETURNS_RETAINED CFDictionaryRef CreateDict(); void IOServiceAddNotification_wrapper(mach_port_t masterPort, const io_name_t notificationType, mach_port_t wakePort, uintptr_t reference, io_iterator_t * notification ) { @@ -791,19 +878,241 @@ void IOServiceAddMatchingNotification_wrapper(IONotificationPortRef notifyPort, } //===----------------------------------------------------------------------===// +// Test of handling objects whose references "escape" to containers. +//===----------------------------------------------------------------------===// + +// +void rdar_6539791(CFMutableDictionaryRef y, void* key, void* val_key) { + CFMutableDictionaryRef x = CFDictionaryCreateMutable(kCFAllocatorDefault, 1, &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks); + CFDictionaryAddValue(y, key, x); + CFRelease(x); // the dictionary keeps a reference, so the object isn't deallocated yet + signed z = 1; + CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &z); + if (value) { + CFDictionaryAddValue(x, val_key, value); // no-warning + CFRelease(value); + CFDictionaryAddValue(y, val_key, value); // no-warning + } +} + +// +// Same issue, except with "AppendValue" functions. +void rdar_6560661(CFMutableArrayRef x) { + signed z = 1; + CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &z); + // CFArrayAppendValue keeps a reference to value. + CFArrayAppendValue(x, value); + CFRelease(value); + CFRetain(value); + CFRelease(value); // no-warning +} + +// +// Same issue, excwept with "CFAttributeStringSetAttribute". +void rdar_7152619(CFStringRef str) { + CFAttributedStringRef string = CFAttributedStringCreate(kCFAllocatorDefault, str, 0); + CFMutableAttributedStringRef attrString = CFAttributedStringCreateMutableCopy(kCFAllocatorDefault, 100, string); + CFRelease(string); + NSNumber *number = [[NSNumber alloc] initWithInt:5]; // expected-warning{{leak}} + CFAttributedStringSetAttribute(attrString, CFRangeMake(0, 1), str, number); + [number release]; + [number retain]; + CFRelease(attrString); +} + +//===----------------------------------------------------------------------===// +// Test of handling CGGradientXXX functions. +//===----------------------------------------------------------------------===// + +void rdar_7184450(CGContextRef myContext, CGFloat x, CGPoint myStartPoint, + CGPoint myEndPoint) { + size_t num_locations = 6; + CGFloat locations[6] = { 0.0, 0.265, 0.28, 0.31, 0.36, 1.0 }; + CGFloat components[28] = { 239.0/256.0, 167.0/256.0, 170.0/256.0, + x, // Start color + 207.0/255.0, 39.0/255.0, 39.0/255.0, x, + 147.0/255.0, 21.0/255.0, 22.0/255.0, x, + 175.0/255.0, 175.0/255.0, 175.0/255.0, x, + 255.0/255.0,255.0/255.0, 255.0/255.0, x, + 255.0/255.0,255.0/255.0, 255.0/255.0, x + }; // End color + + CGGradientRef myGradient = + CGGradientCreateWithColorComponents(CGColorSpaceCreateDeviceRGB(), // expected-warning{{leak}} + components, locations, num_locations); + + CGContextDrawLinearGradient(myContext, myGradient, myStartPoint, myEndPoint, + 0); + CGGradientRelease(myGradient); +} + +void rdar_7184450_pos(CGContextRef myContext, CGFloat x, CGPoint myStartPoint, + CGPoint myEndPoint) { + size_t num_locations = 6; + CGFloat locations[6] = { 0.0, 0.265, 0.28, 0.31, 0.36, 1.0 }; + CGFloat components[28] = { 239.0/256.0, 167.0/256.0, 170.0/256.0, + x, // Start color + 207.0/255.0, 39.0/255.0, 39.0/255.0, x, + 147.0/255.0, 21.0/255.0, 22.0/255.0, x, + 175.0/255.0, 175.0/255.0, 175.0/255.0, x, + 255.0/255.0,255.0/255.0, 255.0/255.0, x, + 255.0/255.0,255.0/255.0, 255.0/255.0, x + }; // End color + + CGGradientRef myGradient = + CGGradientCreateWithColorComponents(CGColorSpaceCreateDeviceRGB(), components, locations, num_locations); // expected-warning 2 {{leak}} + + CGContextDrawLinearGradient(myContext, myGradient, myStartPoint, myEndPoint, + 0); +} + +//===----------------------------------------------------------------------===// +// clang false positive: retained instance passed to +// thread in pthread_create marked as leak +// +// Until we have full IPA, the analyzer should stop tracking the reference +// count of objects passed to pthread_create. +// +//===----------------------------------------------------------------------===// + +struct _opaque_pthread_t {}; +struct _opaque_pthread_attr_t {}; +typedef struct _opaque_pthread_t *__darwin_pthread_t; +typedef struct _opaque_pthread_attr_t __darwin_pthread_attr_t; +typedef __darwin_pthread_t pthread_t; +typedef __darwin_pthread_attr_t pthread_attr_t; + +int pthread_create(pthread_t * restrict, const pthread_attr_t * restrict, + void *(*)(void *), void * restrict); + +void *rdar_7299394_start_routine(void *p) { + [((id) p) release]; + return 0; +} +void rdar_7299394(pthread_attr_t *attr, pthread_t *thread, void *args) { + NSNumber *number = [[NSNumber alloc] initWithInt:5]; // no-warning + pthread_create(thread, attr, rdar_7299394_start_routine, number); +} +void rdar_7299394_positive(pthread_attr_t *attr, pthread_t *thread) { + NSNumber *number = [[NSNumber alloc] initWithInt:5]; // expected-warning{{leak}} +} + +//===----------------------------------------------------------------------===// +// False leak associated with call to +// CVPixelBufferCreateWithBytes () +// +// According to the Core Video Reference (ADC), CVPixelBufferCreateWithBytes and +// CVPixelBufferCreateWithPlanarBytes can release (via a callback) the +// pixel buffer object. These test cases show how the analyzer stops tracking +// the reference count for the objects passed for this argument. This +// could be made smarter. +//===----------------------------------------------------------------------===// + +typedef int int32_t; +typedef UInt32 FourCharCode; +typedef FourCharCode OSType; +typedef uint64_t CVOptionFlags; +typedef int32_t CVReturn; +typedef struct __CVBuffer *CVBufferRef; +typedef CVBufferRef CVImageBufferRef; +typedef CVImageBufferRef CVPixelBufferRef; +typedef void (*CVPixelBufferReleaseBytesCallback)( void *releaseRefCon, const void *baseAddress ); + +extern CVReturn CVPixelBufferCreateWithBytes(CFAllocatorRef allocator, + size_t width, + size_t height, + OSType pixelFormatType, + void *baseAddress, + size_t bytesPerRow, + CVPixelBufferReleaseBytesCallback releaseCallback, + void *releaseRefCon, + CFDictionaryRef pixelBufferAttributes, + CVPixelBufferRef *pixelBufferOut) ; + +typedef void (*CVPixelBufferReleasePlanarBytesCallback)( void *releaseRefCon, const void *dataPtr, size_t dataSize, size_t numberOfPlanes, const void *planeAddresses[] ); + +extern CVReturn CVPixelBufferCreateWithPlanarBytes(CFAllocatorRef allocator, + size_t width, + size_t height, + OSType pixelFormatType, + void *dataPtr, + size_t dataSize, + size_t numberOfPlanes, + void *planeBaseAddress[], + size_t planeWidth[], + size_t planeHeight[], + size_t planeBytesPerRow[], + CVPixelBufferReleasePlanarBytesCallback releaseCallback, + void *releaseRefCon, + CFDictionaryRef pixelBufferAttributes, + CVPixelBufferRef *pixelBufferOut) ; + +extern CVReturn CVPixelBufferCreateWithBytes(CFAllocatorRef allocator, + size_t width, + size_t height, + OSType pixelFormatType, + void *baseAddress, + size_t bytesPerRow, + CVPixelBufferReleaseBytesCallback releaseCallback, + void *releaseRefCon, + CFDictionaryRef pixelBufferAttributes, + CVPixelBufferRef *pixelBufferOut) ; + +CVReturn rdar_7283567(CFAllocatorRef allocator, size_t width, size_t height, + OSType pixelFormatType, void *baseAddress, + size_t bytesPerRow, + CVPixelBufferReleaseBytesCallback releaseCallback, + CFDictionaryRef pixelBufferAttributes, + CVPixelBufferRef *pixelBufferOut) { + + // For the allocated object, it doesn't really matter what type it is + // for the purpose of this test. All we want to show is that + // this is freed later by the callback. + NSNumber *number = [[NSNumber alloc] initWithInt:5]; // no-warning + + return CVPixelBufferCreateWithBytes(allocator, width, height, pixelFormatType, + baseAddress, bytesPerRow, releaseCallback, + number, // potentially released by callback + pixelBufferAttributes, pixelBufferOut) ; +} + +CVReturn rdar_7283567_2(CFAllocatorRef allocator, size_t width, size_t height, + OSType pixelFormatType, void *dataPtr, size_t dataSize, + size_t numberOfPlanes, void *planeBaseAddress[], + size_t planeWidth[], size_t planeHeight[], size_t planeBytesPerRow[], + CVPixelBufferReleasePlanarBytesCallback releaseCallback, + CFDictionaryRef pixelBufferAttributes, + CVPixelBufferRef *pixelBufferOut) { + + // For the allocated object, it doesn't really matter what type it is + // for the purpose of this test. All we want to show is that + // this is freed later by the callback. + NSNumber *number = [[NSNumber alloc] initWithInt:5]; // no-warning + + return CVPixelBufferCreateWithPlanarBytes(allocator, + width, height, pixelFormatType, dataPtr, dataSize, + numberOfPlanes, planeBaseAddress, planeWidth, + planeHeight, planeBytesPerRow, releaseCallback, + number, // potentially released by callback + pixelBufferAttributes, pixelBufferOut) ; +} + +//===----------------------------------------------------------------------===// // Tests of ownership attributes. //===----------------------------------------------------------------------===// typedef NSString* MyStringTy; +@protocol FooP; + @interface TestOwnershipAttr : NSObject -- (NSString*) returnsAnOwnedString __attribute__((ns_returns_retained)); // no-warning -- (NSString*) returnsAnOwnedCFString __attribute__((cf_returns_retained)); // no-warning -- (MyStringTy) returnsAnOwnedTypedString __attribute__((ns_returns_retained)); // no-warning -- (int) returnsAnOwnedInt __attribute__((ns_returns_retained)); // expected-warning{{'ns_returns_retained' attribute only applies to functions or methods that return a pointer or Objective-C object}} +- (NSString*) returnsAnOwnedString NS_RETURNS_RETAINED; // no-warning +- (NSString*) returnsAnOwnedCFString CF_RETURNS_RETAINED; // no-warning +- (MyStringTy) returnsAnOwnedTypedString NS_RETURNS_RETAINED; // no-warning +- (int) returnsAnOwnedInt NS_RETURNS_RETAINED; // expected-warning{{'ns_returns_retained' attribute only applies to functions or methods that return a pointer or Objective-C object}} @end -static int ownership_attribute_doesnt_go_here __attribute__((ns_returns_retained)); // expected-warning{{'ns_returns_retained' attribute only applies to function or method types}} +static int ownership_attribute_doesnt_go_here NS_RETURNS_RETAINED; // expected-warning{{'ns_returns_retained' attribute only applies to function or method types}} void test_attr_1(TestOwnershipAttr *X) { NSString *str = [X returnsAnOwnedString]; // expected-warning{{leak}} @@ -814,12 +1123,14 @@ void test_attr_1b(TestOwnershipAttr *X) { } @interface MyClassTestCFAttr : NSObject {} -- (NSDate*) returnsCFRetained __attribute__((cf_returns_retained)); +- (NSDate*) returnsCFRetained CF_RETURNS_RETAINED; +- (CFDateRef) returnsCFRetainedAsCF CF_RETURNS_RETAINED; - (NSDate*) alsoReturnsRetained; -- (NSDate*) returnsNSRetained __attribute__((ns_returns_retained)); +- (CFDateRef) alsoReturnsRetainedAsCF; +- (NSDate*) returnsNSRetained NS_RETURNS_RETAINED; @end -__attribute__((cf_returns_retained)) +CF_RETURNS_RETAINED CFDateRef returnsRetainedCFDate() { return CFDateCreate(0, CFAbsoluteTimeGetCurrent()); } @@ -829,14 +1140,58 @@ CFDateRef returnsRetainedCFDate() { return (NSDate*) returnsRetainedCFDate(); // No leak. } +- (CFDateRef) returnsCFRetainedAsCF { + return returnsRetainedCFDate(); // No leak. +} + + - (NSDate*) alsoReturnsRetained { return (NSDate*) returnsRetainedCFDate(); // expected-warning{{leak}} } +- (CFDateRef) alsoReturnsRetainedAsCF { + return returnsRetainedCFDate(); // expected-warning{{leak}} +} + + - (NSDate*) returnsNSRetained { return (NSDate*) returnsRetainedCFDate(); // no-warning } @end +//===----------------------------------------------------------------------===// +// Test that leaks post-dominated by "panic" functions are not reported. +// +// do not report a leak when post-dominated by a call +// to a noreturn or panic function +//===----------------------------------------------------------------------===// + +void panic() __attribute__((noreturn)); + +void test_panic_negative() { + signed z = 1; + CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &z); // expected-warning{{leak}} +} + +void test_panic_positive() { + signed z = 1; + CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &z); // no-warning + panic(); +} +void test_panic_neg_2(int x) { + signed z = 1; + CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &z); // expected-warning{{leak}} + if (x) + panic(); +} + +void test_panic_pos_2(int x) { + signed z = 1; + CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &z); // no-warning + if (x) + panic(); + if (!x) + panic(); +} diff --git a/test/Analysis/security-syntax-checks.m b/test/Analysis/security-syntax-checks.m new file mode 100644 index 0000000..ebd7d17 --- /dev/null +++ b/test/Analysis/security-syntax-checks.m @@ -0,0 +1,91 @@ +// RUN: clang-cc -triple i386-apple-darwin10 -analyze -warn-security-syntactic %s -verify + +// rule request: floating point used as loop +// condition (FLP30-C, FLP-30-CPP) +// +// For reference: https://www.securecoding.cert.org/confluence/display/seccode/FLP30-C.+Do+not+use+floating+point+variables+as+loop+counters +// +void test_float_condition() { + for (float x = 0.1f; x <= 1.0f; x += 0.1f) {} // expected-warning{{Variable 'x' with floating point type 'float'}} + for (float x = 100000001.0f; x <= 100000010.0f; x += 1.0f) {} // expected-warning{{Variable 'x' with floating point type 'float'}} + for (float x = 100000001.0f; x <= 100000010.0f; x++ ) {} // expected-warning{{Variable 'x' with floating point type 'float'}} + for (double x = 100000001.0; x <= 100000010.0; x++ ) {} // expected-warning{{Variable 'x' with floating point type 'double'}} + for (double x = 100000001.0; ((x)) <= 100000010.0; ((x))++ ) {} // expected-warning{{Variable 'x' with floating point type 'double'}} + + for (double x = 100000001.0; 100000010.0 >= x; x = x + 1.0 ) {} // expected-warning{{Variable 'x' with floating point type 'double'}} + + int i = 0; + for (double x = 100000001.0; ((x)) <= 100000010.0; ((x))++, ++i ) {} // expected-warning{{Variable 'x' with floating point type 'double'}} + + typedef float FooType; + for (FooType x = 100000001.0f; x <= 100000010.0f; x++ ) {} // expected-warning{{Variable 'x' with floating point type 'FooType'}} +} + +// rule request: gets() buffer overflow +// Part of recommendation: 300-BSI (buildsecurityin.us-cert.gov) +char* gets(char *buf); + +void test_gets() { + char buff[1024]; + gets(buff); // expected-warning{{Call to function 'gets' is extremely insecure as it can always result in a buffer overflow}} +} + +// CWE-273: Failure to Check Whether Privileges Were +// Dropped Successfully +typedef unsigned int __uint32_t; +typedef __uint32_t __darwin_uid_t; +typedef __uint32_t __darwin_gid_t; +typedef __darwin_uid_t uid_t; +typedef __darwin_gid_t gid_t; +int setuid(uid_t); +int setregid(gid_t, gid_t); +int setreuid(uid_t, uid_t); +extern void check(int); + +void test_setuid() +{ + setuid(2); // expected-warning{{The return value from the call to 'setuid' is not checked. If an error occurs in 'setuid', the following code may execute with unexpected privileges}} + setuid(0); // expected-warning{{The return value from the call to 'setuid' is not checked. If an error occurs in 'setuid', the following code may execute with unexpected privileges}} + if (setuid (2) != 0) + abort(); + + // Currently the 'setuid' check is not flow-sensitive, and only looks + // at whether the function was called in a compound statement. This + // will lead to false negatives, but there should be no false positives. + int t = setuid(2); // no-warning + (void)setuid (2); // no-warning + + check(setuid (2)); // no-warning + + setreuid(2,2); // expected-warning{{The return value from the call to 'setreuid' is not checked. If an error occurs in 'setreuid', the following code may execute with unexpected privileges}} + setregid(2,2); // expected-warning{{The return value from the call to 'setregid' is not checked. If an error occurs in 'setregid', the following code may execute with unexpected privileges}} +} + +// CWE-338: Use of cryptographically weak prng +int rand(void); +double drand48(void); +double erand48(unsigned short[3]); +long jrand48(unsigned short[3]); +void lcong48(unsigned short[7]); +long lrand48(void); +long mrand48(void); +long nrand48(unsigned short[3]); +long random(void); +int rand_r(unsigned *); + +void test_rand() +{ + unsigned short a[7]; + unsigned b; + + rand(); // expected-warning{{Function 'rand' is obsolete because it implements a poor random number generator. Use 'arc4random' instead}} + drand48(); // expected-warning{{Function 'drand48' is obsolete because it implements a poor random number generator. Use 'arc4random' instead}} + erand48(a); // expected-warning{{Function 'erand48' is obsolete because it implements a poor random number generator. Use 'arc4random' instead}} + jrand48(a); // expected-warning{{Function 'jrand48' is obsolete because it implements a poor random number generator. Use 'arc4random' instead}} + lcong48(a); // expected-warning{{Function 'lcong48' is obsolete because it implements a poor random number generator. Use 'arc4random' instead}} + lrand48(); // expected-warning{{Function 'lrand48' is obsolete because it implements a poor random number generator. Use 'arc4random' instead}} + mrand48(); // expected-warning{{Function 'mrand48' is obsolete because it implements a poor random number generator. Use 'arc4random' instead}} + nrand48(a); // expected-warning{{Function 'nrand48' is obsolete because it implements a poor random number generator. Use 'arc4random' instead}} + rand_r(&b); // expected-warning{{Function 'rand_r' is obsolete because it implements a poor random number generator. Use 'arc4random' instead}} + random(); // expected-warning{{The 'random' function produces a sequence of values that an adversary may be able to predict. Use 'arc4random' instead}} +} diff --git a/test/Analysis/uninit-vals-ps-region.c b/test/Analysis/uninit-vals-ps-region.c index 32f787d..1561f11 100644 --- a/test/Analysis/uninit-vals-ps-region.c +++ b/test/Analysis/uninit-vals-ps-region.c @@ -15,3 +15,21 @@ void f4() { if (global.data == 0) // When the true branch is feasible 'a = 3'. g(a); // no-warning } + + +// Test uninitialized value due to part of the structure being uninitialized. +struct TestUninit { int x; int y; }; +struct TestUninit test_uninit_aux(); +void test_uninit_pos() { + struct TestUninit v1 = { 0, 0 }; + struct TestUninit v2 = test_uninit_aux(); + int z; + v1.y = z; + test_unit_aux2(v2.x + v1.y); // expected-warning{{The right operand of '+' is a garbage value}} +} +void test_uninit_neg() { + struct TestUninit v1 = { 0, 0 }; + struct TestUninit v2 = test_uninit_aux(); + test_unit_aux2(v2.x + v1.y); // no-warning +} + diff --git a/test/Analysis/uninit-vals-ps.c b/test/Analysis/uninit-vals-ps.c index 4177126..759c7ed 100644 --- a/test/Analysis/uninit-vals-ps.c +++ b/test/Analysis/uninit-vals-ps.c @@ -1,4 +1,4 @@ -// RUN: clang-cc -analyze -checker-cfref -verify %s && +// RUN: clang-cc -analyze -checker-cfref -analyzer-store=basic -verify %s && // RUN: clang-cc -analyze -checker-cfref -analyzer-store=region -verify %s struct FPRec { @@ -22,7 +22,7 @@ int f2() { int x; - if (x+1) // expected-warning{{Branch}} + if (x+1) // expected-warning{{The left operand of '+' is a garbage value}} return 1; return 2; @@ -31,13 +31,13 @@ int f2() { int f2_b() { int x; - return ((x+1)+2+((x))) + 1 ? 1 : 2; // expected-warning{{Branch}} + return ((1+x)+2+((x))) + 1 ? 1 : 2; // expected-warning{{The right operand of '+' is a garbage value}} } int f3(void) { int i; int *p = &i; - if (*p > 0) // expected-warning{{Branch condition evaluates to an uninitialized value}} + if (*p > 0) // expected-warning{{The left operand of '>' is a garbage value}} return 0; else return 1; @@ -61,7 +61,7 @@ int f5(void) { int ret_uninit() { int i; int *p = &i; - return *p; // expected-warning{{Uninitialized or undefined value returned to caller.}} + return *p; // expected-warning{{Undefined or garbage value returned to caller}} } // @@ -83,3 +83,43 @@ CFStringRef rdar_6451816(CFNumberRef nr) { return CFStringConvertEncodingToIANACharSetName(encoding); // no-warning } +// PR 4630 - false warning with nonnull attribute +// This false positive (due to a regression) caused the analyzer to falsely +// flag a "return of uninitialized value" warning in the first branch due to +// the nonnull attribute. +void pr_4630_aux(char *x, int *y) __attribute__ ((nonnull (1))); +void pr_4630_aux_2(char *x, int *y); +int pr_4630(char *a, int y) { + int x; + if (y) { + pr_4630_aux(a, &x); + return x; // no-warning + } + else { + pr_4630_aux_2(a, &x); + return x; // no-warning + } +} + +// PR 4631 - False positive with union initializer +// Previously the analyzer didn't examine the compound initializers of unions, +// resulting in some false positives for initializers with side-effects. +union u_4631 { int a; }; +struct s_4631 { int a; }; +int pr4631_f2(int *p); +int pr4631_f3(void *q); +int pr4631_f1(void) +{ + int x; + union u_4631 m = { pr4631_f2(&x) }; + pr4631_f3(&m); // tell analyzer that we use m + return x; // no-warning +} +int pr4631_f1_b(void) +{ + int x; + struct s_4631 m = { pr4631_f2(&x) }; + pr4631_f3(&m); // tell analyzer that we use m + return x; // no-warning +} + diff --git a/test/Analysis/uninit-vals.c b/test/Analysis/uninit-vals.c index d69250b..8428ca4 100644 --- a/test/Analysis/uninit-vals.c +++ b/test/Analysis/uninit-vals.c @@ -23,7 +23,7 @@ int f4(int x) { return y; // expected-warning {{use of uninitialized variable}} } -int f5() { +void f5() { int a; a = 30; // no-warning } diff --git a/test/Analysis/unions-region.m b/test/Analysis/unions-region.m new file mode 100644 index 0000000..be4f185 --- /dev/null +++ b/test/Analysis/unions-region.m @@ -0,0 +1,41 @@ +// RUN: clang-cc -analyze -checker-cfref -analyzer-store=region -analyzer-constraints=range %s -verify + +//===-- unions-region.m ---------------------------------------------------===// +// +// This file tests the analyzer's reasoning about unions. +// +//===----------------------------------------------------------------------===// + +// [testA] When using RegionStore, this test case previously had a +// false positive of a 'pass-by-value argument is uninitialized' +// warning at the call to 'testA_aux' and 'testA_aux_2'. +union u_testA { + unsigned i; + float f; +}; + +float testA(float f) { + int testA_aux(unsigned x); + int testA_aux_2(union u_testA z); + + union u_testA swap; + swap.f = f; + + if (testA_aux(swap.i)) // no-warning + swap.i = ((swap.i & 0xffff0000) >> 16) | ((swap.i & 0x0000fffff) << 16); + + testA_aux_2(swap); // no-warning + + return swap.f; +} + +// [testB] When using RegionStore, this test case previously had a +// false positive of a 'pass-by-value argument is uninitialized' +// warning at the call to 'testB_aux'. +void testB(int i) { + void testB_aux(short z); + union { short x[2]; unsigned y; } val; + val.y = 10; + testB_aux(val.x[1]); // no-warning +} + diff --git a/test/Analysis/unused-ivars.m b/test/Analysis/unused-ivars.m index 632b395..aacd44e 100644 --- a/test/Analysis/unused-ivars.m +++ b/test/Analysis/unused-ivars.m @@ -1,10 +1,45 @@ -// RUN: clang-cc -analyze -warn-objc-unused-ivars %s -verify +// RUN: clang-cc -triple x86_64-apple-darwin10 -analyze -warn-objc-unused-ivars %s -verify -@interface A -{ - @private int x; // expected-warning {{Instance variable 'x' in class 'A' is never used}} +//===--- BEGIN: Delta-debugging reduced headers. --------------------------===// + +@protocol NSObject +- (id)retain; +- (oneway void)release; +@end +@interface NSObject {} +- (id)init; ++ (id)alloc; +@end + +//===--- END: Delta-debugging reduced headers. ----------------------------===// + +// This test case tests the basic functionality of the unused ivar test. +@interface TestA { +@private + int x; // expected-warning {{Instance variable 'x' in class 'TestA' is never used}} } @end +@implementation TestA @end -@implementation A @end +// This test case tests whether the unused ivar check handles blocks that +// reference an instance variable. () +@interface TestB : NSObject { +@private + id _ivar; // no-warning +} +@property (readwrite,retain) id ivar; +@end + +@implementation TestB +- (id)ivar { + __attribute__((__blocks__(byref))) id value = ((void*)0); + void (^b)() = ^{ value = _ivar; }; + b(); + return value; +} +- (void)setIvar:(id)newValue { + void (^b)() = ^{ [_ivar release]; _ivar = [newValue retain]; }; + b(); +} +@end diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt index d5e2327..2a7f132 100644 --- a/test/CMakeLists.txt +++ b/test/CMakeLists.txt @@ -1,5 +1,6 @@ set(CLANG_TEST_DIRECTORIES "Analysis" + "CodeCompletion" "CodeGen" "CodeGenCXX" "CodeGenObjC" @@ -24,37 +25,59 @@ set(CLANG_TEST_DIRECTORIES include(FindPythonInterp) if(PYTHONINTERP_FOUND) get_target_property(LLVM_TOOLS_PATH clang RUNTIME_OUTPUT_DIRECTORY) - set(TESTING_EXTRA_PATHS - "${LLVM_TOOLS_PATH}/${CMAKE_CFG_INTDIR}:${LLVM_SOURCE_DIR}/test/Scripts") + get_target_property(LLVM_LIBS_PATH clang LIBRARY_OUTPUT_DIRECTORY) set(CLANG_TEST_EXTRA_ARGS) if (MSVC OR XCODE) set(CLANG_TEST_EXTRA_ARGS "--no-progress-bar") endif() - set(all_testdirs) - foreach(testdir ${CLANG_TEST_DIRECTORIES}) - add_custom_target(clang-test-${testdir} - ${PYTHON_EXECUTABLE} - ${LLVM_SOURCE_DIR}/tools/clang/utils/test/MultiTestRunner.py - "--path=${TESTING_EXTRA_PATHS}" - -s ${CLANG_TEST_EXTRA_ARGS} - --clang=${LLVM_TOOLS_PATH}/${CMAKE_CFG_INTDIR}/clang - --clang-cc=${LLVM_TOOLS_PATH}/${CMAKE_CFG_INTDIR}/clang-cc - ${CMAKE_CURRENT_SOURCE_DIR}/${testdir}/ - WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} - COMMENT "Running Clang regression tests in ${testdir}") - list(APPEND all_testdirs ${CMAKE_CURRENT_SOURCE_DIR}/${testdir}/) + foreach(testdir ${CLANG_TEST_DIRECTORIES}) + add_custom_target(clang-test-${testdir} + COMMAND sed -e "s#\@LLVM_SOURCE_DIR\@#${LLVM_MAIN_SRC_DIR}#" + -e "s#\@LLVM_BINARY_DIR\@#${LLVM_BINARY_DIR}#" + -e "s#\@LLVM_TOOLS_DIR\@#${LLVM_TOOLS_PATH}/${CMAKE_CFG_INTDIR}#" + -e "s#\@LLVM_LIBS_DIR\@#${LLVM_LIBS_PATH}/${CMAKE_CFG_INTDIR}#" + -e "s#\@CLANG_SOURCE_DIR\@#${CMAKE_CURRENT_SOURCE_DIR}/..#" + -e "s#\@CLANG_BINARY_DIR\@#${CMAKE_CURRENT_BINARY_DIR}/..#" + ${CMAKE_CURRENT_SOURCE_DIR}/lit.site.cfg.in > + ${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg + COMMAND ${PYTHON_EXECUTABLE} + ${LLVM_SOURCE_DIR}/utils/lit/lit.py + -sv ${CLANG_TEST_EXTRA_ARGS} + ${CMAKE_CURRENT_BINARY_DIR}/${testdir} + DEPENDS clang clang-cc index-test + COMMENT "Running Clang regression tests in ${testdir}") endforeach() add_custom_target(clang-test - ${PYTHON_EXECUTABLE} - ${LLVM_SOURCE_DIR}/tools/clang/utils/test/MultiTestRunner.py - "--path=${TESTING_EXTRA_PATHS}" - -s ${CLANG_TEST_EXTRA_ARGS} - --clang=${LLVM_TOOLS_PATH}/${CMAKE_CFG_INTDIR}/clang - --clang-cc=${LLVM_TOOLS_PATH}/${CMAKE_CFG_INTDIR}/clang-cc - ${all_testdirs} - WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} - DEPENDS clang clang-cc index-test - COMMENT "Running Clang regression tests") + COMMAND sed -e "s#\@LLVM_SOURCE_DIR\@#${LLVM_MAIN_SRC_DIR}#" + -e "s#\@LLVM_BINARY_DIR\@#${LLVM_BINARY_DIR}#" + -e "s#\@LLVM_TOOLS_DIR\@#${LLVM_TOOLS_PATH}/${CMAKE_CFG_INTDIR}#" + -e "s#\@LLVM_LIBS_DIR\@#${LLVM_LIBS_PATH}/${CMAKE_CFG_INTDIR}#" + -e "s#\@CLANG_SOURCE_DIR\@#${CMAKE_CURRENT_SOURCE_DIR}/..#" + -e "s#\@CLANG_BINARY_DIR\@#${CMAKE_CURRENT_BINARY_DIR}/..#" + ${CMAKE_CURRENT_SOURCE_DIR}/lit.site.cfg.in > + ${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg + COMMAND ${PYTHON_EXECUTABLE} + ${LLVM_SOURCE_DIR}/utils/lit/lit.py + -sv ${CLANG_TEST_EXTRA_ARGS} + ${CMAKE_CURRENT_BINARY_DIR} + DEPENDS clang clang-cc index-test + COMMENT "Running Clang regression tests") + + add_custom_target(clang-c++tests + COMMAND sed -e "s#\@LLVM_SOURCE_DIR\@#${LLVM_MAIN_SRC_DIR}#" + -e "s#\@LLVM_BINARY_DIR\@#${LLVM_BINARY_DIR}#" + -e "s#\@LLVM_TOOLS_DIR\@#${LLVM_TOOLS_PATH}/${CMAKE_CFG_INTDIR}#" + -e "s#\@LLVM_LIBS_DIR\@#${LLVM_LIBS_PATH}/${CMAKE_CFG_INTDIR}#" + -e "s#\@CLANG_SOURCE_DIR\@#${CMAKE_CURRENT_SOURCE_DIR}/..#" + -e "s#\@CLANG_BINARY_DIR\@#${CMAKE_CURRENT_BINARY_DIR}/..#" + ${CMAKE_CURRENT_SOURCE_DIR}/lit.site.cfg.in > + ${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg + COMMAND ${PYTHON_EXECUTABLE} + ${LLVM_SOURCE_DIR}/utils/lit/lit.py + -sv ${CLANG_TEST_EXTRA_ARGS} + ${CMAKE_CURRENT_SOURCE_DIR}/../utils/C++Tests + DEPENDS clang clang-cc index-test + COMMENT "Running Clang regression tests") endif() diff --git a/test/CXX/basic/basic.lookup/basic.lookup.argdep/p2-template-id.cpp b/test/CXX/basic/basic.lookup/basic.lookup.argdep/p2-template-id.cpp new file mode 100644 index 0000000..e2c76f9 --- /dev/null +++ b/test/CXX/basic/basic.lookup/basic.lookup.argdep/p2-template-id.cpp @@ -0,0 +1,27 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +namespace N1 { + struct X { }; + int& f(void*); +} + +namespace N2 { + template struct Y { }; +} + +namespace N3 { + void test() { + int &ir = f((N2::Y*)0); + } +} + +int g(void *); +long g(N1::X); + +namespace N1 { + void h(int (*)(void *)); +} + +void test() { + h((&g)); +} diff --git a/test/CXX/basic/basic.lookup/basic.lookup.argdep/p2.cpp b/test/CXX/basic/basic.lookup/basic.lookup.argdep/p2.cpp new file mode 100644 index 0000000..677df828 --- /dev/null +++ b/test/CXX/basic/basic.lookup/basic.lookup.argdep/p2.cpp @@ -0,0 +1,73 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +namespace N { + struct X { }; + + X operator+(X, X); + + void f(X); + void g(X); // expected-note{{candidate function}} + + void test_multiadd(X x) { + (void)(x + x); + } +} + +namespace M { + struct Y : N::X { }; +} + +void f(); + +void test_operator_adl(N::X x, M::Y y) { + (void)(x + x); + (void)(y + y); +} + +void test_func_adl(N::X x, M::Y y) { + f(x); + f(y); + (f)(x); // expected-error{{too many arguments to function call}} + ::f(x); // expected-error{{too many arguments to function call}} +} + +namespace N { + void test_multiadd2(X x) { + (void)(x + x); + } +} + + +void test_func_adl_only(N::X x) { + g(x); +} + +namespace M { + int g(N::X); // expected-note{{candidate function}} + + void test(N::X x) { + g(x); // expected-error{{call to 'g' is ambiguous; candidates are:}} + int i = (g)(x); + + int g(N::X); + g(x); // okay; calls locally-declared function, no ADL + } +} + + +void test_operator_name_adl(N::X x) { + (void)operator+(x, x); +} + +struct Z { }; +int& f(Z); + +namespace O { + char &f(); + void test_global_scope_adl(Z z) { + { + int& ir = f(z); + } + } +} + diff --git a/test/CXX/basic/basic.lookup/basic.lookup.argdep/p4.cpp b/test/CXX/basic/basic.lookup/basic.lookup.argdep/p4.cpp new file mode 100644 index 0000000..8f0bed8 --- /dev/null +++ b/test/CXX/basic/basic.lookup/basic.lookup.argdep/p4.cpp @@ -0,0 +1,42 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +namespace A { + class A { + friend void func(A); + friend A operator+(A,A); + }; +} + +namespace B { + class B { + static void func(B); + }; + B operator+(B,B); +} + +namespace D { + class D {}; +} + +namespace C { + class C {}; + void func(C); + C operator+(C,C); + D::D operator+(D::D,D::D); +} + +namespace D { + using namespace C; +} + +namespace Test { + void test() { + func(A::A()); + func(B::B()); // expected-error {{ no matching function for call to 'func' }} + func(C::C()); + A::A() + A::A(); + B::B() + B::B(); + C::C() + C::C(); + D::D() + D::D(); // expected-error {{ invalid operands to binary expression ('D::D' and 'D::D') }} + } +} diff --git a/test/CXX/basic/basic.lookup/basic.lookup.elab/templateid.cpp b/test/CXX/basic/basic.lookup/basic.lookup.elab/templateid.cpp new file mode 100644 index 0000000..cb9d942 --- /dev/null +++ b/test/CXX/basic/basic.lookup/basic.lookup.elab/templateid.cpp @@ -0,0 +1,18 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +// elaborated-type-specifier: +// class-key '::'? nested-name-specifier? 'template'? simple-template-id +// Tests that this form is accepted by the compiler but does not follow +// the elaborated lookup rules of [basic.lookup.elab]. + +template class Ident {}; // expected-note {{previous use is here}} + +namespace A { + template void Ident(); + + class Ident AIdent; // expected-error {{refers to a function template}} + class ::Ident AnotherIdent; +} + +class Ident GlobalIdent; +union Ident GlobalIdent; // expected-error {{ tag type that does not match }} diff --git a/test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p2.cpp b/test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p2.cpp new file mode 100644 index 0000000..b32948b --- /dev/null +++ b/test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p2.cpp @@ -0,0 +1,65 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +namespace Ints { + int zero = 0; // expected-note {{candidate found by name lookup is 'Ints::zero'}} + void f(int); // expected-note 3 {{candidate function}} + void g(int); +} + +namespace Floats { + float zero = 0.0f; // expected-note {{candidate found by name lookup is 'Floats::zero'}} + void f(float); // expected-note 3 {{candidate function}} + void g(float); +} + +namespace Numbers { + using namespace Ints; + using namespace Floats; +} + +void test() { + int i = Ints::zero; + Ints::f(i); + + float f = Floats::zero; + Floats::f(f); + + double n = Numbers::zero; // expected-error {{reference to 'zero' is ambiguous}} + Numbers::f(n); // expected-error{{call to 'f' is ambiguous}} + Numbers::f(i); + Numbers::f(f); +} + +namespace Numbers { + struct Number { + explicit Number(double d) : d(d) {} + double d; + }; + Number zero(0.0f); + void g(Number); +} + +void test2() { + Numbers::Number n = Numbers::zero; + Numbers::f(n); // expected-error {{no matching function for call to 'f'}} + Numbers::g(n); +} + +namespace Numbers2 { + using Numbers::f; + using Numbers::g; +} + +void test3() { + Numbers::Number n = Numbers::zero; + Numbers2::f(n); // expected-error {{no matching function for call to 'f'}} + Numbers2::g(n); + + int i = Ints::zero; + Numbers2::f(i); + Numbers2::g(i); // expected-error {{incompatible type passing 'int'}} + + float f = Floats::zero; + Numbers2::f(f); + Numbers2::g(f); // expected-error {{incompatible type passing 'float'}} +} diff --git a/test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p3.cpp b/test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p3.cpp new file mode 100644 index 0000000..7a51a7b --- /dev/null +++ b/test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p3.cpp @@ -0,0 +1,41 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +// This is basically paraphrased from the standard. + +namespace Root { + int i = 0; + void f(); +} + +namespace A { + using namespace Root; +} + +namespace B { + using namespace Root; +} + +namespace AB { + using namespace A; + using namespace B; +} + +void test() { + if (AB::i) + AB::f(); +} + +namespace C { + using Root::i; + using Root::f; +} + +namespace AC { + using namespace A; + using namespace C; +} + +void test2() { + if (AC::i) + AC::f(); +} diff --git a/test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p4.cpp b/test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p4.cpp new file mode 100644 index 0000000..2c0ce80 --- /dev/null +++ b/test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p4.cpp @@ -0,0 +1,25 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +namespace A { + int a; +} + +namespace C { + int c; +} + +namespace B { + using namespace C; + int b; +} + +namespace C { + using namespace B; + using namespace A; +} + +void test() { + C::a++; + C::b++; + C::c++; +} diff --git a/test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p5.cpp b/test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p5.cpp new file mode 100644 index 0000000..78af521 --- /dev/null +++ b/test/CXX/basic/basic.lookup/basic.lookup.qual/namespace.qual/p5.cpp @@ -0,0 +1,35 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +namespace A { + struct x {}; // expected-note {{candidate found by name lookup is 'A::x'}} + int x; // expected-note {{candidate found by name lookup is 'A::x'}} + + struct y {}; // expected-note {{type declaration hidden}} + + struct z; + void z(float); +} + +namespace B { + struct x {}; // expected-note {{candidate found by name lookup is 'B::x'}} + float x; // expected-note {{candidate found by name lookup is 'B::x'}} + + float y; // expected-note {{declaration hides type}} + + void z(int); +} + +namespace AB { + using namespace A; + using namespace B; +} + +void test() { + struct AB::x foo; // expected-error {{reference to 'x' is ambiguous}} + int i = AB::x; // expected-error {{reference to 'x' is ambiguous}} + + struct AB::y bar; + float f = AB::y; // expected-error {{a type named 'y' is hidden by a declaration in a different namespace}} + AB::z(i); + AB::z(f); +} diff --git a/test/CXX/basic/basic.lookup/basic.lookup.unqual/p3.cpp b/test/CXX/basic/basic.lookup/basic.lookup.unqual/p3.cpp index 1daf0dd..7fd1b53 100644 --- a/test/CXX/basic/basic.lookup/basic.lookup.unqual/p3.cpp +++ b/test/CXX/basic/basic.lookup/basic.lookup.unqual/p3.cpp @@ -1,9 +1,7 @@ // RUN: clang-cc -fsyntax-only -verify %s -// XFAIL -// FIXME: This part is here to demonstrate the failure in looking up 'f', it can -// be removed once the whole test passes. typedef int f; + namespace N0 { struct A { friend void f(); diff --git a/test/CXX/basic/basic.start/basic.start.main/p2a.cpp b/test/CXX/basic/basic.start/basic.start.main/p2a.cpp new file mode 100644 index 0000000..a6a7587 --- /dev/null +++ b/test/CXX/basic/basic.start/basic.start.main/p2a.cpp @@ -0,0 +1,8 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +typedef int Int; +typedef char Char; +typedef Char* Carp; + +Int main(Int argc, Carp argv[]) { +} diff --git a/test/CXX/basic/basic.start/basic.start.main/p2b.cpp b/test/CXX/basic/basic.start/basic.start.main/p2b.cpp new file mode 100644 index 0000000..caecf60 --- /dev/null +++ b/test/CXX/basic/basic.start/basic.start.main/p2b.cpp @@ -0,0 +1,8 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +typedef int Int; +typedef char Char; +typedef Char* Carp; + +Int main(Int argc, Carp argv[], Char *env[]) { +} diff --git a/test/CXX/basic/basic.start/basic.start.main/p2c.cpp b/test/CXX/basic/basic.start/basic.start.main/p2c.cpp new file mode 100644 index 0000000..8587d8c --- /dev/null +++ b/test/CXX/basic/basic.start/basic.start.main/p2c.cpp @@ -0,0 +1,4 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +int main() { +} diff --git a/test/CXX/basic/basic.start/basic.start.main/p2d.cpp b/test/CXX/basic/basic.start/basic.start.main/p2d.cpp new file mode 100644 index 0000000..777b5ce --- /dev/null +++ b/test/CXX/basic/basic.start/basic.start.main/p2d.cpp @@ -0,0 +1,4 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +static int main() { // expected-error {{'main' is not allowed to be declared static}} +} diff --git a/test/CXX/basic/basic.start/basic.start.main/p2e.cpp b/test/CXX/basic/basic.start/basic.start.main/p2e.cpp new file mode 100644 index 0000000..087cf77 --- /dev/null +++ b/test/CXX/basic/basic.start/basic.start.main/p2e.cpp @@ -0,0 +1,4 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +inline int main() { // expected-error {{'main' is not allowed to be declared inline}} +} diff --git a/test/CXX/basic/basic.start/basic.start.main/p2f.cpp b/test/CXX/basic/basic.start/basic.start.main/p2f.cpp new file mode 100644 index 0000000..b7845b1 --- /dev/null +++ b/test/CXX/basic/basic.start/basic.start.main/p2f.cpp @@ -0,0 +1,7 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +void // expected-error {{error: 'main' must return 'int'}} +main( // expected-error {{error: first argument of 'main' should be of type 'int'}} + float a +) { +} diff --git a/test/CXX/basic/basic.start/basic.start.main/p2g.cpp b/test/CXX/basic/basic.start/basic.start.main/p2g.cpp new file mode 100644 index 0000000..4cedcdb --- /dev/null +++ b/test/CXX/basic/basic.start/basic.start.main/p2g.cpp @@ -0,0 +1,4 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +int main(int argc, const char* const* argv) { +} diff --git a/test/CXX/basic/basic.stc/basic.stc.dynamic/p2-nodef.cpp b/test/CXX/basic/basic.stc/basic.stc.dynamic/p2-nodef.cpp new file mode 100644 index 0000000..ff653d5 --- /dev/null +++ b/test/CXX/basic/basic.stc/basic.stc.dynamic/p2-nodef.cpp @@ -0,0 +1,7 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +int *use_new(int N) { + return new int [N]; +} + +int std = 17; diff --git a/test/CXX/basic/basic.stc/basic.stc.dynamic/p2.cpp b/test/CXX/basic/basic.stc/basic.stc.dynamic/p2.cpp new file mode 100644 index 0000000..f3499e4 --- /dev/null +++ b/test/CXX/basic/basic.stc/basic.stc.dynamic/p2.cpp @@ -0,0 +1,25 @@ +// RUN: clang-cc -fsyntax-only -verify %s +int *use_new(int N) { + if (N == 1) + return new int; + + return new int [N]; +} + +void use_delete(int* ip, int N) { + if (N == 1) + delete ip; + else + delete [] ip; +} + +namespace std { + class bad_alloc { }; + + typedef __SIZE_TYPE__ size_t; +} + +void* operator new(std::size_t) throw(std::bad_alloc); +void* operator new[](std::size_t) throw(std::bad_alloc); +void operator delete(void*) throw(); +void operator delete[](void*) throw(); diff --git a/test/CXX/class.derived/class.virtual/p12.cpp b/test/CXX/class.derived/class.virtual/p12.cpp new file mode 100644 index 0000000..b5974a0 --- /dev/null +++ b/test/CXX/class.derived/class.virtual/p12.cpp @@ -0,0 +1,19 @@ +// RUN: clang-cc -ast-print %s | FileCheck %s + +// CHECK: test12_A::foo() +struct test12_A { + virtual void foo(); + + void bar() { + test12_A::foo(); + } +}; + +// CHECK: xp->test24_B::wibble() +struct test24_B { + virtual void wibble(); +}; + +void foo(test24_B *xp) { + xp->test24_B::wibble(); +} diff --git a/test/CXX/class/class.friend/p1-ambiguous.cpp b/test/CXX/class/class.friend/p1-ambiguous.cpp new file mode 100644 index 0000000..a02bc53 --- /dev/null +++ b/test/CXX/class/class.friend/p1-ambiguous.cpp @@ -0,0 +1,37 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +// Make sure that friend declarations don't introduce ambiguous +// declarations. + +// Test case courtesy of Shantonu Sen. +// Bug 4784. + +class foo; + +extern "C" { + int c_func(foo *a); +}; +int cpp_func(foo *a); + +class foo { +public: + friend int c_func(foo *a); + friend int cpp_func(foo *a); + int caller(); +private: + int x; +}; + +int c_func(foo *a) { + return a->x; +} + +int cpp_func(foo *a) { + return a->x; +} + +int foo::caller() { + c_func(this); + cpp_func(this); + return 0; +} diff --git a/test/CXX/class/class.friend/p1.cpp b/test/CXX/class/class.friend/p1.cpp new file mode 100644 index 0000000..7065a7e --- /dev/null +++ b/test/CXX/class/class.friend/p1.cpp @@ -0,0 +1,76 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +struct Outer { + struct Inner { + int intfield; + }; +}; + +struct Base { + void base_member(); + + typedef int Int; + Int typedeffed_member(); +}; + +struct Derived : public Base { +}; + +int myglobal; + +void global_function(); +extern "C" { + void global_c_function(); +} + +class A { + class AInner { + }; + + friend class PreDeclared; + friend class Outer::Inner; + friend int Outer::Inner::intfield; // expected-error {{ friends can only be classes or functions }} + friend int Outer::Inner::missing_field; //expected-error {{ friends can only be classes or functions }} + friend int myoperation(float); // okay + friend int myglobal; // expected-error {{ friends can only be classes or functions }} + + friend void global_function(); + friend void global_c_function(); + + friend class UndeclaredSoFar; + UndeclaredSoFar x; // expected-error {{ unknown type name 'UndeclaredSoFar' }} + + void a_member(); + friend void A::a_member(); // expected-error {{ friends cannot be members of the declaring class }} + friend void a_member(); // okay (because we ignore class scopes when looking up friends) + friend class A::AInner; // this is okay as an extension + friend class AInner; // okay, refers to ::AInner + + friend void Derived::missing_member(); // expected-error {{ no function named 'missing_member' with type 'void ()' was found in the specified scope }} + + friend void Derived::base_member(); // expected-error {{ no function named 'base_member' with type 'void ()' was found in the specified scope }} + + friend int Base::typedeffed_member(); // okay: should look through typedef + + // These test that the friend is properly not being treated as a + // member function. + friend A operator|(const A& l, const A& r); // okay + friend A operator|(const A& r); // expected-error {{ overloaded 'operator|' must be a binary operator (has 1 parameter) }} + + friend operator bool() const; // expected-error {{ must use a qualified name when declaring a conversion operator as a friend }} + + typedef void ftypedef(); + friend ftypedef typedeffed_function; // okay (because it's not declared as a member) + + class facet; + friend class facet; // should not assert + class facet {}; +}; + +A::UndeclaredSoFar y; // expected-error {{no type named 'UndeclaredSoFar' in 'class A'}} + +class PreDeclared; + +int myoperation(float f) { + return (int) f; +} diff --git a/test/CXX/class/class.friend/p2.cpp b/test/CXX/class/class.friend/p2.cpp new file mode 100644 index 0000000..98be204 --- /dev/null +++ b/test/CXX/class/class.friend/p2.cpp @@ -0,0 +1,10 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +struct B0; + +class A { + friend class B {}; // expected-error {{cannot define a type in a friend declaration}} + friend int; // expected-error {{friends can only be classes or functions}} + friend B0; // expected-error {{must specify 'struct' to befriend}} + friend class C; // okay +}; diff --git a/test/CXX/class/class.friend/p6.cpp b/test/CXX/class/class.friend/p6.cpp new file mode 100644 index 0000000..2e8153c --- /dev/null +++ b/test/CXX/class/class.friend/p6.cpp @@ -0,0 +1,10 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +class A { + friend static class B; // expected-error {{'static' is invalid in friend declarations}} + friend extern class C; // expected-error {{'extern' is invalid in friend declarations}} + friend auto class D; // expected-error {{'auto' is invalid in friend declarations}} + friend register class E; // expected-error {{'register' is invalid in friend declarations}} + friend mutable class F; // expected-error {{'mutable' is invalid in friend declarations}} + friend typedef class G; // expected-error {{'typedef' is invalid in friend declarations}} +}; diff --git a/test/CXX/class/class.local/p3.cpp b/test/CXX/class/class.local/p3.cpp index d888a6d..9c625d1 100644 --- a/test/CXX/class/class.local/p3.cpp +++ b/test/CXX/class/class.local/p3.cpp @@ -27,4 +27,4 @@ void f3(int a) { // expected-note{{'a' declared here}} int f() { return a; } // expected-error{{reference to local variable 'a' declared in enclosed function 'f3'}} }; }; -} \ No newline at end of file +} diff --git a/test/CXX/class/class.local/p4.cpp b/test/CXX/class/class.local/p4.cpp index 40702ad..f2432ec 100644 --- a/test/CXX/class/class.local/p4.cpp +++ b/test/CXX/class/class.local/p4.cpp @@ -7,4 +7,4 @@ void f() { static void f() { } }; -} \ No newline at end of file +} diff --git a/test/CXX/class/class.nest/p1.cpp b/test/CXX/class/class.nest/p1.cpp new file mode 100644 index 0000000..bbc49f9 --- /dev/null +++ b/test/CXX/class/class.nest/p1.cpp @@ -0,0 +1,14 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +class Outer { + int x; + static int sx; + + // C++0x will likely relax this rule in this specific case, but + // we'll still need to enforce it in C++03 mode. See N2253 (or + // successor). + class Inner { + static char a[sizeof(x)]; // expected-error {{ invalid use of nonstatic data member 'x' }} + static char b[sizeof(sx)]; // okay + }; +}; diff --git a/test/CXX/class/class.nested.type/p1.cpp b/test/CXX/class/class.nested.type/p1.cpp index 33bf4b4..61ccd28 100644 --- a/test/CXX/class/class.nested.type/p1.cpp +++ b/test/CXX/class/class.nested.type/p1.cpp @@ -1,3 +1,5 @@ +// RUN: clang-cc -fsyntax-only -verify %s + class X { public: typedef int I; @@ -8,4 +10,4 @@ public: I b; // expected-error{{unknown type name 'I'}} Y c; // expected-error{{unknown type name 'Y'}} X::Y d; -X::I e; \ No newline at end of file +X::I e; diff --git a/test/CXX/class/class.union/p1.cpp b/test/CXX/class/class.union/p1.cpp new file mode 100644 index 0000000..15c2634 --- /dev/null +++ b/test/CXX/class/class.union/p1.cpp @@ -0,0 +1,105 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +void abort() __attribute__((noreturn)); + +class Okay { + int a_; +}; + +class Virtual { + virtual void foo() { abort(); } // expected-note 3 {{because type 'class Virtual' has a virtual member function}} +}; + +class VirtualBase : virtual Okay { // expected-note 3 {{because type 'class VirtualBase' has a virtual base class}} +}; + +class Ctor { + Ctor() { abort(); } // expected-note 3 {{because type 'class Ctor' has a user-declared constructor}} +}; + +class CopyCtor { + CopyCtor(CopyCtor &cc) { abort(); } // expected-note 3 {{because type 'class CopyCtor' has a user-declared copy constructor}} +}; + +// FIXME: this should eventually trigger on the operator's declaration line +class CopyAssign { // expected-note 3 {{because type 'class CopyAssign' has a user-declared copy assignment operator}} + CopyAssign& operator=(CopyAssign& CA) { abort(); } +}; + +class Dtor { + ~Dtor() { abort(); } // expected-note 3 {{because type 'class Dtor' has a user-declared destructor}} +}; + +union U1 { + Virtual v; // expected-error {{union member 'v' has a non-trivial copy constructor}} + VirtualBase vbase; // expected-error {{union member 'vbase' has a non-trivial copy constructor}} + Ctor ctor; // expected-error {{union member 'ctor' has a non-trivial constructor}} + CopyCtor copyctor; // expected-error {{union member 'copyctor' has a non-trivial copy constructor}} + CopyAssign copyassign; // expected-error {{union member 'copyassign' has a non-trivial copy assignment operator}} + Dtor dtor; // expected-error {{union member 'dtor' has a non-trivial destructor}} + Okay okay; +}; + +union U2 { + struct { + Virtual v; // expected-note {{because type 'struct U2::' has a member with a non-trivial copy constructor}} + } m1; // expected-error {{union member 'm1' has a non-trivial copy constructor}} + struct { + VirtualBase vbase; // expected-note {{because type 'struct U2::' has a member with a non-trivial copy constructor}} + } m2; // expected-error {{union member 'm2' has a non-trivial copy constructor}} + struct { + Ctor ctor; // expected-note {{because type 'struct U2::' has a member with a non-trivial constructor}} + } m3; // expected-error {{union member 'm3' has a non-trivial constructor}} + struct { + CopyCtor copyctor; // expected-note {{because type 'struct U2::' has a member with a non-trivial copy constructor}} + } m4; // expected-error {{union member 'm4' has a non-trivial copy constructor}} + struct { + CopyAssign copyassign; // expected-note {{because type 'struct U2::' has a member with a non-trivial copy assignment operator}} + } m5; // expected-error {{union member 'm5' has a non-trivial copy assignment operator}} + struct { + Dtor dtor; // expected-note {{because type 'struct U2::' has a member with a non-trivial destructor}} + } m6; // expected-error {{union member 'm6' has a non-trivial destructor}} + struct { + Okay okay; + } m7; +}; + +union U3 { + struct s1 : Virtual { // expected-note {{because type 'struct U3::s1' has a base class with a non-trivial copy constructor}} + } m1; // expected-error {{union member 'm1' has a non-trivial copy constructor}} + struct s2 : VirtualBase { // expected-note {{because type 'struct U3::s2' has a base class with a non-trivial copy constructor}} + } m2; // expected-error {{union member 'm2' has a non-trivial copy constructor}} + struct s3 : Ctor { // expected-note {{because type 'struct U3::s3' has a base class with a non-trivial constructor}} + } m3; // expected-error {{union member 'm3' has a non-trivial constructor}} + struct s4 : CopyCtor { // expected-note {{because type 'struct U3::s4' has a base class with a non-trivial copy constructor}} + } m4; // expected-error {{union member 'm4' has a non-trivial copy constructor}} + struct s5 : CopyAssign { // expected-note {{because type 'struct U3::s5' has a base class with a non-trivial copy assignment operator}} + } m5; // expected-error {{union member 'm5' has a non-trivial copy assignment operator}} + struct s6 : Dtor { // expected-note {{because type 'struct U3::s6' has a base class with a non-trivial destructor}} + } m6; // expected-error {{union member 'm6' has a non-trivial destructor}} + struct s7 : Okay { + } m7; +}; + +template struct Either { + bool tag; + union { + A a; + B b; + }; + + Either(A& a) : tag(true), a(a) {} + Either(B& b) : tag(false), b(b) {} +}; + +/* FIXME: this should work, but crashes in template code. +void fred() { + Either virt(0); + Either vbase(0); + Either ctor(0); + Either copyctor(0); + Either copyassign(0); + Either dtor(0); + Either okay(0); +} + */ diff --git a/test/CXX/dcl.dcl/basic.namespace/namespace.def/namespace.memdef/p3.cpp b/test/CXX/dcl.dcl/basic.namespace/namespace.def/namespace.memdef/p3.cpp new file mode 100644 index 0000000..2ca7165 --- /dev/null +++ b/test/CXX/dcl.dcl/basic.namespace/namespace.def/namespace.memdef/p3.cpp @@ -0,0 +1,15 @@ +// RUN: clang-cc -fsyntax-only %s + +template struct X0 { }; +struct X1 { }; + +struct Y { + template union X0; + template friend union X0; + + union X1; + friend union X1; +}; + + +// FIXME: Woefully inadequate for testing diff --git a/test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p3-cxx0x.cpp b/test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p3-cxx0x.cpp new file mode 100644 index 0000000..d701f88 --- /dev/null +++ b/test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p3-cxx0x.cpp @@ -0,0 +1,20 @@ +// RUN: clang-cc -fsyntax-only -verify %s +// C++0x N2914. + +struct B { + void f(char); + void g(char); + enum E { e }; + union { int x; }; +}; + +class C { + int g(); +}; + +class D2 : public B { + using B::f; + using B::e; + using B::x; + using C::g; // expected-error{{using declaration refers into 'C::', which is not a base class of 'D2'}} +}; diff --git a/test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p5-cxx0x.cpp b/test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p5-cxx0x.cpp new file mode 100644 index 0000000..63e5c3c --- /dev/null +++ b/test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p5-cxx0x.cpp @@ -0,0 +1,12 @@ +// RUN: clang-cc -fsyntax-only -verify %s +// C++0x N2914. + +struct A { + template void f(T); + template struct X { }; +}; + +struct B : A { + using A::f; // expected-error{{using declaration can not refer to template specialization}} + using A::X; // expected-error{{using declaration can not refer to template specialization}} +}; \ No newline at end of file diff --git a/test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p6-cxx0x.cpp b/test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p6-cxx0x.cpp new file mode 100644 index 0000000..f86f8fb --- /dev/null +++ b/test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p6-cxx0x.cpp @@ -0,0 +1,8 @@ +// RUN: clang-cc -fsyntax-only -verify %s +// C++0x N2914. + +namespace A { + namespace B { } +} + +using A::B; // expected-error{{using declaration can not refer to namespace}} diff --git a/test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p8-cxx0x.cpp b/test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p8-cxx0x.cpp new file mode 100644 index 0000000..59137eb --- /dev/null +++ b/test/CXX/dcl.dcl/basic.namespace/namespace.udecl/p8-cxx0x.cpp @@ -0,0 +1,15 @@ +// RUN: clang-cc -fsyntax-only -verify %s +// C++0x N2914. + +struct X { + int i; + static int a; +}; + +using X::i; // expected-error{{using declaration can not refer to class member}} +using X::s; // expected-error{{using declaration can not refer to class member}} + +void f() { + using X::i; // expected-error{{using declaration can not refer to class member}} + using X::s; // expected-error{{using declaration can not refer to class member}} +} diff --git a/test/CXX/dcl.dcl/dcl.spec/dcl.stc/p9.cpp b/test/CXX/dcl.dcl/dcl.spec/dcl.stc/p9.cpp index 5d9f9e7..907a91a 100644 --- a/test/CXX/dcl.dcl/dcl.spec/dcl.stc/p9.cpp +++ b/test/CXX/dcl.dcl/dcl.spec/dcl.stc/p9.cpp @@ -2,11 +2,11 @@ struct S; // expected-note {{forward declaration of 'struct S'}} extern S a; -extern S f(); +extern S f(); // expected-note {{'f' declared here}} extern void g(S a); // expected-note {{candidate function}} void h() { // FIXME: This diagnostic could be better. g(a); // expected-error {{no matching function for call to 'g'}} - f(); // expected-error {{return type of called function ('struct S') is incomplete}} + f(); // expected-error {{calling 'f' with incomplete return type 'struct S'}} } diff --git a/test/CXX/dcl.dcl/dcl.spec/dcl.type/dcl.spec.auto/p3.cpp b/test/CXX/dcl.dcl/dcl.spec/dcl.type/dcl.spec.auto/p3.cpp new file mode 100644 index 0000000..6bdea20 --- /dev/null +++ b/test/CXX/dcl.dcl/dcl.spec/dcl.type/dcl.spec.auto/p3.cpp @@ -0,0 +1,10 @@ +// RUN: clang-cc -fsyntax-only -verify %s -std=c++0x +void f() { + auto a = a; // expected-error{{variable 'a' declared with 'auto' type cannot appear in its own initializer}} +} + +void g() { + auto a; // expected-error{{declaration of variable 'a' with type 'auto' requires an initializer}} + + auto *b; // expected-error{{declaration of variable 'b' with type 'auto *' requires an initializer}} +} diff --git a/test/CXX/dcl.dcl/dcl.spec/dcl.type/dcl.spec.auto/p5.cpp b/test/CXX/dcl.dcl/dcl.spec/dcl.type/dcl.spec.auto/p5.cpp new file mode 100644 index 0000000..fa3101c --- /dev/null +++ b/test/CXX/dcl.dcl/dcl.spec/dcl.type/dcl.spec.auto/p5.cpp @@ -0,0 +1,13 @@ +// RUN: clang-cc -fsyntax-only -verify %s -std=c++0x +void f() { + auto a = a; // expected-error{{variable 'a' declared with 'auto' type cannot appear in its own initializer}} +} + +struct S { auto a; }; // expected-error{{'auto' not allowed in struct member}} + +void f(auto a) // expected-error{{'auto' not allowed in function prototype}} +{ + try { } catch (auto a) { } // expected-error{{'auto' not allowed in exception declaration}} +} + +template class C { }; // expected-error{{'auto' not allowed in template parameter}} diff --git a/test/CXX/dcl.dcl/dcl.spec/dcl.type/dcl.type.elab/p3.cpp b/test/CXX/dcl.dcl/dcl.spec/dcl.type/dcl.type.elab/p3.cpp new file mode 100644 index 0000000..b9cdb52 --- /dev/null +++ b/test/CXX/dcl.dcl/dcl.spec/dcl.type/dcl.type.elab/p3.cpp @@ -0,0 +1,60 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +class A {}; // expected-note 3 {{previous use is here}} + +void a1(struct A); +void a2(class A); +void a3(union A); // expected-error {{use of 'A' with tag type that does not match previous declaration}} +void a4(enum A); // expected-error {{use of 'A' with tag type that does not match previous declaration}} + +class A1 { + friend struct A; + friend class A; + friend union A; // expected-error {{use of 'A' with tag type that does not match previous declaration}} + + friend enum A; // expected-error {{ISO C++ forbids forward references to 'enum' types}} \ + // expected-error {{enum types cannot be friends}} +}; + +template struct B { // expected-note {{previous use is here}} + class Member {}; // expected-note 2 {{previous use is here}} +}; + +template <> class B { + // no type Member +}; + +template <> struct B { + // FIXME: the error here should be associated with the use at "void foo..." + union Member { // expected-note 4 {{previous use is here}} expected-error {{tag type that does not match previous declaration}} + void* a; + }; +}; + +void b1(struct B); +void b2(class B); +void b3(union B); // expected-error {{use of 'B' with tag type that does not match previous declaration}} +//void b4(enum B); // this just doesn't parse; you can't template an enum directly + +void c1(struct B::Member); +void c2(class B::Member); +void c3(union B::Member); // expected-error {{use of 'Member' with tag type that does not match previous declaration}} +void c4(enum B::Member); // expected-error {{use of 'Member' with tag type that does not match previous declaration}} + +void d1(struct B::Member); // expected-error {{'Member' does not name a tag member in the specified scope}} +void d2(class B::Member); // expected-error {{'Member' does not name a tag member in the specified scope}} +void d3(union B::Member); // expected-error {{'Member' does not name a tag member in the specified scope}} +void d4(enum B::Member); // expected-error {{'Member' does not name a tag member in the specified scope}} + +void e1(struct B::Member); // expected-error {{use of 'Member' with tag type that does not match previous declaration}} +void e2(class B::Member); // expected-error {{use of 'Member' with tag type that does not match previous declaration}} +void e3(union B::Member); +void e4(enum B::Member); // expected-error {{use of 'Member' with tag type that does not match previous declaration}} + +template struct C { + void foo(class B::Member); // expected-error{{no type named 'Member' in 'B'}} +}; + +C f1; +C f2; // expected-note {{in instantiation of template class}} +C f3; // expected-note {{in instantiation of template class}} diff --git a/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p10.cpp b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p10.cpp new file mode 100644 index 0000000..82f5267 --- /dev/null +++ b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p10.cpp @@ -0,0 +1,16 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +struct A { + virtual void f(int a = 7); +}; + +struct B : public A { + void f(int a); +}; + +void m() { + B* pb = new B; + A* pa = pb; + pa->f(); // OK, calls pa->B::f(7) + pb->f(); // expected-error{{too few arguments}} +} diff --git a/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p2.cpp b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p2.cpp new file mode 100644 index 0000000..143a0ca --- /dev/null +++ b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p2.cpp @@ -0,0 +1,9 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +void point(int = 3, int = 4); + +void test_point() { + point(1,2); + point(1); + point(); +} diff --git a/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p3.cpp b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p3.cpp new file mode 100644 index 0000000..ea16f64 --- /dev/null +++ b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p3.cpp @@ -0,0 +1,13 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +void nondecl(int (*f)(int x = 5)) // {expected-error {{default arguments can only be specified}}} +{ + void (*f2)(int = 17) // {expected-error {{default arguments can only be specified}}} + = (void (*)(int = 42))f; // {expected-error {{default arguments can only be specified}}} +} + +struct X0 { + int (*f)(int = 17); // expected-error{{default arguments can only be specified for parameters in a function declaration}} + + void mem8(int (*fp)(int) = (int (*)(int = 17))0); // expected-error{{default arguments can only be specified for parameters in a function declaration}} +}; diff --git a/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p4.cpp b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p4.cpp new file mode 100644 index 0000000..bbfaf90 --- /dev/null +++ b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p4.cpp @@ -0,0 +1,55 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +void f0(int i, int j, int k = 3); +void f0(int i, int j, int k); +void f0(int i, int j = 2, int k); +void f0(int i, int j, int k); +void f0(int i = 1, // expected-note{{previous definition}} + int j, int k); +void f0(int i, int j, int k); + +namespace N0 { + void f0(int, int, int); // expected-note{{candidate}} + + void test_f0_inner_scope() { + f0(); // expected-error{{no matching}} + } +} + +void test_f0_outer_scope() { + f0(); // okay +} + +void f0(int i = 1, // expected-error{{redefinition of default argument}} + int, int); + +template void f1(T); // expected-note{{previous}} + +template +void f1(T = T()); // expected-error{{cannot be added}} + + +namespace N1 { + // example from C++03 standard + // FIXME: make these "f2"s into "f"s, then fix our scoping issues + void f2(int, int); + void f2(int, int = 7); + void h() { + f2(3); // OK, calls f(3, 7) + void f(int = 1, int); // expected-error{{missing default argument}} + } + + void m() + { + void f(int, int); // expected-note{{candidate}} + f(4); // expected-error{{no matching}} + void f(int, int = 5); // expected-note{{previous definition}} + f(4); // okay + void f(int, int = 5); // expected-error{{redefinition of default argument}} + } + + void n() + { + f2(6); // okay + } +} \ No newline at end of file diff --git a/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p5.cpp b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p5.cpp new file mode 100644 index 0000000..894c9b5 --- /dev/null +++ b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p5.cpp @@ -0,0 +1,18 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +float global_f; + +void f0(int *ip = &global_f); // expected-error{{incompatible}} + +// Example from C++03 standard +int a = 1; +int f(int); +int g(int x = f(a)); + +void h() { + a = 2; + { + int *a = 0; + g(); // FIXME: check that a is called with a value of 2 + } +} diff --git a/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p6.cpp b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p6.cpp new file mode 100644 index 0000000..ef00e7b --- /dev/null +++ b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p6.cpp @@ -0,0 +1,32 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +class C { + void f(int i = 3); // expected-note{{here}} + void g(int i, int j = 99); +}; + +void C::f(int i = 3) { } // expected-error{{redefinition of default argument}} + +void C::g(int i = 88, int j) { } + +void test_C(C c) { + c.f(); + c.g(); +} + +template +struct X0 { + void f(int); + + struct Inner { + void g(int); + }; +}; + +// DR217 +template +void X0::f(int = 17) { } // expected-error{{cannot be added}} + +// DR217 + DR205 (reading tea leaves) +template +void X0::Inner::g(int = 17) { } // expected-error{{cannot be added}} diff --git a/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p7.cpp b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p7.cpp new file mode 100644 index 0000000..9c1d3a9 --- /dev/null +++ b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p7.cpp @@ -0,0 +1,7 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +void h() +{ + int i; + extern void h2(int x = sizeof(i)); // expected-error {{default argument references local variable 'i' of enclosing function}} +} diff --git a/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p8.cpp b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p8.cpp new file mode 100644 index 0000000..574237e --- /dev/null +++ b/test/CXX/dcl.decl/dcl.meaning/dcl.fct.default/p8.cpp @@ -0,0 +1,4 @@ +// RUN: clang-cc -fsyntax-only -verify %s +class A { + void f(A* p = this) { } // expected-error{{invalid use of 'this'}} +}; diff --git a/test/CXX/dcl.decl/dcl.meaning/dcl.fct/p3.cpp b/test/CXX/dcl.decl/dcl.meaning/dcl.fct/p3.cpp new file mode 100644 index 0000000..6f71978c --- /dev/null +++ b/test/CXX/dcl.decl/dcl.meaning/dcl.fct/p3.cpp @@ -0,0 +1,3 @@ +// RUN: clang-cc -fsyntax-only -verify %s +void f(int) { } // expected-note {{previous definition is here}} +void f(const int) { } // expected-error {{redefinition of 'f'}} \ No newline at end of file diff --git a/test/CXX/dcl.decl/dcl.meaning/dcl.mptr/p3.cpp b/test/CXX/dcl.decl/dcl.meaning/dcl.mptr/p3.cpp new file mode 100644 index 0000000..101d75f --- /dev/null +++ b/test/CXX/dcl.decl/dcl.meaning/dcl.mptr/p3.cpp @@ -0,0 +1,26 @@ +// RUN: clang-cc -fsyntax-only -verify %t +class A { +public: + int& i; + + A(int& i) : i(i) { } + + static int s; +}; + +template void ft(T& t) { + t.*&T::i = 10; // expected-error{{cannot form a pointer-to-member to member 'i' of reference type 'int &'}} +} + +void f() { + int b; + A a(b); + + int A::*ip = &A::s; // expected-error {{incompatible type initializing 'int *', expected 'int class A::*'}} + a.*&A::s = 10; // expected-error{{right hand operand to .* has non pointer-to-member type 'int *'}} + + a.*&A::i = 10; // expected-error{{cannot form a pointer-to-member to member 'i' of reference type 'int &'}} + ft(a); // expected-note{{in instantiation of function template specialization 'ft' requested here}} + + void A::*p = 0; // expected-error{{'p' declared as a member pointer to void}} +} diff --git a/test/CXX/expr/p3.cpp b/test/CXX/expr/p3.cpp new file mode 100644 index 0000000..40fe052 --- /dev/null +++ b/test/CXX/expr/p3.cpp @@ -0,0 +1,15 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +double operator +(double, double); // expected-error{{overloaded 'operator+' must have at least one parameter of class or enumeration type}} + +struct A +{ + operator int(); +}; + +int main() +{ + A a, b; + int i0 = a + 1; + int i1 = a + b; +} diff --git a/test/CXX/expr/p8.cpp b/test/CXX/expr/p8.cpp new file mode 100644 index 0000000..4f02497 --- /dev/null +++ b/test/CXX/expr/p8.cpp @@ -0,0 +1,18 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +int a0; +const volatile int a1; +int a2[16]; +int a3(); + +void f0(int); +void f1(int *); +void f2(int (*)()); + +int main() +{ + f0(a0); + f0(a1); + f1(a2); + f2(a3); +} diff --git a/test/CXX/expr/p9.cpp b/test/CXX/expr/p9.cpp new file mode 100644 index 0000000..1eec3cf --- /dev/null +++ b/test/CXX/expr/p9.cpp @@ -0,0 +1,50 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +// floating-point overloads + +__typeof__(0 + 0.0L) ld0; +long double &ldr = ld0; + +__typeof__(0 + 0.0) d0; +double &dr = d0; + +__typeof__(0 + 0.0f) f0; +float &fr = f0; + +// integral promotions + +signed char c0; +__typeof__(c0 + c0) c1; +int &cr = c1; + +unsigned char uc0; +__typeof__(uc0 + uc0) uc1; +int &ucr = uc1; + +short s0; +__typeof__(s0 + s0) s1; +int &sr = s1; + +unsigned short us0; +__typeof__(us0 + us0) us1; +int &usr = us1; + +// integral overloads + +__typeof__(0 + 0UL) ul0; +unsigned long &ulr = ul0; + +template struct selector; +template<> struct selector { typedef long type; }; +template<> struct selector {typedef unsigned long type; }; +__typeof__(0U + 0L) ui_l0; +selector<(sizeof(long) > sizeof(unsigned int))>::type &ui_lr = ui_l0; + +__typeof__(0 + 0L) l0; +long &lr = l0; + +__typeof__(0 + 0U) u0; +unsigned &ur = u0; + +__typeof__(0 + 0) i0; +int &ir = i0; diff --git a/test/CXX/lex/lex.trigraph/p1.cpp b/test/CXX/lex/lex.trigraph/p1.cpp new file mode 100644 index 0000000..2a9a34b --- /dev/null +++ b/test/CXX/lex/lex.trigraph/p1.cpp @@ -0,0 +1,19 @@ +// RUN: clang-cc -fsyntax-only -trigraphs -Wtrigraphs -verify %s + +??=pragma // expected-warning {{trigraph converted to '#' character}} + +int a = '??/0'; // expected-warning {{trigraph converted to '\' character}} + +int b = 1 ??' 0; // expected-warning {{trigraph converted to '^' character}} + +int c ??(1]; // expected-warning {{trigraph converted to '[' character}} + +int d [1??); // expected-warning {{trigraph converted to ']' character}} + +int e = 1 ??! 0; // expected-warning {{trigraph converted to '|' character}} + +void f() ??<} // expected-warning {{trigraph converted to '{' character}} + +void g() {??> // expected-warning {{trigraph converted to '}' character}} + +int h = ??- 0; // expected-warning {{trigraph converted to '~' character}} diff --git a/test/CXX/lex/lex.trigraph/p2.cpp b/test/CXX/lex/lex.trigraph/p2.cpp new file mode 100644 index 0000000..5be2d46 --- /dev/null +++ b/test/CXX/lex/lex.trigraph/p2.cpp @@ -0,0 +1,3 @@ +// RUN: clang-cc -fsyntax-only -trigraphs -Wtrigraphs -verify %s + +??=define arraycheck(a,b) a??(b??) ??!??! b??(a??) // expected-warning {{trigraph converted to '#' character}} expected-warning {{trigraph converted to '[' character}} expected-warning {{trigraph converted to ']' character}} expected-warning {{trigraph converted to '|' character}} expected-warning {{trigraph converted to '|' character}} expected-warning {{trigraph converted to '[' character}} expected-warning {{trigraph converted to ']' character}} diff --git a/test/CXX/lex/lex.trigraph/p3.cpp b/test/CXX/lex/lex.trigraph/p3.cpp new file mode 100644 index 0000000..f32af49 --- /dev/null +++ b/test/CXX/lex/lex.trigraph/p3.cpp @@ -0,0 +1,8 @@ +// RUN: clang-cc -fsyntax-only -trigraphs -Wtrigraphs -verify %s + +char a[] = +"?? ??\"??#??$??%??&??*??+??,??.??0??1??2??3??4??5??6" +"??7??8??9??:??;?????@??A??B??C??D??E??F??G??H??I??J" +"??K??L??M??N??O??P??Q??R??S??T??U??V??W??X??Y??Z??[" +"??\\??]??^??_??`??a??b??c??d??e??f??g??h??i??j??k??l" +"??m??n??o??p??q??r??s??t??u??v??w??x??y??z??{??|??}??~"; diff --git a/test/CXX/over/over.match/over.match.best/p1.cpp b/test/CXX/over/over.match/over.match.best/p1.cpp new file mode 100644 index 0000000..df51983 --- /dev/null +++ b/test/CXX/over/over.match/over.match.best/p1.cpp @@ -0,0 +1,16 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template int &f0(T*, int); +float &f0(void*, int); + +void test_f0(int* ip, void *vp) { + // One argument is better... + int &ir = f0(ip, 0); + + // Prefer non-templates to templates + float &fr = f0(vp, 0); +} + +// Partial ordering of function template specializations will be tested +// elsewhere +// FIXME: Initialization by user-defined conversion is tested elsewhere diff --git a/test/CXX/over/over.over/p1.cpp b/test/CXX/over/over.over/p1.cpp new file mode 100644 index 0000000..e7f7d18 --- /dev/null +++ b/test/CXX/over/over.over/p1.cpp @@ -0,0 +1,94 @@ +// RUN: clang-cc -fsyntax-only %s + +template T f0(T); +int f0(int); + +// -- an object or reference being initialized +struct S { + int (*f0)(int); + float (*f1)(float); +}; + +void test_init_f0() { + int (*f0a)(int) = f0; + int (*f0b)(int) = &f0; + int (*f0c)(int) = (f0); + float (*f0d)(float) = f0; + float (*f0e)(float) = &f0; + float (*f0f)(float) = (f0); + int (&f0g)(int) = f0; + int (&f0h)(int) = (f0); + float (&f0i)(float) = f0; + float (&f0j)(float) = (f0); + S s = { f0, f0 }; +} + +// -- the left side of an assignment (5.17), +void test_assign_f0() { + int (*f0a)(int) = 0; + float (*f0b)(float) = 0; + + f0a = f0; + f0a = &f0; + f0a = (f0); + f0b = f0; + f0b = &f0; + f0b = (f0); +} + +// -- a parameter of a function (5.2.2), +void eat_f0(int a(int), float (*b)(float), int (&c)(int), float (&d)(float)); + +void test_pass_f0() { + eat_f0(f0, f0, f0, f0); + eat_f0(&f0, &f0, (f0), (f0)); +} + +// -- a parameter of a user-defined operator (13.5), +struct X { }; +void operator+(X, int(int)); +void operator-(X, float(*)(float)); +void operator*(X, int (&)(int)); +void operator/(X, float (&)(float)); + +void test_operator_pass_f0(X x) { + x + f0; + x + &f0; + x - f0; + x - &f0; + x * f0; + x * (f0); + x / f0; + x / (f0); +} + +// -- the return value of a function, operator function, or conversion (6.6.3), +int (*test_return_f0_a())(int) { return f0; } +int (*test_return_f0_b())(int) { return &f0; } +int (*test_return_f0_c())(int) { return (f0); } +float (*test_return_f0_d())(float) { return f0; } +float (*test_return_f0_e())(float) { return &f0; } +float (*test_return_f0_f())(float) { return (f0); } + +// -- an explicit type conversion (5.2.3, 5.2.9, 5.4), or +void test_convert_f0() { + (void)((int (*)(int))f0); + (void)((int (*)(int))&f0); + (void)((int (*)(int))(f0)); + (void)((float (*)(float))f0); + (void)((float (*)(float))&f0); + (void)((float (*)(float))(f0)); +} + +// -- a non-type template-parameter(14.3.2). +template struct Y0 { }; +template struct Y1 { }; +template struct Y2 { }; +template struct Y3 { }; + +Y0 y0; +Y0<&f0> y0a; +Y1 y1; +Y1<&f0> y1a; +Y2 y2; +Y3 y3; diff --git a/test/CXX/over/over.over/p2.cpp b/test/CXX/over/over.over/p2.cpp new file mode 100644 index 0000000..9ab0260 --- /dev/null +++ b/test/CXX/over/over.over/p2.cpp @@ -0,0 +1,10 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template T f0(T, T); + +void test_f0() { + int (*f0a)(int, int) = f0; + int (*f0b)(int, int) = &f0; + int (*f0c)(int, float) = f0; // expected-error{{incompatible type}} + // FIXME: poor error message above! +} diff --git a/test/CXX/over/over.over/p4.cpp b/test/CXX/over/over.over/p4.cpp new file mode 100644 index 0000000..a05dbae --- /dev/null +++ b/test/CXX/over/over.over/p4.cpp @@ -0,0 +1,23 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template T f0(T); +int f0(int); // expected-note{{candidate function}} + +void test_f0() { + int (*fp0)(int) = f0; + int (*fp1)(int) = &f0; + float (*fp2)(float) = &f0; +} + +namespace N { + int f0(int); // expected-note{{candidate function}} +} + +int f0(int); + +void test_f0_2() { + using namespace N; + int (*fp0)(int) = f0; // expected-error{{ambiguous}} \ + // expected-error{{initializing}} + float (*fp1)(float) = f0; +} diff --git a/test/CXX/temp/temp.decls/temp.class.spec/p6.cpp b/test/CXX/temp/temp.decls/temp.class.spec/p6.cpp new file mode 100644 index 0000000..afe6ab2 --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.class.spec/p6.cpp @@ -0,0 +1,20 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template +struct X0 { + template struct Inner0 { + static const unsigned value = 0; + }; + + template struct Inner0 { + static const unsigned value = 1; + }; +}; + +template template +struct X0::Inner0 { + static const unsigned value = 2; +}; + +// FIXME: Test instantiation of these partial specializations (once they are +// implemented). diff --git a/test/CXX/temp/temp.decls/temp.class.spec/temp.class.order/p2.cpp b/test/CXX/temp/temp.decls/temp.class.spec/temp.class.order/p2.cpp new file mode 100644 index 0000000..b3b7635 --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.class.spec/temp.class.order/p2.cpp @@ -0,0 +1,16 @@ +// RUN: clang-cc -fsyntax-only -verify %s +template class X { + static const int value = 0; +}; + +template class X { + static const int value = 1; +}; + +template class X { + static const int value = 2; +}; + +int array0[X<0, 0, float>::value == 0? 1 : -1]; +int array1[X<0, 1, int>::value == 1? 1 : -1]; +int array2[X<0, 0, int>::value == 2? 1 : -1]; diff --git a/test/CXX/temp/temp.decls/temp.class.spec/temp.class.spec.mfunc/p1-neg.cpp b/test/CXX/temp/temp.decls/temp.class.spec/temp.class.spec.mfunc/p1-neg.cpp new file mode 100644 index 0000000..47cf837 --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.class.spec/temp.class.spec.mfunc/p1-neg.cpp @@ -0,0 +1,25 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template +struct A; + +template // expected-note{{previous template declaration}} +struct A { + void f0(); + void f1(); + void f2(); +}; + +template<> +struct A { + void g0(); +}; + +// FIXME: We should probably give more precise diagnostics here, but the +// diagnostics we give aren't terrible. +// FIXME: why not point to the first parameter that's "too many"? +template // expected-error{{too many template parameters}} +void A::f0() { } + +template +void A::f1() { } // expected-error{{out-of-line definition}} diff --git a/test/CXX/temp/temp.decls/temp.class.spec/temp.class.spec.mfunc/p1.cpp b/test/CXX/temp/temp.decls/temp.class.spec/temp.class.spec.mfunc/p1.cpp new file mode 100644 index 0000000..b63c56c --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.class.spec/temp.class.spec.mfunc/p1.cpp @@ -0,0 +1,26 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template +struct A; + +template +struct A { + A(T); + ~A(); + + void f(T*); + + operator T*(); + + static T value; +}; + +template void A::f(X*) { } + +template X A::value; + +template A::A(X) { value = 0; } + +template A::~A() { } + +template A::operator X*() { return 0; } diff --git a/test/CXX/temp/temp.decls/temp.class/temp.mem.class/p1.cpp b/test/CXX/temp/temp.decls/temp.class/temp.mem.class/p1.cpp new file mode 100644 index 0000000..bc4bb5d --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.class/temp.mem.class/p1.cpp @@ -0,0 +1,27 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template +struct X0 { + struct Inner; +}; + +template +struct X0::Inner { + T x; + U y; + + void f() { x = y; } // expected-error{{incompatible}} +}; + + +void test(int i, float f) { + X0::Inner inner; + inner.x = 5; + inner.y = 3.4; + inner.f(); + + X0::Inner inner2; + inner2.x = &i; + inner2.y = &f; + inner2.f(); // expected-note{{instantiation}} +} diff --git a/test/CXX/temp/temp.decls/temp.class/temp.mem.func/p1-retmem.cpp b/test/CXX/temp/temp.decls/temp.class/temp.mem.func/p1-retmem.cpp new file mode 100644 index 0000000..fd3fb0b --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.class/temp.mem.func/p1-retmem.cpp @@ -0,0 +1,28 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template struct X1 { }; + +template +struct X0 { + typedef int size_type; + typedef T value_type; + + size_type f0() const; + value_type *f1(); + X1 f2(); +}; + +template +typename X0::size_type X0::f0() const { + return 0; +} + +template +typename X0::value_type *X0::f1() { + return 0; +}; + +template +X1::value_type*> X0::f2() { + return 0; +}; diff --git a/test/CXX/temp/temp.decls/temp.class/temp.mem.func/p1.cpp b/test/CXX/temp/temp.decls/temp.class/temp.mem.func/p1.cpp new file mode 100644 index 0000000..725b61c --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.class/temp.mem.func/p1.cpp @@ -0,0 +1,68 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template // expected-note{{previous template}} +class X0 { +public: + typedef int size_type; + + X0(int); + ~X0(); + + void f0(const T&, const U&); + + T& operator[](int i) const; + + void f1(size_type) const; + void f2(size_type) const; + void f3(size_type) const; + void f4() ; + + operator T*() const; + + T value; +}; + +template +void X0::f0(const T&, const U&) { // expected-note{{previous definition}} +} + +template +X& X0::operator[](int i) const { + (void)i; + return value; +} + +template +void X0::f1(int) const { } + +template +void X0::f2(size_type) const { } + +template // expected-error{{too many template parameters}} +void X0::f3(size_type) const { +} + +template +void X0::f4() { } // expected-error{{does not refer}} + +// FIXME: error message should probably say, "redefinition of 'X0::f0'" +// rather than just "redefinition of 'f0'" +template +void X0::f0(const T&, const U&) { // expected-error{{redefinition}} +} + +// Test out-of-line constructors, destructors +template +X0::X0(int x) : value(x) { } + +template +X0::~X0() { } + +// Test out-of-line conversion functions. +template +X0::operator T*() const { + return &value; +} + +namespace N { template class A {void a();}; } +namespace N { template void A::a() {} } diff --git a/test/CXX/temp/temp.decls/temp.class/temp.mem.func/p1inst.cpp b/test/CXX/temp/temp.decls/temp.class/temp.mem.func/p1inst.cpp new file mode 100644 index 0000000..a09d0ef --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.class/temp.mem.func/p1inst.cpp @@ -0,0 +1,17 @@ +// RUN: clang-cc -fsyntax-only -verify %s +// Test instantiation of member functions of class templates defined out-of-line +template +struct X0 { + void f(T *t, const U &u); + void f(T *); +}; + +template +void X0::f(T *t, const U &u) { + *t = u; // expected-error{{not assignable}} +} + +void test_f(X0 xfi, X0 xvi, float *fp, void *vp, int i) { + xfi.f(fp, i); + xvi.f(vp, i); // expected-note{{instantiation}} +} diff --git a/test/CXX/temp/temp.decls/temp.class/temp.mem.func/pr5056.cpp b/test/CXX/temp/temp.decls/temp.class/temp.mem.func/pr5056.cpp new file mode 100644 index 0000000..602fd37 --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.class/temp.mem.func/pr5056.cpp @@ -0,0 +1,17 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +extern "C" void * malloc(int); + +template struct A { + void *malloc(int); +}; + +template +inline void *A::malloc(int) +{ + return 0; +} + +void f() { + malloc(10); +} diff --git a/test/CXX/temp/temp.decls/temp.class/temp.static/p1-inst.cpp b/test/CXX/temp/temp.decls/temp.class/temp.static/p1-inst.cpp new file mode 100644 index 0000000..2ddb8ea --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.class/temp.static/p1-inst.cpp @@ -0,0 +1,28 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +// Test instantiation of static data members declared out-of-line. + +template +struct X { + static T value; +}; + +template + T X::value = 17; // expected-error{{initialize}} + +struct InitOkay { + InitOkay(int) { } +}; + +struct CannotInit { }; + +int &returnInt() { return X::value; } +float &returnFloat() { return X::value; } + +InitOkay &returnInitOkay() { return X::value; } + +unsigned long sizeOkay() { return sizeof(X::value); } + +CannotInit &returnError() { + return X::value; // expected-note{{instantiation}} +} diff --git a/test/CXX/temp/temp.decls/temp.class/temp.static/p1.cpp b/test/CXX/temp/temp.decls/temp.class/temp.static/p1.cpp new file mode 100644 index 0000000..949a8b0 --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.class/temp.static/p1.cpp @@ -0,0 +1,26 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template +struct X0 { + static T value; +}; + +template +T X0::value = 0; // expected-error{{initialize}} + +struct X1 { + X1(int); +}; + +struct X2 { }; + +int& get_int() { return X0::value; } +X1& get_X1() { return X0::value; } + +double*& get_double_ptr() { return X0::value; } // expected-error{{initialized}} + +X2& get_X2() { + return X0::value; // expected-note{{instantiation}} +} + +template T x; // expected-error{{variable 'x' declared as a template}} diff --git a/test/CXX/temp/temp.decls/temp.fct/temp.func.order/p4.cpp b/test/CXX/temp/temp.decls/temp.fct/temp.func.order/p4.cpp new file mode 100644 index 0000000..fe42ba4 --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.fct/temp.func.order/p4.cpp @@ -0,0 +1,23 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template struct A { A(); }; +template int &f(T); +template float &f(T*); +template double &f(const T*); + +template void g(T); // expected-note{{candidate}} +template void g(T&); // expected-note{{candidate}} + +template int &h(const T&); +template float &h(A&); + +void m() { + const int *p; + double &dr1 = f(p); + float x; + g(x); // expected-error{{ambiguous}} + A z; + float &fr1 = h(z); + const A z2; + int &ir1 = h(z2); +} diff --git a/test/CXX/temp/temp.decls/temp.fct/temp.func.order/p5.cpp b/test/CXX/temp/temp.decls/temp.fct/temp.func.order/p5.cpp new file mode 100644 index 0000000..27e4426 --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.fct/temp.func.order/p5.cpp @@ -0,0 +1,12 @@ +// RUN: clang-cc -fsyntax-only -verify %s +template int &f(T); +template float &f(T*, int=1); + +template int &g(T); +template float &g(T*, ...); + +int main() { + int* ip; + float &fr1 = f(ip); + float &fr2 = g(ip); +} diff --git a/test/CXX/temp/temp.decls/temp.fct/temp.over.link/p4-neg.cpp b/test/CXX/temp/temp.decls/temp.fct/temp.over.link/p4-neg.cpp index b482955..399dcc4 100644 --- a/test/CXX/temp/temp.decls/temp.fct/temp.over.link/p4-neg.cpp +++ b/test/CXX/temp/temp.decls/temp.fct/temp.over.link/p4-neg.cpp @@ -17,11 +17,11 @@ template struct MetaFun; template - typename MetaFun::type f0(const T&) { } // expected-note{{previous}} + typename MetaFun::type f0(const T&) { while (1) {} } // expected-note{{previous}} template - typename MetaFun::type f0(const U&) { } // expected-error{{redefinition}} + typename MetaFun::type f0(const U&) { while (1) {} } // expected-error{{redefinition}} // FIXME: We need canonicalization of expressions for this to work // template struct A { }; // template void f0(A) { } // Xpected-note{{previous}} -// template void f0(A) { } // Xpected-error{{redefinition}} \ No newline at end of file +// template void f0(A) { } // Xpected-error{{redefinition}} diff --git a/test/CXX/temp/temp.decls/temp.fct/temp.over.link/p6.cpp b/test/CXX/temp/temp.decls/temp.fct/temp.over.link/p6.cpp new file mode 100644 index 0000000..2571e45 --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.fct/temp.over.link/p6.cpp @@ -0,0 +1,16 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template +struct A0 { + void g0(); +}; + +template void f0(A0) { } // expected-note{{previous}} +template void f0(A0) { } +template void f0(A0) { } // expected-error{{redefinition}} + +template void f1(A0<0, (X + Y)>) { } // expected-note{{previous}} +template void f1(A0<0, (X - Y)>) { } +template void f1(A0<0, (A + B)>) { } // expected-error{{redefinition}} + +template void A0::g0() { } diff --git a/test/CXX/temp/temp.decls/temp.friend/p1.cpp b/test/CXX/temp/temp.decls/temp.friend/p1.cpp new file mode 100644 index 0000000..fc392da --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.friend/p1.cpp @@ -0,0 +1,56 @@ +// RUN: clang-cc -emit-llvm-only %s + +template struct Num { + T value_; + +public: + Num(T value) : value_(value) {} + T get() const { return value_; } + + template struct Rep { + U count_; + Rep(U count) : count_(count) {} + + friend Num operator*(const Num &a, const Rep &n) { + Num x = 0; + for (U count = n.count_; count; --count) + x += a; + return x; + } + }; + + friend Num operator+(const Num &a, const Num &b) { + return a.value_ + b.value_; + } + + Num& operator+=(const Num& b) { + value_ += b.value_; + return *this; + } + + class Representation {}; + friend class Representation; +}; + +class A { + template friend bool iszero(const A &a) throw(); +}; + +template class B_iterator; +template class B { + friend class B_iterator; +}; + +int calc1() { + Num left = -1; + Num right = 1; + Num result = left + right; + return result.get(); +} + +int calc2() { + Num x = 3; + Num::Rep n = (char) 10; + Num result = x * n; + return result.get(); +} diff --git a/test/CXX/temp/temp.decls/temp.friend/p3.cpp b/test/CXX/temp/temp.decls/temp.friend/p3.cpp new file mode 100644 index 0000000..4615beb --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.friend/p3.cpp @@ -0,0 +1,13 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template class A { + typedef int Member; +}; + +class B { + template friend class A; + template friend class Undeclared; + + // FIXME: Diagnostic below could be (and was) better. + template friend typename A::Member; // expected-error {{classes or functions}} +}; diff --git a/test/CXX/temp/temp.decls/temp.friend/p5.cpp b/test/CXX/temp/temp.decls/temp.friend/p5.cpp new file mode 100644 index 0000000..f1142a4 --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.friend/p5.cpp @@ -0,0 +1,11 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template class A { + class Member { + }; +}; + +class B { + template friend class A::Member; +}; + diff --git a/test/CXX/temp/temp.decls/temp.mem/p1.cpp b/test/CXX/temp/temp.decls/temp.mem/p1.cpp new file mode 100644 index 0000000..80b1846 --- /dev/null +++ b/test/CXX/temp/temp.decls/temp.mem/p1.cpp @@ -0,0 +1,16 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template struct A { + static T cond; + + template struct B { + static T twice(U value) { + return (cond ? value + value : value); + } + }; +}; + +int foo() { + A::cond = true; + return A::B::twice(4); +} diff --git a/test/CXX/temp/temp.fct.spec/temp.arg.explicit/p3.cpp b/test/CXX/temp/temp.fct.spec/temp.arg.explicit/p3.cpp index f4970b8..01030b2 100644 --- a/test/CXX/temp/temp.fct.spec/temp.arg.explicit/p3.cpp +++ b/test/CXX/temp/temp.fct.spec/temp.arg.explicit/p3.cpp @@ -8,4 +8,4 @@ void g() { f("aa",3.0); // Y is deduced to be char*, and // Z is deduced to be double f("aa",3.0); // expected-error{{no matching}} -} \ No newline at end of file +} diff --git a/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/p3.cpp b/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/p3.cpp index c014c66..dbe2ff3 100644 --- a/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/p3.cpp +++ b/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/p3.cpp @@ -1,4 +1,4 @@ -// RUN: clang-cc -fsyntax-only %s +// RUN: clang-cc -fsyntax-only -verify %s template struct A { }; @@ -57,4 +57,32 @@ void test_f3(int ***ip, volatile int ***vip) { A a1 = f3(vip); } -// FIXME: the next bullet requires a lot of effort. +// - If P is a class, and P has the form template-id, then A can be a +// derived class of the deduced A. Likewise, if P is a pointer to a class +// of the form template-id, A can be a pointer to a derived class pointed +// to by the deduced A. +template struct C { }; + +struct D : public C { }; +struct E : public D { }; +struct F : A { }; +struct G : A, C { }; + +template + C *f4a(const C&); +template + C *f4b(C); +template + C *f4c(C*); +int *f4c(...); + +void test_f4(D d, E e, F f, G g) { + C *ci1a = f4a(d); + C *ci2a = f4a(e); + C *ci1b = f4b(d); + C *ci2b = f4b(e); + C *ci1c = f4c(&d); + C *ci2c = f4c(&e); + C *ci3c = f4c(&g); + int *ip1 = f4c(&f); +} diff --git a/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.conv/p2.cpp b/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.conv/p2.cpp new file mode 100644 index 0000000..7d17578 --- /dev/null +++ b/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.conv/p2.cpp @@ -0,0 +1,36 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +// FIXME: [temp.deduct.conv]p2 bullets 1 and 2 can't actually happen without +// references? +// struct ConvertibleToArray { +// // template +// // operator T(()[]) const; + +// private: +// typedef int array[17]; + +// operator array() const; +// }; + +// void test_array(ConvertibleToArray cta) { +// int *ip = cta; +// ip = cta; +// const float *cfp = cta; +// } + +// bullet 2 +// struct ConvertibleToFunction { +// template +// operator T(A1, A2) const () { }; +// }; + +// bullet 3 +struct ConvertibleToCVQuals { + template + operator T* const() const; +}; + +void test_cvqual_conv(ConvertibleToCVQuals ctcv) { + int *ip = ctcv; + const int *icp = ctcv; +} diff --git a/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.conv/p3.cpp b/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.conv/p3.cpp new file mode 100644 index 0000000..95bd7fe --- /dev/null +++ b/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.conv/p3.cpp @@ -0,0 +1,30 @@ +// RUN: clang-cc -fsyntax-only -verify %s +struct AnyPtr { + template + operator T*() const; +}; + +// If A is a cv-qualified type, the top level cv-qualifiers of A's type +// are ignored for type deduction. +void test_cvquals(AnyPtr ap) { + int* const ip = ap; + const float * const volatile fp = ap; +} + +// If A is a reference type, the type referred to by A is used for +// type deduction. +void test_ref_arg(AnyPtr ap) { + const int* const &ip = ap; + double * const &dp = ap; +} + +struct AnyRef { + template + operator T&() const; +}; + +void test_ref_param(AnyRef ar) { + int &ir = ar; + const float &fr = ar; + int i = ar; +} diff --git a/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.conv/p4.cpp b/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.conv/p4.cpp new file mode 100644 index 0000000..50d31fb --- /dev/null +++ b/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.conv/p4.cpp @@ -0,0 +1,44 @@ +// RUN: clang-cc -fsyntax-only %s + +struct AnyT { + template + operator T(); +}; + +void test_cvqual_ref(AnyT any) { + const int &cir = any; +} + +struct AnyThreeLevelPtr { + template + operator T***() const + { + T x = 0; + // FIXME: looks like we get this wrong, too! + // x = 0; // will fail if T is deduced to a const type + // (EDG and GCC get this wrong) + return 0; + } +}; + +struct X { }; + +void test_deduce_with_qual(AnyThreeLevelPtr a3) { + int * const * const * const ip = a3; +} + +struct AnyPtrMem { + template + operator T Class::*() const + { + T x = 0; + // FIXME: looks like we get this wrong, too! + // x = 0; // will fail if T is deduced to a const type. + // (EDG and GCC get this wrong) + return 0; + } +}; + +void test_deduce_ptrmem_with_qual(AnyPtrMem apm) { + const float X::* pm = apm; +} diff --git a/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.funcaddr/p1.cpp b/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.funcaddr/p1.cpp new file mode 100644 index 0000000..86a3450 --- /dev/null +++ b/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.funcaddr/p1.cpp @@ -0,0 +1,22 @@ +// RUN: clang-cc -fsyntax-only %s + +template + T f0(T, int); + +void test_f0() { + int (*f0a)(int, int) = f0; + int (*f0b)(int, int) = &f0; + float (*f0c)(float, int) = &f0; +} + +template T f1(T, int); +template T f1(T); + +void test_f1() { + float (*f1a)(float, int) = f1; + float (*f1b)(float, int) = &f1; + float (*f1c)(float) = f1; + float (*f1d)(float) = (f1); + float (*f1e)(float) = &f1; + float (*f1f)(float) = (&f1); +} diff --git a/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.partial/p11.cpp b/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.partial/p11.cpp new file mode 100644 index 0000000..072789c --- /dev/null +++ b/test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.partial/p11.cpp @@ -0,0 +1,22 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template T* f(int); // #1 +template T& f(U); // #2 + +void g() { + int *ip = f(1); // calls #1 +} + +template +struct identity { + typedef T type; +}; + +template + T* f2(int, typename identity::type = 0); // expected-note{{candidate}} +template + T& f2(U, typename identity::type = 0); // expected-note{{candidate}} + +void g2() { + f2(1); // expected-error{{ambiguous}} +} diff --git a/test/CXX/temp/temp.param/p1.cpp b/test/CXX/temp/temp.param/p1.cpp index 488c3a0..a6638b4 100644 --- a/test/CXX/temp/temp.param/p1.cpp +++ b/test/CXX/temp/temp.param/p1.cpp @@ -1 +1,4 @@ +// Suppress 'no run line' failure. +// RUN: true + // Paragraph 1 is descriptive, and therefore requires no tests. diff --git a/test/CXX/temp/temp.res/temp.dep/p3.cpp b/test/CXX/temp/temp.res/temp.dep/p3.cpp new file mode 100644 index 0000000..d47f0d6 --- /dev/null +++ b/test/CXX/temp/temp.res/temp.dep/p3.cpp @@ -0,0 +1,43 @@ +// RUN: clang-cc -fsyntax-only -verify %s +struct A0 { + struct K { }; +}; + +template struct B0: A0 { + static void f() { + K k; + } +}; + +namespace E1 { + typedef double A; + + template class B { + typedef int A; + }; + + template + struct X : B { + A* blarg(double *dp) { + return dp; + } + }; +} + +namespace E2 { + struct A { + struct B; + int *a; + int Y; + }; + + int a; + template struct Y : T { + struct B { /* ... */ }; + B b; + void f(int i) { a = i; } + Y* p; + }; + + Y ya; +} diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p1.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p1.cpp new file mode 100644 index 0000000..239b8ae --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p1.cpp @@ -0,0 +1,99 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +// This test creates cases where implicit instantiations of various entities +// would cause a diagnostic, but provides expliict specializations for those +// entities that avoid the diagnostic. The intent is to verify that +// implicit instantiations do not occur (because the explicit specialization +// is used instead). +struct NonDefaultConstructible { + NonDefaultConstructible(int); +}; + + +// C++ [temp.expl.spec]p1: +// An explicit specialization of any of the following: + +// -- function template +template void f0(T) { + T t; +} + +template<> void f0(NonDefaultConstructible) { } + +void test_f0(NonDefaultConstructible NDC) { + f0(NDC); +} + +// -- class template +template +struct X0 { + static T member; + + void f1(T t) { + t = 17; + } + + struct Inner : public T { }; + + template + struct InnerTemplate : public T { }; + + template + void ft1(T t, U u); +}; + +template +template +void X0::ft1(T t, U u) { + t = u; +} + +template T X0::member; + +template<> struct X0 { }; +X0 test_X0; + + +// -- member function of a class template +template<> void X0::f1(void *) { } + +void test_spec(X0 xvp, void *vp) { + xvp.f1(vp); +} + +// -- static data member of a class template +template<> +NonDefaultConstructible X0::member = 17; + +NonDefaultConstructible &get_static_member() { + return X0::member; +} + +// -- member class of a class template +template<> +struct X0::Inner { }; + +X0::Inner inner0; + +// -- member class template of a class template +template<> +template<> +struct X0::InnerTemplate { }; + +X0::InnerTemplate inner_template0; + +// -- member function template of a class template +template<> +template<> +void X0::ft1(void*, const void*) { } + +void test_func_template(X0 xvp, void *vp, const void *cvp) { + xvp.ft1(vp, cvp); +} + +// example from the standard: +template class stream; +template<> class stream { /* ... */ }; +template class Array { /* ... */ }; +template void sort(Array& v) { /* ... */ } +template<> void sort(Array&) ; diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p10.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p10.cpp new file mode 100644 index 0000000..61f1710 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p10.cpp @@ -0,0 +1,7 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template class X; +template<> class X; // expected-note{{forward}} +X* p; + +X x; // expected-error{{incomplete type}} diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p11.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p11.cpp new file mode 100644 index 0000000..e794e67 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p11.cpp @@ -0,0 +1,8 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template class Array { /* ... */ }; +template void sort(Array& v); + +// explicit specialization for sort(Array&) +// with deduced template-argument of type int +template<> void sort(Array&); diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p13.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p13.cpp new file mode 100644 index 0000000..63cf9f5 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p13.cpp @@ -0,0 +1,6 @@ +// RUN: clang-cc -fsyntax-only %s + +template void f(T); + +template<> void f(int) { } +void f(int) { } diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p14.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p14.cpp new file mode 100644 index 0000000..a5d5b9e --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p14.cpp @@ -0,0 +1,42 @@ +// RUN: clang-cc -emit-llvm -o - %s | FileCheck %s + +template void f(T) { /* ... */ } +template inline void g(T) { /* ... */ } + +// CHECK: define void @_Z1gIiEvT_ +template<> void g<>(int) { /* ... */ } + +template +struct X { + void f() { } + void g(); + void h(); +}; + +template +void X::g() { +} + +template +inline void X::h() { +} + +// CHECK: define void @_ZN1XIiE1fEv +template<> void X::f() { } + +// CHECK: define void @_ZN1XIiE1hEv +template<> void X::h() { } + +// CHECK: define linkonce_odr void @_Z1fIiEvT_ +template<> inline void f<>(int) { /* ... */ } + +// CHECK: define linkonce_odr void @_ZN1XIiE1gEv +template<> inline void X::g() { } + +void test(X xi) { + f(17); + g(17); + xi.f(); + xi.g(); + xi.h(); +} diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p15.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p15.cpp new file mode 100644 index 0000000..840f566 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p15.cpp @@ -0,0 +1,22 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +struct NonDefaultConstructible { + NonDefaultConstructible(const NonDefaultConstructible&); +}; + +template +struct X { + static T member; +}; + +template +T X::member; // expected-error{{no matching constructor}} + +// Okay; this is a declaration, not a definition. +template<> +NonDefaultConstructible X::member; + +NonDefaultConstructible &test(bool b) { + return b? X::member // expected-note{{instantiation}} + : X::member; +} diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p16.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p16.cpp new file mode 100644 index 0000000..ce40afd --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p16.cpp @@ -0,0 +1,26 @@ +// RUN: clang-cc -fsyntax-only %s +template struct A { + void f(T); + template void g1(T, X1); + template void g2(T, X2); + void h(T) { } +}; + +// specialization +template<> void A::f(int); + +// out of class member template definition +template template void A::g1(T, X1) { } + +// member template specialization +template<> template void A::g1(int, X1); + +// member template specialization +template<> template<> + void A::g1(int, char); // X1 deduced as char + +template<> template<> + void A::g2(int, char); // X2 specified as char + // member specialization even if defined in class definition + +template<> void A::h(int) { } diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p17.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p17.cpp new file mode 100644 index 0000000..883cb71 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p17.cpp @@ -0,0 +1,12 @@ +// RUN: clang-cc -fsyntax-only -verify %s +template +class A { + template class B { + void mf(); + }; +}; + +template<> template<> class A::B; +template<> template<> void A::B::mf(); + +template<> void A::B::mf(); // expected-error{{requires 'template<>'}} diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p18.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p18.cpp new file mode 100644 index 0000000..a5877d2 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p18.cpp @@ -0,0 +1,20 @@ +// RUN: clang-cc -fsyntax-only -verify %s +template class A { + template class B { + template void mf1(T3); + void mf2(); + }; +}; + +template<> template +class A::B { }; + +template<> template<> template + void A::B::mf1(T t) { } + +template<> template<> template +void A::B::mf1(T t) { } // expected-error{{does not match}} + +// FIXME: This diagnostic could probably be better. +template template<> + void A::B::mf2() { } // expected-error{{does not refer}} diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p19.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p19.cpp new file mode 100644 index 0000000..1f38e5a --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p19.cpp @@ -0,0 +1,30 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template +struct X { + template struct Inner { }; + + template void f(T, U) { } +}; + +template<> template +struct X::Inner { + U member; +}; + +template<> template +void X::f(int x, U y) { + x = y; // expected-error{{incompatible type}} +} + +void test(X xi, X xl, float *fp) { + X::Inner xii; + xii.member = fp; + xi.f(17, 25); + xi.f(17, 3.14159); + xi.f(17, fp); // expected-note{{instantiation}} + X::Inner xli; + + xli.member = fp; // expected-error{{no member}} + xl.f(17, fp); // okay +} diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p2.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p2.cpp new file mode 100644 index 0000000..6485660 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p2.cpp @@ -0,0 +1,239 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +// This test creates cases where implicit instantiations of various entities +// would cause a diagnostic, but provides expliict specializations for those +// entities that avoid the diagnostic. The specializations are alternately +// declarations and definitions, and the intent of this test is to verify +// that we allow specializations only in the appropriate namespaces (and +// nowhere else). +struct NonDefaultConstructible { + NonDefaultConstructible(int); +}; + + +// C++ [temp.expl.spec]p1: +// An explicit specialization of any of the following: + +// -- function template +namespace N0 { + template void f0(T) { // expected-note{{here}} + T t; + } + + template<> void f0(NonDefaultConstructible) { } + + void test_f0(NonDefaultConstructible NDC) { + f0(NDC); + } + + template<> void f0(int); + template<> void f0(long); +} + +template<> void N0::f0(int) { } // okay + +namespace N1 { + template<> void N0::f0(long) { } // expected-error{{not in a namespace enclosing}} +} + +template<> void N0::f0(double) { } // expected-error{{originally be declared}} + +struct X1 { + template void f(T); + + template<> void f(int); // expected-error{{in class scope}} +}; + +// -- class template +namespace N0 { + +template +struct X0 { // expected-note 2{{here}} + static T member; // expected-note{{here}} + + void f1(T t) { // expected-note{{explicitly specialized declaration is here}} + t = 17; + } + + struct Inner : public T { }; // expected-note 3{{here}} + + template + struct InnerTemplate : public T { }; // expected-note 2{{explicitly specialized}} \ + // expected-error{{base specifier}} + + template + void ft1(T t, U u); // expected-note{{explicitly specialized}} +}; + +} + +template +template +void N0::X0::ft1(T t, U u) { + t = u; +} + +template T N0::X0::member; + +template<> struct N0::X0 { }; // expected-error{{originally}} +N0::X0 test_X0; + +namespace N1 { + template<> struct N0::X0 { }; // expected-error{{originally}} +} + +namespace N0 { + template<> struct X0; +} + +template<> struct N0::X0 { + void f1(void *); +}; + +// -- member function of a class template +template<> void N0::X0::f1(void *) { } // expected-error{{member function specialization}} + +void test_spec(N0::X0 xvp, void *vp) { + xvp.f1(vp); +} + +namespace N0 { + template<> void X0::f1(void *) { } // expected-error{{no function template matches}} + + template<> void X0::f1(const volatile void*); +} + +void test_x0_cvvoid(N0::X0 x0, const volatile void *cvp) { + x0.f1(cvp); // okay: we've explicitly specialized +} + +// -- static data member of a class template +namespace N0 { + // This actually tests p15; the following is a declaration, not a definition. + template<> + NonDefaultConstructible X0::member; + + template<> long X0::member = 17; + + template<> float X0::member; + + template<> double X0::member; +} + +NonDefaultConstructible &get_static_member() { + return N0::X0::member; +} + +template<> int N0::X0::member; // expected-error{{originally}} + +template<> float N0::X0::member = 3.14f; + +namespace N1 { + template<> double N0::X0::member = 3.14; // expected-error{{not in a namespace enclosing}} +} + +// -- member class of a class template +namespace N0 { + + template<> + struct X0::Inner { }; + + template<> + struct X0::Inner { }; + + template<> + struct X0::Inner; + + template<> + struct X0::Inner; + + template<> + struct X0::Inner; // expected-note{{forward declaration}} +} + +template<> +struct N0::X0::Inner { }; // expected-error{{originally}} + +template<> +struct N0::X0::Inner { }; + +namespace N1 { + template<> + struct N0::X0::Inner { }; // expected-error{{member class specialization}} + + template<> + struct N0::X0::Inner { }; // expected-error{{member class specialization}} +}; + +N0::X0::Inner inner0; +N0::X0::Inner inner1; +N0::X0::Inner inner2; +N0::X0::Inner inner3; +N0::X0::Inner inner4; // expected-error{{incomplete}} + +// -- member class template of a class template +namespace N0 { + template<> + template<> + struct X0::InnerTemplate { }; + + template<> template<> + struct X0::InnerTemplate; // expected-note{{forward declaration}} + + template<> template<> + struct X0::InnerTemplate; + + template<> template<> + struct X0::InnerTemplate; +} + +template<> template<> +struct N0::X0::InnerTemplate { }; // okay + +template<> template<> +struct N0::X0::InnerTemplate { }; // expected-error{{class template specialization}} + +namespace N1 { + template<> template<> + struct N0::X0::InnerTemplate { }; // expected-error{{enclosing}} +} + +N0::X0::InnerTemplate inner_template0; +N0::X0::InnerTemplate inner_template1; // expected-error{{incomplete}} +N0::X0::InnerTemplate inner_template2; +N0::X0::InnerTemplate inner_template3; // expected-note{{instantiation}} + +// -- member function template of a class template +namespace N0 { + template<> + template<> + void X0::ft1(void*, const void*) { } + + template<> template<> + void X0::ft1(void *, int); + + template<> template<> + void X0::ft1(void *, unsigned); + + template<> template<> + void X0::ft1(void *, long); +} + +template<> template<> +void N0::X0::ft1(void *, unsigned) { } // okay + +template<> template<> +void N0::X0::ft1(void *, float) { } // expected-error{{function template specialization}} + +namespace N1 { + template<> template<> + void N0::X0::ft1(void *, long) { } // expected-error{{enclosing}} +} + + +void test_func_template(N0::X0 xvp, void *vp, const void *cvp, + int i, unsigned u) { + xvp.ft1(vp, cvp); + xvp.ft1(vp, i); + xvp.ft1(vp, u); +} diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p20.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p20.cpp new file mode 100644 index 0000000..d270b81 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p20.cpp @@ -0,0 +1,14 @@ +// RUN: clang-cc -fsyntax-only -verify %s +template +void f(T); + +template +struct A { }; + +struct X { + template<> friend void f(int); // expected-error{{in class scope}} + template<> friend class A; // expected-error{{cannot be a friend}} + + friend void f(float); // okay + friend class A; // okay +}; diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p21.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p21.cpp new file mode 100644 index 0000000..9dae3eb --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p21.cpp @@ -0,0 +1,30 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template +struct X { + void mf1(T); + template void mf2(T, U); // expected-note{{previous}} +}; + +template<> +void X::mf1(int i = 17) // expected-error{{default}} +{ +} + +template<> template<> +void X::mf2(int, int = 17) // expected-error{{default}} +{ } + +template<> template +void X::mf2(int, U = U()) // expected-error{{default}} +{ +} + +template<> +struct X { + void mf1(float); +}; + +void X::mf1(float = 3.14f) // okay +{ +} diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p3.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p3.cpp new file mode 100644 index 0000000..2bd1400 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p3.cpp @@ -0,0 +1,14 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +namespace N { + template class X; +} + +// FIXME: this diagnostic is terrible (PR3844). +template<> class X { /* ... */ }; // expected-error {{unqualified-id}} + +namespace N { + +template<> class X { /* ... */ }; // OK: X is a template + +} \ No newline at end of file diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p4.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p4.cpp new file mode 100644 index 0000000..8d91068 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p4.cpp @@ -0,0 +1,59 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +struct IntHolder { // expected-note{{here}} + IntHolder(int); +}; + +template +struct X { // expected-note{{here}} + void f() { + T t; // expected-error{{no matching}} + } + + void g() { } + + struct Inner { + T value; // expected-note {{member is declared here}} + }; + + static T value; +}; + +template +T X::value; // expected-error{{no matching constructor}} + +IntHolder &test_X_IntHolderInt(X xih) { + xih.g(); // okay + xih.f(); // expected-note{{instantiation}} + + // FIXME: diagnostic here has incorrect reason (PR5154) + X::Inner inner; // expected-error{{implicit default}} + + return X::value; // expected-note{{instantiation}} +} + +// Explicitly specialize the members of X to not cause +// problems with instantiation. +template<> +void X::f() { } + +template<> +struct X::Inner { + Inner() : value(17) { } + IntHolder value; +}; + +template<> +IntHolder X::value = 17; + +IntHolder &test_X_IntHolderInt(X xih) { + xih.g(); // okay + xih.f(); // okay, uses specialization + + X::Inner inner; // okay, uses specialization + + return X::value; // okay, uses specialization +} + +template<> +X::X() { } // expected-error{{instantiated member}} diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p5.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p5.cpp new file mode 100644 index 0000000..58682c7 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p5.cpp @@ -0,0 +1,61 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +struct IntHolder { + IntHolder(int); +}; + +template +struct X { + void f() { + T t; + } + + void g() { } + + struct Inner { + T value; + }; + + static T value; +}; + +template +T X::value; + +// Explicitly specialize the members of X to not cause +// problems with instantiation, but only provide declarations (not definitions). +template<> +void X::f(); + +template<> +struct X::Inner; // expected-note{{forward declaration}} + +template<> +IntHolder X::value; + +IntHolder &test_X_IntHolderInt(X xih) { + xih.g(); // okay + xih.f(); // okay, uses specialization + + X::Inner inner; // expected-error {{incomplete}} + + return X::value; // okay, uses specialization +} + + +template struct A { + void f(T) { /* ... */ } +}; + +template<> struct A { + void f(int); +}; + +void h() { + A a; + a.f(16); // A::f must be defined somewhere +} + +// explicit specialization syntax not used for a member of +// explicitly specialized class template specialization +void A::f(int) { /* ... */ } diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p6.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p6.cpp new file mode 100644 index 0000000..e92d3f0 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p6.cpp @@ -0,0 +1,56 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +template +struct X0 { + void f(); + + template + void g(U); + + struct Nested { + }; + + static T member; +}; + +int &use_X0_int(X0 x0i, // expected-note{{implicit instantiation first required here}} + int i) { + x0i.f(); // expected-note{{implicit instantiation first required here}} + x0i.g(i); // expected-note{{implicit instantiation first required here}} + X0::Nested nested; // expected-note{{implicit instantiation first required here}} + return X0::member; // expected-note{{implicit instantiation first required here}} +} + +template<> +void X0::f() { // expected-error{{after instantiation}} +} + +template<> template<> +void X0::g(int) { // expected-error{{after instantiation}} +} + +template<> +struct X0::Nested { }; // expected-error{{after instantiation}} + +template<> +int X0::member = 17; // expected-error{{after instantiation}} + +template<> +struct X0 { }; // expected-error{{after instantiation}} + +// Example from the standard +template class Array { /* ... */ }; + +template void sort(Array& v) { /* ... */ } + +struct String {}; + +void f(Array& v) { + + sort(v); // expected-note{{required}} + // use primary template + // sort(Array&), T is String +} + +template<> void sort(Array& v); // // expected-error{{after instantiation}} +template<> void sort<>(Array& v); // OK: sort not yet used diff --git a/test/CXX/temp/temp.spec/temp.expl.spec/p9.cpp b/test/CXX/temp/temp.spec/temp.expl.spec/p9.cpp new file mode 100644 index 0000000..49481d2 --- /dev/null +++ b/test/CXX/temp/temp.spec/temp.expl.spec/p9.cpp @@ -0,0 +1,14 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +namespace N { + template class X { /* ... */ }; + template class Y { /* ... */ }; + template<> class X { /* ... */ }; + template<> class Y; + + const unsigned NumElements = 17; +} + +template<> class N::Y { + int array[NumElements]; +}; diff --git a/test/CodeCompletion/call.cpp b/test/CodeCompletion/call.cpp new file mode 100644 index 0000000..90bf82b --- /dev/null +++ b/test/CodeCompletion/call.cpp @@ -0,0 +1,28 @@ +// Note: the run lines follow their respective tests, since line/column +// matter in this test. +void f(float x, float y); +void f(int i, int j, int k); +struct X { }; +void f(X); +namespace N { + struct Y { + Y(int = 0); + + operator int() const; + }; + void f(Y y, int ZZ); +} +typedef N::Y Y; +void f(); + +void test() { + f(Y(), 0, 0); + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:19:9 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: f(struct N::Y y, <#int ZZ#>) + // CHECK-CC1-NEXT: f(int i, <#int j#>, int k) + // CHECK-CC1-NEXT: f(float x, <#float y#>) + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:19:13 %s -o - | FileCheck -check-prefix=CC2 %s && + // CHECK-CC2-NOT: f(struct N::Y y, int ZZ) + // CHECK-CC2: f(int i, int j, <#int k#>) + // RUN: true +} diff --git a/test/CodeCompletion/enum-switch-case-qualified.cpp b/test/CodeCompletion/enum-switch-case-qualified.cpp new file mode 100644 index 0000000..223aca8 --- /dev/null +++ b/test/CodeCompletion/enum-switch-case-qualified.cpp @@ -0,0 +1,33 @@ +namespace M { + +namespace N { + struct C { + enum Color { + Red, + Orange, + Yellow, + Green, + Blue, + Indigo, + Violet + }; + }; +} + +} + +namespace M { + +void test(enum N::C::Color color) { + switch (color) { + case + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:23:8 %s -o - | FileCheck -check-prefix=CC1 %s && + // RUN: true + // CHECK-CC1: Blue : 0 : N::C::Blue + // CHECK-CC1-NEXT: Green : 0 : N::C::Green + // CHECK-CC1-NEXT: Indigo : 0 : N::C::Indigo + // CHECK-CC1-NEXT: Orange : 0 : N::C::Orange + // CHECK-CC1-NEXT: Red : 0 : N::C::Red + // CHECK-CC1-NEXT: Violet : 0 : N::C::Violet + // CHECK-CC1: Yellow : 0 : N::C::Yellow + diff --git a/test/CodeCompletion/enum-switch-case.c b/test/CodeCompletion/enum-switch-case.c new file mode 100644 index 0000000..d8bb5e8 --- /dev/null +++ b/test/CodeCompletion/enum-switch-case.c @@ -0,0 +1,29 @@ +enum Color { + Red, + Orange, + Yellow, + Green, + Blue, + Indigo, + Violet +}; + +void test(enum Color color) { + switch (color) { + case Red: + break; + + case Yellow: + break; + + case Green: + break; + + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:19:10 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: Blue : 0 + // CHECK-CC1-NEXT: Green : 0 + // CHECK-CC1-NEXT: Indigo : 0 + // CHECK-CC1-NEXT: Orange : 0 + // CHECK-CC1-NEXT: Violet : 0 + // RUN: true + diff --git a/test/CodeCompletion/enum-switch-case.cpp b/test/CodeCompletion/enum-switch-case.cpp new file mode 100644 index 0000000..7a388fc --- /dev/null +++ b/test/CodeCompletion/enum-switch-case.cpp @@ -0,0 +1,29 @@ +namespace N { + enum Color { + Red, + Orange, + Yellow, + Green, + Blue, + Indigo, + Violet + }; +} + +void test(enum N::Color color) { + switch (color) { + case N::Red: + break; + + case N::Yellow: + break; + + case + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:21:8 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: Blue : 0 : N::Blue + // CHECK-CC1-NEXT: Green : 0 : N::Green + // CHECK-CC1-NEXT: Indigo : 0 : N::Indigo + // CHECK-CC1-NEXT: Orange : 0 : N::Orange + // CHECK-CC1-NEXT: Violet : 0 : N::Violet + + // RUN: true diff --git a/test/CodeCompletion/function-templates.cpp b/test/CodeCompletion/function-templates.cpp new file mode 100644 index 0000000..52cba71 --- /dev/null +++ b/test/CodeCompletion/function-templates.cpp @@ -0,0 +1,15 @@ +namespace std { + template + void sort(RandomAccessIterator first, RandomAccessIterator last); + + template + X* dyn_cast(Y *Val); +} + +void f() { + std:: + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:10:8 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: dyn_cast<<#class X#>>(<#Y *Val#>) + // CHECK-CC1: sort(<#RandomAccessIterator first#>, <#RandomAccessIterator last#>) + // RUN: true + diff --git a/test/CodeCompletion/functions.cpp b/test/CodeCompletion/functions.cpp new file mode 100644 index 0000000..2e1bc6e --- /dev/null +++ b/test/CodeCompletion/functions.cpp @@ -0,0 +1,9 @@ +void f(int i, int j = 2, int k = 5); +void f(float x, float y...); + +void test() { + :: + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:5:5 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: f(<#int i#>{#, <#int j#>{#, <#int k#>#}#}) + // CHECK-CC1: f(<#float x#>, <#float y#><#, ...#>) + // RUN: true diff --git a/test/CodeCompletion/member-access.c b/test/CodeCompletion/member-access.c new file mode 100644 index 0000000..1e8e563 --- /dev/null +++ b/test/CodeCompletion/member-access.c @@ -0,0 +1,13 @@ +struct Point { + float x; + float y; + float z; +}; + +void test(struct Point *p) { + p-> + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:8:6 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: x + // CHECK-CC1: y + // CHECK-CC1: z + // RUN: true diff --git a/test/CodeCompletion/member-access.cpp b/test/CodeCompletion/member-access.cpp new file mode 100644 index 0000000..b810366 --- /dev/null +++ b/test/CodeCompletion/member-access.cpp @@ -0,0 +1,43 @@ +struct Base1 { + int member1; + float member2; +}; + +struct Base2 { + int member1; + double member3; + void memfun1(int); +}; + +struct Base3 : Base1, Base2 { + void memfun1(float); + void memfun1(double); + void memfun2(int); +}; + +struct Derived : Base3 { + int member4; + int memfun3(int); +}; + +class Proxy { +public: + Derived *operator->() const; +}; + +void test(const Proxy &p) { + p-> + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:29:6 %s -o - | FileCheck -check-prefix=CHECK-CC1 %s && + // CHECK-CC1: member1 : 0 : [#Base1::#]member1 + // CHECK-CC1: member1 : 0 : [#Base2::#]member1 + // CHECK-CC1: member2 : 0 : [#Base1::#]member2 + // CHECK-CC1: member3 : 0 + // CHECK-CC1: member4 : 0 + // CHECK-CC1: memfun1 : 0 : [#Base3::#]memfun1(<#float#>) + // CHECK-CC1: memfun1 : 0 : [#Base3::#]memfun1(<#double#>) + // CHECK-CC1: memfun2 : 0 : [#Base3::#]memfun2(<#int#>) + // CHECK-CC1: memfun3 : 0 : memfun3(<#int#>) + // CHECK-CC1: Base1 : 0 : Base1:: + // CHECK-CC1: memfun1 : 0 (Hidden) : Base2::memfun1(<#int#>) + // RUN: true + diff --git a/test/CodeCompletion/namespace-alias.cpp b/test/CodeCompletion/namespace-alias.cpp new file mode 100644 index 0000000..0fa2ec2 --- /dev/null +++ b/test/CodeCompletion/namespace-alias.cpp @@ -0,0 +1,21 @@ +namespace N4 { + namespace N3 { } +} + +class N3; + +namespace N2 { + namespace I1 { } + namespace I4 = I1; + namespace I5 { } + namespace I1 { } + + namespace New = + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:13:18 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: I1 : 1 + // CHECK-CC1: I4 : 1 + // CHECK-CC1: I5 : 1 + // CHECK-CC1: N2 : 3 + // CHECK-CC1-NEXT: N4 : 3 + // RUN: true + diff --git a/test/CodeCompletion/namespace.cpp b/test/CodeCompletion/namespace.cpp new file mode 100644 index 0000000..d4ed639 --- /dev/null +++ b/test/CodeCompletion/namespace.cpp @@ -0,0 +1,15 @@ +namespace N3 { +} + +namespace N2 { + namespace I1 { } + namespace I4 = I1; + namespace I5 { } + namespace I1 { } + + namespace + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:10:12 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: I1 : 0 + // CHECK-CC1-NEXT: I5 : 0 + // RUN: true + diff --git a/test/CodeCompletion/nested-name-specifier.cpp b/test/CodeCompletion/nested-name-specifier.cpp new file mode 100644 index 0000000..0cc5a19 --- /dev/null +++ b/test/CodeCompletion/nested-name-specifier.cpp @@ -0,0 +1,18 @@ +namespace N { + struct A { }; + namespace M { + struct C { }; + }; +} + +namespace N { + struct B { }; +} + +N:: +// RUN: clang-cc -fsyntax-only -code-completion-at=%s:12:4 %s -o - | FileCheck -check-prefix=CC1 %s && +// CHECK-CC1: A : 0 +// CHECK-CC1: B : 0 +// CHECK-CC1: M : 0 +// RUN: true + diff --git a/test/CodeCompletion/operator.cpp b/test/CodeCompletion/operator.cpp new file mode 100644 index 0000000..a3950f6 --- /dev/null +++ b/test/CodeCompletion/operator.cpp @@ -0,0 +1,18 @@ +class T { }; + +typedef int Integer; + +namespace N { } + +void f() { + typedef float Float; + + operator + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:10:11 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: Float : 0 + // CHECK-CC1: + : 0 + // CHECK-CC1: short : 0 + // CHECK-CC1: Integer : 2 + // CHECK-CC1: T : 2 + // CHECK-CC1: N : 6 + // RUN: true diff --git a/test/CodeCompletion/ordinary-name.c b/test/CodeCompletion/ordinary-name.c new file mode 100644 index 0000000..586e2b3 --- /dev/null +++ b/test/CodeCompletion/ordinary-name.c @@ -0,0 +1,12 @@ +struct X { int x; }; + +typedef struct t TYPEDEF; + +void foo() { + int y; + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:6:9 %s -o - | FileCheck -check-prefix=CHECK-CC1 %s && + // CHECK-CC1: y : 0 + // CHECK-CC1: foo : 2 + // CHECK-NOT-CC1: y : 2 + // CHECK-CC1-NEXT: TYPEDEF : 2 + // RUN: true diff --git a/test/CodeCompletion/property.m b/test/CodeCompletion/property.m new file mode 100644 index 0000000..7f2321e --- /dev/null +++ b/test/CodeCompletion/property.m @@ -0,0 +1,29 @@ +// Note: the run lines follow their respective tests, since line/column +// matter in this test. + +@interface Foo { + void *isa; +} +@property(copy) Foo *myprop; +@property(retain, nonatomic) id xx; +// RUN: clang-cc -fsyntax-only -code-completion-at=%s:7:11 %s -o - | FileCheck -check-prefix=CC1 %s && +// CC1: assign +// CC1-NEXT: copy +// CC1-NEXT: getter +// CC1-NEXT: nonatomic +// CC1-NEXT: readonly +// CC1-NEXT: readwrite +// CC1-NEXT: retain +// CC1-NEXT: setter +// RUN: clang-cc -fsyntax-only -code-completion-at=%s:8:18 %s -o - | FileCheck -check-prefix=CC2 %s +// CC2: assign +// CC2-NEXT: copy +// CC2-NEXT: getter +// CC2-NEXT: nonatomic +// CC2-NEXT: readonly +// CC2-NEXT: readwrite +// CC2-NEXT: setter +@end + + + diff --git a/test/CodeCompletion/tag.c b/test/CodeCompletion/tag.c new file mode 100644 index 0000000..e7250f5 --- /dev/null +++ b/test/CodeCompletion/tag.c @@ -0,0 +1,13 @@ +enum X { x }; +enum Y { y }; +struct Z { }; + +void X(); + +void test() { + enum X { x }; + enum + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:9:7 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: X : 0 + // CHECK-CC1: Y : 2 + // RUN: true diff --git a/test/CodeCompletion/tag.cpp b/test/CodeCompletion/tag.cpp new file mode 100644 index 0000000..b00ff1f --- /dev/null +++ b/test/CodeCompletion/tag.cpp @@ -0,0 +1,26 @@ +class X { }; +struct Y { }; + +namespace N { + template class Z; +} + +namespace M { + class A; +} +using M::A; + +namespace N { + class Y; + + void test() { + class + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:17:10 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: Y : 2 + // CHECK-CC1: Z : 2 + // CHECK-CC1: A : 4 + // CHECK-CC1: X : 4 + // CHECK-CC1: Y : 4 + // CHECK-CC1: M : 9 : M:: + // CHECK-CC1: N : 9 : N:: + // RUN: true diff --git a/test/CodeCompletion/templates.cpp b/test/CodeCompletion/templates.cpp new file mode 100644 index 0000000..22cca65 --- /dev/null +++ b/test/CodeCompletion/templates.cpp @@ -0,0 +1,17 @@ +namespace std { + template + class allocator; + + template > + class vector; +} + +void f() { + std:: + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:10:8 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: allocator<<#typename T#>> + // CHECK-CC1: vector<<#typename T#>{#, <#typename Alloc#>#}> + // RUN: true + + + diff --git a/test/CodeCompletion/truncation.c b/test/CodeCompletion/truncation.c new file mode 100644 index 0000000..b72aa7f --- /dev/null +++ b/test/CodeCompletion/truncation.c @@ -0,0 +1,12 @@ +#include "truncation.c.h" + +struct + +// RUN: clang-cc -fsyntax-only -code-completion-at=%s.h:4:8 -o - %s | FileCheck -check-prefix=CC1 %s && +// CHECK-CC1: X : 1 +// CHECK-CC1-NEXT: Y : 1 +// RUN: clang-cc -fsyntax-only -code-completion-at=%s:3:8 -o - %s | FileCheck -check-prefix=CC2 %s && +// CHECK-CC2: X : 1 +// CHECK-CC2: Xa : 1 +// CHECK-CC2: Y : 1 +// RUN: true diff --git a/test/CodeCompletion/truncation.c.h b/test/CodeCompletion/truncation.c.h new file mode 100644 index 0000000..a5ebbac --- /dev/null +++ b/test/CodeCompletion/truncation.c.h @@ -0,0 +1,5 @@ +struct X { }; +struct Y { }; + +struct Xa { }; + diff --git a/test/CodeCompletion/using-namespace.cpp b/test/CodeCompletion/using-namespace.cpp new file mode 100644 index 0000000..a332b88 --- /dev/null +++ b/test/CodeCompletion/using-namespace.cpp @@ -0,0 +1,21 @@ +namespace N4 { + namespace N3 { } +} + +class N3; + +namespace N2 { + namespace I1 { } + namespace I4 = I1; + namespace I5 { } + namespace I1 { } + + void foo() { + using namespace + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:14:20 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: I1 : 2 + // CHECK-CC1: I4 : 2 + // CHECK-CC1: I5 : 2 + // CHECK-CC1: N2 : 4 + // CHECK-CC1-NEXT: N4 : 4 + // RUN: true diff --git a/test/CodeCompletion/using.cpp b/test/CodeCompletion/using.cpp new file mode 100644 index 0000000..57b3aa7 --- /dev/null +++ b/test/CodeCompletion/using.cpp @@ -0,0 +1,25 @@ +namespace N4 { + namespace N3 { } +} + +class N3; + +namespace N2 { + namespace I1 { } + namespace I4 = I1; + namespace I5 { } + namespace I1 { } + + void foo() { + int N3; + + using + // RUN: clang-cc -fsyntax-only -code-completion-at=%s:16:10 %s -o - | FileCheck -check-prefix=CC1 %s && + // CHECK-CC1: I1 : 2 + // CHECK-CC1: I4 : 2 + // CHECK-CC1: I5 : 2 + // CHECK-CC1: N2 : 4 + // CHECK-CC1: N3 : 4 + // CHECK-CC1-NEXT: N4 : 4 + // RUN: true + diff --git a/test/CodeGen/2008-07-17-no-emit-on-error.c b/test/CodeGen/2008-07-17-no-emit-on-error.c index 89aeb18..51ba2b4 100644 --- a/test/CodeGen/2008-07-17-no-emit-on-error.c +++ b/test/CodeGen/2008-07-17-no-emit-on-error.c @@ -1,5 +1,5 @@ -// RUN: rm -f %t1.bc -// RUN: not clang-cc %s -emit-llvm-bc -o %t1.bc +// RUN: rm -f %t1.bc && +// RUN: not clang-cc %s -emit-llvm-bc -o %t1.bc && // RUN: not test -f %t1.bc void f() { diff --git a/test/CodeGen/2008-07-22-bitfield-init-after-zero-len-array.c b/test/CodeGen/2008-07-22-bitfield-init-after-zero-len-array.c index 19bf9a2..348ea75 100644 --- a/test/CodeGen/2008-07-22-bitfield-init-after-zero-len-array.c +++ b/test/CodeGen/2008-07-22-bitfield-init-after-zero-len-array.c @@ -1,5 +1,4 @@ -// RUN: clang-cc --emit-llvm -o %t %s && -// RUN: grep "i8 52" %t | count 1 +// RUN: clang-cc -triple=i686-apple-darwin9 --emit-llvm -o - %s | FileCheck %s struct et7 { float lv7[0]; @@ -9,3 +8,5 @@ struct et7 { 52, }; +// CHECK: @yv7 = global +// CHECK: i8 52, \ No newline at end of file diff --git a/test/CodeGen/2008-07-29-override-alias-decl.c b/test/CodeGen/2008-07-29-override-alias-decl.c index 43f4e3e..4a36e0f 100644 --- a/test/CodeGen/2008-07-29-override-alias-decl.c +++ b/test/CodeGen/2008-07-29-override-alias-decl.c @@ -1,6 +1,6 @@ // RUN: clang-cc -emit-llvm -o - %s | grep -e "^@f" | count 1 -int x() {} +int x() { return 1; } int f() __attribute__((weak, alias("x"))); diff --git a/test/CodeGen/2009-01-21-invalid-debug-info.m b/test/CodeGen/2009-01-21-invalid-debug-info.m index 9a955a1..2662b922 100644 --- a/test/CodeGen/2009-01-21-invalid-debug-info.m +++ b/test/CodeGen/2009-01-21-invalid-debug-info.m @@ -10,7 +10,7 @@ @interface I1 @end @implementation I1 --im0 {} +-im0 { return 0; } @end I1 *f1(void) { return 0; } diff --git a/test/CodeGen/2009-04-23-dbg.c b/test/CodeGen/2009-04-23-dbg.c index 4be6dab..c6b1791 100644 --- a/test/CodeGen/2009-04-23-dbg.c +++ b/test/CodeGen/2009-04-23-dbg.c @@ -1,4 +1,4 @@ -// RUN: clang-cc -g -o %t %s -emit-llvm-bc && llc %t -f -o %t.s +// RUN: clang-cc -g -o %t %s -emit-llvm-bc && llc %t -o %t.s # 1 "a.c" # 1 "a.c" 1 # 1 "" 1 diff --git a/test/CodeGen/2009-06-01-addrofknr.c b/test/CodeGen/2009-06-01-addrofknr.c index 16a5bbf..d51a4a4 100644 --- a/test/CodeGen/2009-06-01-addrofknr.c +++ b/test/CodeGen/2009-06-01-addrofknr.c @@ -2,20 +2,20 @@ // PR4289 struct funcptr { - int (*func)(); + int (*func)(); }; static int func(f) - void *f; + void *f; { + return 0; } int main(int argc, char *argv[]) { - struct funcptr fp; + struct funcptr fp; - fp.func = &func; - fp.func = func; + fp.func = &func; + fp.func = func; } - diff --git a/test/CodeGen/2009-07-31-DbgDeclare.c b/test/CodeGen/2009-07-31-DbgDeclare.c new file mode 100644 index 0000000..da49afe --- /dev/null +++ b/test/CodeGen/2009-07-31-DbgDeclare.c @@ -0,0 +1,5 @@ +// RUN: clang-cc -S -g -o %t.s %s +void foo() { + int i = 0; + i = 42; +} diff --git a/test/CodeGen/2009-08-14-vararray-crash.c b/test/CodeGen/2009-08-14-vararray-crash.c new file mode 100644 index 0000000..40e071b --- /dev/null +++ b/test/CodeGen/2009-08-14-vararray-crash.c @@ -0,0 +1,11 @@ +// RUN: clang-cc -emit-llvm < %s + +void sum1(int rb) { + typedef unsigned char imgrow[rb]; + typedef imgrow img[rb]; + + const img *br; + int y; + + (*br)[y]; +} diff --git a/test/CodeGen/PR3613-static-decl.c b/test/CodeGen/PR3613-static-decl.c index 365b9b2..2083581 100644 --- a/test/CodeGen/PR3613-static-decl.c +++ b/test/CodeGen/PR3613-static-decl.c @@ -1,5 +1,5 @@ // RUN: clang-cc -triple i386-unknown-unknown -emit-llvm -o %t %s && -// RUN: grep '@g0 = internal global .struct.s0 <{ i32 3 }>' %t | count 1 +// RUN: grep '@g0 = internal global %.truct.s0 { i32 3 }' %t | count 1 struct s0 { int a; diff --git a/test/CodeGen/PR4611-bitfield-layout.c b/test/CodeGen/PR4611-bitfield-layout.c new file mode 100644 index 0000000..83ce4ff --- /dev/null +++ b/test/CodeGen/PR4611-bitfield-layout.c @@ -0,0 +1,6 @@ +// RUN: clang-cc -triple i386-unknown-unknown %s -emit-llvm -o %t && +// RUN: grep "struct.object_entry = type { i8, \[2 x i8\], i8 }" %t + +struct object_entry { + unsigned int type:3, pack_id:16, depth:13; +} entries; diff --git a/test/CodeGen/PR5060-align.c b/test/CodeGen/PR5060-align.c new file mode 100644 index 0000000..5d86408 --- /dev/null +++ b/test/CodeGen/PR5060-align.c @@ -0,0 +1,13 @@ +// RUN: clang-cc -emit-llvm %s -o - -verify | FileCheck %s + +// CHECK: @foo.p = internal global i8 0, align 32 +char *foo(void) { + static char p __attribute__((aligned(32))); + return &p; +} + +void bar(long n) { + // CHECK: align 32 + char p[n] __attribute__((aligned(32))); +} + diff --git a/test/CodeGen/address-space-compound-literal.c b/test/CodeGen/address-space-compound-literal.c new file mode 100644 index 0000000..79d19ed --- /dev/null +++ b/test/CodeGen/address-space-compound-literal.c @@ -0,0 +1,5 @@ +// RUN: clang-cc -emit-llvm < %s | grep "internal addrspace(1) global i32 1" + +typedef int a __attribute__((address_space(1))); +a* x = &(a){1}; + diff --git a/test/CodeGen/address-space-field1.c b/test/CodeGen/address-space-field1.c new file mode 100644 index 0000000..f8ec83c --- /dev/null +++ b/test/CodeGen/address-space-field1.c @@ -0,0 +1,39 @@ +// RUN: clang-cc -emit-llvm < %s -o - | FileCheck %s +// CHECK:%struct.S = type { i32, i32 } +// CHECK:define void @test_addrspace(%struct.S addrspace(1)* %p1, %struct.S addrspace(2)* %p2) nounwind +// CHECK:entry: +// CHECK: %p1.addr = alloca %struct.S addrspace(1)* ; <%struct.S addrspace(1)**> [#uses=3] +// CHECK: %p2.addr = alloca %struct.S addrspace(2)* ; <%struct.S addrspace(2)**> [#uses=3] +// CHECK: store %struct.S addrspace(1)* %p1, %struct.S addrspace(1)** %p1.addr +// CHECK: store %struct.S addrspace(2)* %p2, %struct.S addrspace(2)** %p2.addr +// CHECK: %tmp = load %struct.S addrspace(2)** %p2.addr ; <%struct.S addrspace(2)*> [#uses=1] +// CHECK: %tmp1 = getelementptr inbounds %struct.S addrspace(2)* %tmp, i32 0, i32 1 ; [#uses=1] +// CHECK: %tmp2 = load i32 addrspace(2)* %tmp1 ; [#uses=1] +// CHECK: %tmp3 = load %struct.S addrspace(1)** %p1.addr ; <%struct.S addrspace(1)*> [#uses=1] +// CHECK: %tmp4 = getelementptr inbounds %struct.S addrspace(1)* %tmp3, i32 0, i32 0 ; [#uses=1] +// CHECK: store i32 %tmp2, i32 addrspace(1)* %tmp4 +// CHECK: %tmp5 = load %struct.S addrspace(2)** %p2.addr ; <%struct.S addrspace(2)*> [#uses=1] +// CHECK: %tmp6 = getelementptr inbounds %struct.S addrspace(2)* %tmp5, i32 0, i32 0 ; [#uses=1] +// CHECK: %tmp7 = load i32 addrspace(2)* %tmp6 ; [#uses=1] +// CHECK: %tmp8 = load %struct.S addrspace(1)** %p1.addr ; <%struct.S addrspace(1)*> [#uses=1] +// CHECK: %tmp9 = getelementptr inbounds %struct.S addrspace(1)* %tmp8, i32 0, i32 1 ; [#uses=1] +// CHECK: store i32 %tmp7, i32 addrspace(1)* %tmp9 +// CHECK: ret void +// CHECK:} + +// Check that we don't lose the address space when accessing a member +// of a structure. + +#define __addr1 __attribute__((address_space(1))) +#define __addr2 __attribute__((address_space(2))) + +typedef struct S { + int a; + int b; +} S; + +void test_addrspace(__addr1 S* p1, __addr2 S*p2) { + // swap + p1->a = p2->b; + p1->b = p2->a; +} diff --git a/test/CodeGen/address-space-field2.c b/test/CodeGen/address-space-field2.c new file mode 100644 index 0000000..5576e55 --- /dev/null +++ b/test/CodeGen/address-space-field2.c @@ -0,0 +1,50 @@ +// RUN: clang-cc -emit-llvm %s -o - | FileCheck %s +// CHECK: addrspace(1) +// CHECK: addrspace(2) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) + +// Check that we don't lose the address space when accessing an array element +// inside a structure. + +#define __addr1 __attribute__((address_space(1))) +#define __addr2 __attribute__((address_space(2))) + +typedef struct S { + int arr[ 3 ]; +} S; + +void test_addrspace(__addr1 S* p1, __addr2 S*p2, int* val, int n) { + for (int i=0; i < 3; ++i) { + int t = val[i]; + p1->arr[i] = t; + for (int j=0; j < n; ++j) + p2[j].arr[i] = t; + } +} diff --git a/test/CodeGen/address-space-field3.c b/test/CodeGen/address-space-field3.c new file mode 100644 index 0000000..567757f --- /dev/null +++ b/test/CodeGen/address-space-field3.c @@ -0,0 +1,46 @@ +// RUN: clang-cc -emit-llvm %s -o - | FileCheck %s +// CHECK: addrspace(1) +// CHECK: addrspace(2) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) + +// Check that we don't lose the address space when accessing an array element +// inside a structure. + +#define __addr1 __attribute__((address_space(1))) +#define __addr2 __attribute__((address_space(2))) + +typedef struct S { + int arr[ 3 ]; +} S; + +void test_addrspace(__addr1 S* p1, __addr2 S*p2, int* val, int n) { + for (int i=0; i < 3; ++i) { + int t = val[i]; + p1->arr[i] = p2->arr[i]; + } +} diff --git a/test/CodeGen/address-space-field4.c b/test/CodeGen/address-space-field4.c new file mode 100644 index 0000000..31df018 --- /dev/null +++ b/test/CodeGen/address-space-field4.c @@ -0,0 +1,61 @@ +// RUN: clang-cc -emit-llvm %s -o - | FileCheck %s +// CHECK: addrspace(2) +// CHECK: addrspace(3) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(3) +// CHECK: addrspace(3) +// CHECK: addrspace(1) +// CHECK: addrspace(3) +// CHECK: addrspace(3) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(1) +// CHECK: addrspace(2) +// CHECK: addrspace(1) +// CHECK: addrspace(2) +// CHECK: addrspace(2) +// CHECK: addrspace(2) + +// Check the load and store are using the correct address space to access +// the variables. + +#define __addr1 __attribute__((address_space(1))) +#define __addr2 __attribute__((address_space(2))) +#define __addr3 __attribute__((address_space(3))) + +typedef struct Pair { + __addr2 int* a; + __addr3 int* b; +} Pair; + +typedef struct S { + Pair arr[ 3 ]; +} S; + +void test_addrspace(__addr1 S* p1, __addr1 S* p2) { + *p1->arr[0].a = *p2->arr[1].b; +} diff --git a/test/CodeGen/arm-arguments.c b/test/CodeGen/arm-arguments.c new file mode 100644 index 0000000..c43ede2 --- /dev/null +++ b/test/CodeGen/arm-arguments.c @@ -0,0 +1,94 @@ +// RUN: clang-cc -triple armv7-apple-darwin9 -target-abi=apcs-gnu -emit-llvm -w -o - %s | FileCheck -check-prefix=APCS-GNU %s && +// RUN: clang-cc -triple armv7-apple-darwin9 -target-abi=aapcs -emit-llvm -w -o - %s | FileCheck -check-prefix=AAPCS %s + +// APCS-GNU: define arm_apcscc signext i8 @f0() +// AAPCS: define arm_aapcscc signext i8 @f0() +char f0(void) { + return 0; +} + +// APCS-GNU: define arm_apcscc i8 @f1() +// AAPCS: define arm_aapcscc i8 @f1() +struct s1 { char f0; }; +struct s1 f1(void) {} + +// APCS-GNU: define arm_apcscc i16 @f2() +// AAPCS: define arm_aapcscc i16 @f2() +struct s2 { short f0; }; +struct s2 f2(void) {} + +// APCS-GNU: define arm_apcscc i32 @f3() +// AAPCS: define arm_aapcscc i32 @f3() +struct s3 { int f0; }; +struct s3 f3(void) {} + +// APCS-GNU: define arm_apcscc i32 @f4() +// AAPCS: define arm_aapcscc i32 @f4() +struct s4 { struct s4_0 { int f0; } f0; }; +struct s4 f4(void) {} + +// APCS-GNU: define arm_apcscc void @f5( +// APCS-GNU: struct.s5* noalias sret +// AAPCS: define arm_aapcscc i32 @f5() +struct s5 { struct { } f0; int f1; }; +struct s5 f5(void) {} + +// APCS-GNU: define arm_apcscc void @f6( +// APCS-GNU: struct.s6* noalias sret +// AAPCS: define arm_aapcscc i32 @f6() +struct s6 { int f0[1]; }; +struct s6 f6(void) {} + +// APCS-GNU: define arm_apcscc void @f7() +// AAPCS: define arm_aapcscc void @f7() +struct s7 { struct { int : 0; } f0; }; +struct s7 f7(void) {} + +// APCS-GNU: define arm_apcscc void @f8( +// APCS-GNU: struct.s8* noalias sret +// AAPCS: define arm_aapcscc void @f8() +struct s8 { struct { int : 0; } f0[1]; }; +struct s8 f8(void) {} + +// APCS-GNU: define arm_apcscc i32 @f9() +// AAPCS: define arm_aapcscc i32 @f9() +struct s9 { int f0; int : 0; }; +struct s9 f9(void) {} + +// APCS-GNU: define arm_apcscc i32 @f10() +// AAPCS: define arm_aapcscc i32 @f10() +struct s10 { int f0; int : 0; int : 0; }; +struct s10 f10(void) {} + +// APCS-GNU: define arm_apcscc void @f11( +// APCS-GNU: struct.s10* noalias sret +// AAPCS: define arm_aapcscc i32 @f11() +struct s11 { int : 0; int f0; }; +struct s11 f11(void) {} + +// APCS-GNU: define arm_apcscc i32 @f12() +// AAPCS: define arm_aapcscc i32 @f12() +union u12 { char f0; short f1; int f2; }; +union u12 f12(void) {} + +// APCS-GNU: define arm_apcscc void @f13( +// APCS-GNU: struct.s13* noalias sret + +// FIXME: This should return a float. +// AAPCS-FIXME: define arm_aapcscc float @f13() +struct s13 { float f0; }; +struct s13 f13(void) {} + +// APCS-GNU: define arm_apcscc void @f14( +// APCS-GNU: struct.s13* noalias sret +// AAPCS: define arm_aapcscc i32 @f14() +union u14 { float f0; }; +union u14 f14(void) {} + +// APCS-GNU: define arm_apcscc void @f15() +// AAPCS: define arm_aapcscc void @f15() +void f15(struct s7 a0) {} + +// APCS-GNU: define arm_apcscc void @f16() +// AAPCS: define arm_aapcscc void @f16() +void f16(struct s8 a0) {} diff --git a/test/CodeGen/arm_asm_clobber.c b/test/CodeGen/arm_asm_clobber.c new file mode 100644 index 0000000..34e2517 --- /dev/null +++ b/test/CodeGen/arm_asm_clobber.c @@ -0,0 +1,21 @@ +// RUN: clang -ccc-host-triple armv6-unknown-unknown -emit-llvm -S -o %t %s + +void test0(void) { + asm volatile("mov r0, r0" :: ); +} +void test1(void) { + asm volatile("mov r0, r0" ::: + "cc", "memory" ); +} +void test2(void) { + asm volatile("mov r0, r0" ::: + "r0", "r1", "r2", "r3"); + asm volatile("mov r0, r0" ::: + "r4", "r5", "r6", "r8"); +} +void test3(void) { + asm volatile("mov r0, r0" ::: + "a1", "a2", "a3", "a4"); + asm volatile("mov r0, r0" ::: + "v1", "v2", "v3", "v5"); +} diff --git a/test/CodeGen/array.c b/test/CodeGen/array.c index 5bcc26e..294dabf 100644 --- a/test/CodeGen/array.c +++ b/test/CodeGen/array.c @@ -1,11 +1,11 @@ // RUN: clang-cc -emit-llvm %s -o %t -int f() { +void f() { int a[2]; a[0] = 0; } -int f2() { +void f2() { int x = 0; int y = 1; int a[10] = { y, x, 2, 3}; diff --git a/test/CodeGen/asm-inout.c b/test/CodeGen/asm-inout.c new file mode 100644 index 0000000..0d8dbdf --- /dev/null +++ b/test/CodeGen/asm-inout.c @@ -0,0 +1,18 @@ +// RUN: clang-cc -triple i386-unknown-unknown -emit-llvm %s -o %t && +// RUN: grep "load i8\*\*\* %p.addr" %t | count 1 +// XFAIL + +// PR3800 +void f(void **p) +{ + __asm__ volatile("" :"+m"(*p)); +} + +#if 0 +// FIXME: Once this works again, we must verify that the code below behaves as expected +// See PR4677. +void f() { + unsigned _data = 42; + __asm__("bswap %0":"+r"(_data)); +} +#endif diff --git a/test/CodeGen/asm.c b/test/CodeGen/asm.c index 58373fc..52afc91 100644 --- a/test/CodeGen/asm.c +++ b/test/CodeGen/asm.c @@ -15,7 +15,7 @@ void t4() { unsigned long long a; struct reg { unsigned long long a, b; } b; - __asm__ volatile ("":: "m"(a), "m"(b)); + __asm__ volatile ("":: "m"(a), "m"(b)); } // PR3417 @@ -33,7 +33,7 @@ void t7(int a) { __asm__ volatile("T7 NAMED: %[input]" : "+r"(a): [input] "i" (4)); } -// RUN: grep "T8 NAMED MODIFIER: \${0:c}" %t +// RUN: grep "T8 NAMED MODIFIER: \${0:c}" %t && void t8() { __asm__ volatile("T8 NAMED MODIFIER: %c[input]" :: [input] "i" (4)); } @@ -101,3 +101,12 @@ void t14(struct S *P) { } +// PR4938 +int t16() { + int a,b; + asm ( "nop;" + :"=%c" (a) + : "r" (b) + ); + return 0; +} diff --git a/test/CodeGen/attr-cleanup.c b/test/CodeGen/attr-cleanup.c index 03dde33..9105ede 100644 --- a/test/CodeGen/attr-cleanup.c +++ b/test/CodeGen/attr-cleanup.c @@ -3,6 +3,6 @@ // void f(void* arg); void g() { - __attribute__((cleanup(f))) void *g; + __attribute__((cleanup(f))) void *g; } diff --git a/test/CodeGen/attributes.c b/test/CodeGen/attributes.c index 8f157f3..d539e03 100644 --- a/test/CodeGen/attributes.c +++ b/test/CodeGen/attributes.c @@ -1,69 +1,77 @@ -// RUN: clang-cc -emit-llvm -o %t %s && -// RUN: grep 't1.*noreturn' %t && -// RUN: grep 't2.*nounwind' %t && -// RUN: grep 'weak.*t3' %t && -// RUN: grep 'hidden.*t4' %t && -// RUN: grep 't5.*weak' %t && -// RUN: grep 't6.*protected' %t && -// RUN: grep 't7.*noreturn' %t && -// RUN: grep 't7.*nounwind' %t && -// RUN: grep 't9.*alias.*weak.*t8' %t && -// RUN: grep '@t10().*section "SECT"' %t && -// RUN: grep '@t11().*section "SECT"' %t && -// RUN: grep '@t12 =.*section "SECT"' %t && -// RUN: grep '@t13 =.*section "SECT"' %t && -// RUN: grep '@t14.x =.*section "SECT"' %t -// RUN: grep 'declare extern_weak i32 @t15()' %t && -// RUN: grep '@t16 = extern_weak global i32' %t && +// RUN: clang-cc -emit-llvm -triple i386-linux-gnu -o %t %s && +// RUN: FileCheck --input-file=%t %s -void t1() __attribute__((noreturn)); -void t1() {} +// CHECK: @t5 = weak global i32 2 +int t5 __attribute__((weak)) = 2; -void t2() __attribute__((nothrow)); -void t2() {} +// CHECK: @t13 = global %0 zeroinitializer, section "SECT" +struct s0 { int x; }; +struct s0 t13 __attribute__((section("SECT"))) = { 0 }; -void t3() __attribute__((weak)); -void t3() {} +// CHECK: @t14.x = internal global i32 0, section "SECT" +void t14(void) { + static int x __attribute__((section("SECT"))) = 0; +} -void t4() __attribute__((visibility("hidden"))); -void t4() {} +// CHECK: @t18 = global i32 1, align 4 +extern int t18 __attribute__((weak_import)); +int t18 = 1; -int t5 __attribute__((weak)) = 2; +// CHECK: @t16 = extern_weak global i32 +extern int t16 __attribute__((weak_import)); +// CHECK: @t6 = common protected global i32 0 int t6 __attribute__((visibility("protected"))); -void t7() __attribute__((noreturn, nothrow)); -void t7() {} +// CHECK: @t12 = global i32 0, section "SECT" +int t12 __attribute__((section("SECT"))); +// CHECK: @t9 = alias weak bitcast (void ()* @__t8 to void (...)*) void __t8() {} void t9() __attribute__((weak, alias("__t8"))); -void t10(void) __attribute__((section("SECT"))); -void t10(void) {} -void __attribute__((section("SECT"))) t11(void) {} - -int t12 __attribute__((section("SECT"))); -struct s0 { int x; }; -struct s0 t13 __attribute__((section("SECT"))) = { 0 }; - -void t14(void) { - static int x __attribute__((section("SECT"))) = 0; -} - +// CHECK: declare extern_weak i32 @t15() int __attribute__((weak_import)) t15(void); -extern int t16 __attribute__((weak_import)); int t17() { return t15() + t16; } -// RUN: grep '@t18 = global i[0-9]* 1, align .*' %t && -extern int t18 __attribute__((weak_import)); -int t18 = 1; +// CHECK: define void @t1() noreturn nounwind { +void t1() __attribute__((noreturn)); +void t1() { while (1) {} } + +// CHECK: define void @t2() nounwind { +void t2() __attribute__((nothrow)); +void t2() {} -// RUN: grep 'define i[0-9]* @t19()' %t && +// CHECK: define weak void @t3() nounwind { +void t3() __attribute__((weak)); +void t3() {} + +// CHECK: define hidden void @t4() nounwind { +void t4() __attribute__((visibility("hidden"))); +void t4() {} + +// CHECK: define void @t7() noreturn nounwind { +void t7() __attribute__((noreturn, nothrow)); +void t7() { while (1) {} } + +// CHECK: define void @t10() nounwind section "SECT" { +void t10(void) __attribute__((section("SECT"))); +void t10(void) {} +// CHECK: define void @t11() nounwind section "SECT" { +void __attribute__((section("SECT"))) t11(void) {} + +// CHECK: define i32 @t19() nounwind { extern int t19(void) __attribute__((weak_import)); int t19(void) { return 10; } -// RUN: true +// CHECK:define void @t20() nounwind { +// CHECK-NEXT:entry: +// CHECK-NEXT: call void @abort() +// CHECK-NEXT: unreachable +void t20(void) { + __builtin_abort(); +} diff --git a/test/CodeGen/blocks-2.c b/test/CodeGen/blocks-2.c index 5ee2a73..bc6c2b9 100644 --- a/test/CodeGen/blocks-2.c +++ b/test/CodeGen/blocks-2.c @@ -1,6 +1,7 @@ -// RUN: clang-cc -g %s -emit-llvm -o %t -fblocks +// RUN: clang-cc -g %s -emit-llvm -o %t -fblocks && // RUN: grep "func.start" %t | count 4 // 1 declaration, 1 bar, 1 test_block_dbg and 1 for the block. +// XFAIL static __inline__ __attribute__((always_inline)) int bar(int va, int vb) { return (va == vb); } diff --git a/test/CodeGen/blocks-aligned-byref-variable.c b/test/CodeGen/blocks-aligned-byref-variable.c new file mode 100644 index 0000000..1ae3062 --- /dev/null +++ b/test/CodeGen/blocks-aligned-byref-variable.c @@ -0,0 +1,19 @@ +// RUN: clang-cc -emit-llvm -o - -triple x86_64-apple-darwin10 && +// RUN: clang-cc -emit-llvm -o - -triple i386-apple-darwin10 +typedef int __attribute__((aligned(32))) ai; + +void f() { + __block ai a = 10; + + ^{ + a = 20; + }(); +} + +void g() { + __block double a = 10; + + ^{ + a = 20; + }(); +} diff --git a/test/CodeGen/blocks-seq.c b/test/CodeGen/blocks-seq.c index f637fbc..3ff241e 100644 --- a/test/CodeGen/blocks-seq.c +++ b/test/CodeGen/blocks-seq.c @@ -1,13 +1,13 @@ -// RUN: clang-cc -fblocks -triple x86_64-apple-darwin10 -emit-llvm -o %t %s && -// RUN: grep '%call = call i32 (...)\* @rhs()' %t | count 1 && -// If this fails, see about sliding %4, %5, %6 and %7... -// RUN: grep '%forwarding1 = getelementptr %0\* %i, i32 0, i32 1' %t | count 1 && -// RUN: grep '%4 = bitcast i8\*\* %forwarding1 to %0\*\*' %t | count 1 && -// RUN: grep '%5 = load %0\*\* %4' %t | count 1 && -// RUN: grep '%call2 = call i32 (...)\* @rhs()' %t | count 1 && -// RUN: grep '%forwarding3 = getelementptr %0\* %i, i32 0, i32 1' %t | count 1 && -// RUN: grep '%6 = bitcast i8\*\* %forwarding3 to %0\*\*' %t | count 1 && -// RUN: grep '%7 = load %0\*\* %6' %t | count 1 +// FIXME: We forcibly strip the names so that the test doesn't vary between +// builds with and without asserts. We need a better solution for this. + +// RUN: clang-cc -fblocks -triple x86_64-apple-darwin10 -emit-llvm-bc -o - %s | opt -strip | llvm-dis > %t && +// RUN: grep '%6 = call i32 (...)\* @rhs()' %t | count 1 && +// RUN: grep '%7 = getelementptr inbounds %0\* %1, i32 0, i32 1' %t | count 1 && +// RUN: grep '%8 = load %0\*\* %7' %t | count 1 && +// RUN: grep '%10 = call i32 (...)\* @rhs()' %t | count 1 && +// RUN: grep '%11 = getelementptr inbounds %0\* %1, i32 0, i32 1' %t | count 1 && +// RUN: grep '%12 = load %0\*\* %11' %t | count 1 int rhs(); diff --git a/test/CodeGen/boolassign.c b/test/CodeGen/boolassign.c index 2d14f8c..73aab8d 100644 --- a/test/CodeGen/boolassign.c +++ b/test/CodeGen/boolassign.c @@ -1,6 +1,7 @@ // RUN: clang-cc %s -emit-llvm -o %t int testBoolAssign(void) { -int ss; -if ((ss = ss && ss)) {} + int ss; + if ((ss = ss && ss)) {} + return 1; } diff --git a/test/CodeGen/builtin-attributes.c b/test/CodeGen/builtin-attributes.c new file mode 100644 index 0000000..184e967 --- /dev/null +++ b/test/CodeGen/builtin-attributes.c @@ -0,0 +1,12 @@ +// RUN: clang-cc -triple arm-unknown-unknown -emit-llvm -o - %s | FileCheck %s + +// CHECK: declare arm_aapcscc i32 @printf(i8*, ...) +void f0() { + printf("a\n"); +} + +// CHECK: call arm_aapcscc void @exit +// CHECK: unreachable +void f1() { + exit(1); +} diff --git a/test/CodeGen/builtins-ffs_parity_popcount.c b/test/CodeGen/builtins-ffs_parity_popcount.c index 4746998..e3fa4d2 100644 --- a/test/CodeGen/builtins-ffs_parity_popcount.c +++ b/test/CodeGen/builtins-ffs_parity_popcount.c @@ -1,5 +1,5 @@ -// RUN: clang-cc -emit-llvm -o - %s > %t -// RUN: ! grep "__builtin" %t +// RUN: clang-cc -emit-llvm -o - %s > %t && +// RUN: not grep "__builtin" %t #include diff --git a/test/CodeGen/builtins-powi.c b/test/CodeGen/builtins-powi.c index 73f752f..5b413a8 100644 --- a/test/CodeGen/builtins-powi.c +++ b/test/CodeGen/builtins-powi.c @@ -1,5 +1,5 @@ -// RUN: clang-cc -emit-llvm -o - %s > %t -// RUN: ! grep "__builtin" %t +// RUN: clang-cc -emit-llvm -o - %s > %t && +// RUN: not grep "__builtin" %t #include #include diff --git a/test/CodeGen/builtins.c b/test/CodeGen/builtins.c index ce5cd74..165db9c 100644 --- a/test/CodeGen/builtins.c +++ b/test/CodeGen/builtins.c @@ -54,6 +54,8 @@ int main() { P(islessgreater, (1., 2.)); P(isunordered, (1., 2.)); + P(isnan, (1.)); + // Bitwise & Numeric Functions P(abs, (N)); diff --git a/test/CodeGen/cast-to-union.c b/test/CodeGen/cast-to-union.c index 6098bcc..6742992 100644 --- a/test/CodeGen/cast-to-union.c +++ b/test/CodeGen/cast-to-union.c @@ -1,7 +1,7 @@ -// RUN: clang-cc -emit-llvm < %s -o %t && -// RUN: grep "store i32 351, i32*" %t && -// RUN: grep "w = global %0 <{ i32 2, i8 0, i8 0, i8 0, i8 0 }>" %t && -// RUN: grep "y = global %1 <{ double 7.300000e+01 }>" %t +// RUN: clang-cc -emit-llvm %s -o - | FileCheck %s +// CHECK: w = global %0 { i32 2, [4 x i8] zeroinitializer } +// CHECK: y = global %union.u { double 7.300000e+0{{[0]*}}1 } +// CHECK: store i32 351, i32 union u { int i; double d; }; diff --git a/test/CodeGen/conditional.c b/test/CodeGen/conditional.c index 2228670..8a30463 100644 --- a/test/CodeGen/conditional.c +++ b/test/CodeGen/conditional.c @@ -1,11 +1,10 @@ // RUN: clang-cc -emit-llvm %s -o %t -float test1(int cond, float a, float b) -{ +float test1(int cond, float a, float b) { return cond ? a : b; } -double test2(int cond, float a, double b) -{ + +double test2(int cond, float a, double b) { return cond ? a : b; } @@ -16,8 +15,8 @@ void test3(){ } void test4() { -int i; short j; -float* k = 1 ? &i : &j; + int i; short j; + float* k = 1 ? &i : &j; } void test5() { @@ -33,12 +32,10 @@ void* test8() {return 1 ? test6 : test7;} void _efree(void *ptr); -void _php_stream_free3() -{ - (1 ? free(0) : _efree(0)); +void _php_stream_free3() { + (1 ? free(0) : _efree(0)); } -void _php_stream_free4() -{ - 1 ? _efree(0) : free(0); +void _php_stream_free4() { + 1 ? _efree(0) : free(0); } diff --git a/test/CodeGen/const-init.c b/test/CodeGen/const-init.c index 0364cc1..29e9c55 100644 --- a/test/CodeGen/const-init.c +++ b/test/CodeGen/const-init.c @@ -1,4 +1,4 @@ -// RUN: clang-cc -triple i386-pc-linux-gnu -verify -emit-llvm -o %t %s && +// RUN: clang-cc -triple i386-pc-linux-gnu -verify -emit-llvm -o - %s | FileCheck %s #include @@ -22,44 +22,57 @@ union s2 { int g0 = (int)(&(((union s2 *) 0)->f0.f0) - 0); -// RUN: grep '@g1x = global %. { double 1.000000e+00, double 0.000000e+00 }' %t && +// CHECK: @g1x = global {{%.}} { double 1.000000e+00{{[0]*}}, double 0.000000e+00{{[0]*}} } _Complex double g1x = 1.0f; -// RUN: grep '@g1y = global %. { double 0.000000e+00, double 1.000000e+00 }' %t && +// CHECK: @g1y = global {{%.}} { double 0.000000e+00{{[0]*}}, double 1.000000e+00{{[0]*}} } _Complex double g1y = 1.0fi; -// RUN: grep '@g1 = global %. { i8 1, i8 10 }' %t && +// CHECK: @g1 = global {{%.}} { i8 1, i8 10 } _Complex char g1 = (char) 1 + (char) 10 * 1i; -// RUN: grep '@g2 = global %2 { i32 1, i32 10 }' %t && +// CHECK: @g2 = global %2 { i32 1, i32 10 } _Complex int g2 = 1 + 10i; -// RUN: grep '@g3 = global %. { float 1.000000e+00, float 1.000000e+01 }' %t && +// CHECK: @g3 = global {{%.}} { float 1.000000e+00{{[0]*}}, float 1.000000e+0{{[0]*}}1 } _Complex float g3 = 1.0 + 10.0i; -// RUN: grep '@g4 = global %. { double 1.000000e+00, double 1.000000e+01 }' %t && +// CHECK: @g4 = global {{%.}} { double 1.000000e+00{{[0]*}}, double 1.000000e+0{{[0]*}}1 } _Complex double g4 = 1.0 + 10.0i; -// RUN: grep '@g5 = global %2 zeroinitializer' %t && +// CHECK: @g5 = global %2 zeroinitializer _Complex int g5 = (2 + 3i) == (5 + 7i); -// RUN: grep '@g6 = global %. { double -1.100000e+01, double 2.900000e+01 }' %t && +// CHECK: @g6 = global {{%.}} { double -1.100000e+0{{[0]*}}1, double 2.900000e+0{{[0]*}}1 } _Complex double g6 = (2.0 + 3.0i) * (5.0 + 7.0i); -// RUN: grep '@g7 = global i32 1' %t && +// CHECK: @g7 = global i32 1 int g7 = (2 + 3i) * (5 + 7i) == (-11 + 29i); -// RUN: grep '@g8 = global i32 1' %t && +// CHECK: @g8 = global i32 1 int g8 = (2.0 + 3.0i) * (5.0 + 7.0i) == (-11.0 + 29.0i); -// RUN: grep '@g9 = global i32 0' %t && +// CHECK: @g9 = global i32 0 int g9 = (2 + 3i) * (5 + 7i) != (-11 + 29i); -// RUN: grep '@g10 = global i32 0' %t && +// CHECK: @g10 = global i32 0 int g10 = (2.0 + 3.0i) * (5.0 + 7.0i) != (-11.0 + 29.0i); +// PR5108 +// CHECK: @gv1 = global %4 <{ i32 0, i8 7 }>, align 1 +struct { + unsigned long a; + unsigned long b:3; +} __attribute__((__packed__)) gv1 = { .a = 0x0, .b = 7, }; + +// PR5118 +// CHECK: @gv2 = global %5 <{ i8 1, i8* null }>, align 1 +struct { + unsigned char a; + char *b; +} __attribute__((__packed__)) gv2 = { 1, (void*)0 }; // Global references -// RUN: grep '@g11.l0 = internal global i32 ptrtoint (i32 ()\* @g11 to i32)' %t && +// CHECK: @g11.l0 = internal global i32 ptrtoint (i32 ()* @g11 to i32) long g11() { static long l0 = (long) g11; return l0; } -// RUN: grep '@g12 = global i32 ptrtoint (i8\* @g12_tmp to i32)' %t && +// CHECK: @g12 = global i32 ptrtoint (i8* @g12_tmp to i32) static char g12_tmp; long g12 = (long) &g12_tmp; -// RUN: grep '@g13 = global \[1 x .struct.g13_s0\] \[.struct.g13_s0 <{ i32 ptrtoint (i8\* @g12_tmp to i32) }>\]' %t && +// CHECK: @g13 = global [1 x %struct.g13_s0] [%struct.g13_s0 { i32 ptrtoint (i8* @g12_tmp to i32) }] struct g13_s0 { long a; }; @@ -67,26 +80,25 @@ struct g13_s0 g13[] = { { (long) &g12_tmp } }; -// RUN: grep '@g14 = global i8\* inttoptr (i64 100 to i8\*)' %t && +// CHECK: @g14 = global i8* inttoptr (i64 100 to i8*) void *g14 = (void*) 100; -// RUN: grep '@g15 = global i32 -1' %t && +// CHECK: @g15 = global i32 -1 int g15 = (int) (char) ((void*) 0 + 255); -// RUN: grep '@g16 = global i64 4294967295' %t && +// CHECK: @g16 = global i64 4294967295 long long g16 = (long long) ((void*) 0xFFFFFFFF); -// RUN: grep '@g17 = global i32\* @g15' %t && +// CHECK: @g17 = global i32* @g15 int *g17 = (int *) ((long) &g15); -// RUN: grep '@g18.p = internal global \[1 x i32\*\] \[i32\* @g19\]' %t && +// CHECK: @g18.p = internal global [1 x i32*] [i32* @g19] void g18(void) { extern int g19; static int *p[] = { &g19 }; } -// RUN: grep '@g20.l0 = internal global .struct.g20_s1 <{ .struct.g20_s0\* null, .struct.g20_s0\*\* getelementptr (.struct.g20_s1\* @g20.l0, i32 0, i32 0) }>' %t && - +// CHECK: @g20.l0 = internal global %struct.g20_s1 { %struct.g20_s0* null, %struct.g20_s0** getelementptr inbounds (%struct.g20_s1* @g20.l0, i32 0, i32 0) } struct g20_s0; struct g20_s1 { struct g20_s0 *f0, **f1; @@ -99,6 +111,3 @@ void *g20(void) { // PR4108 struct g21 {int g21;}; const struct g21 g21 = (struct g21){1}; - -// RUN: true - diff --git a/test/CodeGen/darwin-string-literals.c b/test/CodeGen/darwin-string-literals.c index ff245fc..04e43a2 100644 --- a/test/CodeGen/darwin-string-literals.c +++ b/test/CodeGen/darwin-string-literals.c @@ -1,10 +1,16 @@ -// RUN: clang-cc -triple i386-apple-darwin9 -emit-llvm %s -o %t && +// RUN: clang-cc -triple i386-apple-darwin9 -emit-llvm %s -o - | FileCheck -check-prefix LSB %s && -// RUN: grep -F '@"\01LC" = internal constant [8 x i8] c"string0\00"' %t && -// RUN: grep -F '@"\01LC1" = internal constant [8 x i8] c"string1\00", section "__TEXT,__cstring,cstring_literals"' %t && -// RUN: grep -F '@__utf16_string_ = internal global [35 x i8] c"h\00e\00l\00l\00o\00 \00\92! \00\03& \00\90! \00w\00o\00r\00l\00d\00\00", section "__TEXT,__ustring", align 2' %t && -// RUN: true +// CHECK-LSB: @.str = private constant [8 x i8] c"string0\00" +// CHECK-LSB: @.str1 = private constant [8 x i8] c"string1\00" +// CHECK-LSB: @.str2 = internal constant [36 x i8] c"h\00e\00l\00l\00o\00 \00\92! \00\03& \00\90! \00w\00o\00r\00l\00d\00\00\00", section "__TEXT,__ustring", align 2 + +// RUN: clang-cc -triple powerpc-apple-darwin9 -emit-llvm %s -o - | FileCheck -check-prefix MSB %s + +// CHECK-MSB: @.str = private constant [8 x i8] c"string0\00" +// CHECK-MSB: @.str1 = private constant [8 x i8] c"string1\00" +// CHECK-MSB: @.str2 = internal constant [36 x i8] c"\00h\00e\00l\00l\00o\00 !\92\00 &\03\00 !\90\00 \00w\00o\00r\00l\00d\00\00", section "__TEXT,__ustring", align 2 const char *g0 = "string0"; const void *g1 = __builtin___CFStringMakeConstantString("string1"); const void *g2 = __builtin___CFStringMakeConstantString("hello \u2192 \u2603 \u2190 world"); +const void *g3 = __builtin___CFStringMakeConstantString("testâ„¢"); diff --git a/test/CodeGen/debug-info.c b/test/CodeGen/debug-info.c index e0ec2c9..beee7ac 100644 --- a/test/CodeGen/debug-info.c +++ b/test/CodeGen/debug-info.c @@ -24,14 +24,14 @@ char xpto[]; // PR3427 struct foo { - int a; - void *ptrs[]; + int a; + void *ptrs[]; }; struct foo bar; // PR4143 struct foo2 { - enum bar *bar; + enum bar *bar; }; struct foo2 foo2; diff --git a/test/CodeGen/designated-initializers.c b/test/CodeGen/designated-initializers.c index 4669339..f20bc78 100644 --- a/test/CodeGen/designated-initializers.c +++ b/test/CodeGen/designated-initializers.c @@ -1,5 +1,6 @@ -// RUN: clang-cc -triple i386-unknown-unknown %s -emit-llvm -o - | grep "<{ i8\* null, i32 1024 }>" && -// RUN: clang-cc -triple i386-unknown-unknown %s -emit-llvm -o - | grep "i32 0, i32 22" +// RUN: clang-cc -triple i386-unknown-unknown %s -emit-llvm -o %t && +// RUN: grep "{ i8\* null, i32 1024 }" %t && +// RUN: grep "i32 0, i32 22" %t struct foo { void *a; diff --git a/test/CodeGen/exprs.c b/test/CodeGen/exprs.c index 36cfff9..a0e5b76 100644 --- a/test/CodeGen/exprs.c +++ b/test/CodeGen/exprs.c @@ -15,7 +15,7 @@ void *test(int *i) { } _Bool test2b; -int test2() {if (test2b);} +int test2() { if (test2b); return 0; } // PR1921 int test3() { @@ -48,9 +48,9 @@ int ola() { // this one shouldn't fold as well void eMaisUma() { - double t[1]; - if (*t) - return; + double t[1]; + if (*t) + return; } // rdar://6520707 diff --git a/test/CodeGen/ext-vector-shuffle.c b/test/CodeGen/ext-vector-shuffle.c index 37d3ed4..f53db94 100644 --- a/test/CodeGen/ext-vector-shuffle.c +++ b/test/CodeGen/ext-vector-shuffle.c @@ -1,5 +1,5 @@ -// RUN: clang-cc %s -emit-llvm -o - | not grep 'extractelement' -// RUN: clang-cc %s -emit-llvm -o - | not grep 'insertelement' +// RUN: clang-cc %s -emit-llvm -o - | not grep 'extractelement' && +// RUN: clang-cc %s -emit-llvm -o - | not grep 'insertelement' && // RUN: clang-cc %s -emit-llvm -o - | grep 'shufflevector' typedef __attribute__(( ext_vector_type(2) )) float float2; diff --git a/test/CodeGen/ext-vector.c b/test/CodeGen/ext-vector.c index e3b6211..6a246db 100644 --- a/test/CodeGen/ext-vector.c +++ b/test/CodeGen/ext-vector.c @@ -115,9 +115,21 @@ void test7(int4 *ap, int4 *bp, int c) { a /= c; a %= c; - // Vector comparisons can sometimes crash the x86 backend: rdar://6326239, - // reject them until the implementation is stable. -#if 0 + // Vector comparisons. + int4 cmp; + cmp = a < b; + cmp = a <= b; + cmp = a < b; + cmp = a >= b; + cmp = a == b; + cmp = a != b; +} + +void test8(float4 *ap, float4 *bp, int c) { + float4 a = *ap; + float4 b = *bp; + + // Vector comparisons. int4 cmp; cmp = a < b; cmp = a <= b; @@ -125,5 +137,4 @@ void test7(int4 *ap, int4 *bp, int c) { cmp = a >= b; cmp = a == b; cmp = a != b; -#endif } diff --git a/test/CodeGen/function-attributes.c b/test/CodeGen/function-attributes.c index ba2e4e4..d2d3b03 100644 --- a/test/CodeGen/function-attributes.c +++ b/test/CodeGen/function-attributes.c @@ -56,7 +56,7 @@ int ai_1() { return 4; } static __inline__ __attribute__((always_inline)) struct { int a, b, c, d, e; -} ai_2() { } +} ai_2() { while (1) {} } int foo() { diff --git a/test/CodeGen/functions.c b/test/CodeGen/functions.c index 12dff1b..dba2931 100644 --- a/test/CodeGen/functions.c +++ b/test/CodeGen/functions.c @@ -3,11 +3,11 @@ int g(); int foo(int i) { - return g(i); + return g(i); } int g(int i) { - return g(i); + return g(i); } // rdar://6110827 @@ -32,6 +32,7 @@ void f1() {} // RUN: grep 'define .* @f3' %t | not grep -F '...' struct foo { int X, Y, Z; } f3() { + while (1) {} } // PR4423 - This shouldn't crash in codegen diff --git a/test/CodeGen/global-decls.c b/test/CodeGen/global-decls.c index 80222ea..decb6a9 100644 --- a/test/CodeGen/global-decls.c +++ b/test/CodeGen/global-decls.c @@ -11,7 +11,7 @@ int g0_common __attribute__((weak)); // RUN: grep '@g0_def = weak global i32' %t && int g0_def __attribute__((weak)) = 52; // RUN: grep 'define weak i32 @g1_def()' %t && -int __attribute__((weak)) g1_def (void) {} +int __attribute__((weak)) g1_def (void) { return 0; } // Force _ext references void f0() { diff --git a/test/CodeGen/global-init.c b/test/CodeGen/global-init.c index 4b769f8..2368422 100644 --- a/test/CodeGen/global-init.c +++ b/test/CodeGen/global-init.c @@ -1,7 +1,30 @@ -// RUN: clang-cc -emit-llvm -o - %s | not grep "common" +// RUN: clang-cc -emit-llvm -o - -triple i386-linux-gnu %s | FileCheck %s // This checks that the global won't be marked as common. // (It shouldn't because it's being initialized). int a; int a = 242; +// CHECK: @a = global i32 242 + +// This should get normal weak linkage. +int c __attribute__((weak))= 0; +// CHECK: @c = weak global i32 0 + + + +// Since this is marked const, it should get weak_odr linkage, since all +// definitions have to be the same. +// CHECK: @d = weak_odr constant i32 0 +const int d __attribute__((weak))= 0; + + + +// NOTE: tentative definitions are processed at the end of the translation unit. + +// This shouldn't be emitted as common because it has an explicit section. +// rdar://7119244 +int b __attribute__((section("foo"))); + +// CHECK: @b = global i32 0, section "foo" + diff --git a/test/CodeGen/global-with-initialiser.c b/test/CodeGen/global-with-initialiser.c index 29b4e21..d253782 100644 --- a/test/CodeGen/global-with-initialiser.c +++ b/test/CodeGen/global-with-initialiser.c @@ -17,9 +17,9 @@ long double globalLongDouble = 1; long double globalLongDoubleArray[5] = { 1.0, 2.0 }; struct Struct { - int member1; - float member2; - char *member3; + int member1; + float member2; + char *member3; }; struct Struct globalStruct = { 1, 2.0f, "foobar"}; diff --git a/test/CodeGen/globalinit.c b/test/CodeGen/globalinit.c index 2798cae..b3d0cb5 100644 --- a/test/CodeGen/globalinit.c +++ b/test/CodeGen/globalinit.c @@ -37,7 +37,7 @@ static int a = { 1 }; // References to enums. enum { - EnumA, EnumB + EnumA, EnumB }; int c[] = { EnumA, EnumB }; diff --git a/test/CodeGen/init-with-member-expr.c b/test/CodeGen/init-with-member-expr.c index 7750dbf..197a9ab 100644 --- a/test/CodeGen/init-with-member-expr.c +++ b/test/CodeGen/init-with-member-expr.c @@ -14,7 +14,7 @@ typedef struct mark_header_tag { } mark_header_t; int is_rar_archive(int fd) { const mark_header_t rar_hdr[2] = {{0x52, 0x61, 0x72, 0x21, 0x1a, 0x07, 0x00}, {'U', 'n', 'i', 'q', 'u', 'E', '!'}}; - foo(rar_hdr); + foo(rar_hdr); return 0; } diff --git a/test/CodeGen/inline.c b/test/CodeGen/inline.c index 234f1f8..bf17fd7 100644 --- a/test/CodeGen/inline.c +++ b/test/CodeGen/inline.c @@ -1,5 +1,5 @@ -// RUN: echo "C89 tests:" && -// RUN: clang %s -emit-llvm -S -o %t -std=c89 && +// RUN: echo "GNU89 tests:" && +// RUN: clang %s -emit-llvm -S -o %t -std=gnu89 && // RUN: grep "define available_externally i32 @ei()" %t && // RUN: grep "define i32 @foo()" %t && // RUN: grep "define i32 @bar()" %t && @@ -24,9 +24,9 @@ // RUN: grep "define available_externally void @gnu_ei_inline()" %t && // RUN: grep "define i32 @test1" %t && // RUN: grep "define i32 @test2" %t && -// RUN: grep "define available_externally void @test3" %t && +// RUN: grep "define void @test3" %t && // RUN: grep "define available_externally i32 @test4" %t && -// RUN: grep "define i32 @test5" %t && +// RUN: grep "define available_externally i32 @test5" %t && // RUN: echo "\nC++ tests:" && // RUN: clang %s -emit-llvm -S -o %t -std=c++98 && @@ -67,20 +67,20 @@ void test_test2() { test2(); } // PR3989 extern __inline void test3() __attribute__((gnu_inline)); -__inline void test3() {} - -void test_test3() { test3(); } +__inline void __attribute__((gnu_inline)) test3() {} extern int test4(void); extern __inline __attribute__ ((__gnu_inline__)) int test4(void) { + return 0; } void test_test4() { test4(); } -extern __inline int test5(void); +extern __inline int test5(void) __attribute__ ((__gnu_inline__)); extern __inline int __attribute__ ((__gnu_inline__)) test5(void) { + return 0; } void test_test5() { test5(); } diff --git a/test/CodeGen/inline2.c b/test/CodeGen/inline2.c new file mode 100644 index 0000000..6f165f5 --- /dev/null +++ b/test/CodeGen/inline2.c @@ -0,0 +1,62 @@ +// RUN: clang-cc -std=gnu89 -triple i386-apple-darwin9 -emit-llvm %s -o - | FileCheck -check-prefix GNU89 %s && +// RUN: clang-cc -std=c99 -triple i386-apple-darwin9 -emit-llvm %s -o - | FileCheck -check-prefix C99 %s + +// CHECK-GNU89: define i32 @f0() +// CHECK-C99: define i32 @f0() +int f0(void); +int f0(void) { return 0; } + +// CHECK-GNU89: define i32 @f1() +// CHECK-C99: define i32 @f1() +inline int f1(void); +int f1(void) { return 0; } + +// CHECK-GNU89: define i32 @f2() +// CHECK-C99: define i32 @f2() +int f2(void); +inline int f2(void) { return 0; } + +// CHECK-GNU89: define i32 @f3() +// CHECK-C99: define i32 @f3() +extern inline int f3(void); +int f3(void) { return 0; } + +// CHECK-GNU89: define i32 @f5() +// CHECK-C99: define i32 @f5() +extern inline int f5(void); +inline int f5(void) { return 0; } + +// CHECK-GNU89: define i32 @f6() +// CHECK-C99: define i32 @f6() +inline int f6(void); +extern inline int f6(void) { return 0; } + +// CHECK-GNU89: define i32 @f7() +// CHECK-C99: define i32 @f7() +extern inline int f7(void); +extern int f7(void) { return 0; } + +// CHECK-GNU89: define i32 @fA() +inline int fA(void) { return 0; } + +// CHECK-GNU89: define available_externally i32 @f4() +// CHECK-C99: define i32 @f4() +int f4(void); +extern inline int f4(void) { return 0; } + +// CHECK-GNU89: define available_externally i32 @f8() +// CHECK-C99: define i32 @f8() +extern int f8(void); +extern inline int f8(void) { return 0; } + +// CHECK-GNU89: define available_externally i32 @f9() +// CHECK-C99: define i32 @f9() +extern inline int f9(void); +extern inline int f9(void) { return 0; } + +// CHECK-C99: define available_externally i32 @fA() + +int test_all() { + return f0() + f1() + f2() + f3() + f4() + f5() + f6() + f7() + f8() + f9() + + fA(); +} diff --git a/test/CodeGen/packed-union.c b/test/CodeGen/packed-union.c new file mode 100644 index 0000000..d11d3a4 --- /dev/null +++ b/test/CodeGen/packed-union.c @@ -0,0 +1,16 @@ +// RUN: clang-cc -triple x86_64-apple-darwin10 -emit-llvm %s -o %t && + +// RUN: grep "struct._attrs = type <{ i32, i8 }>" %t && +typedef struct _attrs { + unsigned file_attributes; + unsigned char filename_length; +} __attribute__((__packed__)) attrs; + +// RUN: grep "union._attr_union = type <{ i32, i8 }>" %t +typedef union _attr_union { + attrs file_attrs; + unsigned owner_id; +} __attribute__((__packed__)) attr_union; + +attr_union u; + diff --git a/test/CodeGen/parameter-passing.c b/test/CodeGen/parameter-passing.c index 2ace299..dce0ff8 100644 --- a/test/CodeGen/parameter-passing.c +++ b/test/CodeGen/parameter-passing.c @@ -11,7 +11,7 @@ // RUN: clang-cc %s -triple x86_64-unknown-unknown -O3 -emit-llvm -o %t && // RUN: not grep '@g0' %t && -// RUN: clang-cc %s -triple ppc-unknown-unknown -O3 -emit-llvm -o %t && +// RUN: clang-cc %s -triple powerpc-unknown-unknown -O3 -emit-llvm -o %t && // RUN: not grep '@g0' %t && // RUN: true diff --git a/test/CodeGen/pragma-pack-1.c b/test/CodeGen/pragma-pack-1.c new file mode 100644 index 0000000..bcfcd5a --- /dev/null +++ b/test/CodeGen/pragma-pack-1.c @@ -0,0 +1,7 @@ +// RUN: clang-cc -emit-llvm -o - + +// PR4610 +#pragma pack(4) +struct ref { + struct ref *next; +} refs; diff --git a/test/CodeGen/pragma-pack-2.c b/test/CodeGen/pragma-pack-2.c new file mode 100644 index 0000000..306f02d --- /dev/null +++ b/test/CodeGen/pragma-pack-2.c @@ -0,0 +1,23 @@ +// RUN: clang-cc -triple i386-apple-darwin9 %s -emit-llvm -o - | FileCheck -check-prefix X32 %s && +// CHECK-X32: %struct.s0 = type { i64, i64, i32, [12 x i32] } +// CHECK-X32: %struct.s1 = type { [15 x i32], %struct.s0 } + +// RUN: clang-cc -triple x86_64-apple-darwin9 %s -emit-llvm -o - | FileCheck -check-prefix X64 %s +// CHECK-X64: %struct.s0 = type <{ i64, i64, i32, [12 x i32] }> +// CHECK-X64: %struct.s1 = type <{ [15 x i32], %struct.s0 }> + +// rdar://problem/7095436 +#pragma pack(4) + +struct s0 { + long long a __attribute__((aligned(8))); + long long b __attribute__((aligned(8))); + unsigned int c __attribute__((aligned(8))); + int d[12]; +} a; + +struct s1 { + int a[15]; + struct s0 b; +} b; + diff --git a/test/CodeGen/pragma-pack-3.c b/test/CodeGen/pragma-pack-3.c new file mode 100644 index 0000000..b9166ae --- /dev/null +++ b/test/CodeGen/pragma-pack-3.c @@ -0,0 +1,19 @@ +// RUN: clang-cc -triple i386-apple-darwin9 %s -emit-llvm -o - | FileCheck -check-prefix X32 %s && +// CHECK-X32: %struct.menu = type <{ i8*, i8, i8 }> +// CHECK-X32: %union.command = type <{ i8*, [2 x i8] }> + +// RUN: clang-cc -triple x86_64-apple-darwin9 %s -emit-llvm -o - | FileCheck -check-prefix X64 %s +// CHECK-X64: %struct.menu = type <{ i8*, i8, i8 }> +// CHECK-X64: %union.command = type <{ i8*, [2 x i8] }> + +// +#pragma pack(push, 2) +typedef union command { + void *windowRef; + struct menu { + void *menuRef; + unsigned char menuItemIndex; + } menu; +} command; + +command c; diff --git a/test/CodeGen/pragma-weak.c b/test/CodeGen/pragma-weak.c new file mode 100644 index 0000000..497039a --- /dev/null +++ b/test/CodeGen/pragma-weak.c @@ -0,0 +1,165 @@ +// RUN: clang-cc -emit-llvm %s -o - -verify | FileCheck %s + +// CHECK: @weakvar = weak global +// CHECK: @__weakvar_alias = common global +// CHECK: @correct_linkage = weak global + + +// CHECK: @both = alias void ()* @__both +// CHECK: @both2 = alias void ()* @__both2 +// CHECK: @both3 = alias weak void ()* @__both3 +// CHECK: @a3 = alias weak void ()* @__a3 +// CHECK: @weakvar_alias = alias weak i32* @__weakvar_alias +// CHECK: @foo = alias weak void ()* @__foo +// CHECK: @foo2 = alias weak void ()* @__foo2 +// CHECK: @stutter = alias weak void ()* @__stutter +// CHECK: @stutter2 = alias weak void ()* @__stutter2 +// CHECK: @declfirst = alias weak void ()* @__declfirst +// CHECK: @declfirstattr = alias weak void ()* @__declfirstattr +// CHECK: @mix2 = alias weak void ()* @__mix2 +// CHECK: @a1 = alias weak void ()* @__a1 +// CHECK: @xxx = alias weak void ()* @__xxx + + + +// CHECK: define weak void @weakdef() + + +#pragma weak weakvar +int weakvar; + +#pragma weak weakdef +void weakdef(void) {} + +#pragma weak param // expected-warning {{weak identifier 'param' never declared}} +#pragma weak correct_linkage +void f(int param) { + int correct_linkage; +} + +#pragma weak weakvar_alias = __weakvar_alias +int __weakvar_alias; + +#pragma weak foo = __foo +void __foo(void) {} +// CHECK: define void @__foo() + + +void __foo2(void) {} +#pragma weak foo2 = __foo2 +// CHECK: define void @__foo2() + + +///// test errors + +#pragma weak unused // expected-warning {{weak identifier 'unused' never declared}} +#pragma weak unused_alias = __unused_alias // expected-warning {{weak identifier '__unused_alias' never declared}} + +#pragma weak td // expected-warning {{weak identifier 'td' never declared}} +typedef int td; + +#pragma weak td2 = __td2 // expected-warning {{weak identifier '__td2' never declared}} +typedef int __td2; + + +///// test weird cases + +// test repeats + +#pragma weak stutter = __stutter +#pragma weak stutter = __stutter +void __stutter(void) {} +// CHECK: define void @__stutter() + +void __stutter2(void) {} +#pragma weak stutter2 = __stutter2 +#pragma weak stutter2 = __stutter2 +// CHECK: define void @__stutter2() + + +// test decl/pragma weak order + +void __declfirst(void); +#pragma weak declfirst = __declfirst +void __declfirst(void) {} +// CHECK: define void @__declfirst() + +void __declfirstattr(void) __attribute((noinline)); +#pragma weak declfirstattr = __declfirstattr +void __declfirstattr(void) {} +// CHECK: define void @__declfirstattr() + +//// test that other attributes are preserved + +//// ensure that pragma weak/__attribute((weak)) play nice + +void mix(void); +#pragma weak mix +__attribute((weak)) void mix(void) { } +// CHECK: define weak void @mix() + +// ensure following __attributes are preserved and that only a single +// alias is generated +#pragma weak mix2 = __mix2 +void __mix2(void) __attribute((noinline)); +void __mix2(void) __attribute((noinline)); +void __mix2(void) {} +// CHECK: define void @__mix2() + +////////////// test #pragma weak/__attribute combinations + +// if the SAME ALIAS is already declared then it overrides #pragma weak +// resulting in a non-weak alias in this case +void both(void) __attribute((alias("__both"))); +#pragma weak both = __both +void __both(void) {} +// CHECK: define void @__both() + +// if the TARGET is previously declared then whichever aliasing method +// comes first applies and subsequent aliases are discarded. +// TODO: warn about this + +void __both2(void); +void both2(void) __attribute((alias("__both2"))); // first, wins +#pragma weak both2 = __both2 +void __both2(void) {} +// CHECK: define void @__both2() + +void __both3(void); +#pragma weak both3 = __both3 // first, wins +void both3(void) __attribute((alias("__both3"))); +void __both3(void) {} +// CHECK: define void @__both3() + +///////////// ensure that #pragma weak does not alter existing __attributes() + +void __a1(void) __attribute((noinline)); +#pragma weak a1 = __a1 +void __a1(void) {} +// CHECK: define void @__a1() + +// attributes introduced BEFORE a combination of #pragma weak and alias() +// hold... +void __a3(void) __attribute((noinline)); +#pragma weak a3 = __a3 +void a3(void) __attribute((alias("__a3"))); +void __a3(void) {} +// CHECK: define void @__a3() + +#pragma weak xxx = __xxx +__attribute((pure,noinline,const,fastcall)) void __xxx(void) { } +// CHECK: void @__xxx() + +/// TODO: stuff that still doesn't work + +// due to the fact that disparate TopLevelDecls cannot affect each other +// (due to clang's Parser and ASTConsumer behavior, and quite reasonable) +// #pragma weak must appear before or within the same TopLevelDecl as it +// references. +void yyy(void){} +void zzz(void){} +#pragma weak yyy +// NOTE: weak doesn't apply, not before or in same TopLevelDec(!) +// CHECK: define void @yyy() + +int correct_linkage; diff --git a/test/CodeGen/predefined-expr.c b/test/CodeGen/predefined-expr.c new file mode 100644 index 0000000..9b64593 --- /dev/null +++ b/test/CodeGen/predefined-expr.c @@ -0,0 +1,45 @@ +// RUN: clang-cc %s -emit-llvm -o - | FileCheck %s + +// CHECK: @__func__.plainFunction = private constant [14 x i8] c"plainFunction\00" +// CHECK: @__PRETTY_FUNCTION__.plainFunction = private constant [21 x i8] c"void plainFunction()\00" +// CHECK: @__func__.externFunction = private constant [15 x i8] c"externFunction\00" +// CHECK: @__PRETTY_FUNCTION__.externFunction = private constant [22 x i8] c"void externFunction()\00" +// CHECK: @__func__.privateExternFunction = private constant [22 x i8] c"privateExternFunction\00" +// CHECK: @__PRETTY_FUNCTION__.privateExternFunction = private constant [29 x i8] c"void privateExternFunction()\00" +// CHECK: @__func__.staticFunction = private constant [15 x i8] c"staticFunction\00" +// CHECK: @__PRETTY_FUNCTION__.staticFunction = private constant [22 x i8] c"void staticFunction()\00" + +#include + +void plainFunction() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); +} + +extern void externFunction() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); +} + +__private_extern__ void privateExternFunction() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); +} + +static void staticFunction() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); +} + +int main() { + plainFunction(); + externFunction(); + privateExternFunction(); + staticFunction(); + + return 0; +} diff --git a/test/CodeGen/regparm.c b/test/CodeGen/regparm.c index fdf07ea..28dfae7 100644 --- a/test/CodeGen/regparm.c +++ b/test/CodeGen/regparm.c @@ -9,11 +9,10 @@ typedef struct { } foo; static void FASTCALL -reduced(char b, double c, foo* d, double e, int f) -{ +reduced(char b, double c, foo* d, double e, int f) { } int main(void) { - reduced(0, 0.0, 0, 0.0, 0); + reduced(0, 0.0, 0, 0.0, 0); } diff --git a/test/CodeGen/stack-protector.c b/test/CodeGen/stack-protector.c index bdac853..0b5924d 100644 --- a/test/CodeGen/stack-protector.c +++ b/test/CodeGen/stack-protector.c @@ -12,8 +12,7 @@ // RUN: not grep 'ssp' %t && // RUN: true -#include -#include +int printf(const char * _Format, ...); void test1(const char *msg) { char a[strlen(msg) + 1]; diff --git a/test/CodeGen/statements.c b/test/CodeGen/statements.c index 1ff7601..45bbd9a 100644 --- a/test/CodeGen/statements.c +++ b/test/CodeGen/statements.c @@ -11,3 +11,25 @@ bar(); int test2() { return; } void test3() { return 4; } + +void test4() { +bar: +baz: +blong: +bing: + ; + +// PR5131 +static long x = &&bar - &&baz; +static long y = &&baz; + &&bing; + &&blong; + if (y) + goto *y; + + goto *x; +} + +// PR3869 +int test5(long long b) { goto *b; } + diff --git a/test/CodeGen/staticinit.c b/test/CodeGen/staticinit.c index 91fcdcf..c68366f 100644 --- a/test/CodeGen/staticinit.c +++ b/test/CodeGen/staticinit.c @@ -2,9 +2,9 @@ // RUN: grep "g.b = internal global i8. getelementptr" %t && struct AStruct { - int i; - char *s; - double d; + int i; + char *s; + double d; }; void f() { diff --git a/test/CodeGen/stdcall-fastcall.c b/test/CodeGen/stdcall-fastcall.c index 11b6521..89ed8c9 100644 --- a/test/CodeGen/stdcall-fastcall.c +++ b/test/CodeGen/stdcall-fastcall.c @@ -1,4 +1,4 @@ -// RUN: clang-cc -emit-llvm < %s | grep 'fastcallcc' | count 4 +// RUN: clang-cc -emit-llvm < %s | grep 'fastcallcc' | count 4 && // RUN: clang-cc -emit-llvm < %s | grep 'stdcallcc' | count 4 void __attribute__((fastcall)) f1(void); diff --git a/test/CodeGen/string-init.c b/test/CodeGen/string-init.c index 38c7ec0..4a80851 100644 --- a/test/CodeGen/string-init.c +++ b/test/CodeGen/string-init.c @@ -1,5 +1,5 @@ // RUN: clang-cc -emit-llvm %s -o %t && -// RUN: grep 'internal constant \[10 x i8\]' %t && +// RUN: grep 'private constant \[10 x i8\]' %t && // RUN: not grep -F "[5 x i8]" %t && // RUN: not grep "store " %t diff --git a/test/CodeGen/struct-init.c b/test/CodeGen/struct-init.c index a38442b..cb84fef 100644 --- a/test/CodeGen/struct-init.c +++ b/test/CodeGen/struct-init.c @@ -2,11 +2,11 @@ typedef struct _zend_ini_entry zend_ini_entry; struct _zend_ini_entry { - void *mh_arg1; + void *mh_arg1; }; char a; const zend_ini_entry ini_entries[] = { - { ((char*)&((zend_ini_entry*)0)->mh_arg1 - (char*)(void*)0)}, + { ((char*)&((zend_ini_entry*)0)->mh_arg1 - (char*)(void*)0)}, }; diff --git a/test/CodeGen/struct-x86-darwin.c b/test/CodeGen/struct-x86-darwin.c index 050e26d..c61005f 100644 --- a/test/CodeGen/struct-x86-darwin.c +++ b/test/CodeGen/struct-x86-darwin.c @@ -1,13 +1,13 @@ -// RUN: clang-cc < %s -emit-llvm > %t1 -triple=i686-apple-darwin9 -// Run grep "STest1 = type <{ i32, \[4 x i16\], double }>" %t1 && -// RUN: grep "STest2 = type <{ i16, i16, i32, i32 }>" %t1 && -// RUN: grep "STest3 = type <{ i8, i8, i16, i32 }>" %t1 && -// RUN: grep "STestB1 = type <{ i8, i8 }>" %t1 && -// RUN: grep "STestB2 = type <{ i8, i8, i8 }>" %t1 && -// RUN: grep "STestB3 = type <{ i8, i8 }>" %t1 && -// RUN: grep "STestB4 = type <{ i8, i8, i8, i8 }>" %t1 && -// RUN: grep "STestB5 = type <{ i8, i8, i8, i8, i8, i8 }>" %t1 && -// RUN: grep "STestB6 = type <{ i8, i8, i8, i8 }>" %t1 +// RUN: clang-cc < %s -emit-llvm > %t1 -triple=i686-apple-darwin9 && +// RUN: grep "STest1 = type { i32, \[4 x i16\], double }" %t1 && +// RUN: grep "STest2 = type { i16, i16, i32, i32 }" %t1 && +// RUN: grep "STest3 = type { i8, i16, i32 }" %t1 && +// RUN: grep "STestB1 = type { i8, i8 }" %t1 && +// RUN: grep "STestB2 = type { i8, i8, i8 }" %t1 && +// RUN: grep "STestB3 = type { i8, i8 }" %t1 && +// RUN: grep "STestB4 = type { i8, i8, i8, i8 }" %t1 && +// RUN: grep "STestB5 = type { i8, i8, \[2 x i8\], i8, i8 }" %t1 && +// RUN: grep "STestB6 = type { i8, i8, \[2 x i8\] }" %t1 // Test struct layout for x86-darwin target struct STest1 {int x; short y[4]; double z; } st1; diff --git a/test/CodeGen/struct.c b/test/CodeGen/struct.c index ed36842..d1e58a2 100644 --- a/test/CodeGen/struct.c +++ b/test/CodeGen/struct.c @@ -70,8 +70,7 @@ typedef struct { int length; } range; extern range f6(); -void f7() -{ +void f7() { range r = f6(); } @@ -81,27 +80,23 @@ typedef struct { range range2; } rangepair; -void f8() -{ +void f8() { rangepair p; range r = p.range1; } -void f9(range *p) -{ +void f9(range *p) { range r = *p; } -void f10(range *p) -{ +void f10(range *p) { range r = p[0]; } /* _Bool types */ -struct _w -{ +struct _w { short a,b; short c,d; short e,f; @@ -113,27 +108,24 @@ struct _w } ws; /* Implicit casts (due to typedefs) */ -typedef struct _a -{ +typedef struct _a { int a; } a; -void f11() -{ - struct _a a1; - a a2; +void f11() { + struct _a a1; + a a2; - a1 = a2; - a2 = a1; + a1 = a2; + a2 = a1; } /* Implicit casts (due to const) */ -void f12() -{ - struct _a a1; - const struct _a a2; - - a1 = a2; +void f12() { + struct _a a1; + const struct _a a2; + + a1 = a2; } /* struct initialization */ @@ -147,8 +139,7 @@ struct a15 {char a; int b[];} c15; int a16(void) {c15.a = 1;} /* compound literals */ -void f13() -{ +void f13() { a13 x; x = (a13){1,2}; } diff --git a/test/CodeGen/union-init.c b/test/CodeGen/union-init.c index c882d31..f4e9e9a 100644 --- a/test/CodeGen/union-init.c +++ b/test/CodeGen/union-init.c @@ -4,19 +4,19 @@ typedef int Py_ssize_t; typedef union _gc_head { - struct { - union _gc_head *gc_next; - union _gc_head *gc_prev; - Py_ssize_t gc_refs; - } gc; - long double dummy; /* force worst-case alignment */ + struct { + union _gc_head *gc_next; + union _gc_head *gc_prev; + Py_ssize_t gc_refs; + } gc; + long double dummy; /* force worst-case alignment */ } PyGC_Head; struct gc_generation { - PyGC_Head head; - int threshold; /* collection threshold */ - int count; /* count of allocations or collections of younger - generations */ + PyGC_Head head; + int threshold; /* collection threshold */ + int count; /* count of allocations or collections of younger + generations */ }; #define NUM_GENERATIONS 3 @@ -24,8 +24,8 @@ struct gc_generation { /* linked lists of container objects */ struct gc_generation generations[NUM_GENERATIONS] = { - /* PyGC_Head, threshold, count */ - {{{GEN_HEAD(0), GEN_HEAD(0), 0}}, 700, 0}, - {{{GEN_HEAD(1), GEN_HEAD(1), 0}}, 10, 0}, - {{{GEN_HEAD(2), GEN_HEAD(2), 0}}, 10, 0}, + /* PyGC_Head, threshold, count */ + {{{GEN_HEAD(0), GEN_HEAD(0), 0}}, 700, 0}, + {{{GEN_HEAD(1), GEN_HEAD(1), 0}}, 10, 0}, + {{{GEN_HEAD(2), GEN_HEAD(2), 0}}, 10, 0}, }; diff --git a/test/CodeGen/union-init2.c b/test/CodeGen/union-init2.c new file mode 100644 index 0000000..184d75f --- /dev/null +++ b/test/CodeGen/union-init2.c @@ -0,0 +1,4 @@ +// RUN: clang-cc -emit-llvm %s -o - -triple i686-pc-linux-gnu | grep "bitcast (%0\* @r to %union.x\*), \[4 x i8\] zeroinitializer" + +// Make sure we generate something sane instead of a ptrtoint +union x {long long b;union x* a;} r = {.a = &r}; diff --git a/test/CodeGen/unreachable.c b/test/CodeGen/unreachable.c new file mode 100644 index 0000000..ea4f047 --- /dev/null +++ b/test/CodeGen/unreachable.c @@ -0,0 +1,37 @@ +// RUN: clang-cc -emit-llvm -o %t %s && +// RUN: grep '@unreachable' %t | count 0 + +extern void abort() __attribute__((noreturn)); +extern int unreachable(); + +int f0() { + return 0; + unreachable(); +} + +int f1(int i) { + goto L0; + int a = unreachable(); + L0: + return 0; +} + +int f2(int i) { + goto L0; + unreachable(); + int a; + unreachable(); + L0: + a = i + 1; + return a; +} + +int f3(int i) { + if (i) { + return 0; + } else { + abort(); + } + unreachable(); + return 3; +} diff --git a/test/CodeGen/unwind-attr.c b/test/CodeGen/unwind-attr.c index 4954a0b..86036f9 100644 --- a/test/CodeGen/unwind-attr.c +++ b/test/CodeGen/unwind-attr.c @@ -2,4 +2,5 @@ // RUN: clang-cc -emit-llvm -o - %s | grep "@foo()" | grep nounwind int foo(void) { + return 0; } diff --git a/test/CodeGen/vector.c b/test/CodeGen/vector.c index 1084f6d..5e48fd4 100644 --- a/test/CodeGen/vector.c +++ b/test/CodeGen/vector.c @@ -1,9 +1,8 @@ // RUN: clang-cc -emit-llvm %s -o - typedef short __v4hi __attribute__ ((__vector_size__ (8))); -void f() -{ - __v4hi A = (__v4hi)0LL; +void f() { + __v4hi A = (__v4hi)0LL; } __v4hi x = {1,2,3}; @@ -15,7 +14,6 @@ int a() { vty b; return b[2LL]; } // PR4339 typedef float vec4 __attribute__((vector_size(16))); -void vac ( vec4* a, char b, float c ) -{ - (*a)[b] = c; +void vac ( vec4* a, char b, float c ) { + (*a)[b] = c; } diff --git a/test/CodeGen/visibility.c b/test/CodeGen/visibility.c index bb9b6e0..958eb61 100644 --- a/test/CodeGen/visibility.c +++ b/test/CodeGen/visibility.c @@ -15,7 +15,7 @@ // RUN: grep 'define internal void @f_deferred()' %t && // RUN: grep 'define protected i32 @f_def()' %t && // RUN: clang-cc -triple i386-unknown-unknown -fvisibility=hidden -emit-llvm -o %t %s && -// RUN: grep '@g_com = common hidden global i32 0' %t &&a +// RUN: grep '@g_com = common hidden global i32 0' %t && // RUN: grep '@g_def = hidden global i32 0' %t && // RUN: grep '@g_ext = external global i32' %t && // RUN: grep '@g_deferred = internal global' %t && diff --git a/test/CodeGen/volatile.c b/test/CodeGen/volatile.c index 212a0ae..87cb5ff 100644 --- a/test/CodeGen/volatile.c +++ b/test/CodeGen/volatile.c @@ -38,7 +38,7 @@ volatile extv4 vVE; volatile struct {int x;} aggFct(void); -void main() { +int main() { int i; // load diff --git a/test/CodeGen/x86.c b/test/CodeGen/x86.c index 66d8251..be09302 100644 --- a/test/CodeGen/x86.c +++ b/test/CodeGen/x86.c @@ -1,4 +1,4 @@ -// RUN: clang-cc %s -triple=i686-pc-linux-gnu -emit-llvm -o - > %t1 +// RUN: clang-cc %s -triple=i686-pc-linux-gnu -emit-llvm -o - > %t1 && // RUN: grep "ax" %t1 && // RUN: grep "bx" %t1 && // RUN: grep "cx" %t1 && diff --git a/test/CodeGen/x86_32-arguments.c b/test/CodeGen/x86_32-arguments.c index 43a3ab2..78fb834 100644 --- a/test/CodeGen/x86_32-arguments.c +++ b/test/CodeGen/x86_32-arguments.c @@ -1,4 +1,4 @@ -// RUN: clang-cc -triple i386-apple-darwin9 -emit-llvm -o %t %s && +// RUN: clang-cc -fblocks -triple i386-apple-darwin9 -emit-llvm -o %t %s && // RUN: grep 'define signext i8 @f0()' %t && // RUN: grep 'define signext i16 @f1()' %t && // RUN: grep 'define i32 @f2()' %t && @@ -11,39 +11,41 @@ // RUN: grep 'define void @f8_2(i32 %a0.0, i32 %a0.1)' %t && char f0(void) { + return 0; } short f1(void) { + return 0; } int f2(void) { + return 0; } float f3(void) { + return 0; } double f4(void) { + return 0; } long double f5(void) { + return 0; } -void f6(char a0, short a1, int a2, long long a3, void *a4) { -} +void f6(char a0, short a1, int a2, long long a3, void *a4) {} typedef enum { A, B, C } E; -void f7(E a0) { -} +void f7(E a0) {} struct s8 { int a; int b; }; -struct s8 f8_1(void) { -} -void f8_2(struct s8 a0) { -} +struct s8 f8_1(void) { while (1) {} } +void f8_2(struct s8 a0) {} // This should be passed just as s8. @@ -56,10 +58,8 @@ struct s9 { int a : 17; int b; }; -struct s9 f9_1(void) { -} -void f9_2(struct s9 a0) { -} +struct s9 f9_1(void) { while (1) {} } +void f9_2(struct s9 a0) {} // Return of small structures and unions @@ -67,7 +67,7 @@ void f9_2(struct s9 a0) { struct s10 { union { }; float f; -} f10(void) {} +} f10(void) { while (1) {} } // Small vectors and 1 x {i64,double} are returned in registers @@ -78,17 +78,17 @@ struct s10 { // RUN: grep '<2 x i64> @f15()' %t && // RUN: grep '<2 x i64> @f16()' %t && typedef short T11 __attribute__ ((vector_size (4))); -T11 f11(void) {} +T11 f11(void) { while (1) {} } typedef int T12 __attribute__ ((vector_size (8))); -T12 f12(void) {} +T12 f12(void) { while (1) {} } typedef long long T13 __attribute__ ((vector_size (8))); -T13 f13(void) {} +T13 f13(void) { while (1) {} } typedef double T14 __attribute__ ((vector_size (8))); -T14 f14(void) {} +T14 f14(void) { while (1) {} } typedef long long T15 __attribute__ ((vector_size (16))); -T15 f15(void) {} +T15 f15(void) { while (1) {} } typedef double T16 __attribute__ ((vector_size (16))); -T16 f16(void) {} +T16 f16(void) { while (1) {} } // And when the single element in a struct (but not for 64 and // 128-bits). @@ -99,64 +99,107 @@ T16 f16(void) {} // RUN: grep -F 'void @f20(%4* noalias sret %agg.result)' %t && // RUN: grep -F 'void @f21(%5* noalias sret %agg.result)' %t && // RUN: grep -F 'void @f22(%6* noalias sret %agg.result)' %t && -struct { T11 a; } f17(void) {} -struct { T12 a; } f18(void) {} -struct { T13 a; } f19(void) {} -struct { T14 a; } f20(void) {} -struct { T15 a; } f21(void) {} -struct { T16 a; } f22(void) {} +struct { T11 a; } f17(void) { while (1) {} } +struct { T12 a; } f18(void) { while (1) {} } +struct { T13 a; } f19(void) { while (1) {} } +struct { T14 a; } f20(void) { while (1) {} } +struct { T15 a; } f21(void) { while (1) {} } +struct { T16 a; } f22(void) { while (1) {} } // Single element structures are handled specially // RUN: grep -F 'float @f23()' %t && // RUN: grep -F 'float @f24()' %t && // RUN: grep -F 'float @f25()' %t && -struct { float a; } f23(void) {} -struct { float a[1]; } f24(void) {} -struct { struct {} a; struct { float a[1]; } b; } f25(void) {} +struct { float a; } f23(void) { while (1) {} } +struct { float a[1]; } f24(void) { while (1) {} } +struct { struct {} a; struct { float a[1]; } b; } f25(void) { while (1) {} } // Small structures are handled recursively // RUN: grep -F 'i32 @f26()' %t && // RUN: grep 'void @f27(%.truct.s27\* noalias sret %agg.result)' %t && -struct s26 { struct { char a, b; } a; struct { char a, b; } b; } f26(void) {} -struct s27 { struct { char a, b, c; } a; struct { char a; } b; } f27(void) {} +struct s26 { struct { char a, b; } a; struct { char a, b; } b; } f26(void) { while (1) {} } +struct s27 { struct { char a, b, c; } a; struct { char a; } b; } f27(void) { while (1) {} } // RUN: grep 'void @f28(%.truct.s28\* noalias sret %agg.result)' %t && -struct s28 { int a; int b[]; } f28(void) {} +struct s28 { int a; int b[]; } f28(void) { while (1) {} } // RUN: grep 'define i16 @f29()' %t && -struct s29 { struct { } a[1]; char b; char c; } f29(void) {} +struct s29 { struct { } a[1]; char b; char c; } f29(void) { while (1) {} } // RUN: grep 'define i16 @f30()' %t && -struct s30 { char a; char b : 4; } f30(void) {} +struct s30 { char a; char b : 4; } f30(void) { while (1) {} } // RUN: grep 'define float @f31()' %t && -struct s31 { char : 0; float b; char : 0; } f31(void) {} +struct s31 { char : 0; float b; char : 0; } f31(void) { while (1) {} } // RUN: grep 'define i32 @f32()' %t && -struct s32 { char a; unsigned : 0; } f32(void) {} +struct s32 { char a; unsigned : 0; } f32(void) { while (1) {} } // RUN: grep 'define float @f33()' %t && -struct s33 { float a; long long : 0; } f33(void) {} +struct s33 { float a; long long : 0; } f33(void) { while (1) {} } // RUN: grep 'define float @f34()' %t && -struct s34 { struct { int : 0; } a; float b; } f34(void) {} +struct s34 { struct { int : 0; } a; float b; } f34(void) { while (1) {} } // RUN: grep 'define i16 @f35()' %t && -struct s35 { struct { int : 0; } a; char b; char c; } f35(void) {} +struct s35 { struct { int : 0; } a; char b; char c; } f35(void) { while (1) {} } // RUN: grep 'define i16 @f36()' %t && -struct s36 { struct { int : 0; } a[2][10]; char b; char c; } f36(void) {} +struct s36 { struct { int : 0; } a[2][10]; char b; char c; } f36(void) { while (1) {} } // RUN: grep 'define float @f37()' %t && -struct s37 { float c[1][1]; } f37(void) {} +struct s37 { float c[1][1]; } f37(void) { while (1) {} } // RUN: grep 'define void @f38(.struct.s38. noalias sret .agg.result)' %t && -struct s38 { char a[3]; short b; } f38(void) {} +struct s38 { char a[3]; short b; } f38(void) { while (1) {} } // RUN: grep 'define void @f39(.struct.s39. byval align 16 .x)' %t && typedef int v39 __attribute((vector_size(16))); struct s39 { v39 x; }; void f39(struct s39 x) {} +// +// RUN: grep 'define i32 @f40()' %t && +enum e40 { ec0 = 0 }; +enum e40 f40(void) { } + +// RUN: grep 'define void ()\* @f41()' %t && +typedef void (^vvbp)(void); +vvbp f41(void) { } + +// RUN: grep 'define i32 @f42()' %t && +struct s42 { enum e40 f0; } f42(void) { } + +// RUN: grep 'define i64 @f43()' %t && +struct s43 { enum e40 f0; int f1; } f43(void) { } + +// RUN: grep 'define i32 @f44()' %t && +struct s44 { vvbp f0; } f44(void) { } + +// RUN: grep 'define i64 @f45()' %t && +struct s45 { vvbp f0; int f1; } f45(void) { } + +// RUN: grep 'define void @f46(i32 %a0)' %t && +void f46(enum e40 a0) { } + +// RUN: grep 'define void @f47(void ()\* %a1)' %t && +void f47(vvbp a1) { } + +// RUN: grep 'define void @f48(i32 %a0.0)' %t && +struct s48 { enum e40 f0; }; +void f48(struct s48 a0) { } + +// RUN: grep 'define void @f49(i32 %a0.0, i32 %a0.1)' %t && +struct s49 { enum e40 f0; int f1; }; +void f49(struct s49 a0) { } + +// RUN: grep 'define void @f50(void ()\* %a0.0)' %t && +struct s50 { vvbp f0; }; +void f50(struct s50 a0) { } + +// RUN: grep 'define void @f51(void ()\* %a0.0, i32 %a0.1)' %t && +struct s51 { vvbp f0; int f1; }; +void f51(struct s51 a0) { } + // RUN: true diff --git a/test/CodeGen/x86_64-arguments.c b/test/CodeGen/x86_64-arguments.c index 0b68afd..19f9cda 100644 --- a/test/CodeGen/x86_64-arguments.c +++ b/test/CodeGen/x86_64-arguments.c @@ -7,26 +7,32 @@ // RUN: grep 'define x86_fp80 @f5()' %t && // RUN: grep 'define void @f6(i8 signext %a0, i16 signext %a1, i32 %a2, i64 %a3, i8\* %a4)' %t && // RUN: grep 'define void @f7(i32 %a0)' %t && -// RUN: grep 'type { i64, double }.*type .0' %t && +// RUN: grep '.0 = type { i64, double }' %t && // RUN: grep 'define .0 @f8_1()' %t && // RUN: grep 'define void @f8_2(.0)' %t && char f0(void) { + return 0; } short f1(void) { + return 0; } int f2(void) { + return 0; } float f3(void) { + return 0; } double f4(void) { + return 0; } long double f5(void) { + return 0; } void f6(char a0, short a1, int a2, long long a3, void *a4) { @@ -42,23 +48,23 @@ union u8 { long double a; int b; }; -union u8 f8_1() {} +union u8 f8_1() { while (1) {} } void f8_2(union u8 a0) {} // RUN: grep 'define i64 @f9()' %t && -struct s9 { int a; int b; int : 0; } f9(void) {} +struct s9 { int a; int b; int : 0; } f9(void) { while (1) {} } // RUN: grep 'define void @f10(i64)' %t && struct s10 { int a; int b; int : 0; }; void f10(struct s10 a0) {} // RUN: grep 'define void @f11(.union.anon. noalias sret .agg.result)' %t && -union { long double a; float b; } f11() {} +union { long double a; float b; } f11() { while (1) {} } // RUN: grep 'define i64 @f12_0()' %t && // RUN: grep 'define void @f12_1(i64)' %t && struct s12 { int a __attribute__((aligned(16))); }; -struct s12 f12_0(void) {} +struct s12 f12_0(void) { while (1) {} } void f12_1(struct s12 a0) {} // Check that sret parameter is accounted for when checking available integer @@ -66,8 +72,9 @@ void f12_1(struct s12 a0) {} // RUN: grep 'define void @f13(.struct.s13_0. noalias sret .agg.result, i32 .a, i32 .b, i32 .c, i32 .d, .struct.s13_1. byval .e, i32 .f)' %t && struct s13_0 { long long f0[3]; }; +struct s13_1 { long long f0[2]; }; struct s13_0 f13(int a, int b, int c, int d, - struct s13_1 { long long f0[2]; } e, int f) {} + struct s13_1 e, int f) { while (1) {} } // RUN: grep 'define void @f14(.*, i8 signext .X)' %t && void f14(int a, int b, int c, int d, int e, int f, @@ -83,9 +90,10 @@ void f17(float a, float b, float c, float d, float e, float f, float g, float h, long double X) {} // Check for valid coercion. -// RUN: grep '.1 = bitcast i64. .tmp to .struct.f18_s0.' %t && -// RUN: grep '.2 = load .struct.f18_s0. .1, align 1' %t && -// RUN: grep 'store .struct.f18_s0 .2, .struct.f18_s0. .f18_arg1' %t && -void f18(int a, struct f18_s0 { int f0; } f18_arg1) {} +// RUN: grep '.. = bitcast i64. .* to .struct.f18_s0.' %t && +// RUN: grep '.. = load .struct.f18_s0. .., align 1' %t && +// RUN: grep 'store .struct.f18_s0 .., .struct.f18_s0. .f18_arg1' %t && +struct f18_s0 { int f0; }; +void f18(int a, struct f18_s0 f18_arg1) { while (1) {} } // RUN: true diff --git a/test/CodeGenCXX/PR4827-cast.cpp b/test/CodeGenCXX/PR4827-cast.cpp new file mode 100644 index 0000000..958798d --- /dev/null +++ b/test/CodeGenCXX/PR4827-cast.cpp @@ -0,0 +1,5 @@ +// RUN: clang-cc -emit-llvm -o - %s +struct A; +struct B; +extern A *f(); +void a() { (B *) f(); } diff --git a/test/CodeGenCXX/PR4890-debug-info-dtor.cpp b/test/CodeGenCXX/PR4890-debug-info-dtor.cpp new file mode 100644 index 0000000..a0d3a8d --- /dev/null +++ b/test/CodeGenCXX/PR4890-debug-info-dtor.cpp @@ -0,0 +1,6 @@ +// RUN: clang-cc -emit-llvm-only -g %s +struct X { + ~X(); +}; + +X::~X() { } diff --git a/test/CodeGenCXX/PR4983-constructor-conversion.cpp b/test/CodeGenCXX/PR4983-constructor-conversion.cpp new file mode 100644 index 0000000..31eae2e --- /dev/null +++ b/test/CodeGenCXX/PR4983-constructor-conversion.cpp @@ -0,0 +1,16 @@ +// RUN: clang-cc -emit-llvm-only %s + +struct A { + A(const char *s){} +}; + +struct B { + A a; + + B() : a("test") { } +}; + +void f() { + A a("test"); +} + diff --git a/test/CodeGenCXX/PR5050-constructor-conversion.cpp b/test/CodeGenCXX/PR5050-constructor-conversion.cpp new file mode 100644 index 0000000..e5f722c --- /dev/null +++ b/test/CodeGenCXX/PR5050-constructor-conversion.cpp @@ -0,0 +1,19 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -std=c++0x -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -std=c++0x -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +struct A { A(const A&, int i1 = 1); }; + +struct B : A { }; + +A f(const B &b) { + return b; +} + +// CHECK-LP64: call __ZN1AC1ERKS_i + +// CHECK-LP32: call L__ZN1AC1ERKS_i + + diff --git a/test/CodeGenCXX/PR5093-static-member-function.cpp b/test/CodeGenCXX/PR5093-static-member-function.cpp new file mode 100644 index 0000000..a27b08f --- /dev/null +++ b/test/CodeGenCXX/PR5093-static-member-function.cpp @@ -0,0 +1,9 @@ +// RUN: clang-cc %s -emit-llvm -o - | FileCheck %s +struct a { + static void f(); +}; + +void g(a *a) { + // CHECK: call void @_ZN1a1fEv() + a->f(); +} diff --git a/test/CodeGenCXX/anonymous-namespaces.cpp b/test/CodeGenCXX/anonymous-namespaces.cpp new file mode 100644 index 0000000..dcfd518 --- /dev/null +++ b/test/CodeGenCXX/anonymous-namespaces.cpp @@ -0,0 +1,22 @@ +// RUN: clang-cc -emit-llvm %s -o - | FileCheck %s + +namespace { + // CHECK: @_ZN12_GLOBAL__N_11aE = internal global i32 0 + int a = 0; + + // CHECK: define internal i32 @_ZN12_GLOBAL__N_13fooEv() + int foo() { + return 32; + } + + // CHECK: define internal i32 @_ZN12_GLOBAL__N_11A3fooEv() + namespace A { + int foo() { + return 45; + } + } +} + +int concrete() { + return a + foo() + A::foo(); +} diff --git a/test/CodeGenCXX/anonymous-union-member-initializer.cpp b/test/CodeGenCXX/anonymous-union-member-initializer.cpp new file mode 100644 index 0000000..2030f40 --- /dev/null +++ b/test/CodeGenCXX/anonymous-union-member-initializer.cpp @@ -0,0 +1,12 @@ +// RUN: clang-cc -emit-llvm -o - %s + +struct A { + union { + int a; + void* b; + }; + + A() : a(0) { } +}; + +A a; diff --git a/test/CodeGenCXX/array-pointer-decay.cpp b/test/CodeGenCXX/array-pointer-decay.cpp new file mode 100644 index 0000000..5751b67 --- /dev/null +++ b/test/CodeGenCXX/array-pointer-decay.cpp @@ -0,0 +1,7 @@ +// RUN: clang-cc %s -emit-llvm -o - + +void f(const char*); + +void g() { + f("hello"); +} diff --git a/test/CodeGenCXX/attr.cpp b/test/CodeGenCXX/attr.cpp new file mode 100644 index 0000000..8077b78 --- /dev/null +++ b/test/CodeGenCXX/attr.cpp @@ -0,0 +1,36 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -O0 -S %s -o %t.s && +// RUN: FileCheck --input-file=%t.s %s + +int foo() __attribute__((aligned(1024))); +int foo() { } + +// CHECK:.align 10, 0x90 +// CHECK:.globl __Z3foov +// CHECK:__Z3foov: + + +class C { + virtual void bar1() __attribute__((aligned(1))); + virtual void bar2() __attribute__((aligned(2))); + virtual void bar3() __attribute__((aligned(1024))); +} c; + +void C::bar1() { } + +// CHECK:.align 1, 0x90 +// CHECK-NEXT:.globl __ZN1C4bar1Ev +// CHECK-NEXT:__ZN1C4bar1Ev: + + +void C::bar2() { } + +// CHECK:.align 1, 0x90 +// CHECK-NEXT:.globl __ZN1C4bar2Ev +// CHECK-NEXT:__ZN1C4bar2Ev: + + +void C::bar3() { } + +// CHECK:.align 10, 0x90 +// CHECK-NEXT:.globl __ZN1C4bar3Ev +// CHECK-NEXT:__ZN1C4bar3Ev: diff --git a/test/CodeGenCXX/cast-conversion.cpp b/test/CodeGenCXX/cast-conversion.cpp new file mode 100644 index 0000000..f571f54 --- /dev/null +++ b/test/CodeGenCXX/cast-conversion.cpp @@ -0,0 +1,33 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -std=c++0x -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -std=c++0x -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +struct A { + A(int); +}; + +struct B { + B(A); +}; + +int main () { + (B)10; + B(10); + static_cast(10); +} + +// CHECK-LP64: call __ZN1AC1Ei +// CHECK-LP64: call __ZN1BC1E1A +// CHECK-LP64: call __ZN1AC1Ei +// CHECK-LP64: call __ZN1BC1E1A +// CHECK-LP64: call __ZN1AC1Ei +// CHECK-LP64: call __ZN1BC1E1A + +// CHECK-LP32: call L__ZN1AC1Ei +// CHECK-LP32: call L__ZN1BC1E1A +// CHECK-LP32: call L__ZN1AC1Ei +// CHECK-LP32: call L__ZN1BC1E1A +// CHECK-LP32: call L__ZN1AC1Ei +// CHECK-LP32: call L__ZN1BC1E1A diff --git a/test/CodeGenCXX/class-layout.cpp b/test/CodeGenCXX/class-layout.cpp new file mode 100644 index 0000000..7255d3e --- /dev/null +++ b/test/CodeGenCXX/class-layout.cpp @@ -0,0 +1,5 @@ +// RUN: clang-cc %s -emit-llvm -o %t && + +// An extra byte shoudl be allocated for an empty class. +// RUN: grep '%.truct.A = type { i8 }' %t +struct A { } a; diff --git a/test/CodeGenCXX/conditional-expr-lvalue.cpp b/test/CodeGenCXX/conditional-expr-lvalue.cpp new file mode 100644 index 0000000..7b3233a --- /dev/null +++ b/test/CodeGenCXX/conditional-expr-lvalue.cpp @@ -0,0 +1,7 @@ +// RUN: clang-cc -emit-llvm-only %s +void f(bool flag) { + int a = 1; + int b = 2; + + (flag ? a : b) = 3; +} diff --git a/test/CodeGenCXX/constructor-conversion.cpp b/test/CodeGenCXX/constructor-conversion.cpp new file mode 100644 index 0000000..980b230 --- /dev/null +++ b/test/CodeGenCXX/constructor-conversion.cpp @@ -0,0 +1,55 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -std=c++0x -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -std=c++0x -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +extern "C" int printf(...); + +class X { // ... +public: + X(int) : iX(2), fX(2.3) , name("HELLO\n") { } + + X(const char* arg, int ix=0) { iX = ix; fX = 6.0; name = arg+ix; } + X(): iX(100), fX(1.2) {} + int iX; + float fX; + const char *name; + void pr(void) { + printf("iX = %d fX = %f name = %s\n", iX, fX, name); + } +}; + +void g(X arg) { + arg.pr(); +} + +void f(X arg) { + X a = 1; // a = X(1) + + a.pr(); + + X b = "Jessie"; // b=X("Jessie",0) + + b.pr(); + + + a = 2; // a = X(2) + + a.pr(); +} + + +int main() { + X x; + f(x); + g(3); // g(X(3)) +} + +// CHECK-LP64: call __ZN1XC1Ei +// CHECK-LP64: call __ZN1XC1EPKci +// CHECK-LP64: call __ZN1XC1Ev + +// CHECK-LP32: call L__ZN1XC1Ei +// CHECK-LP32: call L__ZN1XC1EPKci +// CHECK-LP32: call L__ZN1XC1Ev diff --git a/test/CodeGenCXX/constructor-default-arg.cpp b/test/CodeGenCXX/constructor-default-arg.cpp new file mode 100644 index 0000000..7e6a7cd --- /dev/null +++ b/test/CodeGenCXX/constructor-default-arg.cpp @@ -0,0 +1,40 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -std=c++0x -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -std=c++0x -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +extern "C" int printf(...); + + +struct C { + C() : iC(6) {} + int iC; +}; + +int foo() { + return 6; +}; + +class X { // ... +public: + X(int) {} + X(const X&, int i = 1, int j = 2, int k = foo()) { + printf("X(const X&, %d, %d, %d)\n", i, j, k); + } +}; + +int main() { + X a(1); + X b(a, 2); + X c = b; + X d(a, 5, 6); +} + +// CHECK-LP64: call __ZN1XC1ERKS_iii +// CHECK-LP64: call __ZN1XC1ERKS_iii +// CHECK-LP64: call __ZN1XC1ERKS_iii + +// CHECK-LP32: call L__ZN1XC1ERKS_iii +// CHECK-LP32: call L__ZN1XC1ERKS_iii +// CHECK-LP32: call L__ZN1XC1ERKS_iii diff --git a/test/CodeGenCXX/constructor-for-array-members.cpp b/test/CodeGenCXX/constructor-for-array-members.cpp new file mode 100644 index 0000000..fbb13e0 --- /dev/null +++ b/test/CodeGenCXX/constructor-for-array-members.cpp @@ -0,0 +1,44 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -std=c++0x -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -std=c++0x -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +extern "C" int printf(...); + +int i = 1234; +float vf = 1.00; + +struct S { + S() : iS(i++), f1(vf++) {printf("S::S()\n");} + ~S(){printf("S::~S(iS = %d f1 = %f)\n", iS, f1); } + int iS; + float f1; +}; + +struct M { + double dM; + S ARR_S[3]; + void pr() { + for (int i = 0; i < 3; i++) + printf("ARR_S[%d].iS = %d ARR_S[%d].f1 = %f\n", i, ARR_S[i].iS, i, ARR_S[i].f1); + + for (int i = 0; i < 2; i++) + for (int j = 0; j < 3; j++) + for (int k = 0; k < 4; k++) + printf("MULTI_ARR[%d][%d][%d].iS = %d MULTI_ARR[%d][%d][%d].f1 = %f\n", + i,j,k, MULTI_ARR[i][j][k].iS, i,j,k, MULTI_ARR[i][j][k].f1); + + } + + S MULTI_ARR[2][3][4]; +}; + +int main() { + M m1; + m1.pr(); +} + +// CHECK-LP64: call __ZN1SC1Ev + +// CHECK-LP32: call L__ZN1SC1Ev diff --git a/test/CodeGenCXX/constructor-init-reference.cpp b/test/CodeGenCXX/constructor-init-reference.cpp new file mode 100644 index 0000000..040441f --- /dev/null +++ b/test/CodeGenCXX/constructor-init-reference.cpp @@ -0,0 +1,9 @@ +// RUN: clang-cc -emit-llvm -o - %s | grep "store i32\* @x, i32\*\*" + +int x; +class A { + int& y; + A() : y(x) {} +}; +A z; + diff --git a/test/CodeGenCXX/constructor-init.cpp b/test/CodeGenCXX/constructor-init.cpp new file mode 100644 index 0000000..1b02512 --- /dev/null +++ b/test/CodeGenCXX/constructor-init.cpp @@ -0,0 +1,61 @@ +// RUN: clang-cc %s -emit-llvm -o %t + +extern "C" int printf(...); + +struct M { + M() { printf("M()\n"); } + M(int i) { iM = i; printf("M(%d)\n", i); } + int iM; + void MPR() {printf("iM = %d\n", iM); }; +}; + +struct P { + P() { printf("P()\n"); } + P(int i) { iP = i; printf("P(%d)\n", i); } + int iP; + void PPR() {printf("iP = %d\n", iP); }; +}; + +struct Q { + Q() { printf("Q()\n"); } + Q(int i) { iQ = i; printf("Q(%d)\n", i); } + int iQ; + void QPR() {printf("iQ = %d\n", iQ); }; +}; + +struct N : M , P, Q { + N() : f1(1.314), P(2000), ld(00.1234+f1), M(1000), Q(3000), + d1(3.4567), i1(1234), m1(100) { printf("N()\n"); } + M m1; + M m2; + float f1; + int i1; + float d1; + void PR() { + printf("f1 = %f d1 = %f i1 = %d ld = %f \n", f1,d1,i1, ld); + MPR(); + PPR(); + QPR(); + printf("iQ = %d\n", iQ); + printf("iP = %d\n", iP); + printf("iM = %d\n", iM); + // FIXME. We don't yet support this syntax. + // printf("iQ = %d\n", (*this).iQ); + printf("iQ = %d\n", this->iQ); + printf("iP = %d\n", this->iP); + printf("iM = %d\n", this->iM); + } + float ld; + float ff; + M arr_m[3]; + P arr_p[1][3]; + Q arr_q[2][3][4]; +}; + +int main() { + M m1; + + N n1; + n1.PR(); +} + diff --git a/test/CodeGenCXX/constructor-template.cpp b/test/CodeGenCXX/constructor-template.cpp new file mode 100644 index 0000000..8c4f2c9 --- /dev/null +++ b/test/CodeGenCXX/constructor-template.cpp @@ -0,0 +1,56 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -std=c++0x -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -std=c++0x -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +// PR4826 +struct A { + A() { + } +}; + +template +struct B { + B(T) {} + + A nodes; +}; + + +// PR4853 +template class List { +public: + List(){ } // List*>::List() remains undefined. + ~List() {} +}; + +template class Node { + int i; +public: + Node(){ } // Node*>::Node() remains undefined. + ~Node() {} +}; + + +template class BinomialNode : Node*> { +public: + BinomialNode(T value) {} + List*> nodes; +}; + +int main() { + B *n = new B(4); + BinomialNode *node = new BinomialNode(1); + delete node; +} + +// CHECK-LP64: __ZN4ListIP12BinomialNodeIiEED1Ev: +// CHECK-LP64: __ZN4ListIP12BinomialNodeIiEED2Ev: +// CHECK-LP64: __ZN4NodeIP12BinomialNodeIiEEC1Ev: +// CHECK-LP64: __ZN4ListIP12BinomialNodeIiEEC1Ev: + +// CHECK-LP32: __ZN4ListIP12BinomialNodeIiEED1Ev: +// CHECK-LP32: __ZN4ListIP12BinomialNodeIiEED2Ev: +// CHECK-LP32: __ZN4NodeIP12BinomialNodeIiEEC1Ev: +// CHECK-LP32: __ZN4ListIP12BinomialNodeIiEEC1Ev: diff --git a/test/CodeGenCXX/conversion-function.cpp b/test/CodeGenCXX/conversion-function.cpp new file mode 100644 index 0000000..0bfd4af --- /dev/null +++ b/test/CodeGenCXX/conversion-function.cpp @@ -0,0 +1,115 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -std=c++0x -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -std=c++0x -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +extern "C" int printf(...); +struct S { + operator int(); +}; + +S::operator int() { + return 10; +} + + +class X { // ... + public: operator int() { printf("operator int()\n"); return iX; } + public: operator float() { printf("operator float()\n"); return fX; } + X() : iX(100), fX(1.234) {} + int iX; + float fX; +}; + +X x; + +struct Z { + operator X() { printf("perator X()\n"); x.iX += iZ; x.fX += fZ; return x; } + int iZ; + float fZ; + Z() : iZ(1), fZ(1.00) {} +}; + +Z z; + +class Y { // ... + public: operator Z(){printf("perator Z()\n"); return z; } +}; + +Y y; + +int count=0; +class O { // ... +public: + operator int(){ return ++iO; } + O() : iO(count++) {} + int iO; +}; + +void g(O a, O b) { + int i = (a) ? 1+a : 0; + int j = (a&&b) ? a+b : i; + if (a) { } + printf("i = %d j = %d a.iO = %d b.iO = %d\n", i, j, a.iO, b.iO); +} + +int main() { + int c = X(Z(y)); // OK: y.operator Z().operator X().operator int() + printf("c = %d\n", c); + float f = X(Z(y)); + printf("f = %f\n", f); + int i = x; + printf("i = %d float = %f\n", i, float(x)); + i = int(X(Z(y))); + f = float(X(Z(y))); + printf("i = %d float = %f\n", i,f); + f = (float)x; + i = (int)x; + printf("i = %d float = %f\n", i,f); + + int d = (X)((Z)y); + printf("d = %d\n", d); + + int e = (int)((X)((Z)y)); + printf("e = %d\n", e); + O o1, o2; + g(o1, o2); +} + +// Test. Conversion in base class is visible in derived class. +class XB { + int a; +public: + operator int(); +}; + +class Yb : public XB { + double b; +public: + operator char(); +}; + +void f(Yb& a) { + int i = a; // OK. calls XB::operator int(); + char ch = a; // OK. calls Yb::operator char(); +} + + +// CHECK-LP64: .globl __ZN1ScviEv +// CHECK-LP64-NEXT: __ZN1ScviEv: +// CHECK-LP64: call __ZN1Ycv1ZEv +// CHECK-LP64: call __ZN1Zcv1XEv +// CHECK-LP64: call __ZN1XcviEv +// CHECK-LP64: call __ZN1XcvfEv +// CHECK-LP64: call __ZN2XBcviEv +// CHECK-LP64: call __ZN2YbcvcEv + +// CHECK-LP32: .globl __ZN1ScviEv +// CHECK-LP32-NEXT: __ZN1ScviEv: +// CHECK-LP32: call L__ZN1Ycv1ZEv +// CHECK-LP32: call L__ZN1Zcv1XEv +// CHECK-LP32: call L__ZN1XcviEv +// CHECK-LP32: call L__ZN1XcvfEv +// CHECK-LP32: call L__ZN2XBcviEv +// CHECK-LP32: call L__ZN2YbcvcEv diff --git a/test/CodeGenCXX/convert-to-fptr.cpp b/test/CodeGenCXX/convert-to-fptr.cpp new file mode 100644 index 0000000..c0bd2f7 --- /dev/null +++ b/test/CodeGenCXX/convert-to-fptr.cpp @@ -0,0 +1,47 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -std=c++0x -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -std=c++0x -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +extern "C" int printf(...); + +int f1(int arg) { return arg; }; + +int f2(float arg) { return int(arg); }; + +typedef int (*fp1)(int); + +typedef int (*fp2)(float); + +struct A { + operator fp1() { return f1; } + operator fp2() { return f2; } +} a; + + +// Test for function reference. +typedef int (&fr1)(int); +typedef int (&fr2)(float); + +struct B { + operator fr1() { return f1; } + operator fr2() { return f2; } +} b; + +int main() +{ + int i = a(10); // Calls f1 via pointer returned from conversion function + printf("i = %d\n", i); + + int j = b(20); // Calls f1 via pointer returned from conversion function + printf("j = %d\n", j); + return 0; +} + +// CHECK-LP64: call __ZN1AcvPFiiEEv +// CHECK-LP64: call __ZN1BcvRFiiEEv + +// CHECK-LP32: call L__ZN1AcvPFiiEEv +// CHECK-LP32: call L__ZN1BcvRFiiEEv + diff --git a/test/CodeGenCXX/copy-assign-synthesis-1.cpp b/test/CodeGenCXX/copy-assign-synthesis-1.cpp new file mode 100644 index 0000000..d4a93af --- /dev/null +++ b/test/CodeGenCXX/copy-assign-synthesis-1.cpp @@ -0,0 +1,109 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -std=c++0x -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -std=c++0x -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +extern "C" int printf(...); + +struct B { + B() : B1(3.14), B2(3.15), auB2(3.16) {} + float B1; + float B2; + void pr() { + printf("B1 = %f B2 = %f auB1 = %f\n", B1, B2, auB1); + } + + B& operator=(const B& arg) { B1 = arg.B1; B2 = arg.B2; + auB1 = arg.auB1; return *this; } + union { + float auB1; + float auB2; + }; +}; + +struct M { + M() : M1(10), M2(11) , auM1(12) {} + int M1; + int M2; + void pr() { + printf("M1 = %d M2 = %d auM1 = %d auM2 = %d\n", M1, M2, auM1, auM2); + } + union { + int auM1; + int auM2; + }; +}; + +struct N : B { + N() : N1(20), N2(21) {} + int N1; + int N2; + void pr() { + printf("N1 = %d N2 = %d\n", N1, N2); + for (unsigned i = 0; i < 3; i++) + for (unsigned j = 0; j < 2; j++) + printf("arr_b[%d][%d] = %f\n", i,j,arr_b[i][j].B1); + B::pr(); + } + N& operator=(const N& arg) { + N1 = arg.N1; N2 = arg.N2; + for (unsigned i = 0; i < 3; i++) + for (unsigned j = 0; j < 2; j++) + arr_b[i][j] = arg.arr_b[i][j]; + return *this; + } + B arr_b[3][2]; +}; + +struct Q : B { + Q() : Q1(30), Q2(31) {} + int Q1; + int Q2; + void pr() { + printf("Q1 = %d Q2 = %d\n", Q1, Q2); + } +}; + + +struct X : M , N { + X() : d(0.0), d1(1.1), d2(1.2), d3(1.3) {} + double d; + double d1; + double d2; + double d3; + void pr() { + printf("d = %f d1 = %f d2 = %f d3 = %f\n", d, d1,d2,d3); + M::pr(); N::pr(); + q1.pr(); q2.pr(); + } + + Q q1, q2; +}; + + +X srcX; +X dstX; +X dstY; + +int main() { + dstY = dstX = srcX; + srcX.pr(); + dstX.pr(); + dstY.pr(); +} + +// CHECK-LP64: .globl __ZN1XaSERKS_ +// CHECK-LP64: .weak_definition __ZN1XaSERKS_ +// CHECK-LP64: __ZN1XaSERKS_: +// CHECK-LP64: .globl __ZN1QaSERKS_ +// CHECK-LP64: .weak_definition __ZN1QaSERKS_ +// CHECK-LP64: __ZN1QaSERKS_: + +// CHECK-LP32: .globl __ZN1XaSERKS_ +// CHECK-LP32: .weak_definition __ZN1XaSERKS_ +// CHECK-LP32: __ZN1XaSERKS_: +// CHECK-LP32: .globl __ZN1QaSERKS_ +// CHECK-LP32: .weak_definition __ZN1QaSERKS_ +// CHECK-LP32: __ZN1QaSERKS_: + diff --git a/test/CodeGenCXX/copy-assign-synthesis.cpp b/test/CodeGenCXX/copy-assign-synthesis.cpp new file mode 100644 index 0000000..f9baa8f --- /dev/null +++ b/test/CodeGenCXX/copy-assign-synthesis.cpp @@ -0,0 +1,79 @@ +// RUN: clang-cc -emit-llvm -o %t %s && +// RUN: grep "_ZN1XaSERK1X" %t | count 0 + +extern "C" int printf(...); + +struct B { + B() : B1(3.14), B2(3.15), auB2(3.16) {} + float B1; + float B2; + void pr() { + printf("B1 = %f B2 = %f auB1 = %f\n", B1, B2, auB1); + } + + union { + float auB1; + float auB2; + }; +}; + +struct M { + M() : M1(10), M2(11) , auM1(12) {} + int M1; + int M2; + void pr() { + printf("M1 = %d M2 = %d auM1 = %d auM2 = %d\n", M1, M2, auM1, auM2); + } + union { + int auM1; + int auM2; + }; +}; + +struct N : B { + N() : N1(20), N2(21) {} + int N1; + int N2; + void pr() { + printf("N1 = %d N2 = %d\n", N1, N2); + B::pr(); + } +}; + +struct Q { + Q() : Q1(30), Q2(31) {} + int Q1; + int Q2; + void pr() { + printf("Q1 = %d Q2 = %d\n", Q1, Q2); + } +}; + + +struct X : M , N { + X() : d(0.0), d1(1.1), d2(1.2), d3(1.3) {} + double d; + double d1; + double d2; + double d3; + void pr() { + printf("d = %f d1 = %f d2 = %f d3 = %f\n", d, d1,d2,d3); + M::pr(); N::pr(); + q1.pr(); q2.pr(); + } + + Q q1, q2; +}; + + +X srcX; +X dstX; +X dstY; + +int main() { + dstY = dstX = srcX; + srcX.pr(); + dstX.pr(); + dstY.pr(); +} + diff --git a/test/CodeGenCXX/copy-constructor-elim.cpp b/test/CodeGenCXX/copy-constructor-elim.cpp new file mode 100644 index 0000000..daef92c --- /dev/null +++ b/test/CodeGenCXX/copy-constructor-elim.cpp @@ -0,0 +1,43 @@ +// RUN: clang-cc -emit-llvm -o %t %s && +// RUN: grep "_ZN1CC1ERK1C" %t | count 0 && +// RUN: grep "_ZN1SC1ERK1S" %t | count 0 && +// RUN: true + +extern "C" int printf(...); + + +struct C { + C() : iC(6) {printf("C()\n"); } + C(const C& c) { printf("C(const C& c)\n"); } + int iC; +}; + +C foo() { + return C(); +}; + +class X { // ... +public: + X(int) {} + X(const X&, int i = 1, int j = 2, C c = foo()) { + printf("X(const X&, %d, %d, %d)\n", i, j, c.iC); + } +}; + + +struct S { + S(); +}; + +S::S() { printf("S()\n"); } + +void Call(S) {}; + +int main() { + X a(1); + X b(a, 2); + X c = b; + X d(a, 5, 6); + S s; + Call(s); +} diff --git a/test/CodeGenCXX/copy-constructor-synthesis.cpp b/test/CodeGenCXX/copy-constructor-synthesis.cpp new file mode 100644 index 0000000..47971af --- /dev/null +++ b/test/CodeGenCXX/copy-constructor-synthesis.cpp @@ -0,0 +1,110 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +extern "C" int printf(...); + +int init = 100; + +struct M { + int iM; + M() : iM(init++) {} +}; + +struct N { + int iN; + N() : iN(200) {} + N(N const & arg){this->iN = arg.iN; } +}; + +struct P { + int iP; + P() : iP(init++) {} +}; + + +struct X : M, N, P { // ... + X() : f1(1.0), d1(2.0), i1(3), name("HELLO"), bf1(0xff), bf2(0xabcd), + au_i1(1234), au1_4("MASKED") {} + P p0; + void pr() { + printf("iM = %d iN = %d, m1.iM = %d\n", iM, iN, m1.iM); + printf("im = %d p0.iP = %d, p1.iP = %d\n", iP, p0.iP, p1.iP); + printf("f1 = %f d1 = %f i1 = %d name(%s) \n", f1, d1, i1, name); + printf("bf1 = %x bf2 = %x\n", bf1, bf2); + printf("au_i2 = %d\n", au_i2); + printf("au1_1 = %s\n", au1_1); + } + M m1; + P p1; + float f1; + double d1; + int i1; + const char *name; + unsigned bf1 : 8; + unsigned bf2 : 16; + + union { + int au_i1; + int au_i2; + }; + union { + const char * au1_1; + float au1_2; + int au1_3; + const char * au1_4; + }; +}; + +static int ix = 1; +// class with user-defined copy constructor. +struct S { + S() : iS(ix++) { } + S(const S& arg) { *this = arg; } + int iS; +}; + +// class with trivial copy constructor. +struct I { + I() : iI(ix++) { } + int iI; +}; + +struct XM { + XM() { } + double dXM; + S ARR_S[3][4][2]; + void pr() { + for (unsigned i = 0; i < 3; i++) + for (unsigned j = 0; j < 4; j++) + for (unsigned k = 0; k < 2; k++) + printf("ARR_S[%d][%d][%d] = %d\n", i,j,k, ARR_S[i][j][k].iS); + for (unsigned i = 0; i < 3; i++) + for (unsigned k = 0; k < 2; k++) + printf("ARR_I[%d][%d] = %d\n", i,k, ARR_I[i][k].iI); + } + I ARR_I[3][2]; +}; + +int main() { + X a; + X b(a); + b.pr(); + X x; + X c(x); + c.pr(); + + XM m0; + XM m1 = m0; + m1.pr(); +} + +// CHECK-LP64: .globl __ZN1XC1ERKS_ +// CHECK-LP64: .weak_definition __ZN1XC1ERKS_ +// CHECK-LP64: __ZN1XC1ERKS_: + +// CHECK-LP32: .globl __ZN1XC1ERKS_ +// CHECK-LP32: .weak_definition __ZN1XC1ERKS_ +// CHECK-LP32: __ZN1XC1ERKS_: diff --git a/test/CodeGenCXX/decl-ref-init.cpp b/test/CodeGenCXX/decl-ref-init.cpp new file mode 100644 index 0000000..27d200f --- /dev/null +++ b/test/CodeGenCXX/decl-ref-init.cpp @@ -0,0 +1,31 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +struct A {}; + +struct B +{ + operator A&(); +}; + + +struct D : public B { + operator A(); +}; + +extern B f(); +extern D d(); + +int main() { + const A& rca = f(); + const A& rca2 = d(); +} + +// CHECK-LP64: call __ZN1BcvR1AEv +// CHECK-LP64: call __ZN1BcvR1AEv + +// CHECK-LP32: call L__ZN1BcvR1AEv +// CHECK-LP32: call L__ZN1BcvR1AEv diff --git a/test/CodeGenCXX/default-arg-temps.cpp b/test/CodeGenCXX/default-arg-temps.cpp index 2dcf773..2651446 100644 --- a/test/CodeGenCXX/default-arg-temps.cpp +++ b/test/CodeGenCXX/default-arg-temps.cpp @@ -7,9 +7,19 @@ struct T { void f(const T& t = T()); +class X { // ... +public: + X(); + X(const X&, const T& t = T()); +}; + void g() { - // RUN: grep "call void @_ZN1TC1Ev" %t | count 2 && - // RUN: grep "call void @_ZN1TD1Ev" %t | count 2 + // RUN: grep "call void @_ZN1TC1Ev" %t | count 4 && + // RUN: grep "call void @_ZN1TD1Ev" %t | count 4 f(); f(); + + X a; + X b(a); + X c = a; } diff --git a/test/CodeGenCXX/default-constructor-for-members.cpp b/test/CodeGenCXX/default-constructor-for-members.cpp new file mode 100644 index 0000000..2d04bc9 --- /dev/null +++ b/test/CodeGenCXX/default-constructor-for-members.cpp @@ -0,0 +1,24 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +extern "C" int printf(...); + +struct S { + S() { printf("S::S()\n"); } + int iS; +}; + +struct M { + S ARR_S; +}; + +int main() { + M m1; +} + +// CHECK-LP64: call __ZN1SC1Ev + +// CHECK-LP32: call L__ZN1SC1Ev diff --git a/test/CodeGenCXX/default-destructor-synthesis.cpp b/test/CodeGenCXX/default-destructor-synthesis.cpp new file mode 100644 index 0000000..9cc802c --- /dev/null +++ b/test/CodeGenCXX/default-destructor-synthesis.cpp @@ -0,0 +1,60 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -std=c++0x -O0 -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -std=c++0x -O0 -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 -input-file=%t-32.s %s && +// RUN: true + +extern "C" int printf(...); + +int count = 1; + +struct S { + S() : iS(count++), fS(1.23) {}; + ~S(){printf("S::~S(%d, %f)\n", iS, fS); }; + int iS; + float fS; +}; + +struct Q { + Q() : iQ(count++), dQ(2.34) {}; + ~Q(){printf("Q::~Q(%d, %f)\n", iQ, dQ); }; + int iQ; + double dQ; +}; + +struct P { + P() : fP(3.45) , iP(count++) {}; + ~P(){printf("P::~P(%d, %f)\n", iP, fP); }; + float fP; + int iP; +}; + +struct M : Q, P { + S s; + + Q q; + + P p; + + P p_arr[3]; + + Q q_arr[2][3]; + +}; + +M gm; + +int main() {M m1;} + +// CHECK-LP64: call __ZN1MC1Ev +// CHECK-LP64: call __ZN1MD1Ev +// CHECK-LP64: .globl __ZN1MD1Ev +// CHECK-LP64-NEXT: .weak_definition __ZN1MD1Ev +// CHECK-LP64-NEXT: __ZN1MD1Ev: + + +// CHECK-LP32: call L__ZN1MC1Ev +// CHECK-LP32: call L__ZN1MD1Ev +// CHECK-LP32: .globl __ZN1MD1Ev +// CHECK-LP32-NEXT: .weak_definition __ZN1MD1Ev +// CHECK-LP32-NEXT:__ZN1MD1Ev: diff --git a/test/CodeGenCXX/delete.cpp b/test/CodeGenCXX/delete.cpp new file mode 100644 index 0000000..9e3feef --- /dev/null +++ b/test/CodeGenCXX/delete.cpp @@ -0,0 +1,37 @@ +// RUN: clang-cc %s -emit-llvm -o %t && + +void t1(int *a) { + delete a; +} + +struct S { + int a; +}; + +// POD types. +void t3(S *s) { + delete s; +} + +// Non-POD +struct T { + ~T(); + int a; +}; + +void t4(T *t) { + // RUN: grep "call void @_ZN1TD1Ev" %t | count 1 + delete t; +} + +// PR5102 +template +class A { + operator T *() const; +}; + +void f() { + A a; + + delete a; +} diff --git a/test/CodeGenCXX/derived-to-base.cpp b/test/CodeGenCXX/derived-to-base.cpp new file mode 100644 index 0000000..63492d6 --- /dev/null +++ b/test/CodeGenCXX/derived-to-base.cpp @@ -0,0 +1,16 @@ +// RUN: clang-cc -emit-llvm %s -o - +struct A { + void f(); + + int a; +}; + +struct B : A { + double b; +}; + +void f() { + B b; + + b.f(); +} diff --git a/test/CodeGenCXX/destructor-calls.cpp b/test/CodeGenCXX/destructor-calls.cpp new file mode 100644 index 0000000..3f0288b --- /dev/null +++ b/test/CodeGenCXX/destructor-calls.cpp @@ -0,0 +1,41 @@ +// RUN: clang-cc %s -emit-llvm -o %t + +extern "C" int printf(...); + +static int val; + +struct B { + B() : iB(++val) { printf("B()\n"); } + int iB; + ~B() { printf("~B(%d)\n", iB); --val; } +}; + +struct M : B { + M() : iM(++val) { printf("M()\n"); } + int iM; + ~M() { printf("~M(%d)\n", iM); --val; } +}; + +struct P { + P() : iP(++val) { printf("P()\n"); } + int iP; + ~P() { printf("~P(%d)\n", iP); --val; } +}; + +struct N : M, P { + N() { printf("N()\n"); iN = ++val; } + ~N() { printf("~N(%d) val = %d\n", iN, --val); } + int iN; + M m; + P p; +}; + +struct O : B { + ~O() { return; } +}; + +int main() { + N n1; + N n2; + O o; +} diff --git a/test/CodeGenCXX/destructors.cpp b/test/CodeGenCXX/destructors.cpp new file mode 100644 index 0000000..44d2b29 --- /dev/null +++ b/test/CodeGenCXX/destructors.cpp @@ -0,0 +1,30 @@ +// RUN: clang-cc %s -emit-llvm -o - +struct A { + int a; + + ~A(); +}; + +// Base with non-trivial destructor +struct B : A { + ~B(); +}; + +B::~B() { } + +// Field with non-trivial destructor +struct C { + A a; + + ~C(); +}; + +C::~C() { } + +// PR5084 +template +class A1 { + ~A1(); +}; + +template<> A1::~A1(); diff --git a/test/CodeGenCXX/devirtualize-virtual-function-calls.cpp b/test/CodeGenCXX/devirtualize-virtual-function-calls.cpp new file mode 100644 index 0000000..cbf55ad --- /dev/null +++ b/test/CodeGenCXX/devirtualize-virtual-function-calls.cpp @@ -0,0 +1,47 @@ +// RUN: clang-cc %s -emit-llvm -o - | FileCheck %s + +struct A { + virtual void f(); + + A h(); +}; + +A g(); + +void f(A a, A *ap, A& ar) { + // This should not be a virtual function call. + + // CHECK: call void @_ZN1A1fEv(%struct.A* %a) + a.f(); + + // CHECK: call void % + ap->f(); + + // CHECK: call void % + ar.f(); + + // CHECK: call void @_ZN1A1fEv + A().f(); + + // CHECK: call void @_ZN1A1fEv + g().f(); + + // CHECK: call void @_ZN1A1fEv + a.h().f(); +} + +struct B { + virtual void f(); + ~B(); + + B h(); +}; + + +void f() { + // CHECK: call void @_ZN1B1fEv + B().f(); + + // CHECK: call void @_ZN1B1fEv + B().h().f(); +} diff --git a/test/CodeGenCXX/explicit-instantiation.cpp b/test/CodeGenCXX/explicit-instantiation.cpp index 38966aa..8a9e65c 100644 --- a/test/CodeGenCXX/explicit-instantiation.cpp +++ b/test/CodeGenCXX/explicit-instantiation.cpp @@ -1,11 +1,14 @@ -// RUN: clang-cc -emit-llvm -femit-all-decls -o %t %s && -// RUN: grep "_ZNK4plusIillEclERKiRKl" %t | count 1 +// RUN: clang-cc -emit-llvm -triple i686-pc-linue-gnu -o %t %s && +// RUN: grep "define i32 @_ZNK4plusIillEclERKiRKl" %t | count 1 template struct plus { - Result operator()(const T& t, const U& u) const { - return t + u; - } + Result operator()(const T& t, const U& u) const; }; +template +Result plus::operator()(const T& t, const U& u) const { + return t + u; +} + template struct plus; diff --git a/test/CodeGenCXX/function-template-specialization.cpp b/test/CodeGenCXX/function-template-specialization.cpp index bea3af2..677be4c 100644 --- a/test/CodeGenCXX/function-template-specialization.cpp +++ b/test/CodeGenCXX/function-template-specialization.cpp @@ -1,4 +1,4 @@ -// RUN: clang-cc -emit-llvm %s -o %t && +// RUN: clang-cc -emit-llvm %s -o - | FileCheck %s template T* next(T* ptr, const U& diff); @@ -8,11 +8,10 @@ T* next(T* ptr, const U& diff) { } void test(int *iptr, float *fptr, int diff) { - // FIXME: should be "_Z4nextIiiEPT_S1_RKT0_" - // RUN: grep "_Z4nextIiiEPiPiRKi" %t && + // CHECK: _Z4nextIiiEPT_S1_RKT0_ iptr = next(iptr, diff); - // FIXME: should be "_Z4nextIfiEPT_S1_RKT0_" - // RUN: grep "_Z4nextIfiEPfPfRKi" %t && + + // CHECK: _Z4nextIfiEPT_S1_RKT0_ fptr = next(fptr, diff); } @@ -21,7 +20,7 @@ T* next(T* ptr, const U& diff); void test2(int *iptr, double *dptr, int diff) { iptr = next(iptr, diff); - // FIXME: should be "_Z4nextIdiEPT_S1_RKT0_" - // RUN: grep "_Z4nextIdiEPdPdRKi" %t + + // CHECK: _Z4nextIdiEPT_S1_RKT0_ dptr = next(dptr, diff); -} \ No newline at end of file +} diff --git a/test/CodeGenCXX/global-init.cpp b/test/CodeGenCXX/global-init.cpp new file mode 100644 index 0000000..ae450e1 --- /dev/null +++ b/test/CodeGenCXX/global-init.cpp @@ -0,0 +1,16 @@ +// RUN: clang-cc -triple=x86_64-apple-darwin10 -emit-llvm %s -o - |FileCheck %s + +struct A { + A(); + ~A(); +}; + +struct B { B(); ~B(); }; + +// CHECK: call void @_ZN1AC1Ev(%struct.A* @a) +// CHECK: call i32 @__cxa_atexit(void (i8*)* bitcast (void (%struct.A*)* @_ZN1AD1Ev to void (i8*)*), i8* getelementptr inbounds (%struct.A* @a, i32 0, i32 0), i8* bitcast (i8** @__dso_handle to i8*)) +A a; + +// CHECK: call void @_ZN1BC1Ev(%struct.A* @b) +// CHECK: call i32 @__cxa_atexit(void (i8*)* bitcast (void (%struct.A*)* @_ZN1BD1Ev to void (i8*)*), i8* getelementptr inbounds (%struct.A* @b, i32 0, i32 0), i8* bitcast (i8** @__dso_handle to i8*)) +B b; diff --git a/test/CodeGenCXX/mangle-extreme.cpp b/test/CodeGenCXX/mangle-extreme.cpp new file mode 100644 index 0000000..77558d2 --- /dev/null +++ b/test/CodeGenCXX/mangle-extreme.cpp @@ -0,0 +1,47 @@ +// RUN: clang-cc -emit-llvm %s -o - -triple=x86_64-apple-darwin9 | FileCheck %s + +struct X { }; + +// CHECK: define void @_Z1fPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPPP1XS13_S12_S11_S10_SZ_SY_SX_SW_SV_SU_ST_SS_SR_SQ_SP_SO_SN_SM_SL_SK_SJ_SI_SH_SG_SF_SE_SD_SC_SB_SA_S9_S8_S7_S6_S5_S4_S3_S2_S1_S0_S_( +void f(X****************************************, + X****************************************, + X***************************************, + X**************************************, + X*************************************, + X************************************, + X***********************************, + X**********************************, + X*********************************, + X********************************, + X*******************************, + X******************************, + X*****************************, + X****************************, + X***************************, + X**************************, + X*************************, + X************************, + X***********************, + X**********************, + X*********************, + X********************, + X*******************, + X******************, + X*****************, + X****************, + X***************, + X**************, + X*************, + X************, + X***********, + X**********, + X*********, + X********, + X*******, + X******, + X*****, + X****, + X***, + X**, + X*, + X) { } diff --git a/test/CodeGenCXX/mangle-subst-std.cpp b/test/CodeGenCXX/mangle-subst-std.cpp new file mode 100644 index 0000000..fbce204 --- /dev/null +++ b/test/CodeGenCXX/mangle-subst-std.cpp @@ -0,0 +1,39 @@ +// RUN: clang-cc -emit-llvm %s -o - -triple=x86_64-apple-darwin9 | FileCheck %s + +namespace std { + struct A { A(); }; + + // CHECK: define void @_ZNSt1AC1Ev + // CHECK: define void @_ZNSt1AC2Ev + A::A() { } +}; + +namespace std { + template struct allocator { }; +} + +// CHECK: define void @_Z1fSaIcESaIiE +void f(std::allocator, std::allocator) { } + +namespace std { + template struct basic_string { }; +} + +// CHECK: define void @_Z1fSbIcciE +void f(std::basic_string) { } + +namespace std { + template struct char_traits { }; + + typedef std::basic_string, std::allocator > string; +} + +// CHECK: _Z1fSs +void f(std::string) { } + +namespace std { + template struct basic_ostream { }; +} + +// CHECK: _Z1fSo +void f(std::basic_ostream >) { } diff --git a/test/CodeGenCXX/mangle-subst.cpp b/test/CodeGenCXX/mangle-subst.cpp new file mode 100644 index 0000000..c53a630 --- /dev/null +++ b/test/CodeGenCXX/mangle-subst.cpp @@ -0,0 +1,56 @@ +// RUN: clang-cc -emit-llvm %s -o - -triple=x86_64-apple-darwin9 | FileCheck %s + +struct X {}; + +// CHECK: define void @_Z1f1XS_( +void f(X, X) { } + +// CHECK: define void @_Z1fR1XS0_( +void f(X&, X&) { } + +// CHECK: define void @_Z1fRK1XS1_( +void f(const X&, const X&) { } + +typedef void T(); +struct S {}; + +// CHECK: define void @_Z1fPFvvEM1SFvvE( +void f(T*, T (S::*)) {} + +namespace A { + struct A { }; + struct B { }; +}; + +// CHECK: define void @_Z1fN1A1AENS_1BE( +void f(A::A a, A::B b) { } + +struct C { + struct D { }; +}; + +// CHECK: define void @_Z1fN1C1DERS_PS_S1_( +void f(C::D, C&, C*, C&) { } + +template +struct V { + typedef int U; +}; + +template void f1(typename V::U, V) { } + +// CHECK: @_Z2f1IiEvN1VIT_E1UES2_ +template void f1(int, V); + +template void f2(V, typename V::U) { } + +// CHECK: @_Z2f2IiEv1VIT_ENS2_1UE +template void f2(V, int); + +namespace NS { +template struct S1 {}; +template void ft3(S1, S1) { } + +// CHECK: @_ZN2NS3ft3IiEEvNS_2S1IT_EENS1_IcEE +template void ft3(S1, S1); +} diff --git a/test/CodeGenCXX/mangle.cpp b/test/CodeGenCXX/mangle.cpp index ef36a8b..2ffbae7 100644 --- a/test/CodeGenCXX/mangle.cpp +++ b/test/CodeGenCXX/mangle.cpp @@ -1,87 +1,223 @@ -// RUN: clang-cc -emit-llvm %s -o %t -triple=x86_64-apple-darwin9 && +// RUN: clang-cc -emit-llvm %s -o - -triple=x86_64-apple-darwin9 | FileCheck %s -// FIXME: This test is intentionally trivial, because we can't yet -// CodeGen anything real in C++. struct X { }; struct Y { }; -// RUN: grep _ZplRK1YRA100_P1X %t | count 1 && +// CHECK: @unmangled_variable = global +// CHECK: @_ZN1N1iE = global +// CHECK: @_ZZN1N1fEiiE1b = internal global +// CHECK: @_ZZN1N1gEvE1a = internal global +// CHECK: @_ZGVZN1N1gEvE1a = internal global + +// CHECK: define zeroext i1 @_ZplRK1YRA100_P1X bool operator+(const Y&, X* (&xs)[100]) { return false; } -// RUN: grep _Z1f1s %t | count 1 && +// CHECK: define void @_Z1f1s typedef struct { int a; } s; void f(s) { } -// RUN: grep _Z1f1e %t| count 1 && +// CHECK: define void @_Z1f1e typedef enum { foo } e; void f(e) { } -// RUN: grep _Z1f1u %t | count 1 && +// CHECK: define void @_Z1f1u typedef union { int a; } u; void f(u) { } -// RUN: grep _Z1f1x %t | count 1 && +// CHECK: define void @_Z1f1x typedef struct { int a; } x,y; void f(y) { } -// RUN: grep _Z1fv %t | count 1 && +// CHECK: define void @_Z1fv void f() { } -// RUN: grep _ZN1N1fEv %t | count 1 && +// CHECK: define void @_ZN1N1fEv namespace N { void f() { } } -// RUN: grep _ZN1N1N1fEv %t | count 1 && +// CHECK: define void @_ZN1N1N1fEv namespace N { namespace N { void f() { } } } -// RUN: grep unmangled_function %t | count 1 && +// CHECK: define void @unmangled_function extern "C" { namespace N { void unmangled_function() { } } } -// RUN: grep unmangled_variable %t | count 1 && extern "C" { namespace N { int unmangled_variable = 10; } } -// RUN: grep _ZN1N1iE %t | count 1 && namespace N { int i; } -// RUN: grep _ZZN1N1fEiiE1b %t | count 2 && namespace N { int f(int, int) { static int b; return b; } } -// RUN: grep "_ZZN1N1gEvE1a =" %t | count 1 && -// RUN: grep "_ZGVZN1N1gEvE1a =" %t | count 1 && namespace N { int h(); void g() { static int a = h(); } } -// RUN: grep "_Z1fno" %t | count 1 && +// CHECK: define void @_Z1fno void f(__int128_t, __uint128_t) { } template struct S1 {}; -// RUN: grep "_Z1f2S1IiE" %t | count 1 && +// CHECK: define void @_Z1f2S1IiE void f(S1) {} -// RUN: grep "_Z1f2S1IdE" %t | count 1 && +// CHECK: define void @_Z1f2S1IdE void f(S1) {} template struct S2 {}; -// RUN: grep "_Z1f2S2ILi100EE" %t | count 1 && +// CHECK: define void @_Z1f2S2ILi100EE void f(S2<100>) {} -// RUN: grep "_Z1f2S2ILin100EE" %t | count 1 && +// CHECK: define void @_Z1f2S2ILin100EE void f(S2<-100>) {} template struct S3 {}; -// RUN: grep "_Z1f2S3ILb1EE" %t | count 1 && +// CHECK: define void @_Z1f2S3ILb1EE void f(S3) {} -// RUN: grep "_Z1f2S3ILb0EE" %t | count 1 && +// CHECK: define void @_Z1f2S3ILb0EE void f(S3) {} -// RUN: grep "_Z2f22S3ILb1EE" %t | count 1 && +// CHECK: define void @_Z2f22S3ILb1EE void f2(S3<100>) {} struct S; -// RUN: grep "_Z1fM1SKFvvE" %t | count 1 && +// CHECK: define void @_Z1fM1SKFvvE void f(void (S::*)() const) {} -// RUN: grep "_Z1fM1SFvvE" %t | count 1 +// CHECK: define void @_Z1fM1SFvvE void f(void (S::*)()) {} + +// CHECK: define void @_Z1fi +void f(const int) { } + +template void ft1(U u, T t) { } + +template void ft2(T t, void (*)(T), void (*)(T)) { } + +template > struct S4 { }; +template void ft3(S4*) { } + +namespace NS { + template void ft1(T) { } +} + +void g1() { + // CHECK: @_Z3ft1IidEvT0_T_ + ft1(1, 0); + + // CHECK: @_Z3ft2IcEvT_PFvS0_ES2_ + ft2(1, 0, 0); + + // CHECK: @_Z3ft3IiEvP2S4IT_2S1IS1_EE + ft3(0); + + // CHECK: @_ZN2NS3ft1IiEEvT_ + NS::ft1(1); +} + +// Expressions +template struct S5 { }; + +template void ft4(S5) { } +void g2() { + // CHECK: @_Z3ft4ILi10EEv2S5IXT_EE + ft4(S5<10>()); + + // CHECK: @_Z3ft4ILi20EEv2S5IXT_EE + ft4(S5<20>()); +} + +extern "C++" { + // CHECK: @_Z1hv + void h() { } +} + +// PR5019 +extern "C" { struct a { int b; }; } + +// CHECK: @_Z1fP1a +int f(struct a *x) { + return x->b; +} + +// PR5017 +extern "C" { +struct Debug { + const Debug& operator<< (unsigned a) const { } +}; +Debug dbg; +// CHECK: @_ZNK5DebuglsEj +int main(void) { dbg << 32 ;} +} + +template struct S6 { + typedef int B; +}; + +template void ft5(typename S6::B) { } +// CHECK: @_Z3ft5IiEvN2S6IT_E1BE +template void ft5(int); + +template class A {}; + +namespace NS { +template bool operator==(const A&, const A&) { return true; } +} + +// CHECK: @_ZN2NSeqIcEEbRK1AIT_ES5_ +template bool NS::operator==(const ::A&, const ::A&); + +namespace std { +template bool operator==(const A&, const A&) { return true; } +} + +// CHECK: @_ZSteqIcEbRK1AIT_ES4_ +template bool std::operator==(const ::A&, const ::A&); + +struct S { + typedef int U; +}; + +template typename T::U ft6(const T&) { return 0; } + +// CHECK: @_Z3ft6I1SENT_1UERKS1_ +template int ft6(const S&); + +template struct __is_scalar { + enum { __value = 1 }; +}; + +template struct __enable_if { }; + +template struct __enable_if { + typedef T __type; +}; + +// PR5063 +template typename __enable_if<__is_scalar::__value, void>::__type ft7() { } + +// CHECK: @_Z3ft7IiEN11__enable_ifIXsr11__is_scalarIT_E7__valueEvE6__typeEv +template void ft7(); +// CHECK: @_Z3ft7IPvEN11__enable_ifIXsr11__is_scalarIT_E7__valueEvE6__typeEv +template void ft7(); + +// PR5144 +extern "C" { +void extern_f(void); +}; + +// CHECK: @extern_f +void extern_f(void) { } + +struct S7 { + struct S { S(); }; + + struct { + S s; + } a; +}; + +// PR5139 +// CHECK: @_ZN2S7C1Ev +// CHECK: @_ZN2S7C2Ev +// CHECK: @"_ZN2S73$_0C1Ev" +S7::S7() {} + diff --git a/test/CodeGenCXX/member-function-pointers.cpp b/test/CodeGenCXX/member-function-pointers.cpp new file mode 100644 index 0000000..13f7de5 --- /dev/null +++ b/test/CodeGenCXX/member-function-pointers.cpp @@ -0,0 +1,73 @@ +// RUN: clang-cc %s -emit-llvm -o - -triple=x86_64-apple-darwin9 | FileCheck %s + +struct A { int a; void f(); virtual void vf(); }; +struct B { int b; virtual void g(); }; +struct C : B, A { }; + +void (A::*pa)(); +void (A::*volatile vpa)(); +void (B::*pb)(); +void (C::*pc)(); + +// CHECK: @pa2 = global %0 { i64 ptrtoint (void ()* @_ZN1A1fEv to i64), i64 0 }, align 8 +void (A::*pa2)() = &A::f; + +// CHECK: @pa3 = global %0 { i64 1, i64 0 }, align 8 +void (A::*pa3)() = &A::vf; + +// CHECK: @pc2 = global %0 { i64 ptrtoint (void ()* @_ZN1A1fEv to i64), i64 16 }, align 8 +void (C::*pc2)() = &C::f; + +// CHECK: @pc3 = global %0 { i64 1, i64 0 }, align 8 +void (A::*pc3)() = &A::vf; + +void f() { + // CHECK: store i64 0, i64* getelementptr inbounds (%0* @pa, i32 0, i32 0) + // CHECK: store i64 0, i64* getelementptr inbounds (%0* @pa, i32 0, i32 1) + pa = 0; + + // CHECK: volatile store i64 0, i64* getelementptr inbounds (%0* @vpa, i32 0, i32 0) + // CHECK: volatile store i64 0, i64* getelementptr inbounds (%0* @vpa, i32 0, i32 1) + vpa = 0; + + // CHECK: store i64 %0, i64* getelementptr inbounds (%0* @pc, i32 0, i32 0) + // CHECK: [[ADJ:%[a-zA-Z0-9\.]+]] = add i64 %1, 16 + // CHECK: store i64 [[ADJ]], i64* getelementptr inbounds (%0* @pc, i32 0, i32 1) + pc = pa; +} + +void f2() { + // CHECK: [[pa2ptr:%[a-zA-Z0-9\.]+]] = getelementptr inbounds %0* %pa2, i32 0, i32 0 + // CHECK: store i64 ptrtoint (void ()* @_ZN1A1fEv to i64), i64* [[pa2ptr]] + // CHECK: [[pa2adj:%[a-zA-Z0-9\.]+]] = getelementptr inbounds %0* %pa2, i32 0, i32 1 + // CHECK: store i64 0, i64* [[pa2adj]] + void (A::*pa2)() = &A::f; + + // CHECK: [[pa3ptr:%[a-zA-Z0-9\.]+]] = getelementptr inbounds %0* %pa3, i32 0, i32 0 + // CHECK: store i64 1, i64* [[pa3ptr]] + // CHECK: [[pa3adj:%[a-zA-Z0-9\.]+]] = getelementptr inbounds %0* %pa3, i32 0, i32 1 + // CHECK: store i64 0, i64* [[pa2adj]] + void (A::*pa3)() = &A::vf; +} + +void f3(A *a, A &ar) { + (a->*pa)(); + (ar.*pa)(); +} + +// PR5177 +namespace PR5177 { + struct A { + bool foo(int*) const; + } a; + + struct B1 { + bool (A::*pmf)(int*) const; + const A* pa; + + B1() : pmf(&A::foo), pa(&a) {} + bool operator()() const { return (pa->*pmf)(new int); } + }; + + void bar(B1 b2) { while (b2()) ; } +} diff --git a/test/CodeGenCXX/member-functions.cpp b/test/CodeGenCXX/member-functions.cpp index 8ada907..29629d5 100644 --- a/test/CodeGenCXX/member-functions.cpp +++ b/test/CodeGenCXX/member-functions.cpp @@ -58,6 +58,6 @@ struct T { void test3() { T t1, t2; - // RUN: grep "call void @_ZN1TpsERK1T" %t + // RUN: grep "call void @_ZN1TpsERKS_" %t T result = t1 + t2; } diff --git a/test/CodeGenCXX/member-pointers-zero-init.cpp b/test/CodeGenCXX/member-pointers-zero-init.cpp new file mode 100644 index 0000000..e7b0fda --- /dev/null +++ b/test/CodeGenCXX/member-pointers-zero-init.cpp @@ -0,0 +1,34 @@ +// RUN: clang-cc -emit-llvm %s -o %t -triple=x86_64-apple-darwin9 && + +struct A { + int i; +}; + +// RUN: grep "@a = global i64 -1" %t && +int A::* a; + +// RUN: grep "@aa = global \[2 x i64\] \[i64 -1, i64 -1\]" %t && +int A::* aa[2]; + +// RUN: grep "@aaa = global \[2 x \[2 x i64\]\] \[\[2 x i64\] \[i64 -1, i64 -1\], \[2 x i64\] \[i64 -1, i64 -1\]\]" %t && +int A::* aaa[2][2]; + +// RUN: grep "@b = global i64 -1" %t && +int A::* b = 0; + +void f() { + // RUN: grep "%.* = icmp ne i64 %.*, -1" %t | count 2 && + if (a) { } + if (a != 0) { } + + // RUN: grep "%.* = icmp ne i64 -1, %.*" %t | count 1 && + if (0 != a) { } + + // RUN: grep "%.* = icmp eq i64 %.*, -1" %t | count 1 && + if (a == 0) { } + + // RUN: grep "%.* = icmp eq i64 -1, %.*" %t | count 1 + if (0 == a) { } + +} + diff --git a/test/CodeGenCXX/namespace-aliases.cpp b/test/CodeGenCXX/namespace-aliases.cpp new file mode 100644 index 0000000..5baea87 --- /dev/null +++ b/test/CodeGenCXX/namespace-aliases.cpp @@ -0,0 +1,3 @@ +// RUN: clang-cc -emit-llvm-only %s +namespace A { } +namespace B = A; diff --git a/test/CodeGenCXX/nested-base-member-access.cpp b/test/CodeGenCXX/nested-base-member-access.cpp new file mode 100644 index 0000000..308f952 --- /dev/null +++ b/test/CodeGenCXX/nested-base-member-access.cpp @@ -0,0 +1,52 @@ +// RUN: clang-cc %s -emit-llvm -o %t + +extern "C" int printf(...); + +struct M { + M(int i){ iM = i; } + int iM; + void MPR() { printf("iM = %d\n", iM); } + +}; + +struct Q { + Q(int i){ iQ = i; } + int iQ; + void QPR() { printf("iQ = %d\n", iQ); } +}; + +struct IQ { + IQ(int i) { iIQ = i; } + void IQPR() { printf("iIQ = %d\n", iIQ); } + int iIQ; +}; + +struct L : IQ { + L(int i) : IQ(i+100) { iL = i; } + int iL; +}; + +struct P : Q, L { + P(int i) : Q(i+100), L(i+200) { iP = i; } + int iP; + void PPR() { printf("iP = %d\n", iP); } +}; + + +struct N : M,P { + N() : M(100), P(200) {} + void PR() { + this->MPR(); this->PPR(); this->QPR(); + IQPR(); + printf("iM = %d\n", iM); + printf("iP = %d\n", iP); + printf("iQ = %d\n", iQ); + printf("iL = %d\n", iL); + printf("iIQ = %d\n", iIQ); + } +}; + +int main() { + N n1; + n1.PR(); +} diff --git a/test/CodeGenCXX/new.cpp b/test/CodeGenCXX/new.cpp index 480bbce..c6cee18 100644 --- a/test/CodeGenCXX/new.cpp +++ b/test/CodeGenCXX/new.cpp @@ -1,4 +1,4 @@ -// RUN: clang-cc %s -emit-llvm -o %t && +// RUN: clang-cc %s -emit-llvm -o - | FileCheck %s void t1() { int* a = new int; @@ -32,7 +32,7 @@ struct T { }; void t4() { - // RUN: grep "call void @_ZN1TC1Ev" %t | count 1 && + // CHECK: call void @_ZN1TC1Ev T *t = new T; } @@ -42,7 +42,7 @@ struct T2 { }; void t5() { - // RUN: grep "call void @_ZN2T2C1Eii" %t | count 1 + // CHECK: call void @_ZN2T2C1Eii T2 *t2 = new T2(10, 10); } @@ -54,3 +54,20 @@ int *t6() { void t7() { new int(); } + +struct U { + ~U(); +}; + +void t8(int n) { + new int[10]; + new int[n]; + + // Non-POD + new T[10]; + new T[n]; + + // Cookie required + new U[10]; + new U[n]; +} diff --git a/test/CodeGenCXX/nullptr.cpp b/test/CodeGenCXX/nullptr.cpp new file mode 100644 index 0000000..7bc52ad --- /dev/null +++ b/test/CodeGenCXX/nullptr.cpp @@ -0,0 +1,7 @@ +// RUN: clang-cc -std=c++0x %s -emit-llvm -o %t + +int* a = nullptr; + +void f() { + int* a = nullptr; +} diff --git a/test/CodeGenCXX/overload-binop-implicitconvert.cpp b/test/CodeGenCXX/overload-binop-implicitconvert.cpp new file mode 100644 index 0000000..f17a458 --- /dev/null +++ b/test/CodeGenCXX/overload-binop-implicitconvert.cpp @@ -0,0 +1,22 @@ +// RUN: clang-cc %s -emit-llvm-only +class T +{}; + +void print(const char *t); + +T& operator<< (T& t,const char* c) +{ + print(c); + return t; +} + + +int main() +{ + T t; + print("foo"); + t<<"foo"; + + return 0; +} + diff --git a/test/CodeGenCXX/predefined-expr-sizeof.cpp b/test/CodeGenCXX/predefined-expr-sizeof.cpp new file mode 100644 index 0000000..e318fbe --- /dev/null +++ b/test/CodeGenCXX/predefined-expr-sizeof.cpp @@ -0,0 +1,30 @@ +// RUN: clang-cc %s -emit-llvm -o - | FileCheck %s + +// CHECK: store i32 49, i32* %size +// CHECK: store i32 52, i32* %size +template +class TemplateClass { +public: + void templateClassFunction() { + int size = sizeof(__PRETTY_FUNCTION__); + } +}; + +// CHECK: store i32 27, i32* %size +// CHECK: store i32 30, i32* %size +template +void functionTemplate(T t) { + int size = sizeof(__PRETTY_FUNCTION__); +} + +int main() { + TemplateClass t1; + t1.templateClassFunction(); + TemplateClass t2; + t2.templateClassFunction(); + + functionTemplate(0); + functionTemplate(0.0); + + return 0; +} diff --git a/test/CodeGenCXX/predefined-expr.cpp b/test/CodeGenCXX/predefined-expr.cpp new file mode 100644 index 0000000..95bc255 --- /dev/null +++ b/test/CodeGenCXX/predefined-expr.cpp @@ -0,0 +1,226 @@ +// RUN: clang-cc %s -emit-llvm -o - | FileCheck %s + +// CHECK: private constant [15 x i8] c"externFunction\00" +// CHECK: private constant [26 x i8] c"void NS::externFunction()\00" + +// CHECK: private constant [22 x i8] c"classTemplateFunction\00" +// CHECK: private constant [60 x i8] c"void NS::ClassTemplate::classTemplateFunction()\00" +// CHECK: private constant [53 x i8] c"void NS::ClassTemplate::classTemplateFunction()\00" + +// CHECK: private constant [18 x i8] c"functionTemplate1\00" +// CHECK: private constant [45 x i8] c"void NS::Base::functionTemplate1(NS::Base *)\00" +// CHECK: private constant [38 x i8] c"void NS::Base::functionTemplate1(int)\00" + +// CHECK: private constant [12 x i8] c"~Destructor\00" +// CHECK: private constant [35 x i8] c"void NS::Destructor::~Destructor()\00" + +// CHECK: private constant [12 x i8] c"Constructor\00" +// CHECK: private constant [46 x i8] c"void NS::Constructor::Constructor(NS::Base *)\00" +// CHECK: private constant [39 x i8] c"void NS::Constructor::Constructor(int)\00" +// CHECK: private constant [36 x i8] c"void NS::Constructor::Constructor()\00" + +// CHECK: private constant [16 x i8] c"virtualFunction\00" +// CHECK: private constant [44 x i8] c"virtual void NS::Derived::virtualFunction()\00" + +// CHECK: private constant [26 x i8] c"functionReturingTemplate2\00" +// CHECK: private constant [64 x i8] c"ClassTemplate NS::Base::functionReturingTemplate2()\00" + +// CHECK: private constant [26 x i8] c"functionReturingTemplate1\00" +// CHECK: private constant [57 x i8] c"ClassTemplate NS::Base::functionReturingTemplate1()\00" + +// CHECK: private constant [23 x i8] c"withTemplateParameter2\00" +// CHECK: private constant [65 x i8] c"void NS::Base::withTemplateParameter2(ClassTemplate)\00" + +// CHECK: private constant [23 x i8] c"withTemplateParameter1\00" +// CHECK: private constant [58 x i8] c"void NS::Base::withTemplateParameter1(ClassTemplate)\00" + +// CHECK: private constant [23 x i8] c"functionReturningClass\00" +// CHECK: private constant [45 x i8] c"NS::Base *NS::Base::functionReturningClass()\00" + +// CHECK: private constant [23 x i8] c"functionWithParameters\00" +// CHECK: private constant [64 x i8] c"void NS::Base::functionWithParameters(int, float *, NS::Base *)\00" + +// CHECK: private constant [17 x i8] c"variadicFunction\00" +// CHECK: private constant [42 x i8] c"void NS::Base::variadicFunction(int, ...)\00" + +// CHECK: private constant [41 x i8] c"virtual void NS::Base::virtualFunction()\00" + +// CHECK: private constant [15 x i8] c"inlineFunction\00" +// CHECK: private constant [32 x i8] c"void NS::Base::inlineFunction()\00" + +// CHECK: private constant [11 x i8] c"staticFunc\00" +// CHECK: private constant [28 x i8] c"void NS::Base::staticFunc()\00" + +int printf(const char * _Format, ...); + +namespace NS { + +template +class ClassTemplate { +public: + void classTemplateFunction() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } +}; + +class Base { +public: + static void staticFunc() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } + + inline void inlineFunction() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } + + virtual void virtualFunction() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } + + void functionWithParameters(int, float*, Base* base) { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } + + Base *functionReturningClass() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + return 0; + } + + void variadicFunction(int, ...) { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } + + void withTemplateParameter1(ClassTemplate) { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } + + void withTemplateParameter2(ClassTemplate) { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } + + ClassTemplate functionReturingTemplate1() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + return ClassTemplate(); + } + + ClassTemplate functionReturingTemplate2() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + return ClassTemplate(); + } + + template + void functionTemplate1(T t) { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } +}; + +class Derived : public Base { +public: + // Virtual function without being explicitally written. + void virtualFunction() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } +}; + +class Constructor { +public: + Constructor() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } + + Constructor(int) { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } + + Constructor(Base *) { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } + +}; + +class Destructor { +public: + ~Destructor() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); + } +}; + +extern void externFunction() { + printf("__func__ %s\n", __func__); + printf("__FUNCTION__ %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__ %s\n\n", __PRETTY_FUNCTION__); +} + +} + +int main() { + NS::Base::staticFunc(); + + NS::Base b; + b.inlineFunction(); + b.virtualFunction(); + b.variadicFunction(0); + b.functionWithParameters(0, 0, 0); + b.functionReturningClass(); + + b.withTemplateParameter1(NS::ClassTemplate()); + b.withTemplateParameter2(NS::ClassTemplate()); + b.functionReturingTemplate1(); + b.functionReturingTemplate2(); + b.functionTemplate1(0); + b.functionTemplate1(0); + + NS::Derived d; + d.virtualFunction(); + + NS::ClassTemplate t1; + t1.classTemplateFunction(); + NS::ClassTemplate t2; + t2.classTemplateFunction(); + + NS::Constructor c1; + NS::Constructor c2(0); + NS::Constructor c3((NS::Base *)0); + + { + NS::Destructor destructor; + } + + NS::externFunction(); + + return 0; +} diff --git a/test/CodeGenCXX/references.cpp b/test/CodeGenCXX/references.cpp index 8e19356..c235521 100644 --- a/test/CodeGenCXX/references.cpp +++ b/test/CodeGenCXX/references.cpp @@ -87,3 +87,16 @@ int reference_decl() { const int& b = 1; return a+b; } + +struct A { + int& b(); +}; + +void f(A* a) { + int b = a->b(); +} + +// PR5122 +void *foo = 0; +void * const & kFoo = foo; + diff --git a/test/CodeGenCXX/reinterpret-cast.cpp b/test/CodeGenCXX/reinterpret-cast.cpp new file mode 100644 index 0000000..ae3ab2f --- /dev/null +++ b/test/CodeGenCXX/reinterpret-cast.cpp @@ -0,0 +1,12 @@ +// RUN: clang-cc -emit-llvm -o - %s -std=c++0x +void *f1(unsigned long l) { + return reinterpret_cast(l); +} + +unsigned long f2() { + return reinterpret_cast(nullptr); +} + +unsigned long f3(void *p) { + return reinterpret_cast(p); +} \ No newline at end of file diff --git a/test/CodeGenCXX/static-data-member.cpp b/test/CodeGenCXX/static-data-member.cpp new file mode 100644 index 0000000..6e2abcc --- /dev/null +++ b/test/CodeGenCXX/static-data-member.cpp @@ -0,0 +1,8 @@ +// RUN: clang-cc -emit-llvm -o - %s +struct S { + static int i; +}; + +void f() { + int a = S::i; +} diff --git a/test/CodeGenCXX/static-init.cpp b/test/CodeGenCXX/static-init.cpp new file mode 100644 index 0000000..44dd142 --- /dev/null +++ b/test/CodeGenCXX/static-init.cpp @@ -0,0 +1,13 @@ +// RUN: clang-cc -triple=x86_64-apple-darwin9 -emit-llvm %s -o %t && +// RUN: grep "call void @_ZN1AC1Ev" %t | count 1 && +// RUN: grep "call i32 @__cxa_atexit(void (i8\*)\* bitcast (void (%.truct.A\*)\* @_ZN1AD1Ev to void (i8\*)\*), i8\* getelementptr inbounds (%.truct.A\* @_ZZ1fvE1a, i32 0, i32 0), i8\* bitcast (i8\*\* @__dso_handle to i8\*))" %t | count 1 + +struct A { + A(); + ~A(); +}; + +void f() { + static A a; +} + diff --git a/test/CodeGenCXX/temp-1.cpp b/test/CodeGenCXX/temp-1.cpp new file mode 100644 index 0000000..9b97f00 --- /dev/null +++ b/test/CodeGenCXX/temp-1.cpp @@ -0,0 +1,83 @@ +// RUN: clang-cc -emit-llvm %s -o %t -triple=x86_64-apple-darwin9 && +struct A { + A(); + ~A(); + void f(); +}; + +// RUN: grep "call void @_ZN1AC1Ev" %t | count 2 && +// RUN: grep "call void @_ZN1AD1Ev" %t | count 2 && +void f1() { + (void)A(); + A().f(); +} + +// Function calls +struct B { + B(); + ~B(); +}; + +B g(); + +// RUN: grep "call void @_ZN1BC1Ev" %t | count 0 && +// RUN: grep "call void @_ZN1BD1Ev" %t | count 1 && +void f2() { + (void)g(); +} + +// Member function calls +struct C { + C(); + ~C(); + + C f(); +}; + +// RUN: grep "call void @_ZN1CC1Ev" %t | count 1 && +// RUN: grep "call void @_ZN1CD1Ev" %t | count 2 && +void f3() { + C().f(); +} + +// Function call operator +struct D { + D(); + ~D(); + + D operator()(); +}; + +// RUN: grep "call void @_ZN1DC1Ev" %t | count 1 && +// RUN: grep "call void @_ZN1DD1Ev" %t | count 2 && +void f4() { + D()(); +} + +// Overloaded operators +struct E { + E(); + ~E(); + E operator+(const E&); + E operator!(); +}; + +// RUN: grep "call void @_ZN1EC1Ev" %t | count 3 && +// RUN: grep "call void @_ZN1ED1Ev" %t | count 5 && +void f5() { + E() + E(); + !E(); +} + +struct F { + F(); + ~F(); + F& f(); +}; + +// RUN: grep "call void @_ZN1FC1Ev" %t | count 1 && +// RUN: grep "call void @_ZN1FD1Ev" %t | count 1 +void f6() { + F().f(); +} + diff --git a/test/CodeGenCXX/template-anonymous-union-member-initializer.cpp b/test/CodeGenCXX/template-anonymous-union-member-initializer.cpp new file mode 100644 index 0000000..f845428 --- /dev/null +++ b/test/CodeGenCXX/template-anonymous-union-member-initializer.cpp @@ -0,0 +1,10 @@ +// RUN: clang-cc -emit-llvm -o %t %s +template +class A +{ + union { void *d; }; + + A() : d(0) { } +}; + +A a0; diff --git a/test/CodeGenCXX/trivial-constructor-init.cpp b/test/CodeGenCXX/trivial-constructor-init.cpp new file mode 100644 index 0000000..183b31a --- /dev/null +++ b/test/CodeGenCXX/trivial-constructor-init.cpp @@ -0,0 +1,21 @@ +// RUN: clang-cc -S %s -o %t-64.s && +// RUN: clang-cc -S %s -o %t-32.s && +// RUN: true + +extern "C" int printf(...); + +struct S { + S() { printf("S::S\n"); } +}; + +struct A { + double x; + A() : x(), y(), s() { printf("x = %f y = %x \n", x, y); } + int *y; + S s; +}; + +A a; + +int main() { +} diff --git a/test/CodeGenCXX/virt.cpp b/test/CodeGenCXX/virt.cpp new file mode 100644 index 0000000..9ae81e5 --- /dev/null +++ b/test/CodeGenCXX/virt.cpp @@ -0,0 +1,1024 @@ +// RUN: clang-cc -triple x86_64-apple-darwin -std=c++0x -O0 -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -std=c++0x -O0 -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 -input-file=%t-32.s %s && + +// RUN: clang-cc -triple x86_64-apple-darwin -std=c++0x -O3 -S %s -o %t-O3-64.s && +// RUN: FileCheck -check-prefix LPOPT64 --input-file=%t-O3-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -std=c++0x -O3 -S %s -o %t-O3-32.s && +// RUN: FileCheck -check-prefix LPOPT32 -input-file=%t-O3-32.s %s && + +// RUN: true + +struct B { + virtual void bar1(); + virtual void bar2(); + int b; +}; +void B::bar1() { } +void B::bar2() { } + +struct C { + virtual void bee1(); + virtual void bee2(); +}; +void C::bee1() { } +void C::bee2() { } + +struct D { + virtual void boo(); +}; +void D::boo() { } + +struct D1 { + virtual void bar(); + virtual void bar2(); + virtual void bar3(); + virtual void bar4(); + virtual void bar5(); + void *d1; +}; +void D1::bar() { } + +class F : virtual public D1, virtual public D { +public: + virtual void foo(); + void *f; +}; +void F::foo() { } + +int j; +void test2() { + F f; + static int sz = (char *)(&f.f) - (char *)(&f); + j = sz; + // FIXME: These should result in a frontend constant a la fold, no run time + // initializer + // CHECK-LPOPT32: movl $4, __ZZ5test2vE2sz + // CHECK-LPOPT64: movl $8, __ZZ5test2vE2sz(%rip) +} + +static_assert(sizeof(F) == sizeof(void*)*4, "invalid vbase size"); + +struct E { + int e; +}; + +static_assert (sizeof (C) == (sizeof(void *)), "vtable pointer layout"); + +class A : public E, public B, public C { +public: + virtual void foo1(); + virtual void foo2(); + A() { } + int a; +} *ap; +void A::foo1() { } +void A::foo2() { } + +int main() { + A a; + B b; + ap->e = 1; + ap->b = 2; +} + +// CHECK-LP32: main: +// CHECK-LP32: movl $1, 8(%eax) +// CHECK-LP32: movl $2, 4(%eax) + +// CHECK-LP64: main: +// CHECK-LP64: movl $1, 12(%rax) +// CHECK-LP64: movl $2, 8(%rax) + +struct test12_A { + virtual void foo0() { } + virtual void foo(); +} *test12_pa; + +struct test12_B : public test12_A { + virtual void foo() { } +} *test12_pb; + +struct test12_D : public test12_B { +} *test12_pd; +void test12_foo() { + test12_pa->foo0(); + test12_pb->foo0(); + test12_pd->foo0(); + test12_pa->foo(); + test12_pb->foo(); + test12_pd->foo(); + test12_pa->test12_A::foo(); +} + +// CHECK-LPOPT32:__Z10test12_foov: +// CHECK-LPOPT32: movl _test12_pa, %eax +// CHECK-LPOPT32-NEXT: movl (%eax), %ecx +// CHECK-LPOPT32-NEXT: movl %eax, (%esp) +// CHECK-LPOPT32-NEXT: call *(%ecx) +// CHECK-LPOPT32-NEXT: movl _test12_pb, %eax +// CHECK-LPOPT32-NEXT: movl (%eax), %ecx +// CHECK-LPOPT32-NEXT: movl %eax, (%esp) +// CHECK-LPOPT32-NEXT: call *(%ecx) +// CHECK-LPOPT32-NEXT: movl _test12_pd, %eax +// CHECK-LPOPT32-NEXT: movl (%eax), %ecx +// CHECK-LPOPT32-NEXT: movl %eax, (%esp) +// CHECK-LPOPT32-NEXT: call *(%ecx) +// CHECK-LPOPT32-NEXT: movl _test12_pa, %eax +// CHECK-LPOPT32-NEXT: movl (%eax), %ecx +// CHECK-LPOPT32-NEXT: movl %eax, (%esp) +// CHECK-LPOPT32-NEXT: call *4(%ecx) +// CHECK-LPOPT32-NEXT: movl _test12_pb, %eax +// CHECK-LPOPT32-NEXT: movl (%eax), %ecx +// CHECK-LPOPT32-NEXT: movl %eax, (%esp) +// CHECK-LPOPT32-NEXT: call *4(%ecx) +// CHECK-LPOPT32-NEXT: movl _test12_pd, %eax +// CHECK-LPOPT32-NEXT: movl (%eax), %ecx +// CHECK-LPOPT32-NEXT: movl %eax, (%esp) +// CHECK-LPOPT32-NEXT: call *4(%ecx) +// CHECK-LPOPT32-NEXT: movl _test12_pa, %eax +// CHECK-LPOPT32-NEXT: movl %eax, (%esp) +// CHECK-LPOPT32-NEXT: call L__ZN8test12_A3fooEv$stub + +// CHECK-LPOPT64:__Z10test12_foov: +// CHECK-LPOPT64: movq _test12_pa(%rip), %rdi +// CHECK-LPOPT64-NEXT: movq (%rdi), %rax +// CHECK-LPOPT64-NEXT: call *(%rax) +// CHECK-LPOPT64-NEXT: movq _test12_pb(%rip), %rdi +// CHECK-LPOPT64-NEXT: movq (%rdi), %rax +// CHECK-LPOPT64-NEXT: call *(%rax) +// CHECK-LPOPT64-NEXT: movq _test12_pd(%rip), %rdi +// CHECK-LPOPT64-NEXT: movq (%rdi), %rax +// CHECK-LPOPT64-NEXT: call *(%rax) +// CHECK-LPOPT64-NEXT: movq _test12_pa(%rip), %rdi +// CHECK-LPOPT64-NEXT: movq (%rdi), %rax +// CHECK-LPOPT64-NEXT: call *8(%rax) +// CHECK-LPOPT64-NEXT: movq _test12_pb(%rip), %rdi +// CHECK-LPOPT64-NEXT: movq (%rdi), %rax +// CHECK-LPOPT64-NEXT: call *8(%rax) +// CHECK-LPOPT64-NEXT: movq _test12_pd(%rip), %rdi +// CHECK-LPOPT64-NEXT: movq (%rdi), %rax +// CHECK-LPOPT64-NEXT: call *8(%rax) +// CHECK-LPOPT64-NEXT: movq _test12_pa(%rip), %rdi +// CHECK-LPOPT64-NEXT: call __ZN8test12_A3fooEv + +struct test6_B2 { virtual void funcB2(); char b[1000]; }; +struct test6_B1 : virtual test6_B2 { virtual void funcB1(); }; + +struct test6_D : test6_B2, virtual test6_B1 { +}; + +// CHECK-LP32: .zerofill __DATA, __common, _d6, 2012, 4 +// CHECK-LP64: .zerofill __DATA, __common, _d6, 2024, 4 + +struct test7_B2 { virtual void funcB2(); }; +struct test7_B1 : virtual test7_B2 { virtual void funcB1(); }; + +struct test7_D : test7_B2, virtual test7_B1 { +}; + +// CHECK-LP32: .zerofill __DATA, __common, _d7, 8, 3 +// CHECK-LP64: .zerofill __DATA, __common, _d7, 16, 3 + + +struct test3_B3 { virtual void funcB3(); }; +struct test3_B2 : virtual test3_B3 { virtual void funcB2(); }; +struct test3_B1 : virtual test3_B2 { virtual void funcB1(); }; + +struct test3_D : virtual test3_B1 { + virtual void funcD() { } +}; + +// CHECK-LP32:__ZTV7test3_D: +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long __ZTI7test3_D +// CHECK-LP32-NEXT: .long __ZN8test3_B36funcB3Ev +// CHECK-LP32-NEXT: .long __ZN8test3_B26funcB2Ev +// CHECK-LP32-NEXT: .long __ZN8test3_B16funcB1Ev +// CHECK-LP32-NEXT: .long __ZN7test3_D5funcDEv + +// CHECK-LP64:__ZTV7test3_D: +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad __ZTI7test3_D +// CHECK-LP64-NEXT: .quad __ZN8test3_B36funcB3Ev +// CHECK-LP64-NEXT: .quad __ZN8test3_B26funcB2Ev +// CHECK-LP64-NEXT: .quad __ZN8test3_B16funcB1Ev +// CHECK-LP64-NEXT: .quad __ZN7test3_D5funcDEv + +struct test4_D : virtual B, virtual C { +}; + +// CHECK-LP32:__ZTV7test4_D: +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long __ZTI7test4_D +// CHECK-LP32-NEXT: .long __ZN1C4bee1Ev +// CHECK-LP32-NEXT: .long __ZN1C4bee2Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967292 +// CHECK-LP32-NEXT: .long __ZTI7test4_D +// CHECK-LP32-NEXT: .long __ZN1B4bar1Ev +// CHECK-LP32-NEXT: .long __ZN1B4bar2Ev + +// CHECK-LP64:__ZTV7test4_D: +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad __ZTI7test4_D +// CHECK-LP64-NEXT: .quad __ZN1C4bee1Ev +// CHECK-LP64-NEXT: .quad __ZN1C4bee2Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551608 +// CHECK-LP64-NEXT: .quad __ZTI7test4_D +// CHECK-LP64-NEXT: .quad __ZN1B4bar1Ev +// CHECK-LP64-NEXT: .quad __ZN1B4bar2Ev + + +struct test5_B3 { virtual void funcB3(); }; +struct test5_B2 : virtual test5_B3 { virtual void funcB2(); }; +struct test5_B1 : virtual test5_B2 { virtual void funcB1(); }; + +struct test5_B23 { virtual void funcB23(); }; +struct test5_B22 : virtual test5_B23 { virtual void funcB22(); }; +struct test5_B21 : virtual test5_B22 { virtual void funcB21(); }; + + +struct B232 { virtual void funcB232(); }; +struct B231 { virtual void funcB231(); }; + +struct test5_B33 { virtual void funcB33(); }; +struct test5_B32 : virtual test5_B33, virtual B232 { virtual void funcB32(); }; +struct test5_B31 : virtual test5_B32, virtual B231 { virtual void funcB31(); }; + +struct test5_D : virtual test5_B1, virtual test5_B21, virtual test5_B31 { + virtual void funcD() { } +}; + +// CHECK-LP32:__ZTV7test5_D: +// CHECK-LP32-NEXT: .long 16 +// CHECK-LP32-NEXT: .long 12 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .long 4 +// CHECK-LP32-NEXT: .long 4 +// CHECK-LP32-NEXT: .long 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long __ZTI7test5_D +// CHECK-LP32-NEXT: .long __ZN8test5_B36funcB3Ev +// CHECK-LP32-NEXT: .long __ZN8test5_B26funcB2Ev +// CHECK-LP32-NEXT: .long __ZN8test5_B16funcB1Ev +// CHECK-LP32-NEXT: .long __ZN7test5_D5funcDEv +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967292 +// CHECK-LP32-NEXT: .long __ZTI7test5_D +// CHECK-LP32-NEXT: .long __ZN9test5_B237funcB23Ev +// CHECK-LP32-NEXT: .long __ZN9test5_B227funcB22Ev +// CHECK-LP32-NEXT: .long __ZN9test5_B217funcB21Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32: .long 8 +// CHECK-LP32 .space 4 +// CHECK-LP32 .space 4 FIXME +// CHECK-LP32: .long 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967288 +// CHECK-LP32-NEXT: .long __ZTI7test5_D +// CHECK-LP32-NEXT: .long __ZN9test5_B337funcB33Ev +// CHECK-LP32-NEXT: .long __ZN9test5_B327funcB32Ev +// CHECK-LP32-NEXT: .long __ZN9test5_B317funcB31Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967284 +// CHECK-LP32-NEXT: .long __ZTI7test5_D +// CHECK-LP32-NEXT: .long __ZN4B2328funcB232Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967280 +// CHECK-LP32-NEXT: .long __ZTI7test5_D +// CHECK-LP32-NEXT: .long __ZN4B2318funcB231Ev + +// CHECK-LP64:__ZTV7test5_D: +// CHECK-LP64-NEXT: .quad 32 +// CHECK-LP64-NEXT: .quad 24 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .quad 8 +// CHECK-LP64-NEXT: .quad 8 +// CHECK-LP64-NEXT: .quad 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad __ZTI7test5_D +// CHECK-LP64-NEXT: .quad __ZN8test5_B36funcB3Ev +// CHECK-LP64-NEXT: .quad __ZN8test5_B26funcB2Ev +// CHECK-LP64-NEXT: .quad __ZN8test5_B16funcB1Ev +// CHECK-LP64-NEXT: .quad __ZN7test5_D5funcDEv +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551608 +// CHECK-LP64-NEXT: .quad __ZTI7test5_D +// CHECK-LP64-NEXT: .quad __ZN9test5_B237funcB23Ev +// CHECK-LP64-NEXT: .quad __ZN9test5_B227funcB22Ev +// CHECK-LP64-NEXT: .quad __ZN9test5_B217funcB21Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64: .quad 16 +// CHECK-LP64 .space 8 +// CHECK-LP64 .space 8 +// CHECK-LP64: .quad 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551600 +// CHECK-LP64-NEXT: .quad __ZTI7test5_D +// CHECK-LP64-NEXT: .quad __ZN9test5_B337funcB33Ev +// CHECK-LP64-NEXT: .quad __ZN9test5_B327funcB32Ev +// CHECK-LP64-NEXT: .quad __ZN9test5_B317funcB31Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551592 +// CHECK-LP64-NEXT: .quad __ZTI7test5_D +// CHECK-LP64-NEXT: .quad __ZN4B2328funcB232Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551584 +// CHECK-LP64-NEXT: .quad __ZTI7test5_D +// CHECK-LP64-NEXT: .quad __ZN4B2318funcB231Ev + +struct test8_B1 { + virtual void ftest8_B1() { } +}; +struct test8_B2aa { + virtual void ftest8_B2aa() { } + int i; +}; +struct test8_B2ab { + virtual void ftest8_B2ab() { } + int i; +}; +struct test8_B2a : virtual test8_B2aa, virtual test8_B2ab { + virtual void ftest8_B2a() { } +}; +struct test8_B2b { + virtual void ftest8_B2b() { } +}; +struct test8_B2 : test8_B2a, test8_B2b { + virtual void ftest8_B2() { } +}; +struct test8_B3 { + virtual void ftest8_B3() { } +}; +class test8_D : test8_B1, test8_B2, test8_B3 { +}; + +// CHECK-LP32:__ZTV7test8_D: +// CHECK-LP32-NEXT: .long 24 +// CHECK-LP32-NEXT: .long 16 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long __ZTI7test8_D +// CHECK-LP32-NEXT: .long __ZN8test8_B19ftest8_B1Ev +// CHECK-LP32-NEXT: .long 20 +// CHECK-LP32-NEXT: .long 12 +// CHECK-LP32-NEXT: .long 4294967292 +// CHECK-LP32-NEXT: .long __ZTI7test8_D +// CHECK-LP32-NEXT: .long __ZN9test8_B2a10ftest8_B2aEv +// CHECK-LP32-NEXT: .long __ZN8test8_B29ftest8_B2Ev +// CHECK-LP32-NEXT: .long 4294967288 +// CHECK-LP32-NEXT: .long __ZTI7test8_D +// CHECK-LP32-NEXT: .long __ZN9test8_B2b10ftest8_B2bEv +// CHECK-LP32-NEXT: .long 4294967284 +// CHECK-LP32-NEXT: .long __ZTI7test8_D +// CHECK-LP32-NEXT: .long __ZN8test8_B39ftest8_B3Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967280 +// CHECK-LP32-NEXT: .long __ZTI7test8_D +// CHECK-LP32-NEXT: .long __ZN10test8_B2aa11ftest8_B2aaEv +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967272 +// CHECK-LP32-NEXT: .long __ZTI7test8_D +// CHECK-LP32-NEXT: .long __ZN10test8_B2ab11ftest8_B2abEv + +// CHECK-LP64:__ZTV7test8_D: +// CHECK-LP64-NEXT: .quad 48 +// CHECK-LP64-NEXT: .quad 32 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad __ZTI7test8_D +// CHECK-LP64-NEXT: .quad __ZN8test8_B19ftest8_B1Ev +// CHECK-LP64-NEXT: .quad 40 +// CHECK-LP64-NEXT: .quad 24 +// CHECK-LP64-NEXT: .quad 18446744073709551608 +// CHECK-LP64-NEXT: .quad __ZTI7test8_D +// CHECK-LP64-NEXT: .quad __ZN9test8_B2a10ftest8_B2aEv +// CHECK-LP64-NEXT: .quad __ZN8test8_B29ftest8_B2Ev +// CHECK-LP64-NEXT: .quad 18446744073709551600 +// CHECK-LP64-NEXT: .quad __ZTI7test8_D +// CHECK-LP64-NEXT: .quad __ZN9test8_B2b10ftest8_B2bEv +// CHECK-LP64-NEXT: .quad 18446744073709551592 +// CHECK-LP64-NEXT: .quad __ZTI7test8_D +// CHECK-LP64-NEXT: .quad __ZN8test8_B39ftest8_B3Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551584 +// CHECK-LP64-NEXT: .quad __ZTI7test8_D +// CHECK-LP64-NEXT: .quad __ZN10test8_B2aa11ftest8_B2aaEv +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551568 +// CHECK-LP64-NEXT: .quad __ZTI7test8_D +// CHECK-LP64-NEXT: .quad __ZN10test8_B2ab11ftest8_B2abEv + + +struct test9_B3 { virtual void funcB3(); int i; }; +struct test9_B2 : virtual test9_B3 { virtual void funcB2(); int i; }; +struct test9_B1 : virtual test9_B2 { virtual void funcB1(); int i; }; + +struct test9_B23 { virtual void funcB23(); int i; }; +struct test9_B22 : virtual test9_B23 { virtual void funcB22(); int i; }; +struct test9_B21 : virtual test9_B22 { virtual void funcB21(); int i; }; + + +struct test9_B232 { virtual void funcB232(); int i; }; +struct test9_B231 { virtual void funcB231(); int i; }; + +struct test9_B33 { virtual void funcB33(); int i; }; +struct test9_B32 : virtual test9_B33, virtual test9_B232 { virtual void funcB32(); int i; }; +struct test9_B31 : virtual test9_B32, virtual test9_B231 { virtual void funcB31(); int i; }; + +struct test9_D : virtual test9_B1, virtual test9_B21, virtual test9_B31 { + virtual void funcD() { } +}; + +// CHECK-LP64: __ZTV7test9_D: +// CHECK-LP64-NEXT: .quad 168 +// CHECK-LP64-NEXT: .quad 152 +// CHECK-LP64-NEXT: .quad 136 +// CHECK-LP64-NEXT: .quad 120 +// CHECK-LP64-NEXT: .quad 104 +// CHECK-LP64-NEXT: .quad 88 +// CHECK-LP64-NEXT: .quad 72 +// CHECK-LP64-NEXT: .quad 56 +// CHECK-LP64-NEXT: .quad 40 +// CHECK-LP64-NEXT: .quad 24 +// CHECK-LP64-NEXT: .quad 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad __ZTI7test9_D +// CHECK-LP64-NEXT: .quad __ZN7test9_D5funcDEv +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 32 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .quad 18446744073709551608 +// CHECK-LP64-NEXT: .quad __ZTI7test9_D +// CHECK-LP64-NEXT: .quad __ZN8test9_B16funcB1Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .quad 18446744073709551592 +// CHECK-LP64-NEXT: .quad __ZTI7test9_D +// CHECK-LP64-NEXT: .quad __ZN8test9_B26funcB2Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551576 +// CHECK-LP64-NEXT: .quad __ZTI7test9_D +// CHECK-LP64-NEXT: .quad __ZN8test9_B36funcB3Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 32 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .quad 18446744073709551560 +// CHECK-LP64-NEXT: .quad __ZTI7test9_D +// CHECK-LP64-NEXT: .quad __ZN9test9_B217funcB21Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .quad 18446744073709551544 +// CHECK-LP64-NEXT: .quad __ZTI7test9_D +// CHECK-LP64-NEXT: .quad __ZN9test9_B227funcB22Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551528 +// CHECK-LP64-NEXT: .quad __ZTI7test9_D +// CHECK-LP64-NEXT: .quad __ZN9test9_B237funcB23Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 64 +// CHECK-LP64-NEXT: .quad 48 +// CHECK-LP64-NEXT: .quad 32 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .quad 18446744073709551512 +// CHECK-LP64-NEXT: .quad __ZTI7test9_D +// CHECK-LP64-NEXT: .quad __ZN9test9_B317funcB31Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 32 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .quad 18446744073709551496 +// CHECK-LP64-NEXT: .quad __ZTI7test9_D +// CHECK-LP64-NEXT: .quad __ZN9test9_B327funcB32Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551480 +// CHECK-LP64-NEXT: .quad __ZTI7test9_D +// CHECK-LP64-NEXT: .quad __ZN9test9_B337funcB33Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551464 +// CHECK-LP64-NEXT: .quad __ZTI7test9_D +// CHECK-LP64-NEXT: .quad __ZN10test9_B2328funcB232Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551448 +// CHECK-LP64-NEXT: .quad __ZTI7test9_D +// CHECK-LP64-NEXT: .quad __ZN10test9_B2318funcB231Ev + +// CHECK-LP32: __ZTV7test9_D: +// CHECK-LP32-NEXT: .long 84 +// CHECK-LP32-NEXT: .long 76 +// CHECK-LP32-NEXT: .long 68 +// CHECK-LP32-NEXT: .long 60 +// CHECK-LP32-NEXT: .long 52 +// CHECK-LP32-NEXT: .long 44 +// CHECK-LP32-NEXT: .long 36 +// CHECK-LP32-NEXT: .long 28 +// CHECK-LP32-NEXT: .long 20 +// CHECK-LP32-NEXT: .long 12 +// CHECK-LP32-NEXT: .long 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long __ZTI7test9_D +// CHECK-LP32-NEXT: .long __ZN7test9_D5funcDEv +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 16 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .long 4294967292 +// CHECK-LP32-NEXT: .long __ZTI7test9_D +// CHECK-LP32-NEXT: .long __ZN8test9_B16funcB1Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .long 4294967284 +// CHECK-LP32-NEXT: .long __ZTI7test9_D +// CHECK-LP32-NEXT: .long __ZN8test9_B26funcB2Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967276 +// CHECK-LP32-NEXT: .long __ZTI7test9_D +// CHECK-LP32-NEXT: .long __ZN8test9_B36funcB3Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 16 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .long 4294967268 +// CHECK-LP32-NEXT: .long __ZTI7test9_D +// CHECK-LP32-NEXT: .long __ZN9test9_B217funcB21Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .long 4294967260 +// CHECK-LP32-NEXT: .long __ZTI7test9_D +// CHECK-LP32-NEXT: .long __ZN9test9_B227funcB22Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967252 +// CHECK-LP32-NEXT: .long __ZTI7test9_D +// CHECK-LP32-NEXT: .long __ZN9test9_B237funcB23Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 32 +// CHECK-LP32-NEXT: .long 24 +// CHECK-LP32-NEXT: .long 16 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .long 4294967244 +// CHECK-LP32-NEXT: .long __ZTI7test9_D +// CHECK-LP32-NEXT: .long __ZN9test9_B317funcB31Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 16 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .long 4294967236 +// CHECK-LP32-NEXT: .long __ZTI7test9_D +// CHECK-LP32-NEXT: .long __ZN9test9_B327funcB32Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967228 +// CHECK-LP32-NEXT: .long __ZTI7test9_D +// CHECK-LP32-NEXT: .long __ZN9test9_B337funcB33Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967220 +// CHECK-LP32-NEXT: .long __ZTI7test9_D +// CHECK-LP32-NEXT: .long __ZN10test9_B2328funcB232Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967212 +// CHECK-LP32-NEXT: .long __ZTI7test9_D +// CHECK-LP32-NEXT: .long __ZN10test9_B2318funcB231Ev + +struct test10_O { int i; }; + +struct test10_B1 : virtual test10_O { + virtual void ftest10_B1() { } +}; + +struct test10_B2aa : virtual test10_O { + int i; +}; +struct test10_B2ab : virtual test10_O { + int i; +}; +struct test10_B2a : virtual test10_B2aa, virtual test10_B2ab,virtual test10_O { + virtual void ftest10_B2a() { } +}; +struct test10_B2b : virtual test10_O { + virtual void ftest10_B2b() { } +}; +struct test10_B2 : test10_B2a { + virtual void ftest10_B2() { } +}; +class test10_D : test10_B1, test10_B2 { + + void ftest10_B2aa() { } +}; + +// CHECK-LP64:__ZTV8test10_D: +// CHECK-LP64-NEXT: .quad 40 +// CHECK-LP64-NEXT: .quad 24 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad __ZTI8test10_D +// CHECK-LP64-NEXT: .quad __ZN9test10_B110ftest10_B1Ev +// CHECK-LP64-NEXT: .quad 32 +// CHECK-LP64-NEXT: .quad 8 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .quad 18446744073709551608 +// CHECK-LP64-NEXT: .quad __ZTI8test10_D +// CHECK-LP64-NEXT: .quad __ZN10test10_B2a11ftest10_B2aEv +// CHECK-LP64-NEXT: .quad __ZN9test10_B210ftest10_B2Ev +// CHECK-LP64-NEXT: .quad 18446744073709551608 +// CHECK-LP64-NEXT: .quad 18446744073709551592 +// CHECK-LP64-NEXT: .quad __ZTI8test10_D +// CHECK-LP64-NEXT: .quad 18446744073709551592 +// CHECK-LP64-NEXT: .quad 18446744073709551576 +// CHECK-LP64-NEXT: .quad __ZTI8test10_D + +// CHECK-LP32: __ZTV8test10_D: +// CHECK-LP32-NEXT: .long 20 +// CHECK-LP32-NEXT: .long 12 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long __ZTI8test10_D +// CHECK-LP32-NEXT: .long __ZN9test10_B110ftest10_B1Ev +// CHECK-LP32-NEXT: .long 16 +// CHECK-LP32-NEXT: .long 4 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .long 4294967292 +// CHECK-LP32-NEXT: .long __ZTI8test10_D +// CHECK-LP32-NEXT: .long __ZN10test10_B2a11ftest10_B2aEv +// CHECK-LP32-NEXT: .long __ZN9test10_B210ftest10_B2Ev +// CHECK-LP32-NEXT: .long 4294967292 +// CHECK-LP32-NEXT: .long 4294967284 +// CHECK-LP32-NEXT: .long __ZTI8test10_D +// CHECK-LP32-NEXT: .long 4294967284 +// CHECK-LP32-NEXT: .long 4294967276 +// CHECK-LP32-NEXT: .long __ZTI8test10_D + +struct test11_B { + virtual void B1() { } + virtual void D() { } + virtual void B2() { } +}; + +struct test11_D : test11_B { + virtual void D1() { } + virtual void D() { } + virtual void D2() { } +}; + +// CHECK-LP32:__ZTV8test11_D: +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long __ZTI8test11_D +// CHECK-LP32-NEXT: .long __ZN8test11_B2B1Ev +// CHECK-LP32-NEXT: .long __ZN8test11_D1DEv +// CHECK-LP32-NEXT: .long __ZN8test11_B2B2Ev +// CHECK-LP32-NEXT: .long __ZN8test11_D2D1Ev +// CHECK-LP32-NEXT: .long __ZN8test11_D2D2Ev + + +// CHECK-LP64:__ZTV8test11_D: +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad __ZTI8test11_D +// CHECK-LP64-NEXT: .quad __ZN8test11_B2B1Ev +// CHECK-LP64-NEXT: .quad __ZN8test11_D1DEv +// CHECK-LP64-NEXT: .quad __ZN8test11_B2B2Ev +// CHECK-LP64-NEXT: .quad __ZN8test11_D2D1Ev +// CHECK-LP64-NEXT: .quad __ZN8test11_D2D2Ev + +struct test13_B { + virtual void B1() { } + virtual void D() { } + virtual void Da(); + virtual void Db() { } + virtual void Dc() { } + virtual void B2() { } + int i; +}; + + +struct test13_NV1 { + virtual void fooNV1() { } + virtual void D() { } +}; + + +struct test13_B2 : /* test13_NV1, */ virtual test13_B { + virtual void B2a() { } + virtual void B2() { } + virtual void D() { } + virtual void Da(); + virtual void Dd() { } + virtual void B2b() { } + int i; +}; + + +struct test13_D : test13_NV1, virtual test13_B2 { + virtual void D1() { } + virtual void D() { } + virtual void Db() { } + virtual void Dd() { } + virtual void D2() { } + virtual void fooNV1() { } +}; + +// CHECK-LP64:__ZTV8test13_D: +// CHECK-LP64-NEXT: .quad 24 +// CHECK-LP64-NEXT: .quad 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad __ZTI8test13_D +// CHECK-LP64-NEXT: .quad __ZN8test13_D6fooNV1Ev +// CHECK-LP64-NEXT: .quad __ZN8test13_D1DEv +// CHECK-LP64-NEXT: .quad __ZN8test13_D2D1Ev +// CHECK-LP64-NEXT: .quad __ZN8test13_D2DbEv +// CHECK-LP64-NEXT: .quad __ZN8test13_D2DdEv +// CHECK-LP64-NEXT: .quad __ZN8test13_D2D2Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551608 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551608 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .quad 18446744073709551608 +// CHECK-LP64-NEXT: .quad __ZTI8test13_D +// CHECK-LP64-NEXT: .quad __ZN9test13_B23B2aEv +// CHECK-LP64-NEXT: .quad __ZN9test13_B22B2Ev +// CHECK-LP64-NEXT: .quad __ZTv0_n48_N8test13_D1DEv +// CHECK-LP64-NEXT: .quad __ZN9test13_B22DaEv +// CHECK-LP64-NEXT: .quad __ZTv0_n64_N8test13_D2DdEv +// CHECK-LP64-NEXT: .quad __ZN9test13_B23B2bEv +// CHECK-LP64-NEXT: .quad 18446744073709551600 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551592 +// CHECK-LP64-NEXT: .quad 18446744073709551600 +// CHECK-LP64-NEXT: .quad 18446744073709551592 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551592 +// CHECK-LP64-NEXT: .quad __ZTI8test13_D +// CHECK-LP64-NEXT: .quad __ZN8test13_B2B1Ev +// CHECK-LP64-NEXT: .quad __ZTv0_n32_N8test13_D1DEv +// CHECK-LP64-NEXT: .quad __ZTv0_n40_N9test13_B22DaEv +// CHECK-LP64-NEXT: .quad __ZTv0_n48_N8test13_D2DbEv +// CHECK-LP64-NEXT: .quad __ZN8test13_B2DcEv +// CHECK-LP64-NEXT: .quad __ZTv0_n64_N9test13_B22B2Ev + +// CHECK-LP32:__ZTV8test13_D: +// CHECK-LP32-NEXT: .long 12 +// CHECK-LP32-NEXT: .long 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long __ZTI8test13_D +// CHECK-LP32-NEXT: .long __ZN8test13_D6fooNV1Ev +// CHECK-LP32-NEXT: .long __ZN8test13_D1DEv +// CHECK-LP32-NEXT: .long __ZN8test13_D2D1Ev +// CHECK-LP32-NEXT: .long __ZN8test13_D2DbEv +// CHECK-LP32-NEXT: .long __ZN8test13_D2DdEv +// CHECK-LP32-NEXT: .long __ZN8test13_D2D2Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967292 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967292 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .long 4294967292 +// CHECK-LP32-NEXT: .long __ZTI8test13_D +// CHECK-LP32-NEXT: .long __ZN9test13_B23B2aEv +// CHECK-LP32-NEXT: .long __ZN9test13_B22B2Ev +// CHECK-LP32-NEXT: .long __ZTv0_n24_N8test13_D1DEv +// CHECK-LP32-NEXT: .long __ZN9test13_B22DaEv +// CHECK-LP32-NEXT: .long __ZTv0_n32_N8test13_D2DdEv +// CHECK-LP32-NEXT: .long __ZN9test13_B23B2bEv +// CHECK-LP32-NEXT: .long 4294967288 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967284 +// CHECK-LP32-NEXT: .long 4294967288 +// CHECK-LP32-NEXT: .long 4294967284 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967284 +// CHECK-LP32-NEXT: .long __ZTI8test13_D +// CHECK-LP32-NEXT: .long __ZN8test13_B2B1Ev +// CHECK-LP32-NEXT: .long __ZTv0_n16_N8test13_D1DEv +// CHECK-LP32-NEXT: .long __ZTv0_n20_N9test13_B22DaEv +// CHECK-LP32-NEXT: .long __ZTv0_n24_N8test13_D2DbEv +// CHECK-LP32-NEXT: .long __ZN8test13_B2DcEv +// CHECK-LP32-NEXT: .long __ZTv0_n32_N9test13_B22B2Ev + + +class test14 { +public: + virtual void initWithInt(int a); + static test14 *withInt(int a); +}; + +void test14::initWithInt(int a) { } + +test14 *test14::withInt(int a) { + test14 *me = new test14; + me->initWithInt(a); + return me; +} + + +struct test15_B { + virtual test15_B *foo1() { return 0; } + virtual test15_B *foo2() { return 0; } + virtual test15_B *foo3() { return 0; } + int i; +}; + +struct test15_NV1 { + virtual void fooNV1() { } + int i; +}; + +struct test15_B2 : test15_NV1, virtual test15_B { + virtual test15_B2 *foo1() { return 0; } + virtual test15_B2 *foo2() { return 0; } + int i; +}; + +struct test15_D : test15_NV1, virtual test15_B2 { + virtual test15_D *foo1() { return 0; } +}; + +// CHECK-LP64:__ZTV8test15_D: +// CHECK-LP64-NEXT: .quad 32 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad __ZTI8test15_D +// CHECK-LP64-NEXT: .quad __ZN10test15_NV16fooNV1Ev +// CHECK-LP64-NEXT: .quad __ZN8test15_D4foo1Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551600 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .quad 18446744073709551600 +// CHECK-LP64-NEXT: .quad __ZTI8test15_D +// CHECK-LP64-NEXT: .quad __ZN10test15_NV16fooNV1Ev +// CHECK-LP64-NEXT: .quad __ZTcv0_n40_v0_n24_N8test15_D4foo1Ev +// CHECK-LP64-NEXT: .quad __ZN9test15_B24foo2Ev +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551600 +// CHECK-LP64-NEXT: .quad 18446744073709551584 +// CHECK-LP64-NEXT: .quad 18446744073709551584 +// CHECK-LP64-NEXT: .quad __ZTI8test15_D +// CHECK-LP64-NEXT: .quad __ZTcv0_n24_v0_n32_N8test15_D4foo1Ev +// CHECK-LP64-NEXT: .quad __ZTcv0_n32_v0_n24_N9test15_B24foo2Ev +// CHECK-LP64-NEXT: .quad __ZN8test15_B4foo3Ev + +// CHECK-LP32:__ZTV8test15_D: +// CHECK-LP32-NEXT: .long 20 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long __ZTI8test15_D +// CHECK-LP32-NEXT: .long __ZN10test15_NV16fooNV1Ev +// CHECK-LP32-NEXT: .long __ZN8test15_D4foo1Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967288 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 12 +// CHECK-LP32-NEXT: .long 4294967288 +// CHECK-LP32-NEXT: .long __ZTI8test15_D +// CHECK-LP32-NEXT: .long __ZN10test15_NV16fooNV1Ev +// CHECK-LP32-NEXT: .long __ZTcv0_n20_v0_n12_N8test15_D4foo1Ev +// CHECK-LP32-NEXT: .long __ZN9test15_B24foo2Ev +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967284 +// CHECK-LP32-NEXT: .long 4294967276 +// CHECK-LP32-NEXT: .long 4294967276 +// CHECK-LP32-NEXT: .long __ZTI8test15_D +// CHECK-LP32-NEXT: .long __ZTcv0_n12_v0_n16_N8test15_D4foo1Ev +// CHECK-LP32-NEXT: .long __ZTcv0_n16_v0_n12_N9test15_B24foo2Ev +// CHECK-LP32-NEXT: .long __ZN8test15_B4foo3Ev + + + +// CHECK-LP64: __ZTV1B: +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad __ZTI1B +// CHECK-LP64-NEXT: .quad __ZN1B4bar1Ev +// CHECK-LP64-NEXT: .quad __ZN1B4bar2Ev + +// CHECK-LP32: __ZTV1B: +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long __ZTI1B +// CHECK-LP32-NEXT: .long __ZN1B4bar1Ev +// CHECK-LP32-NEXT: .long __ZN1B4bar2Ev + +// CHECK-LP64: __ZTV1A: +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad __ZTI1A +// CHECK-LP64-NEXT: .quad __ZN1B4bar1Ev +// CHECK-LP64-NEXT: .quad __ZN1B4bar2Ev +// CHECK-LP64-NEXT: .quad __ZN1A4foo1Ev +// CHECK-LP64-NEXT: .quad __ZN1A4foo2Ev +// CHECK-LP64-NEXT: .quad 18446744073709551600 +// CHECK-LP64-NEXT: .quad __ZTI1A +// CHECK-LP64-NEXT: .quad __ZN1C4bee1Ev +// CHECK-LP64-NEXT: .quad __ZN1C4bee2Ev + +// CHECK-LP32: __ZTV1A: +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long __ZTI1A +// CHECK-LP32-NEXT: .long __ZN1B4bar1Ev +// CHECK-LP32-NEXT: .long __ZN1B4bar2Ev +// CHECK-LP32-NEXT: .long __ZN1A4foo1Ev +// CHECK-LP32-NEXT: .long __ZN1A4foo2Ev +// CHECK-LP32-NEXT: .long 4294967284 +// CHECK-LP32-NEXT: .long __ZTI1A +// CHECK-LP32-NEXT: .long __ZN1C4bee1Ev +// CHECK-LP32-NEXT: .long __ZN1C4bee2Ev + +// CHECK-LP32:__ZTV1F: +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 8 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long __ZTI1F +// CHECK-LP32-NEXT: .long __ZN1D3booEv +// CHECK-LP32-NEXT: .long __ZN1F3fooEv +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .space 4 +// CHECK-LP32-NEXT: .long 4294967288 +// CHECK-LP32-NEXT: .long __ZTI1F +// CHECK-LP32-NEXT: .long __ZN2D13barEv +// CHECK-LP32-NEXT: .long __ZN2D14bar2Ev +// CHECK-LP32-NEXT: .long __ZN2D14bar3Ev +// CHECK-LP32-NEXT: .long __ZN2D14bar4Ev +// CHECK-LP32-NEXT: .long __ZN2D14bar5Ev + +// CHECK-LP64: __ZTV1F: +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 16 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad __ZTI1F +// CHECK-LP64-NEXT: .quad __ZN1D3booEv +// CHECK-LP64-NEXT: .quad __ZN1F3fooEv +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .space 8 +// CHECK-LP64-NEXT: .quad 18446744073709551600 +// CHECK-LP64-NEXT: .quad __ZTI1F +// CHECK-LP64-NEXT: .quad __ZN2D13barEv +// CHECK-LP64-NEXT: .quad __ZN2D14bar2Ev +// CHECK-LP64-NEXT: .quad __ZN2D14bar3Ev +// CHECK-LP64-NEXT: .quad __ZN2D14bar4Ev +// CHECK-LP64-NEXT: .quad __ZN2D14bar5Ev + +test15_D d15; +test13_D d13; +test11_D d11; +test10_D d10; +test9_D d9; +test8_D d8; + +test5_D d5; +test4_D d4; +test3_D d3; + +test6_D d6; +test7_D d7; diff --git a/test/CodeGenCXX/virtual-base-cast.cpp b/test/CodeGenCXX/virtual-base-cast.cpp new file mode 100644 index 0000000..a825120 --- /dev/null +++ b/test/CodeGenCXX/virtual-base-cast.cpp @@ -0,0 +1,9 @@ +// RUN: clang-cc -emit-llvm-only %s + +struct A { virtual ~A(); }; +struct B : A { virtual ~B(); }; +struct C : virtual B { virtual ~C(); }; + +void f(C *c) { + A* a = c; +} diff --git a/test/CodeGenCXX/virtual-function-calls.cpp b/test/CodeGenCXX/virtual-function-calls.cpp new file mode 100644 index 0000000..ca5acba --- /dev/null +++ b/test/CodeGenCXX/virtual-function-calls.cpp @@ -0,0 +1,11 @@ +// RUN: clang-cc %s -emit-llvm -o - | FileCheck %s + +// PR5021 +struct A { + virtual void f(char); +}; + +void f(A *a) { + // CHECK: call void % + a->f('c'); +} diff --git a/test/CodeGenCXX/vtable-cast-crash.cpp b/test/CodeGenCXX/vtable-cast-crash.cpp new file mode 100644 index 0000000..a91d979 --- /dev/null +++ b/test/CodeGenCXX/vtable-cast-crash.cpp @@ -0,0 +1,21 @@ +// RUN: clang-cc -emit-llvm-only %s +struct A +{ +A(); +virtual ~A(); +}; + +struct B: A +{ + B(); + ~B(); +}; + +B::B() +{ +} + +B::~B() +{ +} + diff --git a/test/CodeGenCXX/x86_64-arguments.cpp b/test/CodeGenCXX/x86_64-arguments.cpp new file mode 100644 index 0000000..426c867 --- /dev/null +++ b/test/CodeGenCXX/x86_64-arguments.cpp @@ -0,0 +1,10 @@ +// RUN: clang-cc -triple x86_64-unknown-unknown -emit-llvm -o %t %s && +struct A { ~A(); }; + +// RUN: grep 'define void @_Z2f11A(.struct.A\* .a)' %t && +void f1(A a) { } + +// RUN: grep 'define void @_Z2f2v(.struct.A\* noalias sret .agg.result)' %t && +A f2() { return A(); } + +// RUN: true diff --git a/test/CodeGenObjC/PR4541.m b/test/CodeGenObjC/PR4541.m new file mode 100644 index 0000000..9a65116 --- /dev/null +++ b/test/CodeGenObjC/PR4541.m @@ -0,0 +1,19 @@ +// RUN: clang-cc -o %t -w -g %s + + +@class NSString; +@interface NSAttributedString +- (NSString *)string; +@end +@interface NSMutableAttributedString : NSAttributedString +@end +@class NSImage; +@implementation CYObjectsController ++ (void)initialize { +} ++ (NSAttributedString *)attributedStringWithString:(id)string image:(NSImage *)image { + NSMutableAttributedString *attrStr; +} +@end + + diff --git a/test/CodeGenObjC/PR4894-recursive-debug-crash.m b/test/CodeGenObjC/PR4894-recursive-debug-crash.m new file mode 100644 index 0000000..c5f901c --- /dev/null +++ b/test/CodeGenObjC/PR4894-recursive-debug-crash.m @@ -0,0 +1,40 @@ +// RUN: clang-cc -triple i386-apple-darwin9 -g -emit-llvm %s -o - | FileCheck %s +// PR4894 +// +// This test is actually just making sure we can generate the debug info for the +// return type from im0 without crashing. +// XFAIL + +@interface I0 { + I0 *_iv0; +} +@end +@protocol P0 @end + +@interface I1 @end +@implementation I1 +- (I0 *) im0 { +// CHECK: @"\01-[I1 im0]" +// CHECK: llvm.dbg.func.start + return 0; +} +@end + +// FIXME: This was another PR4894 test case, which is crashing somewhere +// else. PR5025. +#if 0 +typedef const struct objc_selector { + void *sel_id; + const char *sel_types; +} *SEL; + +@interface I2 ++(id) dictionary; +@end + +@implementation I3; ++(void) initialize { + I2 *a0 = [I2 dictionary]; +} +@end +#endif diff --git a/test/CodeGenObjC/constant-strings.m b/test/CodeGenObjC/constant-strings.m index d4fefd9..82cd916 100644 --- a/test/CodeGenObjC/constant-strings.m +++ b/test/CodeGenObjC/constant-strings.m @@ -1,4 +1,6 @@ -// RUN: clang-cc -fnext-runtime -emit-llvm -o %t %s +// RUN: clang-cc -fnext-runtime -emit-llvm -o %t %s && +// RUN: clang-cc -fgnu-runtime -emit-llvm -o %t %s && grep NXConstantString %t | count 1 && +// RUN: clang-cc -fgnu-runtime -fconstant-string-class=NSConstantString -emit-llvm -o %t %s && grep NSConstantString %t | count 1 id a = @"Hello World!"; diff --git a/test/CodeGenObjC/debug-info-linkagename.m b/test/CodeGenObjC/debug-info-linkagename.m new file mode 100644 index 0000000..7305689 --- /dev/null +++ b/test/CodeGenObjC/debug-info-linkagename.m @@ -0,0 +1,17 @@ +// RUN: clang-cc -g -S -o %t %s && +// RUN: not grep 001 %t + +@interface F +-(int) bar; +@end + +@implementation F +-(int) bar { + return 42; +} +@end + +extern int f(F *fn) { + return [fn bar]; +} + diff --git a/test/CodeGenObjC/for-in.m b/test/CodeGenObjC/for-in.m new file mode 100644 index 0000000..434ff79 --- /dev/null +++ b/test/CodeGenObjC/for-in.m @@ -0,0 +1,44 @@ +// RUN: clang-cc -emit-llvm %s -o %t + +void p(const char*, ...); + +@interface NSArray ++(NSArray*) arrayWithObjects: (id) first, ...; +-(unsigned) count; +@end +@interface NSString +-(const char*) cString; +@end + +#define S(n) @#n +#define L1(n) S(n+0),S(n+1) +#define L2(n) L1(n+0),L1(n+2) +#define L3(n) L2(n+0),L2(n+4) +#define L4(n) L3(n+0),L3(n+8) +#define L5(n) L4(n+0),L4(n+16) +#define L6(n) L5(n+0),L5(n+32) + +void t0() { + NSArray *array = [NSArray arrayWithObjects: L1(0), (void*)0]; + + p("array.length: %d\n", [array count]); + unsigned index = 0; + for (NSString *i in array) { + p("element %d: %s\n", index++, [i cString]); + } +} + +void t1() { + NSArray *array = [NSArray arrayWithObjects: L6(0), (void*)0]; + + p("array.length: %d\n", [array count]); + unsigned index = 0; + for (NSString *i in array) { + index++; + if (index == 10) + continue; + p("element %d: %s\n", index, [i cString]); + if (index == 55) + break; + } +} diff --git a/test/CodeGenObjC/ivar-layout-64-bitfields.m b/test/CodeGenObjC/ivar-layout-64-bitfields.m new file mode 100644 index 0000000..cb56118 --- /dev/null +++ b/test/CodeGenObjC/ivar-layout-64-bitfields.m @@ -0,0 +1,40 @@ +// RUN: clang-cc -triple x86_64-apple-darwin9 -fobjc-gc -emit-llvm -o %t %s +@interface I +{ + struct { + unsigned int d : 1; + } bitfield; +} +@end + +@implementation I +@end + +@interface J +{ + struct { + unsigned short _reserved : 16; + + _Bool _draggedNodesAreDeletable: 1; + _Bool _draggedOutsideOutlineView : 1; + _Bool _adapterRespondsTo_addRootPaths : 1; + _Bool _adapterRespondsTo_moveDataNodes : 1; + _Bool _adapterRespondsTo_removeRootDataNode : 1; + _Bool _adapterRespondsTo_doubleClickDataNode : 1; + _Bool _adapterRespondsTo_selectDataNode : 1; + _Bool _adapterRespondsTo_textDidEndEditing : 1; + + _Bool _adapterRespondsTo_updateAndSaveRoots : 1; + _Bool _adapterRespondsTo_askToDeleteRootNodes : 1; + _Bool _adapterRespondsTo_contextMenuForSelectedNodes : 1; + _Bool _adapterRespondsTo_pasteboardFilenamesForNodes : 1; + _Bool _adapterRespondsTo_writeItemsToPasteboard : 1; + _Bool _adapterRespondsTo_writeItemsToPasteboardXXXX : 1; + } _flags; +} +@end + +@implementation J +@end + + diff --git a/test/CodeGenObjC/ivar-layout-no-optimize.m b/test/CodeGenObjC/ivar-layout-no-optimize.m new file mode 100644 index 0000000..d7796bc --- /dev/null +++ b/test/CodeGenObjC/ivar-layout-no-optimize.m @@ -0,0 +1,18 @@ +// RUN: clang-cc -fobjc-gc -triple x86_64-apple-darwin -O0 -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: true + +@interface NSObject { + id isa; +} +@end + +@interface AllPointers : NSObject { + id foo; + void *__strong bar; NSObject *bletch;} +@end +@implementation AllPointers +@end + +// CHECK-LP64: L_OBJC_CLASS_NAME_6: +// CHECK-LP64-NEXT: .asciz "\004" diff --git a/test/CodeGenObjC/messages.m b/test/CodeGenObjC/messages.m index f9b9be6..b7f42d1 100644 --- a/test/CodeGenObjC/messages.m +++ b/test/CodeGenObjC/messages.m @@ -2,8 +2,8 @@ // RUN: grep "objc_msgSend" %t | count 6 && // RUN: clang-cc -fgnu-runtime --emit-llvm -o %t %s && // RUN: grep "objc_msg_lookup" %t | count 6 && -// RUN: clang-cc -fgnu-runtime -fobjc-sender-dependent-dispatch --emit-llvm -o %t %s && -// RUN: grep "objc_msg_lookup_sender" %t | count 6 +// RUN: clang-cc -fgnu-runtime -fobjc-nonfragile-abi --emit-llvm -o %t %s && +// RUN: grep "objc_msg_lookup_sender" %t | count 6 && // RUN: true typedef struct { diff --git a/test/CodeGenObjC/objc-assign-ivar.m b/test/CodeGenObjC/objc-assign-ivar.m new file mode 100644 index 0000000..f79faaf --- /dev/null +++ b/test/CodeGenObjC/objc-assign-ivar.m @@ -0,0 +1,53 @@ +// RUN: clang-cc -triple x86_64-apple-darwin10 -fobjc-gc -emit-llvm -o %t %s && +// RUN: grep -F '@objc_assign_ivar' %t | count 14 && +// RUN: true + +typedef struct { + id element; + id elementArray[10]; + __strong id cfElement; + __strong id cfElementArray[10]; +} struct_with_ids_t; + + +@interface NSString @end + +@interface Foo { +@public +// assignments to any/all of these fields should generate objc_assign_ivar + __strong id dict; + __strong id dictArray[3]; + id ivar; + id array[10]; + id nsobject; + NSString *stringArray[10]; + struct_with_ids_t inner; + + Foo *obj[20]; + short idx[5]; +} +@end + +// The test cases +int IvarAssigns; +void *rhs = 0; +#define ASSIGNTEST(expr, global) expr = rhs + +void testIvars() { + Foo *foo; + ASSIGNTEST(foo->ivar, IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->dict, IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->dictArray[0], IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->array[0], IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->nsobject, IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->stringArray[0], IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->inner.element, IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->inner.elementArray[0], IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->inner.cfElement, IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->inner.cfElementArray[0], IvarAssigns); // objc_assign_ivar + int counter=1; + ASSIGNTEST(foo->obj[5], IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->obj[++counter], IvarAssigns); // objc_assign_ivar + foo->idx[++counter] = 15; + ASSIGNTEST(foo->obj[foo->idx[2]], IvarAssigns); // objc_assign_ivar +} diff --git a/test/CodeGenObjC/objc-gc-aggr-assign.m b/test/CodeGenObjC/objc-gc-aggr-assign.m new file mode 100644 index 0000000..96a9fdf --- /dev/null +++ b/test/CodeGenObjC/objc-gc-aggr-assign.m @@ -0,0 +1,46 @@ +// RUN: clang-cc -fnext-runtime -fobjc-gc -emit-llvm -o %t %s && +// RUN: grep objc_memmove_collectable %t | grep call | count 3 + +static int count; + +typedef struct S { + int ii; +} SS; + +struct type_s { + SS may_recurse; + id id_val; +}; + +@interface NamedObject +{ + struct type_s type_s_ivar; +} +- (void) setSome : (struct type_s) arg; +- (struct type_s) getSome; +@property(assign) struct type_s aggre_prop; +@end + +@implementation NamedObject +- (void) setSome : (struct type_s) arg + { + type_s_ivar = arg; + } +- (struct type_s) getSome + { + return type_s_ivar; + } +@synthesize aggre_prop = type_s_ivar; +@end + +struct type_s some = {{1234}, (id)0}; + +struct type_s get(void) +{ + return some; +} + +void f(const struct type_s *in, struct type_s *out) { + *out = *in; +} + diff --git a/test/CodeGenObjC/objc-read-weak-byref.m b/test/CodeGenObjC/objc-read-weak-byref.m new file mode 100644 index 0000000..7c297be --- /dev/null +++ b/test/CodeGenObjC/objc-read-weak-byref.m @@ -0,0 +1,26 @@ +// RUN: clang-cc -fblocks -fobjc-gc -triple x86_64-apple-darwin -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -fblocks -fobjc-gc -triple i386-apple-darwin -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +@interface NSObject +- copy; +@end + +int main() { + NSObject *object = 0; + __weak __block NSObject* weak_object = object; + void (^callback) (void) = [^{ + if (weak_object) + [weak_object copy]; + } copy]; + callback(); + return 0; +} + +// CHECK-LP64: call _objc_read_weak +// CHECK-LP64: call _objc_read_weak + +// CHECK-LP32: call L_objc_read_weak +// CHECK-LP32: call L_objc_read_weak diff --git a/test/CodeGenObjC/objc2-assign-global.m b/test/CodeGenObjC/objc2-assign-global.m index ae40761..9b6b415 100644 --- a/test/CodeGenObjC/objc2-assign-global.m +++ b/test/CodeGenObjC/objc2-assign-global.m @@ -1,8 +1,81 @@ -// RUN: clang-cc -fnext-runtime -fobjc-gc -emit-llvm -o %t %s && -// RUN: grep -F '@objc_assign_global' %t | count 2 && +// RUN: clang-cc -triple x86_64-apple-darwin10 -fnext-runtime -fobjc-gc -emit-llvm -o %t %s && +// RUN: grep -F '@objc_assign_global' %t | count 26 && // RUN: true -id a; + +@class NSObject; +typedef const struct __CFDictionary * CFDictionaryRef; +typedef struct { + id element; + id elementArray[10]; + __strong CFDictionaryRef cfElement; + __strong CFDictionaryRef cfElementArray[10]; +} struct_with_ids_t; + + +// assignments to these should generate objc_assign_global +@interface A +@end + +typedef struct s0 { + A *a[4]; +} T; + +T g0; + +extern id FileExternID; +static id FileStaticID; +id GlobalId; +id GlobalArray[20]; +NSObject *GlobalObject; +NSObject *GlobalObjectArray[20]; +__strong CFDictionaryRef Gdict; +__strong CFDictionaryRef Gdictarray[10]; +struct_with_ids_t GlobalStruct; +struct_with_ids_t GlobalStructArray[10]; + +#define ASSIGNTEST(expr, global) expr = rhs +void *rhs = 0; + int main() { - a = 0; -} + static id staticGlobalId; + static id staticGlobalArray[20]; + static NSObject *staticGlobalObject; + static NSObject *staticGlobalObjectArray[20]; + static __strong CFDictionaryRef staticGdict; + static __strong CFDictionaryRef staticGdictarray[10]; + static struct_with_ids_t staticGlobalStruct; + static struct_with_ids_t staticGlobalStructArray[10]; + extern id ExID; + id localID; + + ASSIGNTEST(GlobalId, GlobalAssigns); // objc_assign_global + ASSIGNTEST(GlobalArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(GlobalObject, GlobalAssigns); // objc_assign_global + ASSIGNTEST(GlobalObjectArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(Gdict, GlobalAssigns); // objc_assign_global + ASSIGNTEST(Gdictarray[1], GlobalAssigns); // objc_assign_global + + ASSIGNTEST(GlobalStruct.element, GlobalAssigns); // objc_assign_global + ASSIGNTEST(GlobalStruct.elementArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(GlobalStruct.cfElement, GlobalAssigns); // objc_assign_global + ASSIGNTEST(GlobalStruct.cfElementArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalId, GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalObject, GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalObjectArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGdict, GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGdictarray[1], GlobalAssigns); // objc_assign_global + + ASSIGNTEST(staticGlobalStruct.element, GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalStruct.elementArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalStruct.cfElement, GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalStruct.cfElementArray[0], GlobalAssigns); // objc_assign_global + + ExID = 0; + localID = 0; + FileStaticID = 0; + FileExternID=0; + g0.a[0] = 0; + ((T*) &g0)->a[0] = 0; +} diff --git a/test/CodeGenObjC/objc2-ivar-assign.m b/test/CodeGenObjC/objc2-ivar-assign.m new file mode 100644 index 0000000..cfdf87f2 --- /dev/null +++ b/test/CodeGenObjC/objc2-ivar-assign.m @@ -0,0 +1,41 @@ +// RUN: clang-cc -triple x86_64-apple-darwin10 -fobjc-gc -emit-llvm -o %t %s && +// RUN: grep objc_assign_ivar %t | count 6 && +// RUN: true + +@interface I @end + +typedef I TI; +typedef I* TPI; + +typedef id ID; + +@interface MyClass { +} + +@property id property; +@property I* propertyI; + +@property TI* propertyTI; + +@property TPI propertyTPI; + +@property ID propertyID; +@end + +@implementation MyClass + @synthesize property=_property; + @synthesize propertyI; + @synthesize propertyTI=_propertyTI; + @synthesize propertyTPI=_propertyTPI; + @synthesize propertyID = _propertyID; +@end + +int main () { + MyClass *myObj; + myObj.property = 0; + myObj.propertyI = 0; + myObj.propertyTI = 0; + myObj.propertyTPI = 0; + myObj.propertyID = 0; + return 0; +} diff --git a/test/CodeGenObjC/objc2-new-gc-api-strongcast.m b/test/CodeGenObjC/objc2-new-gc-api-strongcast.m new file mode 100644 index 0000000..6a1aea6 --- /dev/null +++ b/test/CodeGenObjC/objc2-new-gc-api-strongcast.m @@ -0,0 +1,26 @@ +// RUN: clang-cc -triple x86_64-apple-darwin10 -fblocks -fnext-runtime -fobjc-gc -emit-llvm -o %t %s && +// RUN: grep -F '@objc_assign_strongCast' %t | count 4 && +// RUN: true + +@interface DSATextSearch @end + +DSATextSearch **_uniqueIdToIdentifierArray = ((void *)0); +void foo (int _nextId) +{ + _uniqueIdToIdentifierArray[_nextId] = 0; // objc_assign_strongCast +} + +typedef struct { + unsigned long state; + id *itemsPtr; + void (^bp)(); + unsigned long *mutationsPtr; + unsigned long extra[5]; +} NSFastEnumerationState; + +void foo1 (NSFastEnumerationState * state) +{ + state->itemsPtr = 0; + state->bp = ^{}; +} + diff --git a/test/CodeGenObjC/objc2-weak-assign.m b/test/CodeGenObjC/objc2-weak-assign.m index a3740b2..635ca38 100644 --- a/test/CodeGenObjC/objc2-weak-assign.m +++ b/test/CodeGenObjC/objc2-weak-assign.m @@ -9,6 +9,10 @@ __weak id* a1[20]; id* __weak a2[30]; id** __weak a3[40]; +void foo (__weak id *param) { + *param = 0; +} + int main() { *x = 0; diff --git a/test/CodeGenObjC/objc2-weak-ivar-debug.m b/test/CodeGenObjC/objc2-weak-ivar-debug.m new file mode 100644 index 0000000..24a7757 --- /dev/null +++ b/test/CodeGenObjC/objc2-weak-ivar-debug.m @@ -0,0 +1,15 @@ +// RUN: clang-cc -triple x86_64-apple-darwin9 -fobjc-gc -g -emit-llvm -o - %s && +// RUN: clang-cc -triple i386-apple-darwin9 -fobjc-gc -g -emit-llvm -o - %s + +// rdar://7252252 +@interface Loop { +@public + __weak Loop *_loop; +} +@end + +@implementation Loop @end + +void loop(Loop *L) { + L->_loop = 0; +} diff --git a/test/CodeGenObjC/objc2-write-barrier-2.m b/test/CodeGenObjC/objc2-write-barrier-2.m new file mode 100644 index 0000000..c47224f --- /dev/null +++ b/test/CodeGenObjC/objc2-write-barrier-2.m @@ -0,0 +1,80 @@ +// RUN: clang-cc -triple x86_64-apple-darwin10 -fnext-runtime -fobjc-gc -emit-llvm -o %t %s && +// RUN: grep -F '@objc_assign_global' %t | count 7 && +// RUN: grep -F '@objc_assign_ivar' %t | count 5 && +// RUN: grep -F '@objc_assign_strongCast' %t | count 8 && +// RUN: true + +extern id **somefunc(void); +extern id *somefunc2(void); + + +// Globals + +id W, *X, **Y; + +void func(id a, id *b, id **c) { + static id w, *x, **y; + W = a; + w = a; + X = b; + x = b; + Y = c; + y = c; +} + +// Instances + +@interface something { + id w, *x, **y; +} +@end + +@implementation something +- (void)amethod { + id badIdea = *somefunc2(); + w = badIdea; + x = &badIdea; + y = &x; +} +@end + +typedef struct { + int junk; + id alfred; +} AStruct; + +void funct2(AStruct *aptr) { + id **ppptr = somefunc(); + aptr->alfred = 0; + **ppptr = aptr->alfred; + *ppptr = somefunc2(); +} + +typedef const struct __CFString * CFStringRef; +@interface DSATextSearch { +__strong CFStringRef *_documentNames; + struct { + id *innerNames; + struct { + id *nestedDeeperNames; + struct I { + id *is1; + id is2[5]; + } arrI [3]; + } inner_most; + } inner; + +} +- filter; +@end +@implementation DSATextSearch +- filter { + int filteredPos = 0; + _documentNames[filteredPos] = 0; // storing into an element of array ivar. objc_assign_strongCast is needed. + inner.innerNames[filteredPos] = 0; + inner.inner_most.nestedDeeperNames[filteredPos] = 0; + inner.inner_most.arrI[3].is1[5] = 0; + inner.inner_most.arrI[3].is2[5] = 0; +} +@end + diff --git a/test/CodeGenObjC/objc2-write-barrier-3.m b/test/CodeGenObjC/objc2-write-barrier-3.m new file mode 100644 index 0000000..2fb416b --- /dev/null +++ b/test/CodeGenObjC/objc2-write-barrier-3.m @@ -0,0 +1,47 @@ +// RUN: clang-cc -triple x86_64-apple-darwin10 -fobjc-gc -emit-llvm -o %t %s && +// RUN: grep objc_assign_ivar %t | count 3 && +// RUN: grep objc_assign_strongCast %t | count 6 && +// RUN: true + +struct Slice { + void *__strong * items; +}; + +typedef struct Slice Slice; + +@interface ISlice { +@public + void *__strong * IvarItem; +} +@end + +typedef void (^observer_block_t)(id object); +@interface Observer { +@public + observer_block_t block; +} +@end + + +void foo (int i) { + // storing into an array of strong pointer types. + void *__strong* items; + items[i] = 0; + + // storing indirectly into an array of strong pointer types. + void *__strong* *vitems; + *vitems[i] = 0; + + Slice *slice; + slice->items = 0; + // storing into a struct element of an array of strong pointer types. + slice->items[i] = 0; + + ISlice *islice; + islice->IvarItem = 0; + // Storing into an ivar of an array of strong pointer types. + islice->IvarItem[i] = (void*)0; + + Observer *observer; + observer->block = 0; +} diff --git a/test/CodeGenObjC/objc2-write-barrier-4.m b/test/CodeGenObjC/objc2-write-barrier-4.m new file mode 100644 index 0000000..f96a233 --- /dev/null +++ b/test/CodeGenObjC/objc2-write-barrier-4.m @@ -0,0 +1,28 @@ +// RUN: clang-cc -triple x86_64-apple-darwin10 -fobjc-gc -emit-llvm -o %t %s && +// RUN: grep objc_assign_global %t | count 3 && +// RUN: grep objc_assign_strongCast %t | count 2 && +// RUN: true + +@interface A +@end + +typedef struct s0 { + A *a[4]; +} T; + +T g0; + +void f0(id x) { + g0.a[0] = x; +} + +void f1(id x) { + ((T*) &g0)->a[0] = x; +} + +void f2(unsigned idx) +{ + id *keys; + keys[idx] = 0; +} + diff --git a/test/CodeGenObjC/objc2-write-barrier-5.m b/test/CodeGenObjC/objc2-write-barrier-5.m new file mode 100644 index 0000000..5b8f02c --- /dev/null +++ b/test/CodeGenObjC/objc2-write-barrier-5.m @@ -0,0 +1,27 @@ +// RUN: clang-cc -triple x86_64-apple-darwin10 -fobjc-gc -emit-llvm -o %t %s && +// RUN: grep objc_assign_ivar %t | count 0 && +// RUN: grep objc_assign_strongCast %t | count 5 && +// RUN: true + +@interface TestUnarchiver +{ + void *allUnarchivedObjects; +} +@end + +@implementation TestUnarchiver + +struct unarchive_list { + int ifield; + id *list; +}; + +- (id)init { + (*((struct unarchive_list *)allUnarchivedObjects)).list = 0; + ((struct unarchive_list *)allUnarchivedObjects)->list = 0; + (**((struct unarchive_list **)allUnarchivedObjects)).list = 0; + (*((struct unarchive_list **)allUnarchivedObjects))->list = 0; + return 0; +} + +@end diff --git a/test/CodeGenObjC/objc2-write-barrier.m b/test/CodeGenObjC/objc2-write-barrier.m new file mode 100644 index 0000000..53fa10a --- /dev/null +++ b/test/CodeGenObjC/objc2-write-barrier.m @@ -0,0 +1,114 @@ +// RUN: clang-cc -triple x86_64-apple-darwin10 -fnext-runtime -fobjc-gc -emit-llvm -o %t %s && +// RUN: grep -F '@objc_assign_global' %t | count 21 && +// RUN: grep -F '@objc_assign_ivar' %t | count 11 && +// RUN: true + + +typedef const struct __CFDictionary * CFDictionaryRef; + +// callouts to these are generated with cc -fobjc-gc + +int GlobalAssigns; +int IvarAssigns; +int StrongCastAssigns; + + +// The test case elements; +@class NSObject; +@class NSString; + +typedef struct { + id element; + id elementArray[10]; + __strong CFDictionaryRef cfElement; + __strong CFDictionaryRef cfElementArray[10]; +} struct_with_ids_t; + +@interface Foo { +@public +// assignments to any/all of these fields should generate objc_assign_ivar + __strong CFDictionaryRef dict; + __strong CFDictionaryRef dictArray[3]; + id ivar; + id array[10]; + NSObject *nsobject; + NSString *stringArray[10]; + struct_with_ids_t inner; +} + +@end + +// assignments to these should generate objc_assign_global +id GlobalId; +id GlobalArray[20]; +NSObject *GlobalObject; +NSObject *GlobalObjectArray[20]; +__strong CFDictionaryRef Gdict; +__strong CFDictionaryRef Gdictarray[10]; +struct_with_ids_t GlobalStruct; +struct_with_ids_t GlobalStructArray[10]; + + +// The test cases +void *rhs = 0; + +#define ASSIGNTEST(expr, global) expr = rhs + +int testGlobals() { + // Everything in this function generates assign_global intercepts + int counter = 0; + + static id staticGlobalId; + static id staticGlobalArray[20]; + static NSObject *staticGlobalObject; + static NSObject *staticGlobalObjectArray[20]; + static __strong CFDictionaryRef staticGdict; + static __strong CFDictionaryRef staticGdictarray[10]; + static struct_with_ids_t staticGlobalStruct; + static struct_with_ids_t staticGlobalStructArray[10]; + + ASSIGNTEST(GlobalId, GlobalAssigns); // objc_assign_global + ASSIGNTEST(GlobalArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(GlobalObject, GlobalAssigns); // objc_assign_global + ASSIGNTEST(GlobalObjectArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(Gdict, GlobalAssigns); // objc_assign_global + ASSIGNTEST(Gdictarray[1], GlobalAssigns); // objc_assign_global + + ASSIGNTEST(GlobalStruct.element, GlobalAssigns); // objc_assign_global + ASSIGNTEST(GlobalStruct.elementArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(GlobalStruct.cfElement, GlobalAssigns); // objc_assign_global + ASSIGNTEST(GlobalStruct.cfElementArray[0], GlobalAssigns); // objc_assign_global + + ASSIGNTEST(staticGlobalId, GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalObject, GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalObjectArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGdict, GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGdictarray[1], GlobalAssigns); // objc_assign_global + + ASSIGNTEST(staticGlobalStruct.element, GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalStruct.elementArray[0], GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalStruct.cfElement, GlobalAssigns); // objc_assign_global + ASSIGNTEST(staticGlobalStruct.cfElementArray[0], GlobalAssigns); // objc_assign_global + + return counter; +} + + +int testIvars() { + Foo *foo; + int counter = 0; + + ASSIGNTEST(foo->ivar, IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->dict, IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->dictArray[0], IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->array[0], IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->nsobject, IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->stringArray[0], IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->inner.element, IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->inner.elementArray[0], IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->inner.cfElement, IvarAssigns); // objc_assign_ivar + ASSIGNTEST(foo->inner.cfElementArray[0], IvarAssigns); // objc_assign_ivar + + return counter; +} diff --git a/test/CodeGenObjC/object-incr-decr-1.m b/test/CodeGenObjC/object-incr-decr-1.m new file mode 100644 index 0000000..53311f7 --- /dev/null +++ b/test/CodeGenObjC/object-incr-decr-1.m @@ -0,0 +1,19 @@ +// RUN: clang-cc -triple i386-apple-darwin9 -fnext-runtime -emit-llvm %s -o %t + +@interface Foo +{ + double d1,d3,d4; +} +@end + +Foo* foo() +{ + Foo *f; + + // Both of these crash clang nicely + ++f; + --f; + f--; + f++; + return f; +} diff --git a/test/CodeGenObjC/overloadable.m b/test/CodeGenObjC/overloadable.m index 972dc4e..7e9cc3d 100644 --- a/test/CodeGenObjC/overloadable.m +++ b/test/CodeGenObjC/overloadable.m @@ -4,7 +4,7 @@ @class C; // RUN: grep _Z1fP11objc_object %t | count 1 && -void __attribute__((overloadable)) f(C *c) { } +void __attribute__((overloadable)) f(id c) { } // RUN: grep _Z1fP1C %t | count 1 -void __attribute__((overloadable)) f(id c) { } +void __attribute__((overloadable)) f(C *c) { } diff --git a/test/CodeGenObjC/predefined-expr.m b/test/CodeGenObjC/predefined-expr.m new file mode 100644 index 0000000..b27bb34 --- /dev/null +++ b/test/CodeGenObjC/predefined-expr.m @@ -0,0 +1,90 @@ +// RUN: clang-cc -triple i386-apple-darwin9 %s -emit-llvm -o - | FileCheck %s + +// CHECK: @"__func__.-[Foo instanceTest1]" = private constant [21 x i8] c"-[Foo instanceTest1]\00" +// CHECK: @"__func__.-[Foo instanceTest2:]" = private constant [22 x i8] c"-[Foo instanceTest2:]\00" +// CHECK: @"__func__.-[Foo instanceTest3:withB:]" = private constant [28 x i8] c"-[Foo instanceTest3:withB:]\00" +// CHECK: @"__func__.-[Foo instanceTest4]" = private constant [21 x i8] c"-[Foo instanceTest4]\00" +// CHECK: @"__func__.+[Foo classTest1]" = private constant [18 x i8] c"+[Foo classTest1]\00" +// CHECK: @"__func__.+[Foo classTest2:]" = private constant [19 x i8] c"+[Foo classTest2:]\00" +// CHECK: @"__func__.+[Foo classTest3:withB:]" = private constant [25 x i8] c"+[Foo classTest3:withB:]\00" +// CHECK: @"__func__.+[Foo classTest4]" = private constant [18 x i8] c"+[Foo classTest4]\00" +// CHECK: @"__func__.-[Foo(Category) instanceTestWithCategory]" = private constant [42 x i8] c"-[Foo(Category) instanceTestWithCategory]\00" +// CHECK: @"__func__.+[Foo(Category) classTestWithCategory]" = private constant [39 x i8] c"+[Foo(Category) classTestWithCategory]\00" + +int printf(const char * _Format, ...); + +@interface Foo +@end + +@implementation Foo + +- (void)instanceTest1 { + printf("__func__: %s\n", __func__); + printf("__FUNCTION__: %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__: %s\n\n", __PRETTY_FUNCTION__); +} + +- (void)instanceTest2:(int)i { + printf("__func__: %s\n", __func__); + printf("__FUNCTION__: %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__: %s\n\n", __PRETTY_FUNCTION__); +} + +- (void)instanceTest3:(int)a withB:(double)b { + printf("__func__: %s\n", __func__); + printf("__FUNCTION__: %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__: %s\n\n", __PRETTY_FUNCTION__); +} + +- (int)instanceTest4 { + printf("__func__: %s\n", __func__); + printf("__FUNCTION__: %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__: %s\n\n", __PRETTY_FUNCTION__); + return 0; +} + ++ (void)classTest1 { + printf("__func__: %s\n", __func__); + printf("__FUNCTION__: %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__: %s\n\n", __PRETTY_FUNCTION__); +} + ++ (void)classTest2:(int)i { + printf("__func__: %s\n", __func__); + printf("__FUNCTION__: %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__: %s\n\n", __PRETTY_FUNCTION__); +} + ++ (void)classTest3:(int)a withB:(double)b { + printf("__func__: %s\n", __func__); + printf("__FUNCTION__: %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__: %s\n\n", __PRETTY_FUNCTION__); +} + ++ (int)classTest4 { + printf("__func__: %s\n", __func__); + printf("__FUNCTION__: %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__: %s\n\n", __PRETTY_FUNCTION__); + return 0; +} + +@end + +@interface Foo (Category) +@end + +@implementation Foo (Category) + +- (void)instanceTestWithCategory { + printf("__func__: %s\n", __func__); + printf("__FUNCTION__: %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__: %s\n\n", __PRETTY_FUNCTION__); +} + ++ (void)classTestWithCategory { + printf("__func__: %s\n", __func__); + printf("__FUNCTION__: %s\n", __FUNCTION__); + printf("__PRETTY_FUNCTION__: %s\n\n", __PRETTY_FUNCTION__); +} + +@end diff --git a/test/CodeGenObjC/property-agrr-getter.m b/test/CodeGenObjC/property-agrr-getter.m index 0a1df12..4620579 100644 --- a/test/CodeGenObjC/property-agrr-getter.m +++ b/test/CodeGenObjC/property-agrr-getter.m @@ -9,9 +9,30 @@ typedef struct { @end @implementation A --(s0) f0{} +-(s0) f0{ while (1) {} } - (unsigned) bar { return self.f0.f0; } @end + +typedef struct _NSSize { + float width; + float height; +} NSSize; + + +@interface AnObject +{ + NSSize size; +} + +@property NSSize size; + +@end + +float f () +{ + AnObject* obj; + return (obj.size).width; +} diff --git a/test/CodeGenObjC/property-setter-attr.m b/test/CodeGenObjC/property-setter-attr.m index 3903924..5f0edf8 100644 --- a/test/CodeGenObjC/property-setter-attr.m +++ b/test/CodeGenObjC/property-setter-attr.m @@ -1,4 +1,4 @@ -// RUN: clang-cc -emit-llvm -triple=i686-apple-darwin8 -o %t %s +// RUN: clang-cc -emit-llvm -triple=i686-apple-darwin8 -o %t %s && // RUN: grep -e "SiSetOtherThings:" %t @interface A diff --git a/test/CodeGenObjC/protocol-in-extended-class.m b/test/CodeGenObjC/protocol-in-extended-class.m new file mode 100644 index 0000000..87bda46 --- /dev/null +++ b/test/CodeGenObjC/protocol-in-extended-class.m @@ -0,0 +1,29 @@ +// RUN: clang-cc -triple x86_64-apple-darwin10 -S %s -o %t-64.s && +// RUN: FileCheck -check-prefix LP64 --input-file=%t-64.s %s && +// RUN: clang-cc -triple i386-apple-darwin -S %s -o %t-32.s && +// RUN: FileCheck -check-prefix LP32 --input-file=%t-32.s %s && +// RUN: true + +@protocol MyProtocol +@end + +@protocol ExtendedProtocol +@end + +@interface ItDoesntWork { +} +-(void) Meth; +@end + +@interface ItDoesntWork() +@end + +@implementation ItDoesntWork +-(void) Meth { + ItDoesntWork *p = 0; + } +@end + +// CHECK-LP64: l_OBJC_PROTOCOL_$_ExtendedProtocol: + +// CHECK-LP32: L_OBJC_PROTOCOL_ExtendedProtocol: diff --git a/test/CodeGenObjC/protocols-lazy.m b/test/CodeGenObjC/protocols-lazy.m index e91cc0a..a8f7902 100644 --- a/test/CodeGenObjC/protocols-lazy.m +++ b/test/CodeGenObjC/protocols-lazy.m @@ -26,7 +26,7 @@ void f1() { id x = @protocol(P3); } // RUN: grep OBJC_PROTOCOL_INSTANCE_METHODS_P4 %t | count 3 && @protocol P4 -im1; @end @interface I0 @end -@implementation I0 -im1 {}; @end +@implementation I0 -im1 { return 0; }; @end // Definition following forward reference. // RUN: grep OBJC_PROTOCOL_P5 %t | count 3 && @@ -42,7 +42,7 @@ void f2() { id x = @protocol(P5); } // This generates a forward // RUN: grep OBJC_PROTOCOL_INSTANCE_METHODS_P6 %t | count 3 && @protocol P6 -im1; @end @interface I1 @end -@implementation I1 -im1 {}; @end +@implementation I1 -im1 { return 0; }; @end void f3() { id x = @protocol(P6); } // RUN: true diff --git a/test/CodeGenObjC/protocols.m b/test/CodeGenObjC/protocols.m new file mode 100644 index 0000000..4cfb83b --- /dev/null +++ b/test/CodeGenObjC/protocols.m @@ -0,0 +1,50 @@ +// RUN: clang-cc -fnext-runtime -emit-llvm %s -o %t + +void p(const char*, ...); + +@interface Root +-(int) conformsTo: (id) x; +@end + +@protocol P0; + +@protocol P1 ++(void) classMethodReq0; +-(void) methodReq0; +@optional ++(void) classMethodOpt1; +-(void) methodOpt1; +@required ++(void) classMethodReq2; +-(void) methodReq2; +@end + +@protocol P2 +//@property(readwrite) int x; +@end + +@protocol P3 +-(id ) print0; +-(void) print1; +@end + +void foo(const id a) { + void *p = @protocol(P3); +} + +int main() { + Protocol *P0 = @protocol(P0); + Protocol *P1 = @protocol(P1); + Protocol *P2 = @protocol(P2); + Protocol *P3 = @protocol(P3); + +#define Pbool(X) p(#X ": %s\n", X ? "yes" : "no"); + Pbool([P0 conformsTo: P1]); + Pbool([P1 conformsTo: P0]); + Pbool([P1 conformsTo: P2]); + Pbool([P2 conformsTo: P1]); + Pbool([P3 conformsTo: P1]); + Pbool([P1 conformsTo: P3]); + + return 0; +} diff --git a/test/CodeGenObjC/variadic-sends.m b/test/CodeGenObjC/variadic-sends.m new file mode 100644 index 0000000..8697fee --- /dev/null +++ b/test/CodeGenObjC/variadic-sends.m @@ -0,0 +1,41 @@ +// RUN: clang-cc -triple i386-unknown-unknown -fnext-runtime -emit-llvm -o - %s | FileCheck -check-prefix=CHECK-X86-32 %s && +// RUN: clang-cc -triple x86_64-unknown-unknown -fnext-runtime -emit-llvm -o - %s | FileCheck -check-prefix=CHECK-X86-64 %s + +@interface A +-(void) im0; +-(void) im1: (int) x; +-(void) im2: (int) x, ...; +@end + +void f0(A *a) { + // CHECK-X86-32: call void bitcast (i8* (i8*, %struct.objc_selector*, ...)* @objc_msgSend to void (i8*, %struct.objc_selector*)*) + // CHECK-X86-64: call void bitcast (i8* (i8*, %struct.objc_selector*, ...)* @objc_msgSend to void (i8*, %struct.objc_selector*)*) + [a im0]; +} + +void f1(A *a) { + // CHECK-X86-32: call void bitcast (i8* (i8*, %struct.objc_selector*, ...)* @objc_msgSend to void (i8*, %struct.objc_selector*, i32)*) + // CHECK-X86-64: call void bitcast (i8* (i8*, %struct.objc_selector*, ...)* @objc_msgSend to void (i8*, %struct.objc_selector*, i32)*) + [a im1: 1]; +} + +void f2(A *a) { + // CHECK-X86-32: call void (i8*, %struct.objc_selector*, i32, i32, ...)* bitcast (i8* (i8*, %struct.objc_selector*, ...)* @objc_msgSend to void (i8*, %struct.objc_selector*, i32, i32, ...)*) + // CHECK-X86-64: call void (i8*, %struct.objc_selector*, i32, i32, ...)* bitcast (i8* (i8*, %struct.objc_selector*, ...)* @objc_msgSend to void (i8*, %struct.objc_selector*, i32, i32, ...)*) + [a im2: 1, 2]; +} + +@interface B : A @end +@implementation B : A +-(void) foo { + // CHECK-X86-32: call void bitcast (i8* (%struct._objc_super*, %struct.objc_selector*, ...)* @objc_msgSendSuper to void (%struct._objc_super*, %struct.objc_selector*, i32)*) + // CHECK-X86-64: call void bitcast (i8* (%struct._objc_super*, %struct.objc_selector*, ...)* @objc_msgSendSuper to void (%struct._objc_super*, %struct.objc_selector*, i32)*) + [super im1: 1]; +} +-(void) bar { + // CHECK-X86-32: call void (%struct._objc_super*, %struct.objc_selector*, i32, i32, ...)* bitcast (i8* (%struct._objc_super*, %struct.objc_selector*, ...)* @objc_msgSendSuper to void (%struct._objc_super*, %struct.objc_selector*, i32, i32, ...)*) + // CHECK-X86-64: call void (%struct._objc_super*, %struct.objc_selector*, i32, i32, ...)* bitcast (i8* (%struct._objc_super*, %struct.objc_selector*, ...)* @objc_msgSendSuper to void (%struct._objc_super*, %struct.objc_selector*, i32, i32, ...)*) + [super im2: 1, 2]; +} + +@end diff --git a/test/Coverage/targets.c b/test/Coverage/targets.c index 5a547a5..5a87b4d 100644 --- a/test/Coverage/targets.c +++ b/test/Coverage/targets.c @@ -1,18 +1,19 @@ -// RUN: clang-cc -g -triple i686-unknown-unknown -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple armv6-apple-darwin9 -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple armv6-unknown-unknown -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple bfin-unknown-unknown -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple i686-apple-darwin9 -emit-llvm -o %t %s && // RUN: clang-cc -g -triple i686-pc-linux-gnu -emit-llvm -o %t %s && // RUN: clang-cc -g -triple i686-unknown-dragonfly -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple i686-unknown-unknown -emit-llvm -o %t %s && // RUN: clang-cc -g -triple i686-unknown-win32 -emit-llvm -o %t %s && -// RUN: clang-cc -g -triple i686-apple-darwin9 -emit-llvm -o %t %s && -// RUN: clang-cc -g -triple x86_64-unknown-unknown -emit-llvm -o %t %s && -// RUN: clang-cc -g -triple x86_64-pc-linux-gnu -emit-llvm -o %t %s && -// RUN: clang-cc -g -triple x86_64-apple-darwin9 -emit-llvm -o %t %s && -// RUN: clang-cc -g -triple ppc-unknown-unknown -emit-llvm -o %t %s && -// RUN: clang-cc -g -triple ppc-apple-darwin9 -emit-llvm -o %t %s && -// RUN: clang-cc -g -triple ppc64-unknown-unknown -emit-llvm -o %t %s && -// RUN: clang-cc -g -triple ppc64-apple-darwin9 -emit-llvm -o %t %s && -// RUN: clang-cc -g -triple armv6-unknown-unknown -emit-llvm -o %t %s && -// RUN: clang-cc -g -triple armv6-apple-darwin9 -emit-llvm -o %t %s && -// RUN: clang-cc -g -triple sparc-unknown-unknown -emit-llvm -o %t %s && -// RUN: clang-cc -g -triple sparc-unknown-solaris -emit-llvm -o %t %s && // RUN: clang-cc -g -triple pic16-unknown-unknown -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple powerpc-apple-darwin9 -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple powerpc-unknown-unknown -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple powerpc64-apple-darwin9 -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple powerpc64-unknown-unknown -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple sparc-unknown-solaris -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple sparc-unknown-unknown -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple x86_64-apple-darwin9 -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple x86_64-pc-linux-gnu -emit-llvm -o %t %s && +// RUN: clang-cc -g -triple x86_64-unknown-unknown -emit-llvm -o %t %s && // RUN: true diff --git a/test/Driver/arm-darwin-builtin.c b/test/Driver/arm-darwin-builtin.c new file mode 100644 index 0000000..5da8074 --- /dev/null +++ b/test/Driver/arm-darwin-builtin.c @@ -0,0 +1,14 @@ +// FIXME: Disable pending PR4941. +// RUX: clang -ccc-host-triple x86_64-apple-darwin9 -arch arm -### -fsyntax-only %s 2> %t && +// RUX: grep -- "-fno-builtin-strcat" %t && +// RUX: grep -- "-fno-builtin-strcpy" %t && + +// FIXME: Disable pending PR4941. +// RUX: clang -ccc-host-triple x86_64-apple-darwin9 -arch arm -### -fsyntax-only %s -fbuiltin-strcat -fbuiltin-strcpy 2> %t && +// RUX: not grep -- "-fno-builtin-strcat" %t && +// RUX: not grep -- "-fno-builtin-strcpy" %t && + +// RUN: clang -ccc-no-clang -ccc-host-triple x86_64-apple-darwin9 -arch arm -### -fsyntax-only %s -fbuiltin-strcat -fbuiltin-strcpy 2> %t && +// RUN: not grep -- "-fno-builtin-strcat" %t && +// RUN: not grep -- "-fno-builtin-strcpy" %t + diff --git a/test/Driver/ast.c b/test/Driver/ast.c new file mode 100644 index 0000000..814b597 --- /dev/null +++ b/test/Driver/ast.c @@ -0,0 +1,26 @@ +// RUN: clang -ccc-host-triple i386-unknown-unknown -ccc-print-phases -emit-ast %s 2> %t && +// RUN: echo 'END' >> %t && +// RUN: FileCheck -check-prefix EMIT-AST-PHASES -input-file %t %s && + +// EMIT-AST-PHASES: 0: input, +// EMIT-AST-PHASES: , c +// EMIT-AST-PHASES: 1: preprocessor, {0}, cpp-output +// EMIT-AST-PHASES: 2: compiler, {1}, ast +// EMIT-AST-PHASES-NOT: 3: +// EMIT-AST-PHASES: END + +// RUN: touch %t.ast && +// RUN: clang -ccc-host-triple i386-unknown-unknown -ccc-print-phases -c %t.ast 2> %t && +// RUN: echo 'END' >> %t && +// RUN: FileCheck -check-prefix COMPILE-AST-PHASES -input-file %t %s + +// COMPILE-AST-PHASES: 0: input, +// COMPILE-AST-PHASES: , ast +// COMPILE-AST-PHASES: 1: compiler, {0}, assembler +// COMPILE-AST-PHASES: 2: assembler, {1}, object +// COMPILE-AST-PHASES-NOT: 3: +// COMPILE-AST-PHASES: END + +// FIXME: There is a problem with compiling AST's in that the input language is +// not availabe for use by other tools (for example, to automatically add +// -lstdc++). We may need -x [objective-]c++-ast and all that goodness. :( diff --git a/test/Driver/bindings.c b/test/Driver/bindings.c index 3cac22c..3937390 100644 --- a/test/Driver/bindings.c +++ b/test/Driver/bindings.c @@ -30,7 +30,7 @@ // RUN: grep '"clang", inputs: \[".*bindings.c"\], output: (nothing)' %t && // RUN: clang -ccc-host-triple i386-unknown-unknown -ccc-print-bindings -ccc-no-clang -fsyntax-only %s 2> %t && // RUN: grep '"gcc::Compile", inputs: \[".*bindings.c"\], output: (nothing)' %t && -// RUN: clang -ccc-host-triple i386-unknown-unknown -ccc-print-bindings -fsyntax-only -x c++ %s 2> %t && +// RUN: clang -ccc-host-triple i386-unknown-unknown -ccc-print-bindings -ccc-no-clang-cxx -fsyntax-only -x c++ %s 2> %t && // RUN: grep '"gcc::Compile", inputs: \[".*bindings.c"\], output: (nothing)' %t && // RUN: clang -ccc-host-triple i386-unknown-unknown -ccc-print-bindings -ccc-clang-cxx -fsyntax-only -x c++ %s 2> %t && // RUN: grep '"clang", inputs: \[".*bindings.c"\], output: (nothing)' %t && @@ -39,12 +39,12 @@ // RUN: grep '"clang", inputs: \[".*\.i"\], output: (nothing)' %t && // RUN: clang -ccc-host-triple i386-apple-darwin9 -ccc-print-bindings -ccc-clang-archs i386 %s -S -arch ppc 2> %t && // RUN: grep '"gcc::Compile", inputs: \[".*bindings.c"\], output: "bindings.s"' %t && -// RUN: clang -ccc-host-triple i386-apple-darwin9 -ccc-print-bindings -ccc-clang-archs ppc %s -S -arch ppc 2> %t && +// RUN: clang -ccc-host-triple i386-apple-darwin9 -ccc-print-bindings -ccc-clang-archs powerpc %s -S -arch ppc 2> %t && // RUN: grep '"clang", inputs: \[".*bindings.c"\], output: "bindings.s"' %t && // RUN: clang -ccc-host-triple powerpc-unknown-unknown -ccc-print-bindings -ccc-clang-archs "" %s -S 2> %t && // RUN: grep '"clang", inputs: \[".*bindings.c"\], output: "bindings.s"' %t && -// RUN: clang -ccc-host-triple powerpc-unknown-unknown -ccc-print-bindings %s -S 2> %t && +// RUN: clang -ccc-host-triple powerpc-unknown-unknown -ccc-print-bindings -ccc-clang-archs "i386" %s -S 2> %t && // RUN: grep '"gcc::Compile", inputs: \[".*bindings.c"\], output: "bindings.s"' %t && // Darwin bindings diff --git a/test/Driver/clang-translation.c b/test/Driver/clang-translation.c index ca60a8d..e0b9e3a 100644 --- a/test/Driver/clang-translation.c +++ b/test/Driver/clang-translation.c @@ -1,4 +1,4 @@ -// RUN: clang -ccc-host-triple i386-unknown-unknown -### -S -O0 -Os %s -o %t.s -fverbose-asm 2> %t.log +// RUN: clang -ccc-host-triple i386-unknown-unknown -### -S -O0 -Os %s -o %t.s -fverbose-asm 2> %t.log && // RUN: grep '"-triple" "i386-unknown-unknown"' %t.log && // RUN: grep '"-S"' %t.log && // RUN: grep '"-disable-free"' %t.log && @@ -7,10 +7,10 @@ // RUN: grep '"--unwind-tables=0"' %t.log && // RUN: grep '"--fmath-errno=1"' %t.log && // RUN: grep '"-Os"' %t.log && -// RUN: grep '"-o" .*clang-translation\.c\.out\.tmp\.s' %t.log && +// RUN: grep '"-o" .*clang-translation.*' %t.log && // RUN: grep '"--asm-verbose"' %t.log && -// RUN: clang -ccc-host-triple i386-apple-darwin9 -### -S %s -o %t.s 2> %t.log +// RUN: clang -ccc-host-triple i386-apple-darwin9 -### -S %s -o %t.s 2> %t.log && // RUN: grep '"--mcpu=yonah"' %t.log && -// RUN: clang -ccc-host-triple x86_64-apple-darwin9 -### -S %s -o %t.s 2> %t.log +// RUN: clang -ccc-host-triple x86_64-apple-darwin9 -### -S %s -o %t.s 2> %t.log && // RUN: grep '"--mcpu=core2"' %t.log && // RUN: true diff --git a/test/Driver/darwin-arm.c b/test/Driver/darwin-arm.c new file mode 100644 index 0000000..8b4c23d5 --- /dev/null +++ b/test/Driver/darwin-arm.c @@ -0,0 +1,4 @@ +// RUN: clang -ccc-host-triple i386-apple-darwin9 -arch arm -print-search-dirs | FileCheck %s + +// Check that we look in the relative libexec directory. +// CHECK: {{programs: =.*/../libexec:}} diff --git a/test/Driver/darwin-as.c b/test/Driver/darwin-as.c new file mode 100644 index 0000000..486dc2e --- /dev/null +++ b/test/Driver/darwin-as.c @@ -0,0 +1,10 @@ +// RUN: clang -ccc-host-triple i386-apple-darwin10 -### -x assembler -c %s -static -dynamic 2>%t && +// RUN: FileCheck -check-prefix=STATIC_AND_DYNAMIC-32 --input-file %t %s && + +// CHECK-STATIC_AND_DYNAMIC-32: as{{(.exe)?}}" "-arch" "i386" "-force_cpusubtype_ALL" "-static" "-o" + +// RUN: clang -ccc-host-triple x86_64-apple-darwin10 -### -x assembler -c %s -static 2>%t && +// RUN: FileCheck -check-prefix=STATIC-64 --input-file %t %s + +// CHECK-STATIC-64: as{{(.exe)?}}" "-arch" "x86_64" "-force_cpusubtype_ALL" "-o" + diff --git a/test/Driver/darwin-cc.c b/test/Driver/darwin-cc.c index ac5d9a9..77193cd 100644 --- a/test/Driver/darwin-cc.c +++ b/test/Driver/darwin-cc.c @@ -1,4 +1,3 @@ -// RUN: unset MACOSX_DEPLOYMENT_TARGET && // RUN: clang -ccc-no-clang -ccc-host-triple i386-apple-darwin10 -m32 -### -MD -g -fast -Q -dA -mkernel -ansi -aFOO -S -o /tmp/OUTPUTNAME -g0 -gfull -O2 -Werror -pedantic -Wmost -w -std=c99 -trigraphs -v -pg -fFOO -undef -Qn --param a=b -fmudflap -coverage -save-temps -nostdinc -I ARG0 -F ARG1 -I ARG2 -P -MF ARG3 -MG -MP -remap -g3 -H -D ARG4 -U ARG5 -A ARG6 -D ARG7 -U ARG8 -A ARG9 -include ARG10 -pthread %s 2> %t.log && // RUN: grep ' ".*cc1" "-E" "-nostdinc" "-v" "-I" "ARG0" "-F" "ARG1" "-I" "ARG2" "-P" "-MD" "/tmp/OUTPUTNAME.d" "-MF" "ARG3" "-MG" "-MP" "-MQ" "/tmp/OUTPUTNAME" "-remap" "-dD" "-H" "-D__STATIC__" "-D_REENTRANT" "-D" "ARG4" "-U" "ARG5" "-A" "ARG6" "-D" "ARG7" "-U" "ARG8" "-A" "ARG9" "-include" "ARG10" ".*darwin-cc.c" "-D_MUDFLAP" "-include" "mf-runtime.h" "-mmacosx-version-min=10.6.0" "-m32" "-mkernel" "-mtune=core2" "-ansi" "-std=c99" "-trigraphs" "-Werror" "-pedantic" "-Wmost" "-w" "-fast" "-fno-eliminate-unused-debug-symbols" "-fFOO" "-fmudflap" "-O2" "-undef" "-fpch-preprocess" "-o" ".*darwin-cc.i"' %t.log && // RUN: grep ' ".*cc1" "-fpreprocessed" ".*darwin-cc.i" "-O3" "-dumpbase" ".*darwin-cc.c" "-dA" "-mmacosx-version-min=10.6.0" "-m32" "-mkernel" "-mtune=core2" "-ansi" "-aFOO" "-auxbase-strip" "/tmp/OUTPUTNAME" "-g" "-g0" "-g" "-g3" "-O2" "-Werror" "-pedantic" "-Wmost" "-w" "-ansi" "-std=c99" "-trigraphs" "-version" "-p" "-fast" "-fno-eliminate-unused-debug-symbols" "-fFOO" "-fmudflap" "-undef" "-fno-ident" "-o" "/tmp/OUTPUTNAME" "--param" "a=b" "-fno-builtin" "-fno-merge-constants" "-fprofile-arcs" "-ftest-coverage"' %t.log && diff --git a/test/Driver/darwin-ld.c b/test/Driver/darwin-ld.c index 2e6fc57..d81605b 100644 --- a/test/Driver/darwin-ld.c +++ b/test/Driver/darwin-ld.c @@ -1,8 +1,7 @@ // Check that ld gets arch_multiple. -// RUN: unset MACOSX_DEPLOYMENT_TARGET && // RUN: clang -ccc-host-triple i386-apple-darwin9 -arch i386 -arch x86_64 %s -### -o foo 2> %t.log && -// RUN: grep '".*ld" .*"-arch_multiple" "-final_output" "foo"' %t.log && +// RUN: grep '".*ld.*" .*"-arch_multiple" "-final_output" "foo"' %t.log && // RUN: clang -ccc-host-triple i386-apple-darwin9 -### -filelist FOO -static 2> %t.log && // RUN: grep '"-lcrt0.o" .*"-lgcc_static"' %t.log && @@ -33,8 +32,8 @@ // // Note that at conception, this exactly matches gcc. -// RUN: clang -ccc-host-triple i386-apple-darwin9 -### -A ARG0 -F ARG1 -L ARG2 -Mach -T ARG4 -X -Z -all_load -allowable_client ARG8 -bind_at_load -compatibility_version ARG11 -current_version ARG12 -d -dead_strip -dylib_file ARG14 -dylinker -dylinker_install_name ARG16 -dynamic -dynamiclib -e ARG19 -exported_symbols_list ARG20 -fexceptions -flat_namespace -fnested-functions -fopenmp -force_cpusubtype_ALL -fpie -fprofile-arcs -headerpad_max_install_names -image_base ARG29 -init ARG30 -install_name ARG31 -m ARG33 -miphoneos-version-min=2.0 -mmacosx-version-min=10.3.2 -multi_module -multiply_defined ARG37 -multiply_defined_unused ARG38 -no_dead_strip_inits_and_terms -nodefaultlibs -nofixprebinding -nomultidefs -noprebind -noseglinkedit -nostartfiles -nostdlib -object -pagezero_size ARG54 -pg -prebind -prebind_all_twolevel_modules -preload -r -read_only_relocs ARG55 -s -sectalign ARG57_0 ARG57_1 ARG57_2 -sectcreate ARG58_0 ARG58_1 ARG58_2 -sectobjectsymbols ARG59_0 ARG59_1 -sectorder ARG60_0 ARG60_1 ARG60_2 -seg1addr ARG61 -seg_addr_table ARG62 -seg_addr_table_filename ARG63 -segaddr ARG64_0 ARG64_1 -segcreate ARG65_0 ARG65_1 ARG65_2 -seglinkedit -segprot ARG67_0 ARG67_1 ARG67_2 -segs_read_FOO -segs_read_only_addr ARG69 -segs_read_write_addr ARG70 -shared-libgcc -single_module -static -static-libgcc -sub_library ARG77 -sub_umbrella ARG78 -t -twolevel_namespace -twolevel_namespace_hints -u ARG82 -umbrella ARG83 -undefined ARG84 -unexported_symbols_list ARG85 -w -weak_reference_mismatches ARG87 -whatsloaded -whyload -y -filelist FOO 2> %t.log && -// RUN: grep '".*ld" "-static" "-dylib" "-dylib_compatibility_version" "ARG11" "-dylib_current_version" "ARG12" "-arch" "i386" "-dylib_install_name" "ARG31" "-all_load" "-allowable_client" "ARG8" "-bind_at_load" "-dead_strip" "-no_dead_strip_inits_and_terms" "-dylib_file" "ARG14" "-dynamic" "-exported_symbols_list" "ARG20" "-flat_namespace" "-headerpad_max_install_names" "-image_base" "ARG29" "-init" "ARG30" "-macosx_version_min" "10.3.2" "-iphoneos_version_min" "2.0" "-nomultidefs" "-multi_module" "-single_module" "-multiply_defined" "ARG37" "-multiply_defined_unused" "ARG38" "-pie" "-prebind" "-noprebind" "-nofixprebinding" "-prebind_all_twolevel_modules" "-read_only_relocs" "ARG55" "-sectcreate" "ARG58_0" "ARG58_1" "ARG58_2" "-sectorder" "ARG60_0" "ARG60_1" "ARG60_2" "-seg1addr" "ARG61" "-segprot" "ARG67_0" "ARG67_1" "ARG67_2" "-segaddr" "ARG64_0" "ARG64_1" "-segs_read_only_addr" "ARG69" "-segs_read_write_addr" "ARG70" "-seg_addr_table" "ARG62" "-seg_addr_table_filename" "ARG63" "-sub_library" "ARG77" "-sub_umbrella" "ARG78" "-twolevel_namespace" "-twolevel_namespace_hints" "-umbrella" "ARG83" "-undefined" "ARG84" "-unexported_symbols_list" "ARG85" "-weak_reference_mismatches" "ARG87" "-X" "-y" "-w" "-pagezero_size" "ARG54" "-segs_read_FOO" "-seglinkedit" "-noseglinkedit" "-sectalign" "ARG57_0" "ARG57_1" "ARG57_2" "-sectobjectsymbols" "ARG59_0" "ARG59_1" "-segcreate" "ARG65_0" "ARG65_1" "ARG65_2" "-whyload" "-whatsloaded" "-dylinker_install_name" "ARG16" "-dylinker" "-Mach" "-d" "-s" "-t" "-Z" "-u" "ARG82" "-undefined" "ARG84" "-A" "ARG0" "-e" "ARG19" "-m" "ARG33" "-r" "-object" "-o" "a.out" "-L" "ARG2" "-lgomp" "-L/usr/lib/i686-apple-darwin9/4.2.1" "-L/usr/lib/gcc/i686-apple-darwin9/4.2.1" "-L/usr/lib/gcc/i686-apple-darwin9/4.2.1" "-L/usr/lib/gcc/i686-apple-darwin9/4.2.1/../../../i686-apple-darwin9/4.2.1" "-L/usr/lib/gcc/i686-apple-darwin9/4.2.1/../../.." "-filelist" "FOO" "-lgcov" "-allow_stack_execute" "-T" "ARG4" "-F" "ARG1"' %t.log && +// RUN: clang -ccc-host-triple i386-apple-darwin9 -### -A ARG0 -F ARG1 -L ARG2 -Mach -T ARG4 -X -Z -all_load -allowable_client ARG8 -bind_at_load -compatibility_version ARG11 -current_version ARG12 -d -dead_strip -dylib_file ARG14 -dylinker -dylinker_install_name ARG16 -dynamic -dynamiclib -e ARG19 -exported_symbols_list ARG20 -fexceptions -flat_namespace -fnested-functions -fopenmp -force_cpusubtype_ALL -fpie -fprofile-arcs -headerpad_max_install_names -image_base ARG29 -init ARG30 -install_name ARG31 -m ARG33 -miphoneos-version-min=2.0 -mmacosx-version-min=10.3.2 -multi_module -multiply_defined ARG37 -multiply_defined_unused ARG38 -no_dead_strip_inits_and_terms -nodefaultlibs -nofixprebinding -nomultidefs -noprebind -noseglinkedit -nostartfiles -nostdlib -pagezero_size ARG54 -pg -prebind -prebind_all_twolevel_modules -preload -r -read_only_relocs ARG55 -s -sectalign ARG57_0 ARG57_1 ARG57_2 -sectcreate ARG58_0 ARG58_1 ARG58_2 -sectobjectsymbols ARG59_0 ARG59_1 -sectorder ARG60_0 ARG60_1 ARG60_2 -seg1addr ARG61 -seg_addr_table ARG62 -seg_addr_table_filename ARG63 -segaddr ARG64_0 ARG64_1 -segcreate ARG65_0 ARG65_1 ARG65_2 -seglinkedit -segprot ARG67_0 ARG67_1 ARG67_2 -segs_read_FOO -segs_read_only_addr ARG69 -segs_read_write_addr ARG70 -shared-libgcc -single_module -static -static-libgcc -sub_library ARG77 -sub_umbrella ARG78 -t -twolevel_namespace -twolevel_namespace_hints -u ARG82 -umbrella ARG83 -undefined ARG84 -unexported_symbols_list ARG85 -w -weak_reference_mismatches ARG87 -whatsloaded -whyload -y -filelist FOO 2> %t.log && +// RUN: grep '".*ld.*" "-static" "-dylib" "-dylib_compatibility_version" "ARG11" "-dylib_current_version" "ARG12" "-arch" "i386" "-dylib_install_name" "ARG31" "-all_load" "-allowable_client" "ARG8" "-bind_at_load" "-dead_strip" "-no_dead_strip_inits_and_terms" "-dylib_file" "ARG14" "-dynamic" "-exported_symbols_list" "ARG20" "-flat_namespace" "-headerpad_max_install_names" "-image_base" "ARG29" "-init" "ARG30" "-macosx_version_min" "10.3.2" "-iphoneos_version_min" "2.0" "-nomultidefs" "-multi_module" "-single_module" "-multiply_defined" "ARG37" "-multiply_defined_unused" "ARG38" "-pie" "-prebind" "-noprebind" "-nofixprebinding" "-prebind_all_twolevel_modules" "-read_only_relocs" "ARG55" "-sectcreate" "ARG58_0" "ARG58_1" "ARG58_2" "-sectorder" "ARG60_0" "ARG60_1" "ARG60_2" "-seg1addr" "ARG61" "-segprot" "ARG67_0" "ARG67_1" "ARG67_2" "-segaddr" "ARG64_0" "ARG64_1" "-segs_read_only_addr" "ARG69" "-segs_read_write_addr" "ARG70" "-seg_addr_table" "ARG62" "-seg_addr_table_filename" "ARG63" "-sub_library" "ARG77" "-sub_umbrella" "ARG78" "-twolevel_namespace" "-twolevel_namespace_hints" "-umbrella" "ARG83" "-undefined" "ARG84" "-unexported_symbols_list" "ARG85" "-weak_reference_mismatches" "ARG87" "-X" "-y" "-w" "-pagezero_size" "ARG54" "-segs_read_FOO" "-seglinkedit" "-noseglinkedit" "-sectalign" "ARG57_0" "ARG57_1" "ARG57_2" "-sectobjectsymbols" "ARG59_0" "ARG59_1" "-segcreate" "ARG65_0" "ARG65_1" "ARG65_2" "-whyload" "-whatsloaded" "-dylinker_install_name" "ARG16" "-dylinker" "-Mach" "-d" "-s" "-t" "-Z" "-u" "ARG82" "-undefined" "ARG84" "-A" "ARG0" "-e" "ARG19" "-m" "ARG33" "-r" "-o" "a.out" "-L" "ARG2" "-lgomp" "-L/usr/lib/i686-apple-darwin9/4.2.1" "-L/usr/lib/gcc/i686-apple-darwin9/4.2.1" "-L/usr/lib/gcc/i686-apple-darwin9/4.2.1" "-L/usr/lib/gcc/i686-apple-darwin9/4.2.1/../../../i686-apple-darwin9/4.2.1" "-L/usr/lib/gcc/i686-apple-darwin9/4.2.1/../../.." "-filelist" "FOO" "-lgcov" "-allow_stack_execute" "-T" "ARG4" "-F" "ARG1"' %t.log && // Don't run dsymutil on a fat build of an executable. // RUN: clang -ccc-host-triple i386-apple-darwin9 -### -arch i386 -arch x86_64 -g %s 2> %t.log && diff --git a/test/Driver/default-toolchain.c b/test/Driver/default-toolchain.c index 216394f..0e8a026 100644 --- a/test/Driver/default-toolchain.c +++ b/test/Driver/default-toolchain.c @@ -1,8 +1,8 @@ -// RUN: clang -ccc-host-triple i386-unknown-unknown -m64 -v 2> %t +// RUN: clang -ccc-host-triple i386-unknown-unknown -m64 -v 2> %t && // RUN: grep 'Target: x86_64-unknown-unknown' %t && -// RUN: clang -ccc-host-triple i386-apple-darwin9 -arch ppc -m64 -v 2> %t +// RUN: clang -ccc-host-triple i386-apple-darwin9 -arch ppc -m64 -v 2> %t && // RUN: grep 'Target: powerpc64-apple-darwin9' %t && -// RUN: clang -ccc-host-triple i386-apple-darwin9 -arch ppc64 -m32 -v 2> %t +// RUN: clang -ccc-host-triple i386-apple-darwin9 -arch ppc64 -m32 -v 2> %t && // RUN: grep 'Target: powerpc-apple-darwin9' %t diff --git a/test/Driver/dragonfly.c b/test/Driver/dragonfly.c index 5d7b0b0..f0b09f7 100644 --- a/test/Driver/dragonfly.c +++ b/test/Driver/dragonfly.c @@ -1,6 +1,8 @@ // RUN: clang -ccc-host-triple amd64-pc-dragonfly %s -### 2> %t.log && -// RUN: grep 'clang-cc" "-triple" "x86_64-pc-dragonfly"' %t.log && -// RUN: grep 'as" "-o" ".*\.o" ".*\.s' %t.log && -// RUN: grep 'ld" "-dynamic-linker" ".*ld-elf.*" "-o" "a\.out" ".*crt1.o" ".*crti.o" "crtbegin.o" ".*\.o" "-L.*/gcc.*" .* "-lc" "-lgcc" ".*crtend.o" ".*crtn.o"' %t.log && -// RUN: true +// RUN: FileCheck -input-file %t.log %s + +// CHECK: clang-cc{{.*}}" "-triple" "amd64-pc-dragonfly" +// CHECK: as{{.*}}" "-o" "{{.*}}.o" "{{.*}}.s +// CHECK: ld{{.*}}" "-dynamic-linker" "{{.*}}ld-elf.{{.*}}" "-o" "a.out" "{{.*}}crt1.o" "{{.*}}crti.o" "{{.*}}crtbegin.o" "{{.*}}.o" "-L{{.*}}/gcc{{.*}}" {{.*}} "-lc" "-lgcc" "{{.*}}crtend.o" "{{.*}}crtn.o" + diff --git a/test/Driver/freebsd.c b/test/Driver/freebsd.c index 91258d9..d50c85b 100644 --- a/test/Driver/freebsd.c +++ b/test/Driver/freebsd.c @@ -1,7 +1,7 @@ -// RUN: clang -ccc-clang-archs "" -ccc-host-triple ppc64-pc-freebsd8 %s -### 2> %t.log && +// RUN: clang -ccc-clang-archs "" -ccc-host-triple powerpc64-pc-freebsd8 %s -### 2> %t.log && // RUN: cat %t.log && -// RUN: grep 'clang-cc" "-triple" "powerpc64-pc-freebsd8"' %t.log && -// RUN: grep 'as" "-o" ".*\.o" ".*\.s' %t.log && -// RUN: grep 'ld" "--eh-frame-hdr" "-dynamic-linker" ".*ld-elf.*" "-o" "a\.out" ".*crt1.o" ".*crti.o" "crtbegin.o" ".*\.o" "-lgcc" "--as-needed" "-lgcc_s" "--no-as-needed" "-lc" "-lgcc" "--as-needed" "-lgcc_s" "--no-as-needed" ".*crtend.o" ".*crtn.o"' %t.log && -// RUN: true +// RUN: FileCheck -input-file %t.log %s +// CHECK: clang-cc{{.*}}" "-triple" "powerpc64-pc-freebsd8" +// CHECK: as{{.*}}" "-o" "{{.*}}.o" "{{.*}}.s +// CHECK: ld{{.*}}" "--eh-frame-hdr" "-dynamic-linker" "{{.*}}ld-elf{{.*}}" "-o" "a.out" "{{.*}}crt1.o" "{{.*}}crti.o" "{{.*}}crtbegin.o" "{{.*}}.o" "-lgcc" "--as-needed" "-lgcc_s" "--no-as-needed" "-lc" "-lgcc" "--as-needed" "-lgcc_s" "--no-as-needed" "{{.*}}crtend.o" "{{.*}}crtn.o" diff --git a/test/Driver/openbsd.c b/test/Driver/openbsd.c index fd0d4fa..c73ef20 100644 --- a/test/Driver/openbsd.c +++ b/test/Driver/openbsd.c @@ -1,6 +1,6 @@ // RUN: clang -ccc-clang-archs "" -ccc-host-triple i686-pc-openbsd %s -### 2> %t.log && -// RUN: grep 'clang-cc" "-triple" "i386-pc-openbsd"' %t.log && -// RUN: grep 'as" "-o" ".*\.o" ".*\.s' %t.log && -// RUN: grep 'ld" "--eh-frame-hdr" "-dynamic-linker" ".*ld.so" "-o" "a\.out" ".*crt0.o" ".*crtbegin.o" ".*\.o" "-lc" ".*crtend.o"' %t.log && -// RUN: true +// RUN: FileCheck -input-file %t.log %s +// CHECK: clang-cc{{.*}}" "-triple" "i686-pc-openbsd" +// CHECK: as{{.*}}" "-o" "{{.*}}.o" "{{.*}}.s +// CHECK: ld{{.*}}" "-e" "__start" "--eh-frame-hdr" "-Bdynamic" "-dynamic-linker" "{{.*}}ld.so" "-o" "a.out" "{{.*}}crt0.o" "{{.*}}crtbegin.o" "{{.*}}.o" "-lgcc" "-lc" "-lgcc" "{{.*}}crtend.o" diff --git a/test/Driver/pth.c b/test/Driver/pth.c index 7480538..5c83aea 100644 --- a/test/Driver/pth.c +++ b/test/Driver/pth.c @@ -1,8 +1,12 @@ // Test transparent PTH support. // RUN: clang -ccc-pch-is-pth -x c-header %s -o %t.h.pth -### 2> %t.log && -// RUN: grep '".*/clang-cc" .* "-o" ".*\.h\.pth" "-x" "c-header" ".*pth\.c"' %t.log && +// RUN: FileCheck -check-prefix CHECK1 -input-file %t.log %s && + +// CHECK1: "{{.*}}/clang-cc{{.*}}" {{.*}} "-o" "{{.*}}.h.pth" "-x" "c-header" "{{.*}}pth.c" // RUN: touch %t.h.pth && // RUN: clang -ccc-pch-is-pth -E -include %t.h %s -### 2> %t.log && -// RUN: grep '".*/clang-cc" .*"-include-pth" ".*\.h\.pth" .*"-x" "c" ".*pth\.c"' %t.log +// RUN: FileCheck -check-prefix CHECK2 -input-file %t.log %s + +// CHECK2: "{{.*}}/clang-cc{{.*}}" {{.*}}"-include-pth" "{{.*}}.h.pth" {{.*}}"-x" "c" "{{.*}}pth.c" diff --git a/test/Driver/qa_override.c b/test/Driver/qa_override.c index 0ff578c..46e150c 100644 --- a/test/Driver/qa_override.c +++ b/test/Driver/qa_override.c @@ -1,4 +1,5 @@ -// RUN: env QA_OVERRIDE_GCC3_OPTIONS="+-Os +-Oz +-O +-O3 +-Oignore +a +b +c xb Xa Omagic ^-ccc-print-options " clang x -O2 b -O3 2> %t && +// RUN: env QA_OVERRIDE_GCC3_OPTIONS="#+-Os +-Oz +-O +-O3 +-Oignore +a +b +c xb Xa Omagic ^-ccc-print-options " clang x -O2 b -O3 2> %t && +// RUN: grep '### ' %t | count 0 && // RUN: grep -F 'Option 0 - Name: "", Values: {"x"}' %t && // RUN: grep -F 'Option 1 - Name: "-O", Values: {"ignore"}' %t && // RUN: grep -F 'Option 2 - Name: "-O", Values: {"magic"}' %t && diff --git a/test/Driver/redzone.c b/test/Driver/redzone.c index 8709e71..64729ac 100644 --- a/test/Driver/redzone.c +++ b/test/Driver/redzone.c @@ -1,6 +1,6 @@ -// RUN: clang -mno-red-zone %s -S -emit-llvm -o %t.log && -// RUN: grep 'noredzone' %t.log -// RUN: clang -mred-zone %s -S -emit-llvm -o %t.log && +// RUN: clang -ccc-host-triple i386-unknown-unknown -mno-red-zone %s -S -emit-llvm -o %t.log && +// RUN: grep 'noredzone' %t.log && +// RUN: clang -ccc-host-triple i386-unknown-unknown -mred-zone %s -S -emit-llvm -o %t.log && // RUN: grep -v 'noredzone' %t.log int foo() { return 42; } diff --git a/test/Frontend/ast-codegen.c b/test/Frontend/ast-codegen.c new file mode 100644 index 0000000..1fe74d4 --- /dev/null +++ b/test/Frontend/ast-codegen.c @@ -0,0 +1,12 @@ +// RUN: clang -emit-ast -o %t.ast %s && +// RUN: clang -emit-llvm -S -o - %t.ast | FileCheck %s + +// CHECK: module asm "foo" +__asm__("foo"); + +// CHECK: @g0 = common global i32 0, align 4 +int g0; + +// CHECK: define i32 @f0() +int f0() { +} diff --git a/test/Frontend/ast-main.c b/test/Frontend/ast-main.c new file mode 100644 index 0000000..7831406 --- /dev/null +++ b/test/Frontend/ast-main.c @@ -0,0 +1,8 @@ +// RUN: clang -emit-llvm -S -o %t1.ll -x c - < %s && +// RUN: clang -emit-ast -o %t.ast %s && +// RUN: clang -emit-llvm -S -o %t2.ll -x ast - < %t.ast && +// RUN: diff %t1.ll %t2.ll + +int main() { + return 0; +} diff --git a/test/Frontend/dependency-gen.c b/test/Frontend/dependency-gen.c index 456ce94..4a1611a 100644 --- a/test/Frontend/dependency-gen.c +++ b/test/Frontend/dependency-gen.c @@ -1,6 +1,6 @@ // rdar://6533411 // RUN: clang -MD -MF %t.d -c -x c -o %t.o /dev/null && -// RUN: grep '.*dependency-gen.c.out.tmp.o:' %t.d && +// RUN: grep '.*dependency-gen.*:' %t.d && // RUN: grep '/dev/null' %t.d && // RUN: clang -M -x c /dev/null -o %t.deps && diff --git a/test/Frontend/stdin.c b/test/Frontend/stdin.c index 35fe45d..5b719b2 100644 --- a/test/Frontend/stdin.c +++ b/test/Frontend/stdin.c @@ -1,3 +1,3 @@ -// RUN: clang-cc -E - < /dev/null > %t +// RUN: clang-cc -E - < /dev/null > %t && // RUN: grep '' %t diff --git a/test/Index/c-index-api-test.m b/test/Index/c-index-api-test.m new file mode 100644 index 0000000..20d4d7b --- /dev/null +++ b/test/Index/c-index-api-test.m @@ -0,0 +1,224 @@ +// RUN: clang-cc -triple x86_64-apple-darwin10 -emit-pch -x objective-c %s -o %t.ast && +// RUN: c-index-test %t.ast all | FileCheck %s + +// CHECK: :0:0: TypedefDecl=__int128_t:0:0 [Context=c-index-api-test.m] +// CHECK: :0:0: TypedefDecl=__uint128_t:0:0 [Context=c-index-api-test.m] +// CHECK: :0:0: StructDecl=objc_selector:0:0 [Context=c-index-api-test.m] +// CHECK: :0:0: TypedefDecl=SEL:0:0 [Context=c-index-api-test.m] +// CHECK: :0:0: ObjCInterfaceDecl=Protocol:0:0 [Context=c-index-api-test.m] +// CHECK: :0:0: TypedefDecl=id:0:0 [Context=c-index-api-test.m] +// CHECK: :0:0: TypedefDecl=Class:0:0 [Context=c-index-api-test.m] +// CHECK: :79:16: StructDecl=__va_list_tag:79:16 [Context=c-index-api-test.m] +// CHECK: :79:42: FieldDecl=gp_offset:79:42 [Context=__va_list_tag] +// CHECK: :79:63: FieldDecl=fp_offset:79:63 [Context=__va_list_tag] +// CHECK: :79:81: FieldDecl=overflow_arg_area:79:81 [Context=__va_list_tag] +// CHECK: :79:107: FieldDecl=reg_save_area:79:107 [Context=__va_list_tag] +// CHECK: :79:123: TypedefDecl=__va_list_tag:79:123 [Context=c-index-api-test.m] +// CHECK: :79:159: TypedefDecl=__builtin_va_list:79:159 [Context=c-index-api-test.m] +// + +@interface Foo +{ +} + +- foo; ++ fooC; + +@end + +@interface Bar : Foo +{ +} + +@end + +@interface Foo (FooCat) +- (int) catMethodWithFloat:(float) fArg; +- (float) floatMethod; +@end + +@protocol Proto +- pMethod; +@end + +@protocol SubP +- spMethod; +@end + +@interface Baz : Bar +{ + int _anIVar; +} + +- (Foo *) bazMethod; + +@end + +enum { + someEnum +}; + +// CHECK: c-index-api-test.m:20:12: ObjCInterfaceDecl=Foo:20:1 [Context=c-index-api-test.m] +// CHECK: c-index-api-test.m:24:1: ObjCInstanceMethodDecl=foo:24:1 [Context=Foo] +// CHECK: c-index-api-test.m:25:1: ObjCClassMethodDecl=fooC:25:1 [Context=Foo] +// CHECK: c-index-api-test.m:29:12: ObjCInterfaceDecl=Bar:29:1 [Context=c-index-api-test.m] +// CHECK: c-index-api-test.m:29:18: ObjCSuperClassRef=Foo:29:1 [Context=Bar] +// CHECK: c-index-api-test.m:35:1: ObjCCategoryDecl=FooCat:35:1 [Context=c-index-api-test.m] +// CHECK: c-index-api-test.m:20:1: ObjCClassRef=Foo:35:1 [Context=FooCat] +// CHECK: c-index-api-test.m:36:1: ObjCInstanceMethodDecl=catMethodWithFloat::36:1 [Context=FooCat] +// CHECK: c-index-api-test.m:37:1: ObjCInstanceMethodDecl=floatMethod:37:1 [Context=FooCat] +// CHECK: c-index-api-test.m:40:1: ObjCProtocolDecl=Proto:40:1 [Context=c-index-api-test.m] +// CHECK: c-index-api-test.m:41:1: ObjCInstanceMethodDecl=pMethod:41:1 [Context=Proto] +// CHECK: c-index-api-test.m:44:1: ObjCProtocolDecl=SubP:44:1 [Context=c-index-api-test.m] +// CHECK: c-index-api-test.m:40:1: ObjCProtocolRef=Proto:40:1 [Context=SubP] +// CHECK: c-index-api-test.m:45:1: ObjCInstanceMethodDecl=spMethod:45:1 [Context=SubP] +// CHECK: c-index-api-test.m:48:12: ObjCInterfaceDecl=Baz:48:1 [Context=c-index-api-test.m] +// CHECK: c-index-api-test.m:48:18: ObjCSuperClassRef=Bar:48:1 [Context=Baz] +// CHECK: c-index-api-test.m:44:1: ObjCProtocolRef=SubP:44:1 [Context=Baz] +// CHECK: c-index-api-test.m:50:9: ObjCIvarDecl=_anIVar:50:9 [Context=Baz] +// CHECK: c-index-api-test.m:53:1: ObjCInstanceMethodDecl=bazMethod:53:1 [Context=Baz] +// CHECK: c-index-api-test.m:57:1: EnumDecl=:57:1 [Context=c-index-api-test.m] +// CHECK: c-index-api-test.m:58:3: EnumConstantDecl=someEnum:58:3 [Context=] + +int main (int argc, const char * argv[]) { + Baz * bee; + id a = [bee foo]; + id c = [Foo fooC]; + id d; + d = c; + [d pMethod]; + [bee catMethodWithFloat:[bee floatMethod]]; + main(someEnum, (const char **)bee); +} + +// CHECK: c-index-api-test.m:83:5: FunctionDefn=main [Context=c-index-api-test.m] +// CHECK: c-index-api-test.m:83:15: ParmDecl=argc:83:15 [Context=main] +// CHECK: c-index-api-test.m:83:34: ParmDecl=argv:83:34 [Context=main] +// CHECK: c-index-api-test.m:84:8: VarDecl=bee:84:8 [Context=main] +// CHECK: c-index-api-test.m:85:5: VarDecl=a:85:5 [Context=main] +// CHECK: c-index-api-test.m:86:12: VarDecl=c:86:12 [Context=main] +// CHECK: c-index-api-test.m:87:13: VarDecl=d:87:13 [Context=main] +// CHECK: c-index-api-test.m:84:2: ObjCClassRef=Baz:84:8 [Context:Baz] +// CHECK: c-index-api-test.m:84:3: ObjCClassRef=Baz:84:8 [Context:Baz] +// CHECK: c-index-api-test.m:84:4: ObjCClassRef=Baz:84:8 [Context:Baz] +// CHECK: c-index-api-test.m:84:6: VarDecl=bee:84:8 [Context:bee] +// CHECK: c-index-api-test.m:84:8: VarDecl=bee:84:8 [Context:bee] +// CHECK: c-index-api-test.m:84:9: VarDecl=bee:84:8 [Context:bee] +// CHECK: c-index-api-test.m:84:10: VarDecl=bee:84:8 [Context:bee] +// CHECK: :85:2: TypedefDecl=id:0:0 [Context:id] +// CHECK: :85:3: TypedefDecl=id:0:0 [Context:id] +// CHECK: c-index-api-test.m:85:5: VarDecl=a:85:5 [Context:a] +// CHECK: c-index-api-test.m:85:6: VarDecl=a:85:5 [Context:a] +// CHECK: c-index-api-test.m:85:7: VarDecl=a:85:5 [Context:a] +// CHECK: c-index-api-test.m:85:8: VarDecl=a:85:5 [Context:a] +// CHECK: c-index-api-test.m:85:9: ObjCSelectorRef=foo:24:1 [Context:a] +// CHECK: c-index-api-test.m:85:10: VarRef=bee:84:8 [Context:a] +// CHECK: c-index-api-test.m:85:11: VarRef=bee:84:8 [Context:a] +// CHECK: c-index-api-test.m:85:12: VarRef=bee:84:8 [Context:a] +// CHECK: c-index-api-test.m:85:13: ObjCSelectorRef=foo:24:1 [Context:a] +// CHECK: c-index-api-test.m:85:14: ObjCSelectorRef=foo:24:1 [Context:a] +// CHECK: c-index-api-test.m:85:15: ObjCSelectorRef=foo:24:1 [Context:a] +// CHECK: c-index-api-test.m:85:16: ObjCSelectorRef=foo:24:1 [Context:a] +// CHECK: c-index-api-test.m:85:17: ObjCSelectorRef=foo:24:1 [Context:a] +// CHECK: :86:2: TypedefDecl=id:0:0 [Context:id] +// CHECK: :86:3: TypedefDecl=id:0:0 [Context:id] +// CHECK: c-index-api-test.m:86:5: VarDecl=c:86:12 [Context:c] +// CHECK: c-index-api-test.m:86:6: ObjCProtocolRef=SubP:86:12 [Context:SubP] +// CHECK: c-index-api-test.m:86:7: ObjCProtocolRef=SubP:86:12 [Context:SubP] +// CHECK: c-index-api-test.m:86:8: ObjCProtocolRef=SubP:86:12 [Context:SubP] +// CHECK: c-index-api-test.m:86:9: ObjCProtocolRef=SubP:86:12 [Context:SubP] +// CHECK: c-index-api-test.m:86:10: VarDecl=c:86:12 [Context:c] +// CHECK: c-index-api-test.m:86:12: VarDecl=c:86:12 [Context:c] +// CHECK: c-index-api-test.m:86:13: VarDecl=c:86:12 [Context:c] +// CHECK: c-index-api-test.m:86:14: VarDecl=c:86:12 [Context:c] +// CHECK: c-index-api-test.m:86:15: VarDecl=c:86:12 [Context:c] +// CHECK: c-index-api-test.m:86:16: ObjCSelectorRef=fooC:25:1 [Context:c] +// CHECK: c-index-api-test.m:86:17: ObjCSelectorRef=fooC:25:1 [Context:c] +// CHECK: c-index-api-test.m:86:18: ObjCSelectorRef=fooC:25:1 [Context:c] +// CHECK: c-index-api-test.m:86:19: ObjCSelectorRef=fooC:25:1 [Context:c] +// CHECK: c-index-api-test.m:86:20: ObjCSelectorRef=fooC:25:1 [Context:c] +// CHECK: c-index-api-test.m:86:21: ObjCSelectorRef=fooC:25:1 [Context:c] +// CHECK: c-index-api-test.m:86:22: ObjCSelectorRef=fooC:25:1 [Context:c] +// CHECK: c-index-api-test.m:86:23: ObjCSelectorRef=fooC:25:1 [Context:c] +// CHECK: c-index-api-test.m:86:24: ObjCSelectorRef=fooC:25:1 [Context:c] +// CHECK: c-index-api-test.m:86:25: ObjCSelectorRef=fooC:25:1 [Context:c] +// CHECK: :87:2: TypedefDecl=id:0:0 [Context:id] +// CHECK: :87:3: TypedefDecl=id:0:0 [Context:id] +// CHECK: c-index-api-test.m:87:5: VarDecl=d:87:13 [Context:d] +// CHECK: c-index-api-test.m:87:6: ObjCProtocolRef=Proto:87:13 [Context:Proto] +// CHECK: c-index-api-test.m:87:7: ObjCProtocolRef=Proto:87:13 [Context:Proto] +// CHECK: c-index-api-test.m:87:8: ObjCProtocolRef=Proto:87:13 [Context:Proto] +// CHECK: c-index-api-test.m:87:9: ObjCProtocolRef=Proto:87:13 [Context:Proto] +// CHECK: c-index-api-test.m:87:10: ObjCProtocolRef=Proto:87:13 [Context:Proto] +// CHECK: c-index-api-test.m:87:11: VarDecl=d:87:13 [Context:d] +// CHECK: c-index-api-test.m:87:13: VarDecl=d:87:13 [Context:d] +// CHECK: c-index-api-test.m:88:2: VarRef=d:87:13 [Context:main] +// CHECK: c-index-api-test.m:88:6: VarRef=c:86:12 [Context:main] +// CHECK: c-index-api-test.m:89:2: ObjCSelectorRef=pMethod:41:1 [Context:main] +// CHECK: c-index-api-test.m:89:3: VarRef=d:87:13 [Context:main] +// CHECK: c-index-api-test.m:89:4: ObjCSelectorRef=pMethod:41:1 [Context:main] +// CHECK: c-index-api-test.m:89:5: ObjCSelectorRef=pMethod:41:1 [Context:main] +// CHECK: c-index-api-test.m:89:6: ObjCSelectorRef=pMethod:41:1 [Context:main] +// CHECK: c-index-api-test.m:89:7: ObjCSelectorRef=pMethod:41:1 [Context:main] +// CHECK: c-index-api-test.m:89:8: ObjCSelectorRef=pMethod:41:1 [Context:main] +// CHECK: c-index-api-test.m:89:9: ObjCSelectorRef=pMethod:41:1 [Context:main] +// CHECK: c-index-api-test.m:89:10: ObjCSelectorRef=pMethod:41:1 [Context:main] +// CHECK: c-index-api-test.m:89:11: ObjCSelectorRef=pMethod:41:1 [Context:main] +// CHECK: c-index-api-test.m:89:12: ObjCSelectorRef=pMethod:41:1 [Context:main] +// CHECK: c-index-api-test.m:90:2: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:3: VarRef=bee:84:8 [Context:main] +// CHECK: c-index-api-test.m:90:4: VarRef=bee:84:8 [Context:main] +// CHECK: c-index-api-test.m:90:5: VarRef=bee:84:8 [Context:main] +// CHECK: c-index-api-test.m:90:6: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:7: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:8: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:9: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:10: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:11: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:12: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:13: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:14: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:15: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:16: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:17: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:18: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:19: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:20: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:21: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:22: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:23: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:24: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:25: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:90:26: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:27: VarRef=bee:84:8 [Context:main] +// CHECK: c-index-api-test.m:90:28: VarRef=bee:84:8 [Context:main] +// CHECK: c-index-api-test.m:90:29: VarRef=bee:84:8 [Context:main] +// CHECK: c-index-api-test.m:90:30: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:31: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:32: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:33: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:34: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:35: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:36: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:37: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:38: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:39: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:40: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:41: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:42: ObjCSelectorRef=floatMethod:37:1 [Context:main] +// CHECK: c-index-api-test.m:90:43: ObjCSelectorRef=catMethodWithFloat::36:1 [Context:main] +// CHECK: c-index-api-test.m:91:3: FunctionRef=main:83:5 [Context:main] +// CHECK: c-index-api-test.m:91:4: FunctionRef=main:83:5 [Context:main] +// CHECK: c-index-api-test.m:91:5: FunctionRef=main:83:5 [Context:main] +// CHECK: c-index-api-test.m:91:6: FunctionRef=main:83:5 [Context:main] +// CHECK: c-index-api-test.m:91:8: EnumConstantRef=someEnum:58:3 [Context:main] +// CHECK: c-index-api-test.m:91:9: EnumConstantRef=someEnum:58:3 [Context:main] +// CHECK: c-index-api-test.m:91:10: EnumConstantRef=someEnum:58:3 [Context:main] +// CHECK: c-index-api-test.m:91:11: EnumConstantRef=someEnum:58:3 [Context:main] +// CHECK: c-index-api-test.m:91:12: EnumConstantRef=someEnum:58:3 [Context:main] +// CHECK: c-index-api-test.m:91:13: EnumConstantRef=someEnum:58:3 [Context:main] +// CHECK: c-index-api-test.m:91:14: EnumConstantRef=someEnum:58:3 [Context:main] +// CHECK: c-index-api-test.m:91:15: EnumConstantRef=someEnum:58:3 [Context:main] +// CHECK: c-index-api-test.m:91:33: VarRef=bee:84:8 [Context:main] +// CHECK: c-index-api-test.m:91:34: VarRef=bee:84:8 [Context:main] +// CHECK: c-index-api-test.m:91:35: VarRef=bee:84:8 [Context:main] diff --git a/test/Index/comments.c b/test/Index/comments.c index 7ad8fd7..689ce88 100644 --- a/test/Index/comments.c +++ b/test/Index/comments.c @@ -1,15 +1,4 @@ -// RUN: clang-cc -emit-pch -o %t.ast %s && -// RUN: index-test %t.ast -point-at %s:22:6 | grep "starts here" && -// RUN: index-test %t.ast -point-at %s:22:6 | grep "block comment" && -// RUN: index-test %t.ast -point-at %s:28:6 | grep "BCPL" && -// RUN: index-test %t.ast -point-at %s:28:6 | grep "But" && -// RUN: index-test %t.ast -point-at %s:28:6 | grep "NOT" | count 0 && -// RUN: index-test %t.ast -point-at %s:30:6 | grep "member" - - - - - +// Run lines are sensitive to line numbers and come below the code. //! It all starts here. /*! It's a little odd to continue line this, @@ -27,4 +16,19 @@ void f(int, int); /** But there are other blocks that are part of the comment, too. */ void g(int); -void h(int); ///< This is a member comment. \ No newline at end of file +void h(int); ///< This is a member comment. + + +// RUN: clang-cc -emit-pch -o %t.ast %s && + +// RUN: index-test %t.ast -point-at %s:11:6 > %t && +// RUN: grep "starts here" %t && +// RUN: grep "block comment" %t && + +// RUN: index-test %t.ast -point-at %s:17:6 > %t && +// RUN: grep "BCPL" %t && +// RUN: grep "But" %t && + +// RUN: index-test %t.ast -point-at %s:19:6 > %t && +// RUN: grep "NOT" %t | count 0 && +// RUN: grep "member" %t diff --git a/test/Index/cxx-operator-overload.cpp b/test/Index/cxx-operator-overload.cpp new file mode 100644 index 0000000..9bda03e --- /dev/null +++ b/test/Index/cxx-operator-overload.cpp @@ -0,0 +1,28 @@ +// Run lines are sensitive to line numbers and come below the code. +// FIXME: re-enable this when we can serialize more C++ ASTs +class Cls { +public: + Cls operator +(const Cls &RHS); +}; + +static void bar() { + Cls x1, x2, x3; + Cls x4 = x1 + x2 + x3; +} + +Cls Cls::operator +(const Cls &RHS) { while (1) {} } + +// RUN: clang-cc -emit-pch %s -o %t.ast + +// RUNx: index-test %t.ast -point-at %s:10:17 -print-decls > %t && +// RUNx: cat %t | count 2 && +// RUNx: grep ':5:9,' %t && +// RUNx: grep ':13:10,' %t && + +// Yep, we can show references of '+' plus signs that are overloaded, w00t! +// RUNx: index-test %t.ast -point-at %s:5:15 -print-refs > %t && +// RUNx: cat %t | count 2 && +// RUNx: grep ':10:17,' %t && +// RUNx: grep ':10:22,' %t && + +// RUNx: index-test %t.ast -point-at %s:10:14 | grep 'DeclRefExpr x1' diff --git a/test/Index/find-decls.c b/test/Index/find-decls.c new file mode 100644 index 0000000..50a233d --- /dev/null +++ b/test/Index/find-decls.c @@ -0,0 +1,25 @@ +// RUN: clang-cc -fblocks -emit-pch %S/t1.c -o %t1.ast && +// RUN: clang-cc -fblocks -emit-pch %S/t2.c -o %t2.ast && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/t1.c:8:7 -print-decls > %t && +// RUN: cat %t | count 3 && +// RUN: grep 'foo.h:4:6,' %t | count 2 && +// RUN: grep 't2.c:5:6,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/t1.c:5:47 -print-decls > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't1.c:5:12,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/t1.c:6:20 -print-decls > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't1.c:3:19,' %t && + +// field test + +// RUN: index-test %t1.ast %t2.ast -point-at %S/t1.c:21:6 -print-decls > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't1.c:12:7,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/t1.c:22:21 -print-decls > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't1.c:16:7,' %t diff --git a/test/Index/find-defs.c b/test/Index/find-defs.c new file mode 100644 index 0000000..0e63ae7 --- /dev/null +++ b/test/Index/find-defs.c @@ -0,0 +1,18 @@ +// RUN: clang-cc -fblocks -emit-pch %S/t1.c -o %t1.ast && +// RUN: clang-cc -fblocks -emit-pch %S/t2.c -o %t2.ast && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/foo.h:1:14 -print-defs > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't2.c:3:5,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/foo.h:3:9 -print-defs > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't1.c:3:6,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/foo.h:4:9 -print-defs > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't2.c:5:6,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/t1.c:8:7 -print-defs > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't2.c:5:6,' %t diff --git a/test/Index/find-refs.c b/test/Index/find-refs.c new file mode 100644 index 0000000..1b58b37 --- /dev/null +++ b/test/Index/find-refs.c @@ -0,0 +1,47 @@ +// RUN: clang-cc -fblocks -emit-pch %S/t1.c -o %t1.ast && +// RUN: clang-cc -fblocks -emit-pch %S/t2.c -o %t2.ast && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/foo.h:1:14 -print-refs > %t && +// RUN: cat %t | count 4 && +// RUN: grep 't1.c:4:19,' %t && +// RUN: grep 't1.c:28:40,' %t && +// RUN: grep 't2.c:6:3,' %t && +// RUN: grep 't2.c:7:12,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/foo.h:3:9 -print-refs > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't2.c:7:3,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/foo.h:4:9 -print-refs > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't1.c:8:3,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/t1.c:3:22 -print-refs > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't1.c:6:17,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/t1.c:4:11 -print-refs > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't1.c:6:5,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/t1.c:5:30 -print-refs > %t && +// RUN: cat %t | count 3 && +// RUN: grep 't1.c:5:27,' %t && +// RUN: grep 't1.c:5:44,' %t && +// RUN: grep 't1.c:6:26,' %t && + +// field test + +// FIXME: References point at the start of MemberExpr, make them point at the field instead. +// RUN: index-test %t1.ast %t2.ast -point-at %S/t1.c:12:7 -print-refs > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't1.c:21:3,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/t1.c:16:7 -print-refs > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't1.c:22:3,' %t && + +// RUN: index-test %t1.ast %t2.ast -point-at %S/foo.h:7:11 -print-refs > %t && +// RUN: cat %t | count 2 && +// RUN: grep 't1.c:25:3,' %t && +// RUN: grep 't2.c:10:3,' %t diff --git a/test/Index/foo.h b/test/Index/foo.h new file mode 100644 index 0000000..7670c00 --- /dev/null +++ b/test/Index/foo.h @@ -0,0 +1,8 @@ +extern int global_var; + +void foo_func(int param1); +void bar_func(void); + +struct MyStruct { + int field_var; +}; diff --git a/test/Index/multiple-redecls.c b/test/Index/multiple-redecls.c new file mode 100644 index 0000000..6f1f75b --- /dev/null +++ b/test/Index/multiple-redecls.c @@ -0,0 +1,12 @@ +// RUN: clang-cc -emit-pch %s -o %t.ast && +// RUN: index-test %t.ast -point-at %s:8:4 -print-decls | count 2 && +// RUN: index-test %t.ast -point-at %s:8:4 -print-defs | count 1 + +static void foo(int x); + +static void bar(void) { + foo(10); +} + +void foo(int x) { +} diff --git a/test/Index/objc-decls.m b/test/Index/objc-decls.m new file mode 100644 index 0000000..1a8ab4b --- /dev/null +++ b/test/Index/objc-decls.m @@ -0,0 +1,16 @@ +// RUN: clang-cc -emit-pch %S/t1.m -o %t1.m.ast && +// RUN: clang-cc -emit-pch %S/t2.m -o %t2.m.ast && + +// RUN: index-test %t1.m.ast %t2.m.ast -point-at %S/t1.m:12:12 -print-decls > %t && +// RUN: cat %t | count 2 && +// RUN: grep 'objc.h:2:9,' %t | count 2 && + +// RUN: index-test %t1.m.ast %t2.m.ast -point-at %S/objc.h:5:13 -print-decls > %t && +// RUN: cat %t | count 3 && +// RUN: grep 'objc.h:5:1,' %t | count 2 && +// RUN: grep 't1.m:15:1,' %t | count 1 && + +// RUN: index-test %t1.m.ast %t2.m.ast -point-at %S/objc.h:10:13 -print-decls > %t && +// RUN: cat %t | count 3 && +// RUN: grep 'objc.h:10:1,' %t | count 2 && +// RUN: grep 't2.m:11:1,' %t | count 1 diff --git a/test/Index/objc-message.m b/test/Index/objc-message.m new file mode 100644 index 0000000..45ce838 --- /dev/null +++ b/test/Index/objc-message.m @@ -0,0 +1,38 @@ +// RUN: clang-cc -emit-pch %S/t1.m -o %t1.m.ast && +// RUN: clang-cc -emit-pch %S/t2.m -o %t2.m.ast && + +// RUN: index-test %t1.m.ast %t2.m.ast -point-at %S/objc.h:5:13 -print-refs > %t && +// RUN: cat %t | count 1 && +// RUN: grep 't1.m:6:3,' %t && + +// RUN: index-test %t1.m.ast %t2.m.ast -point-at %S/objc.h:6:13 -print-refs > %t && +// RUN: cat %t | count 2 && +// RUN: grep 't1.m:7:3,' %t && +// RUN: grep 't2.m:7:3,' %t && + +// RUN: index-test %t1.m.ast %t2.m.ast -point-at %S/objc.h:10:13 -print-refs > %t && +// RUN: cat %t | count 2 && +// RUN: grep 't1.m:6:3,' %t && +// RUN: grep 't2.m:6:3,' %t && + +// RUN: index-test %t1.m.ast %t2.m.ast -point-at %S/t1.m:6:15 -print-decls > %t && +// RUN: cat %t | count 6 && +// RUN: grep 'objc.h:5:1,' %t | count 2 && +// RUN: grep 'objc.h:10:1,' %t | count 2 && +// RUN: grep 't1.m:15:1,' %t && +// RUN: grep 't2.m:11:1,' %t && + +// RUN: index-test %t1.m.ast %t2.m.ast -point-at %S/t1.m:7:15 -print-decls > %t && +// RUN: cat %t | count 3 && +// RUN: grep 'objc.h:6:1,' %t | count 2 && +// RUN: grep 't1.m:18:1,' %t && + +// RUN: index-test %t2.m.ast %t1.m.ast -point-at %S/t2.m:6:15 -print-decls > %t && +// RUN: cat %t | count 3 && +// RUN: grep 'objc.h:10:1,' %t | count 2 && +// RUN: grep 't2.m:11:1,' %t && + +// RUN: index-test %t2.m.ast %t1.m.ast -point-at %S/t2.m:7:15 -print-decls > %t && +// RUN: cat %t | count 3 && +// RUN: grep 'objc.h:6:1,' %t | count 2 && +// RUN: grep 't1.m:18:1,' %t diff --git a/test/Index/objc.h b/test/Index/objc.h new file mode 100644 index 0000000..c671add --- /dev/null +++ b/test/Index/objc.h @@ -0,0 +1,11 @@ +@interface Base { + int my_var; +} +-(int) my_var; +-(void) my_method: (int)param; ++(void) my_method: (int)param; +@end + +@interface Sub : Base +-(void) my_method: (int)param; +@end diff --git a/test/Index/resolve-loc.c b/test/Index/resolve-loc.c index d04b79b..cae86f3 100644 --- a/test/Index/resolve-loc.c +++ b/test/Index/resolve-loc.c @@ -1,16 +1,4 @@ -// RUN: clang-cc -emit-pch %s -o %t.ast && -// RUN: index-test %t.ast -point-at %s:15:8 | grep top_var && -// RUN: index-test %t.ast -point-at %s:17:15 | grep top_func_decl && -// RUN: index-test %t.ast -point-at %s:17:25 | grep param1 && -// RUN: index-test %t.ast -point-at %s:19:17 | grep top_func_def && -// RUN: index-test %t.ast -point-at %s:19:23 | grep param2 && -// RUN: index-test %t.ast -point-at %s:20:10 | grep local_var1 && -// RUN: index-test %t.ast -point-at %s:21:15 | grep for_var && -// RUN: index-test %t.ast -point-at %s:21:43 | grep top_func_def && -// RUN: index-test %t.ast -point-at %s:21:43 | grep '++for_var' && -// RUN: index-test %t.ast -point-at %s:22:9 | grep local_var2 && -// RUN: index-test %t.ast -point-at %s:22:30 | grep local_var2 && -// RUN: index-test %t.ast -point-at %s:22:30 | grep 'for_var + 1' +// Run lines are sensitive to line numbers and come below the code. int top_var; @@ -22,3 +10,28 @@ void top_func_def(int param2) { int local_var2 = for_var + 1; } } + +struct S { + int field_var; +}; + + +// RUN: clang-cc -emit-pch %s -o %t.ast && +// RUN: index-test %t.ast -point-at %s:3:8 | grep top_var && +// RUN: index-test %t.ast -point-at %s:5:15 | grep top_func_decl && +// RUN: index-test %t.ast -point-at %s:5:25 | grep param1 && +// RUN: index-test %t.ast -point-at %s:7:17 | grep top_func_def && +// RUN: index-test %t.ast -point-at %s:7:23 | grep param2 && +// RUN: index-test %t.ast -point-at %s:8:10 | grep local_var1 && +// RUN: index-test %t.ast -point-at %s:9:15 | grep for_var && + +// RUN: index-test %t.ast -point-at %s:9:43 > %t && +// RUN: grep '++for_var' %t && + +// RUN: index-test %t.ast -point-at %s:10:9 | grep local_var2 && + +// RUN: index-test %t.ast -point-at %s:10:30 > %t && +// RUN: grep 'for_var + 1' %t && + +// fields test. +// RUN: index-test %t.ast -point-at %s:15:10 | grep field_var diff --git a/test/Index/t1.c b/test/Index/t1.c new file mode 100644 index 0000000..45e0488 --- /dev/null +++ b/test/Index/t1.c @@ -0,0 +1,31 @@ +#include "foo.h" + +void foo_func(int param1) { + int local_var = global_var; + for (int for_var = 100; for_var < 500; ++for_var) { + local_var = param1 + for_var; + } + bar_func(); +} + +struct S1 { + int x; +}; + +struct S2 { + int x; +}; + +void field_test(void) { + struct S1 s1; + s1.x = 0; + ((struct S2 *)0)->x = 0; + + struct MyStruct ms; + ms.field_var = 10; +} + +int (^CP)(int) = ^(int x) { return x * global_var; }; + +// Suppress 'no run line' failure. +// RUN: true diff --git a/test/Index/t1.m b/test/Index/t1.m new file mode 100644 index 0000000..b2a7a37 --- /dev/null +++ b/test/Index/t1.m @@ -0,0 +1,23 @@ +#include "objc.h" + +static void foo() { + Base *base; + int x = [base my_var]; + [base my_method:x]; + [Base my_method:x]; +} + +@implementation Base +-(int) my_var { + return my_var; +} + +-(void) my_method: (int)param { +} + ++(void) my_method: (int)param { +} +@end + +// Suppress 'no run line' failure. +// RUN: true diff --git a/test/Index/t2.c b/test/Index/t2.c new file mode 100644 index 0000000..bf52869 --- /dev/null +++ b/test/Index/t2.c @@ -0,0 +1,14 @@ +#include "foo.h" + +int global_var = 10; + +void bar_func(void) { + global_var += 100; + foo_func(global_var); + + struct MyStruct *ms; + ms->field_var = 10; +} + +// Suppress 'no run line' failure. +// RUN: true diff --git a/test/Index/t2.m b/test/Index/t2.m new file mode 100644 index 0000000..00d2f1d --- /dev/null +++ b/test/Index/t2.m @@ -0,0 +1,16 @@ +#include "objc.h" + +static void foo() { + Sub *sub; + int x = [sub my_var]; + [sub my_method:x]; + [Sub my_method:x]; +} + +@implementation Sub +-(void) my_method: (int)param { +} +@end + +// Suppress 'no run line' failure. +// RUN: true diff --git a/test/Lexer/11-27-2007-FloatLiterals.c b/test/Lexer/11-27-2007-FloatLiterals.c index f3ea7cb..ab3aba1 100644 --- a/test/Lexer/11-27-2007-FloatLiterals.c +++ b/test/Lexer/11-27-2007-FloatLiterals.c @@ -1,5 +1,9 @@ -// RUN: clang-cc %s -emit-llvm -o - | grep 0x3BFD83C940000000 | count 2 && -// RUN: clang-cc %s -emit-llvm -o - | grep 2.000000e+32 | count 2 +// RUN: clang-cc %s -emit-llvm -o - | FileCheck %s + +// CHECK: 0x3BFD83C940000000 +// CHECK: 2.000000e+{{[0]*}}32 +// CHECK: 0x3BFD83C940000000 +// CHECK: 2.000000e+{{[0]*}}32 float F = 1e-19f; double D = 2e32; diff --git a/test/Lexer/comment-escape.c b/test/Lexer/comment-escape.c index c568cd6..c461457 100644 --- a/test/Lexer/comment-escape.c +++ b/test/Lexer/comment-escape.c @@ -2,5 +2,5 @@ // rdar://6757323 // foo \ -#define blork 32 +#define blork 32 diff --git a/test/Lexer/dollar-idents.c b/test/Lexer/dollar-idents.c index 7635ea1..f5c33b1 100644 --- a/test/Lexer/dollar-idents.c +++ b/test/Lexer/dollar-idents.c @@ -1,5 +1,5 @@ // RUN: clang-cc -dump-tokens %s 2> %t && -// RUN: grep "identifier '\$A'" %t +// RUN: grep "identifier '\$A'" %t && // RUN: clang-cc -dump-tokens -x assembler-with-cpp %s 2> %t && // RUN: grep "identifier 'A'" %t // PR3808 diff --git a/test/Makefile b/test/Makefile index 271f46f..8543d43 100644 --- a/test/Makefile +++ b/test/Makefile @@ -2,7 +2,14 @@ LEVEL = ../../.. include $(LEVEL)/Makefile.common # Test in all immediate subdirectories if unset. -TESTDIRS ?= $(shell echo $(PROJ_SRC_DIR)/*/) +ifdef TESTSUITE +TESTDIRS := $(TESTSUITE:%=$(PROJ_SRC_DIR)/%) +else +TESTDIRS ?= $(PROJ_SRC_DIR) +endif + +# 'lit' wants objdir paths, so it will pick up the lit.site.cfg. +TESTDIRS := $(TESTDIRS:$(PROJ_SRC_DIR)%=$(PROJ_OBJ_DIR)%) ifndef TESTARGS ifdef VERBOSE @@ -12,9 +19,28 @@ TESTARGS = -s endif endif -all:: +ifdef VG + VGARG="--vg" +else + VGARG= +endif + +all:: lit.site.cfg @ echo '--- Running clang tests for $(TARGET_TRIPLE) ---' - @ PATH=$(ToolDir):$(LLVM_SRC_ROOT)/test/Scripts:$$PATH VG=$(VG) ../utils/test/MultiTestRunner.py $(TESTARGS) $(TESTDIRS) + @ $(PYTHON) $(LLVM_SRC_ROOT)/utils/lit/lit.py \ + $(TESTARGS) $(TESTDIRS) $(VGARG) + +FORCE: + +lit.site.cfg: FORCE + @echo "Making Clang 'lit.site.cfg' file..." + @sed -e "s#@LLVM_SOURCE_DIR@#$(LLVM_SRC_ROOT)#g" \ + -e "s#@LLVM_BINARY_DIR@#$(LLVM_OBJ_ROOT)#g" \ + -e "s#@LLVM_TOOLS_DIR@#$(ToolDir)#g" \ + -e "s#@LLVM_LIBS_DIR@#$(LibDir)#g" \ + -e "s#@CLANG_SOURCE_DIR@#$(PROJ_SRC_DIR)/..#g" \ + -e "s#@CLANG_BINARY_DIR@#$(PROJ_OBJ_DIR)/..#g" \ + $(PROJ_SRC_DIR)/lit.site.cfg.in > $@ clean:: @ rm -rf Output/ diff --git a/test/Misc/diag-mapping2.c b/test/Misc/diag-mapping2.c index 7e0d774..c5fd7ff 100644 --- a/test/Misc/diag-mapping2.c +++ b/test/Misc/diag-mapping2.c @@ -12,7 +12,10 @@ // RUN: clang-cc %s -Werror=#warnings 2>&1 | grep "error:" && // -Wno-error= overrides -Werror. rdar://3158301 -// RUN: clang-cc %s -Werror -Wno-error=#warnings 2>&1 | grep "warning:" +// RUN: clang-cc %s -Werror -Wno-error=#warnings 2>&1 | grep "warning:" && + +// -Wno-error overrides -Werror. PR4715 +// RUN: clang-cc %s -Werror -Wno-error 2>&1 | grep "warning:" #warning foo diff --git a/test/PCH/cxx-method.cpp b/test/PCH/cxx-method.cpp new file mode 100644 index 0000000..144406e --- /dev/null +++ b/test/PCH/cxx-method.cpp @@ -0,0 +1,7 @@ +// RUN: clang-cc -emit-pch %s -o %t + +struct S { + void m(int x); +}; + +void S::m(int x) { } diff --git a/test/PCH/libroot/usr/include/reloc.h b/test/PCH/libroot/usr/include/reloc.h new file mode 100644 index 0000000..04eeacb --- /dev/null +++ b/test/PCH/libroot/usr/include/reloc.h @@ -0,0 +1,15 @@ +#ifndef RELOC_H +#define RELOC_H + +#include + + + + + + + +// Line number 13 below is important +int x = 2; + +#endif // RELOC_H diff --git a/test/PCH/libroot/usr/include/reloc2.h b/test/PCH/libroot/usr/include/reloc2.h new file mode 100644 index 0000000..995415c --- /dev/null +++ b/test/PCH/libroot/usr/include/reloc2.h @@ -0,0 +1,15 @@ +#ifndef RELOC2_H +#define RELOC2_H +#include + + + + + + + + + +// Line number below is important! +int y = 2; +#endif // RELOC2_H diff --git a/test/PCH/method_pool.h b/test/PCH/method_pool.h index f7af904..8085836 100644 --- a/test/PCH/method_pool.h +++ b/test/PCH/method_pool.h @@ -22,8 +22,7 @@ @end @implementation TestMethodPool1 -+ alloc { -} ++ alloc { return 0; } - (double)instMethod:(int)foo { return foo; diff --git a/test/PCH/objc_exprs.m b/test/PCH/objc_exprs.m index eb1ae43..48966f3 100644 --- a/test/PCH/objc_exprs.m +++ b/test/PCH/objc_exprs.m @@ -6,7 +6,7 @@ // RUN: clang-cc -fblocks -include-pch %t -fsyntax-only -verify %s // Expressions -int *A1 = (objc_string)0; // expected-warning {{'struct objc_object *'}} +int *A1 = (objc_string)0; // expected-warning {{aka 'id'}} char A2 = (objc_encode){}; // expected-error {{not a compile-time constant}} \ expected-warning {{char [2]}} @@ -15,8 +15,7 @@ int *A3 = (objc_protocol)0; // expected-warning {{aka 'Protocol *'}} // Types. -int *T0 = (objc_id_protocol_ty)0; // expected-error {{not a compile-time constant}} \ - expected-warning {{aka 'id'}} +int *T0 = (objc_id_protocol_ty)0; // expected-warning {{aka 'id'}} int *T1 = (objc_interface_ty)0; // expected-warning {{aka 'itf *'}} int *T2 = (objc_qual_interface_ty)0; // expected-warning {{aka 'itf *'}} diff --git a/test/PCH/pr4489.c b/test/PCH/pr4489.c index 696da5b..7730819 100644 --- a/test/PCH/pr4489.c +++ b/test/PCH/pr4489.c @@ -1,7 +1,8 @@ // RUN: clang -x c-header -o %t.pch %s && // RUN: clang -include %t -x c /dev/null -emit-llvm -S -o - // PR 4489: Crash with PCH - +// PR 4492: Crash with PCH (round two) +// PR 4509: Crash with PCH (round three) typedef struct _IO_FILE FILE; extern int fprintf (struct _IO_FILE *__restrict __stream, __const char *__restrict __format, ...); @@ -17,4 +18,23 @@ int x(void) void y(void) { extern char z; fprintf (0, "a"); +} + +struct y0 { int i; } y0[1] = {}; + +void x0(void) +{ + extern char z0; + fprintf (0, "a"); +} + +void x1(void) +{ + fprintf (0, "asdf"); +} + +void y1(void) +{ + extern char e; + fprintf (0, "asdf"); } \ No newline at end of file diff --git a/test/PCH/reloc.c b/test/PCH/reloc.c new file mode 100644 index 0000000..b08187f --- /dev/null +++ b/test/PCH/reloc.c @@ -0,0 +1,14 @@ +// RUN: clang-cc -emit-pch -o %t --relocatable-pch -isysroot %S/libroot %S/libroot/usr/include/reloc.h && +// RUN: clang-cc -include-pch %t -isysroot %S/libroot %s -verify && +// RUN: not clang-cc -include-pch %t %s + +#include + +int x = 2; // expected-error{{redefinition}} +int y = 5; // expected-error{{redefinition}} + + + + +// expected-note{{previous definition}} +// expected-note{{previous definition}} diff --git a/test/Parser/CompoundStmtScope.c b/test/Parser/CompoundStmtScope.c index 6a404aa..90e3d24 100644 --- a/test/Parser/CompoundStmtScope.c +++ b/test/Parser/CompoundStmtScope.c @@ -1,6 +1,6 @@ // RUN: clang-cc -fsyntax-only -verify %s -int foo() { +void foo() { { typedef float X; } diff --git a/test/Parser/MicrosoftExtensions.c b/test/Parser/MicrosoftExtensions.c index 6f5622e..572ac44 100644 --- a/test/Parser/MicrosoftExtensions.c +++ b/test/Parser/MicrosoftExtensions.c @@ -9,22 +9,22 @@ __declspec(noalias) __declspec(restrict) void * __cdecl xxx( void * _Memory ); typedef __w64 unsigned long ULONG_PTR, *PULONG_PTR; void * __ptr64 PtrToPtr64(const void *p) { - return((void * __ptr64) (unsigned __int64) (ULONG_PTR)p ); + return((void * __ptr64) (unsigned __int64) (ULONG_PTR)p ); } -__forceinline InterlockedBitTestAndSet (long *Base, long Bit) // expected-warning {{type specifier missing, defaults to 'int'}} +void __forceinline InterlockedBitTestAndSet (long *Base, long Bit) { - __asm { - mov eax, Bit - mov ecx, Base - lock bts [ecx], eax - setc al - }; + __asm { + mov eax, Bit + mov ecx, Base + lock bts [ecx], eax + setc al + }; } void *_alloca(int); void foo() { - __declspec(align(16)) int *buffer = (int *)_alloca(9); + __declspec(align(16)) int *buffer = (int *)_alloca(9); } typedef bool (__stdcall __stdcall *blarg)(int); diff --git a/test/Parser/argument_redef.c b/test/Parser/argument_redef.c index 1a43178..fd22c46 100644 --- a/test/Parser/argument_redef.c +++ b/test/Parser/argument_redef.c @@ -1,6 +1,6 @@ /* RUN: clang-cc -fsyntax-only -verify %s */ -int foo(int A) { /* expected-note {{previous definition is here}} */ +void foo(int A) { /* expected-note {{previous definition is here}} */ int A; /* expected-error {{redefinition of 'A'}} */ } diff --git a/test/Parser/bad-control.c b/test/Parser/bad-control.c index 6e59667..0bdd179 100644 --- a/test/Parser/bad-control.c +++ b/test/Parser/bad-control.c @@ -1,9 +1,9 @@ /* RUN: clang-cc -fsyntax-only -verify %s */ -int foo() { +void foo() { break; /* expected-error {{'break' statement not in loop or switch statement}} */ } -int foo2() { +void foo2() { continue; /* expected-error {{'continue' statement not in loop statement}} */ } diff --git a/test/Parser/cxx-ambig-paren-expr.cpp b/test/Parser/cxx-ambig-paren-expr.cpp index 1712d84..324f6b5 100644 --- a/test/Parser/cxx-ambig-paren-expr.cpp +++ b/test/Parser/cxx-ambig-paren-expr.cpp @@ -5,9 +5,9 @@ void f() { int x, *px; // Type id. - (T())x; // expected-error {{used type 'T ()'}} - (T())+x; // expected-error {{used type 'T ()'}} - (T())*px; // expected-error {{used type 'T ()'}} + (T())x; // expected-error {{cast from 'int' to 'T ()'}} + (T())+x; // expected-error {{cast from 'int' to 'T ()'}} + (T())*px; // expected-error {{cast from 'int' to 'T ()'}} // Expression. x = (T()); diff --git a/test/Parser/cxx-friend.cpp b/test/Parser/cxx-friend.cpp index ea30ddc..14b31af 100644 --- a/test/Parser/cxx-friend.cpp +++ b/test/Parser/cxx-friend.cpp @@ -1,4 +1,4 @@ -// RUN: clang-cc -fsyntax-only %s +// RUN: clang-cc -fsyntax-only -verify %s class C { friend class D; @@ -6,12 +6,27 @@ class C { class A { public: - void f(); + void f(); +}; + +friend int x; // expected-error {{'friend' used outside of class}} + +friend class D {}; // expected-error {{'friend' used outside of class}} + +union U { + int u1; }; class B { // 'A' here should refer to the declaration above. friend class A; - void f(A *a) { a->f(); } + friend C; // expected-error {{must specify 'class' to befriend}} + friend U; // expected-error {{must specify 'union' to befriend}} + friend int; // expected-error {{friends can only be classes or functions}} + + friend void myfunc(); + + void f(A *a) { a->f(); } }; + diff --git a/test/Parser/cxx-member-initializers.cpp b/test/Parser/cxx-member-initializers.cpp new file mode 100644 index 0000000..bebb5c5 --- /dev/null +++ b/test/Parser/cxx-member-initializers.cpp @@ -0,0 +1,10 @@ +// RUN: clang-cc -fsyntax-only -verify %s + +struct x { + x() : a(4) ; // expected-error {{expected '{'}} +}; + +struct y { + int a; + y() : a(4) ; // expected-error {{expected '{'}} +}; diff --git a/test/Parser/cxx-template-decl.cpp b/test/Parser/cxx-template-decl.cpp index 6955018..9309b72 100644 --- a/test/Parser/cxx-template-decl.cpp +++ b/test/Parser/cxx-template-decl.cpp @@ -2,16 +2,17 @@ // Errors export class foo { }; // expected-error {{expected template}} -template x; // expected-error {{C++ requires a type specifier for all declarations}} -export template x; // expected-error {{expected '<' after 'template'}} \ - // expected-note {{exported templates are unsupported}} \ -// expected-error {{C++ requires a type specifier for all declarations}} -// See Sema::ParsedFreeStandingDeclSpec about the double diagnostic. This is -// because ParseNonTypeTemplateParameter starts parsing a DeclSpec. +template x; // expected-error {{C++ requires a type specifier for all declarations}} \ + // expected-error {{does not refer}} +export template x; // expected-error {{expected '<' after 'template'}} +export template class x0; // expected-note {{exported templates are unsupported}} template < ; // expected-error {{parse error}} expected-error {{declaration does not declare anything}} -template