llvm.org GIT mirror llvm / 7c82e6a
More replacing of target-dependent intrinsics with target-indepdent intrinsics. The second instruction(s) to be handled are the vector versions of count set bits (ctpop). The changes here are to clang so that it generates a target independent vector ctpop when it sees an ARM dependent vector bits set count. The changes in llvm are to match the target independent vector ctpop and in VMCore/AutoUpgrade.cpp to update any existing bc files containing ARM dependent vector pop counts with target-independent ctpops. There are also changes to an existing test case in llvm for ARM vector count instructions and to a test for the bitcode upgrade. <rdar://problem/11892519> There is deliberately no test for the change to clang, as so far as I know, no consensus has been reached regarding how to test neon instructions in clang; q.v. <rdar://problem/8762292> git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@160410 91177308-0d34-0410-b5e6-96231b3b80d8 Joel Jones 8 years ago
4 changed file(s) with 29 addition(s) and 10 deletion(s). Raw diff Collapse all Expand all
48284828 // VCNT : Vector Count One Bits
48294829 def VCNTd : N2VDInt<0b11, 0b11, 0b00, 0b00, 0b01010, 0,
48304830 IIC_VCNTiD, "vcnt", "8",
4831 v8i8, v8i8, int_arm_neon_vcnt>;
4831 v8i8, v8i8, ctpop>;
48324832 def VCNTq : N2VQInt<0b11, 0b11, 0b00, 0b00, 0b01010, 0,
48334833 IIC_VCNTiQ, "vcnt", "8",
4834 v16i8, v16i8, int_arm_neon_vcnt>;
4834 v16i8, v16i8, ctpop>;
48354835
48364836 // Vector Swap
48374837 def VSWPd : N2VX<0b11, 0b11, 0b00, 0b10, 0b00000, 0, 0,
6363 FunctionType* fType = FunctionType::get(F->getReturnType(), args, false);
6464 NewFn = Function::Create(fType, F->getLinkage(),
6565 "llvm.ctlz." + Name.substr(14), F->getParent());
66 return true;
67 }
68 if (Name.startswith("arm.neon.vcnt")) {
69 NewFn = Intrinsic::getDeclaration(F->getParent(), Intrinsic::ctpop,
70 F->arg_begin()->getType());
6671 return true;
6772 }
6873 break;
313318 case Intrinsic::arm_neon_vclz: {
314319 // Change name from llvm.arm.neon.vclz.* to llvm.ctlz.*
315320 CI->replaceAllUsesWith(Builder.CreateCall2(NewFn, CI->getArgOperand(0),
316 Builder.getFalse(),
321 Builder.getFalse(),
317322 "llvm.ctlz." + Name.substr(14)));
323 CI->eraseFromParent();
324 return;
325 }
326 case Intrinsic::ctpop: {
327 CI->replaceAllUsesWith(Builder.CreateCall(NewFn, CI->getArgOperand(0)));
318328 CI->eraseFromParent();
319329 return;
320330 }
0 ; RUN: llvm-as < %s | llvm-dis | FileCheck %s
1 ; NB: currently tests only vclz, should also test vcnt and vcls
1 ; Tests vclz and vcnt
22
33 define <4 x i16> @vclz16(<4 x i16>* %A) nounwind {
44 ;CHECK: @vclz16
88 ret <4 x i16> %tmp2
99 }
1010
11 define <8 x i8> @vcnt8(<8 x i8>* %A) nounwind {
12 ;CHECK: @vcnt8
13 %tmp1 = load <8 x i8>* %A
14 %tmp2 = call <8 x i8> @llvm.arm.neon.vcnt.v8i8(<8 x i8> %tmp1)
15 ;CHECK: call <8 x i8> @llvm.ctpop.v8i8(<8 x i8>
16 ret <8 x i8> %tmp2
17 }
18
1119 declare <4 x i16> @llvm.arm.neon.vclz.v4i16(<4 x i16>) nounwind readnone
20 declare <8 x i8> @llvm.arm.neon.vcnt.v8i8(<8 x i8>) nounwind readnone
22
33 define <8 x i8> @vcnt8(<8 x i8>* %A) nounwind {
44 ;CHECK: vcnt8:
5 ;CHECK: vcnt.8
5 ;CHECK: vcnt.8 {{d[0-9]+}}, {{d[0-9]+}}
66 %tmp1 = load <8 x i8>* %A
7 %tmp2 = call <8 x i8> @llvm.arm.neon.vcnt.v8i8(<8 x i8> %tmp1)
7 %tmp2 = call <8 x i8> @llvm.ctpop.v8i8(<8 x i8> %tmp1)
88 ret <8 x i8> %tmp2
99 }
1010
1111 define <16 x i8> @vcntQ8(<16 x i8>* %A) nounwind {
1212 ;CHECK: vcntQ8:
13 ;CHECK: vcnt.8
13 ;CHECK: vcnt.8 {{q[0-9]+}}, {{q[0-9]+}}
1414 %tmp1 = load <16 x i8>* %A
15 %tmp2 = call <16 x i8> @llvm.arm.neon.vcnt.v16i8(<16 x i8> %tmp1)
15 %tmp2 = call <16 x i8> @llvm.ctpop.v16i8(<16 x i8> %tmp1)
1616 ret <16 x i8> %tmp2
1717 }
1818
19 declare <8 x i8> @llvm.arm.neon.vcnt.v8i8(<8 x i8>) nounwind readnone
20 declare <16 x i8> @llvm.arm.neon.vcnt.v16i8(<16 x i8>) nounwind readnone
19 declare <8 x i8> @llvm.ctpop.v8i8(<8 x i8>) nounwind readnone
20 declare <16 x i8> @llvm.ctpop.v16i8(<16 x i8>) nounwind readnone
2121
2222 define <8 x i8> @vclz8(<8 x i8>* %A) nounwind {
2323 ;CHECK: vclz8: