1 //===-- PlatformRemoteMacOSX.cpp -------------------------------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 #include <memory> 10 #include <string> 11 #include <vector> 12 13 #include "PlatformRemoteMacOSX.h" 14 15 #include "lldb/Breakpoint/BreakpointLocation.h" 16 #include "lldb/Core/Module.h" 17 #include "lldb/Core/ModuleList.h" 18 #include "lldb/Core/ModuleSpec.h" 19 #include "lldb/Core/PluginManager.h" 20 #include "lldb/Host/Host.h" 21 #include "lldb/Host/HostInfo.h" 22 #include "lldb/Target/Process.h" 23 #include "lldb/Target/Target.h" 24 #include "lldb/Utility/ArchSpec.h" 25 #include "lldb/Utility/FileSpec.h" 26 #include "lldb/Utility/LLDBLog.h" 27 #include "lldb/Utility/Log.h" 28 #include "lldb/Utility/StreamString.h" 29 30 using namespace lldb; 31 using namespace lldb_private; 32 33 /// Default Constructor 34 PlatformRemoteMacOSX::PlatformRemoteMacOSX() : PlatformRemoteDarwinDevice() {} 35 36 // Static Variables 37 static uint32_t g_initialize_count = 0; 38 39 // Static Functions 40 void PlatformRemoteMacOSX::Initialize() { 41 PlatformDarwin::Initialize(); 42 43 if (g_initialize_count++ == 0) { 44 PluginManager::RegisterPlugin(PlatformRemoteMacOSX::GetPluginNameStatic(), 45 PlatformRemoteMacOSX::GetDescriptionStatic(), 46 PlatformRemoteMacOSX::CreateInstance); 47 } 48 } 49 50 void PlatformRemoteMacOSX::Terminate() { 51 if (g_initialize_count > 0) { 52 if (--g_initialize_count == 0) { 53 PluginManager::UnregisterPlugin(PlatformRemoteMacOSX::CreateInstance); 54 } 55 } 56 57 PlatformDarwin::Terminate(); 58 } 59 60 PlatformSP PlatformRemoteMacOSX::CreateInstance(bool force, 61 const ArchSpec *arch) { 62 Log *log = GetLog(LLDBLog::Platform); 63 if (log) { 64 const char *arch_name; 65 if (arch && arch->GetArchitectureName()) 66 arch_name = arch->GetArchitectureName(); 67 else 68 arch_name = "<null>"; 69 70 const char *triple_cstr = 71 arch ? arch->GetTriple().getTriple().c_str() : "<null>"; 72 73 LLDB_LOGF(log, "PlatformMacOSX::%s(force=%s, arch={%s,%s})", __FUNCTION__, 74 force ? "true" : "false", arch_name, triple_cstr); 75 } 76 77 bool create = force; 78 if (!create && arch && arch->IsValid()) { 79 const llvm::Triple &triple = arch->GetTriple(); 80 switch (triple.getVendor()) { 81 case llvm::Triple::Apple: 82 create = true; 83 break; 84 85 #if defined(__APPLE__) 86 // Only accept "unknown" for vendor if the host is Apple and it "unknown" 87 // wasn't specified (it was just returned because it was NOT specified) 88 case llvm::Triple::UnknownVendor: 89 create = !arch->TripleVendorWasSpecified(); 90 break; 91 #endif 92 default: 93 break; 94 } 95 96 if (create) { 97 switch (triple.getOS()) { 98 case llvm::Triple::Darwin: // Deprecated, but still support Darwin for 99 // historical reasons 100 case llvm::Triple::MacOSX: 101 break; 102 #if defined(__APPLE__) 103 // Only accept "vendor" for vendor if the host is Apple and it "unknown" 104 // wasn't specified (it was just returned because it was NOT specified) 105 case llvm::Triple::UnknownOS: 106 create = !arch->TripleOSWasSpecified(); 107 break; 108 #endif 109 default: 110 create = false; 111 break; 112 } 113 } 114 } 115 116 if (create) { 117 LLDB_LOGF(log, "PlatformRemoteMacOSX::%s() creating platform", 118 __FUNCTION__); 119 return std::make_shared<PlatformRemoteMacOSX>(); 120 } 121 122 LLDB_LOGF(log, "PlatformRemoteMacOSX::%s() aborting creation of platform", 123 __FUNCTION__); 124 125 return PlatformSP(); 126 } 127 128 std::vector<ArchSpec> PlatformRemoteMacOSX::GetSupportedArchitectures() { 129 // macOS for ARM64 support both native and translated x86_64 processes 130 std::vector<ArchSpec> result; 131 ARMGetSupportedArchitectures(result, llvm::Triple::MacOSX); 132 133 // We can't use x86GetSupportedArchitectures() because it uses 134 // the system architecture for some of its return values and also 135 // has a 32bits variant. 136 result.push_back(ArchSpec("x86_64-apple-macosx")); 137 result.push_back(ArchSpec("x86_64-apple-ios-macabi")); 138 result.push_back(ArchSpec("arm64-apple-ios")); 139 result.push_back(ArchSpec("arm64e-apple-ios")); 140 return result; 141 } 142 143 lldb_private::Status PlatformRemoteMacOSX::GetFileWithUUID( 144 const lldb_private::FileSpec &platform_file, 145 const lldb_private::UUID *uuid_ptr, lldb_private::FileSpec &local_file) { 146 if (m_remote_platform_sp) { 147 std::string local_os_build; 148 #if !defined(__linux__) 149 local_os_build = HostInfo::GetOSBuildString().getValueOr(""); 150 #endif 151 llvm::Optional<std::string> remote_os_build = 152 m_remote_platform_sp->GetOSBuildString(); 153 if (local_os_build == remote_os_build) { 154 // same OS version: the local file is good enough 155 local_file = platform_file; 156 return Status(); 157 } else { 158 // try to find the file in the cache 159 std::string cache_path(GetLocalCacheDirectory()); 160 std::string module_path(platform_file.GetPath()); 161 cache_path.append(module_path); 162 FileSpec module_cache_spec(cache_path); 163 if (FileSystem::Instance().Exists(module_cache_spec)) { 164 local_file = module_cache_spec; 165 return Status(); 166 } 167 // bring in the remote module file 168 FileSpec module_cache_folder = 169 module_cache_spec.CopyByRemovingLastPathComponent(); 170 // try to make the local directory first 171 Status err( 172 llvm::sys::fs::create_directory(module_cache_folder.GetPath())); 173 if (err.Fail()) 174 return err; 175 err = GetFile(platform_file, module_cache_spec); 176 if (err.Fail()) 177 return err; 178 if (FileSystem::Instance().Exists(module_cache_spec)) { 179 local_file = module_cache_spec; 180 return Status(); 181 } else 182 return Status("unable to obtain valid module file"); 183 } 184 } 185 local_file = platform_file; 186 return Status(); 187 } 188 189 llvm::StringRef PlatformRemoteMacOSX::GetDescriptionStatic() { 190 return "Remote Mac OS X user platform plug-in."; 191 } 192 193 llvm::StringRef PlatformRemoteMacOSX::GetDeviceSupportDirectoryName() { 194 return "macOS DeviceSupport"; 195 } 196 197 llvm::StringRef PlatformRemoteMacOSX::GetPlatformName() { 198 return "MacOSX.platform"; 199 } 200