diff options
Diffstat (limited to 'contrib/llvm-project/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp')
| -rw-r--r-- | contrib/llvm-project/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp | 409 | 
1 files changed, 340 insertions, 69 deletions
diff --git a/contrib/llvm-project/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp b/contrib/llvm-project/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp index bc84988e3254..7c7c2f000368 100644 --- a/contrib/llvm-project/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp +++ b/contrib/llvm-project/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp @@ -9,6 +9,11 @@  #include "llvm/ExecutionEngine/Orc/LLJIT.h"  #include "llvm/ExecutionEngine/JITLink/EHFrameSupport.h"  #include "llvm/ExecutionEngine/JITLink/JITLinkMemoryManager.h" +#include "llvm/ExecutionEngine/Orc/COFFPlatform.h" +#include "llvm/ExecutionEngine/Orc/DebugObjectManagerPlugin.h" +#include "llvm/ExecutionEngine/Orc/DebuggerSupportPlugin.h" +#include "llvm/ExecutionEngine/Orc/ELFNixPlatform.h" +#include "llvm/ExecutionEngine/Orc/EPCDynamicLibrarySearchGenerator.h"  #include "llvm/ExecutionEngine/Orc/EPCEHFrameRegistrar.h"  #include "llvm/ExecutionEngine/Orc/ExecutorProcessControl.h"  #include "llvm/ExecutionEngine/Orc/MachOPlatform.h" @@ -98,10 +103,16 @@ public:        ORC_RT_RTLD_GLOBAL = 0x8      }; -    if (auto WrapperAddr = J.lookup("__orc_rt_jit_dlopen_wrapper")) { -      return J.getExecutionSession().callSPSWrapper<SPSDLOpenSig>( -          *WrapperAddr, DSOHandles[&JD], JD.getName(), -          int32_t(ORC_RT_RTLD_LAZY)); +    auto &ES = J.getExecutionSession(); +    auto MainSearchOrder = J.getMainJITDylib().withLinkOrderDo( +        [](const JITDylibSearchOrder &SO) { return SO; }); + +    if (auto WrapperAddr = +            ES.lookup(MainSearchOrder, +                      J.mangleAndIntern("__orc_rt_jit_dlopen_wrapper"))) { +      return ES.callSPSWrapper<SPSDLOpenSig>(WrapperAddr->getAddress(), +                                             DSOHandles[&JD], JD.getName(), +                                             int32_t(ORC_RT_RTLD_LAZY));      } else        return WrapperAddr.takeError();    } @@ -110,10 +121,16 @@ public:      using llvm::orc::shared::SPSExecutorAddr;      using SPSDLCloseSig = int32_t(SPSExecutorAddr); -    if (auto WrapperAddr = J.lookup("__orc_rt_jit_dlclose_wrapper")) { +    auto &ES = J.getExecutionSession(); +    auto MainSearchOrder = J.getMainJITDylib().withLinkOrderDo( +        [](const JITDylibSearchOrder &SO) { return SO; }); + +    if (auto WrapperAddr = +            ES.lookup(MainSearchOrder, +                      J.mangleAndIntern("__orc_rt_jit_dlclose_wrapper"))) {        int32_t result;        auto E = J.getExecutionSession().callSPSWrapper<SPSDLCloseSig>( -          *WrapperAddr, result, DSOHandles[&JD]); +          WrapperAddr->getAddress(), result, DSOHandles[&JD]);        if (E)          return E;        else if (result) @@ -176,7 +193,7 @@ private:  /// some runtime API, including __cxa_atexit, dlopen, and dlclose.  class GenericLLVMIRPlatformSupport : public LLJIT::PlatformSupport {  public: -  GenericLLVMIRPlatformSupport(LLJIT &J) +  GenericLLVMIRPlatformSupport(LLJIT &J, JITDylib &PlatformJD)        : J(J), InitFunctionPrefix(J.mangle("__orc_init_func.")),          DeInitFunctionPrefix(J.mangle("__orc_deinit_func.")) { @@ -188,17 +205,14 @@ public:      SymbolMap StdInterposes; -    StdInterposes[J.mangleAndIntern("__lljit.platform_support_instance")] = -        JITEvaluatedSymbol(pointerToJITTargetAddress(this), -                           JITSymbolFlags::Exported); -    StdInterposes[J.mangleAndIntern("__lljit.cxa_atexit_helper")] = -        JITEvaluatedSymbol(pointerToJITTargetAddress(registerCxaAtExitHelper), -                           JITSymbolFlags()); - -    cantFail( -        J.getMainJITDylib().define(absoluteSymbols(std::move(StdInterposes)))); -    cantFail(setupJITDylib(J.getMainJITDylib())); -    cantFail(J.addIRModule(J.getMainJITDylib(), createPlatformRuntimeModule())); +    StdInterposes[J.mangleAndIntern("__lljit.platform_support_instance")] = { +        ExecutorAddr::fromPtr(this), JITSymbolFlags::Exported}; +    StdInterposes[J.mangleAndIntern("__lljit.cxa_atexit_helper")] = { +        ExecutorAddr::fromPtr(registerCxaAtExitHelper), JITSymbolFlags()}; + +    cantFail(PlatformJD.define(absoluteSymbols(std::move(StdInterposes)))); +    cantFail(setupJITDylib(PlatformJD)); +    cantFail(J.addIRModule(PlatformJD, createPlatformRuntimeModule()));    }    ExecutionSession &getExecutionSession() { return J.getExecutionSession(); } @@ -208,12 +222,10 @@ public:      // Add per-jitdylib standard interposes.      SymbolMap PerJDInterposes; -    PerJDInterposes[J.mangleAndIntern("__lljit.run_atexits_helper")] = -        JITEvaluatedSymbol(pointerToJITTargetAddress(runAtExitsHelper), -                           JITSymbolFlags()); -    PerJDInterposes[J.mangleAndIntern("__lljit.atexit_helper")] = -        JITEvaluatedSymbol(pointerToJITTargetAddress(registerAtExitHelper), -                           JITSymbolFlags()); +    PerJDInterposes[J.mangleAndIntern("__lljit.run_atexits_helper")] = { +        ExecutorAddr::fromPtr(runAtExitsHelper), JITSymbolFlags()}; +    PerJDInterposes[J.mangleAndIntern("__lljit.atexit_helper")] = { +        ExecutorAddr::fromPtr(registerAtExitHelper), JITSymbolFlags()};      cantFail(JD.define(absoluteSymbols(std::move(PerJDInterposes))));      auto Ctx = std::make_unique<LLVMContext>(); @@ -227,7 +239,7 @@ public:          "__dso_handle");      DSOHandle->setVisibility(GlobalValue::DefaultVisibility);      DSOHandle->setInitializer( -        ConstantInt::get(Int64Ty, pointerToJITTargetAddress(&JD))); +        ConstantInt::get(Int64Ty, ExecutorAddr::fromPtr(&JD).getValue()));      auto *GenericIRPlatformSupportTy =          StructType::create(*Ctx, "lljit.GenericLLJITIRPlatformSupport"); @@ -287,7 +299,7 @@ public:            dbgs() << "  Running init " << formatv("{0:x16}", InitFnAddr)                   << "...\n";          }); -        auto *InitFn = jitTargetAddressToFunction<void (*)()>(InitFnAddr); +        auto *InitFn = InitFnAddr.toPtr<void (*)()>();          InitFn();        }      } else @@ -308,7 +320,7 @@ public:            dbgs() << "  Running deinit " << formatv("{0:x16}", DeinitFnAddr)                   << "...\n";          }); -        auto *DeinitFn = jitTargetAddressToFunction<void (*)()>(DeinitFnAddr); +        auto *DeinitFn = DeinitFnAddr.toPtr<void (*)()>();          DeinitFn();        }      } else @@ -329,8 +341,7 @@ public:    }  private: - -  Expected<std::vector<JITTargetAddress>> getInitializers(JITDylib &JD) { +  Expected<std::vector<ExecutorAddr>> getInitializers(JITDylib &JD) {      if (auto Err = issueInitLookups(JD))        return std::move(Err); @@ -370,7 +381,7 @@ private:      if (!LookupResult)        return LookupResult.takeError(); -    std::vector<JITTargetAddress> Initializers; +    std::vector<ExecutorAddr> Initializers;      while (!DFSLinkOrder.empty()) {        auto &NextJD = *DFSLinkOrder.back();        DFSLinkOrder.pop_back(); @@ -384,7 +395,7 @@ private:      return Initializers;    } -  Expected<std::vector<JITTargetAddress>> getDeinitializers(JITDylib &JD) { +  Expected<std::vector<ExecutorAddr>> getDeinitializers(JITDylib &JD) {      auto &ES = getExecutionSession();      auto LLJITRunAtExits = J.mangleAndIntern("__lljit_run_atexits"); @@ -427,7 +438,7 @@ private:      if (!LookupResult)        return LookupResult.takeError(); -    std::vector<JITTargetAddress> DeInitializers; +    std::vector<ExecutorAddr> DeInitializers;      for (auto &NextJD : DFSLinkOrder) {        auto DeInitsItr = LookupResult->find(NextJD.get());        assert(DeInitsItr != LookupResult->end() && @@ -695,6 +706,14 @@ Error LLJITBuilderState::prepareForConstruction() {        dbgs() << "\n";    }); +  // Create DL if not specified. +  if (!DL) { +    if (auto DLOrErr = JTMB->getDefaultDataLayoutForTarget()) +      DL = std::move(*DLOrErr); +    else +      return DLOrErr.takeError(); +  } +    // If neither ES nor EPC has been set then create an EPC instance.    if (!ES && !EPC) {      LLVM_DEBUG({ @@ -705,21 +724,38 @@ Error LLJITBuilderState::prepareForConstruction() {        EPC = std::move(*EPCOrErr);      else        return EPCOrErr.takeError(); -  } else +  } else if (EPC) {      LLVM_DEBUG({        dbgs() << "Using explicitly specified ExecutorProcessControl instance "               << EPC.get() << "\n";      }); +  } else { +    LLVM_DEBUG({ +      dbgs() << "Using explicitly specified ExecutionSession instance " +             << ES.get() << "\n"; +    }); +  }    // If the client didn't configure any linker options then auto-configure the    // JIT linker.    if (!CreateObjectLinkingLayer) {      auto &TT = JTMB->getTargetTriple(); -    if (TT.getArch() == Triple::riscv64 || -        TT.getArch() == Triple::loongarch64 || -        (TT.isOSBinFormatMachO() && -         (TT.getArch() == Triple::aarch64 || TT.getArch() == Triple::x86_64))) { - +    bool UseJITLink = false; +    switch (TT.getArch()) { +    case Triple::riscv64: +    case Triple::loongarch64: +      UseJITLink = true; +      break; +    case Triple::aarch64: +      UseJITLink = !TT.isOSBinFormatCOFF(); +      break; +    case Triple::x86_64: +      UseJITLink = !TT.isOSBinFormatCOFF(); +      break; +    default: +      break; +    } +    if (UseJITLink) {        JTMB->setRelocationModel(Reloc::PIC_);        JTMB->setCodeModel(CodeModel::Small);        CreateObjectLinkingLayer = @@ -737,6 +773,30 @@ Error LLJITBuilderState::prepareForConstruction() {      }    } +  // If we need a process JITDylib but no setup function has been given then +  // create a default one. +  if (!SetupProcessSymbolsJITDylib && +      (LinkProcessSymbolsByDefault || EnableDebuggerSupport)) { + +    LLVM_DEBUG({ +      dbgs() << "Creating default Process JD setup function (neeeded for"; +      if (LinkProcessSymbolsByDefault) +        dbgs() << " <link-process-syms-by-default>"; +      if (EnableDebuggerSupport) +        dbgs() << " <debugger-support>"; +      dbgs() << ")\n"; +    }); + +    SetupProcessSymbolsJITDylib = [this](JITDylib &JD) -> Error { +      auto G = orc::DynamicLibrarySearchGenerator::GetForCurrentProcess( +          DL->getGlobalPrefix()); +      if (!G) +        return G.takeError(); +      JD.addGenerator(std::move(*G)); +      return Error::success(); +    }; +  } +    return Error::success();  } @@ -747,6 +807,54 @@ LLJIT::~LLJIT() {      ES->reportError(std::move(Err));  } +JITDylibSP LLJIT::getProcessSymbolsJITDylib() { return ProcessSymbols; } + +JITDylibSP LLJIT::getPlatformJITDylib() { return Platform; } + +Expected<JITDylib &> LLJIT::createJITDylib(std::string Name) { +  auto JD = ES->createJITDylib(std::move(Name)); +  if (!JD) +    return JD.takeError(); + +  JD->addToLinkOrder(DefaultLinks); +  return JD; +} + +Expected<JITDylib &> LLJIT::loadPlatformDynamicLibrary(const char *Path) { +  auto G = EPCDynamicLibrarySearchGenerator::Load(*ES, Path); +  if (!G) +    return G.takeError(); + +  if (auto *ExistingJD = ES->getJITDylibByName(Path)) +    return *ExistingJD; + +  auto &JD = ES->createBareJITDylib(Path); +  JD.addGenerator(std::move(*G)); +  return JD; +} + +Error LLJIT::linkStaticLibraryInto(JITDylib &JD, +                                   std::unique_ptr<MemoryBuffer> LibBuffer) { +  auto G = StaticLibraryDefinitionGenerator::Create(*ObjLinkingLayer, +                                                    std::move(LibBuffer)); +  if (!G) +    return G.takeError(); + +  JD.addGenerator(std::move(*G)); + +  return Error::success(); +} + +Error LLJIT::linkStaticLibraryInto(JITDylib &JD, const char *Path) { +  auto G = StaticLibraryDefinitionGenerator::Load(*ObjLinkingLayer, Path); +  if (!G) +    return G.takeError(); + +  JD.addGenerator(std::move(*G)); + +  return Error::success(); +} +  Error LLJIT::addIRModule(ResourceTrackerSP RT, ThreadSafeModule TSM) {    assert(TSM && "Can not add null module"); @@ -777,7 +885,7 @@ Expected<ExecutorAddr> LLJIT::lookupLinkerMangled(JITDylib &JD,    if (auto Sym = ES->lookup(          makeJITDylibSearchOrder(&JD, JITDylibLookupFlags::MatchAllSymbols),          Name)) -    return ExecutorAddr(Sym->getAddress()); +    return Sym->getAddress();    else      return Sym.takeError();  } @@ -832,7 +940,7 @@ LLJIT::createCompileFunction(LLJITBuilderState &S,  }  LLJIT::LLJIT(LLJITBuilderState &S, Error &Err) -    : DL(""), TT(S.JTMB->getTargetTriple()) { +    : DL(std::move(*S.DL)), TT(S.JTMB->getTargetTriple()) {    ErrorAsOutParameter _(&Err); @@ -851,22 +959,6 @@ LLJIT::LLJIT(LLJITBuilderState &S, Error &Err)      }    } -  if (auto MainOrErr = this->ES->createJITDylib("main")) -    Main = &*MainOrErr; -  else { -    Err = MainOrErr.takeError(); -    return; -  } - -  if (S.DL) -    DL = std::move(*S.DL); -  else if (auto DLOrErr = S.JTMB->getDefaultDataLayoutForTarget()) -    DL = std::move(*DLOrErr); -  else { -    Err = DLOrErr.takeError(); -    return; -  } -    auto ObjLayer = createObjectLinkingLayer(S, *ES);    if (!ObjLayer) {      Err = ObjLayer.takeError(); @@ -905,10 +997,77 @@ LLJIT::LLJIT(LLJITBuilderState &S, Error &Err)      });    } -  if (S.SetUpPlatform) -    Err = S.SetUpPlatform(*this); -  else -    setUpGenericLLVMIRPlatform(*this); +  if (S.SetupProcessSymbolsJITDylib) { +    ProcessSymbols = &ES->createBareJITDylib("<Process Symbols>"); +    if (auto Err2 = S.SetupProcessSymbolsJITDylib(*ProcessSymbols)) { +      Err = std::move(Err2); +      return; +    } +  } + +  if (S.EnableDebuggerSupport) { +    if (auto *OLL = dyn_cast<ObjectLinkingLayer>(ObjLinkingLayer.get())) { +      switch (TT.getObjectFormat()) { +      case Triple::ELF: { +        auto Registrar = createJITLoaderGDBRegistrar(*ES); +        if (!Registrar) { +          Err = Registrar.takeError(); +          return; +        } +        OLL->addPlugin(std::make_unique<DebugObjectManagerPlugin>( +            *ES, std::move(*Registrar), true, true)); +        break; +      } +      case Triple::MachO: { +        assert(ProcessSymbols && "ProcessSymbols JD should be available when " +                                 "EnableDebuggerSupport is set"); +        auto DS = +            GDBJITDebugInfoRegistrationPlugin::Create(*ES, *ProcessSymbols, TT); +        if (!DS) { +          Err = DS.takeError(); +          return; +        } +        OLL->addPlugin(std::move(*DS)); +        break; +      } +      default: +        LLVM_DEBUG({ +          dbgs() << "Cannot enable LLJIT debugger support: " +                 << Triple::getObjectFormatTypeName(TT.getObjectFormat()) +                 << " not supported.\n"; +        }); +      } +    } else { +      LLVM_DEBUG({ +        dbgs() << "Cannot enable LLJIT debugger support: " +                  " debugger support is only available when using JITLink.\n"; +      }); +    } +  } + +  if (!S.SetUpPlatform) +    S.SetUpPlatform = setUpGenericLLVMIRPlatform; + +  if (auto PlatformJDOrErr = S.SetUpPlatform(*this)) { +    Platform = PlatformJDOrErr->get(); +    if (Platform) +      DefaultLinks.push_back( +          {Platform, JITDylibLookupFlags::MatchExportedSymbolsOnly}); +  } else { +    Err = PlatformJDOrErr.takeError(); +    return; +  } + +  if (S.LinkProcessSymbolsByDefault) +    DefaultLinks.push_back( +        {ProcessSymbols, JITDylibLookupFlags::MatchExportedSymbolsOnly}); + +  if (auto MainOrErr = createJITDylib("main")) +    Main = &*MainOrErr; +  else { +    Err = MainOrErr.takeError(); +    return; +  }  }  std::string LLJIT::mangle(StringRef UnmangledName) const { @@ -934,24 +1093,136 @@ Error LLJIT::applyDataLayout(Module &M) {    return Error::success();  } -Error setUpOrcPlatform(LLJIT& J) { -    LLVM_DEBUG( -        { dbgs() << "Setting up orc platform support for LLJIT\n"; }); -    J.setPlatformSupport(std::make_unique<ORCPlatformSupport>(J)); +Error setUpOrcPlatformManually(LLJIT &J) { +  LLVM_DEBUG({ dbgs() << "Setting up orc platform support for LLJIT\n"; }); +  J.setPlatformSupport(std::make_unique<ORCPlatformSupport>(J)); +  return Error::success(); +} + +class LoadAndLinkDynLibrary { +public: +  LoadAndLinkDynLibrary(LLJIT &J) : J(J) {} +  Error operator()(JITDylib &JD, StringRef DLLName) { +    if (!DLLName.ends_with_insensitive(".dll")) +      return make_error<StringError>("DLLName not ending with .dll", +                                     inconvertibleErrorCode()); +    auto DLLNameStr = DLLName.str(); // Guarantees null-termination. +    auto DLLJD = J.loadPlatformDynamicLibrary(DLLNameStr.c_str()); +    if (!DLLJD) +      return DLLJD.takeError(); +    JD.addToLinkOrder(*DLLJD);      return Error::success(); +  } + +private: +  LLJIT &J; +}; + +Expected<JITDylibSP> ExecutorNativePlatform::operator()(LLJIT &J) { +  auto ProcessSymbolsJD = J.getProcessSymbolsJITDylib(); +  if (!ProcessSymbolsJD) +    return make_error<StringError>( +        "Native platforms require a process symbols JITDylib", +        inconvertibleErrorCode()); + +  const Triple &TT = J.getTargetTriple(); +  ObjectLinkingLayer *ObjLinkingLayer = +      dyn_cast<ObjectLinkingLayer>(&J.getObjLinkingLayer()); + +  if (!ObjLinkingLayer) +    return make_error<StringError>( +        "SetUpTargetPlatform requires ObjectLinkingLayer", +        inconvertibleErrorCode()); + +  std::unique_ptr<MemoryBuffer> RuntimeArchiveBuffer; +  if (OrcRuntime.index() == 0) { +    auto A = errorOrToExpected(MemoryBuffer::getFile(std::get<0>(OrcRuntime))); +    if (!A) +      return A.takeError(); +    RuntimeArchiveBuffer = std::move(*A); +  } else +    RuntimeArchiveBuffer = std::move(std::get<1>(OrcRuntime)); + +  auto &ES = J.getExecutionSession(); +  auto &PlatformJD = ES.createBareJITDylib("<Platform>"); +  PlatformJD.addToLinkOrder(*ProcessSymbolsJD); + +  J.setPlatformSupport(std::make_unique<ORCPlatformSupport>(J)); + +  switch (TT.getObjectFormat()) { +  case Triple::COFF: { +    const char *VCRuntimePath = nullptr; +    bool StaticVCRuntime = false; +    if (VCRuntime) { +      VCRuntimePath = VCRuntime->first.c_str(); +      StaticVCRuntime = VCRuntime->second; +    } +    if (auto P = COFFPlatform::Create( +            ES, *ObjLinkingLayer, PlatformJD, std::move(RuntimeArchiveBuffer), +            LoadAndLinkDynLibrary(J), StaticVCRuntime, VCRuntimePath)) +      J.getExecutionSession().setPlatform(std::move(*P)); +    else +      return P.takeError(); +    break; +  } +  case Triple::ELF: { +    auto G = StaticLibraryDefinitionGenerator::Create( +        *ObjLinkingLayer, std::move(RuntimeArchiveBuffer)); +    if (!G) +      return G.takeError(); + +    if (auto P = ELFNixPlatform::Create(ES, *ObjLinkingLayer, PlatformJD, +                                        std::move(*G))) +      J.getExecutionSession().setPlatform(std::move(*P)); +    else +      return P.takeError(); +    break; +  } +  case Triple::MachO: { +    auto G = StaticLibraryDefinitionGenerator::Create( +        *ObjLinkingLayer, std::move(RuntimeArchiveBuffer)); +    if (!G) +      return G.takeError(); + +    if (auto P = MachOPlatform::Create(ES, *ObjLinkingLayer, PlatformJD, +                                       std::move(*G))) +      ES.setPlatform(std::move(*P)); +    else +      return P.takeError(); +    break; +  } +  default: +    return make_error<StringError>("Unsupported object format in triple " + +                                       TT.str(), +                                   inconvertibleErrorCode()); +  } + +  return &PlatformJD;  } -void setUpGenericLLVMIRPlatform(LLJIT &J) { +Expected<JITDylibSP> setUpGenericLLVMIRPlatform(LLJIT &J) {    LLVM_DEBUG(        { dbgs() << "Setting up GenericLLVMIRPlatform support for LLJIT\n"; }); -  J.setPlatformSupport(std::make_unique<GenericLLVMIRPlatformSupport>(J)); +  auto ProcessSymbolsJD = J.getProcessSymbolsJITDylib(); +  if (!ProcessSymbolsJD) +    return make_error<StringError>( +        "Native platforms require a process symbols JITDylib", +        inconvertibleErrorCode()); + +  auto &PlatformJD = J.getExecutionSession().createBareJITDylib("<Platform>"); +  PlatformJD.addToLinkOrder(*ProcessSymbolsJD); + +  J.setPlatformSupport( +      std::make_unique<GenericLLVMIRPlatformSupport>(J, PlatformJD)); + +  return &PlatformJD;  } -Error setUpInactivePlatform(LLJIT &J) { +Expected<JITDylibSP> setUpInactivePlatform(LLJIT &J) {    LLVM_DEBUG(        { dbgs() << "Explicitly deactivated platform support for LLJIT\n"; });    J.setPlatformSupport(std::make_unique<InactivePlatformSupport>()); -  return Error::success(); +  return nullptr;  }  Error LLLazyJITBuilderState::prepareForConstruction() { @@ -984,7 +1255,7 @@ LLLazyJIT::LLLazyJIT(LLLazyJITBuilderState &S, Error &Err) : LLJIT(S, Err) {      LCTMgr = std::move(S.LCTMgr);    else {      if (auto LCTMgrOrErr = createLocalLazyCallThroughManager( -        S.TT, *ES, S.LazyCompileFailureAddr.getValue())) +            S.TT, *ES, S.LazyCompileFailureAddr))        LCTMgr = std::move(*LCTMgrOrErr);      else {        Err = LCTMgrOrErr.takeError();  | 
