+
+template <typename FunTy, typename InstructionTy, typename ValueTy,
+ typename CallSiteTy>
+std::vector<GCRelocateOperands>
+StatepointBase<FunTy, InstructionTy, ValueTy, CallSiteTy>::getRelocates()
+ const {
+
+ std::vector<GCRelocateOperands> Result;
+
+ CallSiteTy StatepointCS = getCallSite();
+
+ // Search for relocated pointers. Note that working backwards from the
+ // gc_relocates ensures that we only get pairs which are actually relocated
+ // and used after the statepoint.
+ for (const User *U : getInstruction()->users())
+ if (isGCRelocate(U))
+ Result.push_back(GCRelocateOperands(U));
+
+ if (!StatepointCS.isInvoke())
+ return Result;
+
+ // We need to scan thorough exceptional relocations if it is invoke statepoint
+ LandingPadInst *LandingPad =
+ cast<InvokeInst>(getInstruction())->getLandingPadInst();
+
+ // Search for extract value from landingpad instruction to which
+ // gc relocates will be attached
+ for (const User *LandingPadUser : LandingPad->users()) {
+ if (!isa<ExtractValueInst>(LandingPadUser))
+ continue;
+
+ // gc relocates should be attached to this extract value
+ for (const User *U : LandingPadUser->users())
+ if (isGCRelocate(U))
+ Result.push_back(GCRelocateOperands(U));
+ }
+ return Result;