1972a253aSDimitry Andric //===------- SEHFrameSupport.h - JITLink seh-frame utils --------*- C++ -*-===// 2972a253aSDimitry Andric // 3972a253aSDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4972a253aSDimitry Andric // See https://llvm.org/LICENSE.txt for license information. 5972a253aSDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6972a253aSDimitry Andric // 7972a253aSDimitry Andric //===----------------------------------------------------------------------===// 8972a253aSDimitry Andric // 9972a253aSDimitry Andric // SEHFrame utils for JITLink. 10972a253aSDimitry Andric // 11972a253aSDimitry Andric //===----------------------------------------------------------------------===// 12972a253aSDimitry Andric 13972a253aSDimitry Andric #ifndef LLVM_EXECUTIONENGINE_JITLINK_SEHFRAMESUPPORT_H 14972a253aSDimitry Andric #define LLVM_EXECUTIONENGINE_JITLINK_SEHFRAMESUPPORT_H 15972a253aSDimitry Andric 16*0fca6ea1SDimitry Andric #include "llvm/ADT/SetVector.h" 17972a253aSDimitry Andric #include "llvm/ExecutionEngine/JITLink/JITLink.h" 18972a253aSDimitry Andric #include "llvm/ExecutionEngine/JITSymbol.h" 19972a253aSDimitry Andric #include "llvm/Support/Error.h" 2006c3fb27SDimitry Andric #include "llvm/TargetParser/Triple.h" 21972a253aSDimitry Andric 22972a253aSDimitry Andric namespace llvm { 23972a253aSDimitry Andric namespace jitlink { 24972a253aSDimitry Andric /// This pass adds keep-alive edge from SEH frame sections 25972a253aSDimitry Andric /// to the parent function content block. 26972a253aSDimitry Andric class SEHFrameKeepAlivePass { 27972a253aSDimitry Andric public: 28972a253aSDimitry Andric SEHFrameKeepAlivePass(StringRef SEHFrameSectionName) 29972a253aSDimitry Andric : SEHFrameSectionName(SEHFrameSectionName) {} 30972a253aSDimitry Andric 31972a253aSDimitry Andric Error operator()(LinkGraph &G) { 32972a253aSDimitry Andric auto *S = G.findSectionByName(SEHFrameSectionName); 33972a253aSDimitry Andric if (!S) 34972a253aSDimitry Andric return Error::success(); 35972a253aSDimitry Andric 36972a253aSDimitry Andric // Simply consider every block pointed by seh frame block as parants. 37972a253aSDimitry Andric // This adds some unnecessary keep-alive edges to unwind info blocks, 38972a253aSDimitry Andric // (xdata) but these blocks are usually dead by default, so they wouldn't 39972a253aSDimitry Andric // count for the fate of seh frame block. 40972a253aSDimitry Andric for (auto *B : S->blocks()) { 41972a253aSDimitry Andric auto &DummySymbol = G.addAnonymousSymbol(*B, 0, 0, false, false); 42*0fca6ea1SDimitry Andric SetVector<Block *> Children; 43972a253aSDimitry Andric for (auto &E : B->edges()) { 44972a253aSDimitry Andric auto &Sym = E.getTarget(); 45972a253aSDimitry Andric if (!Sym.isDefined()) 46972a253aSDimitry Andric continue; 47972a253aSDimitry Andric Children.insert(&Sym.getBlock()); 48972a253aSDimitry Andric } 49972a253aSDimitry Andric for (auto *Child : Children) 50972a253aSDimitry Andric Child->addEdge(Edge(Edge::KeepAlive, 0, DummySymbol, 0)); 51972a253aSDimitry Andric } 52972a253aSDimitry Andric return Error::success(); 53972a253aSDimitry Andric } 54972a253aSDimitry Andric 55972a253aSDimitry Andric private: 56972a253aSDimitry Andric StringRef SEHFrameSectionName; 57972a253aSDimitry Andric }; 58972a253aSDimitry Andric 59972a253aSDimitry Andric } // end namespace jitlink 60972a253aSDimitry Andric } // end namespace llvm 61972a253aSDimitry Andric 62972a253aSDimitry Andric #endif // LLVM_EXECUTIONENGINE_JITLINK_SEHFRAMESUPPORT_H 63