@@ -834,6 +834,42 @@ class ModuleSplitter {
834
834
size_t totalSplits () { return GMap.size (); }
835
835
};
836
836
837
+ // Removes the global variable "llvm.used" and returns true on success.
838
+ // "llvm.used" is a global constant array containing references to kernels
839
+ // available in the module and callable from host code. The elements of
840
+ // the array are ConstantExpr bitcast to i8*.
841
+ // The variable must be removed as it is a) has done the job to the moment
842
+ // of this function call and b) the references to the kernels callable from
843
+ // host must not have users.
844
+ static bool removeSYCLKernelsConstRefArray (GlobalVariable *GV) {
845
+ assert (GV->getGlobalIdentifier () == " llvm.used" &&
846
+ " Unexpected global value is passed for removal, should be llvm.used" );
847
+ assert (GV->user_empty () && " Unexpected llvm.used users" );
848
+ Constant *Initializer = GV->getInitializer ();
849
+ GV->setInitializer (nullptr );
850
+ GV->eraseFromParent ();
851
+
852
+ // Destroy the initializer and all operands of it.
853
+ SmallVector<Constant *, 8 > IOperands;
854
+ for (auto It = Initializer->op_begin (); It != Initializer->op_end (); It++) {
855
+ assert (isa<Constant>(*It) && " Unexpected initializer of llvm.used" );
856
+ IOperands.push_back (dyn_cast<Constant>(*It));
857
+ }
858
+ assert (llvm::isSafeToDestroyConstant (Initializer) &&
859
+ " Cannot remove initializer of llvm.used global" );
860
+ Initializer->destroyConstant ();
861
+ for (auto It = IOperands.begin (); It != IOperands.end (); It++) {
862
+ assert (llvm::isSafeToDestroyConstant (*It) &&
863
+ " Cannot remove an element of initializer of llvm.used global" );
864
+ auto F = cast<Function>((*It)->getOperand (0 ));
865
+ (*It)->destroyConstant ();
866
+ // Remove unused kernel declarations to avoid LLVM IR check fails.
867
+ if (F->isDeclaration ())
868
+ F->eraseFromParent ();
869
+ }
870
+ return true ;
871
+ }
872
+
837
873
using TableFiles = std::map<StringRef, string_vector>;
838
874
839
875
TableFiles processOneModule (std::unique_ptr<Module> M, bool IsEsimd,
@@ -850,33 +886,8 @@ TableFiles processOneModule(std::unique_ptr<Module> M, bool IsEsimd,
850
886
// issue remove "llvm.used" from the input module before performing any other
851
887
// actions.
852
888
bool IsLLVMUsedRemoved = false ;
853
- if (GlobalVariable *GV = M->getGlobalVariable (" llvm.used" )) {
854
- assert (GV->user_empty () && " unexpected llvm.used users" );
855
- Constant *Initializer = GV->getInitializer ();
856
- GV->setInitializer (nullptr );
857
- GV->eraseFromParent ();
858
-
859
- // Destroy the initializer and all operands of it.
860
- SmallVector<Constant *, 8 > IOperands;
861
- for (auto It = Initializer->op_begin (); It != Initializer->op_end (); It++) {
862
- assert (isa<Constant>(*It) && " Unexpected initializer of llvm.used" );
863
- IOperands.push_back (dyn_cast<Constant>(*It));
864
- }
865
- assert (llvm::isSafeToDestroyConstant (Initializer) &&
866
- " Cannot remove initializer of llvm.used global" );
867
- Initializer->destroyConstant ();
868
- for (auto It = IOperands.begin (); It != IOperands.end (); It++) {
869
- assert (llvm::isSafeToDestroyConstant (*It) &&
870
- " Cannot remove an element of initializer of llvm.used global" );
871
- auto F = dyn_cast<Function>((*It)->getOperand (0 ));
872
- (*It)->destroyConstant ();
873
- // Remove unused kernel declarations to avoid LLVM IR check fails.
874
- if (F->isDeclaration ())
875
- F->eraseFromParent ();
876
- }
877
-
878
- IsLLVMUsedRemoved = true ;
879
- }
889
+ if (GlobalVariable *GV = M->getGlobalVariable (" llvm.used" ))
890
+ IsLLVMUsedRemoved = removeSYCLKernelsConstRefArray (GV);
880
891
881
892
if (IsEsimd && LowerEsimd)
882
893
lowerEsimdConstructs (*M);
0 commit comments